FreeRTOS之奇淫技巧
前言
工欲善其事,必先利其器。
串口打印
笔者的环境是ST STM32F103VE + IAR。printf
依赖IAR的库函数,移植的时候需实现putchar
。
CPU监控
依赖ST开源的Utilities for CPU Load calculation。
cpu_utils.c
cpu_utils.h
cpu_utils.c
里面有非常详细移植方法,请认证阅读。
API
void vDisplayOsCPUUsage( void )
{
uint16_t usPercentage;
usPercentage = osGetCPUUsage();
printf( "CPU Usage %d%%\n", usPercentage );
}
效果
CPU Usage 10%
Runtime
在FreeRTOS.h中使能以下宏
#ifndef configGENERATE_RUN_TIME_STATS
#define configGENERATE_RUN_TIME_STATS 1
#endif
#define portCONFIGURE_TIMER_FOR_RUN_TIME_STATS()
#define portGET_RUN_TIME_COUNTER_VALUE() xTickCount
API
void vDisplayRunTimeStatesInf( void )
{
uint8_t *buf = pvPortMalloc(4096);
if (buf == NULL)
{
printf( "pvPortMalloc 4096 failed!\n" );
return;
}
memset( buf, 0, 4096 );
vTaskGetRunTimeStats( ( char * ) buf );
printf( "******************************************************\n" );
printf( "%s\n", buf );
printf( "******************************************************\n" );
vPortFree( buf );
}
效果
******************************************************
COMRx 100 <1%
IDLE 7647946 90%
sDevice 224 <1%
Tmr Svc 848759 9%
******************************************************
第一列是任务名称,其中IDLE为空闲任务。第二列是时间片的统计。第三列是是对应任务的CPU占用率。
Task
在FreeRTOSConfig.h中使能以下宏
#define configUSE_TRACE_FACILITY 1
API
void vDisplayTaskInf( void )
{
uint8_t *buf = pvPortMalloc(4096);
if (buf == NULL)
{
printf( "pvPortMalloc 4096 failed!\n" );
return;
}
memset( buf, 0, 4096 );
vTaskList( ( char * ) buf );
printf( "******************************************************\n" );
printf( "%s\n", buf );
printf( "******************************************************\n" );
vPortFree( buf );
}
效果
******************************************************
COMRx X 1 882 1
IDLE R 0 104 3
sDevice B 3 882 2
Tmr Svc B 1 34 4
******************************************************
第一列是任务名称,其中IDLE为空闲任务。
第二列是运行状态。
#define tskRUNNING_CHAR ( 'X' )
#define tskBLOCKED_CHAR ( 'B' )
#define tskREADY_CHAR ( 'R' )
#define tskDELETED_CHAR ( 'D' )
#define tskSUSPENDED_CHAR ( 'S' )
第三列是对应任务的优先级,数字越大,优先级越高。例如,IDLE任务为0,优先级最低。
第四列是对应任务栈的剩余空间历史最小值。这个对于调整栈的大小非常有指导价值。
第五列是任务的序号。
Memory
API
void vDisplayMemInf( void )
{
printf( "\nRemaining Memory %d Bytes\r\n", ( int )xPortGetFreeHeapSize() );
}
效果
Remaining Memory 11864 Bytes
以上的数字是Heap的剩余空间。一般来说,尽量从Heap中分配堆存会增加内存利用率。但是Heap也会有碎片化和不稳定等因素。