It’s time to learn how the “OS_TASK_CREATEEX()
" function works. when we are in the necessity of using one single function for different tasks we can pass a parameter to this function and use it in the way we want. To do this, we’re going to use the “OS_TASK_CREATEEX()
" to provide a void pointer as parameter and use it into the different tasks. This void pointer is call “task context” and in the case of the example below we are using it to represent different delay values
#include "bsp.h"
static int Stack1[128], Stack2[128]; // Task stacks
static OS_TASK Task1, Task2; // Task control blocks
void Task_Demo1( void* Parameter );
int main( void )
{
OS_Init(); // Initialize embOS (must be first)
HAL_Init();
OS_InitHW(); // Initialize Hardware for embOS
OS_TASK_CREATEEX(&Task1, "HP Task1", 100, Task_Demo1, Stack1, (void*) 1000); // creating the first task with its respective context
OS_TASK_CREATEEX(&Task2, "HP Task2", 50, Task_Demo1, Stack2, (void*) 200); // creating the second task with its respective context
OS_Start(); // Start multitasking
return 0u;
}
void Task_Demo1( void* Parameter ){
GPIO_InitTypeDef GPIO_InitStruct;
__HAL_RCC_GPIOA_CLK_ENABLE( );
__HAL_RCC_GPIOC_CLK_ENABLE( );
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.Pin = GPIO_PIN_5;
HAL_GPIO_Init( GPIOA, &GPIO_InitStruct );
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
GPIO_InitStruct.Pin = GPIO_PIN_0;
HAL_GPIO_Init( GPIOC, &GPIO_InitStruct );
for( ;; ){
if( (OS_TIME)Parameter == 1000 ){
SEGGER_SYSVIEW_PrintfHost( "TASK 1" );
HAL_GPIO_TogglePin( GPIOA, GPIO_PIN_5 );
OS_TASK_Delay((OS_TIME)Parameter);
}
else{
SEGGER_SYSVIEW_PrintfHost( "TASK2 2" );
HAL_GPIO_TogglePin( GPIOC, GPIO_PIN_0 );
OS_TASK_Delay((OS_TIME)Parameter);
}
}
}
The example above is a simple demonstration for using context within a task. However, embOS offers another little complex way of using the context.
SYSTEMVIEW
Build and flash the program and then run systemview.

Look at the timeline. You can see how every 200ms a task runs (TASK 2) and when the program reaches 1 second both tasks run.

looking closer you can notice how the tasks are running according with their priorities.

In the Event List we can see the messages that the tasks printed when each one was executed. In this way, we corroborate the task contexts are correct.