uc/os-ii任務調度的鎖定與解鎖

調度器上鎖函數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回零爲止。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章