rgarnett
(Rob Garnett)
September 26, 2022, 7:11am
1
Hi,
I wished to display all of the freeRTOS tasks in the form below:
I included the idle task using:
rtosCountersNow.idle = ulTaskGetIdleRunTimeCounter();
But i also wished to include the timer service task. I worked out that it had the handle:
xTimerTaskHandle
But is has been defined as static viz:
/* A queue that is used to send commands to the timer service task. */
PRIVILEGED_DATA static QueueHandle_t xTimerQueue = NULL;
PRIVILEGED_DATA TaskHandle_t xTimerTaskHandle = NULL;
So it is not available to use in order to get its RunTimeCounter field using:
#ifndef DRIVERS_FREERTOS_STATS_INC_FREERTOS_TASKS_C_ADDITIONS_H_
#define DRIVERS_FREERTOS_STATS_INC_FREERTOS_TASKS_C_ADDITIONS_H_
#include "FreeRTOS.h"
#include "task.h"
uint32_t TaskGetRunTimeCounter( TaskHandle_t xTask )
{
TCB_t *pxTCB;
uint32_t ulRunTimeCounter = 0;
/* xTask is NULL then get the state of the calling task. */
pxTCB = prvGetTCBFromHandle( xTask );
#if ( configGENERATE_RUN_TIME_STATS == 1 )
{
ulRunTimeCounter = pxTCB->ulRunTimeCounter;
}
#endif
return ulRunTimeCounter;
}
#endif /* DRIVERS_FREERTOS_STATS_INC_FREERTOS_TASKS_C_ADDITIONS_H_ */
I wasn’t sure what to do, so I did a naughty thing and changed the xTimerTaskHandle to global.
PRIVILEGED_DATA /* static */ TaskHandle_t xTimerTaskHandle = NULL;
This fixed my problem, but I feel dissatisfied as I’m sure there is a better way than me hacking the code.
Could someone advise me what I should do?
Best Regards
Rob.
PS I think someone did ask about this before, but a built in general per task
GetRuntime Counter function for individual tasks and the timer service would seem a useful feature.
aggarg
(Gaurav Aggarwal)
September 26, 2022, 11:22am
2
One alternative would be to use xTaskGetHandle, which lets you get a task handle from the name of a task.
A Second would be to use uxTaskGetSystemState to get an array of task statuses, which includes the information you are looking for.
rgarnett
(Rob Garnett)
September 26, 2022, 12:20pm
4
Hi GA
Thanks for that.
I must spend a bit more time browsing through the API so I get to know it better.
Regards
Rob
rgarnett
(Rob Garnett)
September 27, 2022, 3:58am
6
Hi GA,
I took your advice - all good.
I ended up with the following code. I am posting it to help others who may wish to display or otherwise process counters.
I added a reset counter function to the code so the user can reset all counters without rebooting.
FreeRTOSConfig
...
#define configUSE_TRACE_FACILITY 1
#define configGENERATE_RUN_TIME_STATS 1
#define configUSE_STATS_FORMATTING_FUNCTIONS 1
#define configRECORD_STACK_HIGH_ADDRESS 1
#define configUSE_16_BIT_TICKS 0
#define configUSE_MUTEXES 1
#define configQUEUE_REGISTRY_SIZE 8
#define configUSE_RECURSIVE_MUTEXES 1
#define configUSE_COUNTING_SEMAPHORES 1
#define configUSE_PORT_OPTIMISED_TASK_SELECTION 0
#define configCHECK_FOR_STACK_OVERFLOW 0
#define configUSE_TASK_NOTIFICATIONS 1
#define configINCLUDE_FREERTOS_TASK_C_ADDITIONS_H 1
...
#define INCLUDE_xTaskGetCurrentTaskHandle 1
#define INCLUDE_eTaskGetState 1
#define INCLUDE_xTaskGetIdleTaskHandle 1
freertos_tasks_c_additions.h
/*
******************************************************************************
* Project : STM32H7B3I_DISCO
* File Name : freertos_tasks_c_additions.h
* File Path : G:\ShorttClock_V2\ShorttClock_V2\STM32CubeIDE\Drivers\FreeRTOS Stats\Inc\freertos_tasks_c_additions.h
* File Wrk Spc : /STM32H7B3I_DISCO/Drivers/FreeRTOS Stats/Inc/freertos_tasks_c_additions.h
* Created On : 25 Sep. 2022 3:37:48 pm
* Description :
* Author : R J Garnett - Admin
******************************************************************************
*/
#ifndef DRIVERS_FREERTOS_STATS_INC_FREERTOS_TASKS_C_ADDITIONS_H_
#define DRIVERS_FREERTOS_STATS_INC_FREERTOS_TASKS_C_ADDITIONS_H_
#include "FreeRTOS.h"
#include "task.h"
uint32_t TaskGetRunTimeCounter(TaskHandle_t xTask)
{
TCB_t *pxTCB;
uint32_t ulRunTimeCounter = 0;
/* xTask is NULL then get the state of the calling task. */
pxTCB = prvGetTCBFromHandle( xTask );
#if ( configGENERATE_RUN_TIME_STATS == 1 )
{
ulRunTimeCounter = pxTCB->ulRunTimeCounter;
}
#endif
return ulRunTimeCounter;
}
/******************************************************************************/
void TaskResetRunTimeCounter(TaskHandle_t xTask)
{
TCB_t *pxTCB;
uint32_t ulRunTimeCounter = 0;
/* xTask is NULL then get the state of the calling task. */
pxTCB = prvGetTCBFromHandle( xTask );
#if ( configGENERATE_RUN_TIME_STATS == 1 )
{
pxTCB->ulRunTimeCounter = 0;
}
#endif
}
#endif /* DRIVERS_FREERTOS_STATS_INC_FREERTOS_TASKS_C_ADDITIONS_H_ */
/*
******************************************************************************
* Project : STM32H7B3I_DISCO
* File Name : freeRTOS_Stats.c
* File Path : G:\ShorttClock_V2\ShorttClock_V2\STM32CubeIDE\Drivers\FreeRTOS Stats\Src\freeRTOS_Stats.c
* File Wrk Spc : /STM32H7B3I_DISCO/Drivers/FreeRTOS Stats/Src/freeRTOS_Stats.c
* Created On : 25 Sep. 2022 2:07:24 pm
* Description :
* Author : R J Garnett - Admin
******************************************************************************
*/
#pragma GCC optimize ("Ofast") /* rjg todo */
//#pragma GCC optimize ("O0") /* rjg todo */
#define USE_DTCM __attribute__((section (".DTCM_MISC")))
//#define USE_DTCM
#define USE_ITCM __attribute__((section(".ITCM_SECTION")))
//#define USE_ITCM
#include "FreeRTOS.h"
#include "task.h"
#include "timers.h"
#include "freeRTOS_Stats.h"
uint32_t TaskGetRunTimeCounter(TaskHandle_t xTask);
void TaskResetRunTimeCounter(TaskHandle_t xTask);
volatile rtosCounter_t USE_DTCM rtosCountersNow;
volatile rtosCounter_t USE_DTCM rtosCountersSplit;
volatile rtosCounterPct_t USE_DTCM rtosCountersPct;
//volatile bool USE_DTCM counterSplitFlag = false;
//bool USE_DTCM countCaptured = false;
extern volatile unsigned long ulStatsTimerTicks;
extern TaskHandle_t xHandleClkCont;
extern TaskHandle_t wiFiTskHandle;
extern TaskHandle_t printTaskHandle;
extern TaskHandle_t xHandleProx;
extern TaskHandle_t monitorTskHandle;
extern TaskHandle_t norFlashTskHandle;
extern TaskHandle_t dtmTskHandle;
extern TaskHandle_t xHandlePosStats;
extern TaskHandle_t xTimerTaskHandle;
extern osThreadId_t GUI_TaskHandle;
USE_ITCM inline void calcTaskUtilisation(void)
{
float k;
rtosCountersNow.ulStatsTimerTicks = ulStatsTimerTicks;
rtosCountersNow.idle = ulTaskGetIdleRunTimeCounter();
rtosCountersNow.I2C_task = TaskGetRunTimeCounter(xHandleProx);
rtosCountersNow.ClkContTsk = TaskGetRunTimeCounter(xHandleClkCont);
rtosCountersNow.GUI_Task = TaskGetRunTimeCounter(GUI_TaskHandle);
rtosCountersNow.dtmTask = TaskGetRunTimeCounter(dtmTskHandle);
rtosCountersNow.monTask = TaskGetRunTimeCounter(monitorTskHandle);
rtosCountersNow.tmrSrvc = TaskGetRunTimeCounter(xTimerGetTimerDaemonTaskHandle());
rtosCountersNow.wiFiTask = TaskGetRunTimeCounter(wiFiTskHandle);
rtosCountersNow.printTask = TaskGetRunTimeCounter(printTaskHandle);
rtosCountersNow.norFlashTask = TaskGetRunTimeCounter(norFlashTskHandle);
rtosCountersNow.PosStatsTsk = TaskGetRunTimeCounter(xHandlePosStats);
k = -0.002f;
if(ulStatsTimerTicks > 0)
{
k = 100.0f / (float)ulStatsTimerTicks;
}
/* Now calc percentages */
rtosCountersPct.idle = (float)rtosCountersNow.idle * k;
rtosCountersPct.I2C_task = (float)rtosCountersNow.I2C_task * k;
rtosCountersPct.ClkContTsk = (float)rtosCountersNow.ClkContTsk * k;
rtosCountersPct.GUI_Task = (float)rtosCountersNow.GUI_Task * k;
rtosCountersPct.dtmTask = (float)rtosCountersNow.dtmTask * k;
rtosCountersPct.monTask = (float)rtosCountersNow.monTask * k;
rtosCountersPct.tmrSrvc = (float)rtosCountersNow.tmrSrvc * k;
rtosCountersPct.wiFiTask = (float)rtosCountersNow.wiFiTask * k;
rtosCountersPct.printTask = (float)rtosCountersNow.printTask * k;
rtosCountersPct.norFlashTask = (float)rtosCountersNow.norFlashTask * k;
rtosCountersPct.PosStatsTsk = (float)rtosCountersNow.PosStatsTsk * k;
}
USE_ITCM inline void resetRunTimeCounters(void)
{
// rtosCountersNow.ulStatsTimerTicks = ulStatsTimerTicks;
// rtosCountersNow.idle = ulTaskGetIdleRunTimeCounter();
// rtosCountersNow.I2C_task = TaskGetRunTimeCounter(xHandleProx);
// rtosCountersNow.ClkContTsk = TaskGetRunTimeCounter(xHandleClkCont);
// rtosCountersNow.GUI_Task = TaskGetRunTimeCounter(GUI_TaskHandle);
// rtosCountersNow.dtmTask = TaskGetRunTimeCounter(dtmTskHandle);
// rtosCountersNow.monTask = TaskGetRunTimeCounter(monitorTskHandle);
// rtosCountersNow.tmrSrvc = TaskGetRunTimeCounter(xTimerGetTimerDaemonTaskHandle());
// rtosCountersNow.wiFiTask = TaskGetRunTimeCounter(wiFiTskHandle);
// rtosCountersNow.printTask = TaskGetRunTimeCounter(printTaskHandle);
// rtosCountersNow.norFlashTask = TaskGetRunTimeCounter(norFlashTskHandle);
// rtosCountersNow.PosStatsTsk = TaskGetRunTimeCounter(xHandlePosStats);
ulStatsTimerTicks = 0;
TaskResetRunTimeCounter(xTaskGetIdleTaskHandle());
TaskResetRunTimeCounter(xHandleProx);
TaskResetRunTimeCounter(xHandleClkCont);
TaskResetRunTimeCounter(GUI_TaskHandle);
TaskResetRunTimeCounter(dtmTskHandle);
TaskResetRunTimeCounter(monitorTskHandle);
TaskResetRunTimeCounter(xTimerGetTimerDaemonTaskHandle());
TaskResetRunTimeCounter(wiFiTskHandle);
TaskResetRunTimeCounter(printTaskHandle);
TaskResetRunTimeCounter(norFlashTskHandle);
TaskResetRunTimeCounter(xHandlePosStats);
/* Now calc percentages */
rtosCountersPct.idle = 0.0f;
rtosCountersPct.I2C_task = 0.0f;;
rtosCountersPct.ClkContTsk = 0.0f;;
rtosCountersPct.GUI_Task = 0.0f;;
rtosCountersPct.dtmTask = 0.0f;;
rtosCountersPct.monTask = 0.0f;;
rtosCountersPct.tmrSrvc = 0.0f;;
rtosCountersPct.wiFiTask = 0.0f;;
rtosCountersPct.printTask = 0.0f;;
rtosCountersPct.norFlashTask = 0.0f;;
rtosCountersPct.PosStatsTsk = 0.0f;;
}
Hope someone finds this useful.
aggarg
(Gaurav Aggarwal)
September 27, 2022, 4:49am
7
Thank you for taking time to report your solution.