I am using TIM1 to drive a DMA channel which is sending bytes to GPIOF on an STM32F407. TIM1 is started by an OC channel on a different timer. In the DMA stream interrupt handler, I am attempting to stop TIM1 and also reset the counter by generating an Update event. For troubleshooting purposes I have configured an OC channel on TIM1 so I can confirm it is starting and stopping as expected.
It does appear to start and stop at the correct times when viewing the pin output using a logic analyzer, but when stepping through the interrupt handler in the debugger I see that the CEN bit is still set after clearing it. Also, TIM1->CNT continues to increment as I step through each line.
The interrupt handler is as follows:
void __attribute__((interrupt("IRQ"))) DMA2_Stream5_IRQHandler(void)
{
// Clear interrupt flags
do
{
DMA2->HIFCR = DMA_HIFCR_CTCIF5 | DMA_HIFCR_CHTIF5;
}
while(DMA2->HISR & DMA_HISR_TCIF5);
// Stop TIM1, TIM5 will re-enable it
//TIM1->CR1 &= (u16)~TIM_CR1_CEN;
do
{
TIM1->CR1 &= (u16)~TIM_CR1_CEN;
}
while(TIM1->CR1 & TIM_CR1_CEN);
TIM1->EGR = TIM_EventSource_Update; // Trigger an Update to reset the counter
// Re-enable DMA for next TIM5 event
DMA2_Stream5->CR |= DMA_SxCR_EN;
}
The code does exit the loop which clears CEN, but afterwards viewing the TIM1 registers shows CEN is still set. How can I ensure the timer is really stopped and will start counting from 0 next time it is started?