目录
前言
临界段代码也叫做临界区,是指那些必须完整运行,不能被打断的代码段。比如有的外设的初始化IIC、SPI等等,需要严格的时序,初始化过程中不能被打断。
一、临界区相关函数
FreeRTOS
与 临 界 段 代 码 保 护 有 关 的 函 数 有
4
个 :
taskENTER_CRITICAL() //任务中进入临界区
taskEXIT_CRITICAL() //任务中退出临界区
taskENTER_CRITICAL_FROM_ISR() //中断中进入临界区
taskEXIT_CRITICAL_FROM_ISR() //中断中退出临界区
这四个函数其实是宏定义,在
task.h
文件中有定义。这四个函数的区别
是
前两个是任务级的临界段代码保护
,后两个是
中断级的临界段代码保护
。
二、使用
任务中使用临界区:
FreeRTOS 在进入临界段代码的时候需要关闭中断,当处理完临界段代码以后再打开中断。
进入然后退出临界段是“
资源同步
”的方法之一,能够在访问共享资源时保障信息的可靠性和完整性。
进入和退出临界区的函数要配套使用。
简单测试:
创建两个任务:
任务1:
对全局变量
sum1
和
sum2
操作。低优先级任
务让这两个变量始终相等,并不断在计数;
任务2:
高优先级任务不断的判断这两个变量是否相等,不相等则点亮
LED
相关代码:
void led0_task(void *pvParameters)
{
while(1)
{
taskENTER_CRITICAL();//进入临界区
if(sum1 != sum2)
LED0 = ~LED0;
taskEXIT_CRITICAL();//退出临界区
vTaskDelay(500);
}
}
//LED1任务函数
void led1_task(void *pvParameters)
{
while(1)
{
taskENTER_CRITICAL();//进入临界区
sum1++;
delay_xms(500);
sum2++;
taskEXIT_CRITICAL();//退出临界区
}
}
结果是两个任务都在执行的前后增加了进入和退出临界区,保证了每个任务的代码完整执行,所以sum1永远等于sum2,LED0不闪烁。