mirror of
https://github.com/espressif/esp-idf.git
synced 2026-10-01 18:50:34 +03:00
Merge branch 'fix/coredump_max_tasks_num_v5.4' into 'release/v5.4'
fix(coredump): implement CONFIG_ESP_COREDUMP_MAX_TASKS_NUM limitation (v5.4) See merge request espressif/esp-idf!41016
This commit is contained in:
@@ -85,7 +85,9 @@ menu "Core dump"
|
||||
depends on ESP_COREDUMP_ENABLE
|
||||
default 64
|
||||
help
|
||||
Maximum number of tasks snapshots in core dump.
|
||||
Maximum number of tasks that will be included in the core dump.
|
||||
Crashed task registers and stacks are always included.
|
||||
Other tasks are included in order of their priority. (Highest priority ready task first)
|
||||
|
||||
config ESP_COREDUMP_UART_DELAY
|
||||
int "Delay before print to UART"
|
||||
|
||||
@@ -412,6 +412,7 @@ static int elf_process_tasks_regs(core_dump_elf_t *self)
|
||||
void *task = NULL;
|
||||
int len = 0;
|
||||
int ret = 0;
|
||||
int tasks_num = 0;
|
||||
|
||||
esp_core_dump_reset_tasks_snapshots_iter();
|
||||
task = esp_core_dump_get_current_task_handle();
|
||||
@@ -425,6 +426,7 @@ static int elf_process_tasks_regs(core_dump_elf_t *self)
|
||||
ELF_CHECK_ERR((ret > 0), ret, "Task %x, PR_STATUS write failed, return (%d).", task, ret);
|
||||
}
|
||||
len += ret;
|
||||
tasks_num++;
|
||||
}
|
||||
// processes PR_STATUS and register dump for each task
|
||||
// each call to the processing function appends PR_STATUS note into note segment
|
||||
@@ -435,6 +437,11 @@ static int elf_process_tasks_regs(core_dump_elf_t *self)
|
||||
if (!task || task == esp_core_dump_get_current_task_handle()) { // skip current task (already processed)
|
||||
continue;
|
||||
}
|
||||
if (tasks_num > CONFIG_ESP_COREDUMP_MAX_TASKS_NUM) {
|
||||
ESP_COREDUMP_LOG_PROCESS("Reached maximum number of tasks (%d), stopping task register processing",
|
||||
CONFIG_ESP_COREDUMP_MAX_TASKS_NUM);
|
||||
break;
|
||||
}
|
||||
if (esp_core_dump_get_task_snapshot(task, &task_hdr, NULL)) {
|
||||
ret = elf_add_regs(self, &task_hdr);
|
||||
if (self->elf_stage == ELF_STAGE_PLACE_HEADERS) {
|
||||
@@ -444,6 +451,7 @@ static int elf_process_tasks_regs(core_dump_elf_t *self)
|
||||
ELF_CHECK_ERR((ret > 0), ret, "Task %x, PR_STATUS write failed, return (%d).", task, ret);
|
||||
}
|
||||
len += ret;
|
||||
tasks_num++;
|
||||
}
|
||||
}
|
||||
ret = elf_process_note_segment(self, len); // tasks regs note
|
||||
@@ -467,23 +475,69 @@ static int elf_save_task(core_dump_elf_t *self, core_dump_task_header_t *task)
|
||||
return elf_len;
|
||||
}
|
||||
|
||||
static int elf_save_interrupted_stack(core_dump_elf_t *self, core_dump_mem_seg_header_t *interrupted_stack)
|
||||
{
|
||||
int ret = 0;
|
||||
#if !CONFIG_ESP_COREDUMP_CAPTURE_DRAM
|
||||
/* interrupt stacks:
|
||||
- 'port_IntStack' is in the data section for xtensa
|
||||
- 'xIsrStack' is in the bss section for risc-v
|
||||
When DRAM capture is enabled, interrupt stack saving can be done during the full section store
|
||||
*/
|
||||
if (interrupted_stack->size > 0) {
|
||||
ESP_COREDUMP_LOG_PROCESS("Add interrupted task stack %lu bytes @ %x",
|
||||
interrupted_stack->size, interrupted_stack->start);
|
||||
ret = elf_add_segment(self, PT_LOAD,
|
||||
(uint32_t)interrupted_stack->start,
|
||||
(void*)interrupted_stack->start,
|
||||
(uint32_t)interrupted_stack->size);
|
||||
ELF_CHECK_ERR((ret > 0), ret, "Interrupted task stack write failed, return (%d).", ret);
|
||||
}
|
||||
#endif
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int elf_process_task_data(core_dump_elf_t *self)
|
||||
{
|
||||
int elf_len = 0;
|
||||
core_dump_task_header_t task_hdr = { 0 };
|
||||
core_dump_mem_seg_header_t interrupted_stack = { 0 };
|
||||
TaskIterator_t task_iter;
|
||||
uint16_t tasks_num = 0;
|
||||
uint16_t bad_tasks_num = 0;
|
||||
int tasks_num = 0;
|
||||
int bad_tasks_num = 0;
|
||||
|
||||
ESP_COREDUMP_LOG_PROCESS("================ Processing task data ================");
|
||||
// processes all task's stack data and writes segment data into partition
|
||||
// if flash configuration is set
|
||||
|
||||
// first write crashed task data
|
||||
esp_core_dump_reset_tasks_snapshots_iter();
|
||||
void *current_task = esp_core_dump_get_current_task_handle();
|
||||
if (esp_core_dump_get_task_snapshot(current_task, &task_hdr, &interrupted_stack)) {
|
||||
int ret = elf_save_task(self, &task_hdr);
|
||||
ELF_CHECK_ERR((ret > 0), ret,
|
||||
"Task %x, TCB write failed, return (%d).", current_task, ret);
|
||||
elf_len += ret;
|
||||
|
||||
// Handle interrupted stack (only relevant for current task)
|
||||
ret = elf_save_interrupted_stack(self, &interrupted_stack);
|
||||
if (ret > 0) {
|
||||
elf_len += ret;
|
||||
}
|
||||
tasks_num++;
|
||||
}
|
||||
|
||||
esp_core_dump_task_iterator_init(&task_iter);
|
||||
while (esp_core_dump_task_iterator_next(&task_iter) != -1) {
|
||||
// Skip the current task (already processed above)
|
||||
if (!task_iter.pxTaskHandle || task_iter.pxTaskHandle == current_task) {
|
||||
continue;
|
||||
}
|
||||
if (tasks_num > CONFIG_ESP_COREDUMP_MAX_TASKS_NUM) {
|
||||
ESP_COREDUMP_LOG_PROCESS("Reached maximum number of tasks (%d), stopping task data processing",
|
||||
CONFIG_ESP_COREDUMP_MAX_TASKS_NUM);
|
||||
break;
|
||||
}
|
||||
tasks_num++;
|
||||
if (!esp_core_dump_get_task_snapshot(task_iter.pxTaskHandle, &task_hdr, &interrupted_stack)) {
|
||||
if (!esp_core_dump_get_task_snapshot(task_iter.pxTaskHandle, &task_hdr, NULL)) {
|
||||
bad_tasks_num++;
|
||||
continue;
|
||||
}
|
||||
@@ -491,23 +545,6 @@ static int elf_process_task_data(core_dump_elf_t *self)
|
||||
ELF_CHECK_ERR((ret > 0), ret,
|
||||
"Task %x, TCB write failed, return (%d).", task_iter.pxTaskHandle, ret);
|
||||
elf_len += ret;
|
||||
/* interrupt stacks:
|
||||
- 'port_IntStack' is in the data section for xtensa
|
||||
- 'xIsrStack' is in the bss section for risc-v
|
||||
When DRAM capture is enabled, interrupt stack saving can be done during the full section store
|
||||
*/
|
||||
#if !CONFIG_ESP_COREDUMP_CAPTURE_DRAM
|
||||
if (interrupted_stack.size > 0) {
|
||||
ESP_COREDUMP_LOG_PROCESS("Add interrupted task stack %lu bytes @ %x",
|
||||
interrupted_stack.size, interrupted_stack.start);
|
||||
ret = elf_add_segment(self, PT_LOAD,
|
||||
(uint32_t)interrupted_stack.start,
|
||||
(void*)interrupted_stack.start,
|
||||
(uint32_t)interrupted_stack.size);
|
||||
ELF_CHECK_ERR((ret > 0), ret, "Interrupted task stack write failed, return (%d).", ret);
|
||||
elf_len += ret;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
ESP_COREDUMP_LOG_PROCESS("Found %d bad task out of %d", bad_tasks_num, tasks_num);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user