一、写在前面
STM32单片机使用时间较长,所以使用TC1784后,很多功能实现就想移植之前STM32的。比如本文提到的 采用DMA方式的ADC采集。
二、准备工具
1、tasking (TASKING VX-toolset for TriCore and PCP v3.5r1)
2、DAvE (DAvE 2.2r2)
3、LAUTERBACH仿真器 配合 仿真上位机(TRACE32 PowerView for Tricore release sep 2019(64-bit) R.2019.09.000114442)
三、开发历程
0、ADC采集(顺序请求源方式) 测试硬件OK 相应通道有数据反映
1)DAvE 配置顺序请求源(Sequential source 0) 配置通道 顺序请求源门控打开
2)使用DAvE生成ADC0.C ADC0.h文件
3)启动转换 读取转换结果
ADC0_vStartSeq0ReqChNum(0,0,0,ch);
ADC0_vSeqSoftTrigger(0);
while(ADC0_uwBusy());
RESRD = (uword volatile *) 0xF01011C0;
RESR = (uword volatile *) 0xF0101180;
RESRD += ch;
RESR += ch;
if ( (*RESRD) & 0x80000000 )
{
resl = (*RESR) & 0x00003fff;
Analog_Ch[ch] = resl;
}
1、ADC采集(扫描请求源方式)
1)DAvE 配置扫描请求源(Parallel source 1) 配置通道 扫描请求源门控打开 使能自动扫描 使能扫描源中断(SENPx) 选择SR0 (注:该SR0使能 仅仅为了 硬件触发DMA使用 并不真正使用中断 对于此理解 强烈建议查看 UM中的 中断框图)
2)使用DAvE生成ADC0.C ADC0.h文件
3)启动转换 读取转换结果
/ADC0.C 初始化完成后 添加以下代码
ADC0_vStartParReqChNum(0xFFFF, ADC_SOURCE_1);
ADC0_vSetLoadEvent(SOURCE_1);
//LAUTERBACH仿真上位机 查看ADC转换结果及工作状态
CPU——》Peripherals——》ADC ADC0 Result Registers
2、DMA测试 内存到内存搬移 ADC结果寄存器到内存搬移
1)DAvE Block0 配置DMA Channel 00
配置DMA Channel 00
Channel Control
CHMODE 连续转换模式 使能硬件触发(ECH00) 选择ADC_SR00(ADC)【确保步骤1可以触发该信号 也可以使用软件触发DMA方式 待研究】
Address Control
根据实际填写 源地址SADR 目标地址DADR 对应的地址循环长度(CBLS CBLD ) 对应地址的增加模式(INCS INCD)
注:a)tricore的地址循环长度,是一个大坑,这里仅仅用于指示源地址或者目标最低几位变化情况,请查看相关CBLS CBLD理解
b)tricore对于地址访问有很强的保护 当然 后果就是调试时一直测试不通过。准确了解将要使用的 源地址与目标地址范围【当初发现该问题 是内存到内存测试是 DMA_ERRSR ME0SER 位指示了错误】
比如 源地址 ADC0结果寄存器(地址 0xF0101180) 内存地址(程序数组标量)(0xD0009000-0xD0009040 )
根据这些信息 配置下一步 Memory 0
配置DMA Memory0
a)配置AENx 勾选ADC0、ADC1 用于 ADC0结果寄存器(地址 0xF0101180) 勾选DMI,DMI Image用于 内存地址(程序数组标量)(xxxxx 注意步骤2 )
b)仅仅勾选 DMI,DMI Image 对于 内存地址(程序数组标量)还不够 还需要选择 DMI SIZE调整为 128kBytes 才能将内存地址(0xD0009000-0xD0009040 )覆盖
注:DMI SLICE 有点小坑 强烈建议查看UM 理解内存地址范围。
2)使用DAvE生成DMA.C DMA.h文件
3) 代码中不要额外 添加代码 等待ADC0触发即可工作
3、集成工作 ADC采集16个通道 (DMA方式)
集成步骤1 步骤2 工作,即可实现ADC DMA采集。
调试注意点:
单个结果寄存器4字节 16通道 共64字节 = 4*16 CBLS CBLD均选择64字节
源地址及目标start地址均应为64字节整数倍
比如 内存地址(程序数组标量)(0xD0009000-0xD0009040 ) 在tasking定义方式如下
uword ADC0_raw_u32[16] __at( 0xD0009000 ); 注意 __at( xxx )里xxx前后一定要加空格