Skip to main content
SMarm.1
Associate
October 22, 2020
Question

Hi, Is it possible to start at the same time PWM on Ch1 and Ch2? Because there is a delay between them Thnaks

  • October 22, 2020
  • 5 replies
  • 2398 views

..

This topic has been closed for replies.

5 replies

waclawek.jan
Super User
October 22, 2020

Which STM32?

Two channels of the same timer?

What do you mean by delay? Post screenshot of oscilloscope/logic analyzer.

JW

SMarm.1
SMarm.1Author
Associate
October 22, 2020

stm32G4321RB

Yes, tim1 with ch1 and ch2 when PWM start there is a delay between ch1 and ch2. I want to freeze and begin at same time ch1 and ch2 without delay. Is it possible?

right now I don't have oscilloscope images

 if(HAL_TIM_OC_Start(&htim1, TIM_CHANNEL_1) != HAL_OK)
 {
// Starting Error
 Error_Handler();
 }
// Start channel 1N
 if(HAL_TIMEx_OCN_Start(&htim1, TIM_CHANNEL_1) != HAL_OK)
 {
// Starting Error
 Error_Handler();
 }
 
// Start channel 2
 if(HAL_TIM_OC_Start(&htim1, TIM_CHANNEL_2) != HAL_OK)
 {
// Starting Error
 Error_Handler();
 }
// Start channel 2N
 if(HAL_TIMEx_OCN_Start(&htim1, TIM_CHANNEL_2) != HAL_OK)
 {
// Starting Error
 Error_Handler();
 }

TDK
October 22, 2020

I don't believe it's possible with HAL functions, but you could certainly do this in your own code. Configure all channels first, then start the timer.

"If you feel a post has answered your question, please click ""Accept as Solution""."
waclawek.jan
Super User
October 22, 2020

> HAL_TIM_OC_Start(&htim1, TIM_CHANNEL_2|TIM_CHANNEL_1);

Cube is open source so it's easy to check what exactly this function does.

I suspect it sets TIMx_CCER.CCEx/CCNEx bits. It may be able to set several of them. This may appear as these channels are "enabled" at once; however, depending on the minute details of the appication this may or may not be the required behaviour, as before enabling a channel it's "turned to input", while the timer's counter already runs.

JW

Explorer
January 19, 2024

This post is a bit older, but since I just had the same problem, I'll add my solution here. In my case, I also wanted to stop at the same time.

I had also initially done it in such a way that I enabled both channels in one call and disabled them again to stop.

If you want to prevent the pins from switching to input, you can instead switch the mode of both channels simultaneously from Forced inactive to PWM and vice versa.

Please note that if the output is inverted, Forced active must be used instead. In my case the second channel was inverted.

 

Start PWM:

uint32_t tmp;

// Read the entire CCMR1 register
tmp = htim1.Instance->CCMR1;
// Clearing all bits of the channel mode.
tmp &= ~(TIM_CCMR1_OC1M | TIM_CCMR1_OC2M);
// Set both channels simultaneously to PWM mode 1.
tmp |= (TIM_CCMR1_OC1M_2 | TIM_CCMR1_OC1M_1) | (TIM_CCMR1_OC2M_2 | TIM_CCMR1_OC2M_1);
// Write the register back
htim1.Instance->CCMR1 = tmp;

 

Stop PWM:

uint32_t tmp;

// Read the entire CCMR1 register
tmp = htim1.Instance->CCMR1;
// Clearing all bits of the channel mode.
tmp &= ~(TIM_CCMR1_OC1M | TIM_CCMR1_OC2M);
// Simultaneously set Channel 1 to Force inactivate level and Channel 2 to Force activate level.
// Since Channel 2 is inverted, it needs to be set to Force activate level to turn the output off as well.
tmp |= (TIM_CCMR1_OC1M_2) | (TIM_CCMR1_OC2M_2 | TIM_CCMR1_OC2M_0);
// Write the register back
htim1.Instance->CCMR1 = tmp;