mirror of
https://github.com/espressif/esp-idf.git
synced 2024-10-05 20:47:46 -04:00
Merge branch 'feature/introduce_internal_sleep_sub_mode_configure_api' into 'master'
feat(esp_hw_support): introduce internal sleep sub mode configure api Closes PM-216 See merge request espressif/esp-idf!30687
This commit is contained in:
commit
eab98765ad
@ -127,7 +127,7 @@ esp_err_t adc_oneshot_new_unit(const adc_oneshot_unit_init_cfg_t *init_config, a
|
||||
sar_periph_ctrl_adc_oneshot_power_acquire();
|
||||
} else {
|
||||
#if SOC_LIGHT_SLEEP_SUPPORTED || SOC_DEEP_SLEEP_SUPPORTED
|
||||
esp_sleep_enable_adc_tsens_monitor(true);
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, true);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -230,7 +230,7 @@ esp_err_t adc_oneshot_del_unit(adc_oneshot_unit_handle_t handle)
|
||||
sar_periph_ctrl_adc_oneshot_power_release();
|
||||
} else {
|
||||
#if SOC_LIGHT_SLEEP_SUPPORTED || SOC_DEEP_SLEEP_SUPPORTED
|
||||
esp_sleep_enable_adc_tsens_monitor(false);
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, false);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@ -19,6 +19,7 @@
|
||||
#include "driver/ledc.h"
|
||||
#include "esp_rom_gpio.h"
|
||||
#include "clk_ctrl_os.h"
|
||||
#include "esp_private/esp_sleep_internal.h"
|
||||
#include "esp_private/periph_ctrl.h"
|
||||
#include "esp_private/gpio.h"
|
||||
#include "esp_private/esp_gpio_reserve.h"
|
||||
@ -561,6 +562,16 @@ static esp_err_t ledc_set_timer_div(ledc_mode_t speed_mode, ledc_timer_t timer_n
|
||||
}
|
||||
p_ledc_obj[speed_mode]->glb_clk_is_acquired[timer_num] = true;
|
||||
if (p_ledc_obj[speed_mode]->glb_clk != glb_clk) {
|
||||
#if SOC_LIGHT_SLEEP_SUPPORTED
|
||||
/* keep ESP_PD_DOMAIN_RC_FAST on during light sleep */
|
||||
if (glb_clk == LEDC_SLOW_CLK_RC_FAST) {
|
||||
/* Keep ESP_PD_DOMAIN_RC_FAST on during light sleep */
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_DIG_USE_RC_FAST_MODE, true);
|
||||
} else if (p_ledc_obj[speed_mode]->glb_clk == LEDC_SLOW_CLK_RC_FAST) {
|
||||
/* No need to keep ESP_PD_DOMAIN_RC_FAST on during light sleep anymore */
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_DIG_USE_RC_FAST_MODE, false);
|
||||
}
|
||||
#endif
|
||||
// TODO: release old glb_clk (if not UNINIT), and acquire new glb_clk [clk_tree]
|
||||
p_ledc_obj[speed_mode]->glb_clk = glb_clk;
|
||||
LEDC_FUNC_CLOCK_ATOMIC() {
|
||||
@ -571,12 +582,6 @@ static esp_err_t ledc_set_timer_div(ledc_mode_t speed_mode, ledc_timer_t timer_n
|
||||
portEXIT_CRITICAL(&ledc_spinlock);
|
||||
|
||||
ESP_LOGD(LEDC_TAG, "In slow speed mode, global clk set: %d", glb_clk);
|
||||
|
||||
/* keep ESP_PD_DOMAIN_RC_FAST on during light sleep */
|
||||
#if SOC_LIGHT_SLEEP_SUPPORTED
|
||||
extern void esp_sleep_periph_use_8m(bool use_or_not);
|
||||
esp_sleep_periph_use_8m(glb_clk == LEDC_SLOW_CLK_RC_FAST);
|
||||
#endif
|
||||
}
|
||||
|
||||
/* The divisor is correct, we can write in the hardware. */
|
||||
|
@ -9,7 +9,7 @@
|
||||
#include "unity_test_utils.h"
|
||||
#include "esp_heap_caps.h"
|
||||
|
||||
#define TEST_MEMORY_LEAK_THRESHOLD (200)
|
||||
#define TEST_MEMORY_LEAK_THRESHOLD (212)
|
||||
|
||||
void setUp(void)
|
||||
{
|
||||
|
@ -31,13 +31,35 @@ typedef struct {
|
||||
void esp_sleep_set_sleep_context(esp_sleep_context_t *sleep_ctx);
|
||||
#endif
|
||||
|
||||
typedef enum {
|
||||
ESP_SLEEP_RTC_USE_RC_FAST_MODE, //!< The mode requested by RTC peripherals to keep RC_FAST clock on during sleep (both HP_SLEEP and LP_SLEEP mode). (Will override the RC_FAST domain config by esp_sleep_pd_config)
|
||||
ESP_SLEEP_DIG_USE_RC_FAST_MODE, //!< The mode requested by digital peripherals to keep RC_FAST clock on during sleep (both HP_SLEEP and LP_SLEEP mode). (!!! Only valid for lightsleep, will override the RC_FAST domain config by esp_sleep_pd_config)
|
||||
ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, //!< Will enables the use of ADC and temperature sensor in monitor (ULP) mode.
|
||||
ESP_SLEEP_ULTRA_LOW_MODE, //!< In ultra low mode, 2uA is saved, but RTC memory can't use at high temperature, and RTCIO can't be used as INPUT.
|
||||
ESP_SLEEP_RTC_FAST_USE_XTAL_MODE, //!< The mode in which the crystal is used as the RTC_FAST clock source, need keep XTAL on in HP_SLEEP mode when ULP is working.
|
||||
ESP_SLEEP_DIG_USE_XTAL_MODE, //!< The mode requested by digital peripherals to keep XTAL clock on during sleep (both HP_SLEEP and LP_SLEEP mode). (!!! Only valid for lightsleep, will override the XTAL domain config by esp_sleep_pd_config)
|
||||
ESP_SLEEP_MODE_MAX,
|
||||
} esp_sleep_sub_mode_t;
|
||||
|
||||
/**
|
||||
* @brief Enables the use of ADC and temperature sensor in monitor (ULP) mode
|
||||
* @brief Set sub-sleep power mode in sleep, mode enabled status is maintained by reference count.
|
||||
* This submode configuration will kept after deep sleep wakeup.
|
||||
*
|
||||
* @note This state is kept in RTC memory and will keep its value after a deep sleep wakeup
|
||||
* @param mode sub-sleep mode type
|
||||
* @param activate Activate or deactivate the sleep sub mode
|
||||
*
|
||||
* @return
|
||||
* - ESP_OK on success
|
||||
* - ESP_ERR_INVALID_ARG if either of the arguments is out of range
|
||||
*/
|
||||
void esp_sleep_enable_adc_tsens_monitor(bool enable);
|
||||
esp_err_t esp_sleep_sub_mode_config(esp_sleep_sub_mode_t mode, bool activate);
|
||||
|
||||
/**
|
||||
* Dump the sub-sleep power mode enable status
|
||||
* @param stream The stream to dump to, if NULL then nothing will be dumped
|
||||
* @return return the reference count array pointer
|
||||
*/
|
||||
int32_t* esp_sleep_sub_mode_dump_config(FILE *stream);
|
||||
|
||||
#if SOC_GPIO_SUPPORT_HOLD_IO_IN_DSLP && !SOC_GPIO_SUPPORT_HOLD_SINGLE_IO_IN_DSLP
|
||||
/**
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include <stdlib.h>
|
||||
#include "soc/rtc.h"
|
||||
#include "esp_private/rtc_clk.h"
|
||||
#include "esp_private/esp_sleep_internal.h"
|
||||
#include "soc/rtc_periph.h"
|
||||
#include "soc/sens_reg.h"
|
||||
#include "soc/soc_caps.h"
|
||||
@ -273,15 +274,23 @@ void rtc_clk_apll_coeff_set(uint32_t o_div, uint32_t sdm0, uint32_t sdm1, uint32
|
||||
|
||||
void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
{
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
#ifndef BOOTLOADER_BUILD
|
||||
soc_rtc_slow_clk_src_t clk_src_before_switch = clk_ll_rtc_slow_get_src();
|
||||
// Keep the RTC8M_CLK on in sleep if RTC clock is rc_fast_d256.
|
||||
if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch != SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch to RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, true);
|
||||
} else if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch away from RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, false);
|
||||
}
|
||||
#endif
|
||||
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
// The logic should be moved to BT driver
|
||||
if (clk_src == SOC_RTC_SLOW_CLK_SRC_XTAL32K) {
|
||||
clk_ll_xtal32k_digi_enable();
|
||||
} else {
|
||||
clk_ll_xtal32k_digi_disable();
|
||||
}
|
||||
|
||||
esp_rom_delay_us(SOC_DELAY_RTC_SLOW_CLK_SWITCH);
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "esp32c2/rom/rtc.h"
|
||||
#include "esp32c2/rom/uart.h"
|
||||
#include "soc/rtc.h"
|
||||
#include "esp_private/esp_sleep_internal.h"
|
||||
#include "esp_private/rtc_clk.h"
|
||||
#include "soc/io_mux_reg.h"
|
||||
#include "soc/soc.h"
|
||||
@ -66,6 +67,16 @@ bool rtc_clk_8md256_enabled(void)
|
||||
|
||||
void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
{
|
||||
#ifndef BOOTLOADER_BUILD
|
||||
soc_rtc_slow_clk_src_t clk_src_before_switch = clk_ll_rtc_slow_get_src();
|
||||
// Keep the RTC8M_CLK on in sleep if RTC clock is rc_fast_d256.
|
||||
if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch != SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch to RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, true);
|
||||
} else if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch away from RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, false);
|
||||
}
|
||||
#endif
|
||||
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
|
||||
/* Why we need to connect this clock to digital?
|
||||
@ -76,7 +87,6 @@ void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
} else {
|
||||
clk_ll_xtal32k_digi_disable();
|
||||
}
|
||||
|
||||
esp_rom_delay_us(SOC_DELAY_RTC_SLOW_CLK_SWITCH);
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "esp32c3/rom/rtc.h"
|
||||
#include "soc/rtc.h"
|
||||
#include "soc/io_mux_reg.h"
|
||||
#include "esp_private/esp_sleep_internal.h"
|
||||
#include "esp_private/rtc_clk.h"
|
||||
#include "esp_hw_log.h"
|
||||
#include "esp_rom_sys.h"
|
||||
@ -99,8 +100,17 @@ bool rtc_clk_8md256_enabled(void)
|
||||
|
||||
void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
{
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
#ifndef BOOTLOADER_BUILD
|
||||
soc_rtc_slow_clk_src_t clk_src_before_switch = clk_ll_rtc_slow_get_src();
|
||||
// Keep the RTC8M_CLK on in sleep if RTC clock is rc_fast_d256.
|
||||
if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch != SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch to RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, true);
|
||||
} else if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch away from RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, false);
|
||||
}
|
||||
#endif
|
||||
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
/* Why we need to connect this clock to digital?
|
||||
* Or maybe this clock should be connected to digital when xtal 32k clock is enabled instead?
|
||||
*/
|
||||
@ -109,7 +119,6 @@ void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
} else {
|
||||
clk_ll_xtal32k_digi_disable();
|
||||
}
|
||||
|
||||
esp_rom_delay_us(SOC_DELAY_RTC_SLOW_CLK_SWITCH);
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "esp32s2/rom/rtc.h"
|
||||
#include "soc/rtc.h"
|
||||
#include "esp_private/rtc_clk.h"
|
||||
#include "esp_private/esp_sleep_internal.h"
|
||||
#include "soc/rtc_cntl_reg.h"
|
||||
#include "soc/rtc_io_reg.h"
|
||||
#include "soc/soc_caps.h"
|
||||
@ -174,8 +175,17 @@ void rtc_clk_apll_coeff_set(uint32_t o_div, uint32_t sdm0, uint32_t sdm1, uint32
|
||||
|
||||
void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
{
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
#ifndef BOOTLOADER_BUILD
|
||||
soc_rtc_slow_clk_src_t clk_src_before_switch = clk_ll_rtc_slow_get_src();
|
||||
// Keep the RTC8M_CLK on in sleep if RTC clock is rc_fast_d256.
|
||||
if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch != SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch to RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, true);
|
||||
} else if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch away from RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, false);
|
||||
}
|
||||
#endif
|
||||
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
/* Why we need to connect this clock to digital?
|
||||
* Or maybe this clock should be connected to digital when xtal 32k clock is enabled instead?
|
||||
*/
|
||||
@ -184,7 +194,6 @@ void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
} else {
|
||||
clk_ll_xtal32k_digi_disable();
|
||||
}
|
||||
|
||||
esp_rom_delay_us(SOC_DELAY_RTC_SLOW_CLK_SWITCH);
|
||||
}
|
||||
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "esp32s3/rom/rtc.h"
|
||||
#include "soc/rtc.h"
|
||||
#include "soc/io_mux_reg.h"
|
||||
#include "esp_private/esp_sleep_internal.h"
|
||||
#include "esp_private/rtc_clk.h"
|
||||
#include "soc/rtc_io_reg.h"
|
||||
#include "esp_rom_sys.h"
|
||||
@ -114,8 +115,17 @@ bool rtc_clk_8md256_enabled(void)
|
||||
|
||||
void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
{
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
#ifndef BOOTLOADER_BUILD
|
||||
soc_rtc_slow_clk_src_t clk_src_before_switch = clk_ll_rtc_slow_get_src();
|
||||
// Keep the RTC8M_CLK on in sleep if RTC clock is rc_fast_d256.
|
||||
if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch != SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch to RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, true);
|
||||
} else if (clk_src == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256 && clk_src_before_switch == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256) { // Switch away from RC_FAST_D256
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_RTC_USE_RC_FAST_MODE, false);
|
||||
}
|
||||
#endif
|
||||
|
||||
clk_ll_rtc_slow_set_src(clk_src);
|
||||
/* Why we need to connect this clock to digital?
|
||||
* Or maybe this clock should be connected to digital when xtal 32k clock is enabled instead?
|
||||
*/
|
||||
@ -124,7 +134,6 @@ void rtc_clk_slow_src_set(soc_rtc_slow_clk_src_t clk_src)
|
||||
} else {
|
||||
clk_ll_xtal32k_digi_disable();
|
||||
}
|
||||
|
||||
esp_rom_delay_us(SOC_DELAY_RTC_SLOW_CLK_SWITCH);
|
||||
}
|
||||
|
||||
|
@ -8,6 +8,7 @@
|
||||
#include <string.h>
|
||||
#include <sys/lock.h>
|
||||
#include <sys/param.h>
|
||||
#include <inttypes.h>
|
||||
|
||||
#include "esp_attr.h"
|
||||
#include "esp_rom_caps.h"
|
||||
@ -279,16 +280,9 @@ static bool s_light_sleep_wakeup = false;
|
||||
static portMUX_TYPE spinlock_rtc_deep_sleep = portMUX_INITIALIZER_UNLOCKED;
|
||||
|
||||
static const char *TAG = "sleep";
|
||||
static RTC_FAST_ATTR bool s_adc_tsen_enabled = false;
|
||||
static RTC_FAST_ATTR int32_t s_sleep_sub_mode_ref_cnt[ESP_SLEEP_MODE_MAX] = { 0 };
|
||||
//in this mode, 2uA is saved, but RTC memory can't use at high temperature, and RTCIO can't be used as INPUT.
|
||||
static bool s_ultra_low_enabled = false;
|
||||
|
||||
static bool s_periph_use_8m_flag = false;
|
||||
|
||||
void esp_sleep_periph_use_8m(bool use_or_not)
|
||||
{
|
||||
s_periph_use_8m_flag = use_or_not;
|
||||
}
|
||||
|
||||
static uint32_t get_power_down_flags(void);
|
||||
#if SOC_PM_SUPPORT_EXT0_WAKEUP
|
||||
@ -686,7 +680,7 @@ FORCE_INLINE_ATTR void misc_modules_sleep_prepare(uint32_t pd_flags, bool deep_s
|
||||
|
||||
#if !CONFIG_IDF_TARGET_ESP32P4 && !CONFIG_IDF_TARGET_ESP32C61
|
||||
// TODO: IDF-7370
|
||||
if (!(deep_sleep && s_adc_tsen_enabled)){
|
||||
if (!(deep_sleep && (s_sleep_sub_mode_ref_cnt[ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE] != 0))){
|
||||
sar_periph_ctrl_power_disable();
|
||||
}
|
||||
#endif
|
||||
@ -778,20 +772,6 @@ static esp_err_t IRAM_ATTR esp_sleep_start(uint32_t pd_flags, esp_sleep_mode_t m
|
||||
|
||||
int64_t sleep_duration = (int64_t) s_config.sleep_duration - (int64_t) s_config.sleep_time_adjustment;
|
||||
|
||||
#if SOC_RTC_SLOW_CLK_SUPPORT_RC_FAST_D256
|
||||
//Keep the RTC8M_CLK on if RTC clock is rc_fast_d256.
|
||||
bool rtc_using_8md256 = (rtc_clk_slow_src_get() == SOC_RTC_SLOW_CLK_SRC_RC_FAST_D256);
|
||||
#else
|
||||
bool rtc_using_8md256 = false;
|
||||
#endif
|
||||
//Keep the RTC8M_CLK on if the ledc low-speed channel is clocked by RTC8M_CLK in lightsleep mode
|
||||
bool periph_using_8m = !deep_sleep && s_periph_use_8m_flag;
|
||||
|
||||
//Override user-configured power modes.
|
||||
if (rtc_using_8md256 || periph_using_8m) {
|
||||
pd_flags &= ~RTC_SLEEP_PD_INT_8M;
|
||||
}
|
||||
|
||||
// Sleep UART prepare
|
||||
if (deep_sleep) {
|
||||
flush_uarts();
|
||||
@ -903,17 +883,31 @@ static esp_err_t IRAM_ATTR esp_sleep_start(uint32_t pd_flags, esp_sleep_mode_t m
|
||||
reject_triggers |= sleep_modem_reject_triggers();
|
||||
}
|
||||
|
||||
// Override user-configured FOSC power modes.
|
||||
if (s_sleep_sub_mode_ref_cnt[ESP_SLEEP_RTC_USE_RC_FAST_MODE]) {
|
||||
pd_flags &= ~RTC_SLEEP_PD_INT_8M;
|
||||
}
|
||||
|
||||
// Override user-configured XTAL power modes.
|
||||
if (s_sleep_sub_mode_ref_cnt[ESP_SLEEP_DIG_USE_XTAL_MODE] && !deep_sleep) {
|
||||
pd_flags &= ~RTC_SLEEP_PD_XTAL;
|
||||
}
|
||||
|
||||
//Append some flags in addition to power domains
|
||||
uint32_t sleep_flags = pd_flags;
|
||||
if (s_adc_tsen_enabled) {
|
||||
|
||||
if (s_sleep_sub_mode_ref_cnt[ESP_SLEEP_DIG_USE_RC_FAST_MODE] && !deep_sleep) {
|
||||
pd_flags &= ~RTC_SLEEP_PD_INT_8M;
|
||||
sleep_flags |= RTC_SLEEP_DIG_USE_8M;
|
||||
}
|
||||
|
||||
if (s_sleep_sub_mode_ref_cnt[ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE]) {
|
||||
sleep_flags |= RTC_SLEEP_USE_ADC_TESEN_MONITOR;
|
||||
}
|
||||
if (!s_ultra_low_enabled) {
|
||||
|
||||
if (s_sleep_sub_mode_ref_cnt[ESP_SLEEP_ULTRA_LOW_MODE] == 0) {
|
||||
sleep_flags |= RTC_SLEEP_NO_ULTRA_LOW;
|
||||
}
|
||||
if (periph_using_8m) {
|
||||
sleep_flags |= RTC_SLEEP_DIG_USE_8M;
|
||||
}
|
||||
|
||||
#if CONFIG_ESP_SLEEP_DEBUG
|
||||
if (s_sleep_ctx != NULL) {
|
||||
@ -2178,6 +2172,42 @@ esp_err_t esp_sleep_pd_config(esp_sleep_pd_domain_t domain, esp_sleep_pd_option_
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
esp_err_t esp_sleep_sub_mode_config(esp_sleep_sub_mode_t mode, bool activate)
|
||||
{
|
||||
if (mode >= ESP_SLEEP_MODE_MAX) {
|
||||
return ESP_ERR_INVALID_ARG;
|
||||
}
|
||||
|
||||
portENTER_CRITICAL_SAFE(&s_config.lock);
|
||||
if (activate) {
|
||||
s_sleep_sub_mode_ref_cnt[mode]++;
|
||||
} else {
|
||||
s_sleep_sub_mode_ref_cnt[mode]--;
|
||||
}
|
||||
assert(s_sleep_sub_mode_ref_cnt[mode] >= 0);
|
||||
portEXIT_CRITICAL_SAFE(&s_config.lock);
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
int32_t* esp_sleep_sub_mode_dump_config(FILE *stream) {
|
||||
if (stream) {
|
||||
for (uint32_t mode = 0; mode < ESP_SLEEP_MODE_MAX; mode++) {
|
||||
fprintf(stream, LOG_COLOR_I "%s : %s (cnt = %" PRId32 ")\n" LOG_RESET_COLOR,
|
||||
(const char*[]){
|
||||
[ESP_SLEEP_RTC_USE_RC_FAST_MODE] = "ESP_SLEEP_RTC_USE_RC_FAST_MODE",
|
||||
[ESP_SLEEP_DIG_USE_RC_FAST_MODE] = "ESP_SLEEP_DIG_USE_RC_FAST_MODE",
|
||||
[ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE] = "ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE",
|
||||
[ESP_SLEEP_ULTRA_LOW_MODE] = "ESP_SLEEP_ULTRA_LOW_MODE",
|
||||
[ESP_SLEEP_RTC_FAST_USE_XTAL_MODE] = "ESP_SLEEP_RTC_FAST_USE_XTAL_MODE",
|
||||
[ESP_SLEEP_DIG_USE_XTAL_MODE] = "ESP_SLEEP_DIG_USE_XTAL_MODE",
|
||||
}[mode],
|
||||
s_sleep_sub_mode_ref_cnt[mode] ? "ENABLED" : "DISABLED",
|
||||
s_sleep_sub_mode_ref_cnt[mode]);
|
||||
}
|
||||
}
|
||||
return s_sleep_sub_mode_ref_cnt;
|
||||
}
|
||||
|
||||
/**
|
||||
* The modules in the CPU and modem power domains still depend on the top power domain.
|
||||
* To be safe, the CPU and Modem power domains must also be powered off and saved when
|
||||
@ -2382,12 +2412,17 @@ esp_deep_sleep_disable_rom_logging(void)
|
||||
rtc_suppress_rom_log();
|
||||
}
|
||||
|
||||
void esp_sleep_enable_adc_tsens_monitor(bool enable)
|
||||
__attribute__((deprecated("Please use esp_sleep_sub_mode_config instead"))) void esp_sleep_periph_use_8m(bool use_or_not)
|
||||
{
|
||||
s_adc_tsen_enabled = enable;
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_DIG_USE_RC_FAST_MODE, use_or_not);
|
||||
}
|
||||
|
||||
void rtc_sleep_enable_ultra_low(bool enable)
|
||||
__attribute__((deprecated("Please use esp_sleep_sub_mode_config instead"))) void esp_sleep_enable_adc_tsens_monitor(bool enable)
|
||||
{
|
||||
s_ultra_low_enabled = enable;
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, enable);
|
||||
}
|
||||
|
||||
__attribute__((deprecated("Please use esp_sleep_sub_mode_config instead"))) void rtc_sleep_enable_ultra_low(bool enable)
|
||||
{
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_ULTRA_LOW_MODE, enable);
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2021-2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2021-2024 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@ -21,6 +21,11 @@
|
||||
|
||||
static const char TAG[] = "rtc_power";
|
||||
|
||||
static void check_deepsleep_reset(void)
|
||||
{
|
||||
TEST_ASSERT_EQUAL(ESP_RST_DEEPSLEEP, esp_reset_reason());
|
||||
}
|
||||
|
||||
static void test_deepsleep(void)
|
||||
{
|
||||
esp_sleep_enable_timer_wakeup(2000000);
|
||||
@ -28,33 +33,48 @@ static void test_deepsleep(void)
|
||||
esp_deep_sleep_start();
|
||||
}
|
||||
|
||||
// Deepsleep (with 8MD256 or ADC/TSEN in monitor)
|
||||
TEST_CASE("Power Test: DSLP_8MD256", "[pm]")
|
||||
{
|
||||
esp_sleep_enable_adc_tsens_monitor(true);
|
||||
|
||||
test_deepsleep();
|
||||
static void test_set_adc_tsen_monitor_mode(void) {
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, true);
|
||||
}
|
||||
|
||||
static void test_unset_adc_tesen_monitor_mode(void) {
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, false);
|
||||
TEST_ASSERT_EQUAL(0, esp_sleep_sub_mode_dump_config(NULL)[ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE]);
|
||||
}
|
||||
|
||||
// Deepsleep (with 8MD256 or ADC/TSEN in monitor)
|
||||
TEST_CASE_MULTIPLE_STAGES( "Power Test: DSLP_8MD256", "[pm]",
|
||||
test_set_adc_tsen_monitor_mode,
|
||||
test_deepsleep,
|
||||
check_deepsleep_reset,
|
||||
test_unset_adc_tesen_monitor_mode
|
||||
)
|
||||
|
||||
#if !CONFIG_RTC_CLK_SRC_INT_8MD256
|
||||
// Deepsleep (default)
|
||||
TEST_CASE("Power Test: DSLP_DEFAULT", "[pm]")
|
||||
{
|
||||
esp_sleep_enable_adc_tsens_monitor(false); //This is the default option. Add this line to avoid the case executing this case directly after the DSLP_8MD256 case.
|
||||
TEST_CASE_MULTIPLE_STAGES( "Power Test: DSLP_DEFAULT", "[pm]",
|
||||
test_deepsleep,
|
||||
check_deepsleep_reset
|
||||
)
|
||||
|
||||
test_deepsleep();
|
||||
static void test_set_ultra_low_mode(void) {
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_ULTRA_LOW_MODE, true);
|
||||
}
|
||||
|
||||
static void test_unset_ultra_low_mode(void) {
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_ULTRA_LOW_MODE, false);
|
||||
TEST_ASSERT_EQUAL(0, esp_sleep_sub_mode_dump_config(NULL)[ESP_SLEEP_ULTRA_LOW_MODE]);
|
||||
}
|
||||
|
||||
// Deepsleep (ultra-low power)
|
||||
TEST_CASE("Power Test: DSLP_ULTRA_LOW", "[pm]")
|
||||
{
|
||||
esp_sleep_enable_adc_tsens_monitor(false); //This is the default option. Add this line to avoid the case executing this case directly after the DSLP_8MD256 case.
|
||||
TEST_CASE_MULTIPLE_STAGES( "Power Test: DSLP_ULTRA_LOW", "[pm]",
|
||||
test_set_ultra_low_mode,
|
||||
test_deepsleep,
|
||||
check_deepsleep_reset,
|
||||
test_unset_ultra_low_mode
|
||||
)
|
||||
|
||||
extern void rtc_sleep_enable_ultra_low(bool);
|
||||
rtc_sleep_enable_ultra_low(true);
|
||||
|
||||
test_deepsleep();
|
||||
}
|
||||
#endif //!CONFIG_RTC_CLK_SRC_INT_8MD256
|
||||
|
||||
static void test_lightsleep(void)
|
||||
@ -125,17 +145,14 @@ TEST_CASE("Power Test: LSLP_8MD256", "[pm]")
|
||||
// Lightsleep (with ADC/TSEN in monitor)
|
||||
TEST_CASE("Power Test: LSLP_ADC_TSENS", "[pm]")
|
||||
{
|
||||
extern void esp_sleep_enable_adc_tsens_monitor(bool);
|
||||
esp_sleep_enable_adc_tsens_monitor(true);
|
||||
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, true);
|
||||
test_lightsleep();
|
||||
esp_sleep_sub_mode_config(ESP_SLEEP_USE_ADC_TSEN_MONITOR_MODE, false);
|
||||
}
|
||||
|
||||
// Lightsleep (default)
|
||||
TEST_CASE("Power Test: LSLP_DEFAULT", "[pm]")
|
||||
{
|
||||
esp_sleep_enable_adc_tsens_monitor(false); //This is the default option. Add this line to avoid the case executing this case directly after the DSLP_8MD256 case.
|
||||
|
||||
test_lightsleep();
|
||||
}
|
||||
#endif //!CONFIG_RTC_CLK_SRC_INT_8MD256
|
||||
|
Loading…
x
Reference in New Issue
Block a user