EmbDev.net

Forum: ARM programming with GCC/GNU tools STM32F4 PWM outputs do not have the same frequency after updated


von Minh P. (Company: Hanoi University of Science an) (minhphambkhn)


Rate this post
useful
not useful
Hello.
I have a problem. I'm using Kit STM32F407VG Discovery to control 
frequency of FullBridge LLC Converter. I use 50kHz Interrupt TIM2 and 
CH1,1N,3,3N PWM TIM1. The PWM frequency band is 80-140kHz.
When updating new frequency (TIM1->ARR), the frequency of 4 PWM outputs 
is randomly not the same, shortcircuiting my converter.
Might anybody have any idea for me to fix this problem, please?!
Thank you so much.

P/S: I post my PWM configuration below if anyone need to see.

static void TIM1_Configuration(void)
{
  NVIC_InitTypeDef NVIC_InitStructure;

  /* Enable the TIM2 Update Interrupt */
  NVIC_InitStructure.NVIC_IRQChannel           = TIM1_UP_TIM10_IRQn;
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
  NVIC_InitStructure.NVIC_IRQChannelSubPriority     = 2;
  NVIC_InitStructure.NVIC_IRQChannelCmd         = ENABLE;
  NVIC_Init(&NVIC_InitStructure);

  /* Time Base configuration */
  TIM_TimeBaseStructure.TIM_Prescaler       = 1;
  TIM_TimeBaseStructure.TIM_CounterMode     = TIM_CounterMode_Down;
  TIM_TimeBaseStructure.TIM_Period       = Timer_Period;
  TIM_TimeBaseStructure.TIM_ClockDivision     = TIM_CKD_DIV1;
  TIM_TimeBaseStructure.TIM_RepetitionCounter   = 1; // update event is 
generated at each counter overflow
  TIM_TimeBaseInit(TIM1, &TIM_TimeBaseStructure);
  TIM1->EGR = TIM_PSCReloadMode_Update; // Update when over/under flow
  TIM1->CR1 |= TIM_CR1_URS; // = 1 Only counter overflow/underflow 
generates an update interrupt or DMA request if enabled.
  TIM1->CR1 &= (uint16_t)~TIM_OPMode_Single; // = 0 Counter is not 
stopped at update event

  /* Channel 1, 3 Configuration in PWM mode */
  TIM_OCInitStructure.TIM_OCMode     = TIM_OCMode_PWM2;
  TIM_OCInitStructure.TIM_OutputState   = TIM_OutputState_Enable;
  TIM_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Enable;
  TIM_OCInitStructure.TIM_Pulse     = Channel_Pulse;
  TIM_OCInitStructure.TIM_OCPolarity   = TIM_OCPolarity_High;
  TIM_OCInitStructure.TIM_OCNPolarity   = TIM_OCNPolarity_High;
  TIM_OCInitStructure.TIM_OCIdleState   = TIM_OCIdleState_Reset;
  TIM_OCInitStructure.TIM_OCNIdleState = TIM_OCNIdleState_Reset;
//  TIM_OC1PreloadConfig(TIM1, TIM_CCMR1_OC1PE);
//  TIM_OC1Init(TIM1, &TIM_OCInitStructure);
//  TIM_OC3PreloadConfig(TIM1, TIM_CCMR2_OC3PE);
  TIM_OC3Init(TIM1, &TIM_OCInitStructure);
//  TIM1->CR1 |= TIM_CR1_ARPE; // Set the ARR Preload Bit

  /* Automatic Output enable, Break, dead time and lock configuration*/
  TIM_BDTRInitStructure.TIM_OSSRState   = TIM_OSSRState_Disable;
  TIM_BDTRInitStructure.TIM_OSSIState   = TIM_OSSIState_Disable;
  TIM_BDTRInitStructure.TIM_LOCKLevel   = TIM_LOCKLevel_OFF;
  TIM_BDTRInitStructure.TIM_DeadTime   = 0;
  TIM_BDTRInitStructure.TIM_Break     = TIM_Break_Disable;
//  Khi TIM_Break = Disable thi khong can quan tam den cai Polarity nay
//  TIM_BDTRInitStructure.TIM_BreakPolarity = TIM_BreakPolarity_Low;// 
Sua High thanh Low de thu => khong chay duoc.
  TIM_BDTRInitStructure.TIM_AutomaticOutput = 
TIM_AutomaticOutput_Disable;
  TIM_BDTRConfig(TIM1, &TIM_BDTRInitStructure);

  // TIM1 TRGO selection
  TIM_SelectOutputTrigger(TIM1, TIM_TRGOSource_Update);

  // TIM1 IT enable
  TIM_ITConfig(TIM1, TIM_IT_Update, ENABLE);

}

void TIM1_PWM_Freq_Update(void)
{
/*  tmpbdtr = TIM1->BDTR;
  tmpbdtr &= 0xFF00;
  tmpbdtr |= Dead_Time;
  tmparr  = Timer_Period;
  tmpccr  = Channel_Pulse;*/
//  TIM1->CR1 |= TIM_CR1_UDIS;
  TIM1->ARR   = Timer_Period;
//  TIM1->CCR3   = Channel_Pulse;
//  TIM1->CCR1   = Channel_Pulse;
//  TIM1->BDTR   = tmpbdtr;
//  TIM1->CR1 &= (uint16_t)~TIM_CR1_UDIS;
}

void TIM1_PWM_Freq_Update_SoftStart(void)
{
  tmpbdtr = TIM1->BDTR;
  tmpbdtr &= 0xFF00;
  tmpbdtr |= Dead_Time;
  TIM1->CR1 |= TIM_CR1_UDIS;
  TIM1->BDTR   = tmpbdtr;
  TIM1->CR1 &= (uint16_t)~TIM_CR1_UDIS;
}

void TIM2_Configuration(void)
{
  NVIC_InitTypeDef NVIC_InitStructure;
    TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;

  /* Enable the TIM2 Update Interrupt */
  NVIC_InitStructure.NVIC_IRQChannel           = TIM2_IRQn;
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
  NVIC_InitStructure.NVIC_IRQChannelSubPriority     = 1;
  NVIC_InitStructure.NVIC_IRQChannelCmd         = ENABLE;
  NVIC_Init(&NVIC_InitStructure);

  /* Time Base configuration */
  TIM_TimeBaseStructure.TIM_Prescaler     = 1;
  TIM_TimeBaseStructure.TIM_CounterMode   = TIM_CounterMode_Up;
  TIM_TimeBaseStructure.TIM_ClockDivision   = TIM_CKD_DIV1;
  TIM_TimeBaseStructure.TIM_Period     = 1499; // fsamp = 50kHz
  TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);

  // TIM2 TRGO selection
  TIM_SelectOutputTrigger(TIM2, TIM_TRGOSource_Update);

  // TIM2 IT enable
  TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE);

  // TIM2 enable counter
  TIM_Cmd(TIM2, ENABLE);

  /* TIM1 counter enable */
  TIM_Cmd(TIM1, ENABLE);//1Tcy

  /* Main Output Enable */
  TIM_CtrlPWMOutputs(TIM1, ENABLE);

}

: Edited by User
von DD4DA (Guest)


Rate this post
useful
not useful
I am not sure but i remember on an timer reload values and using the Irq 
issue, that was descripted in an errata of ST related to the Cortex M4F 
controller. I would recommend that you do some recherche about errata's. 
They are often solve the Problems about the Controllers.

Please log in before posting. Registration is free and takes only a minute.
Existing account
Do you have a Google/GoogleMail account? No registration required!
Log in with Google account
No account? Register here.