ucos II任务管理之二:恢复任务
一个任务被挂起之后,想要再次被执行,是需要恢复的,恢复任务需要调用
OSTaskResume()函数实现。想OSTaskSuspend()一样,调用OSTaskResume()只需一个参数,就是优先级。如OSTaskResume(5)就是恢复优先级为5的任务。
INT8U OSTaskResume (INT8U prio) |
{ |
OS_TCB *ptcb; |
|
|
If (prio >= OS_LOWEST_PRIO) { (1) |
return (OS_PRIO_INVALID); |
} |
OS_ENTER_CRITICAL(); |
If ((ptcb = OSTCBPrioTbl[prio]) == (OS_TCB *)0) { (2) |
OS_EXIT_CRITICAL(); |
return (OS_TASK_RESUME_PRIO); |
} else { |
if (ptcb->OSTCBStat & OS_STAT_SUSPEND) { (3) |
if (((ptcb->OSTCBStat &= ~OS_STAT_SUSPEND) == OS_STAT_RDY) && (4) |
(ptcb->OSTCBDly == 0)) { (5) |
OSRdyGrp |= ptcb->OSTCBBitY; (6) |
OSRdyTbl[ptcb->OSTCBY] |= ptcb->OSTCBBitX; |
OS_EXIT_CRITICAL(); |
OSSched(); (7) |
} else { |
OS_EXIT_CRITICAL(); |
} |
return (OS_NO_ERR); |
} else { |
OS_EXIT_CRITICAL(); |
return (OS_TASK_NOT_SUSPENDED); |
} |
} |
} |
任务恢复的实现基本上任务挂起的反向操作。
因为OSTaskSuspend()不能挂起空闲任务,所以必须得确认用户的应用程序不是在恢复空闲任务[ (1)]。注意,这个测试也可以确保用户不是在恢复优先级为OS_PRIO_SELF的任务(OS_PRIO_SELF被定义为0xFF,它总是比OS_LOWEST_PRIO大)。
要恢复的任务必须是存在的,因为用户要需要操作它的任务控制块OS_TCB[ (2)],并且该任务必须是被挂起的[(3)]。OSTaskResume()是通过清除OSTCBStat域中的OS_STAT_SUSPEND位来取消挂起的[ (4)]。要使任务处于就绪状态,OS_TCBDly域必须为0[(5)],这是因为在OSTCBStat中没有任何标志表明任务正在等待延时的期满。只有当以上两个条件都满足的时候,任务才处于就绪状态[ (6)]。最后,任务调度程序会检查被恢复的任务拥有的优先级是否比调用本函数的任务的优先级高[ (7)]。
其中最重要的是这两句程序:
OSRdyGrp |= ptcb->OSTCBBitY;
OSRdyTbl[ptcb->OSTCBY] |= ptcb->OSTCBBitX;
程序的作用就是把任务重新添加进就绪表。