FreeRTOS学习第7篇--周期性延迟和相对性延迟函数

发布时间:2024年01月18日

FreeRTOS学习第7篇–周期性延迟和相对性延迟函数

本文目标:学习与使用FreeRTOS中的延迟函数,主要是学习两个函数的使用。

按照本文的描述,应该可以跑通实验并举一反三。

本文实验条件:拥有C语言基础,装有编译和集成的开发环境,比如:Keil uVision5

时间延迟

在freertos中的时间延迟有两个:vTaskDelayUntil和vTaskDelay,区别如下:

vTaskDelay是相对延时函数,它指定的是从调用该函数后开始计算的延时时间,单位是系统节拍时钟周期。这个函数适合需要固定时间间隔的延时操作,但是它可能受到其他任务和中断的影响,导致下一次执行的时间不准确。

vTaskDelayUntil是绝对延时函数,它指定的是一个绝对的唤醒时间,单位也是系统节拍时钟周期。这个函数适合实现周期性的延时操作,它可以保证任务以固定的频率执行,不受其他因素的干扰。但是如果指定的唤醒时间已经过去,那么该函数会立即返回,不会有延时效果。

vTaskDelay函数原型

void vTaskDelay( const TickType_t xTicksToDelay );

函数描述:

函数 vTaskDelay 用于任务的延迟。

参数 xTicksToDelay 用于设置延迟的时钟节拍个数,范围 1- 0xFFFFFFFF。延迟时间的最大值在portmacro.h 文件里面有定义:

typedef uint32_t TickType_t;

#define portMAX_DELAY ( TickType_t )0xffffffffUL

即延迟时间的范围是:1- 0xFFFFFFFF

vTaskDelayUntil函数原型

void vTaskDelayUntil( TickType_t *pxPreviousWakeTime, 
                      const TickType_t xTimeIncrement ); 

函数描述:

函数 vTaskDelayUntil 用于周期性延迟。

第 1 个参数,存储任务上次处于非阻塞状态时刻的变量地址。

第 2 个参数,周期性延迟时间。

使用这个函数要注意的点:

使用此函数需要在 FreeRTOSConfig.h 配置文件中配置如下宏定义为 1

#define INCLUDE_vTaskDelayUntil             1

这个两个的函数使用举例可以看我下面的代码片段

PrintTask_Task任务相关代码片段

void PrintTask(void *params)
{
	struct TaskPrintInfo *pInfo = params;
	uint32_t cnt = 0;
	OLED_Init();
	TickType_t ticks;
	BaseType_t preTime;
	uint64_t t1, t2;
	
	preTime = xTaskGetTickCount();
	while (1)
	{
		/* 打印信息 */
		if (g_LCDCanUse)
		{
			g_LCDCanUse = 0;
			OLED_ShowString(pInfo->x,pInfo->y,pInfo->name,16);
			OLED_ShowNum((pInfo->x + 8 * 6),pInfo->y,cnt++,4,16);
			g_LCDCanUse = 1;
			mdelay(cnt & 0x07);  // 简单限制  模拟干一些活  使得运行PrintTask这个函数有不一样的时长
		}
		

		t1 = system_get_ns();
		ticks = 500 / portTICK_PERIOD_MS;
		vTaskDelayUntil(&preTime, ticks);   // 绝对延迟 打印出来的时间差是跟下面的时间差有区别
//		vTaskDelay(ticks);  // 相对延迟函数 会进行Block 
		t2 = system_get_ns();
		
		OLED_ShowNum((pInfo->x + 8),pInfo->y + 16,t2-t1,9,16);
		OLED_Refresh();     
		
	}
}
 xTaskCreate(PrintTask, "task1", 128, &g_Task1Info, osPriorityNormal, NULL);
static struct TaskPrintInfo g_Task1Info = {0, 0,   "Task1"};

实验现象

下载代码到板子上,使用vTaskDelay的相对延迟函数时,我显示的时间差始终是稳定的,我使用vTaskDelayUntil的绝对延迟时,我显示的时间差就有部分变化。

绝对延迟显示

相对延迟显示

本文中使用的测试工程

文章来源:https://blog.csdn.net/weixin_44317448/article/details/135662750
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。