I am working on an ESP32 project where I need to read luminosity data in a continuous loop. Despite following various recommendations, including creating a task with tskIDLE_PRIORITY and increasing the watchdog timeout, I am still facing issues with the task watchdog being triggered. Below is a detailed description of my problem, the code, and the steps I have taken so far.
ESP IDF version : 5.2
When running my code, the task watchdog gets triggered with the following message:
I (15255) MONIDAT: Measurement 86800: Luminosity: 3
I (15265) MONIDAT: Measurement 86900: Luminosity: 3
I (15285) MONIDAT: Measurement 87000: Luminosity: 3
I (15305) MONIDAT: Measurement 87100: Luminosity: 3
E (15305) task_wdt: Task watchdog got triggered. The following tasks/users did not reset the watchdog in time:
E (15305) task_wdt: - IDLE0 (CPU 0)
E (15305) task_wdt: Tasks currently running:
E (15305) task_wdt: CPU 0: main
E (15305) task_wdt: CPU 1: IDLE1
E (15305) task_wdt: Print CPU 0 (current core) backtrace
Backtrace: 0x4200D673:0x3FC93300 0x4200DA90:0x3FC93320 0x40377175:0x3FC93350 0x4200AF31:0x3FC99090 0x4200B10C:0x3FC990C0 0x4200B1D3:0x3FC99100 0x4200BE12:0x3FC99130 0x42008436:0x3FC991D0 0x4200849B:0x3FC99200 0x420085E9:0x3FC99240 0x4201B877:0x3FC992A0 0x4037A9E1:0x3FC992D0
0x4200d673: task_wdt_timeout_handling at C:/ESP/components/esp_system/task_wdt/task_wdt.c:441
0x4200da90: task_wdt_isr at C:/ESP/components/esp_system/task_wdt/task_wdt.c:515
0x40377175: _xt_lowint1 at C:/ESP/components/xtensa/xtensa_vectors.S:1240
0x4200af31: s_i2c_send_commands at C:/ESP/components/driver/i2c/i2c_master.c:433 (discriminator 1)
0x4200b10c: s_i2c_transaction_start at C:/ESP/components/driver/i2c/i2c_master.c:509
0x4200b1d3: s_i2c_synchronous_transaction at C:/ESP/components/driver/i2c/i2c_master.c:780
0x4200be12: i2c_master_transmit_receive at C:/ESP/components/driver/i2c/i2c_master.c:995
0x42008436: tsl2591_read_register at C:/ESP/examples/get-started/lisi_monidat/main/lisi_monidat.c:34
0x4200849b: measure_task at C:/ESP/examples/get-started/lisi_monidat/main/lisi_monidat.c:55
0x420085e9: app_main at C:/ESP/examples/get-started/lisi_monidat/main/lisi_monidat.c:98
0x4201b877: main_task at C:/ESP/components/freertos/app_startup.c:208
0x4037a9e1: vPortTaskWrapper at C:/ESP/components/freertos/FreeRTOS-Kernel/portable/xtensa/port.c:134
I (15375) MONIDAT: Measurement 87200: Luminosity: 3
I (15385) MONIDAT: Measurement 87300: Luminosity: 3
I (15405) MONIDAT: Measurement 87400: Luminosity: 3
I (15425) MONIDAT: Measurement 87500: Luminosity: 3
But then the code conitunue to run it seems that the WDT is not blocking. For example with a WD set to 6sec in the menue config, each 6 sec I will have a WDT. SO my function will have a real time of +-22s of execution but is timed 17second by the elepsed time.
I attempted to create a task with tskIDLE_PRIORITY as recommended here , but it did not resolve the issue.
I then increased the watchdog timeout value from 6 seconds to 20 seconds in menuConfig, which worked temporarily because my loop takes 17.21 seconds. However, when increasing the number of measurements to 200,000, the loop exceeds 20 seconds, causing the watchdog to trigger again.
Adding a delay (e.g., 10ms) avoids triggering the watchdog, but any delay below 10ms results in an infinite loop due to the default tick period of 10ms.
Code Snippet :
void measure_task(i2c_master_dev_handle_t dev_handle)
{
uint8_t data[2];
int num_measurements = 100000;
int64_t start_time = esp_timer_get_time();
for (int i = 0; i < num_measurements; i++)
{
ESP_ERROR_CHECK(tsl2591_read_register(TSL2591_REGISTER_CHAN0_LOW, data, 2,dev_handle));
uint16_t luminosity = (data[1] << 8) | data[0];
// Optionally log every 1000th measurement to avoid overwhelming the log
if (i % 100 == 0) {
ESP_LOGI(TAG, "Measurement %d: Luminosity: %d", i, luminosity);
}
}
int64_t end_time = esp_timer_get_time();
float elapsed_time_sec = (end_time - start_time) / 1000000.0;
ESP_LOGI(TAG, "Completed %d measurements in %.2f seconds good job", num_measurements, elapsed_time_sec);
}
Steps Taken :
- Created a Task with tskIDLE_PRIORITY: Followed suggestions to create a task with tskIDLE_PRIORITY, but it did not solve the issue.
- Increased Watchdog Timeout: Changed the watchdog timeout from 6 seconds to 20 seconds, which worked temporarily, but increasing the loop count caused the issue to reappear.
- Added Delay: Adding a delay (10ms) prevents the watchdog from triggering, but delays below 10ms result in the loop being considered infinite.
- Creating a task and pinned the task to core 1
- Increasing the priority of the task
Any help or suggestions would be greatly appreciated. Thank you!