Thread 中讨论的其他器件:controlSUITE
工具/软件:Code Composer Studio
这是我从 ti controlSUITE 上的 EPWM_ADC.c 和 dma_transfer.c 中更改的 ADC+DMA。 以前使用的 controlSUITE 新 ADC+DMA.c 已长时间更改、无法满足要求、这是对连续采样的单次更改、在完全缺少数据后更改为连续采样、正弦图像不完整、然后我自己在 EPWM_ADC 上更改。 在数据从 AdcResults []传递到 RDATA []后、通过 DmaRegs.ch1.control.bit.PERINTFRC=1直接在 ADC 中断中或软件触发 DMA 的循环中、我希望通过一轮采样来完成该程序。 然而,这似乎没有效果。 目前只有 AdcaResults 有正确的数据。 RDATA、全为0、我看到 dma_transfer.c 正在这样做、我似乎没有找到缺失的器件、所以我觉得很愚蠢、不知道如何参与、下面是我更改的一些代码、感谢您的回复。
//######################################################################################################################
//
//文件: adc_soc_ePWM_cpu01.c
//
//标题: 针对 F2837xD 通过 ePWM 触发 ADC。
//
//! addtogroup cpu01_example_list
//!
ADC ePWM 触发(ADC_SoC_ePWM)
//!
//! 此示例设置 EPWM 以定期触发 ADC。
//!
//! 程序运行后,内存将包含:\n
//! -\b 结果:一系列的模数转换样本
//! 引脚 A0。 采样之间的时间根据周期确定
//! PWM 计时器的功能。
//
//######################################################################################################################
//$TI 版本:F2837xD 支持库 V210 $
//$Release Date:Tue Nov1 14:46:15 CDT 2016 $
//版权所有:版权所有(C) 2013-2016 Texas Instruments Incorporated -
// http://www.ti.com/ 保留所有权利$
//######################################################################################################################
//
//包含的文件
//
#include "F28x_Project.h"
//
//函数原型
//
void ConfigureADC (void);
void ConfigureEPWM (void);
void SetupADCepwm (uint16 通道);
中断 void adca1_ISR (void);
中断 空 LOCAL_D_INTCH1_ISR (空);
void dma_init (void);
//
//定义
//
#define results_buffer_size 512
//
//全局
//
uint16 AdcaResults[results_buffer_size];
uint16 RDATA[Results_buffer_size];
uint16 结果索引;
易失 性 uint16 bufferFull;
易失 性 uint16 * DMADest;
易失 性 uint16 * DMASSOURCE;
void main (void)
{
//
//步骤1. 初始化系统控制:
// PLL、安全装置、启用外设时钟
//此示例函数位于 F2837xD_SYSCTRL.c 文件中。
//
InitSysCtrl();
//
//步骤2. 初始化 GPIO:
//此示例函数位于 F2837xD_GPIO.c 文件和中
//说明了如何将 GPIO 设置为其默认状态。
//
InitGpio(); //针对此示例跳过
//
//步骤3. 清除所有中断并初始化 PIE 矢量表:
//禁用 CPU 中断
//
Dint;
//
//将 PIE 控制寄存器初始化为默认状态。
//默认状态为禁用所有 PIE 中断和标志
//被清除。
//此函数位于 F2837xD_PIECTRL.c 文件中。
//
InitPieCtrl();
//
//禁用 CPU 中断并清除所有 CPU 中断标志:
//
IER = 0x0000;
IFR = 0x0000;
//
//使用指向 shell 中断的指针初始化 PIE 矢量表
//服务例程(ISR)。
//这将填充整个表,即使是中断也是如此
//在本例中未使用。 这对于调试很有用。
//可以在 F2837xD_DefaultIsr.c 中找到 shell ISR 例程
//此函数可在 F2837xD_PieVect.c 中找到
//
InitPieVectTable();
//
//映射 ISR 函数
//
EALLOW;
PieVectTable.ADCA1_INT =&adca1_ISR; //针对 ADCA 中断1的函数
PieVectTable.DMA_CH1_INT=&LOCAL_D_INTCH1_ISR;//中断入口函数 μ s
EDIS;
//启用全局中断和更高优先级的实时调试事件:
//
IER |= M_INT1; //启用组1中断
IER |= M_INT7;//启用组1中断
//
PieCtrlRegs.PIECTRL.bit.ENPIE = 1; //启用 PIE 块
PieCtrlRegs.PIEIER1.bit.INTx1 = 1;
PieCtrlRegs.PIEIER7.bit.INTx1 = 1; //启用 PIE 组7、INT 2 (DMA CH2)
//启用 CPU INT6
EINT; //启用全局中断 INTM
ERTM; //启用全局 实时 中断 DBGM
//
//配置 ADC 并为其加电
//
ConfigureADC();
//
//配置 ePWM
//
ConfigureEPWM();
//
//在通道0上设置用于 ePWM 触发转换的 ADC
//
SetupADCepwm (2);
dma_init (); //设置 DMA
//确保 DMA 连接到外设帧2桥接器(EALLOW 受保护)
//
EALLOW;
CpuSysRegs.SECMSEL.bit.PF2SEL = 1;
EDIS;
//
DmaRegs.ch1.control.bit.PERINTCLR = 1;
// StartDMACH1(); //启动 DMA 通道
//
//初始化结果缓冲区
//
for (resultsIndex = 0;resultsIndex < results_buffer_size;resultsIndex++)
{
AdcaResults[resultsIndex]=0;
RDATA[resultsIndex]=0;
}
resultsIndex = 0;
bufferFull = 0;
//
//启用 PIE 中断
//
StartDMACH1(); //启动 DMA 通道
//
//同步 ePWM
//
EALLOW;
CpuSysRegs.PCLKCR0.bit.TBCLKSYNC=1 ;
EDIS;
//
//循环无限地进行转换
//
操作
{
//
//启动 ePWM
//
EPwm1Regs.ETSEL.bit.SOCAEN = 1; //启用 SOCA
EPwm1Regs.TBCTL.bit.CTRMODE = 0; //取消冻结、并进入递增计数模式
//
//等待、而 ePWM 导致 ADC 转换、然后导致中断、
//填充结果缓冲区,最终设置 bufferFull
//flag
//
while (!bufferFull);
bufferFull = 0; //清除缓冲区已满标志
EALLOW;
// DmaRegs.ch1.control.bit.PERINTFRC = 1;
EDIS;
//
//停止 ePWM
//
EPwm1Regs.ETSEL.bit.SOCAEN = 0; //禁用 SOCA
EPwm1Regs.TBCTL.bit.CTRMODE = 3; //冻结计数器
//
//此时,AdcaResults[]包含一系列转换
//从所选通道
//
//
//软件断点,再次点击运行以获取更新的转换
//
asm (" ESTOP0");
} while (1);
}
//
// ConfigureADC -写入 ADC 配置并为两者加电
// ADC A 和 ADC B
//
空 配置 ADC (空)
{
EALLOW;
//
//写入配置
//
AdcaRegs.ADCCTL2.bit.prescale = 6; //将 ADCCLK 分频器设置为/4
AdcSetMode (ADC_ADCA、ADC_Resolution_16BIT、ADC_SIGNALMODE_differential);
//
//将脉冲位置设置为晚期
//
AdcaRegs.ADCCTL1.bit.INTPULSEPOS=1 ;
//
//为 ADC 加电
//
AdcaRegs.ADCCTL1.bit.ADCPWDNZ = 1;
//
//延迟1ms 以允许 ADC 加电时间
//
DELAY_US (1000);
EDIS;
}
//
// ConfigureEPWM -配置 ePWM SOC 并比较值
//
空 配置 EPWM (空)
{
EALLOW;
//假设 ePWM 时钟已启用
EPwm1Regs.ETSEL.bit.SOCAEN = 0; //禁用组上的 SOC
EPwm1Regs.ETSEL.bit.SOCASEL = 4; //在递增计数时选择 SOC
EPwm1Regs.ETPS.bit.SOCAPRD = 1; //在发生第一个事件时生成脉冲
EPwm1Regs.CMPA.bit.CMPA = 2000; //将比较 A 值设置为2000计数
EPwm1Regs.TBPRD = 4000; //将周期设置为4000个计数
EPwm1Regs.TBCTL.bit.CTRMODE = 3; //冻结计数器
EDIS;
}
//
// SetupADCepwm -设置 ADC ePWM 采集窗口
//
void SetupADCepwm (uint16 通道)
{
uint16 acqps;
//
//根据分辨率确定最小采集窗口(在 SYSCLKS 中)
//
if (adc_resolution_12bit = AdcaRegs.ADCCTL2.bit.resolution)
{
acqps = 14; //75ns
}
否则 、//分辨率为16位
{
acqps = 63; //320ns
}
//
//选择要转换的通道和转换结束标志
//
EALLOW;
AdcaRegs.ADCSOC0CTL.bit.CHSEL =通道; //SOC0将转换引脚 A2
AdcaRegs.ADCSOC0CTL.bit.ACQPS = acqps; //采样窗口为100个 SYSCLK 周期
AdcaRegs.ADCSOC0CTL.bit.TRIGSEL = 5; // ePWM1 SOCA/C 上的触发
AdcaRegs.ADCINTSEL1N2.bit.INT1SEL = 0; // SOC0结束将设置 INT1标志
AdcaRegs.ADCINTSEL1N2.bit.INT1E = 1; //启用 INT1标志
AdcaRegs.ADCINTFLGCLR.bit.ADCINT1 = 1; //确保 INT1标志被清除
EDIS;
}
//
// adca1_ISR -在 ISR 中读取 ADC 缓冲器
//
中断 void adca1_ISR (void)
{
AdcaResults[resultsIndex++]= AdcaResultRegs.ADCRESULT0;
// DmaRegs.ch1.control.bit.PERINTFRC = 1;
if (results_buffer_size <= resultsIndex)
{
resultsIndex = 0;
bufferFull=1;
}
EALLOW;
DmaRegs.ch1.control.bit.PERINTFRC = 1;
EDIS;
AdcaRegs.ADCINTFLGCLR.bit.ADCINT1 = 1; //清除 INT1标志
PieCtrlRegs.PIEACX.ALL = PIEACK_Group1;
}
// dma_init - TX 和 RX 通道的 DMA 设置。
//
void dma_init()
{
//
//有关以下函数的说明,请参阅 dma.c。
//
//
//初始化 DMA
//
DMAInitialize();
DMASSOURCE =结果;
DMADest = RDATA;
//
//配置 DMA CH1
//
DMACH1AddrConfig (DMADest、DMASource);
DMACH1BurstConfig (15、1、1);
DMACH1TransferConfig (31、1、1);
DMACH1ModeConfig (0、PERINT_ENABLE、OneShot_disable、CONT_ENABLE、
SYNC_DISABLE、SYNC_SRC、OVRFLOW_DISABLE、十六位、
CHINT_BEGIN、CHINT_ENABLE);
}
// local_D_INTCH6_ISR - DMA 通道6 ISR
//
中断 空 LOCAL_D_INTCH1_ISR (空)
{
PieCtrlRegs.PIEACK.all = PIEACK_group7; // ACK 以接收更多中断
//来自此 PIE 组
}
//
//文件结束
//
。