简体   繁体   中英

How can I start and stop a timer on STM32?

I have a big problem. I don't know how I can stop a timer with a button and restart the timer with another button.

This is the code that I have for it so far:


This code is the interrupt handler for the button that starts the timer. I thought that it is possible by enabling the timer, that works so far.

void EXTI0_1_IRQHandler(void)
{
    if ((EXTI->PR & EXTI_PR_PR1) == EXTI_PR_PR1)  /* Check line 1 has triggered the IT */
    {
        EXTI->PR = EXTI_PR_PR1; /* Clear the pending bit */
        NVIC_EnableIRQ(TIM7_IRQn);

    }
}

This code is the interrupt handler for the button that stops the timer. This piece of code doesn't work, and the timer stays on.

void EXTI4_15_IRQHandler(void)
{
    if ((EXTI->PR & EXTI_PR_PR4) == EXTI_PR_PR4)  /* Check line 1 has triggered the IT */
    {
        EXTI->PR = EXTI_PR_PR4; /* Clear the pending bit */
        NVIC_DisableIRQ(TIM7_IRQn);
    }
}

Does anyone have some tips or know how it must be?

I think “NVIC_DisableIRQ(TIM7_IRQn);” just disable the timer's interrupt but not stop the timer. You may need: "TIM_Cmd(TIM7, DISABLE);" instead of “NVIC_DisableIRQ(TIM7_IRQn);”

或者,您可以在CR1寄存器中设置/取消设置CEN位以启用/禁用定时器

The timers can be enabled/disabled by toggling the CEN bit of the timers control register 1 (TIMx_CR1). CEN is usually the 0th bit.

TIM_Cmd(ENABLE) function call will enable the timer.

TIM_Cmd(DISABLE) function call will disable the timer.

By calling NVIC_DisableIRQ(TIM7_IRQn) , you are just disabling the interrupt for Timer7 not the Timer.

You canchange CR1 value to enable or disable timer.As follows,

#define EnableTim(n)               (n.TIMx->CR1 |= TIM_CR1_CEN)
#define DisableTim(n)              (n.TIMx->CR1 &= (~((U16)TIM_CR1_CEN)))

In addtion, when disable timer, it is best to clear CNT and SR register.Because when you use the 32bit timer, timer maybe go wrong if you do not chear CNT and SR.Code follows,

#define ClearTimCount(n)           (n.TIMx->CNT = 0)
#define ClearTimeFlag(n)           (n.TIMx->SR = (U16)~TIM_FLAG_Update)

Using HAL , start:

HAL_TIM_Base_Start(&htim#);
HAL_TIM_Base_Start_IT(&htim#);

Stop:

HAL_TIM_Base_Stop(&htim#);
HAL_TIM_Base_Stop_IT(&htim#);

Where _IT is for timer interrupt mode. And you can reconfigure timer after stopping it.

  * @brief  Enables or disables the specified TIM peripheral.
  * @param  TIMx: where x can be 1 to 17 to select the TIMx peripheral.
  * @param  NewState: new state of the TIMx peripheral.
  *   This parameter can be: ENABLE or DISABLE.
  * @retval None
  */
void TIM_Cmd(TIM_TypeDef* TIMx, FunctionalState NewState)
{
  /* Check the parameters */
  assert_param(IS_TIM_ALL_PERIPH(TIMx));
  assert_param(IS_FUNCTIONAL_STATE(NewState));
  
  if (NewState != DISABLE)
  {
    /* Enable the TIM Counter */
    TIMx->CR1 |= TIM_CR1_CEN;
  }
  else
  {
    /* Disable the TIM Counter */
    TIMx->CR1 &= (uint16_t)(~((uint16_t)TIM_CR1_CEN));
  }
}```

Like said before, the CR1 does the work.

You can write TIMx->CR1 |= value; where the 0th bit in 0 disables the TIM, and 1 enables.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM