jefftenney / LPTIM-Tick

FreeRTOS Tick/Tickless via LPTIM
42 stars 2 forks source link

Utilizing LSI in Tickless idle might lead to Initialization fail of the IWDG #17

Closed Scarittagle closed 2 months ago

Scarittagle commented 2 months ago

MCU: STM32G031G8U6

Core Speed: 2MHz (HSI 8 Div)

Behavior: Because my application don't have external crystals so I used LSI for the LPTIM. It works fine in the tickless idle. But when it comes to IWDG, the HAL_IWDG_Init(&hiwdg) always failed.

I traced the code to somewhere around here:

/* Check pending flag, if previous update not done, return timeout */
  tickstart = HAL_GetTick();

  /* Wait for register to be updated */
  while ((hiwdg->Instance->SR & IWDG_KERNEL_UPDATE_FLAGS) != 0x00u)
  {
    if ((HAL_GetTick() - tickstart) > HAL_IWDG_DEFAULT_TIMEOUT)
    {
      if ((hiwdg->Instance->SR & IWDG_KERNEL_UPDATE_FLAGS) != 0x00u)
      {
        return HAL_TIMEOUT;
      }
    }
  }

It seems like it would always return timeout if I don't put a breakpoint in there. Not sure if it related to this but IWDG uses LSI too.

If I removed LPTIM-Tick and go back to the usual Tickless idle, the IWDG works fine.

jefftenney commented 2 months ago

Hi @Scarittagle - are you using STOP modes when you observe this issue with IWDG? You must avoid STOP mode while the IWDG is updating any of its registers using its synchronization mechanism. When all of its updating is finished, it runs properly even in STOP mode. In my applications I have defined ulpPERIPHERAL_IWDG_UPDATING to help manage this issue.

Olstyle commented 2 months ago

I am using LSI and IWDG combined without issues on the STM32WBx5 and The STM32U5. So it is no general compatibility issue. Like @jefftenney mentioned you should make sure that the watchdog init is not interrupted by a stop. But I have not seen or read about any issues during the retrigger. Actually I think it is good practise to have the watchdog initialized before the scheduler is even started. Which would also solve the problem above.