diff --git a/components/bootloader_support/src/esp32c5/bootloader_esp32c5.c b/components/bootloader_support/src/esp32c5/bootloader_esp32c5.c index 163dadd207..bd7511fa91 100644 --- a/components/bootloader_support/src/esp32c5/bootloader_esp32c5.c +++ b/components/bootloader_support/src/esp32c5/bootloader_esp32c5.c @@ -43,6 +43,7 @@ #include "hal/lpwdt_ll.h" #include "hal/regi2c_ctrl_ll.h" #include "hal/brownout_ll.h" +#include "hal/axi_icm_ll.h" static const char *TAG = "boot.esp32c5"; @@ -85,6 +86,9 @@ static void bootloader_super_wdt_auto_feed(void) static inline void bootloader_hardware_init(void) { + // Clear bit reset_event_bypass to ensure that the system bus is also reset during a core reset (WDT), + // preventing bus freezing caused by an incorrect MSPI core reset in ROM. + axi_icm_ll_reset_with_core_reset(true); _regi2c_ctrl_ll_master_enable_clock(true); // keep ana i2c mst clock always enabled in bootloader regi2c_ctrl_ll_master_force_enable_clock(true); // TODO: IDF-8667 Remove this? regi2c_ctrl_ll_master_configure_clock(); diff --git a/components/bootloader_support/src/esp32c61/bootloader_esp32c61.c b/components/bootloader_support/src/esp32c61/bootloader_esp32c61.c index 449649b714..55137ac2e6 100644 --- a/components/bootloader_support/src/esp32c61/bootloader_esp32c61.c +++ b/components/bootloader_support/src/esp32c61/bootloader_esp32c61.c @@ -44,6 +44,7 @@ #include "hal/lpwdt_ll.h" #include "hal/regi2c_ctrl_ll.h" #include "hal/brownout_ll.h" +#include "hal/axi_icm_ll.h" static const char *TAG = "boot.esp32c61"; @@ -86,6 +87,9 @@ static void bootloader_super_wdt_auto_feed(void) static inline void bootloader_hardware_init(void) { + // Clear bit reset_event_bypass to ensure that the system bus is also reset during a core reset (WDT), + // preventing bus freezing caused by an incorrect MSPI core reset in ROM. + axi_icm_ll_reset_with_core_reset(true); _regi2c_ctrl_ll_master_enable_clock(true); // keep ana i2c mst clock always enabled in bootloader regi2c_ctrl_ll_master_force_enable_clock(true); // TODO: IDF-9274 Remove this? regi2c_ctrl_ll_master_configure_clock(); diff --git a/components/esp_system/port/soc/esp32c5/system_internal.c b/components/esp_system/port/soc/esp32c5/system_internal.c index c5608e4a37..b62820da4a 100644 --- a/components/esp_system/port/soc/esp32c5/system_internal.c +++ b/components/esp_system/port/soc/esp32c5/system_internal.c @@ -48,6 +48,7 @@ void esp_system_reset_modules_on_exit(void) modem_lpcon_ll_reset_all(&MODEM_LPCON); #endif // Set Peripheral clk rst + SET_PERI_REG_MASK(PCR_MSPI_CLK_CONF_REG, PCR_MSPI_AXI_RST_EN); // Must reset mspi AXI before reset mspi core. SET_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); SET_PERI_REG_MASK(PCR_UART0_CONF_REG, PCR_UART0_RST_EN); SET_PERI_REG_MASK(PCR_UART1_CONF_REG, PCR_UART1_RST_EN); @@ -59,9 +60,11 @@ void esp_system_reset_modules_on_exit(void) SET_PERI_REG_MASK(PCR_SDIO_SLAVE_CONF_REG, PCR_SDIO_SLAVE_RST_EN); //ETM may directly control the GPIO or other peripherals even after CPU reset. Reset to stop these control. SET_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + SET_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Clear Peripheral clk rst CLEAR_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); + CLEAR_PERI_REG_MASK(PCR_MSPI_CLK_CONF_REG, PCR_MSPI_AXI_RST_EN); // Must release mspi core reset before mspi AXI. CLEAR_PERI_REG_MASK(PCR_UART0_CONF_REG, PCR_UART0_RST_EN); CLEAR_PERI_REG_MASK(PCR_UART1_CONF_REG, PCR_UART1_RST_EN); CLEAR_PERI_REG_MASK(PCR_SYSTIMER_CONF_REG, PCR_SYSTIMER_RST_EN); @@ -70,6 +73,7 @@ void esp_system_reset_modules_on_exit(void) CLEAR_PERI_REG_MASK(PCR_PWM_CONF_REG, PCR_PWM_RST_EN); CLEAR_PERI_REG_MASK(PCR_SDIO_SLAVE_CONF_REG, PCR_SDIO_SLAVE_RST_EN); CLEAR_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + CLEAR_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Reset crypto peripherals. This ensures a clean state for the crypto peripherals after a CPU restart // and hence avoiding any possibility with crypto failure in ROM security workflows. diff --git a/components/esp_system/port/soc/esp32c6/system_internal.c b/components/esp_system/port/soc/esp32c6/system_internal.c index 98536cfae9..a811b0cb12 100644 --- a/components/esp_system/port/soc/esp32c6/system_internal.c +++ b/components/esp_system/port/soc/esp32c6/system_internal.c @@ -53,6 +53,7 @@ void esp_system_reset_modules_on_exit(void) SET_PERI_REG_MASK(PCR_PWM_CONF_REG, PCR_PWM_RST_EN); //ETM may directly control the GPIO or other peripherals even after CPU reset. Reset to stop these control. SET_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + SET_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Clear Peripheral clk rst CLEAR_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); @@ -79,6 +80,7 @@ void esp_system_reset_modules_on_exit(void) CLEAR_PERI_REG_MASK(PCR_HMAC_CONF_REG, PCR_HMAC_RST_EN); CLEAR_PERI_REG_MASK(PCR_RSA_CONF_REG, PCR_RSA_RST_EN); CLEAR_PERI_REG_MASK(PCR_SHA_CONF_REG, PCR_SHA_RST_EN); + CLEAR_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // UART's sclk is controlled in the PCR register and does not reset with the UART module. The ROM missed enabling // it when initializing the ROM UART. If it is not turned on, it will trigger LP_WDT in the ROM. diff --git a/components/esp_system/port/soc/esp32c61/system_internal.c b/components/esp_system/port/soc/esp32c61/system_internal.c index 60d38fdd3e..896dc34e3c 100644 --- a/components/esp_system/port/soc/esp32c61/system_internal.c +++ b/components/esp_system/port/soc/esp32c61/system_internal.c @@ -48,6 +48,7 @@ void esp_system_reset_modules_on_exit(void) #endif // Set Peripheral clk rst + SET_PERI_REG_MASK(PCR_MSPI_CLK_CONF_REG, PCR_MSPI_AXI_RST_EN); // Must reset mspi AXI before reset mspi core. SET_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); SET_PERI_REG_MASK(PCR_UART0_CONF_REG, PCR_UART0_RST_EN); SET_PERI_REG_MASK(PCR_UART1_CONF_REG, PCR_UART1_RST_EN); @@ -58,8 +59,10 @@ void esp_system_reset_modules_on_exit(void) SET_PERI_REG_MASK(PCR_SDIO_SLAVE_CONF_REG, PCR_SDIO_SLAVE_RST_EN); //ETM may directly control the GPIO or other peripherals even after CPU reset. Reset to stop these control. SET_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + SET_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Clear Peripheral clk rst + CLEAR_PERI_REG_MASK(PCR_MSPI_CLK_CONF_REG, PCR_MSPI_AXI_RST_EN); // Must release mspi core reset before mspi AXI. CLEAR_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); CLEAR_PERI_REG_MASK(PCR_UART0_CONF_REG, PCR_UART0_RST_EN); CLEAR_PERI_REG_MASK(PCR_UART1_CONF_REG, PCR_UART1_RST_EN); @@ -68,6 +71,7 @@ void esp_system_reset_modules_on_exit(void) CLEAR_PERI_REG_MASK(PCR_MODEM_CONF_REG, PCR_MODEM_RST_EN); CLEAR_PERI_REG_MASK(PCR_SDIO_SLAVE_CONF_REG, PCR_SDIO_SLAVE_RST_EN); CLEAR_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + CLEAR_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Reset crypto peripherals. This ensures a clean state for the crypto peripherals after a CPU restart // and hence avoiding any possibility with crypto failure in ROM security workflows. diff --git a/components/esp_system/port/soc/esp32h2/system_internal.c b/components/esp_system/port/soc/esp32h2/system_internal.c index afd0384c70..88c6e8511e 100644 --- a/components/esp_system/port/soc/esp32h2/system_internal.c +++ b/components/esp_system/port/soc/esp32h2/system_internal.c @@ -50,6 +50,7 @@ void esp_system_reset_modules_on_exit(void) SET_PERI_REG_MASK(PCR_PWM_CONF_REG, PCR_PWM_RST_EN); //ETM may directly control the GPIO or other peripherals even after CPU reset. Reset to stop these control. SET_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + SET_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Clear Peripheral clk rst CLEAR_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); @@ -60,6 +61,7 @@ void esp_system_reset_modules_on_exit(void) CLEAR_PERI_REG_MASK(PCR_MODEM_CONF_REG, PCR_MODEM_RST_EN); CLEAR_PERI_REG_MASK(PCR_PWM_CONF_REG, PCR_PWM_RST_EN); CLEAR_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + CLEAR_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Reset crypto peripherals. This ensures a clean state for the crypto peripherals after a CPU restart // and hence avoiding any possibility with crypto failure in ROM security workflows. diff --git a/components/esp_system/port/soc/esp32h21/system_internal.c b/components/esp_system/port/soc/esp32h21/system_internal.c index 9ce076894c..4f64427deb 100644 --- a/components/esp_system/port/soc/esp32h21/system_internal.c +++ b/components/esp_system/port/soc/esp32h21/system_internal.c @@ -50,6 +50,7 @@ void esp_system_reset_modules_on_exit(void) SET_PERI_REG_MASK(PCR_PWM_CONF_REG, PCR_PWM_RST_EN); //ETM may directly control the GPIO or other peripherals even after CPU reset. Reset to stop these control. SET_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + SET_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Clear Peripheral clk rst CLEAR_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); @@ -60,6 +61,7 @@ void esp_system_reset_modules_on_exit(void) CLEAR_PERI_REG_MASK(PCR_MODEM_CONF_REG, PCR_MODEM_RST_EN); CLEAR_PERI_REG_MASK(PCR_PWM_CONF_REG, PCR_PWM_RST_EN); CLEAR_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + CLEAR_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Reset crypto peripherals. This ensures a clean state for the crypto peripherals after a CPU restart // and hence avoiding any possibility with crypto failure in ROM security workflows. diff --git a/components/esp_system/port/soc/esp32h4/system_internal.c b/components/esp_system/port/soc/esp32h4/system_internal.c index 2c8dd1a8c9..a29680fa34 100644 --- a/components/esp_system/port/soc/esp32h4/system_internal.c +++ b/components/esp_system/port/soc/esp32h4/system_internal.c @@ -35,6 +35,7 @@ void esp_system_reset_modules_on_exit(void) } // Set Peripheral clk rst + SET_PERI_REG_MASK(PCR_MSPI_CLK_CONF_REG, PCR_MSPI_AXI_RST_EN); // Must reset mspi AXI before reset mspi core. SET_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); SET_PERI_REG_MASK(PCR_UART0_CONF_REG, PCR_UART0_RST_EN); SET_PERI_REG_MASK(PCR_UART1_CONF_REG, PCR_UART1_RST_EN); @@ -45,9 +46,11 @@ void esp_system_reset_modules_on_exit(void) SET_PERI_REG_MASK(PCR_PWM1_CONF_REG, PCR_PWM1_RST_EN); //ETM may directly control the GPIO or other peripherals even after CPU reset. Reset to stop these control. SET_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + SET_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Clear Peripheral clk rst CLEAR_PERI_REG_MASK(PCR_MSPI_CONF_REG, PCR_MSPI_RST_EN); + CLEAR_PERI_REG_MASK(PCR_MSPI_CLK_CONF_REG, PCR_MSPI_AXI_RST_EN); // Must release mspi core reset before mspi AXI. CLEAR_PERI_REG_MASK(PCR_UART0_CONF_REG, PCR_UART0_RST_EN); CLEAR_PERI_REG_MASK(PCR_UART1_CONF_REG, PCR_UART1_RST_EN); CLEAR_PERI_REG_MASK(PCR_SYSTIMER_CONF_REG, PCR_SYSTIMER_RST_EN); @@ -56,6 +59,7 @@ void esp_system_reset_modules_on_exit(void) CLEAR_PERI_REG_MASK(PCR_PWM0_CONF_REG, PCR_PWM0_RST_EN); CLEAR_PERI_REG_MASK(PCR_PWM1_CONF_REG, PCR_PWM1_RST_EN); CLEAR_PERI_REG_MASK(PCR_ETM_CONF_REG, PCR_ETM_RST_EN); + CLEAR_PERI_REG_MASK(PCR_REGDMA_CONF_REG, PCR_REGDMA_RST_EN); // Reset crypto peripherals. This ensures a clean state for the crypto peripherals after a CPU restart // and hence avoiding any possibility with crypto failure in ROM security workflows. diff --git a/components/hal/esp32c5/include/hal/axi_icm_ll.h b/components/hal/esp32c5/include/hal/axi_icm_ll.h index 903a49490d..fd975954bb 100644 --- a/components/hal/esp32c5/include/hal/axi_icm_ll.h +++ b/components/hal/esp32c5/include/hal/axi_icm_ll.h @@ -7,8 +7,10 @@ #include #include +#include #include "hal/assert.h" #include "soc/hp_system_struct.h" +#include "soc/pcr_struct.h" #ifdef __cplusplus extern "C" { @@ -36,6 +38,15 @@ static inline void axi_icm_ll_set_cache_arbiter_prio(uint8_t priority) HP_SYSTEM.axi_mst_pri.cache_priority = priority; } +/** + * @brief Reset system bus with soc core reset. + * @param reset_with_core_reset True to reset system bus with soc core reset. + */ +static inline void axi_icm_ll_reset_with_core_reset(bool reset_with_core_reset) +{ + PCR.reset_event_bypass.reset_event_bypass = !reset_with_core_reset; +} + #ifdef __cplusplus } #endif diff --git a/components/hal/esp32c61/include/hal/axi_icm_ll.h b/components/hal/esp32c61/include/hal/axi_icm_ll.h index 1742a9933c..4cf121d6d7 100644 --- a/components/hal/esp32c61/include/hal/axi_icm_ll.h +++ b/components/hal/esp32c61/include/hal/axi_icm_ll.h @@ -7,8 +7,10 @@ #include #include +#include #include "hal/assert.h" #include "soc/hp_system_struct.h" +#include "soc/pcr_struct.h" #ifdef __cplusplus extern "C" { @@ -36,6 +38,15 @@ static inline void axi_icm_ll_set_cache_arbiter_prio(uint8_t priority) HP_SYSTEM.system_axi_mst_pri.system_cache_priority = priority; } +/** + * @brief Reset system bus with soc core reset. + * @param reset_with_core_reset True to reset system bus with soc core reset. + */ +static inline void axi_icm_ll_reset_with_core_reset(bool reset_with_core_reset) +{ + PCR.reset_event_bypass.reset_event_bypass = !reset_with_core_reset; +} + #ifdef __cplusplus } #endif diff --git a/components/soc/esp32c61/register/soc/pcr_struct.h b/components/soc/esp32c61/register/soc/pcr_struct.h index 9e36f9e790..97b48ecdb5 100644 --- a/components/soc/esp32c61/register/soc/pcr_struct.h +++ b/components/soc/esp32c61/register/soc/pcr_struct.h @@ -1774,6 +1774,30 @@ typedef union { uint32_t val; } pcr_timergroup_xtal_conf_reg_t; +/** Type of reset_event_bypass register + * reset event bypass backdoor configuration register + */ +typedef union { + struct { + /** reset_event_bypass_apm : R/W; bitpos: [0]; default: 0; + * This field is used to control reset event relationship for + * tee_reg/apm_reg/hp_system_reg. 1: tee_reg/apm_reg/hp_system_reg will only be reset + * by power-reset. some reset event will be bypass. 0: tee_reg/apm_reg/hp_system_reg + * will not only be reset by power-reset, but also some reset event. + */ + uint32_t reset_event_bypass_apm:1; + /** reset_event_bypass : R/W; bitpos: [1]; default: 1; + * This field is used to control reset event relationship for system-bus. 1: system + * bus (including arbiter/router) will only be reset by power-reset. some reset event + * will be bypass. 0: system bus (including arbiter/router) will not only be reset by + * power-reset, but also some reset event. + */ + uint32_t reset_event_bypass:1; + uint32_t reserved_2:30; + }; + uint32_t val; +} pcr_reset_event_bypass_reg_t; + /** Type of regdma_conf register * REGDMA configuration register */ @@ -1966,7 +1990,7 @@ typedef struct { uint32_t reserved_128; volatile pcr_timergroup_wdt_conf_reg_t timergroup_wdt_conf; volatile pcr_timergroup_xtal_conf_reg_t timergroup_xtal_conf; - uint32_t reserved_134; + volatile pcr_reset_event_bypass_reg_t reset_event_bypass; volatile pcr_regdma_conf_reg_t regdma_conf; volatile pcr_etm_conf_reg_t etm_conf; uint32_t reserved_140[6];