优先级反转
定义:高优先级任务需要等待低优先级任务释放资源,而低优先级任务又正在等待中等优先级任务的现象叫做优先级反转。 此时高优先级任务和中等优先级任务之间没有任何共享资源但执行顺序却发生了倒置,这种情况称为优先级反转,而高优先级任务因为等待低优先级任务释放资源而阻塞的情况则不称为优先级反转.
两种经典的防止反转的方法:
优先级继承策略(Priority inheritance):继承现有被阻塞任务的最高优先级作为其优先级,任务退出临界区,恢复初始优先级。 在上述例子中体现为当高优先级任务需要等待低优先级任务释放资源而阻塞时,就将低优先级任务的优先级升为高优先级任务的优先级,当它退出临界区后就将其优先级恢复为初始优先级
优先级天花板策略(Priority ceilings): 优先级天花板是指将申请(占有)某资源的任务的优先级提升到可能访问该资源的所有任务中最高优先级任务的优先级.(这个优先级称为该资源的优先级天花板) 。在上述例子中体现为当低优先级任务申请占有某资源时就将这个低优先级任务的优先级升为能访问该资源的所有任务中最高优先级任务的优先级。
优先级继承策略对任务执行流程的影响相对较小,因为只有当高优先级任务申请已被低优先级任务占有的临界资源这一事实发生时,才抬升低优先级任务的优先级。而天花板策略是谁占有就直接升到最高。
本文采用的嵌入式微处理器为SAMSUNG公司的S3C2510,CPU核为arm940T。应项目要求任务task1和task2中分别进行调用微秒级和毫秒级的定时器功能函数,由于S3C2510处理器有5个32位定时器,因此只利用其中的两个即可。这里,ms级定时器实现的代码架构如下: 1) 中断处理函数: LOCAL void Timer1_Int_Handle(void) { *S3C2510_TIC |= S3C2510_TIC_T1;/*清除中断*/ ... semGive(TelID4_Stop);/*释放二进制信号量*/ ... } | 2) 毫秒级定时函数 void ms_Delay(int ms) { ... semTake(TelID4_Stop,WAIT_FOREVER); ... } | 3) 时钟初始化函数 void msTimer_Init() { TelID4_Stop=semCreate (SEM_Q_FIFO,SEM_EMPTY);/*初始化二进制信号量*/ assert(TelID4_Stop); ... } | us级定时器功能实现的代码与上面类似,这里不再给出相应的代码。函数调用说明:先进行初始化,然后任务可随意调用定时功能函数。当某个任务调用定时功能函数时,该任务被信号量阻塞,同时定时器开始进行减一计数,当计数器减到0时,会产生一个中断请求信号,此时系统会调用中断处理函数,在中断处理函数时将信号量释放,此时信号量变的可用,任务继续执行。 当两个不同优先级任务task1,task2(设优先级分别为93和94)同时运行,并分别调用us和ms级定时功能函数时,优先级反转出现了,task1会被长时间阻塞。其中,task1和task2的调用如下: |