soc: st: stm32h7: synchronize cores during boot properly
On dual-core STM32H7, the Cortex-M4 core is supposed to wait until the Cortex-M7 initializes the system before starting to execute. CM7 should signal this by locking a specific HSEM, which CM4 should poll until locked. However, the logic on the Cortex-M4 side was reading the "RLR" register of HSEM, which *locks the semaphore on read* - in turn, this makes the CM4 start directly since it sees that the semaphore is locked (by itself). Use proper LL API to read HSEM status - which will read the "R" register instead - to make sure CM4 doesn't begin execution earlier than it should. Suggested-by: hglassdyb Signed-off-by: Mathieu Choplain <mathieu.choplain@st.com>
This commit is contained in:
parent
86c5135982
commit
4282d67ac2
2 changed files with 18 additions and 14 deletions
|
@ -37,19 +37,19 @@ void soc_early_init_hook(void)
|
|||
/* Enable hardware semaphore clock */
|
||||
LL_AHB4_GRP1_EnableClock(LL_AHB4_GRP1_PERIPH_HSEM);
|
||||
|
||||
/* In case CM4 has not been forced boot by CM7,
|
||||
* CM4 needs to wait until CM7 has setup clock configuration
|
||||
/**
|
||||
* Cortex-M7 is responsible for initializing the system.
|
||||
*
|
||||
* CM7 will start CM4 ("forced boot") at the end of system
|
||||
* initialization if the core is not already running - in
|
||||
* this scenario, we don't have to wait because the system
|
||||
* is initialized. Otherwise, wait for CM7 to initialize the
|
||||
* system before proceeding with the boot process. CM7 will
|
||||
* acquire a specific HSEM to indicate that CM4 can proceed.
|
||||
*/
|
||||
if (!LL_RCC_IsCM4BootForced()) {
|
||||
/*
|
||||
* Domain D2 is waiting for Cortex-M7 to perform
|
||||
* system initialization
|
||||
* (system clock config, external memory configuration.. ).
|
||||
* End of system initialization is reached when CM7 takes HSEM.
|
||||
*/
|
||||
while ((HSEM->RLR[CFG_HW_ENTRY_STOP_MODE_SEMID] & HSEM_R_LOCK)
|
||||
!= HSEM_R_LOCK) {
|
||||
;
|
||||
while (!LL_HSEM_IsSemaphoreLocked(HSEM, CFG_HW_ENTRY_STOP_MODE_SEMID)) {
|
||||
/* Wait for CM7 to lock the HSEM after system initialization */
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -31,9 +31,13 @@ static int stm32h7_m4_wakeup(void)
|
|||
LL_APB4_GRP1_EnableClock(LL_APB4_GRP1_PERIPH_SYSCFG);
|
||||
|
||||
if (READ_BIT(SYSCFG->UR1, SYSCFG_UR1_BCM4)) {
|
||||
/* Cortex-M4 is waiting for end of system initialization made by
|
||||
* Cortex-M7. This initialization is now finished,
|
||||
* then Cortex-M7 takes HSEM so that CM4 can continue running.
|
||||
/**
|
||||
* Cortex-M4 has been started by hardware.
|
||||
* Its `soc_early_init_hook()` will stall boot until
|
||||
* a specific HSEM becomes locked, which indicates
|
||||
* that Cortex-M7 has finished initializing the system.
|
||||
* As system initialization is now complete, lock the
|
||||
* HSEM to release CM4 and allow it to continue booting.
|
||||
*/
|
||||
LL_HSEM_1StepLock(HSEM, CFG_HW_ENTRY_STOP_MODE_SEMID);
|
||||
} else if (IS_ENABLED(CONFIG_STM32H7_BOOT_M4_AT_INIT)) {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue