大家好,我在使用stm32 芯片做PWM输出的时候碰到了一个问题:
设计需求如下:
需要产生一路PWM信号,并且精确计算脉冲数的输出,比如某个频率输出了10个后更改为另外一个频率在输出10个,。
目前是使用Timer3 产生一路PWM 并使用Timer3 来计算脉冲数,现在大体上设计已经差不多完成,可是用逻辑分析仪调试的时候发现一个问题,当频率由高变低的时候脉冲波形会出现异常,每次改变频率的时候都会产生1~2个异常的波形。不知道为什么,同样的频率由低变高的时候就没有问题。
TIM初始化如下:
NVIC_InitTypeDef NVIC_InitStructure;
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
TIM_DeInit(TIM3);
/* Compute the value to be set in ARR regiter to generate signal frequency at 200 hz */
Moto3TimerPeriod = AccSpeedTable[MOTO2_ACC_SPEED_INDEX].MotoTimerPeriod;
/* Compute CCR2 value to generate a duty cycle at 50% for channel 1 */
Moto3Pulse = AccSpeedTable[MOTO2_ACC_SPEED_INDEX].MotoPulse;
/* TIM2 clock enable */
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
/* Enable the TIM2 gloabal Interrupt */
NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
/* Time Base configuration */
if(TimerPrescaler > 0)
{
TIM3_TimeBaseStructure.TIM_Prescaler = (TimerPrescaler -1);//need decrease 1
}
else
{
TIM3_TimeBaseStructure.TIM_Prescaler = 0;// init value is 0
}
TIM3_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM3_TimeBaseStructure.TIM_Period = Moto3TimerPeriod;
TIM3_TimeBaseStructure.TIM_ClockDivision = 0;
TIM3_TimeBaseStructure.TIM_RepetitionCounter = 0;
TIM_TimeBaseInit(TIM3, &TIM3_TimeBaseStructure);
/* Channel 1 Configuration in PWM mode */
TIM3_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1;
TIM3_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable;
TIM3_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Enable;
TIM3_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_Low;
TIM3_OCInitStructure.TIM_OCNPolarity = TIM_OCNPolarity_High;
TIM3_OCInitStructure.TIM_OCIdleState = TIM_OCIdleState_Set;
TIM3_OCInitStructure.TIM_OCNIdleState = TIM_OCIdleState_Reset;
TIM3_OCInitStructure.TIM_Pulse = Moto3Pulse;
TIM_OC1Init(TIM3, &TIM3_OCInitStructure);
/* TIM Interrupts enable */
TIM_ITConfig(TIM3, TIM_IT_CC1 , ENABLE);
/* TIM3 counter enable */
TIM_Cmd(TIM3, ENABLE);
/* TIM3 Main Output Enable */
TIM_CtrlPWMOutputs(TIM3, ENABLE);
初始化完后在TIM3_IRQHandler 函数处理脉冲计数以及频率更改的问题。
void TIM3_IRQHandler(void)
{
if (TIM_GetITStatus(TIM3, TIM_IT_CC1) != RESET)
{
TIM_ClearITPendingBit(TIM3, TIM_IT_CC1);
TIM_SetAutoreload(TIM3,MotoTimerPeriod);
TIM_SetCompare1(TIM3,MotoPulse);
}
}
|