FreeRTOS学习笔记-软件定时器
概述
软件定时器用于调度在未来的设定时间执行的函数,或以固定频率定期执行的函数。 由软件定时器执行的函数称为软件定时器的回调函数。软件定时器由FreeRTOS实现,不需要硬件支持,与硬件定时器或计数器无关。
关键函数说明
头文件
#include “freertos/timers.h”
创建与删除软件定时器
//创建
TimerHandle_t xTimerCreate(
const char * const pcTimerName,//定时器名
TickType_t xTimerPeriodInTicks,//定时周期,单位为Tick 如:pdMS_TO_TICKS( 500 ) == 500ms
UBaseType_t uxAutoReload,//是否重载 pdTRUE / pdFALSE
void * pvTimerID,//定时器ID指针
TimerCallbackFunction_t pxCallbackFunction //回调函数指针
);//返回值为所创建的定时器句柄
//删除
BaseType_t xTimerDelete(
TimerHandle_t xTimer, //定时器句柄
TickType_t xTicksToWait//删除超时
);
软件定时器控制
这几个函数返回值均为: pdPASS / pdFAIL
//启动
BaseType_t xTimerStart( TimerHandle_t xTimer, TickType_t xTicksToWait );
//停止
BaseType_t xTimerStop( TimerHandle_t xTimer, TickType_t xTicksToWait );
//复位
BaseType_t xTimerReset( TimerHandle_t xTimer, TickType_t xTicksToWait );
//修改定时周期
BaseType_t xTimerChangePeriod(
TimerHandle_t xTimer,
TickType_t xNewPeriod,//新的定时器周期
TickType_t xTicksToWait
);
xTicksToWait 说明:
FreeRTOS内核不提供计时功能,而是由 timer service (or daemon) 任务 实现,定时器API通过定时器队列发送命令到 timer service (or daemon) 任务 ,xTicksToWait 表示如果队列已满,则任务应保持阻塞状态,以等待队列腾出可用空间的最长时间。
获取定时器名字、周期和ID
//获取定时器名
const char * pcTimerGetName( TimerHandle_t xTimer );
//获取定时周期
TickType_t xTimerGetPeriod( TimerHandle_t xTimer );
//获取定时器ID
void *pvTimerGetTimerID( TimerHandle_t xTimer );
课程示例
软件定时器的创建、启动、修改、复位、停止和删除测试
#include <stdio.h>
#include "sdkconfig.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"
#include "freertos/timers.h"
void timer1_callback(TimerHandle_t xTimer)
{
printf("callback1 run \n");
}
void app_main(void)
{
TimerHandle_t Timer1;
int ID1 = 1;
Timer1 = xTimerCreate("Timer1", pdMS_TO_TICKS(1000), pdTRUE, (void *)ID1, timer1_callback); //是否重载 pdTRUE / pdFALSE
printf("creat timer1 period = 1s \n");
//启动
xTimerStart(Timer1, 0);
printf("start timer1 \n");
vTaskDelay(3000 / portTICK_PERIOD_MS);
//复位
for (int i = 0; i < 5; i++)
{
xTimerReset(Timer1, 0);
printf("reset timer1 count = %d \n", i + 1);
vTaskDelay(500 / portTICK_PERIOD_MS);
}
//修改定时周期
xTimerChangePeriod(Timer1, pdMS_TO_TICKS(3000), 0);
printf("change timer1 period = 3s \n");
vTaskDelay(9000 / portTICK_PERIOD_MS);
//停止
xTimerStop(Timer1, 0);
printf("stop timer1 \n");
xTimerDelete(Timer1, 0);
printf("delete timer1 \n");
}
多个定时器控制同一个回调函数
#include <stdio.h>
#include "sdkconfig.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"
#include "freertos/timers.h"
void timer_callback(TimerHandle_t xTimer)
{
char *timer_name;
int *timer_id;
timer_name = pcTimerGetName(xTimer);
timer_id = (int *)pvTimerGetTimerID(xTimer);
if (*timer_id == 1)
{
printf("%s_callback run ******* \n", timer_name);
}
if (*timer_id == 2)
{
printf("%s_callback run **************** \n", timer_name);
}
}
void app_main(void)
{
TimerHandle_t Timer1, Timer2;
int ID1 = 1;
int ID2 = 2;
Timer1 = xTimerCreate("Timer1", pdMS_TO_TICKS(2000), pdTRUE, (void *)&ID1, timer_callback); //是否重载 pdTRUE / pdFALSE
Timer2 = xTimerCreate("Timer2", pdMS_TO_TICKS(500), pdTRUE, (void *)&ID2, timer_callback); //ID需要取地址
xTimerStart(Timer1, 0);
xTimerStart(Timer2, 0);
vTaskDelay(10000 / portTICK_PERIOD_MS);
xTimerStop(Timer1, 0);
xTimerStop(Timer2, 0);
printf("stop timer \n");
xTimerDelete(Timer1, 0);
xTimerDelete(Timer2, 0);
}
效果
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer1_callback run *******
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer1_callback run *******
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer1_callback run *******
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer1_callback run *******
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
Timer2_callback run ****************
stop timer