四、FreeRTOS之FreeRTOS移植

本文围绕FreeRTOS展开,介绍了从官网获取V10.4.6版本源码的方法,重点讲解在正点原子开发板上移植FreeRTOS的步骤,包括添加源码、配置文件、修改相关文件等。还说明了系统配置文件FreeRTOSConfig.h的作用,可对其进行功能配置和裁剪。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、获取FreeRTOS(熟悉)

1.1 源码获取:
  • FreeRTOS官网:https://www.freertos.org/,本人所使用的例程为FreeRTOS的V10.4.6版本。

  • 进入后点击下载FreeRTOS,选择“FreeRTOS 202112.00”文件,下载完成后解压到指定目录。

 

名称

描述

FreeRTOS

FreeRTOS内核

FreeRTOS-Plus

FreeRTOS组件

tools

工具

GitHub-FreeRTOS-Home

FreeRTOSGitHub仓库链接

Quick_Start_Guide

快速入门指南官方文档链接

Upgrading-to-FreeRTOS-xxx

升级到指定FreeRTOS版本官方文档链接

History.txt

FreeRTOS历史更新记录

其他

其他

我们主要掌握 FreeRTOS内核就 可以了,内核里面有以下文件

名称

描述

Demo

FreeRTOS演示例程

License

FreeRTOS相关许可

Source

FreeRTOS源码

Test

公用以及移植层测试代码

 我们主要掌握demo以及source即可

 Demo文件夹

Demo文件夹里面就是FreeRTOS的演示例程,如下所示:我们主要看就就是这两个STM32相关的

可以看出FreeRTOS 支持多种芯片架构,支持多种不同型号芯片,对于入门学习FreeRTOS是十分有帮助的,在学习移植FreeRTOS的过程中可以参考这些演示工程。

Source文件夹

就是FreeRTOS源码

名称

描述

include

内包含了FreeRTOS的头文件

portable

内包含了FreeRTOS的移植文件

croutine.c

协程相关文件

event_groups.c

事件相关文件

list.c

列表相关文件

queue.c

队列相关文件

stream_buffer.c

流式缓冲区相关文件

tasks.c

任务相关文件

timers.c

软件定时器相关文件

portable文件夹

FreeRTOS操作系统归根到底是一个软件层面的东西,那FreeRTOS是如何跟硬件联系在一起的呢?

portable文件夹里面的东西就是连接桥梁

由于我们使用MDK开发,因此这里只重点介绍其中的部分移植文件

名称

描述

Keil

指向RVDS文件夹

RVDS

不同内核芯片的移植文件

MemMang

内存管理文件

二、FreeRTOS手把手移植(掌握)

 2.1 目的:实现正点原子开发板的FreeRTOS移植 
 2.2 移植准备:


①FreeRTOS源码

②使用HAL库版本的《内存管理的实验为基础工程进行FreeRTOS的移植。(有需要可以留言或者私信)

2.3 移植步骤:

 2.3.1 添加FreeRTOS源码

详见FreeRTOS操作指南V1.5(后期会免费提供给大家,如需可留言或者私信)

将所有FreeRTOS相关的所需文件添加到工程后,如下图 所示:

 2.3.2添加FreeRTOSConfig.h文件,添加至user路径下

FreeRTOSConfig.h是 FreeRTOS操作系统的配置文件, FreeRTOS操作系统是可裁剪的,用户可以根据需求对 FreeRTOS进行裁剪,裁剪掉不需要用到的 FreeRTOS功能,以此来节约 MCU中寸土寸金的内存资源。那么 FreeRTOSConfig.h文件从哪里来呢?主要有三个途径:

  1. 自己编写(新手不推荐)
  2. 演示demo
  3. 参考的项目

2.3.3修改SYSTEM文件

SYSTEM文件夹中的文件一开始是针对 μC/OS编写的,因此使用 FreeRTOS的话,就需要作相应的修改。SYSTEM文件夹中一共需要修改三个文件,分别是 sys.h、 usart.c、 delay.c。

  • sys.h文件 :sys.h文件的修改很简单, 在 sys.h文件中使用了宏 SYS_SUPPORT_OS来定义是否支持 OS因为要支持 FreeRTOS,因此应当将宏 SYS_SUPPORT_OS定义为 1,具体修改如下 所示​​​​​​​​​​​​​​

  • usart.c文件:usart.c文件的修改也很简单,一共有两个地方需要修改, 首先就是串口的中断服务函数,原本在使用 μC/OS的时候,进入和退出中断需要添加 OSIntEnter()和 OSIntExit()两个函数,这是 μC/OS对于中断 的相关处理机制,而 FreeRTOS中并没有这种机制,因此 将这两行代码删除,修改后串口的中断服务函数如下 所示

 一个 是 添加 FreeRTOS.h头 文件,默认 是添加的 UCOS中 的 includes.h头文件,修改以后如下:

  •  修改 delay.c文件:接下来修改SYSTEM文件夹中的最后一个文件 delay.c delay.c文件需要改动的地方就比较多了,大致可分为三个步骤:删除适用于 μC/OS但不适用于 FreeRTOS的相关代码、添加FreeRTOS的相关代码、修改部分 内容 。

        (1) 删除适用于 μC/OS但不适用于 FreeRTOS的相关代码: 一共需要删除1个 全局变量、 6个宏定义、 3个函数 ,这些要删除的代码在使用 μC/OS的时候会使用到,但是在使用 FreeRTOS的时候无需使用 ,需要删除的代码如下所示:

/* 定义g_fac_ms变量, 表示ms延时的倍乘数, 
 * 代表每个节拍的ms数, (仅在使能os的时候,需要用到) 
 */ 
static uint16_t g_fac_ms = 0; 
/* 
 * 当delay_us/delay_ms需要支持OS的时候需要三个与OS相关的宏定义和函数来支持 
 * 首先是3个宏定义: 
 *     delay_osrunning :用于表示OS当前是否正在运行,以决定是否可以使用相关函数 
 *     delay_ostickspersec :用于表示OS设定的时钟节拍, 
 *                            delay_init将根据这个参数来初始化systick 
 *     delay_osintnesting :用于表示OS中断嵌套级别,因为中断里面不可以调度,
 *     delay_ms使用该参数来决定如何运行
 * 然后是3个函数:
 *     delay_osschedlock :用于锁定OS任务调度,禁止调度 
 *     delay_osschedunlock :用于解锁OS任务调度,重新开启调度 
 *     delay_ostimedly :用于OS延时,可以引起任务调度. 
 * 
 * 本例程仅作UCOSII和UCOSIII的支持,其他OS,请自行参考着移植 */
/* 支持UCOSII */
#ifdef  OS_CRITICAL_METHOD                      /* OS_CRITICAL_METHOD定义了,说明要支持UCOSII */
#define delay_osrunning     OSRunning           /* OS是否运行标记,0,不运行;1,在运行 */
#define delay_ostickspersec OS_TICKS_PER_SEC    /* OS时钟节拍,即每秒调度次数 */
#define delay_osintnesting  OSIntNesting        /* 中断嵌套级别,即中断嵌套次数 */
#endif

/* 支持UCOSIII */
#ifdef  CPU_CFG_CRITICAL_METHOD                 /* CPU_CFG_CRITICAL_METHOD定义了,说明要支持UCOSIII */
#define delay_osrunning     OSRunning           /* OS是否运行标记,0,不运行;1,在运行 */
#define delay_ostickspersec OSCfg_TickRate_Hz   /* OS时钟节拍,即每秒调度次数 */
#define delay_osintnesting  OSIntNestingCtr     /* 中断嵌套级别,即中断嵌套次数 */
#endif

/**
 * @brief     us级延时时,关闭任务调度(防止打断us级延迟)
 * @param     无  
 * @retval    无
 */  
void delay_osschedlock(void)
{
#ifdef CPU_CFG_CRITICAL_METHOD          /* 使用UCOSIII */
    OS_ERR err;
    OSSchedLock(&err);                  /* UCOSIII的方式,禁止调度,防止打断us延时 */
#else                                   /* 否则UCOSII */
    OSSchedLock();                      /* UCOSII的方式,禁止调度,防止打断us延时 */
#endif
}

/**
 * @brief     us级延时时,恢复任务调度
 * @param     无
 * @retval    无
 */  
void delay_osschedunlock(void)
{
#ifdef CPU_CFG_CRITICAL_METHOD          /* 使用UCOSIII */
    OS_ERR err;
    OSSchedUnlock(&err);                /* UCOSIII的方式,恢复调度 */
#else                                   /* 否则UCOSII */
    OSSchedUnlock();                    /* UCOSII的方式,恢复调度 */
#endif
}

/**
 * @brief     us级延时时,恢复任务调度
 * @param     ticks : 延时的节拍数
 * @retval    无
 */  
void delay_ostimedly(uint32_t ticks)
{
#ifdef CPU_CFG_CRITICAL_METHOD
    OS_ERR err; 
    OSTimeDly(ticks, OS_OPT_TIME_PERIODIC, &err);   /* UCOSIII延时采用周期模式 */
#else
    OSTimeDly(ticks);                               /* UCOSII延时 */
#endif 
}

(2) 添加 FreeRTOS的相关代码:只需要在delay.c文件中使用 extern关键字导入一个 FreeRTOS函数xPortSysTickHandler()即可,这个函数是 用于处理 FreeRTOS系统时钟节拍的,本教程是使用
SysTick作为 FreeRTOS操作系统的心跳,因此需要在 SysTick的中断服务函数中调用这个函数,因此将代码添加到 SysTick中断服务函数之前,代码修改如下:

 
extern void xPortSysTickHandler(void);
/** 
 * @brief systick中断服务函数,使用OS时用到 
 * @param ticks: 延时的节拍数 
 * @retval 无 
 */
void SysTick_Handler(void)
{	

/*代码省略*/

}

 (3) 修改部分内容最后要修改的内容包括两个,分别是包含头文件和4个函数。首先来看需要修改的4个函数,分别是 SysTick_Handler()、 delay_init()、 delay_us()和delay_ms()。

        (a)SysTick_Handler()这个函数是SysTick的中断服务函数,需要在这个函数中重复调用上          个步骤中导入的函数xPortSysTickHand(),xPortSysTickHandler(),代码修改后如下所示

/** 
  * @brief systick中断服务函数,使用OS时用到 
  * @param ticks: 延时的节拍数 
  * @retval 无 
  */
//systick中断服务函数,使用ucos时用到
void SysTick_Handler(void)
{	
    HAL_IncTick();
    /* OS开始跑了,才执行正常的调度处理 */
    if(xTaskGetSchedulerState()!=taskSCHEDULER_NOT_STARTED)//系统已经运行
    {
        xPortSysTickHandler();	
    }
}

(b) delay_init() 函数delay_init()主要用于初始化 SysTick。这里要说明的是, 在后续调用函数
vTaskStartScheduler()这个函数在下文中讲解到 FreeRTOS任务调度器的时候会具体分析)的
时候, FreeRTOS会按照 FreeRTOSConfig.h文件的配置对 SysTick进行初始化,因此 delay_init()函数初始化的 SysTick主要使用在 FreeRTOS开始任务调度之前。函数 delay_init()要修改的部分
主要为 SysTick的重装载值以及删除不用的代码,代码修改如下:

//初始化延迟函数
//SYSTICK的时钟固定为AHB时钟,基础例程里面SYSTICK时钟频率为AHB/8
//这里为了兼容FreeRTOS,所以将SYSTICK的时钟频率改为AHB的频率!
//SYSCLK:系统时钟频率
void delay_init()
{
	u32 reload;
	SysTick_CLKSourceConfig(SysTick_CLKSource_HCLK);//选择外部时钟  HCLK
	fac_us=SystemCoreClock/1000000;				//不论是否使用OS,fac_us都需要使用
	reload=SystemCoreClock/1000000;				//每秒钟的计数次数 单位为M  
	reload*=1000000/configTICK_RATE_HZ;			//根据configTICK_RATE_HZ设定溢出时间
												//reload为24位寄存器,最大值:16777216,在72M下,约合0.233s左右	
	fac_ms=1000/configTICK_RATE_HZ;				//代表OS可以延时的最少单位	   

	SysTick->CTRL|=SysTick_CTRL_TICKINT_Msk;   	//开启SYSTICK中断
	SysTick->LOAD=reload; 						//每1/configTICK_RATE_HZ秒中断一次	
	SysTick->CTRL|=SysTick_CTRL_ENABLE_Msk;   	//开启SYSTICK    
}								    

 (c) delay_us()函数
delay_us()用于微秒级的 CPU忙延时 ,原本的函数 delay_us()延时的前后加入了自定义函数 delay_osschedlock()和 delay_osschedunlock()用于锁定和解锁 μC/OS的任务调度器,以此来
让延时更加准确。在 FreeRTOS中可以不用加入这两个函数,但是要注意的是,这会让函数
delay_us()的微秒级延时的精度有所下降, 函数 delay_us()修改后的代码如下所示:

//延时nus
//nus:要延时的us数.	
//nus:0~204522252(最大值即2^32/fac_us@fac_us=168)	    								   
void delay_us(u32 nus)
{		
	u32 ticks;
	u32 told,tnow,tcnt=0;
	u32 reload=SysTick->LOAD;				//LOAD的值
    /* 删除适用于μC/OS用于锁定任务调度器的自定义函数 */	    	 
	ticks=nus*fac_us; 						//需要的节拍数 
 	told=SysTick->VAL;        				//刚进入时的计数器值
	while(1)
	{
		tnow=SysTick->VAL;	
		if(tnow!=told)
		{	    
			if(tnow<told)tcnt+=told-tnow;	//这里注意一下SYSTICK是一个递减的计数器就可以了.
			else tcnt+=reload-tnow+told;	    
			told=tnow;
			if(tcnt>=ticks)break;			//时间超过/等于要延迟的时间,则退出.
		}  
	};										    
} 

 (d) delay_ms()函数
delay_ms()用于毫秒级的 CPU忙延时,原本的函数 delay_ms()会判断 μC/OS是否运
行,如果 μC/OS正在运行的话,就使用 μC/OS的 OS延时进行毫秒级的延时,否则就调用函数
delay_us()进行毫秒级的 CPU忙延时。在 FreeRTOS中,可以将函数 delay_ms()定义为只进行
CPU忙延时,当需要 OS延时的时候,调用 FreeRTOS提供的 OS延时函数 vTaskDelay()(在下
文讲解 FreeRTOS时间管理的时候会对此函数进行分析)进行系统节拍级延时,函数 delay_ms()修改后的代码如下所示:

//延时nms
//nms:要延时的ms数
//nms:0~65535
void delay_ms(u32 nms)
{	
	if(xTaskGetSchedulerState()!=taskSCHEDULER_NOT_STARTED)//系统已经运行
	{		
		if(nms>=fac_ms)						//延时的时间大于OS的最少时间周期 
		{ 
   			vTaskDelay(nms/fac_ms);	 		//FreeRTOS延时
		}
		nms%=fac_ms;						//OS已经无法提供这么小的延时了,采用普通方式延时    
	}
	delay_us((u32)(nms*1000));				//普通方式延时
}

 (e) 包含头文件  根据上述步骤的修改,delay.c文件中使用到了 FreeRTOS的相关函数,因此就需要在 delay.c文件中包含 FreeRTOS的相关头文件,并且移除掉原本存在的 μC/OS相关头文件。先看一下修改前 delay.c文件中包含的 μC/OS相关的头文件:

 至此,SYSTEM文件夹针对 FreeRTOS的修改就完成了。

2.3.4 修改中断相应文件

在FreeRTOS的移植过程中会这几到三个重要的中断,分别是 FreeRTOS系统时基定时器的中断( SysTick中断)、 SVC中断、 PendSV中断( SVC中断和 PendSV中断在下文讲解 FreeRTOS中断和 FreeRTOS任务切换的时候会具体分析),这三个中断的中断服务函数在 HAL库提供的文件中都有定义。

其中,SysTick的中断服务函数在 delay.c文件中已经定义了,并且 FreeRTOS也提供了 SVC和 PendSV的中断服务函数,因此需要将 提供的这三个中断服务函数注释掉,修改后的代码如下所示:

 最后,也是移植FreeRTOS要修改的最后一个地方 FreeRTOSConfig.h文件中有如下定义,改成如下

​​​​​​​

三、系统配置文件说明(熟悉)

3.1 系统配置文件详解

FreeRTOSConfig.h配置文件的作用:对FreeRTOS进行功能配置和裁剪,以及API函数的使能。

配置:FreeRTOS的调度器算法有三种:抢占式,协作式,时间片,也可以通过FreeRTOSConfig.h来配置。

裁剪:很多不用的功能我们便可以将其裁剪掉,FreeRTOSConfig.h的宏定义便可实现这个功能。

相关宏大致可分为三类:

  • “INCLUDE”:配置FreeRTOS中可选的API函数,通过控制这类宏还选择使能还是失能。使用“ INCLUDE”配置项对部分 API函数进行条件编译,当“ INCLUDE”配置项被定义为 1时,其对应的 API函数则会加入编译。对于用不到的 API函数,用户则可以将其对应的“ INCLUDE”配置项设置为 0,那么这个 API函数就不会加入编译,以减少不必要的系统开销。“
  • “config”:完成FreeRTOS的功能配置和裁剪,“config”配置项按照配置的 功能分类,可分为 十类,分别为基础配置项、内存分配相关定义、钩子函数相关定义、运行时间和任务状态统计相关定义、协 程相关定义、软件定时器相关定义、中断嵌套行为配置、断言、 FreeRTOS MPU特殊定义和 ARMv8-M 安全侧端口相关定义。
  • 其他配置项:PendSV宏定义、SVC宏定义,这两个宏为PendSV和 SVC的中断服务函数,主要用于 FreeRTOS操作系统的任务切换,有关 FreeRTOS操作系统中任务切换的相关内容。

具体如下:

/* 基础配置项 */
#define configUSE_PREEMPTION                            1                       /* 1: 抢占式调度器, 0: 协程式调度器, 无默认需定义 */
#define configUSE_PORT_OPTIMISED_TASK_SELECTION         1                       /* 1: 使用硬件计算下一个要运行的任务, 0: 使用软件算法计算下一个要运行的任务, 默认: 0 */
#define configUSE_TICKLESS_IDLE                         0                       /* 1: 使能tickless低功耗模式, 默认: 0 */
#define configCPU_CLOCK_HZ                              SystemCoreClock         /* 定义CPU主频, 单位: Hz, 无默认需定义 */
//#define configSYSTICK_CLOCK_HZ                          (configCPU_CLOCK_HZ / 8)/* 定义SysTick时钟频率,当SysTick时钟频率与内核时钟频率不同时才可以定义, 单位: Hz, 默认: 不定义 */
#define configTICK_RATE_HZ                              1000                    /* 定义系统时钟节拍频率, 单位: Hz, 无默认需定义 */
#define configMAX_PRIORITIES                            32                      /* 定义最大优先级数, 最大优先级=configMAX_PRIORITIES-1, 无默认需定义 */
#define configMINIMAL_STACK_SIZE                        128                     /* 定义空闲任务的栈空间大小, 单位: Word, 无默认需定义 */
#define configMAX_TASK_NAME_LEN                         16                      /* 定义任务名最大字符数, 默认: 16 */
#define configUSE_16_BIT_TICKS                          0                       /* 1: 定义系统时钟节拍计数器的数据类型为16位无符号数, 无默认需定义 */
#define configIDLE_SHOULD_YIELD                         1                       /* 1: 使能在抢占式调度下,同优先级的任务能抢占空闲任务, 默认: 1 */
#define configUSE_TASK_NOTIFICATIONS                    1                       /* 1: 使能任务间直接的消息传递,包括信号量、事件标志组和消息邮箱, 默认: 1 */
#define configTASK_NOTIFICATION_ARRAY_ENTRIES           1                       /* 定义任务通知数组的大小, 默认: 1 */
#define configUSE_MUTEXES                               1                       /* 1: 使能互斥信号量, 默认: 0 */
#define configUSE_RECURSIVE_MUTEXES                     1                       /* 1: 使能递归互斥信号量, 默认: 0 */
#define configUSE_COUNTING_SEMAPHORES                   1                       /* 1: 使能计数信号量, 默认: 0 */
#define configUSE_ALTERNATIVE_API                       0                       /* 已弃用!!! */
#define configQUEUE_REGISTRY_SIZE                       8                       /* 定义可以注册的信号量和消息队列的个数, 默认: 0 */
#define configUSE_QUEUE_SETS                            1                       /* 1: 使能队列集, 默认: 0 */
#define configUSE_TIME_SLICING                          1                       /* 1: 使能时间片调度, 默认: 1 */
#define configUSE_NEWLIB_REENTRANT                      0                       /* 1: 任务创建时分配Newlib的重入结构体, 默认: 0 */
#define configENABLE_BACKWARD_COMPATIBILITY             0                       /* 1: 使能兼容老版本, 默认: 1 */
#define configNUM_THREAD_LOCAL_STORAGE_POINTERS         0                       /* 定义线程本地存储指针的个数, 默认: 0 */
#define configSTACK_DEPTH_TYPE                          uint16_t                /* 定义任务堆栈深度的数据类型, 默认: uint16_t */
#define configMESSAGE_BUFFER_LENGTH_TYPE                size_t                  /* 定义消息缓冲区中消息长度的数据类型, 默认: size_t */

/* 内存分配相关定义 */
#define configSUPPORT_STATIC_ALLOCATION                 0                       /* 1: 支持静态申请内存, 默认: 0 */
#define configSUPPORT_DYNAMIC_ALLOCATION                1                       /* 1: 支持动态申请内存, 默认: 1 */
#define configTOTAL_HEAP_SIZE                           ((size_t)(10 * 1024))   /* FreeRTOS堆中可用的RAM总量, 单位: Byte, 无默认需定义 */
#define configAPPLICATION_ALLOCATED_HEAP                0                       /* 1: 用户手动分配FreeRTOS内存堆(ucHeap), 默认: 0 */
#define configSTACK_ALLOCATION_FROM_SEPARATE_HEAP       0                       /* 1: 用户自行实现任务创建时使用的内存申请与释放函数, 默认: 0 */

/* 钩子函数相关定义 */
#define configUSE_IDLE_HOOK                             0                       /* 1: 使能空闲任务钩子函数, 无默认需定义  */
#define configUSE_TICK_HOOK                             0                       /* 1: 使能系统时钟节拍中断钩子函数, 无默认需定义 */
#define configCHECK_FOR_STACK_OVERFLOW                  0                       /* 1: 使能栈溢出检测方法1, 2: 使能栈溢出检测方法2, 默认: 0 */
#define configUSE_MALLOC_FAILED_HOOK                    0                       /* 1: 使能动态内存申请失败钩子函数, 默认: 0 */
#define configUSE_DAEMON_TASK_STARTUP_HOOK              0                       /* 1: 使能定时器服务任务首次执行前的钩子函数, 默认: 0 */

/* 运行时间和任务状态统计相关定义 */
#define configGENERATE_RUN_TIME_STATS                   0                       /* 1: 使能任务运行时间统计功能, 默认: 0 */
#if configGENERATE_RUN_TIME_STATS
#include "./BSP/TIMER/btim.h"
#define portCONFIGURE_TIMER_FOR_RUN_TIME_STATS()        ConfigureTimeForRunTimeStats()
extern uint32_t FreeRTOSRunTimeTicks;
#define portGET_RUN_TIME_COUNTER_VALUE()                FreeRTOSRunTimeTicks
#endif
#define configUSE_TRACE_FACILITY                        1                       /* 1: 使能可视化跟踪调试, 默认: 0 */
#define configUSE_STATS_FORMATTING_FUNCTIONS            1                       /* 1: configUSE_TRACE_FACILITY为1时,会编译vTaskList()和vTaskGetRunTimeStats()函数, 默认: 0 */

/* 协程相关定义 */
#define configUSE_CO_ROUTINES                           0                       /* 1: 启用协程, 默认: 0 */
#define configMAX_CO_ROUTINE_PRIORITIES                 2                       /* 定义协程的最大优先级, 最大优先级=configMAX_CO_ROUTINE_PRIORITIES-1, 无默认configUSE_CO_ROUTINES为1时需定义 */

/* 软件定时器相关定义 */
#define configUSE_TIMERS                                1                               /* 1: 使能软件定时器, 默认: 0 */
#define configTIMER_TASK_PRIORITY                       ( configMAX_PRIORITIES - 1 )    /* 定义软件定时器任务的优先级, 无默认configUSE_TIMERS为1时需定义 */
#define configTIMER_QUEUE_LENGTH                        5                               /* 定义软件定时器命令队列的长度, 无默认configUSE_TIMERS为1时需定义 */
#define configTIMER_TASK_STACK_DEPTH                    ( configMINIMAL_STACK_SIZE * 2) /* 定义软件定时器任务的栈空间大小, 无默认configUSE_TIMERS为1时需定义 */

/* 可选函数, 1: 使能 */
#define INCLUDE_vTaskPrioritySet                        1                       /* 设置任务优先级 */
#define INCLUDE_uxTaskPriorityGet                       1                       /* 获取任务优先级 */
#define INCLUDE_vTaskDelete                             1                       /* 删除任务 */
#define INCLUDE_vTaskSuspend                            1                       /* 挂起任务 */
#define INCLUDE_xResumeFromISR                          1                       /* 恢复在中断中挂起的任务 */
#define INCLUDE_vTaskDelayUntil                         1                       /* 任务绝对延时 */
#define INCLUDE_vTaskDelay                              1                       /* 任务延时 */
#define INCLUDE_xTaskGetSchedulerState                  1                       /* 获取任务调度器状态 */
#define INCLUDE_xTaskGetCurrentTaskHandle               1                       /* 获取当前任务的任务句柄 */
#define INCLUDE_uxTaskGetStackHighWaterMark             1                       /* 获取任务堆栈历史剩余最小值 */
#define INCLUDE_xTaskGetIdleTaskHandle                  1                       /* 获取空闲任务的任务句柄 */
#define INCLUDE_eTaskGetState                           1                       /* 获取任务状态 */
#define INCLUDE_xEventGroupSetBitFromISR                1                       /* 在中断中设置事件标志位 */
#define INCLUDE_xTimerPendFunctionCall                  1                       /* 将函数的执行挂到定时器服务任务 */
#define INCLUDE_xTaskAbortDelay                         1                       /* 中断任务延时 */
#define INCLUDE_xTaskGetHandle                          1                       /* 通过任务名获取任务句柄 */
#define INCLUDE_xTaskResumeFromISR                      1                       /* 恢复在中断中挂起的任务 */

/* 中断嵌套行为配置 */
#ifdef __NVIC_PRIO_BITS
    #define configPRIO_BITS __NVIC_PRIO_BITS
#else
    #define configPRIO_BITS 4
#endif

#define configLIBRARY_LOWEST_INTERRUPT_PRIORITY         15                  /* 中断最低优先级 */
#define configLIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY    5                   /* FreeRTOS可管理的最高中断优先级 */
#define configKERNEL_INTERRUPT_PRIORITY                 ( configLIBRARY_LOWEST_INTERRUPT_PRIORITY << (8 - configPRIO_BITS) )
#define configMAX_SYSCALL_INTERRUPT_PRIORITY            ( configLIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY << (8 - configPRIO_BITS) )
#define configMAX_API_CALL_INTERRUPT_PRIORITY           configMAX_SYSCALL_INTERRUPT_PRIORITY

/* FreeRTOS中断服务函数相关定义 */
#define xPortPendSVHandler                              PendSV_Handler
#define vPortSVCHandler                                 SVC_Handler

四、课堂总结

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

I am Supreme

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值