FreeRTOS软件定时器

FreeRTOS软件定时器

FreeRTOS软件定时器简介

软件定时器允许设置一段时间,当设置的时间达到之后就执行功能函数,被定时器调用的这个功能函数叫做定时器的回调函数。回调函数的两次执行间隔叫做定时器的定时周期,简而言之,当定时器到达了以后就会执行回调函数。
软件定时器的回调函数在定时器的服务任务中执行,所以一定不要在回调函数中调用任何会阻塞任务的API函数。(比如:vTaskDelay(10))
定时器是一个可选的、不属于FreeRTOS内核的功能,它是由定时器服务函数或任务提供的·。FreeRTOS提供了很多有关定时器的函数,这些函数都能被FreeRTOS的队列发送命令给定时器服务函数的。这个队列叫做定时器命令队列。定时器命令队列是提供FreeRTOS软件定时器使用的,用户不能直接访问。

定时器相关配置

FreeRTOS软件定时器_第1张图片

单次定时器和周期定时器

软件定时器分两种:单次定时器和周期定时器。单次定时器:定时器回调函数只执行一次,然后定时器停止运行(不能自动重新启用);周期定时器:定时器回调函数周期运行。(自动重新启用)

FreeRTOS软件定时器相关函数

复位软件定时器函数

在这里插入图片描述
FreeRTOS软件定时器_第2张图片
FreeRTOS软件定时器_第3张图片

创建软件定时器函数

在这里插入图片描述
FreeRTOS软件定时器_第4张图片
FreeRTOS软件定时器_第5张图片
FreeRTOS软件定时器_第6张图片
FreeRTOS软件定时器_第7张图片

开启软件定时器函数

在这里插入图片描述
FreeRTOS软件定时器_第8张图片
FreeRTOS软件定时器_第9张图片

停止软件定时器函数

在这里插入图片描述
FreeRTOS软件定时器_第10张图片
FreeRTOS软件定时器_第11张图片

实验

要求

FreeRTOS软件定时器_第12张图片
FreeRTOS软件定时器_第13张图片

程序

#include "sys.h"
#include "delay.h"
#include "usart.h"
#include "led.h"
#include "timer.h"
#include "lcd.h"
#include "key.h"
#include "beep.h"
#include "string.h"
#include "malloc.h"
#include "FreeRTOS.h"
#include "task.h"
#include "timers.h"

//任务优先级
#define START_TASK_PRIO			1
#define TIMERCONTROL_TASK_PRIO	2

//任务堆栈大小
#define START_STK_SIZE 			256  
#define TIMERCONTROL_STK_SIZE 	256  

//任务句柄
TaskHandle_t StartTask_Handler;
TaskHandle_t TimerControlTask_Handler;

//任务函数
void start_task(void *pvParameters);
void timercontrol_task(void *pvParameters);


TimerHandle_t 	AutoReloadTimer_Handle;			//周期定时器句柄
TimerHandle_t	OneShotTimer_Handle;			//单次定时器句柄

void AutoReloadCallback(TimerHandle_t xTimer); 	//周期定时器回调函数
void OneShotCallback(TimerHandle_t xTimer);		//单次定时器回调函数

//LCD使用的刷屏颜色
int lcd_discolor[14]={	WHITE, BLACK, BLUE,  BRED,      
						GRED,  GBLUE, RED,   MAGENTA,       	 
						GREEN, CYAN,  YELLOW,BROWN, 			
						BRRED, GRAY };

int main(void)
{ 
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);
	delay_init(168);					
	uart_init(115200);     				
	LED_Init();		        			
	KEY_Init();							
	BEEP_Init();						
	LCD_Init();						
	my_mem_init(SRAMIN);            	//初始化内部内存池
    
    POINT_COLOR = RED;
	LCD_ShowString(30,10,200,16,16,"STM32F407");	
	LCD_ShowString(30,30,200,16,16,"FreeRTOS Examp 15-1");
	LCD_ShowString(30,50,200,16,16,"KEY_UP:Start Tmr1");
	LCD_ShowString(30,70,200,16,16,"KEY0:Start Tmr2");
	LCD_ShowString(30,90,200,16,16,"KEY1:Stop Tmr1 and Tmr2");

	LCD_DrawLine(0,108,239,108);		//画线
	LCD_DrawLine(119,108,119,319);		//画线
	
	POINT_COLOR = BLACK;
	LCD_DrawRectangle(5,110,115,314); 	//画一个矩形
	LCD_DrawLine(5,130,115,130);		//画线
	
	LCD_DrawRectangle(125,110,234,314); //画一个矩形
	LCD_DrawLine(125,130,234,130);		//画线
	POINT_COLOR = BLUE;
	LCD_ShowString(6,111,110,16,16,	 "AutoTim:000");
	LCD_ShowString(126,111,110,16,16,"OneTim: 000");
	
	//创建开始任务
    xTaskCreate((TaskFunction_t )start_task,            //任务函数
                (const char*    )"start_task",          //任务名
                (uint16_t       )START_STK_SIZE,        //任务堆栈大小
                (void*          )NULL,                  //传递给任务的参数
                (UBaseType_t    )START_TASK_PRIO,       //任务优先级
                (TaskHandle_t*  )&StartTask_Handler);   //任务句柄             
    vTaskStartScheduler();          //开启任务调度器
}

//开始任务
void start_task(void *pvParameters)
{
    taskENTER_CRITICAL();           //进入临界区
    //创建软件定时器周期任务
    AutoReloadTimer_Handle=xTimerCreate((const char*		)"AutoReloadTimer",
									    (TickType_t			)1000,
							            (UBaseType_t		)pdTRUE,
							            (void*				)1,
							            (TimerCallbackFunction_t)AutoReloadCallback); //周期1S
    //创建软件定时器单次任务
	OneShotTimer_Handle=xTimerCreate((const char*			)"OneShotTimer",
							         (TickType_t			)2000,
							         (UBaseType_t			)pdFALSE,
							         (void*					)2,
							         (TimerCallbackFunction_t)OneShotCallback); //2s				  
    //创建定时器控制任务
    xTaskCreate((TaskFunction_t )timercontrol_task,             
                (const char*    )"timercontrol_task",           
                (uint16_t       )TIMERCONTROL_STK_SIZE,        
                (void*          )NULL,                  
                (UBaseType_t    )TIMERCONTROL_TASK_PRIO,        
                (TaskHandle_t*  )&TimerControlTask_Handler);    
    vTaskDelete(StartTask_Handler); //删除开始任务
    taskEXIT_CRITICAL();            //退出临界区
}

//TimerControl软件定时器控制任务
void timercontrol_task(void *pvParameters)
{
	u8 key,num;
	while(1)
	{
		//周期定时器和单次定时器创建成功执行下面
		if((AutoReloadTimer_Handle!=NULL)&&(OneShotTimer_Handle!=NULL))
		{
			key = KEY_Scan(0);
			switch(key)
			{
				case WKUP_PRES:     
					xTimerStart(AutoReloadTimer_Handle,0);	//开启周期定时器
					printf("开启周期定时器\r\n");
					break;
				case KEY0_PRES:	
					xTimerStart(OneShotTimer_Handle,0);		//开启单次定时器
					printf("开启单次定时器\r\n");
					break;
				case KEY1_PRES:	
					xTimerStop(AutoReloadTimer_Handle,0); 	//关闭周期定时器
					xTimerStop(OneShotTimer_Handle,0); 		//关闭单次定时器
					printf("关闭定时器\r\n");
					break;	
			}
		}
		num++;
		if(num==50) 	//500MS灯闪一次
		{
			num=0;
			LED0=!LED0;	
		}
        vTaskDelay(10); 
	}
}

//周期定时器回调函数
void AutoReloadCallback(TimerHandle_t xTimer)
{
	static u8 tmr1_num=0;
	tmr1_num++;									
	LCD_ShowxNum(70,111,tmr1_num,3,16,0x80); 	
	LCD_Fill(6,131,114,313,lcd_discolor[tmr1_num%14]);
}

//单次定时器回调函数
void OneShotCallback(TimerHandle_t xTimer)
{
	static u8 tmr2_num = 0;
	tmr2_num++;		
	LCD_ShowxNum(190,111,tmr2_num,3,16,0x80); 
	LCD_Fill(126,131,233,313,lcd_discolor[tmr2_num%14]); 
	LED1=!LED1;
    printf("单次定时器运行结束\r\n");
}

你可能感兴趣的:(FreeRTOS软件定时器)