#include "esp_task_wdt.h"
#include "esp_phy_init.h"
#include "esp_coexist.h"
+#include "esp_panic.h"
#include "esp_core_dump.h"
#include "trax.h"
void IRAM_ATTR call_start_cpu0()
{
+#if CONFIG_FREERTOS_UNICORE
+ RESET_REASON rst_reas[1];
+#else
+ RESET_REASON rst_reas[2];
+#endif
cpu_configure_region_protection();
//Move exception vectors to IRAM
"wsr %0, vecbase\n" \
::"r"(&_init_start));
+ rst_reas[0] = rtc_get_reset_reason(0);
+#if !CONFIG_FREERTOS_UNICORE
+ rst_reas[1] = rtc_get_reset_reason(1);
+#endif
+ // from panic handler we can be reset by RWDT or TG0WDT
+ if (rst_reas[0] == RTCWDT_SYS_RESET || rst_reas[0] == TG0WDT_SYS_RESET
+#if !CONFIG_FREERTOS_UNICORE
+ || rst_reas[1] == RTCWDT_SYS_RESET || rst_reas[1] == TG0WDT_SYS_RESET
+#endif
+ ) {
+ // stop wdt in case of any
+ ESP_EARLY_LOGI(TAG, "Stop panic WDT");
+ esp_panic_wdt_stop();
+ }
+
memset(&_bss_start, 0, (&_bss_end - &_bss_start) * sizeof(_bss_start));
/* Unless waking from deep sleep (implying RTC memory is intact), clear RTC bss */
- if (rtc_get_reset_reason(0) != DEEPSLEEP_RESET) {
+ if (rst_reas[0] != DEEPSLEEP_RESET) {
memset(&_rtc_bss_start, 0, (&_rtc_bss_end - &_rtc_bss_start) * sizeof(_rtc_bss_start));
}
#define RTC_CNTL_WDT_PAUSE_IN_SLP_M (BIT(7))
#define RTC_CNTL_WDT_PAUSE_IN_SLP_V 0x1
#define RTC_CNTL_WDT_PAUSE_IN_SLP_S 7
+/* RTC_CNTL_WDT_STGX : */
+/*description: stage action selection values */
+#define RTC_WDT_STG_SEL_OFF 0
+#define RTC_WDT_STG_SEL_INT 1
+#define RTC_WDT_STG_SEL_RESET_CPU 2
+#define RTC_WDT_STG_SEL_RESET_SYSTEM 3
#define RTC_CNTL_WDTCONFIG1_REG (DR_REG_RTCCNTL_BASE + 0x90)
/* RTC_CNTL_WDT_STG0_HOLD : R/W ;bitpos:[31:0] ;default: 32'd128000 ; */
TIMERG0.wdt_wprotect = 0;
TIMERG1.wdt_wprotect = TIMG_WDT_WKEY_VALUE;
TIMERG1.wdt_config0.en = 0;
- TIMERG0.wdt_wprotect = 0;
+ TIMERG1.wdt_wprotect = 0;
}
#endif
+static void esp_panic_wdt_start()
+{
+ if (REG_GET_BIT(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_EN)) {
+ return;
+ }
+ WRITE_PERI_REG(RTC_CNTL_WDTWPROTECT_REG, RTC_CNTL_WDT_WKEY_VALUE);
+ WRITE_PERI_REG(RTC_CNTL_WDTFEED_REG, 1);
+ REG_SET_FIELD(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_SYS_RESET_LENGTH, 7);
+ REG_SET_FIELD(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_CPU_RESET_LENGTH, 7);
+ REG_SET_FIELD(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_STG0, RTC_WDT_STG_SEL_RESET_SYSTEM);
+ // 64KB of core dump data (stacks of about 30 tasks) will produce ~85KB base64 data.
+ // @ 115200 UART speed it will take more than 6 sec to print them out.
+ WRITE_PERI_REG(RTC_CNTL_WDTCONFIG1_REG, RTC_CNTL_SLOWCLK_FREQ*7);
+ REG_SET_BIT(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_EN);
+ WRITE_PERI_REG(RTC_CNTL_WDTWPROTECT_REG, 0);
+}
+
+void esp_panic_wdt_stop()
+{
+ WRITE_PERI_REG(RTC_CNTL_WDTWPROTECT_REG, RTC_CNTL_WDT_WKEY_VALUE);
+ WRITE_PERI_REG(RTC_CNTL_WDTFEED_REG, 1);
+ REG_SET_FIELD(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_STG0, RTC_WDT_STG_SEL_OFF);
+ REG_CLR_BIT(RTC_CNTL_WDTCONFIG0_REG, RTC_CNTL_WDT_EN);
+ WRITE_PERI_REG(RTC_CNTL_WDTWPROTECT_REG, 0);
+}
+
static inline bool stackPointerIsSane(uint32_t sp)
{
return !(sp < 0x3ffae010 || sp > 0x3ffffff0 || ((sp & 0xf) != 0));
"A14 ", "A15 ", "SAR ", "EXCCAUSE", "EXCVADDR", "LBEG ", "LEND ", "LCOUNT "
};
+ // start panic WDT to restart system if we hang in this handler
+ esp_panic_wdt_start();
+
//Feed the watchdogs, so they will give us time to print out debug info
reconfigureAllWdts();
#if CONFIG_ESP32_PANIC_GDBSTUB
disableAllWdts();
+ esp_panic_wdt_stop();
panicPutStr("Entering gdb stub now.\r\n");
esp_gdbstub_panic_handler(frame);
#else
#endif
reconfigureAllWdts();
#endif
+ esp_panic_wdt_stop();
#if CONFIG_ESP32_PANIC_PRINT_REBOOT || CONFIG_ESP32_PANIC_SILENT_REBOOT
panicPutStr("Rebooting...\r\n");
esp_restart_noos();