diff --git a/components/driver/test_apps/legacy_timer_driver/README.md b/components/driver/test_apps/legacy_timer_driver/README.md index 7b96141437..15bfc62bf3 100644 --- a/components/driver/test_apps/legacy_timer_driver/README.md +++ b/components/driver/test_apps/legacy_timer_driver/README.md @@ -1,2 +1,2 @@ -| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-P4 | ESP32-S2 | ESP32-S3 | -| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | -------- | -------- | -------- | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-H21 | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | --------- | -------- | -------- | -------- | diff --git a/components/esp_driver_gptimer/test_apps/gptimer/README.md b/components/esp_driver_gptimer/test_apps/gptimer/README.md index 7b96141437..15bfc62bf3 100644 --- a/components/esp_driver_gptimer/test_apps/gptimer/README.md +++ b/components/esp_driver_gptimer/test_apps/gptimer/README.md @@ -1,2 +1,2 @@ -| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-P4 | ESP32-S2 | ESP32-S3 | -| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | -------- | -------- | -------- | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-H21 | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | --------- | -------- | -------- | -------- | diff --git a/components/esp_driver_gptimer/test_apps/gptimer/main/CMakeLists.txt b/components/esp_driver_gptimer/test_apps/gptimer/main/CMakeLists.txt index 3fb34ea479..43ba517690 100644 --- a/components/esp_driver_gptimer/test_apps/gptimer/main/CMakeLists.txt +++ b/components/esp_driver_gptimer/test_apps/gptimer/main/CMakeLists.txt @@ -15,6 +15,8 @@ endif() # In order for the cases defined by `TEST_CASE` to be linked into the final elf, # the component can be registered as WHOLE_ARCHIVE -idf_component_register(SRCS ${srcs} - PRIV_REQUIRES unity esp_driver_gptimer esp_driver_gpio - WHOLE_ARCHIVE) +idf_component_register( + SRCS ${srcs} + PRIV_REQUIRES unity esp_driver_gptimer esp_driver_gpio + WHOLE_ARCHIVE +) diff --git a/components/esp_driver_gptimer/test_apps/gptimer/main/test_gptimer.c b/components/esp_driver_gptimer/test_apps/gptimer/main/test_gptimer.c index 757c2f715c..11f8cd0e13 100644 --- a/components/esp_driver_gptimer/test_apps/gptimer/main/test_gptimer.c +++ b/components/esp_driver_gptimer/test_apps/gptimer/main/test_gptimer.c @@ -103,7 +103,7 @@ TEST_CASE("gptimer_wallclock_with_various_clock_sources", "[gptimer]") printf("get raw count of gptimer %d: %llu\r\n", i, value); // convert the raw count to us value = value * 1000000 / timer_resolution_hz[i]; - TEST_ASSERT_UINT_WITHIN(200, 20000, value); + TEST_ASSERT_UINT_WITHIN(400, 20000, value); //200 more threshold for cpu on stop process } printf("restart timers\r\n"); for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) { @@ -121,7 +121,7 @@ TEST_CASE("gptimer_wallclock_with_various_clock_sources", "[gptimer]") printf("get raw count of gptimer %d: %llu\r\n", i, value); // convert the raw count to us value = value * 1000000 / timer_resolution_hz[i]; - TEST_ASSERT_UINT_WITHIN(400, 40000, value); + TEST_ASSERT_UINT_WITHIN(600, 40000, value); //same 200 for cpu time } printf("disable timers\r\n"); for (int i = 0; i < SOC_TIMER_GROUP_TOTAL_TIMERS; i++) { diff --git a/components/esp_hw_support/port/esp32h21/esp_clk_tree.c b/components/esp_hw_support/port/esp32h21/esp_clk_tree.c index d321b399e9..a0c3e5a07d 100644 --- a/components/esp_hw_support/port/esp32h21/esp_clk_tree.c +++ b/components/esp_hw_support/port/esp32h21/esp_clk_tree.c @@ -24,8 +24,15 @@ uint32_t *freq_value) ESP_RETURN_ON_FALSE(precision < ESP_CLK_TREE_SRC_FREQ_PRECISION_INVALID, ESP_ERR_INVALID_ARG, TAG, "unknown precision"); ESP_RETURN_ON_FALSE(freq_value, ESP_ERR_INVALID_ARG, TAG, "null pointer"); +#if !SOC_CLK_TREE_SUPPORTED + // Have only XTAL 32M before clock tree supported + assert(clk_src == SOC_MOD_CLK_XTAL); +#endif uint32_t clk_src_freq = 0; switch (clk_src) { + case SOC_MOD_CLK_XTAL: + clk_src_freq = SOC_XTAL_FREQ_32M * MHZ; + break; case SOC_MOD_CLK_PLL_F48M: clk_src_freq = CLK_LL_PLL_48M_FREQ_MHZ * MHZ; break; @@ -39,8 +46,7 @@ uint32_t *freq_value) break; } - ESP_RETURN_ON_FALSE(clk_src_freq, ESP_FAIL, TAG, - "freq shouldn't be 0, calibration failed"); + ESP_RETURN_ON_FALSE(clk_src_freq, ESP_FAIL, TAG, "freq shouldn't be 0, calibration failed"); *freq_value = clk_src_freq; return ESP_OK; } diff --git a/components/esp_hw_support/test_apps/esp_hw_support_unity_tests/main/CMakeLists.txt b/components/esp_hw_support/test_apps/esp_hw_support_unity_tests/main/CMakeLists.txt index bc5e4d3423..4b26bbdced 100644 --- a/components/esp_hw_support/test_apps/esp_hw_support_unity_tests/main/CMakeLists.txt +++ b/components/esp_hw_support/test_apps/esp_hw_support_unity_tests/main/CMakeLists.txt @@ -21,7 +21,7 @@ if(CONFIG_SOC_ETM_SUPPORTED) list(APPEND srcs "test_etm_core.c") endif() -if(CONFIG_SOC_GPTIMER_SUPPORTED) +if(CONFIG_SOC_GPTIMER_SUPPORTED AND CONFIG_SOC_GPSPI_SUPPORTED) list(APPEND srcs "test_intr_alloc.c") endif() diff --git a/components/esp_system/int_wdt.c b/components/esp_system/int_wdt.c index 50bae64fc3..78fe8e7f80 100644 --- a/components/esp_system/int_wdt.c +++ b/components/esp_system/int_wdt.c @@ -53,7 +53,7 @@ #endif // SOC_TIMER_GROUPS > 1 #if CONFIG_ESP_INT_WDT -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION static const char* TAG = "int_wdt"; static esp_err_t sleep_int_wdt_retention_init(void *arg) { @@ -160,7 +160,7 @@ void esp_int_wdt_init(void) wdt_hal_enable(&iwdt_context); wdt_hal_write_protect_enable(&iwdt_context); -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION esp_int_wdt_retention_enable(IWDT_TIMER_GROUP); #endif diff --git a/components/esp_system/task_wdt/task_wdt_impl_timergroup.c b/components/esp_system/task_wdt/task_wdt_impl_timergroup.c index bb972c2f94..c602f20186 100644 --- a/components/esp_system/task_wdt/task_wdt_impl_timergroup.c +++ b/components/esp_system/task_wdt/task_wdt_impl_timergroup.c @@ -21,7 +21,7 @@ #include "esp_private/periph_ctrl.h" #include "esp_private/esp_task_wdt_impl.h" -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION #include "esp_private/sleep_retention.h" #endif @@ -46,7 +46,7 @@ typedef struct { * init function. */ static twdt_ctx_hard_t init_context; -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION static const char* TAG = "task_wdt"; static esp_err_t sleep_task_wdt_retention_init(void *arg) { @@ -124,7 +124,7 @@ esp_err_t esp_task_wdt_impl_timer_allocate(const esp_task_wdt_config_t *config, /* Return the implementation context to the caller */ *obj = (twdt_ctx_t) ctx; -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION esp_task_wdt_retention_enable(TWDT_TIMER_GROUP); #endif } @@ -171,7 +171,7 @@ void esp_task_wdt_impl_timer_free(twdt_ctx_t obj) /* Deregister interrupt */ ESP_ERROR_CHECK(esp_intr_free(ctx->intr_handle)); -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION ESP_ERROR_CHECK(esp_task_wdt_retention_disable(TWDT_TIMER_GROUP)); #endif } diff --git a/components/esp_system/test_apps/esp_system_unity_tests/main/test_task_wdt.c b/components/esp_system/test_apps/esp_system_unity_tests/main/test_task_wdt.c index c2db367117..274cdc4e72 100644 --- a/components/esp_system/test_apps/esp_system_unity_tests/main/test_task_wdt.c +++ b/components/esp_system/test_apps/esp_system_unity_tests/main/test_task_wdt.c @@ -16,7 +16,7 @@ #include "soc/rtc.h" #include "soc/soc_caps.h" -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION #include "esp_sleep.h" #include "esp_private/esp_sleep_internal.h" #include "esp_private/sleep_cpu.h" @@ -49,7 +49,7 @@ TEST_CASE("Task WDT task timeout", "[task_wdt]") TEST_ASSERT_EQUAL(ESP_OK, esp_task_wdt_deinit()); } -#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if CONFIG_PM_POWER_DOWN_PERIPHERAL_IN_LIGHT_SLEEP && SOC_MWDT_SUPPORT_SLEEP_RETENTION TEST_CASE("Task WDT task timeout after peripheral powerdown lightsleep", "[task_wdt]") { timeout_flag = false; diff --git a/components/hal/esp32h21/include/hal/mwdt_ll.h b/components/hal/esp32h21/include/hal/mwdt_ll.h index f7967e8725..3edf7a87cf 100644 --- a/components/hal/esp32h21/include/hal/mwdt_ll.h +++ b/components/hal/esp32h21/include/hal/mwdt_ll.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -276,31 +276,23 @@ FORCE_INLINE_ATTR void mwdt_ll_set_intr_enable(timg_dev_t *hw, bool enable) * @param hw Beginning address of the peripheral registers. * @param clk_src Clock source */ - FORCE_INLINE_ATTR void mwdt_ll_set_clock_source(timg_dev_t *hw, mwdt_clock_source_t clk_src) { - uint8_t clk_id = 0; + uint8_t group_id = (hw == &TIMERG0) ? 0 : 1; switch (clk_src) { case MWDT_CLK_SRC_XTAL: - clk_id = 0; + PCR.timergroup[group_id].timergroup_wdt_clk_conf.tg_wdt_clk_sel = 0; break; case MWDT_CLK_SRC_RC_FAST: - clk_id = 1; + PCR.timergroup[group_id].timergroup_wdt_clk_conf.tg_wdt_clk_sel = 1; break; case MWDT_CLK_SRC_PLL_F48M: - clk_id = 2; + PCR.timergroup[group_id].timergroup_wdt_clk_conf.tg_wdt_clk_sel = 2; break; default: HAL_ASSERT(false); break; } - - - if (hw == &TIMERG0) { - PCR.timergroup0_wdt_clk_conf.tg0_wdt_clk_sel = clk_id; - } else { - PCR.timergroup1_wdt_clk_conf.tg1_wdt_clk_sel = clk_id; - } } /** @@ -312,11 +304,8 @@ FORCE_INLINE_ATTR void mwdt_ll_set_clock_source(timg_dev_t *hw, mwdt_clock_sourc __attribute__((always_inline)) static inline void mwdt_ll_enable_clock(timg_dev_t *hw, bool en) { - if (hw == &TIMERG0) { - PCR.timergroup0_wdt_clk_conf.tg0_wdt_clk_en = en; - } else { - PCR.timergroup1_wdt_clk_conf.tg1_wdt_clk_en = en; - } + uint8_t group_id = (hw == &TIMERG0) ? 0 : 1; + PCR.timergroup[group_id].timergroup_wdt_clk_conf.tg_wdt_clk_en = en; } #ifdef __cplusplus diff --git a/components/hal/esp32h21/include/hal/timer_ll.h b/components/hal/esp32h21/include/hal/timer_ll.h index d2353ecb0e..b191b23826 100644 --- a/components/hal/esp32h21/include/hal/timer_ll.h +++ b/components/hal/esp32h21/include/hal/timer_ll.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -17,8 +17,6 @@ #include "soc/pcr_struct.h" #include "soc/soc_etm_source.h" -//TODO: [ESP32H21] IDF-11594, inherit from h2 - #ifdef __cplusplus extern "C" { #endif @@ -62,11 +60,7 @@ extern "C" { */ static inline void _timer_ll_enable_bus_clock(int group_id, bool enable) { - if (group_id == 0) { - PCR.timergroup0_conf.tg0_clk_en = enable; - } else { - PCR.timergroup1_conf.tg1_clk_en = enable; - } + PCR.timergroup[group_id].timergroup_conf.tg_clk_en = enable; } /// use a macro to wrap the function, force the caller to use it in a critical section @@ -84,15 +78,11 @@ static inline void _timer_ll_enable_bus_clock(int group_id, bool enable) */ static inline void _timer_ll_reset_register(int group_id) { - if (group_id == 0) { - PCR.timergroup0_conf.tg0_rst_en = 1; - PCR.timergroup0_conf.tg0_rst_en = 0; - TIMERG0.wdtconfig0.wdt_flashboot_mod_en = 0; - } else { - PCR.timergroup1_conf.tg1_rst_en = 1; - PCR.timergroup1_conf.tg1_rst_en = 0; - TIMERG1.wdtconfig0.wdt_flashboot_mod_en = 0; - } + timg_dev_t *hw = TIMER_LL_GET_HW(group_id); + + PCR.timergroup[group_id].timergroup_conf.tg_rst_en = 1; + PCR.timergroup[group_id].timergroup_conf.tg_rst_en = 0; + hw->wdtconfig0.wdt_flashboot_mod_en = 0; } /// use a macro to wrap the function, force the caller to use it in a critical section @@ -109,26 +99,21 @@ static inline void _timer_ll_reset_register(int group_id) static inline void timer_ll_set_clock_source(timg_dev_t *hw, uint32_t timer_num, gptimer_clock_source_t clk_src) { (void)timer_num; // only one timer in each group - uint8_t clk_id = 0; + uint8_t group_id = (hw == &TIMERG0) ? 0 : 1; switch (clk_src) { case GPTIMER_CLK_SRC_XTAL: - clk_id = 0; + PCR.timergroup[group_id].timergroup_timer_clk_conf.tg_timer_clk_sel = 0; break; case GPTIMER_CLK_SRC_RC_FAST: - clk_id = 1; + PCR.timergroup[group_id].timergroup_timer_clk_conf.tg_timer_clk_sel = 1; break; case GPTIMER_CLK_SRC_PLL_F48M: - clk_id = 2; + PCR.timergroup[group_id].timergroup_timer_clk_conf.tg_timer_clk_sel = 2; break; default: HAL_ASSERT(false); break; } - if (hw == &TIMERG0) { - PCR.timergroup0_timer_clk_conf.tg0_timer_clk_sel = clk_id; - } else { - PCR.timergroup1_timer_clk_conf.tg1_timer_clk_sel = clk_id; - } } /** @@ -141,11 +126,9 @@ static inline void timer_ll_set_clock_source(timg_dev_t *hw, uint32_t timer_num, static inline void timer_ll_enable_clock(timg_dev_t *hw, uint32_t timer_num, bool en) { (void)timer_num; // only one timer in each group - if (hw == &TIMERG0) { - PCR.timergroup0_timer_clk_conf.tg0_timer_clk_en = en; - } else { - PCR.timergroup1_timer_clk_conf.tg1_timer_clk_en = en; - } + uint8_t group_id = (hw == &TIMERG0) ? 0 : 1; + + PCR.timergroup[group_id].timergroup_timer_clk_conf.tg_timer_clk_en = en; } /** diff --git a/components/soc/esp32h21/include/soc/Kconfig.soc_caps.in b/components/soc/esp32h21/include/soc/Kconfig.soc_caps.in index 2d7188f64b..e2375e746a 100644 --- a/components/soc/esp32h21/include/soc/Kconfig.soc_caps.in +++ b/components/soc/esp32h21/include/soc/Kconfig.soc_caps.in @@ -7,6 +7,10 @@ config SOC_UART_SUPPORTED bool default y +config SOC_GPTIMER_SUPPORTED + bool + default y + config SOC_EFUSE_KEY_PURPOSE_FIELD bool default y @@ -471,6 +475,10 @@ config SOC_TIMER_GROUP_TIMERS_PER_GROUP int default 1 +config SOC_TIMER_GROUP_TOTAL_TIMERS + int + default 2 + config SOC_TIMER_GROUP_COUNTER_BIT_WIDTH int default 54 @@ -483,9 +491,9 @@ config SOC_TIMER_GROUP_SUPPORT_RC_FAST bool default y -config SOC_TIMER_GROUP_TOTAL_TIMERS - int - default 2 +config SOC_TIMER_SUPPORT_SLEEP_RETENTION + bool + default y config SOC_MWDT_SUPPORT_XTAL bool diff --git a/components/soc/esp32h21/include/soc/clk_tree_defs.h b/components/soc/esp32h21/include/soc/clk_tree_defs.h index 25c9d9b74e..058994ba54 100644 --- a/components/soc/esp32h21/include/soc/clk_tree_defs.h +++ b/components/soc/esp32h21/include/soc/clk_tree_defs.h @@ -158,7 +158,11 @@ typedef enum { * } * @endcode */ +#if SOC_CLK_TREE_SUPPORTED #define SOC_GPTIMER_CLKS {SOC_MOD_CLK_PLL_F48M, SOC_MOD_CLK_RC_FAST, SOC_MOD_CLK_XTAL} +#else +#define SOC_GPTIMER_CLKS {SOC_MOD_CLK_XTAL} +#endif /** * @brief Type of GPTimer clock source @@ -167,7 +171,11 @@ typedef enum { GPTIMER_CLK_SRC_PLL_F48M = SOC_MOD_CLK_PLL_F48M, /*!< Select PLL_F48M as the source clock */ GPTIMER_CLK_SRC_RC_FAST = SOC_MOD_CLK_RC_FAST, /*!< Select RC_FAST as the source clock */ GPTIMER_CLK_SRC_XTAL = SOC_MOD_CLK_XTAL, /*!< Select XTAL as the source clock */ +#if SOC_CLK_TREE_SUPPORTED GPTIMER_CLK_SRC_DEFAULT = SOC_MOD_CLK_PLL_F48M, /*!< Select PLL_F48M as the default choice */ +#else + GPTIMER_CLK_SRC_DEFAULT = SOC_MOD_CLK_XTAL, /*!< Select XTAL as the default choice if no clk_tree */ +#endif } soc_periph_gptimer_clk_src_t; /** @@ -176,7 +184,11 @@ typedef enum { typedef enum { TIMER_SRC_CLK_PLL_F48M = SOC_MOD_CLK_PLL_F48M, /*!< Timer group clock source is PLL_F48M */ TIMER_SRC_CLK_XTAL = SOC_MOD_CLK_XTAL, /*!< Timer group clock source is XTAL */ - TIMER_SRC_CLK_DEFAULT = SOC_MOD_CLK_PLL_F48M, /*!< Timer group clock source default choice is PLL_F48M */ +#if SOC_CLK_TREE_SUPPORTED + TIMER_SRC_CLK_DEFAULT = SOC_MOD_CLK_PLL_F48M, /*!< Select PLL_F48M as the default choice */ +#else + TIMER_SRC_CLK_DEFAULT = SOC_MOD_CLK_XTAL, /*!< Select XTAL as the default choice if no clk_tree */ +#endif } soc_periph_tg_clk_src_legacy_t; ///////////////////////////////////////////////////UART///////////////////////////////////////////////////////////////// diff --git a/components/soc/esp32h21/include/soc/soc_caps.h b/components/soc/esp32h21/include/soc/soc_caps.h index a85199d7c0..8ce5578e70 100644 --- a/components/soc/esp32h21/include/soc/soc_caps.h +++ b/components/soc/esp32h21/include/soc/soc_caps.h @@ -23,7 +23,7 @@ #define SOC_UART_SUPPORTED 1 //TODO: [ESP32H21] IDF-11618 // #define SOC_GDMA_SUPPORTED 1 //TODO: [ESP32H21] IDF-11603 // #define SOC_AHB_GDMA_SUPPORTED 1 //TODO: [ESP32H21] IDF-11603 -// #define SOC_GPTIMER_SUPPORTED 1 //TODO: [ESP32H21] IDF-11594 +#define SOC_GPTIMER_SUPPORTED 1 // #define SOC_BT_SUPPORTED 1 // #define SOC_IEEE802154_SUPPORTED 1 // #define SOC_IEEE802154_BLE_ONLY 1 @@ -436,12 +436,12 @@ /*--------------------------- TIMER GROUP CAPS ---------------------------------------*/ #define SOC_TIMER_GROUPS (2) #define SOC_TIMER_GROUP_TIMERS_PER_GROUP (1U) +#define SOC_TIMER_GROUP_TOTAL_TIMERS (2) #define SOC_TIMER_GROUP_COUNTER_BIT_WIDTH (54) #define SOC_TIMER_GROUP_SUPPORT_XTAL (1) #define SOC_TIMER_GROUP_SUPPORT_RC_FAST (1) -#define SOC_TIMER_GROUP_TOTAL_TIMERS (2) -// #define SOC_TIMER_SUPPORT_ETM (1) -// #define SOC_TIMER_SUPPORT_SLEEP_RETENTION (1) +// #define SOC_TIMER_SUPPORT_ETM (1) //TODO: [ESP32H21] IDF-11576 +#define SOC_TIMER_SUPPORT_SLEEP_RETENTION (1) /*--------------------------- WATCHDOG CAPS ---------------------------------------*/ #define SOC_MWDT_SUPPORT_XTAL (1) diff --git a/components/soc/esp32h21/register/soc/pcr_struct.h b/components/soc/esp32h21/register/soc/pcr_struct.h index 7e3c68bc9c..3346d98feb 100644 --- a/components/soc/esp32h21/register/soc/pcr_struct.h +++ b/components/soc/esp32h21/register/soc/pcr_struct.h @@ -424,145 +424,75 @@ typedef union { uint32_t val; } pcr_ledc_sclk_conf_reg_t; -/** Type of timergroup0_conf register - * TIMERGROUP0 configuration register +/** Type of timergroup_conf register + * TIMERGROUP configuration register */ typedef union { struct { - /** tg0_clk_en : R/W; bitpos: [0]; default: 1; + /** tg_clk_en : R/W; bitpos: [0]; default: 1; * Set 1 to enable timer_group0 apb clock */ - uint32_t tg0_clk_en:1; - /** tg0_rst_en : R/W; bitpos: [1]; default: 0; + uint32_t tg_clk_en:1; + /** tg_rst_en : R/W; bitpos: [1]; default: 0; * Set 0 to reset timer_group0 module */ - uint32_t tg0_rst_en:1; - /** tg0_wdt_ready : RO; bitpos: [2]; default: 1; + uint32_t tg_rst_en:1; + /** tg_wdt_ready : RO; bitpos: [2]; default: 1; * Query this field after reset timer_group0 wdt module */ - uint32_t tg0_wdt_ready:1; - /** tg0_timer0_ready : RO; bitpos: [3]; default: 1; + uint32_t tg_wdt_ready:1; + /** tg_timer0_ready : RO; bitpos: [3]; default: 1; * Query this field after reset timer_group0 timer0 module */ - uint32_t tg0_timer0_ready:1; - /** tg0_timer1_ready : RO; bitpos: [4]; default: 1; + uint32_t tg_timer0_ready:1; + /** tg_timer1_ready : RO; bitpos: [4]; default: 1; * reserved */ - uint32_t tg0_timer1_ready:1; + uint32_t tg_timer1_ready:1; uint32_t reserved_5:27; }; uint32_t val; -} pcr_timergroup0_conf_reg_t; +} pcr_timergroup_conf_reg_t; -/** Type of timergroup0_timer_clk_conf register - * TIMERGROUP0_TIMER_CLK configuration register +/** Type of timergroup_timer_clk_conf register + * TIMERGROUP_TIMER_CLK configuration register */ typedef union { struct { uint32_t reserved_0:20; - /** tg0_timer_clk_sel : R/W; bitpos: [21:20]; default: 0; - * set this field to select clock-source. 0(default): XTAL, 1: 80MHz, 2: FOSC, 3: + /** tg_timer_clk_sel : R/W; bitpos: [21:20]; default: 0; + * set this field to select clock-source. 0(default): XTAL, 1: FOSC, 2: 48MHz, 3: * reserved. */ - uint32_t tg0_timer_clk_sel:2; - /** tg0_timer_clk_en : R/W; bitpos: [22]; default: 1; + uint32_t tg_timer_clk_sel:2; + /** tg_timer_clk_en : R/W; bitpos: [22]; default: 1; * Set 1 to enable timer_group0 timer clock */ - uint32_t tg0_timer_clk_en:1; + uint32_t tg_timer_clk_en:1; uint32_t reserved_23:9; }; uint32_t val; -} pcr_timergroup0_timer_clk_conf_reg_t; +} pcr_timergroup_timer_clk_conf_reg_t; -/** Type of timergroup0_wdt_clk_conf register - * TIMERGROUP0_WDT_CLK configuration register +/** Type of timergroup_wdt_clk_conf register + * TIMERGROUP_WDT_CLK configuration register */ typedef union { struct { uint32_t reserved_0:20; - /** tg0_wdt_clk_sel : R/W; bitpos: [21:20]; default: 0; - * set this field to select clock-source. 0(default): XTAL, 1: 80MHz, 2: FOSC, 3: + /** tg_wdt_clk_sel : R/W; bitpos: [21:20]; default: 0; + * set this field to select clock-source. 0(default): XTAL, 1: FOSC, 2: 48MHz, 3: * reserved. */ - uint32_t tg0_wdt_clk_sel:2; - /** tg0_wdt_clk_en : R/W; bitpos: [22]; default: 1; + uint32_t tg_wdt_clk_sel:2; + /** tg_wdt_clk_en : R/W; bitpos: [22]; default: 1; * Set 1 to enable timer_group0 wdt clock */ - uint32_t tg0_wdt_clk_en:1; + uint32_t tg_wdt_clk_en:1; uint32_t reserved_23:9; }; uint32_t val; -} pcr_timergroup0_wdt_clk_conf_reg_t; - -/** Type of timergroup1_conf register - * TIMERGROUP1 configuration register - */ -typedef union { - struct { - /** tg1_clk_en : R/W; bitpos: [0]; default: 1; - * Set 1 to enable timer_group1 apb clock - */ - uint32_t tg1_clk_en:1; - /** tg1_rst_en : R/W; bitpos: [1]; default: 0; - * Set 0 to reset timer_group1 module - */ - uint32_t tg1_rst_en:1; - /** tg1_wdt_ready : RO; bitpos: [2]; default: 1; - * Query this field after reset timer_group1 wdt module - */ - uint32_t tg1_wdt_ready:1; - /** tg1_timer0_ready : RO; bitpos: [3]; default: 1; - * Query this field after reset timer_group1 timer0 module - */ - uint32_t tg1_timer0_ready:1; - /** tg1_timer1_ready : RO; bitpos: [4]; default: 1; - * reserved - */ - uint32_t tg1_timer1_ready:1; - uint32_t reserved_5:27; - }; - uint32_t val; -} pcr_timergroup1_conf_reg_t; - -/** Type of timergroup1_timer_clk_conf register - * TIMERGROUP1_TIMER_CLK configuration register - */ -typedef union { - struct { - uint32_t reserved_0:20; - /** tg1_timer_clk_sel : R/W; bitpos: [21:20]; default: 0; - * set this field to select clock-source. 0(default): XTAL, 1: 80MHz, 2: FOSC, 3: - * reserved. - */ - uint32_t tg1_timer_clk_sel:2; - /** tg1_timer_clk_en : R/W; bitpos: [22]; default: 1; - * Set 1 to enable timer_group1 timer clock - */ - uint32_t tg1_timer_clk_en:1; - uint32_t reserved_23:9; - }; - uint32_t val; -} pcr_timergroup1_timer_clk_conf_reg_t; - -/** Type of timergroup1_wdt_clk_conf register - * TIMERGROUP1_WDT_CLK configuration register - */ -typedef union { - struct { - uint32_t reserved_0:20; - /** tg1_wdt_clk_sel : R/W; bitpos: [21:20]; default: 0; - * set this field to select clock-source. 0(default): XTAL, 1: 80MHz, 2: FOSC, 3: - * reserved. - */ - uint32_t tg1_wdt_clk_sel:2; - /** tg1_wdt_clk_en : R/W; bitpos: [22]; default: 1; - * Set 1 to enable timer_group0 wdt clock - */ - uint32_t tg1_wdt_clk_en:1; - uint32_t reserved_23:9; - }; - uint32_t val; -} pcr_timergroup1_wdt_clk_conf_reg_t; +} pcr_timergroup_wdt_clk_conf_reg_t; /** Type of systimer_conf register * SYSTIMER configuration register @@ -1944,6 +1874,13 @@ typedef union { uint32_t val; } pcr_date_reg_t; +/** Type of timergroup PCR config register + */ +typedef struct { + volatile pcr_timergroup_conf_reg_t timergroup_conf; + volatile pcr_timergroup_timer_clk_conf_reg_t timergroup_timer_clk_conf; + volatile pcr_timergroup_wdt_clk_conf_reg_t timergroup_wdt_clk_conf; +} pcr_timergroup_reg_t; typedef struct { volatile pcr_uart0_conf_reg_t uart0_conf; @@ -1963,12 +1900,7 @@ typedef struct { volatile pcr_rmt_sclk_conf_reg_t rmt_sclk_conf; volatile pcr_ledc_conf_reg_t ledc_conf; volatile pcr_ledc_sclk_conf_reg_t ledc_sclk_conf; - volatile pcr_timergroup0_conf_reg_t timergroup0_conf; - volatile pcr_timergroup0_timer_clk_conf_reg_t timergroup0_timer_clk_conf; - volatile pcr_timergroup0_wdt_clk_conf_reg_t timergroup0_wdt_clk_conf; - volatile pcr_timergroup1_conf_reg_t timergroup1_conf; - volatile pcr_timergroup1_timer_clk_conf_reg_t timergroup1_timer_clk_conf; - volatile pcr_timergroup1_wdt_clk_conf_reg_t timergroup1_wdt_clk_conf; + volatile pcr_timergroup_reg_t timergroup[2]; volatile pcr_systimer_conf_reg_t systimer_conf; volatile pcr_systimer_func_clk_conf_reg_t systimer_func_clk_conf; volatile pcr_twai0_conf_reg_t twai0_conf; diff --git a/components/soc/esp32h21/register/soc/timer_group_struct.h b/components/soc/esp32h21/register/soc/timer_group_struct.h index c5360f1c0b..08fcb25372 100644 --- a/components/soc/esp32h21/register/soc/timer_group_struct.h +++ b/components/soc/esp32h21/register/soc/timer_group_struct.h @@ -531,7 +531,7 @@ typedef struct { volatile timg_txload_reg_t load; } timg_hwtimer_reg_t; -typedef struct { +typedef struct timg_dev_t { volatile timg_hwtimer_reg_t hw_timer[1]; uint32_t reserved_024[9]; volatile timg_wdtconfig0_reg_t wdtconfig0; diff --git a/components/soc/esp32h21/timer_periph.c b/components/soc/esp32h21/timer_periph.c new file mode 100644 index 0000000000..08db6213f1 --- /dev/null +++ b/components/soc/esp32h21/timer_periph.c @@ -0,0 +1,131 @@ +/* + * SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#include "soc/timer_periph.h" + +const timer_group_signal_conn_t timer_group_periph_signals = { + .groups = { + [0] = { + .module = PERIPH_TIMG0_MODULE, + .timer_irq_id = { + [0] = ETS_TG0_T0_INTR_SOURCE, + } + }, + [1] = { + .module = PERIPH_TIMG1_MODULE, + .timer_irq_id = { + [0] = ETS_TG1_T0_INTR_SOURCE, + } + } + } +}; + +#if SOC_PAU_SUPPORTED && SOC_TIMER_SUPPORT_SLEEP_RETENTION +/* Registers in retention context: + * TIMG_T0CONFIG_REG + * TIMG_T0ALARMLO_REG + * TIMG_T0ALARMHI_REG + * TIMG_T0LOADLO_REG + * TIMG_T0LOADHI_REG + * TIMG_INT_ENA_TIMERS_REG + * TIMG_REGCLK_REG + */ +#define TG_TIMER_RETENTION_REGS_CNT 7 +static const uint32_t tg_timer_regs_map[4] = {0x100000f1, 0x80000000, 0x0, 0x0}; + +const regdma_entries_config_t tg0_timer_regdma_entries[] = { + // backup stage: trigger a soft capture + [0] = { + .config = REGDMA_LINK_WRITE_INIT(REGDMA_TG0_TIMER_LINK(0x00), + TIMG_T0UPDATE_REG(0), TIMG_T0_UPDATE, TIMG_T0_UPDATE_M, 0, 1), + .owner = ENTRY(0) | ENTRY(2) + }, + // backup stage: wait for the capture done + [1] = { + .config = REGDMA_LINK_WAIT_INIT(REGDMA_TG0_TIMER_LINK(0x01), + TIMG_T0UPDATE_REG(0), 0x0, TIMG_T0_UPDATE_M, 0, 1), + .owner = ENTRY(0) | ENTRY(2) + }, + // backup stage: save the captured counter value + // restore stage: store the captured counter value to the loader register + [2] = { + .config = REGDMA_LINK_CONTINUOUS_INIT(REGDMA_TG0_TIMER_LINK(0x02), + TIMG_T0LO_REG(0), TIMG_T0LOADLO_REG(0), 2, 0, 0), + .owner = ENTRY(0) | ENTRY(2) + }, + // restore stage: trigger a soft reload, so the timer can continue from where it was backed up + [3] = { + .config = REGDMA_LINK_WRITE_INIT(REGDMA_TG0_TIMER_LINK(0x03), + TIMG_T0LOAD_REG(0), 0x1, TIMG_T0_LOAD_M, 1, 0), + .owner = ENTRY(0) | ENTRY(2) + }, + // backup stage: save other configuration and status registers + // restore stage: restore the configuration and status registers + [4] = { + .config = REGDMA_LINK_ADDR_MAP_INIT(REGDMA_TG0_TIMER_LINK(0x04), + TIMG_T0CONFIG_REG(0), TIMG_T0CONFIG_REG(0), + TG_TIMER_RETENTION_REGS_CNT, 0, 0, + tg_timer_regs_map[0], tg_timer_regs_map[1], + tg_timer_regs_map[2], tg_timer_regs_map[3]), + .owner = ENTRY(0) | ENTRY(2) + }, +}; + +const regdma_entries_config_t tg1_timer_regdma_entries[] = { + // backup stage: trigger a soft capture + [0] = { + .config = REGDMA_LINK_WRITE_INIT(REGDMA_TG1_TIMER_LINK(0x00), + TIMG_T0UPDATE_REG(1), TIMG_T0_UPDATE, TIMG_T0_UPDATE_M, 0, 1), + .owner = ENTRY(0) | ENTRY(2) + }, + // backup stage: wait for the capture done + [1] = { + .config = REGDMA_LINK_WAIT_INIT(REGDMA_TG1_TIMER_LINK(0x01), + TIMG_T0UPDATE_REG(1), 0x0, TIMG_T0_UPDATE_M, 0, 1), + .owner = ENTRY(0) | ENTRY(2) + }, + // backup stage: save the captured counter value + // restore stage: store the captured counter value to the loader register + [2] = { + .config = REGDMA_LINK_CONTINUOUS_INIT(REGDMA_TG1_TIMER_LINK(0x02), + TIMG_T0LO_REG(1), TIMG_T0LOADLO_REG(1), 2, 0, 0), + .owner = ENTRY(0) | ENTRY(2) + }, + // restore stage: trigger a soft reload, so the timer can continue from where it was backed up + [3] = { + .config = REGDMA_LINK_WRITE_INIT(REGDMA_TG1_TIMER_LINK(0x03), + TIMG_T0LOAD_REG(1), 0x1, TIMG_T0_LOAD_M, 1, 0), + .owner = ENTRY(0) | ENTRY(2) + }, + // backup stage: save other configuration and status registers + // restore stage: restore the configuration and status registers + [4] = { + .config = REGDMA_LINK_ADDR_MAP_INIT(REGDMA_TG1_TIMER_LINK(0x04), + TIMG_T0CONFIG_REG(1), TIMG_T0CONFIG_REG(1), + TG_TIMER_RETENTION_REGS_CNT, 0, 0, + tg_timer_regs_map[0], tg_timer_regs_map[1], + tg_timer_regs_map[2], tg_timer_regs_map[3]), + .owner = ENTRY(0) | ENTRY(2) + }, +}; + +const tg_timer_reg_retention_info_t tg_timer_reg_retention_info[SOC_TIMER_GROUPS][SOC_TIMER_GROUP_TIMERS_PER_GROUP] = { + [0] = { + [0] = { + .module = SLEEP_RETENTION_MODULE_TG0_TIMER0, + .regdma_entry_array = tg0_timer_regdma_entries, + .array_size = ARRAY_SIZE(tg0_timer_regdma_entries) + } + }, + [1] = { + [0] = { + .module = SLEEP_RETENTION_MODULE_TG1_TIMER0, + .regdma_entry_array = tg1_timer_regdma_entries, + .array_size = ARRAY_SIZE(tg1_timer_regdma_entries) + } + }, +}; +#endif //SOC_PAU_SUPPORTED && SOC_TIMER_SUPPORT_SLEEP_RETENTION diff --git a/components/soc/include/soc/timer_periph.h b/components/soc/include/soc/timer_periph.h index 2907c3bac3..faa9bb7c45 100644 --- a/components/soc/include/soc/timer_periph.h +++ b/components/soc/include/soc/timer_periph.h @@ -13,9 +13,9 @@ #include "soc/periph_defs.h" #include "soc/regdma.h" -#if SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if SOC_PAU_SUPPORTED #include "soc/retention_periph_defs.h" -#endif // SOC_TIMER_SUPPORT_SLEEP_RETENTION +#endif // SOC_PAU_SUPPORTED #ifdef __cplusplus extern "C" { @@ -30,7 +30,7 @@ typedef struct { extern const timer_group_signal_conn_t timer_group_periph_signals; -#if SOC_TIMER_SUPPORT_SLEEP_RETENTION +#if SOC_PAU_SUPPORTED && SOC_TIMER_SUPPORT_SLEEP_RETENTION typedef struct { const periph_retention_module_t module; const regdma_entries_config_t *regdma_entry_array; diff --git a/docs/docs_not_updated/esp32h21.txt b/docs/docs_not_updated/esp32h21.txt index 5b315478e6..4247a52b75 100644 --- a/docs/docs_not_updated/esp32h21.txt +++ b/docs/docs_not_updated/esp32h21.txt @@ -172,7 +172,6 @@ api-reference/peripherals/cap_touch_sens.rst api-reference/peripherals/index.rst api-reference/peripherals/rmt.rst api-reference/peripherals/ds.rst -api-reference/peripherals/gptimer.rst api-reference/peripherals/sdio_slave.rst api-reference/peripherals/bitscrambler.rst api-reference/peripherals/temp_sensor.rst diff --git a/examples/peripherals/.build-test-rules.yml b/examples/peripherals/.build-test-rules.yml index 7fc3a4a152..771f2d984f 100644 --- a/examples/peripherals/.build-test-rules.yml +++ b/examples/peripherals/.build-test-rules.yml @@ -448,7 +448,7 @@ examples/peripherals/timer_group/gptimer: examples/peripherals/timer_group/gptimer_capture_hc_sr04: disable: - - if: SOC_GPTIMER_SUPPORTED != 1 or SOC_TIMER_SUPPORT_ETM != 1 + - if: SOC_ETM_SUPPORTED != 1 or SOC_TIMER_SUPPORT_ETM != 1 depends_components: - esp_driver_gptimer diff --git a/examples/peripherals/timer_group/gptimer/README.md b/examples/peripherals/timer_group/gptimer/README.md index fd9d9811d8..152fb42822 100644 --- a/examples/peripherals/timer_group/gptimer/README.md +++ b/examples/peripherals/timer_group/gptimer/README.md @@ -1,5 +1,5 @@ -| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-P4 | ESP32-S2 | ESP32-S3 | -| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | -------- | -------- | -------- | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-H21 | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | --------- | -------- | -------- | -------- | # Example: General Purpose Timer diff --git a/examples/peripherals/timer_group/wiegand_interface/README.md b/examples/peripherals/timer_group/wiegand_interface/README.md index 794c25b0f7..5aff7db3b0 100644 --- a/examples/peripherals/timer_group/wiegand_interface/README.md +++ b/examples/peripherals/timer_group/wiegand_interface/README.md @@ -1,5 +1,5 @@ -| Supported Targets | ESP32 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-P4 | ESP32-S2 | ESP32-S3 | -| ----------------- | ----- | -------- | -------- | -------- | --------- | -------- | -------- | -------- | -------- | +| Supported Targets | ESP32 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-H21 | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | ----- | -------- | -------- | -------- | --------- | -------- | --------- | -------- | -------- | -------- | # Wiegand Interface Example diff --git a/examples/system/sysview_tracing/README.md b/examples/system/sysview_tracing/README.md index ffd33ae877..acf5b1ea61 100644 --- a/examples/system/sysview_tracing/README.md +++ b/examples/system/sysview_tracing/README.md @@ -1,5 +1,5 @@ -| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-P4 | ESP32-S2 | ESP32-S3 | -| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | -------- | -------- | -------- | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-H21 | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | --------- | -------- | -------- | -------- | # Example: Application Level Tracing - SystemView Tracing (sysview_tracing) This test code shows how to perform system-wide behavioral analysis of the program using [SEGGER SystemView tool](https://www.segger.com/products/development-tools/systemview/). diff --git a/examples/system/sysview_tracing_heap_log/README.md b/examples/system/sysview_tracing_heap_log/README.md index be71899cc7..3f2999bcf5 100644 --- a/examples/system/sysview_tracing_heap_log/README.md +++ b/examples/system/sysview_tracing_heap_log/README.md @@ -1,5 +1,5 @@ -| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-P4 | ESP32-S2 | ESP32-S3 | -| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | -------- | -------- | -------- | +| Supported Targets | ESP32 | ESP32-C2 | ESP32-C3 | ESP32-C5 | ESP32-C6 | ESP32-C61 | ESP32-H2 | ESP32-H21 | ESP32-P4 | ESP32-S2 | ESP32-S3 | +| ----------------- | ----- | -------- | -------- | -------- | -------- | --------- | -------- | --------- | -------- | -------- | -------- | # SystemView Heap and Log Tracing Example