vTaskDelete()删除正在打印日志的任务导致esp32卡死无法恢复
Posted: Fri May 27, 2022 6:56 am
实际的应用场景是录音的时候创建了一个任务去读i2s数据,放到一个ringbuf里,然后主任务从ringbuf里取数据进行降噪编码处理。
长跑测试发现设备在执行录音时偶然会发生死机现象,排查发现是读i2s数据的任务在结束前会调用ESP_LOG接口打印任务结束的日志,如果子任务正在打印日志时,被主任务调用vTaskDelete()销毁,会导致esp32卡死,且没有打印报错信息
在一段时间后(几十分钟甚至几个小时后),报错“ assert failed: vTaskPriorityDisinheritAfterTimeout”,然后设备重启
关键部分的代码类似下面这段
长跑测试发现设备在执行录音时偶然会发生死机现象,排查发现是读i2s数据的任务在结束前会调用ESP_LOG接口打印任务结束的日志,如果子任务正在打印日志时,被主任务调用vTaskDelete()销毁,会导致esp32卡死,且没有打印报错信息
在一段时间后(几十分钟甚至几个小时后),报错“ assert failed: vTaskPriorityDisinheritAfterTimeout”,然后设备重启
关键部分的代码类似下面这段
Code: Select all
#include <stdio.h>
#include "sdkconfig.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"
#include "esp_log.h"
static const char *TAG = "main";
static void test_task(void *args)
{
while (1)
{
ESP_LOGI(TAG, "test_task working");
}
vTaskDelete(NULL);
}
void app_main(void)
{
while (1)
{
ESP_LOGI(TAG, "main task running");
TaskHandle_t test_task_handle = NULL;
xTaskCreate(test_task, "test_task", 1024 * 5, NULL, 10, &test_task_handle);
vTaskDelay(10);
vTaskDelete(test_task_handle);
vTaskDelay(100);
}
fflush(stdout);
esp_restart();
}