// Trace User Events Channels
traceString ue1, ue2;
Then, in the body of main(), before the scheduler is started, we need to register the user event channels:
...
// Register the Trace User Event Channels
ue1 = xTraceRegisterString("count");
ue2 = xTraceRegisterString("msg");
...
Now we can use ue1 and ue2 channel to issue printf-like messages into the recorder.
Let us print out the value of count in Task_1:
/*
* Task_1 toggles LED every 10ms
*/
void vTask1 (void *pvParameters)
{
portTickType xLastWakeTime;
uint16_t count;
count = 0;
// Initialize timing
xLastWakeTime = xTaskGetTickCount();
while(1)
{
// Toggle LED only if button is released
if (!BSP_PB_GetState())
{
BSP_LED_Toggle();
count++;
}
// Release semaphore every 10 count
if (count == 10)
{
xSemaphoreGive(xSem);
count = 0;
}
// Send count value into trace UEC
vTracePrintF(ue1, "%d", count);
// Wait here for 10ms since last wakeup
vTaskDelayUntil (&xLastWakeTime, (10/portTICK_RATE_MS));
}
}
And display a cool message whenever the semaphore was successfully taken in Task_2:
/*
* Task_2 sends a message to console when xSem semaphore is given
*/
void vTask2 (void *pvParameters)
{
portBASE_TYPE xStatus;
uint16_t count;
count = 0;
// Take the semaphore once to make sure it is empty
xSemaphoreTake(xSem, 0);
while(1)
{
// Wait here for Semaphore with 2s timeout
xStatus = xSemaphoreTake(xSem, 2000);
// Test the result of the take attempt
if (xStatus == pdPASS)
{
// The semaphore was taken as expected
vTracePrint(ue2, "Yep!");
// Display console message
my_printf("Hello %2d from task2\r\n", count);
count++;
}
else
{
// The 2s timeout elapsed without Semaphore being taken
// Display another message
my_printf("Hey! Where is my semaphore?\r\n");
}
}
}
Note that we used both vTracePrint() and vTracePrintF() functions. vTracePrint() is faster but it doesn't format numbers.
And now the result (yellow tags):
![]() |
![]() ![]() |