本帖最后由 GZZXB 于 2021-7-4 11:51 编辑
感谢 香版的回复. 我的理解是定时器的dma burst传输 外设地址是通过TIM17_DMAR_ADDRESS来间接访问,而我是用的TIM17->CCR1.应该是常规传输吧? TIM_DMAConfig(TIM17, TIM_DMABase_CCR1,TIM_DMABurstLength_1Transfer); 这一句是不是不管什么传输都得加上呢? 另外我在GPIOA7上做 tim3 pwm输入/tim17 pwm输出切换时,就死机。 这个需要注意什么吗?
编辑补充:TIM_DMAConfig(TIM17, TIM_DMABase_CCR1,TIM_DMABurstLength_1Transfer); 常规模式下加不加应该都可以,加上只是设定而已,只要不将目的地址设为DMAR就不起作用. 楼主位代码加上自动重载函数可以输出波形了, 有两个新的问题是初始化时输出是正常的. 而在代码中切换GPIOA7复用功能时直接跑飞。本代码用途是复用GPIOA7, 切换为PWM输入时扑捉GPIOA7上出现的占空比方波. 切换为PWM输出时在GPIOA7上输出不同占空比的方波。
切换为pwm输入代码
GPIO_PinAFConfig(GPIOA,GPIO_PinSource7,GPIO_AF_1); //TIM3_CH2 PWM输入捕捉
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOA, &GPIO_InitStructure);
TIM_Cmd(TIM17, DISABLE); //停止PWM输出
TIM_Cmd(TIM3, ENABLE); //使能PWM输入捕捉
切换为输出代码
#if(1)
GPIO_PinAFConfig(GPIOA,GPIO_PinSource7,GPIO_AF_5); //TIM17_CH1 PWM输出
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType=GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOA, &GPIO_InitStructure);
#endif
//TIM_DMACmd(TIM17, TIM_DMA_CC1, ENABLE);
//DMA_Cmd(DMA1_Channel1,ENABLE); //通过dma1 逐次修改占空比
TIM_Cmd(TIM3, DISABLE); //停止PWM输入
切换为输出后,用该函数发送不同占空比脉冲
void Encode(uint16_t *p,uint8_t dataLen)
{
uint8_t i;
for(i=0;i<dataLen;i++)
{
Encode_Tab=p;
}
DMA_Cmd(DMA1_Channel1, DISABLE);/* DMA1 Channel1 disable */
DMA1_Channel1->CNDTR=dataLen;
DMA_Cmd(DMA1_Channel1, ENABLE);/* DMA1 Channel1 enable */
TIM_Cmd(TIM17, ENABLE);
}
经排查没有指针越界和非法内存访问情况,只要将 Encode_Tab全部填入0不会死机,正常输出波形。 将 Encode_Tab某个单元填入0xff就跑飞,单步运行时发现运行到TIM_Cmd(TIM17, ENABLE);时正常, 一执行TIM_Cmd(TIM17, ENABLE);就跑飞直接死机。
|