調度器上鎖函數OSSchedlock()
的功能是用於禁止任務調度,使任務保持對CPU的控制權。調度器開鎖函數OSSchedUnlock()
的功能是解除對任務調度的禁止。
調度器上鎖和開鎖的實現原理是:對全局變量鎖定嵌套計數器OSLockNesting
進行操作,OSLockNesting
跟蹤OS SchedLock()
函數被調用的次數,允許嵌套深度達255層。調度器上鎖即對變量OSLockNesting
進行加1操作,開鎖即對變量OSLockNesting
進行減1操作。
- 調度器鎖定函數
OSSchedLock()
void OSSchedLock (void)
{
#if OS_CRITICAL_METHOD == 3 /* Allocate storage for CPU status register */
OS_CPU_SR cpu_sr = 0;
#endif
if (OSRunning == OS_TRUE) { /* Make sure multitasking is running */
OS_ENTER_CRITICAL();
if (OSIntNesting == 0) { /* Can't call from an ISR */
if (OSLockNesting < 255u) { /* Prevent OSLockNesting from wrapping back to 0 */
OSLockNesting++; /* Increment lock nesting level */
}
}
OS_EXIT_CRITICAL();
}
}
- 調度器解鎖函數
OSSchedUnlock()
由於OSSchedUnlock()
函數是被某任務調用的,在調度器上鎖期間,可能會有事件發生並使一個更高優先級的任務進入就緒態,因此當OSLockNesting
減到零時,OSSchedUnlock()
必須調用OSSched()
函數,但是這種調用還必須滿足另一個前提,也就是調用者不是中斷服務子程序。
void OSSchedUnlock (void)
{
#if OS_CRITICAL_METHOD == 3 /* Allocate storage for CPU status register */
OS_CPU_SR cpu_sr = 0;
#endif
if (OSRunning == OS_TRUE) { /* Make sure multitasking is running */
OS_ENTER_CRITICAL();
if (OSLockNesting > 0) { /* Do not decrement if already 0 */
OSLockNesting--; /* Decrement lock nesting level */
if (OSLockNesting == 0) { /* See if scheduler is enabled and ... */
if (OSIntNesting == 0) { /* ... not in an ISR */
OS_EXIT_CRITICAL();
OS_Sched(); /* See if a HPT is ready */
} else {
OS_EXIT_CRITICAL();
}
} else {
OS_EXIT_CRITICAL();
}
} else {
OS_EXIT_CRITICAL();
}
}
}
最後一點注意,OSSchedLock()
和 OSSchedUnlock()
必須成對調用。上鎖後必須要記住解鎖。使用時務必非常謹慎,因爲它們影響μC/OS-Ⅱ對任務的正常管理。
當一個任務調用OSSchedLock()
以後,應用程序不得使用任何系統調用將該任務掛起。因爲調度器一旦上鎖,系統就被鎖住,其它任何任務都不能運行。這些系統調用包括OSTaskSuspend(OS_PRIO_SELF)
、OSMboxPend()
、OSQPend()
、OSSemPend()
、OSTimeDly()
和OSTimeDly HMSM()
等,直到OSLockNesting
回零爲止。