mirror of
https://github.com/espressif/esp-idf.git
synced 2026-10-02 03:00:34 +03:00
Merge branch 'feature/esp_sys_event_restart_panic' into 'master'
refactor(esp_system): route panic through esp_sys_event See merge request espressif/esp-idf!48407
This commit is contained in:
@@ -28,4 +28,9 @@ idf_component_register(SRCS ${srcs}
|
||||
PRIV_INCLUDE_DIRS ${priv_includes}
|
||||
LDFRAGMENTS "linker.lf"
|
||||
REQUIRES "freertos"
|
||||
PRIV_REQUIRES esp_hal_wdt esp_hal_uart)
|
||||
PRIV_REQUIRES esp_hal_wdt esp_hal_uart esp_system)
|
||||
|
||||
if(CONFIG_ESP_SYSTEM_PANIC_GDBSTUB)
|
||||
# Make sure the panic event registration in gdbstub.c is considered by the linker
|
||||
target_link_libraries(${COMPONENT_LIB} INTERFACE "-u esp_gdbstub_panic_handler")
|
||||
endif()
|
||||
|
||||
@@ -24,6 +24,10 @@
|
||||
#include "hal/wdt_hal.h"
|
||||
#endif
|
||||
|
||||
#include "esp_private/esp_sys_event_panic.h"
|
||||
#include "esp_private/panic_internal.h"
|
||||
#include "esp_private/crosscore_int.h"
|
||||
|
||||
#if GDBSTUB_QXFER_FEATURES_ENABLED
|
||||
#define GDBSTUB_QXFER_SUPPORTED_STR ";qXfer:features:read+"
|
||||
#else
|
||||
@@ -55,6 +59,7 @@ static void send_reason(void);
|
||||
esp_gdbstub_scratch_t s_scratch;
|
||||
esp_gdbstub_gdb_regfile_t *gdb_local_regfile = &s_scratch.regfile;
|
||||
|
||||
|
||||
/**
|
||||
* @brief panic handler
|
||||
*/
|
||||
@@ -105,6 +110,21 @@ void esp_gdbstub_panic_handler(void *in_frame)
|
||||
}
|
||||
}
|
||||
|
||||
#if CONFIG_ESP_SYSTEM_PANIC_GDBSTUB
|
||||
// Panic event handler - enters GDB stub (never returns)
|
||||
// Priority 999 ensures this runs last, after trace and coredump handlers
|
||||
ESP_PANIC_HANDLER_REGISTER(esp_gdbstub_panic_event, 999)
|
||||
{
|
||||
(void)user_arg;
|
||||
esp_panic_ctx_t *panic_ctx = (esp_panic_ctx_t *)ctx;
|
||||
panic_print_str("Entering gdb stub now.\r\n");
|
||||
panic_disable_all_wdts();
|
||||
esp_gdbstub_panic_handler((void *)panic_ctx->info->frame);
|
||||
// Never returns
|
||||
return ESP_OK;
|
||||
}
|
||||
#endif /* CONFIG_ESP_SYSTEM_PANIC_GDBSTUB */
|
||||
|
||||
/**
|
||||
* Set interrupt reason to GDB
|
||||
*/
|
||||
@@ -612,6 +632,14 @@ void update_breakpoints(void)
|
||||
#endif // CONFIG_IDF_TARGET_ARCH_XTENSA
|
||||
}
|
||||
|
||||
// Strong override of the weak hook in esp_system's crosscore_int.c. Called from
|
||||
// the crosscore ISR on the target core to apply breakpoint/watchpoint changes
|
||||
// requested from the other core. Placed in IRAM as it runs in interrupt context.
|
||||
IRAM_ATTR void esp_crosscore_int_gdb_call_hook(void)
|
||||
{
|
||||
update_breakpoints();
|
||||
}
|
||||
|
||||
/** Write breakpoint */
|
||||
static void handle_Z0_command(const unsigned char *cmd, int len)
|
||||
{
|
||||
|
||||
@@ -141,18 +141,6 @@ target_link_libraries(${COMPONENT_LIB} INTERFACE "-u esp_system_include_startup_
|
||||
|
||||
# [refactor-todo] requirements due to init code, should be removable
|
||||
# once link-time registration of component init functions is used.
|
||||
if(CONFIG_ESP_TRACE_ENABLE)
|
||||
idf_component_optional_requires(PRIVATE esp_trace)
|
||||
endif()
|
||||
|
||||
if(CONFIG_ESP_COREDUMP_ENABLE)
|
||||
idf_component_optional_requires(PRIVATE espcoredump)
|
||||
endif()
|
||||
|
||||
# [refactor-todo] requirement from the panic handler,
|
||||
# need to introduce panic "event" concept to remove this dependency (IDF-2194)
|
||||
idf_component_optional_requires(PRIVATE esp_gdbstub)
|
||||
|
||||
if(NOT CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT)
|
||||
idf_component_optional_requires(PRIVATE esp_app_format)
|
||||
endif()
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2025 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2015-2026 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -10,6 +10,7 @@
|
||||
#include "esp_cpu.h"
|
||||
#include "esp_intr_alloc.h"
|
||||
#include "esp_debug_helpers.h"
|
||||
#include "esp_private/crosscore_int.h"
|
||||
#include "soc/periph_defs.h"
|
||||
#include "soc/system_intr.h"
|
||||
#include "hal/crosscore_int_ll.h"
|
||||
@@ -17,10 +18,6 @@
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/portmacro.h"
|
||||
|
||||
#if CONFIG_ESP_SYSTEM_GDBSTUB_RUNTIME
|
||||
#include "esp_gdbstub.h"
|
||||
#endif
|
||||
|
||||
#define REASON_YIELD BIT(0)
|
||||
#define REASON_FREQ_SWITCH BIT(1)
|
||||
#define REASON_PRINT_BACKTRACE BIT(2)
|
||||
@@ -30,6 +27,15 @@
|
||||
static portMUX_TYPE reason_spinlock = portMUX_INITIALIZER_UNLOCKED;
|
||||
static volatile uint32_t reason[CONFIG_FREERTOS_NUMBER_OF_CORES];
|
||||
|
||||
/* Weak no-op hook for the REASON_GDB_CALL crosscore interrupt. esp_gdbstub
|
||||
* provides a strong override (see gdbstub.c) when the runtime gdbstub is
|
||||
* enabled. Keeping the default here lets esp_system trigger the gdb-call
|
||||
* handling without taking any dependency on the esp_gdbstub component. Runs in
|
||||
* interrupt context, hence placed in IRAM. */
|
||||
void __attribute__((weak)) ESP_SYSTEM_IRAM_ATTR esp_crosscore_int_gdb_call_hook(void)
|
||||
{
|
||||
}
|
||||
|
||||
/*
|
||||
ToDo: There is a small chance the CPU already has yielded when this ISR is serviced. In that case, it's running the intended task but
|
||||
the ISR will cause it to switch _away_ from it. portYIELD_FROM_ISR will probably just schedule the task again, but have to check that.
|
||||
@@ -64,11 +70,9 @@ static void ESP_SYSTEM_IRAM_ATTR esp_crosscore_isr(void *arg)
|
||||
* to allow DFS features without the extra latency of the ISR hook.
|
||||
*/
|
||||
}
|
||||
#if CONFIG_ESP_SYSTEM_GDBSTUB_RUNTIME
|
||||
if (my_reason_val & REASON_GDB_CALL) {
|
||||
update_breakpoints();
|
||||
esp_crosscore_int_gdb_call_hook();
|
||||
}
|
||||
#endif // !CONFIG_ESP_SYSTEM_GDBSTUB_RUNTIME
|
||||
|
||||
if (my_reason_val & REASON_PRINT_BACKTRACE) {
|
||||
esp_backtrace_print(100);
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2015-2026 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -48,6 +48,15 @@ void esp_crosscore_int_send_freq_switch(int core_id);
|
||||
|
||||
void esp_crosscore_int_send_gdb_call(int core_id);
|
||||
|
||||
/**
|
||||
* Hook invoked from the crosscore ISR when a REASON_GDB_CALL interrupt is
|
||||
* received on this core. esp_system provides a weak no-op default; esp_gdbstub
|
||||
* supplies a strong override that updates this core's hardware breakpoints and
|
||||
* watchpoints. Runs in interrupt context (possibly with cache disabled), so any
|
||||
* override must be placed in IRAM.
|
||||
*/
|
||||
void esp_crosscore_int_gdb_call_hook(void);
|
||||
|
||||
#if !CONFIG_ESP_SYSTEM_SINGLE_CORE_MODE
|
||||
/**
|
||||
* Send an interrupt to a CPU indicating it should print its current backtrace
|
||||
|
||||
@@ -0,0 +1,65 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2026 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "esp_sys_event.h"
|
||||
#include "esp_private/panic_internal.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @file esp_sys_event_panic.h
|
||||
* @brief Panic event using esp_sys_event framework
|
||||
*
|
||||
* This header provides macros for registering panic handlers that are
|
||||
* called when the system panics. Panic handlers receive information about
|
||||
* the panic via panic_info_t and can perform actions like logging, core
|
||||
* dump preparation, or custom diagnostics.
|
||||
*
|
||||
* Note: Panic handlers run in a very restricted context. They must:
|
||||
* - Be placed in IRAM if they access any non-IRAM data
|
||||
* - Not allocate memory
|
||||
* - Not use FreeRTOS APIs
|
||||
* - Complete quickly to avoid triggering watchdog timeout
|
||||
*/
|
||||
|
||||
// Context passed to panic handlers
|
||||
typedef struct {
|
||||
const panic_info_t *info; /*!< Pointer to panic info */
|
||||
} esp_panic_ctx_t;
|
||||
|
||||
/**
|
||||
* @brief Register a static (link-time) panic handler
|
||||
*
|
||||
* Handlers registered with this macro are called during panic processing
|
||||
* in priority order (lower priority values run first). The watchdog is
|
||||
* fed before and after each handler to prevent timeout during handler
|
||||
* execution.
|
||||
*
|
||||
* @param fn Handler function name
|
||||
* @param prio Priority (lower runs first)
|
||||
*/
|
||||
#define ESP_PANIC_HANDLER_REGISTER(fn, prio) \
|
||||
_ESP_SYS_EVENT_REGISTER(PANIC, prio, fn)
|
||||
|
||||
/**
|
||||
* @brief Register a static (link-time) early panic breakpoint handler
|
||||
*
|
||||
* Handlers registered with this macro are called before
|
||||
* panic handler breaks with debugger attached.
|
||||
*
|
||||
* @param fn Handler function name
|
||||
* @param prio Priority (lower runs first)
|
||||
*/
|
||||
#define ESP_PANIC_EARLY_BREAK_HANDLER_REGISTER(fn, prio) \
|
||||
_ESP_SYS_EVENT_REGISTER(PANIC_EARLY_BREAK, prio, fn)
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2023 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2015-2026 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@@ -90,6 +90,15 @@ void panic_prepare_frame_from_ctx(void* frame);
|
||||
|
||||
void panic_clear_active_interrupts(const void* frame);
|
||||
|
||||
/**
|
||||
* @brief Disable all watchdog timers
|
||||
*
|
||||
* This function disables all watchdog timers (Timer Group WDTs and RTC WDT).
|
||||
* It is intended for use by panic handlers that take over execution (e.g., gdbstub)
|
||||
* or that halt the system.
|
||||
*/
|
||||
void panic_disable_all_wdts(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -34,9 +34,13 @@
|
||||
#define _ESP_SYS_EVENT_SECTION_SHUTDOWN esysev_shdn
|
||||
#define _ESP_SYS_EVENT_SECTION_SYSTEM_INIT_CORE esysev_initc
|
||||
#define _ESP_SYS_EVENT_SECTION_SYSTEM_INIT_SECONDARY esysev_inits
|
||||
#define _ESP_SYS_EVENT_SECTION_PANIC esysev_panic
|
||||
#define _ESP_SYS_EVENT_SECTION_PANIC_EARLY_BREAK esysev_paneb
|
||||
#endif
|
||||
|
||||
/* ESP_SYS_EVENT_DEF(ENUM_SUFFIX) */
|
||||
ESP_SYS_EVENT_DEF(SHUTDOWN)
|
||||
ESP_SYS_EVENT_DEF(SYSTEM_INIT_CORE)
|
||||
ESP_SYS_EVENT_DEF(SYSTEM_INIT_SECONDARY)
|
||||
ESP_SYS_EVENT_DEF(PANIC)
|
||||
ESP_SYS_EVENT_DEF(PANIC_EARLY_BREAK)
|
||||
|
||||
@@ -21,6 +21,16 @@ SECTIONS
|
||||
PROVIDE(_esysev_inits_start = .);
|
||||
KEEP(*(SORT_BY_INIT_PRIORITY(.esysev_inits.*)))
|
||||
PROVIDE(_esysev_inits_end = .);
|
||||
|
||||
. = ALIGN(4);
|
||||
PROVIDE(_esysev_panic_start = .);
|
||||
KEEP(*(SORT_BY_INIT_PRIORITY(.esysev_panic.*)))
|
||||
PROVIDE(_esysev_panic_end = .);
|
||||
|
||||
. = ALIGN(4);
|
||||
PROVIDE(_esysev_paneb_start = .);
|
||||
KEEP(*(SORT_BY_INIT_PRIORITY(.esysev_paneb.*)))
|
||||
PROVIDE(_esysev_paneb_end = .);
|
||||
}
|
||||
}
|
||||
INSERT AFTER .data;
|
||||
|
||||
@@ -12,12 +12,22 @@ entries:
|
||||
entries:
|
||||
.esysev_inits+
|
||||
|
||||
[sections:esysev_panic]
|
||||
entries:
|
||||
.esysev_panic+
|
||||
|
||||
[sections:esysev_paneb]
|
||||
entries:
|
||||
.esysev_paneb+
|
||||
|
||||
# Default placements (overridden below with ALIGN/SURROUND flags)
|
||||
[scheme:esp_sys_event_default]
|
||||
entries:
|
||||
esysev_shdn -> flash_rodata
|
||||
esysev_initc -> flash_rodata
|
||||
esysev_inits -> flash_rodata
|
||||
esysev_panic -> flash_rodata
|
||||
esysev_paneb -> flash_rodata
|
||||
|
||||
[mapping:esp_sys_event]
|
||||
archive: *
|
||||
@@ -25,7 +35,9 @@ entries:
|
||||
* (esp_sys_event_default);
|
||||
esysev_shdn -> flash_rodata ALIGN(4, pre) KEEP() SORT(init_priority) SURROUND(esysev_shdn),
|
||||
esysev_initc -> flash_rodata ALIGN(4, pre) KEEP() SORT(init_priority) SURROUND(esysev_initc),
|
||||
esysev_inits -> flash_rodata ALIGN(4, pre) KEEP() SORT(init_priority) SURROUND(esysev_inits)
|
||||
esysev_inits -> flash_rodata ALIGN(4, pre) KEEP() SORT(init_priority) SURROUND(esysev_inits),
|
||||
esysev_panic -> flash_rodata ALIGN(4, pre) KEEP() SORT(init_priority) SURROUND(esysev_panic),
|
||||
esysev_paneb -> flash_rodata ALIGN(4, pre) KEEP() SORT(init_priority) SURROUND(esysev_paneb)
|
||||
|
||||
# ============== esp_system component mappings ==============
|
||||
|
||||
|
||||
@@ -23,6 +23,8 @@
|
||||
#include "esp_private/esp_int_wdt.h"
|
||||
|
||||
#include "esp_private/panic_internal.h"
|
||||
#include "esp_private/esp_sys_event_panic.h"
|
||||
#include "esp_private/esp_sys_event_internal.h"
|
||||
#include "port/panic_funcs.h"
|
||||
#include "esp_rom_sys.h"
|
||||
|
||||
@@ -35,22 +37,10 @@
|
||||
#endif
|
||||
#endif // CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT
|
||||
|
||||
#if CONFIG_ESP_COREDUMP_ENABLE
|
||||
#include "esp_core_dump.h"
|
||||
#endif
|
||||
|
||||
#if CONFIG_ESP_TRACE_ENABLE
|
||||
#include "esp_trace.h"
|
||||
#endif
|
||||
|
||||
#if !CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT
|
||||
#include "hal/uart_hal.h"
|
||||
#endif
|
||||
|
||||
#if CONFIG_ESP_SYSTEM_PANIC_GDBSTUB
|
||||
#include "esp_gdbstub.h"
|
||||
#endif
|
||||
|
||||
#if CONFIG_ESP_CONSOLE_USB_SERIAL_JTAG || CONFIG_ESP_CONSOLE_SECONDARY_USB_SERIAL_JTAG
|
||||
#include "hal/usb_serial_jtag_ll.h"
|
||||
#endif
|
||||
@@ -270,9 +260,20 @@ void esp_panic_handler_feed_wdts(void)
|
||||
}
|
||||
#endif /* SOC_WDT_SUPPORTED || SOC_RTC_WDT_SUPPORTED */
|
||||
|
||||
/********************** esp_sys_event panic trigger **********************/
|
||||
|
||||
static void esp_panic_trigger_event(esp_sys_event_id_t id, esp_panic_ctx_t *ctx)
|
||||
{
|
||||
ESP_SYS_EVENT_FOREACH(h, id) {
|
||||
esp_panic_handler_feed_wdts();
|
||||
h->handler(NULL, ctx);
|
||||
}
|
||||
esp_panic_handler_feed_wdts();
|
||||
}
|
||||
|
||||
#if SOC_WDT_SUPPORTED || SOC_RTC_WDT_SUPPORTED
|
||||
/* This function disables all the watchdogs */
|
||||
static inline void disable_all_wdts(void)
|
||||
void panic_disable_all_wdts(void)
|
||||
{
|
||||
#if SOC_WDT_SUPPORTED
|
||||
//Disable Timer Group WDTs
|
||||
@@ -286,7 +287,7 @@ static inline void disable_all_wdts(void)
|
||||
#endif /* SOC_RTC_WDT_SUPPORTED */
|
||||
}
|
||||
#else /* SOC_WDT_SUPPORTED || SOC_RTC_WDT_SUPPORTED */
|
||||
static inline void disable_all_wdts(void)
|
||||
void panic_disable_all_wdts(void)
|
||||
{
|
||||
}
|
||||
#endif /* SOC_WDT_SUPPORTED || SOC_RTC_WDT_SUPPORTED */
|
||||
@@ -395,11 +396,14 @@ void esp_panic_handler(panic_info_t *info)
|
||||
panic_print_hex((uint32_t)info->addr);
|
||||
panic_print_str(" and returning...\r\n");
|
||||
|
||||
#if CONFIG_ESP_TRACE_ENABLE
|
||||
esp_trace_panic_handler(info);
|
||||
#endif
|
||||
// Trigger early breakpoint handlers before returning to debugger.
|
||||
// This allows trace to dump info before breaking
|
||||
esp_panic_ctx_t panic_ctx = {
|
||||
.info = info,
|
||||
};
|
||||
esp_panic_trigger_event(ESP_SYS_EVENT_PANIC_EARLY_BREAK, &panic_ctx);
|
||||
|
||||
disable_all_wdts();
|
||||
panic_disable_all_wdts();
|
||||
esp_cpu_set_breakpoint(0, info->addr); // use breakpoint 0
|
||||
return;
|
||||
}
|
||||
@@ -432,28 +436,16 @@ void esp_panic_handler(panic_info_t *info)
|
||||
|
||||
panic_print_str("\r\n");
|
||||
|
||||
#if CONFIG_ESP_TRACE_ENABLE
|
||||
esp_panic_handler_feed_wdts();
|
||||
esp_trace_panic_handler(info);
|
||||
#endif
|
||||
// Trigger esp_sys_event panic handlers (includes trace, coredump, gdbstub if enabled)
|
||||
// If gdbstub is enabled and registered, it will take over and never return.
|
||||
// If we return here, proceed to reboot/halt.
|
||||
{
|
||||
esp_panic_ctx_t panic_ctx = {
|
||||
.info = info,
|
||||
};
|
||||
esp_panic_trigger_event(ESP_SYS_EVENT_PANIC, &panic_ctx);
|
||||
|
||||
#if CONFIG_ESP_COREDUMP_ENABLE
|
||||
esp_panic_handler_feed_wdts();
|
||||
static bool s_dumping_core = false;
|
||||
if (s_dumping_core) {
|
||||
panic_print_str("Re-entered core dump! Exception happened during core dump!\r\n");
|
||||
} else {
|
||||
s_dumping_core = true;
|
||||
esp_core_dump_write(info);
|
||||
s_dumping_core = false;
|
||||
}
|
||||
#endif /* CONFIG_ESP_COREDUMP_ENABLE */
|
||||
|
||||
#if CONFIG_ESP_SYSTEM_PANIC_GDBSTUB
|
||||
panic_print_str("Entering gdb stub now.\r\n");
|
||||
disable_all_wdts();
|
||||
esp_gdbstub_panic_handler((void *)info->frame);
|
||||
#else
|
||||
#if CONFIG_ESP_SYSTEM_PANIC_REBOOT_DELAY_SECONDS
|
||||
esp_panic_handler_feed_wdts();
|
||||
|
||||
@@ -488,10 +480,9 @@ void esp_panic_handler(panic_info_t *info)
|
||||
#else /* CONFIG_ESP_SYSTEM_PANIC_PRINT_REBOOT || CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT */
|
||||
esp_panic_handler_feed_wdts();
|
||||
panic_print_str("CPU halted.\r\n");
|
||||
disable_all_wdts();
|
||||
panic_disable_all_wdts();
|
||||
esp_panic_handler_reset_modules_on_exit_and_halt();
|
||||
#endif /* CONFIG_ESP_SYSTEM_PANIC_PRINT_REBOOT || CONFIG_ESP_SYSTEM_PANIC_SILENT_REBOOT */
|
||||
#endif /* CONFIG_ESP_SYSTEM_PANIC_GDBSTUB */
|
||||
}
|
||||
|
||||
void __attribute__((noreturn, no_sanitize_undefined)) panic_abort(const char *details)
|
||||
@@ -499,10 +490,6 @@ void __attribute__((noreturn, no_sanitize_undefined)) panic_abort(const char *de
|
||||
g_panic_abort = true;
|
||||
g_panic_abort_details = (char *) details;
|
||||
|
||||
#if CONFIG_ESP_TRACE_ENABLE
|
||||
esp_trace_panic_handler(NULL);
|
||||
#endif
|
||||
|
||||
#ifdef __XTENSA__
|
||||
asm("ill"); // should be an invalid operation on xtensa targets
|
||||
#elif __riscv
|
||||
|
||||
@@ -30,6 +30,7 @@ set(priv_requires
|
||||
"esp_hal_usb"
|
||||
"esp_driver_usb_serial_jtag"
|
||||
"esp_timer"
|
||||
"esp_system"
|
||||
)
|
||||
set(priv_includes "")
|
||||
set(requires "app_trace")
|
||||
|
||||
@@ -23,6 +23,8 @@
|
||||
#include "esp_trace.h"
|
||||
#include "esp_trace_port_transport.h"
|
||||
#include "esp_private/startup_internal.h"
|
||||
#include "esp_private/esp_sys_event_system_init.h"
|
||||
#include "esp_private/esp_sys_event_panic.h"
|
||||
|
||||
static const char *TAG = "esp_trace_core";
|
||||
|
||||
@@ -231,6 +233,26 @@ void esp_trace_panic_handler(const void *info)
|
||||
}
|
||||
}
|
||||
|
||||
static esp_err_t esp_trace_panic_event_handler(void *user_arg, void *ctx)
|
||||
{
|
||||
(void)user_arg;
|
||||
esp_panic_ctx_t *panic_ctx = (esp_panic_ctx_t *)ctx;
|
||||
esp_trace_panic_handler(panic_ctx->info);
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
// Panic event handler - flushes trace buffers on panic
|
||||
ESP_PANIC_HANDLER_REGISTER(esp_trace_panic, 100)
|
||||
{
|
||||
return esp_trace_panic_event_handler(user_arg, ctx);
|
||||
}
|
||||
|
||||
// Early breakpoint event handler - flushes trace before returning to debugger
|
||||
ESP_PANIC_EARLY_BREAK_HANDLER_REGISTER(esp_trace_panic_early_break, 100)
|
||||
{
|
||||
return esp_trace_panic_event_handler(user_arg, ctx);
|
||||
}
|
||||
|
||||
esp_trace_open_params_t __attribute__((weak)) esp_trace_get_user_params(void)
|
||||
{
|
||||
esp_trace_open_params_t trace_params = {
|
||||
|
||||
@@ -1,11 +1,14 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2024 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2024-2026 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
#include "sdkconfig.h"
|
||||
|
||||
#include "esp_private/startup_internal.h"
|
||||
#include "esp_private/esp_sys_event_system_init.h"
|
||||
#include "esp_private/esp_sys_event_panic.h"
|
||||
#include "esp_private/panic_internal.h"
|
||||
#include "esp_core_dump.h"
|
||||
|
||||
// Hook to force the linker to include this file
|
||||
@@ -18,3 +21,20 @@ ESP_SYSTEM_INIT_FN(init_coredump, SECONDARY, BIT(0), 130)
|
||||
esp_core_dump_init();
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
// Panic event handler - writes core dump on panic
|
||||
ESP_PANIC_HANDLER_REGISTER(esp_coredump_panic, 200)
|
||||
{
|
||||
(void)user_arg;
|
||||
esp_panic_ctx_t *panic_ctx = (esp_panic_ctx_t *)ctx;
|
||||
|
||||
static bool s_dumping_core = false;
|
||||
if (s_dumping_core) {
|
||||
panic_print_str("Re-entered core dump! Exception happened during core dump!\r\n");
|
||||
return ESP_ERR_INVALID_STATE;
|
||||
}
|
||||
s_dumping_core = true;
|
||||
esp_core_dump_write((panic_info_t *)panic_ctx->info);
|
||||
s_dumping_core = false;
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user