From efa4eeafd07ed028db747c24023f79c49ecb0e11 Mon Sep 17 00:00:00 2001 From: Li Shuai Date: Mon, 26 Jun 2023 11:26:27 +0800 Subject: [PATCH] light sleep: enable system clock in PMU HP sleep state when selecting a 40 MHz XTAL as low power clock source of ble --- .../esp_hw_support/include/esp_private/esp_pmu.h | 9 +++++++++ components/esp_hw_support/modem_clock.c | 10 ++++++++-- components/esp_hw_support/port/esp32c6/pmu_sleep.c | 5 +++++ 3 files changed, 22 insertions(+), 2 deletions(-) diff --git a/components/esp_hw_support/include/esp_private/esp_pmu.h b/components/esp_hw_support/include/esp_private/esp_pmu.h index 4dcb820b11..187784fae6 100644 --- a/components/esp_hw_support/include/esp_private/esp_pmu.h +++ b/components/esp_hw_support/include/esp_private/esp_pmu.h @@ -249,6 +249,15 @@ bool pmu_sleep_finish(void); */ void pmu_init(void); +/** + * @brief Enable or disable system clock in PMU HP sleep state + * + * This API only used for fix BLE 40 MHz low power clock source issue + * + * @param enable true to enable, false to disable + */ +void pmu_sleep_enable_hp_sleep_sysclk(bool enable); + #endif //#if SOC_PMU_SUPPORTED diff --git a/components/esp_hw_support/modem_clock.c b/components/esp_hw_support/modem_clock.c index 0348d68652..443b7c78bb 100644 --- a/components/esp_hw_support/modem_clock.c +++ b/components/esp_hw_support/modem_clock.c @@ -334,6 +334,9 @@ void modem_clock_select_lp_clock_source(periph_module_t module, modem_clock_lpcl modem_clock_hal_select_ble_rtc_timer_lpclk_source(MODEM_CLOCK_instance()->hal, src); modem_clock_hal_set_ble_rtc_timer_divisor_value(MODEM_CLOCK_instance()->hal, divider); modem_clock_hal_enable_ble_rtc_timer_clock(MODEM_CLOCK_instance()->hal, true); + if (src == MODEM_CLOCK_LPCLK_SRC_MAIN_XTAL) { + pmu_sleep_enable_hp_sleep_sysclk(true); + } break; #endif // SOC_BT_SUPPORTED @@ -372,6 +375,8 @@ void modem_clock_deselect_lp_clock_source(periph_module_t module) { assert(IS_MODEM_MODULE(module)); portENTER_CRITICAL_SAFE(&MODEM_CLOCK_instance()->lock); + modem_clock_lpclk_src_t last_src = MODEM_CLOCK_instance()->lpclk_src[module - PERIPH_MODEM_MODULE_MIN]; + MODEM_CLOCK_instance()->lpclk_src[module - PERIPH_MODEM_MODULE_MIN] = MODEM_CLOCK_LPCLK_SRC_INVALID; switch (module) { #if SOC_WIFI_SUPPORTED @@ -385,6 +390,9 @@ void modem_clock_deselect_lp_clock_source(periph_module_t module) case PERIPH_BT_MODULE: modem_clock_hal_deselect_all_ble_rtc_timer_lpclk_source(MODEM_CLOCK_instance()->hal); modem_clock_hal_enable_ble_rtc_timer_clock(MODEM_CLOCK_instance()->hal, false); + if (last_src == MODEM_CLOCK_LPCLK_SRC_MAIN_XTAL) { + pmu_sleep_enable_hp_sleep_sysclk(false); + } break; #endif // SOC_BT_SUPPORTED case PERIPH_COEX_MODULE: @@ -394,8 +402,6 @@ void modem_clock_deselect_lp_clock_source(periph_module_t module) default: break; } - modem_clock_lpclk_src_t last_src = MODEM_CLOCK_instance()->lpclk_src[module - PERIPH_MODEM_MODULE_MIN]; - MODEM_CLOCK_instance()->lpclk_src[module - PERIPH_MODEM_MODULE_MIN] = MODEM_CLOCK_LPCLK_SRC_INVALID; portEXIT_CRITICAL_SAFE(&MODEM_CLOCK_instance()->lock); esp_sleep_pd_domain_t pd_domain = (esp_sleep_pd_domain_t) ( \ diff --git a/components/esp_hw_support/port/esp32c6/pmu_sleep.c b/components/esp_hw_support/port/esp32c6/pmu_sleep.c index 07f96f4803..dfb63c9ff3 100644 --- a/components/esp_hw_support/port/esp32c6/pmu_sleep.c +++ b/components/esp_hw_support/port/esp32c6/pmu_sleep.c @@ -294,3 +294,8 @@ bool pmu_sleep_finish(void) { return pmu_ll_hp_is_sleep_reject(PMU_instance()->hal->dev); } + +void pmu_sleep_enable_hp_sleep_sysclk(bool enable) +{ + pmu_ll_hp_set_icg_sysclk_enable(PMU_instance()->hal->dev, HP(SLEEP), enable); +}