static portTASK_FUNCTION( prvTimerTask, pvParameters )
{
TickType_t xNextExpireTime;
BaseType_t xListWasEmpty;
/* Just to avoid compiler warnings. */
( void ) pvParameters;
#if ( configUSE_DAEMON_TASK_STARTUP_HOOK == 1 )
{
/* Allow the application writer to execute some code in the context of
* this task at the point the task starts executing. This is useful if the
* application includes initialisation code that would benefit from
* executing after the scheduler has been started. */
vApplicationDaemonTaskStartupHook();
}
#endif /* configUSE_DAEMON_TASK_STARTUP_HOOK */
for( ; configCONTROL_INFINITE_LOOP(); )
{
/* Query the timers list to see if it contains any timers, and if so,
* obtain the time at which the next timer will expire. */
xNextExpireTime = prvGetNextExpireTime( &xListWasEmpty );
/* If a timer has expired, process it. Otherwise, block this task
* until either a timer does expire, or a command is received. */
prvProcessTimerOrBlockTask( xNextExpireTime, xListWasEmpty );
/* Empty the command queue. */
prvProcessReceivedCommands();
}
}
xNextExpireTime = prvGetNextExpireTime( &xListWasEmpty );
获取下一个列表节点
prvProcessTimerOrBlockTask( xNextExpireTime, xListWasEmpty );
( void ) xTaskResumeAll();
prvProcessExpiredTimer( xNextExpireTime, xTimeNow );
static void prvProcessExpiredTimer( const TickType_t xNextExpireTime,
const TickType_t xTimeNow )
{
/* MISRA Ref 11.5.3 Void pointer assignment */
/* More details at: https://github.com/FreeRTOS/FreeRTOS-Kernel/blob/main/MISRA.md#rule-115 */
/* coveritymisra_c_2012_rule_11_5_violation */
Timer_t * const pxTimer = ( Timer_t * ) listGET_OWNER_OF_HEAD_ENTRY( pxCurrentTimerList );
/* Remove the timer from the list of active timers. A check has already
* been performed to ensure the list is not empty. */
( void ) uxListRemove( &( pxTimer->xTimerListItem ) );
if( ( pxTimer->ucStatus & tmrSTATUS_IS_AUTORELOAD ) != 0U )
{
prvReloadTimer( pxTimer, xNextExpireTime, xTimeNow );
}
else
{
pxTimer->ucStatus &= ( ( uint8_t ) ~tmrSTATUS_IS_ACTIVE );
}
/* Call the timer callback. */
traceTIMER_EXPIRED( pxTimer );
pxTimer->pxCallbackFunction( ( TimerHandle_t ) pxTimer );
}
如果节点超时时间到达,那么删除节点,触发回调
/* Empty the command queue. */
prvProcessReceivedCommands();
如果节点时间没有达到,那么不触发回调
重新将任务挂起,设置超时剩余的超时时间。
vQueueWaitForMessageRestricted( xTimerQueue, ( xNextExpireTime - xTimeNow ), xListWasEmpty );
定时器接收消息处理,启动,停止,删除