vTaskDelay: how it works

Hi,

I’m trying to understand how ‘vTaskDelay’ works.
Here is my simple code:

void app_main(void)
{
    s_led_state=1;
    vTaskDelay(4);
    s_led_state = 2;
    
    while (1) ;
}

I assume somewhere in the FreeRTOS code there is check ‘count == 4’ or similar. So I’m looking this code line, where is it exactly.

The reason I have a simulator which never stops for vTaskDelay (s_led_state = 2; never reached) but it works on ESP32C3. I can debug both.

Thanks for the help.

very roughly:

vTasDelay suspends the task, ie puts the task on a system list of tasks that will not be scheduled. The number of ticks to wait for is recorded in the TCB (task control block). The sys tick handler decrements the count of each task on the suspended list and puts the task back on the ready list once the count reaches zero, so the scheduler can grant the task CPU time according to the scheduling rules.

The code is in tasks.c.

This is ‘xTaskIncrementTick’ ?

No, xTaskIncrementTick is only for use by the scheduler to increment tick count and check if any task got unblocked. @RAc has given an accurate description of vTaskDelay and you can read about it more and look at an example here.

Also, looking at the code that you shared, are you sure you are calling vTaskDelay from a task and not your application’s main function. This API is used to delay a task for a given number of ticks.

vTaskDelay works by putting the task on the “Delay List” (or the overflow delayed list if the time to delay is shorter than the time to the Tick Counter to overflow), with a list value of the tick count to wake up the task. The tick interrupt routine will check the front of that list and wake up every task that has a list value (the time to wake up) that has been reached. This is in xTaskIncrementTick.

In which field is this recorded? I assume pTCB->field or similar…

I’m working with ESP-IDF FreeRTOS implementation and there is a default task inserted before calling ‘app_main’. I also debugged my code on the eval board and it waits exactly 4 ticks.

So my questiions
What is the C type of pTCB?
What is the field name ?
Is there any macro/routine associated with this operation ?

again, as @rohitmdn pointed out, your code appears to be executed in the main loop instead of a task which is an error. Then again, if your app_main() is indeed a task function, then you need to relocate the while(1), otherwise your call to vTaskDelay() is executed exactly once.

As others have pointed out, your code isn’t going to work because of where you are calling vTaskDelay(). I recommend starting with the free to download book, which will explain things for you, and come with simple examples. As to your questions on C types and function implementations - all the source code is available for you. The easiest thing for you to do is step through the code in the debugger to see exactly how it works. For example, this is the vTaskDelay() implementation. It’s not productive to ask others to look up types for your.

1 Like

As I said, it isn’t in the TCB, it is in a member of the List item (A List_t). That is part of the TCB, in the xStateListItem, in the member xItemValue.

I suggest you actually look at the code for vTaskDelay, and the routines it calls to see how it is done.

Note, the TCB is defined in Task.c as a struct tskTaskControlBlock.

@jsmith786x You may find these tutorials helpful to learn FreeRTOS - GitHub - FreeRTOS/Lab-Project-FreeRTOS-Tutorials: Tutorials to learn FreeRTOS Kernel..

In the case of ESP-IDF, app_main is called from main_task - esp-idf/components/freertos/app_startup.c at b5ac4fbdf9e9fb320bb0a98ee4fbaa18f8566f37 · espressif/esp-idf · GitHub. Is the same true for your simulator too? If not, try to create a separate task and call vTaskDelay from there.