动态方法创建软件定时器xTimerCreate,新创建的软件定时处于休眠状态
TimerHandle_t xTimerCreate(
const char *const pcTimerName, //软件定时器名字,用于调试使用
const TickType_t xTimerPeriodInTicks, //软件定时器的定时器周期,单位是时钟节拍数
const UBaseType_t uxAutoReload, //设置定时器模式,单次还是周期.参数为pdTRUE表示周期
void *const pvTimerID, //定时器ID号,多个定时器用回一个回调函数时,可以用此号区分
TimerCallbackFunction_t pxCallbackFunction
) //一般情况下每个定时器都有一个回调函数,周期到了以后就会执行这个回调函数
启动软件定时器
BaseType_t xTimerStart(TimerHandle_t xTimer, //要开启的软件定时器的句柄
TickType_t xTicksToWait) //设置阻塞时间
返回值:
pdPASS:
软件定时器开启成功, 其实就是命令发送成功
pdFAIL:
软件定时器开启失败
停止软件定时器 xTimerstop
BaseType_t xTimerStop(TimerHandle_t xTimer, //要停止的软件定时器的句柄
TickType_t xTicksToWait ) //设置阻塞时间
返回值:
pdPASS:
软件定时器停止成功
pdFAIL:
软件定时器停止失败
简述
考虑平台硬件定时器个数限制的, FreeRTOS 通过一个 Daemon 任务(启动调度器时自动创建)管理软定时器, 满足用户定时需求. Daemon 任务会在其执行期间检查用户启动的时间周期溢出的定时器,并调用其回调函数。
对于硬件定时器的中断服务程序, 我们知道不应该在里面执行复杂,可能导致阻塞的工作,相应的, 虽然软定时器实际是在定时Daemon 任务中执行,但是阻塞的话会导致其他定时器调用被延时, 所以实际使用也应该避免。
软定时器是通过一个任务来辅助实现,该功能时刻裁剪的 , 只有设置 FreeRTOSConfig.h
中configUSE_TIMERS == 1
将相关代码编译进来, 才能正常使用相关功能。
分析的源码版本是 v9.0.0
使用定时器
开始先介绍下如何在自己的工程中使用 FreeRTOS 的软件定时器。
配置定时器服务任务
程序中需要使用到软件定时器, 需要先在 FreeRTOSConfig.h
中正确配置如下宏 :
- configUSE_TIMERS
是否编译定时器相关代码, 如需要使用定时器, 设置为 1 - configTIMER_TASK_PRIORITY
设置定时器Daemon 任务优先级, 如果优先级太低, 可能导致定时器无法及时执行 - configTIMER_QUEUE_LENGTH
设置定时器Daemon 任务的命令队列深度, 设置定时器都是通过发送消息到该队列实现的。 - configTIMER_TASK_STACK_DEPTH
设置定时器Daemon 任务的栈大小
创建 启动 停止定时器
如下示例代码所示
TimerHandle_t xTimerUser; // 定义句柄
// 定时器回调函数格式
void vTimerCallback( TimerHandle_t xTimer )
{
// do something no block
// 获取溢出次数
static uin32_t ulCount = ( uint32_t ) pvTimerGetTimerID( xTimer );
// 累积溢出次数
++ulCount;
// 更新溢出次数
vTimerSetTimerID( xTimer, ( void * ) ulCount );
if (ulCount == 10) {
// 停止定时器
xTimerStop( xTimer, 0 );
}
}
void fun()
{
// 申请定时器, 配置
xTimerUser = xTimerCreate
/*调试用, 系统不用*/
("Timer's name",
/*定时溢出周期, 单位是任务节拍数*/
100,
/*是否自动重载, 此处设置周期性执行*/
pdTRUE,
/*记录定时器溢出次数, 初始化零, 用户自己设置*/
( void * ) 0,
/*回调函数*/
vTimerCallback);
if( xTimerUser != NULL ) {
// 启动定时器, 0 表示不阻塞
xTimerStart( xTimerUser, 0 );
}
}
如上所示, 调用函数 xTimerCreate
申请,配置定时器, 通过 xTimerStart
启动定时器, 当定时器计数溢出时, 系统回调注册的函数。
定时器可以设置为一次性 One-shot 或者自动重载 Auto-reload 两种, 第一种溢出后停止定时器, 第二种溢出后会再次启动定时器。