STMicroelectronics / STM32CubeL4

STM32Cube MCU Full Package for the STM32L4 series - (HAL + LL Drivers, CMSIS Core, CMSIS Device, MW libraries plus a set of Projects running on all boards provided by ST (Nucleo, Evaluation and Discovery Kits))
Other
259 stars 151 forks source link

LL_RTC_WaitForSynchro race condition #64

Closed jminack closed 1 year ago

jminack commented 2 years ago

Setup

Describe the bug When calling LL_RTC_WaitForSynchro(), the function would intermittently timeout waiting for the flag to clear.

How To Reproduce If a delay of ~100us is added between these two lines:

  LL_RTC_ClearFlag_RS(RTCx);
----> Delay here  < -------
  /* Wait the registers to be synchronised */
  tmp = LL_RTC_IsActiveFlag_RS(RTCx);

this will induce the bug. _This is equivalent to an interrupt occurring just after LL_RTC_ClearFlagRS.

Additional context As per https://community.st.com/s/question/0D53W000004Hjo3SAC/bug-in-llrtcwaitforsynchro-function-in-stm32l1xxllrtcc, the behavior of waiting for the flag to clear is not present in either the HAL function HAL_RTC_WaitForSynchro or the older driver code.

Nor does it match the comments above the function:

  * @note   To read the calendar through the shadow registers after Calendar
  *         initialization, calendar update or after wakeup from low power modes
  *         the software must first clear the RSF flag.
  *         The software must then wait until it is set again before reading
  *         the calendar, which means that the calendar registers have been
  *         correctly copied into the RTC_TR and RTC_DR shadow registers.

Unless this function is called with interrupts disabled, there will always be a danger of it failing.

ALABSTM commented 2 years ago

Hi @jminack,

Thank you for this report. We will get back to you with a feedback as soon as possible. Please excuse the delay it may take us sometimes to reply. Thank you for your comprehension.

With regards,

ALABSTM commented 2 years ago

ST Internal Reference: 127004

ALABSTM commented 2 years ago

Hi @jminack,

Thank you for your report. Actually, it seems that between line 807 where RSF bit is cleared, and line 810 where its status is read, "enough" time is elapsed for the synchronization. Thus, the RSF bit is set again by the hardware before even entering the while loop at line 811. This would explain the observed timeout.

https://github.com/STMicroelectronics/STM32CubeL4/blob/5223f4b55990987748dfc523ed751bc0c938650e/Drivers/STM32L4xx_HAL_Driver/Src/stm32l4xx_ll_rtc.c#L806-L811

The solution is to remove this first while loop and to keep only the second, as shown below. The point has been logged internally and a fix will be made available in a future release. Thank you again for your report.

With regards,

  /* Clear RSF flag */
  LL_RTC_ClearFlag_RS(RTCx);

  /* Wait the registers to be synchronised */
  tmp = LL_RTC_IsActiveFlag_RS(RTCx);
-  while ((timeout != 0U) && (tmp != 0U))
-  {
-    if (LL_SYSTICK_IsActiveCounterFlag() == 1U)
-    {
-      timeout--;
-    }
-    tmp = LL_RTC_IsActiveFlag_RS(RTCx);
-    if (timeout == 0U)
-    {
-      status = ERROR;
-    }
-  }
-
-  if (status != ERROR)
-  {
-    timeout = RTC_SYNCHRO_TIMEOUT;
-    tmp = LL_RTC_IsActiveFlag_RS(RTCx);
    while ((timeout != 0U) && (tmp != 1U))
    {
      if (LL_SYSTICK_IsActiveCounterFlag() == 1U)
      {
        timeout--;
      }
      tmp = LL_RTC_IsActiveFlag_RS(RTCx);
      if (timeout == 0U)
      {
        status = ERROR;
      }
    }
-  }
beachmiles commented 1 year ago

systick is not incrementing using the latest stm32cubeL4 driver. Its an identical issue with the stm32cubeF4 driver that still isnt fixed. The good news is its a 1 line fix. Uncomment this line below in system_stm32l4xx.c #define USER_VECT_TAB_ADDRESS

The issue has persisted for over a year here for the stm32F4 and I suspect the stm32L4 as well. https://github.com/STMicroelectronics/STM32CubeF4/issues/113

I suppose I should open this issue for this stm32L4 repo as well.

HBOSTM commented 1 year ago

Hello @jminack

The fix you requested has been implemented and is now available in the frame of the latest stm32Cube l4 firmware package V1.18.0 release. This issue can be closed now. Thank you again for your contribution.

Best Regards,