mirror of
https://github.com/espressif/esp-idf
synced 2025-03-10 01:29:21 -04:00
Merge branch 'fix/coredump_checksum_error_v5.4' into 'release/v5.4'
Fix/coredump checksum error (v5.4) See merge request espressif/esp-idf!35762
This commit is contained in:
commit
f335a2d6ea
@ -136,12 +136,6 @@ esp_err_t esp_core_dump_write_data(core_dump_write_data_t *wr_data, void *data,
|
||||
*/
|
||||
esp_err_t esp_core_dump_write_end(core_dump_write_data_t *wr_data);
|
||||
|
||||
/**
|
||||
* @brief Retrieve the stack information which will be used from the coredump module itself.
|
||||
* It will show the whole stack boundaries in case the stack is shared with the crashed task.
|
||||
*/
|
||||
void esp_core_dump_get_own_stack_info(uint32_t *addr, uint32_t *size);
|
||||
|
||||
/**
|
||||
* @brief Stores the core dump in either binary or ELF format.
|
||||
*/
|
||||
|
@ -312,26 +312,6 @@ int esp_core_dump_get_user_ram_info(coredump_region_t region, uint32_t *start)
|
||||
return total_sz;
|
||||
}
|
||||
|
||||
#if CONFIG_ESP_COREDUMP_CAPTURE_DRAM
|
||||
void esp_core_dump_get_own_stack_info(uint32_t *addr, uint32_t *size)
|
||||
{
|
||||
#if CONFIG_ESP_COREDUMP_STACK_SIZE > 0
|
||||
/* Custom stack reserved for the coredump */
|
||||
*addr = (uint32_t)s_coredump_stack;
|
||||
*size = sizeof(s_coredump_stack);
|
||||
#else
|
||||
/* Shared stack with the crashed task */
|
||||
core_dump_task_handle_t handle = esp_core_dump_get_current_task_handle();
|
||||
TaskSnapshot_t rtos_snapshot = { 0 };
|
||||
vTaskGetSnapshot(handle, &rtos_snapshot);
|
||||
StaticTask_t *current = (StaticTask_t *)handle;
|
||||
*addr = (uint32_t)current->pxDummy6; //pxStack
|
||||
*size = (uint32_t)rtos_snapshot.pxTopOfStack - (uint32_t)current->pxDummy6; /* free */
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* CONFIG_ESP_COREDUMP_CAPTURE_DRAM */
|
||||
|
||||
inline bool esp_core_dump_tcb_addr_is_sane(uint32_t addr)
|
||||
{
|
||||
return esp_core_dump_mem_seg_is_sane(addr, esp_core_dump_get_tcb_len());
|
||||
|
@ -81,11 +81,6 @@ typedef struct _core_dump_elf_t {
|
||||
uint16_t segs_count;
|
||||
core_dump_write_data_t write_data;
|
||||
uint32_t note_data_size; /* can be used where static storage needed */
|
||||
#if CONFIG_ESP_COREDUMP_CAPTURE_DRAM
|
||||
/* To avoid checksum failure, coredump stack region will be excluded while storing the sections. */
|
||||
uint32_t coredump_stack_start;
|
||||
uint32_t coredump_stack_size;
|
||||
#endif
|
||||
} core_dump_elf_t;
|
||||
|
||||
typedef struct {
|
||||
@ -524,61 +519,6 @@ static int elf_write_tasks_data(core_dump_elf_t *self)
|
||||
|
||||
#if CONFIG_ESP_COREDUMP_CAPTURE_DRAM
|
||||
|
||||
/* Coredump stack will also be used by the checksum functions while saving sections.
|
||||
* There is a potential for inconsistency when writing coredump stack to the flash and calculating checksum simultaneously.
|
||||
* This is because, coredump stack will be modified during the process, leading to incorrect checksum calculations.
|
||||
* To mitigate this issue, it's important to ensure that the coredump stack excluded from checksum calculation by
|
||||
* filter out from the written regions.
|
||||
* Typically, the coredump stack can be located in two different sections.
|
||||
* 1. In the bss section;
|
||||
* 1.a if `CONFIG_ESP_COREDUMP_STACK_SIZE` set to a nonzero value
|
||||
* 1.b if the crashed task is created with a static task buffer using the xTaskCreateStatic() api
|
||||
* 2. In the heap section, if custom stack is not defined and the crashed task buffer is allocated in the heap
|
||||
* with the xTaskCreate() api
|
||||
*
|
||||
* esp_core_dump_store_section() will check if the coredump stack is located inside the section.
|
||||
* If it is, this part will be skipped.
|
||||
* |+++++++++| xxxxxxxxxxxxxx |++++++++|
|
||||
* |+++++++++| coredump stack |++++++++|
|
||||
*/
|
||||
static int esp_core_dump_store_section(core_dump_elf_t *self, uint32_t start, uint32_t data_len)
|
||||
{
|
||||
uint32_t end = start + data_len;
|
||||
int total_sz = 0;
|
||||
int ret;
|
||||
|
||||
if (self->coredump_stack_start > start && self->coredump_stack_start < end) {
|
||||
/* write until the coredump stack. */
|
||||
data_len = self->coredump_stack_start - start;
|
||||
ret = elf_add_segment(self, PT_LOAD,
|
||||
start,
|
||||
(void*)start,
|
||||
data_len);
|
||||
|
||||
if (ret <= 0) {
|
||||
return ret;
|
||||
}
|
||||
total_sz += ret;
|
||||
|
||||
/* Skip coredump stack and set offset for the rest of the section */
|
||||
start = self->coredump_stack_start + self->coredump_stack_size;
|
||||
data_len = end - start;
|
||||
}
|
||||
|
||||
if (data_len > 0) {
|
||||
ret = elf_add_segment(self, PT_LOAD,
|
||||
(uint32_t)start,
|
||||
(void*)start,
|
||||
(uint32_t)data_len);
|
||||
if (ret <= 0) {
|
||||
return ret;
|
||||
}
|
||||
total_sz += ret;
|
||||
}
|
||||
|
||||
return total_sz;
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
core_dump_elf_t *self;
|
||||
int *total_sz;
|
||||
@ -611,11 +551,6 @@ bool esp_core_dump_write_heap_blocks(walker_heap_into_t heap_info, walker_block_
|
||||
return false;
|
||||
}
|
||||
|
||||
if (self->coredump_stack_start == (uint32_t)block_info.ptr) {
|
||||
/* skip writing coredump stack block */
|
||||
return true;
|
||||
}
|
||||
|
||||
*ret = elf_add_segment(self, PT_LOAD,
|
||||
(uint32_t)block_info.ptr,
|
||||
(void*)block_info.ptr,
|
||||
@ -629,7 +564,7 @@ bool esp_core_dump_write_heap_blocks(walker_heap_into_t heap_info, walker_block_
|
||||
return true;
|
||||
}
|
||||
|
||||
#else
|
||||
#endif
|
||||
|
||||
static int esp_core_dump_store_section(core_dump_elf_t *self, uint32_t start, uint32_t data_len)
|
||||
{
|
||||
@ -639,8 +574,6 @@ static int esp_core_dump_store_section(core_dump_elf_t *self, uint32_t start, ui
|
||||
data_len);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
static int elf_write_core_dump_user_data(core_dump_elf_t *self)
|
||||
{
|
||||
int total_sz = 0;
|
||||
@ -825,12 +758,6 @@ static esp_err_t esp_core_dump_write_elf(void)
|
||||
int tot_len = sizeof(dump_hdr);
|
||||
int write_len = sizeof(dump_hdr);
|
||||
|
||||
#if CONFIG_ESP_COREDUMP_CAPTURE_DRAM
|
||||
esp_core_dump_get_own_stack_info(&self.coredump_stack_start, &self.coredump_stack_size);
|
||||
ESP_COREDUMP_LOG_PROCESS("Core dump stack start=%p size = %d",
|
||||
(void *)self.coredump_stack_start, self.coredump_stack_size);
|
||||
#endif
|
||||
|
||||
esp_err_t err = esp_core_dump_write_init();
|
||||
if (err != ESP_OK) {
|
||||
ESP_COREDUMP_LOGE("Elf write init failed!");
|
||||
|
@ -154,21 +154,15 @@ static esp_err_t esp_core_dump_flash_write_data(core_dump_write_data_t* wr_data,
|
||||
uint32_t written = 0;
|
||||
uint32_t wr_sz = 0;
|
||||
|
||||
/* Make sure that the partition is large enough to hold the data. */
|
||||
ESP_COREDUMP_ASSERT((wr_data->off + data_size) < s_core_flash_config.partition.size);
|
||||
/* Make sure that the partition is large enough to store both the cached and new data. */
|
||||
ESP_COREDUMP_ASSERT((wr_data->off + wr_data->cached_bytes + data_size) < s_core_flash_config.partition.size);
|
||||
|
||||
if (wr_data->cached_bytes) {
|
||||
/* Some bytes are in the cache, let's continue filling the cache
|
||||
* with the data received as parameter. Let's calculate the maximum
|
||||
* amount of bytes we can still fill the cache with. */
|
||||
if ((COREDUMP_CACHE_SIZE - wr_data->cached_bytes) > data_size) {
|
||||
wr_sz = data_size;
|
||||
} else {
|
||||
wr_sz = COREDUMP_CACHE_SIZE - wr_data->cached_bytes;
|
||||
}
|
||||
while (data_size > 0) {
|
||||
/* Calculate the maximum amount of bytes we can still fill the cache with. */
|
||||
wr_sz = MIN(data_size, COREDUMP_CACHE_SIZE - wr_data->cached_bytes);
|
||||
|
||||
/* Append wr_sz bytes from data parameter to the cache. */
|
||||
memcpy(&wr_data->cached_data[wr_data->cached_bytes], data, wr_sz);
|
||||
memcpy(&wr_data->cached_data[wr_data->cached_bytes], data + written, wr_sz);
|
||||
wr_data->cached_bytes += wr_sz;
|
||||
|
||||
if (wr_data->cached_bytes == COREDUMP_CACHE_SIZE) {
|
||||
@ -196,47 +190,6 @@ static esp_err_t esp_core_dump_flash_write_data(core_dump_write_data_t* wr_data,
|
||||
data_size -= wr_sz;
|
||||
}
|
||||
|
||||
/* Figure out how many bytes we can write onto the flash directly, without
|
||||
* using the cache. In our case the cache size is a multiple of the flash's
|
||||
* minimum writing block size, so we will use it for our calculation.
|
||||
* For example, if COREDUMP_CACHE_SIZE equals 32, here are interesting
|
||||
* values:
|
||||
* +---------+-----------------------+
|
||||
* | | data_size |
|
||||
* +---------+---+----+----+----+----+
|
||||
* | | 0 | 31 | 32 | 40 | 64 |
|
||||
* +---------+---+----+----+----+----+
|
||||
* | (blocks | 0 | 0 | 1 | 1 | 2) |
|
||||
* +---------+---+----+----+----+----+
|
||||
* | wr_sz | 0 | 0 | 32 | 32 | 64 |
|
||||
* +---------+---+----+----+----+----+
|
||||
*/
|
||||
wr_sz = (data_size / COREDUMP_CACHE_SIZE) * COREDUMP_CACHE_SIZE;
|
||||
if (wr_sz) {
|
||||
/* Write the contiguous amount of bytes to the flash,
|
||||
* without using the cache */
|
||||
err = esp_core_dump_flash_custom_write(s_core_flash_config.partition.start + wr_data->off, data + written, wr_sz);
|
||||
|
||||
if (err != ESP_OK) {
|
||||
ESP_COREDUMP_LOGE("Failed to write data to flash (%d)!", err);
|
||||
return err;
|
||||
}
|
||||
|
||||
/* Update the checksum with the newly written bytes */
|
||||
esp_core_dump_checksum_update(&wr_data->checksum_ctx, data + written, wr_sz);
|
||||
wr_data->off += wr_sz;
|
||||
written += wr_sz;
|
||||
data_size -= wr_sz;
|
||||
}
|
||||
|
||||
if (data_size > 0) {
|
||||
/* There still some bytes from the data parameter that need to be sent,
|
||||
* append it to cache in order to write them later. (i.e. when there
|
||||
* will be enough bytes to fill the cache) */
|
||||
memcpy(&wr_data->cached_data, data + written, data_size);
|
||||
wr_data->cached_bytes = data_size;
|
||||
}
|
||||
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user