In this article, we will take a look at the software timers in FreeRTOS.
A software timer allows a function to be executed at a set time in the future.
FreeRTOS – RTOS software timer functionality and features description
The function that is executed is referred to as a timer’s callback function. The interval between starting the timer and the time its callback function is executed is called the timer period. The timer period is user-configurable. Software timers do not rely on the underlying hardware timers of the microcontroller, instead, they use the OS tick counter.
A software timer can be configured in one of the following modes of operation:
- One-shot – The timer’s callback function is executed only once. It does not restart itself automatically, it should be explicitly restarted by the user.
- Auto-reload – The timer automatically restarts itself after the callback function is executed. This results in periodic callback function execution.
Each new software timer creation does not require a new individual FreeRTOS task. Instead, there is just one task (timer service task) for servicing all of the software timers. It is automatically created when the scheduler is started. All software timers and their callback functions execute in the context of this task. The task just as any other RTOS task runs according to the selected scheduling algorithm (e.g when it has the highest priority and is in a ready state). The timer service task checks if it is time to execute a timer’s callback function.
Software Timers vs Hardware Timers
It is important to know when to use software timers and when to use hardware timers. The following requirements should be considered when making the choice:
- timer accuracy
- timer resolution
Timer Accuracy
Every hardware timer needs a clock source in order to operate. The accuracy of this clock (which is usually very high) directly influences the hardware timer’s accuracy. We can use these kinds of timers for measuring pulse duration, generating precise timings, etc.
When we judge the accuracy of FreeRTOS software timers we should take into account not only the accuracy of the OS tick counter but also additional error due to the scheduling algorithm. Remember, the timer service task is just a regular task with a specific priority, and its execution may be delayed if there is a higher priority task.
Timer Resolution
The timer resolution is the smallest unit of time that the timer can measure (not to be confused with the timer bit resolution (e.g 8bit, 16bit, etc.)). It is equal to the time period of its input clock.
A hardware timer with an input clock with a frequency of 10MHz will have a resolution of 1µs. Hardware timers have configurations and controls that make them very flexible and useful in a lot of embedded systems scenarios.
The FreeRTOS software timers’ resolution is equal to the selected OS tick counter period. The minimum practical tick counter period for an RTOS starts at 1ms. This makes the software timers, not a good fit for scenarios requiring time resolution higher that 1ms.
Example: LED Blinking Using a Software Timer
This example is used to demonstrate the usage of FreeRTOS software timers. It is an alternative approach to the example shown in FreeRTOS: LED Blinking And Button Polling article.
The program will use one FreeRTOS task for reading the state of the bush-button and one software timer for operating the blinking of the LED. In the event of a button press, the information will be passed using an event group. The LED blinking will be enabled/disabled by pressing the push-button.
The code for the board and peripheral initialization is removed for simplicity. The full code of the program and the FreeRTOS configuration can be found in the following GitHub repository.
We start with the timer’s callback function. It is important to remember that these callback functions should be non-blocking.
static void led_toggle_callback( TimerHandle_t xTimer) {
EventBits_t event_bits;
static uint8_t toggle_en = 0;
//Get the button pressed event bit and clear it.
event_bits = xEventGroupClearBits( xFlagsEventGroup,BTN_PRESSED_Msk);
if (event_bits & BTN_PRESSED_Msk) {
toggle_en = ~toggle_en;
/* if toggling was enabled then we turn off the LED
if toggling was disabled, then the led was turned off anyway */
LED_OFF();
}
if (toggle_en) {
LED_TOGGLE();
}
}
In the code below we can see how a software timer called led_timer
is created. It is configured for auto-reload operation with a period of 200ms. The callback function is set to led_toggle_callback()
.
static void btn_read_task(void *pvParameters);
static void led_toggle_callback( TimerHandle_t xTimer);
TimerHandle_t led_timer;
/* Declare a variable to hold the created event group. */
static EventGroupHandle_t xFlagsEventGroup;
int main(void)
{
/* create the event group. */
xFlagsEventGroup = xEventGroupCreate();
xTaskCreate(btn_read_task, "button_read_task", configMINIMAL_STACK_SIZE + 10, NULL, btn_press_task_PRIO, NULL);
led_timer = xTimerCreate
( /* Just a text name, not used by the RTOS
kernel. */
"LED_toggle_timer",
/* The timer period in ticks, must be
greater than 0. */
200/portTICK_PERIOD_MS,
/* The timers will auto-reload themselves
when they expire. */
pdTRUE,
/* The ID is used to store a count of the
number of times the timer has expired, which
is initialised to 0. */
( void * ) 0,
/* Each timer calls the same callback when
it expires. */
led_toggle_callback
);
xTimerStart(led_timer,0);
vTaskStartScheduler();
for (;;)
;
}
Conclusion
Software timers are a very useful feature of FreeRTOS. They are simple to use and a good alternative to hardware timers in many scenarios. When deciding if a software timer should be used in your design, always think about the required resolution and accuracy.
I want to handle with PWM (TIM1). what should i use in Freertos ?
Software or hardware timers ?
For capturing or generating PWM it is best to use the available hardware timers as they can provide better accuracy and precision.
Thanks for your reply Yasen. One more question. please answer if you know? Do ı have to create a Task or can i use the PWM with hal out of task in FreeRtos ? (stm32wb- cmsis rtos v2)
It really depends on the use case and the rest of the system you’re designing. In general, you are not required to have a separate FreeRTOS task for every processing you will be doing in your app. Using a PWM driver based on hardware timers of the MCU will in most cases involve the usage of interrupts so calling PWM API outside of FreeRTOS is acceptable.
Thanks a lot Yasen.