STM32 HAL_InitTick Bug

我的平台是H743, 这个应该是通用的:

这个bug跟复位级别、Systick使用TIM有关,如果只复位了内核而没有复位外设,则会触发这个bug,先关注由

//------HERE------HERE------HERE------///
框住的两段区域:

HAL_StatusTypeDef HAL_InitTick(uint32_t TickPriority)
{
  RCC_ClkInitTypeDef    clkconfig;
  uint32_t              uwTimclock;

  uint32_t              uwPrescalerValue;
  uint32_t              pFLatency;
/*Configure the TIM16 IRQ priority */
  if (TickPriority < (1UL << __NVIC_PRIO_BITS))
  {
  HAL_NVIC_SetPriority(TIM16_IRQn, TickPriority ,0U);

  /* Enable the TIM16 global Interrupt */
//------HERE------HERE------HERE------///
  HAL_NVIC_EnableIRQ(TIM16_IRQn);
//------HERE------HERE------HERE------///
    uwTickPrio = TickPriority;
    }
  else
  {
    return HAL_ERROR;
  }

  /* Enable TIM16 clock */
  __HAL_RCC_TIM16_CLK_ENABLE();

  /* Get clock configuration */
  HAL_RCC_GetClockConfig(&clkconfig, &pFLatency);

  /* Compute TIM16 clock */
      uwTimclock = 2*HAL_RCC_GetPCLK2Freq();

  /* Compute the prescaler value to have TIM16 counter clock equal to 1MHz */
  uwPrescalerValue = (uint32_t) ((uwTimclock / 1000000U) - 1U);

  /* Initialize TIM16 */
//------HERE------HERE------HERE------///
  htim16.Instance = TIM16;
//------HERE------HERE------HERE------///

  /* Initialize TIMx peripheral as follow:

  + Period = [(TIM16CLK/1000) - 1]. to have a (1/1000) s time base.
  + Prescaler = (uwTimclock/1000000 - 1) to have a 1MHz counter clock.
  + ClockDivision = 0
  + Counter direction = Up
  */
  htim16.Init.Period = (1000000U / 1000U) - 1U;
  htim16.Init.Prescaler = uwPrescalerValue;
  htim16.Init.ClockDivision = 0;
  htim16.Init.CounterMode = TIM_COUNTERMODE_UP;

  if(HAL_TIM_Base_Init(&htim16) == HAL_OK)
  {
    /* Start the TIM time Base generation in interrupt mode */
    return HAL_TIM_Base_Start_IT(&htim16);
  }

  /* Return function status */
  return HAL_ERROR;
}

假设系统仅复位内核后,运行到这里:

外设中断使能中(这里是溢出中断),则在NVIC_ENABLE的地方会立即进入TIM_IRQ,而此时htim并没有指向TIM16 Instance,从而导致itflag、itsource读取失败,从而触发bug。

修复的方法也很简单,使用ARM Compiler提供的Sub、Super给InitTick打补丁就好,或者注释掉重新写。

我选择在InitTick前手动清掉TIM的中断使能,这样最简单。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值