From 5670bad5057b1c2af7dd13b275f993866ad5420f Mon Sep 17 00:00:00 2001 From: Max van Kessel Date: Thu, 31 Aug 2023 10:00:27 +0200 Subject: [PATCH] drivers: clock: stm32: overdrive after sysclock According to the reference manual the overdrive should be enabled after setup of the sysclock (HSE or HSI) and enabling the PLL (PLLON). The flash latency should be enabled after the PLL has been turned on, but before switching the system clock to the PLL. Signed-off-by: Max van Kessel --- drivers/clock_control/clock_stm32_ll_common.c | 25 ++++------------ drivers/clock_control/clock_stm32f2_f4_f7.c | 30 +++++++++++++++++++ 2 files changed, 35 insertions(+), 20 deletions(-) diff --git a/drivers/clock_control/clock_stm32_ll_common.c b/drivers/clock_control/clock_stm32_ll_common.c index b596ac08da9..40a2bf28ce3 100644 --- a/drivers/clock_control/clock_stm32_ll_common.c +++ b/drivers/clock_control/clock_stm32_ll_common.c @@ -723,20 +723,11 @@ int stm32_clock_control_init(const struct device *dev) /* Some clocks would be activated by default */ config_enable_default_clocks(); -#if defined(STM32_PLL_ENABLED) && defined(CONFIG_SOC_SERIES_STM32F7X) - /* Assuming we stay on Power Scale default value: Power Scale 1 */ - if (CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC > 180000000) { - /* Set Overdrive if needed before configuring the Flash Latency */ - LL_PWR_EnableOverDriveMode(); - while (LL_PWR_IsActiveFlag_OD() != 1) { - /* Wait for OverDrive mode ready */ - } - LL_PWR_EnableOverDriveSwitching(); - while (LL_PWR_IsActiveFlag_ODSW() != 1) { - /* Wait for OverDrive switch ready */ - } - } -#endif /* STM32_PLL_ENABLED && CONFIG_SOC_SERIES_STM32F7X */ + /* Set up indiviual enabled clocks */ + set_up_fixed_clock_sources(); + + /* Set up PLLs */ + set_up_plls(); #if defined(FLASH_ACR_LATENCY) uint32_t old_flash_freq; @@ -754,12 +745,6 @@ int stm32_clock_control_init(const struct device *dev) } #endif /* FLASH_ACR_LATENCY */ - /* Set up indiviual enabled clocks */ - set_up_fixed_clock_sources(); - - /* Set up PLLs */ - set_up_plls(); - if (DT_PROP(DT_NODELABEL(rcc), undershoot_prevention) && (STM32_CORE_PRESCALER == LL_RCC_SYSCLK_DIV_1) && (MHZ(80) < CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC)) { diff --git a/drivers/clock_control/clock_stm32f2_f4_f7.c b/drivers/clock_control/clock_stm32f2_f4_f7.c index e7a28445572..6131fcd4c06 100644 --- a/drivers/clock_control/clock_stm32f2_f4_f7.c +++ b/drivers/clock_control/clock_stm32f2_f4_f7.c @@ -8,6 +8,7 @@ #include #include +#include #include #include #include @@ -59,6 +60,35 @@ void config_pll_sysclock(void) pllm(STM32_PLL_M_DIVISOR), STM32_PLL_N_MULTIPLIER, pllp(STM32_PLL_P_DIVISOR)); + +#if defined(CONFIG_SOC_SERIES_STM32F7X) + /* Assuming we stay on Power Scale default value: Power Scale 1 */ + if (CONFIG_SYS_CLOCK_HW_CYCLES_PER_SEC > 180000000) { + /* Enable the PLL (PLLON) before setting overdrive. Skipping the PLL + * locking phase since the system will be stalled during the switch + * (ODSW) but the PLL clock system will be running during the locking + * phase. See reference manual (RM0431) ยง4.1.4 Voltage regulator + * Sub section: Entering Over-drive mode. + */ + LL_RCC_PLL_Enable(); + + /* Set Overdrive if needed before configuring the Flash Latency */ + LL_PWR_EnableOverDriveMode(); + while (LL_PWR_IsActiveFlag_OD() != 1) { + /* Wait for OverDrive mode ready */ + } + LL_PWR_EnableOverDriveSwitching(); + while (LL_PWR_IsActiveFlag_ODSW() != 1) { + /* Wait for OverDrive switch ready */ + } + + /* The PLL could still not be locked when returning to the caller + * function. But the caller doesn't know we've turned on the PLL + * for the overdrive function. The caller will try to turn on the PLL + * And start waiting for the PLL locking phase to complete. + */ + } +#endif /* CONFIG_SOC_SERIES_STM32F7X */ } #endif /* defined(STM32_PLL_ENABLED) */