diff --git a/components/esp_hw_support/include/esp_sleep.h b/components/esp_hw_support/include/esp_sleep.h index fc3e11447d..fc311581ba 100644 --- a/components/esp_hw_support/include/esp_sleep.h +++ b/components/esp_hw_support/include/esp_sleep.h @@ -251,7 +251,7 @@ esp_err_t esp_sleep_enable_ext0_wakeup(gpio_num_t gpio_num, int level); * It will work even if RTC peripherals are shut down during sleep. * * This feature can monitor any number of pins which are in RTC IOs. - * Once any of the selected pins goes into the state given by mode argument, + * Once selected pins go into the state given by level_mode argument, * the chip will be woken up. * * @note This function does not modify pin configuration. The pins are @@ -267,28 +267,68 @@ esp_err_t esp_sleep_enable_ext0_wakeup(gpio_num_t gpio_num, int level); * the pins during sleep. HOLD feature will be acted on the pin internally * before the system entering sleep, and this can further reduce power consumption. * - * @param mask bit mask of GPIO numbers which will cause wakeup. Only GPIOs - * which have RTC functionality can be used in this bit map. - * For different SoCs, the related GPIOs are: - * - ESP32: 0, 2, 4, 12-15, 25-27, 32-39 - * - ESP32-S2: 0-21 - * - ESP32-S3: 0-21 - * - ESP32-C6: 0-7 - * - ESP32-H2: 7-14 - * @param mode select logic function used to determine wakeup condition: - * When target chip is ESP32: - * - ESP_EXT1_WAKEUP_ALL_LOW: wake up when all selected GPIOs are low - * - ESP_EXT1_WAKEUP_ANY_HIGH: wake up when any of the selected GPIOs is high - * When target chip is ESP32-S2, ESP32-S3, ESP32-C6 or ESP32-H2: - * - ESP_EXT1_WAKEUP_ANY_LOW: wake up when any of the selected GPIOs is low - * - ESP_EXT1_WAKEUP_ANY_HIGH: wake up when any of the selected GPIOs is high + * @param io_mask Bit mask of GPIO numbers which will cause wakeup. Only GPIOs + * which have RTC functionality can be used in this bit map. + * For different SoCs, the related GPIOs are: + * - ESP32: 0, 2, 4, 12-15, 25-27, 32-39 + * - ESP32-S2: 0-21 + * - ESP32-S3: 0-21 + * - ESP32-C6: 0-7 + * - ESP32-H2: 7-14 + * @param level_mode Select logic function used to determine wakeup condition: + * When target chip is ESP32: + * - ESP_EXT1_WAKEUP_ALL_LOW: wake up when all selected GPIOs are low + * - ESP_EXT1_WAKEUP_ANY_HIGH: wake up when any of the selected GPIOs is high + * When target chip is ESP32-S2, ESP32-S3, ESP32-C6 or ESP32-H2: + * - ESP_EXT1_WAKEUP_ANY_LOW: wake up when any of the selected GPIOs is low + * - ESP_EXT1_WAKEUP_ANY_HIGH: wake up when any of the selected GPIOs is high * @return * - ESP_OK on success * - ESP_ERR_INVALID_ARG if any of the selected GPIOs is not an RTC GPIO, * or mode is invalid */ -esp_err_t esp_sleep_enable_ext1_wakeup(uint64_t mask, esp_sleep_ext1_wakeup_mode_t mode); +esp_err_t esp_sleep_enable_ext1_wakeup(uint64_t io_mask, esp_sleep_ext1_wakeup_mode_t level_mode); +#if SOC_PM_SUPPORT_EXT1_WAKEUP_MODE_PER_PIN +/** + * @brief Enable wakeup using multiple pins, allows different trigger mode per pin + * + * This function uses external wakeup feature of RTC controller. + * It will work even if RTC peripherals are shut down during sleep. + * + * This feature can monitor any number of pins which are in RTC IOs. + * Once selected pins go into the state given by level_mode argument, + * the chip will be woken up. + * + * @note This function does not modify pin configuration. The pins are + * configured in esp_deep_sleep_start/esp_light_sleep_start, + * immediately before entering sleep mode. + * + * @note Internal pullups and pulldowns don't work when RTC peripherals are + * shut down. In this case, external resistors need to be added. + * Alternatively, RTC peripherals (and pullups/pulldowns) may be + * kept enabled using esp_sleep_pd_config function. If we turn off the + * ``RTC_PERIPH`` domain or certain chips lack the ``RTC_PERIPH`` domain, + * we will use the HOLD feature to maintain the pull-up and pull-down on + * the pins during sleep. HOLD feature will be acted on the pin internally + * before the system entering sleep, and this can further reduce power consumption. + * + * @param io_mask Bit mask of GPIO numbers which will cause wakeup. Only GPIOs + * which have RTC functionality can be used in this bit map. + * For different SoCs, the related GPIOs are: + * - ESP32-C6: 0-7. + * - ESP32-H2: 7-14. + * @param level_mask Select logic function used to determine wakeup condition per pin. + * Each bit of the level_mask corresponds to the respective GPIO. Each bit's corresponding + * position is set to 0, the wakeup level will be low, on the contrary, + * each bit's corresponding position is set to 1, the wakeup level will be high. + * @return + * - ESP_OK on success + * - ESP_ERR_INVALID_ARG if any of the selected GPIOs is not an RTC GPIO, + * or mode is invalid + */ +esp_err_t esp_sleep_enable_ext1_wakeup_with_level_mask(uint64_t io_mask, uint64_t level_mask); +#endif // SOC_PM_SUPPORT_EXT1_WAKEUP_MODE_PER_PIN #endif // SOC_PM_SUPPORT_EXT1_WAKEUP #if SOC_GPIO_SUPPORT_DEEPSLEEP_WAKEUP diff --git a/components/esp_hw_support/sleep_modes.c b/components/esp_hw_support/sleep_modes.c index 970bdf05b4..9b43e5cce1 100644 --- a/components/esp_hw_support/sleep_modes.c +++ b/components/esp_hw_support/sleep_modes.c @@ -189,8 +189,8 @@ typedef struct { uint64_t sleep_duration; uint32_t wakeup_triggers : 15; #if SOC_PM_SUPPORT_EXT1_WAKEUP - uint32_t ext1_trigger_mode : 1; - uint32_t ext1_rtc_gpio_mask : 22; // 22 is the maximum RTCIO number in all chips + uint32_t ext1_trigger_mode : 22; // 22 is the maximum RTCIO number in all chips + uint32_t ext1_rtc_gpio_mask : 22; #endif #if SOC_PM_SUPPORT_EXT0_WAKEUP uint32_t ext0_trigger_level : 1; @@ -1395,15 +1395,15 @@ static void ext0_wakeup_prepare(void) #endif // SOC_PM_SUPPORT_EXT0_WAKEUP #if SOC_PM_SUPPORT_EXT1_WAKEUP -esp_err_t esp_sleep_enable_ext1_wakeup(uint64_t mask, esp_sleep_ext1_wakeup_mode_t mode) +esp_err_t esp_sleep_enable_ext1_wakeup(uint64_t io_mask, esp_sleep_ext1_wakeup_mode_t level_mode) { - if (mode > ESP_EXT1_WAKEUP_ANY_HIGH) { + if (level_mode > ESP_EXT1_WAKEUP_ANY_HIGH) { return ESP_ERR_INVALID_ARG; } // Translate bit map of GPIO numbers into the bit map of RTC IO numbers uint32_t rtc_gpio_mask = 0; - for (int gpio = 0; mask; ++gpio, mask >>= 1) { - if ((mask & 1) == 0) { + for (int gpio = 0; io_mask; ++gpio, io_mask >>= 1) { + if ((io_mask & 1) == 0) { continue; } if (!esp_sleep_is_valid_wakeup_gpio(gpio)) { @@ -1413,11 +1413,44 @@ esp_err_t esp_sleep_enable_ext1_wakeup(uint64_t mask, esp_sleep_ext1_wakeup_mode rtc_gpio_mask |= BIT(rtc_io_number_get(gpio)); } s_config.ext1_rtc_gpio_mask = rtc_gpio_mask; - s_config.ext1_trigger_mode = mode; + if (level_mode) { + s_config.ext1_trigger_mode = io_mask; + } else { + s_config.ext1_trigger_mode = 0; + } s_config.wakeup_triggers |= RTC_EXT1_TRIG_EN; return ESP_OK; } +#if SOC_PM_SUPPORT_EXT1_WAKEUP_MODE_PER_PIN +esp_err_t esp_sleep_enable_ext1_wakeup_with_level_mask(uint64_t io_mask, uint64_t level_mask) +{ + if ((level_mask & io_mask) != level_mask) { + return ESP_ERR_INVALID_ARG; + } + // Translate bit map of GPIO numbers into the bit map of RTC IO numbers + // Translate bit map of GPIO wakeup mode into the bit map of RTC IO wakeup mode + uint32_t rtc_gpio_mask = 0, rtc_gpio_wakeup_mode_mask = 0; + for (int gpio = 0; io_mask; ++gpio, io_mask >>= 1, level_mask >>= 1) { + if ((io_mask & 1) == 0) { + continue; + } + if (!esp_sleep_is_valid_wakeup_gpio(gpio)) { + ESP_LOGE(TAG, "Not an RTC IO Considering io_mask: GPIO%d", gpio); + return ESP_ERR_INVALID_ARG; + } + rtc_gpio_mask |= BIT(rtc_io_number_get(gpio)); + if ((level_mask & 1) == 1) { + rtc_gpio_wakeup_mode_mask |= BIT(rtc_io_number_get(gpio)); + } + } + s_config.ext1_rtc_gpio_mask = rtc_gpio_mask; + s_config.ext1_trigger_mode = rtc_gpio_wakeup_mode_mask; + s_config.wakeup_triggers |= RTC_EXT1_TRIG_EN; + return ESP_OK; +} +#endif + static void ext1_wakeup_prepare(void) { // Configure all RTC IOs selected as ext1 wakeup inputs diff --git a/components/hal/esp32/include/hal/rtc_cntl_ll.h b/components/hal/esp32/include/hal/rtc_cntl_ll.h index 7e87d1d2ab..3c495752d3 100644 --- a/components/hal/esp32/include/hal/rtc_cntl_ll.h +++ b/components/hal/esp32/include/hal/rtc_cntl_ll.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2020-2023 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -11,6 +11,7 @@ #include "esp_attr.h" #include "clk_tree_ll.h" #include "esp_rom_sys.h" +#include "hal/assert.h" #ifdef __cplusplus extern "C" { @@ -32,11 +33,18 @@ FORCE_INLINE_ATTR uint32_t rtc_cntl_ll_ext1_get_wakeup_status(void) return REG_GET_FIELD(RTC_CNTL_EXT_WAKEUP1_STATUS_REG, RTC_CNTL_EXT_WAKEUP1_STATUS); } -FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_set_wakeup_pins(uint32_t mask, int mode) +FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_set_wakeup_pins(uint32_t io_mask, uint32_t mode_mask) { - REG_SET_FIELD(RTC_CNTL_EXT_WAKEUP1_REG, RTC_CNTL_EXT_WAKEUP1_SEL, mask); - SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, - mode, RTC_CNTL_EXT_WAKEUP1_LV_S); + // The target only supports a unified trigger mode among all EXT1 wakeup IOs + HAL_ASSERT((io_mask & mode_mask) == io_mask || (io_mask & mode_mask) == 0); + REG_SET_FIELD(RTC_CNTL_EXT_WAKEUP1_REG, RTC_CNTL_EXT_WAKEUP1_SEL, io_mask); + if ((io_mask & mode_mask) == io_mask) { + SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, + 1, RTC_CNTL_EXT_WAKEUP1_LV_S); + } else { + SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, + 0, RTC_CNTL_EXT_WAKEUP1_LV_S); + } } FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_clear_wakeup_pins(void) diff --git a/components/hal/esp32c6/include/hal/lp_aon_hal.h b/components/hal/esp32c6/include/hal/lp_aon_hal.h index f3cd9e6b85..c38f6da831 100644 --- a/components/hal/esp32c6/include/hal/lp_aon_hal.h +++ b/components/hal/esp32c6/include/hal/lp_aon_hal.h @@ -8,10 +8,10 @@ #include "hal/lp_aon_ll.h" -#define rtc_hal_ext1_get_wakeup_status() lp_aon_ll_ext1_get_wakeup_status() -#define rtc_hal_ext1_clear_wakeup_status() lp_aon_ll_ext1_clear_wakeup_status() -#define rtc_hal_ext1_set_wakeup_pins(mask, mode) lp_aon_ll_ext1_set_wakeup_pins(mask, mode) -#define rtc_hal_ext1_clear_wakeup_pins() lp_aon_ll_ext1_clear_wakeup_pins() -#define rtc_hal_ext1_get_wakeup_pins() lp_aon_ll_ext1_get_wakeup_pins() +#define rtc_hal_ext1_get_wakeup_status() lp_aon_ll_ext1_get_wakeup_status() +#define rtc_hal_ext1_clear_wakeup_status() lp_aon_ll_ext1_clear_wakeup_status() +#define rtc_hal_ext1_set_wakeup_pins(io_mask, mode_mask) lp_aon_ll_ext1_set_wakeup_pins(io_mask, mode_mask) +#define rtc_hal_ext1_clear_wakeup_pins() lp_aon_ll_ext1_clear_wakeup_pins() +#define rtc_hal_ext1_get_wakeup_pins() lp_aon_ll_ext1_get_wakeup_pins() -#define lp_aon_hal_inform_wakeup_type(dslp) lp_aon_ll_inform_wakeup_type(dslp) +#define lp_aon_hal_inform_wakeup_type(dslp) lp_aon_ll_inform_wakeup_type(dslp) diff --git a/components/hal/esp32c6/include/hal/lp_aon_ll.h b/components/hal/esp32c6/include/hal/lp_aon_ll.h index 22ae12dbf6..ef77b7561d 100644 --- a/components/hal/esp32c6/include/hal/lp_aon_ll.h +++ b/components/hal/esp32c6/include/hal/lp_aon_ll.h @@ -39,22 +39,22 @@ static inline void lp_aon_ll_ext1_clear_wakeup_status(void) /** * @brief Set the wake-up LP_IO of the ext1 wake-up source - * @param mask wakeup LP_IO bitmap, bit 0~7 corresponds to LP_IO 0~7 - * @param mode 0: Wake the chip when any of the selected GPIOs go low - * 1: Wake the chip when any of the selected GPIOs go high + * @param io_mask wakeup LP_IO bitmap, bit 0~7 corresponds to LP_IO 0~7 + * @param level_mask LP_IO wakeup level bitmap, bit 0~7 corresponds to LP_IO 0~7 wakeup level + * each bit's corresponding position is set to 0, the wakeup level will be low + * on the contrary, each bit's corresponding position is set to 1, the wakeup + * level will be high */ -static inline void lp_aon_ll_ext1_set_wakeup_pins(uint32_t mask, int mode) +static inline void lp_aon_ll_ext1_set_wakeup_pins(uint32_t io_mask, uint32_t level_mask) { uint32_t wakeup_sel_mask = HAL_FORCE_READ_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_sel); - wakeup_sel_mask |= mask; + wakeup_sel_mask |= io_mask; HAL_FORCE_MODIFY_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_sel, wakeup_sel_mask); uint32_t wakeup_level_mask = HAL_FORCE_READ_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_lv); - if (mode) { - wakeup_level_mask |= mask; - } else { - wakeup_level_mask &= ~mask; - } + wakeup_level_mask |= io_mask & level_mask; + wakeup_level_mask &= ~(io_mask & ~level_mask); + HAL_FORCE_MODIFY_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_lv, wakeup_level_mask); } diff --git a/components/hal/esp32h2/include/hal/lp_aon_hal.h b/components/hal/esp32h2/include/hal/lp_aon_hal.h index f3cd9e6b85..c38f6da831 100644 --- a/components/hal/esp32h2/include/hal/lp_aon_hal.h +++ b/components/hal/esp32h2/include/hal/lp_aon_hal.h @@ -8,10 +8,10 @@ #include "hal/lp_aon_ll.h" -#define rtc_hal_ext1_get_wakeup_status() lp_aon_ll_ext1_get_wakeup_status() -#define rtc_hal_ext1_clear_wakeup_status() lp_aon_ll_ext1_clear_wakeup_status() -#define rtc_hal_ext1_set_wakeup_pins(mask, mode) lp_aon_ll_ext1_set_wakeup_pins(mask, mode) -#define rtc_hal_ext1_clear_wakeup_pins() lp_aon_ll_ext1_clear_wakeup_pins() -#define rtc_hal_ext1_get_wakeup_pins() lp_aon_ll_ext1_get_wakeup_pins() +#define rtc_hal_ext1_get_wakeup_status() lp_aon_ll_ext1_get_wakeup_status() +#define rtc_hal_ext1_clear_wakeup_status() lp_aon_ll_ext1_clear_wakeup_status() +#define rtc_hal_ext1_set_wakeup_pins(io_mask, mode_mask) lp_aon_ll_ext1_set_wakeup_pins(io_mask, mode_mask) +#define rtc_hal_ext1_clear_wakeup_pins() lp_aon_ll_ext1_clear_wakeup_pins() +#define rtc_hal_ext1_get_wakeup_pins() lp_aon_ll_ext1_get_wakeup_pins() -#define lp_aon_hal_inform_wakeup_type(dslp) lp_aon_ll_inform_wakeup_type(dslp) +#define lp_aon_hal_inform_wakeup_type(dslp) lp_aon_ll_inform_wakeup_type(dslp) diff --git a/components/hal/esp32h2/include/hal/lp_aon_ll.h b/components/hal/esp32h2/include/hal/lp_aon_ll.h index f556def282..38492a1728 100644 --- a/components/hal/esp32h2/include/hal/lp_aon_ll.h +++ b/components/hal/esp32h2/include/hal/lp_aon_ll.h @@ -39,22 +39,22 @@ static inline void lp_aon_ll_ext1_clear_wakeup_status(void) /** * @brief Set the wake-up LP_IO of the ext1 wake-up source - * @param mask wakeup LP_IO bitmap, bit 0~7 corresponds to LP_IO 0~7 - * @param mode 0: Wake the chip when any of the selected GPIOs go low - * 1: Wake the chip when any of the selected GPIOs go high + * @param io_mask wakeup LP_IO bitmap, bit 0~7 corresponds to LP_IO 0~7 + * @param level_mask LP_IO wakeup level bitmap, bit 0~7 corresponds to LP_IO 0~7 wakeup level + * each bit's corresponding position is set to 0, the wakeup level will be low + * on the contrary, each bit's corresponding position is set to 1, the wakeup + * level will be high */ -static inline void lp_aon_ll_ext1_set_wakeup_pins(uint32_t mask, int mode) +static inline void lp_aon_ll_ext1_set_wakeup_pins(uint32_t io_mask, uint32_t level_mask) { uint32_t wakeup_sel_mask = HAL_FORCE_READ_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_sel); - wakeup_sel_mask |= mask; + wakeup_sel_mask |= io_mask; HAL_FORCE_MODIFY_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_sel, wakeup_sel_mask); uint32_t wakeup_level_mask = HAL_FORCE_READ_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_lv); - if (mode) { - wakeup_level_mask |= mask; - } else { - wakeup_level_mask &= ~mask; - } + wakeup_level_mask |= io_mask & level_mask; + wakeup_level_mask &= ~(io_mask & ~level_mask); + HAL_FORCE_MODIFY_U32_REG_FIELD(LP_AON.ext_wakeup_cntl, ext_wakeup_lv, wakeup_level_mask); } diff --git a/components/hal/esp32s2/include/hal/rtc_cntl_ll.h b/components/hal/esp32s2/include/hal/rtc_cntl_ll.h index 0ccdedc879..754e9bcf11 100644 --- a/components/hal/esp32s2/include/hal/rtc_cntl_ll.h +++ b/components/hal/esp32s2/include/hal/rtc_cntl_ll.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2020-2023 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -10,6 +10,7 @@ #include "soc/rtc.h" #include "soc/rtc_cntl_reg.h" #include "esp_attr.h" +#include "hal/assert.h" #ifdef __cplusplus extern "C" { @@ -34,11 +35,18 @@ FORCE_INLINE_ATTR uint32_t rtc_cntl_ll_ext1_get_wakeup_status(void) return REG_GET_FIELD(RTC_CNTL_EXT_WAKEUP1_STATUS_REG, RTC_CNTL_EXT_WAKEUP1_STATUS); } -FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_set_wakeup_pins(uint32_t mask, int mode) +FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_set_wakeup_pins(uint32_t io_mask, uint32_t mode_mask) { - REG_SET_FIELD(RTC_CNTL_EXT_WAKEUP1_REG, RTC_CNTL_EXT_WAKEUP1_SEL, mask); - SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, - mode, RTC_CNTL_EXT_WAKEUP1_LV_S); + // The target only supports a unified trigger mode among all EXT1 wakeup IOs + HAL_ASSERT((io_mask & mode_mask) == io_mask || (io_mask & mode_mask) == 0); + REG_SET_FIELD(RTC_CNTL_EXT_WAKEUP1_REG, RTC_CNTL_EXT_WAKEUP1_SEL, io_mask); + if ((io_mask & mode_mask) == io_mask) { + SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, + 1, RTC_CNTL_EXT_WAKEUP1_LV_S); + } else { + SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, + 0, RTC_CNTL_EXT_WAKEUP1_LV_S); + } } FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_clear_wakeup_pins(void) diff --git a/components/hal/esp32s3/include/hal/rtc_cntl_ll.h b/components/hal/esp32s3/include/hal/rtc_cntl_ll.h index 3c3cd9dbf0..ba7121109f 100644 --- a/components/hal/esp32s3/include/hal/rtc_cntl_ll.h +++ b/components/hal/esp32s3/include/hal/rtc_cntl_ll.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2020-2023 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -11,6 +11,7 @@ #include "soc/rtc_cntl_reg.h" #include "soc/syscon_reg.h" #include "esp_attr.h" +#include "hal/assert.h" #ifdef __cplusplus extern "C" { @@ -38,11 +39,18 @@ FORCE_INLINE_ATTR uint32_t rtc_cntl_ll_ext1_get_wakeup_status(void) return REG_GET_FIELD(RTC_CNTL_EXT_WAKEUP1_STATUS_REG, RTC_CNTL_EXT_WAKEUP1_STATUS); } -FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_set_wakeup_pins(uint32_t mask, int mode) +FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_set_wakeup_pins(uint32_t io_mask, uint32_t mode_mask) { - REG_SET_FIELD(RTC_CNTL_EXT_WAKEUP1_REG, RTC_CNTL_EXT_WAKEUP1_SEL, mask); - SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, - mode, RTC_CNTL_EXT_WAKEUP1_LV_S); + // The target only supports a unified trigger mode among all EXT1 wakeup IOs + HAL_ASSERT((io_mask & mode_mask) == io_mask || (io_mask & mode_mask) == 0); + REG_SET_FIELD(RTC_CNTL_EXT_WAKEUP1_REG, RTC_CNTL_EXT_WAKEUP1_SEL, io_mask); + if ((io_mask & mode_mask) == io_mask) { + SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, + 1, RTC_CNTL_EXT_WAKEUP1_LV_S); + } else { + SET_PERI_REG_BITS(RTC_CNTL_EXT_WAKEUP_CONF_REG, 0x1, + 0, RTC_CNTL_EXT_WAKEUP1_LV_S); + } } FORCE_INLINE_ATTR void rtc_cntl_ll_ext1_clear_wakeup_pins(void) diff --git a/components/hal/include/hal/rtc_hal.h b/components/hal/include/hal/rtc_hal.h index ad1dbccf08..99f7c07e66 100644 --- a/components/hal/include/hal/rtc_hal.h +++ b/components/hal/include/hal/rtc_hal.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2020-2023 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -51,15 +51,15 @@ typedef struct rtc_cntl_sleep_retent { #if SOC_PM_SUPPORT_EXT1_WAKEUP -#define rtc_hal_ext1_get_wakeup_status() rtc_cntl_ll_ext1_get_wakeup_status() +#define rtc_hal_ext1_get_wakeup_status() rtc_cntl_ll_ext1_get_wakeup_status() -#define rtc_hal_ext1_clear_wakeup_status() rtc_cntl_ll_ext1_clear_wakeup_status() +#define rtc_hal_ext1_clear_wakeup_status() rtc_cntl_ll_ext1_clear_wakeup_status() -#define rtc_hal_ext1_set_wakeup_pins(mask, mode) rtc_cntl_ll_ext1_set_wakeup_pins(mask, mode) +#define rtc_hal_ext1_set_wakeup_pins(io_mask, mode_mask) rtc_cntl_ll_ext1_set_wakeup_pins(io_mask, mode_mask) -#define rtc_hal_ext1_clear_wakeup_pins() rtc_cntl_ll_ext1_clear_wakeup_pins() +#define rtc_hal_ext1_clear_wakeup_pins() rtc_cntl_ll_ext1_clear_wakeup_pins() -#define rtc_hal_ext1_get_wakeup_pins() rtc_cntl_ll_ext1_get_wakeup_pins() +#define rtc_hal_ext1_get_wakeup_pins() rtc_cntl_ll_ext1_get_wakeup_pins() #endif // SOC_PM_SUPPORT_EXT1_WAKEUP diff --git a/components/soc/esp32c6/include/soc/Kconfig.soc_caps.in b/components/soc/esp32c6/include/soc/Kconfig.soc_caps.in index c3d572d073..10679b6e0d 100644 --- a/components/soc/esp32c6/include/soc/Kconfig.soc_caps.in +++ b/components/soc/esp32c6/include/soc/Kconfig.soc_caps.in @@ -1159,6 +1159,10 @@ config SOC_PM_SUPPORT_EXT1_WAKEUP bool default y +config SOC_PM_SUPPORT_EXT1_WAKEUP_MODE_PER_PIN + bool + default y + config SOC_PM_SUPPORT_CPU_PD bool default y diff --git a/components/soc/esp32c6/include/soc/soc_caps.h b/components/soc/esp32c6/include/soc/soc_caps.h index 52d9b8f7da..823b5d62a5 100644 --- a/components/soc/esp32c6/include/soc/soc_caps.h +++ b/components/soc/esp32c6/include/soc/soc_caps.h @@ -481,6 +481,7 @@ #define SOC_PM_SUPPORT_BEACON_WAKEUP (1) #define SOC_PM_SUPPORT_BT_WAKEUP (1) #define SOC_PM_SUPPORT_EXT1_WAKEUP (1) +#define SOC_PM_SUPPORT_EXT1_WAKEUP_MODE_PER_PIN (1) /*!