cancel
Showing results for 
Search instead for 
Did you mean: 

STM32F303RE: PWMs utilizing Timers with Phase Shift

KMew
Senior III

Hello,

I am assisting with the firmware development of a dual-active bridge converter and I am trying to create a phase-shifted PWM signal that will control the switches. Creating the phase shift is proving challenging, but I had an idea that I believe, in theory, should work. However, I cannot seem to get the configuration correct to implement it.

 

I am using the STM32F303RE. Let me explain my strategy:

I am utilizing TIM1 and TIM3. Specifically:
TIM1-CH1 - PWM Signal that goes externally, used as reference (aka not phase shifted)

TIM1-CH2 - PWM Signal that goes externally, used as reference (aka not phase shifted)

TIM1-CH3 - PWM Signal that's internal

 

TIM8-CH1 - PWM Signal that goes externally, in slave mode

TIM8-CH2 - PWM Signal that goes externally, in slave mode

 

I would like to make both TIM8's a slave that starts its counter on the falling edge of TIM1-CH3. TIM1-CH3 will be synchorized with TIM1-CH1/2 (in other words, their rising edges will always be the same). I will then change the duty cycle of  TIM1-CH3. Since TIM8 is a slave of TIM1-CH3, TIM8 will start its counter and rise on the falling edge of TIM1-CH3. See the visual below to help understand.

KMew_0-1706889515705.png

I am trying to implement them in the STM32CubeMX/IDE, but it's not working. Here is my CubeMX configuration

 

TIM1:

KMew_1-1706889584526.pngKMew_2-1706889611420.pngKMew_3-1706889628508.png

 

TIM8:

KMew_4-1706889658934.pngKMew_5-1706889671820.pngKMew_6-1706889680915.png

 

 

In the CubeIDE, I also added the following lines after the initialization:

	HAL_TIM_PWM_Start(&htim1, TIM_CHANNEL_1);
	HAL_TIMEx_PWMN_Start(&htim1, TIM_CHANNEL_1);
	HAL_TIM_PWM_Start(&htim1, TIM_CHANNEL_2);
	HAL_TIMEx_PWMN_Start(&htim1, TIM_CHANNEL_2);
	HAL_TIM_PWM_Start(&htim1, TIM_CHANNEL_3);


	HAL_TIM_PWM_Start(&htim8, TIM_CHANNEL_1);
	HAL_TIMEx_PWMN_Start(&htim8, TIM_CHANNEL_1);
	HAL_TIM_PWM_Start(&htim8, TIM_CHANNEL_2);
	HAL_TIMEx_PWMN_Start(&htim8, TIM_CHANNEL_2);


  TIM1->CCR1 = 80;
  TIM1->CCR2 = 80;
  TIM1->CCR3 = 10;

  TIM8->CCR1 = 80;
  TIM8->CCR2 = 80;

 

Unfortunately, it is not working. TIM1-CH1/2 and TIM8-CH1/2 are in sync with no shaft shift, despite the TIM1->CCR3 = 10 that should shift it by 10 counts.

 

Can anyone help me figure out what I'm doing wrong?

 

12 REPLIES 12

@Michal Dudka, good point. I did not realize the 'F3xx already have Asymmetric PWM in timers; I thought it only came in newer STM32.

JW

Hello @Michal Dudka 


Thank you for the reply!

So if I set things up as I have, what do I need to adjust to make it work?

What will the TGRO need to be in this case?

What registers do I have to use/change to create the phase shift? 

How to set up and manage this mode is described in Reference manual ( 20.3.12 Asymmetric PWM mode ). If i read manual correctly, then you control rising and falling edges positions on one channel by registers CCR1 and CCR2 and on second channel by CCR3 and CCR4. Just follow reference manual.
If you need both TIMers (more then two outputs), then choose one as Master (for example TIM1) and second as slave (TIM8). Configure TRGO signal to "Enable (event)" in TIM1 (MMS bits in TIM1_CR2). Configure TRGI in TIM8 to ITR0 (TS bits in TIM8_SMCR)  and select slave mode to "Trigger" (SMS bits in TIM8_SMCR). 
Then when you enable TIM1, it sends signal on its TRGO on which is connected TRGI input of TIM8. TIM8 recieve that signal and start counting. All that should happen in one clock tick and both timers should run synchronized.