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 3420e9afdf..1d8d2c309b 100644 --- a/components/esp_hw_support/include/esp_private/esp_pmu.h +++ b/components/esp_hw_support/include/esp_private/esp_pmu.h @@ -291,6 +291,11 @@ void pmu_init(void); */ void pmu_sleep_enable_hp_sleep_sysclk(bool enable); +/** + * Get the time overhead used by regdma to work on the retention link during the hardware wake-up process + * @return regdma time cost during hardware wake-up stage in microseconds + */ +uint32_t pmu_sleep_get_wakup_retention_cost(void); #endif //#if SOC_PMU_SUPPORTED diff --git a/components/esp_hw_support/port/esp32c6/pmu_sleep.c b/components/esp_hw_support/port/esp32c6/pmu_sleep.c index faa6a4d008..9628cc794f 100644 --- a/components/esp_hw_support/port/esp32c6/pmu_sleep.c +++ b/components/esp_hw_support/port/esp32c6/pmu_sleep.c @@ -286,3 +286,8 @@ void pmu_sleep_enable_hp_sleep_sysclk(bool enable) { pmu_ll_hp_set_icg_sysclk_enable(PMU_instance()->hal->dev, HP(SLEEP), enable); } + +uint32_t pmu_sleep_get_wakup_retention_cost(void) +{ + return PMU_REGDMA_S2A_WORK_TIME_US; +} diff --git a/components/esp_hw_support/port/esp32c6/private_include/pmu_param.h b/components/esp_hw_support/port/esp32c6/private_include/pmu_param.h index 0938e058b8..75e1f99ff2 100644 --- a/components/esp_hw_support/port/esp32c6/private_include/pmu_param.h +++ b/components/esp_hw_support/port/esp32c6/private_include/pmu_param.h @@ -44,6 +44,8 @@ extern "C" { #define PMU_HP_XPD_DEEPSLEEP 0 #define PMU_LP_DRVB_DEEPSLEEP 0 +#define PMU_REGDMA_S2A_WORK_TIME_US 480 + #define PMU_DBG_ATTEN_DEEPSLEEP_DEFAULT 12 #define PMU_LP_DBIAS_DEEPSLEEP_0V7 23 @@ -456,7 +458,7 @@ typedef struct pmu_sleep_machine_constant { .power_supply_wait_time_us = 2, \ .power_up_wait_time_us = 2, \ .regdma_s2m_work_time_us = 172, \ - .regdma_s2a_work_time_us = 480, \ + .regdma_s2a_work_time_us = PMU_REGDMA_S2A_WORK_TIME_US, \ .regdma_m2a_work_time_us = 278, \ .regdma_a2s_work_time_us = 382, \ .regdma_rf_on_work_time_us = 70, \ diff --git a/components/esp_hw_support/port/esp32h2/pmu_sleep.c b/components/esp_hw_support/port/esp32h2/pmu_sleep.c index 1f39dd0a7f..75a170d6a4 100644 --- a/components/esp_hw_support/port/esp32h2/pmu_sleep.c +++ b/components/esp_hw_support/port/esp32h2/pmu_sleep.c @@ -228,3 +228,8 @@ bool pmu_sleep_finish(void) { return pmu_ll_hp_is_sleep_reject(PMU_instance()->hal->dev); } + +uint32_t pmu_sleep_get_wakup_retention_cost(void) +{ + return PMU_REGDMA_S2A_WORK_TIME_US; +} diff --git a/components/esp_hw_support/port/esp32h2/private_include/pmu_param.h b/components/esp_hw_support/port/esp32h2/private_include/pmu_param.h index 824ccb9db7..50f55ed258 100644 --- a/components/esp_hw_support/port/esp32h2/private_include/pmu_param.h +++ b/components/esp_hw_support/port/esp32h2/private_include/pmu_param.h @@ -41,6 +41,8 @@ extern "C" { #define PMU_HP_DBIAS_LIGHTSLEEP_0V6 1 #define PMU_LP_DBIAS_LIGHTSLEEP_0V7 6 +#define PMU_REGDMA_S2A_WORK_TIME_US 0 + // FOR DEEPSLEEP #define PMU_HP_XPD_DEEPSLEEP 0 #define PMU_LP_DRVB_DEEPSLEEP 7 @@ -438,7 +440,7 @@ typedef struct pmu_sleep_machine_constant { .analog_wait_time_us = 154, \ .power_supply_wait_time_us = 2, \ .power_up_wait_time_us = 2, \ - .regdma_s2a_work_time_us = 0, \ + .regdma_s2a_work_time_us = PMU_REGDMA_S2A_WORK_TIME_US, \ .regdma_a2s_work_time_us = 0, \ .xtal_wait_stable_time_us = 250, \ .pll_wait_stable_time_us = 1 \ diff --git a/components/esp_hw_support/sleep_modes.c b/components/esp_hw_support/sleep_modes.c index 309c7f8379..e021d25962 100644 --- a/components/esp_hw_support/sleep_modes.c +++ b/components/esp_hw_support/sleep_modes.c @@ -1045,6 +1045,18 @@ static esp_err_t esp_light_sleep_inner(uint32_t pd_flags, // If SPI flash was powered down, wait for it to become ready if (pd_flags & RTC_SLEEP_PD_VDDSDIO) { +#if SOC_PM_SUPPORT_TOP_PD + if (pd_flags & PMU_SLEEP_PD_TOP) { + uint32_t flash_ready_hw_waited_time_us = pmu_sleep_get_wakup_retention_cost(); + uint32_t flash_ready_sw_waited_time_us = (esp_cpu_get_cycle_count() - s_config.ccount_ticks_record) / (esp_clk_cpu_freq() / MHZ); + uint32_t flash_ready_waited_time_us = flash_ready_hw_waited_time_us + flash_ready_sw_waited_time_us; + if (flash_enable_time_us > flash_ready_waited_time_us){ + flash_enable_time_us -= flash_ready_waited_time_us; + } else { + flash_enable_time_us = 0; + } + } +#endif // Wait for the flash chip to start up esp_rom_delay_us(flash_enable_time_us); } @@ -1157,9 +1169,6 @@ esp_err_t esp_light_sleep_start(void) + rtc_time_slowclk_to_us(rtc_cntl_xtl_buf_wait_slp_cycles + RTC_CNTL_CK8M_WAIT_SLP_CYCLES + RTC_CNTL_WAKEUP_DELAY_CYCLES, s_config.rtc_clk_cal_period); #endif -#if CONFIG_IDF_TARGET_ESP32C6 // TODO: IDF-6930 - const uint32_t flash_enable_time_us = 0; -#else // Decide if VDD_SDIO needs to be powered down; // If it needs to be powered down, adjust sleep time. const uint32_t flash_enable_time_us = VDD_SDIO_POWERUP_TO_FLASH_READ_US + DEEP_SLEEP_WAKEUP_DELAY; @@ -1201,7 +1210,6 @@ esp_err_t esp_light_sleep_start(void) } } } -#endif periph_inform_out_light_sleep_overhead(s_config.sleep_time_adjustment - sleep_time_overhead_in);