Skip to main content
Associate II
September 14, 2026
Question

CubeMX codegen defect: wrong bus group when disabling the PWR clock in `HAL_RTC_MspInit()`

  • September 14, 2026
  • 0 replies
  • 5 views

Summary

 

STM32CubeMX (STM32U5 targets; reproduced with 6.18.0-RC3 and 6.18.1-RC2) generates an incorrect clock-disable call in the LSE bring-up block of HAL_RTC_MspInit() in Core/Src/rtc.c. The restore path that is meant to switch the PWR peripheral clock back off passes an AHB3 peripheral mask to the APB1 disable function:

/* Restore clock configuration if changed */

if (pwrclkchanged == SET)

{

LL_APB1_GRP1_DisableClock(LL_AHB3_GRP1_PERIPH_PWR); /* generated — wrong bus group */

}

The matching enable earlier in the same function is generated correctly:

if (LL_AHB3_GRP1_IsEnabledClock (LL_AHB3_GRP1_PERIPH_PWR) != 1U)

{

/* Enables the PWR Clock and Enables access to the backup domain */

LL_AHB3_GRP1_EnableClock(LL_AHB3_GRP1_PERIPH_PWR);

pwrclkchanged = SET;

}

 

Diagnosis

On the STM32U5, the PWR peripheral clock lives on AHB3, and the two enable registers happen to use the same bit position:

Register Bit 2 Reference
RCC_AHB3ENR PWREN — PWR clock enable RM0456 Rev 5, §11.8.32, p. 558
RCC_APB1ENR1 TIM4EN — TIM4 clock enable RM0456 Rev 5, §11.8.33, p. 560

 

LL_AHB3_GRP1_PERIPH_PWR is defined as RCC_AHB3ENR_PWREN (bit 2), so the generated call compiles cleanly but clears bit 2 of RCC_APB1ENR1 instead of RCC_AHB3ENR. The consequences:

  1. The PWR clock is never disabled — the restore that pwrclkchanged exists for does not happen (mostly benign, but the generated intent is defeated).
  2. TIM4's clock is silently gated. If TIM4 were enabled and in use before HAL_RTC_MspInit() runs, it would stop dead with no error. The failure would present as TIM4 mysteriously not counting, with nothing pointing back to RTC initialisation.

We are not currently bitten by (2) — on our boards HAL_RTC_MspInit() runs during early init before any APB1 timer is claimed, and the block only executes at all when the RTC clock source is not yet LSE (i.e. after a backup-domain reset). It is nonetheless a latent defect in generated code that any later init-order change could expose.

 

Where it occurs

  • STM32/Core/Src/rtc.c (line 113)

The block appears to be emitted when the RTC is configured with LSE as its clock source while RCC uses the LL driver (Project Manager → Advanced Settings).

Re-tested with the 6.18.1-RC2 point release: still emits LL_APB1_GRP1_DisableClock(LL_AHB3_GRP1_PERIPH_PWR) — the defect is not fixed.

 

Fix

One-line correction, making the disable symmetric with the enable:

LL_AHB3_GRP1_DisableClock(LL_AHB3_GRP1_PERIPH_PWR);

 

References

  • RM0456 Rev 5 (STM32U5 reference manual): §11.8.32 RCC_AHB3ENR (PWREN, bit 2); §11.8.33 RCC_APB1ENR1 (TIM4EN, bit 2).
  • stm32u5xx_ll_bus.h#define LL_AHB3_GRP1_PERIPH_PWR RCC_AHB3ENR_PWREN.
  • stm32u575xx.h / stm32u5a9xx.hRCC_AHB3ENR_PWREN_Pos (2UL)RCC_APB1ENR1_TIM4EN_Pos (2UL).