Ch4嵌入式實(shí)時操作系統(tǒng)_第1頁
Ch4嵌入式實(shí)時操作系統(tǒng)_第2頁
Ch4嵌入式實(shí)時操作系統(tǒng)_第3頁
Ch4嵌入式實(shí)時操作系統(tǒng)_第4頁
Ch4嵌入式實(shí)時操作系統(tǒng)_第5頁
已閱讀5頁,還剩71頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報或認(rèn)領(lǐng)

文檔簡介

第四章

μC/OS-Ⅱ內(nèi)核結(jié)構(gòu)與運(yùn)行流程本章要點(diǎn)μC/OS-Ⅱ內(nèi)核結(jié)構(gòu)及可裁剪性μC/OS-Ⅱ任務(wù)管理及表管理μC/OS-Ⅱ就緒表管理及算法分析μC/OS-Ⅱ任務(wù)調(diào)度及實(shí)現(xiàn)、任務(wù)調(diào)度的打開和關(guān)閉μC/OS-Ⅱ空閑任務(wù)及實(shí)現(xiàn)μC/OS-Ⅱ統(tǒng)計任務(wù)及實(shí)現(xiàn)μC/OS-Ⅱ任務(wù)的初始化μC/OS-Ⅱ中斷處理μC/OS-Ⅱ時鐘節(jié)拍μC/OS-Ⅱ內(nèi)核的核心模塊core.c1.操作系統(tǒng)服務(wù)嵌入式實(shí)時操作系統(tǒng)基本性質(zhì)RTOS是一種能夠響應(yīng)時間約束控制以及事件控制過程的操作系統(tǒng),這個控制過程具有預(yù)先設(shè)置的時限要求。RTOS是一種對任務(wù)、中斷服務(wù)子程序有實(shí)時限制和截止時間要求的操作系統(tǒng)。實(shí)時操作系統(tǒng)軟件提供的服務(wù)

任務(wù)管理、任務(wù)優(yōu)先級、任務(wù)調(diào)度及算法、優(yōu)先級繼承系統(tǒng)預(yù)計時間屬性:任務(wù)抖動即時限值最好情況和最壞情況的時間差。內(nèi)存管理:應(yīng)用程序任務(wù)能夠在內(nèi)核空間運(yùn)行,訪問內(nèi)核代碼、堆棧、數(shù)據(jù)的內(nèi)存空間,將導(dǎo)致內(nèi)核代碼不可防護(hù)。采用定長內(nèi)存塊分配的內(nèi)存分配方法,分配速度快。時鐘管理:提供計時函數(shù),完成時間分配和重置,以確保給定計時時限的有效性。任務(wù)同步機(jī)制:信號量、郵箱、消息隊(duì)列等。2.基于RTOS嵌入式系統(tǒng)基本設(shè)計基本機(jī)制RTOS提供在內(nèi)核空間運(yùn)行用戶線程的機(jī)制;RTOS提供中斷、驅(qū)動、IST、任務(wù)或線程的處理;RTOS提供內(nèi)存分配和釋放函數(shù);RTOS提供對零到多個任務(wù)的調(diào)度、運(yùn)行和阻塞操作;RTOS提供簡單操作,如I/O、文件、管道第等;RTOS提供對于CPU的多個狀態(tài)、內(nèi)部和外部設(shè)備的有效管理。RTOS支持下的嵌入式系統(tǒng)基本設(shè)計原則中斷處理子程序ISR和任務(wù)的設(shè)計原則中斷服務(wù)線程或任務(wù)的設(shè)計原則任務(wù)設(shè)計原則模塊化設(shè)計原則堅(jiān)持?jǐn)?shù)據(jù)封裝任務(wù)設(shè)計原則減少系統(tǒng)調(diào)用話費(fèi)時間設(shè)計原則優(yōu)先級設(shè)置策略和搶占式調(diào)度策略避免刪除任務(wù)設(shè)計原則利用空閑的CPU時間執(zhí)行系統(tǒng)內(nèi)部函數(shù)任務(wù)內(nèi)完成內(nèi)存分配和回收的設(shè)計原則謹(jǐn)慎使用任務(wù)間共享資源和數(shù)據(jù)層次和限定范圍優(yōu)先級搶占調(diào)度任務(wù)的運(yùn)行規(guī)律假設(shè)一個編碼消息流到達(dá)一個嵌入式系統(tǒng)端口A,對每個消息進(jìn)行解碼,并傳送到端口B。應(yīng)用程序功能設(shè)計為5個任務(wù)運(yùn)行,優(yōu)先級大到?。喝蝿?wù)B1:檢測端口A是否有消息任務(wù)B2:讀出端口A的消息任務(wù)B3:消息解碼任務(wù)B4:消息編碼任務(wù)B5:傳送編碼消息到端口B任務(wù)B1等待來自端口A的中斷任務(wù)B2讀出來自端口A的消息任務(wù)B3解碼來自端口A的消息隊(duì)列消息任務(wù)B4對消息再次編碼任務(wù)B5向端口B寫入編碼消息運(yùn)行上下文任務(wù)B1任務(wù)ISRB2任務(wù)B3任務(wù)B4任務(wù)B5保存上下文B3RunningB1RunningBlockedB3B2FinishRunningBlockedB3B3FinishFinishRunningB4FinishFinishFinishRunningB5FinishFinishFinishFinishRunningB1RunningBlockedB5B2FinishRunningBlockedB5B3FinishFinishRunningBlockedB5程序運(yùn)行過程中各任務(wù)執(zhí)行情況及上下文切換

操作系統(tǒng)μC/OS-II的內(nèi)核模塊結(jié)構(gòu)核心雜項(xiàng)功能管理:os_core.c標(biāo)志功能管理:os_flag.c消息郵箱管理:os_mbox.c內(nèi)存塊管理:os_mem.c互斥信號量管理:os_mutex消息隊(duì)列管理:os_q.c計數(shù)信號量管理:os_sem.c任務(wù)管理:os_task.c時鐘管理:os_time.c基于內(nèi)核的應(yīng)用軟件編程當(dāng)用戶基于μC/OS-II內(nèi)核,進(jìn)行應(yīng)用程序設(shè)計實(shí)現(xiàn)時,用戶應(yīng)用代碼可以通過調(diào)用內(nèi)核函數(shù),并完成編譯、鏈接等操作,用以形成可執(zhí)行程序代碼,實(shí)現(xiàn)具有實(shí)時特性的軟件。3.uC/OS-II基本模塊功能OSInit()OSIntEnter()OSIntExit()OSSchedLock()OSSchedUnlock()OSStart()OSStartInit()OSVersion()OSTimeTick()3.uC/OS-II基本模塊功能OS_Dummy()OS_EventTaskRdy()OS_EventTaskWait()OS_EventTO()OS_EventWaitListInit()OS_InitEventList()OS_InitMisc()OS_InitRdyList()OS_InitTaskIdle()OS_EventTO()3.uC/OS-II基本模塊功能OS_InitTaskStat()OS_InitTCBList()OS_Sched()OS_TaskIdle()OS_TaskStat()OS_TCBInit()OS_EventTO()核心雜項(xiàng)功能管理——os_core.c系統(tǒng)初始化函數(shù):voidOSInit(void)OSinit()負(fù)責(zé)對μC/OS-Ⅱ操作系統(tǒng)進(jìn)行初始化工作,完成雜項(xiàng)數(shù)據(jù)、任務(wù)就緒隊(duì)列、空閑任務(wù)控制塊、空閑事件控制塊等數(shù)據(jù)結(jié)構(gòu)的初始化工作。該函數(shù)功能為初始化核心數(shù)據(jù),調(diào)用這個函數(shù)必須在調(diào)用OSStart()函數(shù)之前,OSStart()函數(shù)用于開始多任務(wù)應(yīng)用系統(tǒng)運(yùn)行,必須在創(chuàng)建所有μC/OS-Ⅱ任務(wù)之后調(diào)用。中斷進(jìn)入函數(shù)voidOSIntEnter(void)本函數(shù)告知μC/OS-Ⅱ內(nèi)核,要開始執(zhí)行一個中斷處理子程序段,在該段程序執(zhí)行期間,不能響應(yīng)任何中斷,程序員需要確保中斷處理子程序的正確性、穩(wěn)定性,以免程序癱瘓。μC/OS-Ⅱ可據(jù)此記錄、跟蹤中斷嵌套的層數(shù),確保只對最外層的中斷處理子程序做出響應(yīng)。OSIntEnter()函數(shù)和OSIntExit()函數(shù)成對使用,調(diào)用OSIntEnter()函數(shù)表示封中斷開始,調(diào)用OSIntExit()函數(shù)表示封中斷結(jié)束。中斷退出函數(shù)voidOSIntExit(void)該函數(shù)告知μC/OS-Ⅱ內(nèi)核,當(dāng)前正在執(zhí)行的中斷服務(wù)子程序已執(zhí)行完畢,μC/OS-Ⅱ可據(jù)此記錄、跟蹤中斷嵌套的變化。當(dāng)最后一層嵌套的中斷處理子程序執(zhí)行完畢后,也就是本程序可以響應(yīng)中斷的時候,由于實(shí)時內(nèi)核采用可搶占式優(yōu)先級調(diào)度進(jìn)行任務(wù)調(diào)度。如果在執(zhí)行中斷處理子程序期間,有更高優(yōu)先級的任務(wù)進(jìn)入就緒態(tài),μC/OS-Ⅱ會通過任務(wù)調(diào)度函數(shù)的執(zhí)行,令中斷返回到更高優(yōu)先級的任務(wù)。而被中斷執(zhí)行的任務(wù),要等待在就緒任務(wù)中,直到成為優(yōu)先級最高時才能得到執(zhí)行。系統(tǒng)任務(wù)調(diào)度關(guān)閉函數(shù)voidOSSchedLock(void)調(diào)用該函數(shù)允許應(yīng)用程序禁止任務(wù)間的上下文切換,以確保當(dāng)前任務(wù)能夠執(zhí)行,不被高優(yōu)先級的就緒任務(wù)搶奪運(yùn)行權(quán)。系統(tǒng)任務(wù)調(diào)度打開函數(shù)voidOSSchedUnlock(void)。調(diào)用該函數(shù),表示應(yīng)用程序此時解除了任務(wù)調(diào)度關(guān)閉狀態(tài),即允許上下文切換的發(fā)生。啟動多任務(wù)函數(shù)voidOSStart(void)該函數(shù)用于啟動多任務(wù)運(yùn)行過程,令uC/OS-II內(nèi)核管理已經(jīng)創(chuàng)建好的任務(wù)。請注意,調(diào)用該函數(shù)之前,必須調(diào)用OSInit()函數(shù),完成系統(tǒng)數(shù)據(jù)結(jié)構(gòu)的初始化工作,并且,必須至少創(chuàng)建一個應(yīng)用任務(wù)。系統(tǒng)統(tǒng)計數(shù)據(jù)初始化函數(shù)voidOSStatInit(void)應(yīng)用代碼調(diào)用該函數(shù)計算CPU利用率首先確定,在1秒鐘內(nèi),如果沒有其他任務(wù)執(zhí)行的話,一個32位計數(shù)器能夠完成的最大計數(shù)是多少CPU利用率可以由此這樣確定:每秒鐘,令一個低優(yōu)先級任務(wù)跟蹤這個32位計數(shù)器的計數(shù)值,該任務(wù)優(yōu)先級高,可以執(zhí)行。CPU利用率的計算公式如下:CPUUsage(%)=100*(1–OSIdleCtr/OSIdleCtrMax)

OSIdleCtr指在較低優(yōu)先級任務(wù)執(zhí)行過程中,計數(shù)器得到的計數(shù)值

OSIdleCtrMax指在沒被中斷情況下獲取的計數(shù)器的值。表明,實(shí)時內(nèi)核在并發(fā)執(zhí)行實(shí)時任務(wù)時,具有的實(shí)際執(zhí)行率,與單任務(wù)執(zhí)行是不同的。系統(tǒng)版本函數(shù)INT16UOSVersion(void)。該函數(shù)用于返回uC/OS-II的版本號,返回值等于uC/OS-II版本號乘以100,也就是說,版本號2.00的返回值為200。系統(tǒng)時鐘節(jié)拍函數(shù)voidOSTimeTick(void)該函數(shù)用于系統(tǒng)時鐘嘀嗒發(fā)生時,向uC/OS-II內(nèi)核發(fā)送信號。該函數(shù)一般由時鐘嘀嗒中斷處理程序調(diào)用,也可由更高優(yōu)先級任務(wù)調(diào)用。等待事件發(fā)生,任務(wù)就緒函數(shù):INT8UOS_EventTaskRdy(OS_EVENT*pevent,void*msg,INT8Umsk)該函數(shù)由其他uC/OS-II服務(wù)函數(shù)調(diào)用,用于當(dāng)?shù)却录l(fā)生,一個任務(wù)由等待變?yōu)榫途w。掛起等待事件的任務(wù)voidOS_EventTaskWait(OS_EVENT*pevent)

事件到來,任務(wù)就緒voidOS_EventTO(OS_EVENT*pevent)該函數(shù)由其他uC/OS-II服務(wù)函數(shù)調(diào)用,表明時間到時,一個任務(wù)就緒,可以運(yùn)行。初始化事件控制塊隊(duì)列voidOS_EventWaitListInit(OS_EVENT*pevent)該函數(shù)由OSInit()調(diào)用,用于初始化事件控制塊自由隊(duì)列。初始化事件控制塊自由隊(duì)列函數(shù)voidOS_EventWaitListInit(OS_EVENT*pevent)該函數(shù)由OSInit()調(diào)用,用于初始化事件控制塊自由隊(duì)列。staticvoidOS_InitEventList(void)初始化雜項(xiàng)變量函數(shù):staticvoidOS_InitMisc(void)該函數(shù)由OSInit()調(diào)用,用于初始化雜項(xiàng)數(shù)據(jù)變量。初始化就緒隊(duì)列/初始化創(chuàng)建空閑任務(wù)staticvoidOS_InitRdyList(void)該函數(shù)由OSInit()調(diào)用,用于初始化就緒隊(duì)列。staticvoidOS_InitTaskIdle(void)該函數(shù)用于創(chuàng)建空閑任務(wù)。創(chuàng)建統(tǒng)計任務(wù)staticvoidOS_InitTaskStat(void)

調(diào)用參數(shù):無。返回值:無。初始化函數(shù):staticvoidOS_InitTCBList(void)該函數(shù)用于初始化任務(wù)控制塊自由隊(duì)列。由OSInit()函數(shù)調(diào)用,初始化由OS_TCB構(gòu)成的自由隊(duì)列。調(diào)用參數(shù):無。返回值:無。調(diào)度函數(shù):voidOS_Sched(void)調(diào)用該函數(shù),判定是否有一個新的更高優(yōu)先級任務(wù)就緒,等待運(yùn)行。該函數(shù)由任務(wù)級代碼喚醒,不能用于中斷處理子程序中重新調(diào)度任務(wù)。中斷服務(wù)子程序的重新調(diào)度,調(diào)用系統(tǒng)函數(shù)OSIntExit()完成。調(diào)用說明: 1)該函數(shù)屬于uC/OS-II的內(nèi)部函數(shù),應(yīng)用代碼不會調(diào)用。 2)當(dāng)調(diào)度程序被鎖定時,可以防止重新調(diào)度的發(fā)生。參見函數(shù)OS_SchedLock()的使用。閑逛任務(wù)函數(shù)voidOS_TaskIdle(void*pdata) 當(dāng)沒有其它高優(yōu)先級任務(wù)執(zhí)行時執(zhí)行該任務(wù),也許其它任務(wù)都在等待事件的發(fā)生。說明:系統(tǒng)函數(shù)OSTaskIdleHook()在臨界區(qū)執(zhí)行之后被調(diào)用。統(tǒng)計任務(wù)函數(shù)voidOS_TaskStat(void*pdata)用于計算多任務(wù)環(huán)境下的一些統(tǒng)計數(shù)據(jù)。OS_TaskStat()是專門用來計算CPU利用率。

OSCPUUsage=100*(1–OSIdleCtr/OSIdleCtrMax)調(diào)用說明:1)該任務(wù)的優(yōu)先級高于閑逛任務(wù)的優(yōu)先級。該任務(wù)運(yùn)行的優(yōu)先級為OS_IDLE_PRIO-1。2)可以通過設(shè)置配置參數(shù)不運(yùn)行該任務(wù),即定義#defineOS_TASK_STAT_EN為0。3)可以在初始狀態(tài)下,延遲5秒鐘,使系統(tǒng)到達(dá)一個穩(wěn)定的狀態(tài),所有需要的任務(wù)創(chuàng)建完畢,才執(zhí)行統(tǒng)計任務(wù)。初始化任務(wù)控制塊函數(shù)創(chuàng)建任務(wù)時使用函數(shù)原型:INT8UOS_TCBInit(INT8Uprio,OS_STK*ptos,OS_STK*pbos,INT16Uid,INT32Ustk_size,void*pext,INT16Uopt)參考任務(wù)管理函數(shù)OSTaskCreate()和

OSTaskCreateExt()調(diào)用。4.μC/OS-II內(nèi)核結(jié)構(gòu)(1)μC/OS-II內(nèi)核實(shí)現(xiàn)4層架構(gòu)應(yīng)用代碼層:面向用戶應(yīng)用功能的程序設(shè)計代碼,一般是基于內(nèi)核進(jìn)行的應(yīng)用程序設(shè)計源代碼。處理器無關(guān)代碼層&與應(yīng)用代碼相關(guān)代碼層:與處理器無關(guān)的內(nèi)核功能代碼,供應(yīng)用代碼層的源程序調(diào)用,以及面向應(yīng)用代碼的配置文件,對應(yīng)用代碼的參數(shù)等進(jìn)行設(shè)置,也與處理器無關(guān)。與處理器相關(guān)代碼層:內(nèi)核功能只涉及三個文件與處理器相關(guān),將移植的工作量降到最低。當(dāng)嵌入式軟件需要移植到另一個硬件平臺時,需要按照目標(biāo)機(jī)的機(jī)器指令修改該層文件中的功能實(shí)現(xiàn)。硬件層:嵌入式系統(tǒng)的硬件構(gòu)成,包括系統(tǒng)時鐘。這是嵌入式軟件運(yùn)行的平臺。μC/OS-II內(nèi)核的核心功能(OS_CORE.C)可裁減的如果用戶應(yīng)用程序不去調(diào)用該項(xiàng)內(nèi)核功能,這部分功能代碼就不用包含在應(yīng)用軟件中。不可裁減的分別實(shí)現(xiàn)了中斷的關(guān)閉和打開,內(nèi)核初始化,任務(wù)調(diào)度,中斷ISR的入口函數(shù)和出口函數(shù),任務(wù)調(diào)度的關(guān)閉和打開等。不可裁減的內(nèi)核功能μC/OS-II內(nèi)核功能函數(shù)OS_CFG.H中置1表示函數(shù)有效函數(shù)功能OS_ENTER_CRITICAL()必有關(guān)中斷OS_EXIT_CRITICAL()必有開中斷OSInit()必有內(nèi)核初始化OSStart()必有任務(wù)調(diào)度OSIntEnter()必有中斷進(jìn)入OSIntExit()必有中斷退出OSSchedLock()OS_SCHED_LOCK_EN置1任務(wù)調(diào)度加鎖OSSchedUnlock()OS_SCHED_LOCK_EN置0任務(wù)調(diào)度解鎖OSVersion()必有版本(2)任務(wù)任務(wù)函數(shù)的定義形式voidYourTask(void*pdata){for(;;){/*該任務(wù)應(yīng)用代碼*/ 調(diào)用uC/OS-II的某種系統(tǒng)服務(wù),例如:

OSMboxPend();

OSQPend();

OSSemPend();

OSTaskDel(OS_PRIO_SELF);OSTaskSuspend(OS_PRIO_SELF);

OSTimeDly();

OSTimeDlyHMSM(); /*該任務(wù)用戶代碼*/}}任務(wù)的狀態(tài)(3)任務(wù)控制塊(TaskControlBlocks)typedef

struct

os_tcb{

OS_STK*OSTCBStkPtr;#ifOS_TASK_CREATE_EXT_EN/*如果使用擴(kuò)展任務(wù)創(chuàng)建*/

Void*OSTCBExtPtr;

OS_STK*OSTCBStkBottom;

INT32UOSTCBStkSize;

INT16UOSTCBOpt;

INT16UOSTCBId;#endif

struct

os_tcb*OSTCBNext;

struct

os_tcb*OSTCBPrev;#if(OS_Q_EN&&(OS_MAX_QS>=2))||OS_MBOX_EN||OS_SEM_EN/*如果使用事件*/

OS_EVENT*OSTCBEventPtr;#endif#if(OS_Q_EN&&(OS_MAX_QS>=2))||OS_MBOX_EN/*如果使用消息*/

Void*OSTCBMsg;#endif

INT16UOSTCBDly;

INT8UOSTCBStat;

INT8UOSTCBPrio;

INT8UOSTCBX;

INT8UOSTCBY;

INT8UOSTCBBitX;

INT8UOSTCBBitY;#ifOS_TASK_DEL_EN/*如果允許刪除任務(wù)*/

BOOLEANOSTCBDelReq;#endif}OS_TCB;空閑任務(wù)表μC/OS-Ⅱ初始化時,所有任務(wù)控制塊OS_TCBs被鏈接成一個單向空閑任務(wù)表。任務(wù)建立時——空閑任務(wù)控制塊指針OSTCBFreeList指向的任務(wù)控制塊,便分配給該任務(wù),OSTCBFreeList的值調(diào)整為指向下鏈表中下一個空閑的任務(wù)控制塊。任務(wù)刪除時——任務(wù)控制塊就鏈入空閑任務(wù)表尾。(4)任務(wù)就緒表及其操作實(shí)現(xiàn)根據(jù)就緒表確定最高優(yōu)先級任務(wù)進(jìn)入運(yùn)行態(tài)新就緒任務(wù)存入就緒表算法基礎(chǔ):就緒表的結(jié)構(gòu)優(yōu)先數(shù)分解為高三位和低三位,分別確定優(yōu)先級高優(yōu)先數(shù)小

根據(jù)優(yōu)先級找到任務(wù)在就緒任務(wù)表中的位置就緒任務(wù)放入任務(wù)就緒表,就緒表用兩個變量表示:OSRdyGrp、OSRdyTbl[]OSRdyGrp1207654300XXXYYY任務(wù)優(yōu)先級2017654310891514131211181617232221201926242531302928273432333938373635424041474645444350484955545352515856576362616059[0][1][2][3][4][5][6][7]OSRdyTbl[8]XY優(yōu)先級最低任務(wù)(空閑任務(wù))優(yōu)先級最高任務(wù)任務(wù)優(yōu)先級號00001100001010011221為了找到就緒態(tài)優(yōu)先級最高的任務(wù),不需要從OSRdyTbl[0]開始掃描整個就緒任務(wù)表的各個元素值,算法設(shè)計查表,即優(yōu)先級判定表OSUnMapTbl[],見文件OS_CORE.C中關(guān)于該數(shù)組表定義:INT8UconstOSUnMapTbl[]={0,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0, /*0x00to0x0F*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x10to0x1F*/5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x20to0x2F*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x30to0x3F*/6,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x40to0x4F*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x50to0x5F*/5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x60to0x6F*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x70to0x7F*/7,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x80to0x8F*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0x90to0x9F*/5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0xA0to0xAF*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0xB0to0xBF*/6,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0xC0to0xCF*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0xD0to0xDF*/5,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0,/*0xE0to0xEF*/4,0,1,0,2,0,1,0,3,0,1,0,2,0,1,0/*0xF0to0xFF*/};1)采用查表法確定高優(yōu)先級任務(wù)查表法具有確定時間,增加系統(tǒng)可預(yù)測性,C/OS–II所有系統(tǒng)調(diào)用時間確定。High3=OSUnMapTbl[OSRdyGrp];Low3=OSUnMapTbl[OSRdyTbl[High3]];Prio=(High3<<3)+Low3;OSRdyGrp0110100000XXXYYY任務(wù)優(yōu)先級0000010000000010100001000000000000000000000000001000000000011000[0][1][2][3][4][5][6][7]OSRdyTbl[8]XY就緒表(ReadyList)結(jié)構(gòu)

處于就緒態(tài)的任務(wù)將就緒態(tài)標(biāo)志置于就緒表中。就緒表由變量OSRdyGrp和OSRdyTbl[]構(gòu)成。如對應(yīng)組中有就緒態(tài)任務(wù),OSRdyGrp對應(yīng)位置1。就緒表OSRdyTbl[]對應(yīng)(Y,X)元素置1。就緒表OSRdyTbl[]數(shù)組的大小取決于OS_LOWEST_PRIO的值,可在文件OS_CFG.H中定義。OS_LOWEST_PRIO值越小,占用RAM空間越少。為確定就緒任務(wù)優(yōu)先級,內(nèi)核調(diào)度程序總是先將OS_LOWEST_PRIO在就緒表相應(yīng)位置1。Index(下標(biāo)索引)BitMask(二進(jìn)制位掩碼)0000000011000000102000001003000010004000100005001000006010000007100000002、使任務(wù)進(jìn)入就緒態(tài):該算法中用到的二進(jìn)制位映射查找表OSMapTbl[],定義在OS_CORE.C文件中,可確保算法執(zhí)行時間的確定。該表數(shù)組值如下。使任務(wù)進(jìn)入就緒態(tài)程序清單OSRdyGrp|=OSMapTbl[prio>>3];OSRdyTbl[prio>>3]|=OSMapTbl[prio&0x07];使任務(wù)進(jìn)入就緒態(tài)(修改OSRdyGrp)C語句OSRdyGrp|=OSMapTbl[prio>>3]:直接從TCB中取出OSTCBY的值(即priority>>3),該值表示該任務(wù)在就緒表中的邏輯行號,即Y值,以該值為下標(biāo)索引,取得OSMapTbl[Y]的值,該值為對應(yīng)就緒表中的邏輯行號的掩碼值,行號所對應(yīng)的二進(jìn)制bit位是1。使用該掩碼值與OSRdyGrp作按位或操作,將OSRdyGrp的對應(yīng)就緒表中的邏輯行號的二進(jìn)制位置1。使任務(wù)進(jìn)入就緒態(tài)(修改OSRdyTbl[])C語句OSRdyTbl[prio>>3]|=OSMapTbl[prio&0x07]:直接從TCB中取出OSTCBY的值(即priority>>3),該值表示該任務(wù)在就緒表中的邏輯行號,即Y值,以該值為下標(biāo)索引,取得OSRdyTbl[Y]變量,即該語句等號的右邊。等式左邊:直接從TCB中取出OSTCBX的值(即priority&0x07),該值表示該priority任務(wù)在就緒表中的某邏輯行號下的第幾個任務(wù),即X值,以該值為下標(biāo)索引,取得OSMapTbl[X]變量,該值為對應(yīng)就緒表中某邏輯行號下的序號的掩碼值,該序號所對應(yīng)的二進(jìn)制bit位是1。使用該掩碼值與OSRdyTbl[Y]作按或操作,達(dá)到將對應(yīng)就緒表OSRdyTbl[]中的邏輯行號下的任務(wù)序號對應(yīng)的二進(jìn)制位置1的目的。OSRdyTbl[]表示優(yōu)先級priority對應(yīng)的就緒表中的邏輯行號及該行下的任務(wù)序號的二進(jìn)制位,已置1,表明第Y行的第X個任務(wù)已就緒。附加說明:TCB表中有四個變量用來記錄相關(guān)值。任務(wù)進(jìn)入就緒態(tài)或進(jìn)入等待事件發(fā)生狀態(tài)算法使用。使得任務(wù)進(jìn)入就緒表或進(jìn)入等待表的時間是個常數(shù),便于控制性能。避免在運(yùn)行中去計算這些值。這些值在任務(wù)建立時確定,或在改變?nèi)蝿?wù)優(yōu)先級時更新。

OSTCBY=priority>>3;OSTCBBitY=OSMapTbl[priority>>3];OSTCBX=priority&0x07;OSTCBBitX=OSMapTbl[priority&0x07];運(yùn)用TCB成員算法代碼:使任務(wù)進(jìn)入就緒態(tài)程序清單OSRdyGrp|=OSMapTbl[priority>>3];OSRdyTbl[priority>>3]|=OSMapTbl[priority&0x07];使任務(wù)進(jìn)入就緒態(tài)程序清單OSRdyGrp|=OSTCBBitY;OSRdyTbl[OSTCBY]|=OSTCBBitX;(5)任務(wù)調(diào)度(TaskScheduling)

μC/OS-Ⅱ內(nèi)核總是運(yùn)行就緒態(tài)任務(wù)中優(yōu)先級最高的。前面算法已確定最高優(yōu)先級任務(wù)。下面由調(diào)度程序(Scheduler)完成該任務(wù)運(yùn)行。任務(wù)級調(diào)度由函數(shù)OSSched()完成中斷級調(diào)度由函數(shù)OSIntExt()完成根據(jù)實(shí)時內(nèi)核的設(shè)計需求,μC/OS-Ⅱ任務(wù)調(diào)度程序運(yùn)行所花費(fèi)時間是個常數(shù),與應(yīng)用程序中建立的任務(wù)數(shù)無關(guān)。

程序清單任務(wù)調(diào)度程序(TaskScheduler)voidOSSched(void){

INT8Uy;

OS_ENTER_CRITICAL();

if((OSLockNesting|OSIntNesting)==0){ (1)

Y=OSUnMapTbl[OSRdyGrp]; (2)

OSPrioHighRdy=(INT8U)((y<<3)+OSUnMapTbl[OSRdyTbl[y]]); (2)

if(OSPrioHighRdy!=OSPrioCur){ (3)

OSTCBHighRdy=OSTCBPrioTbl[OSPrioHighRdy]; (4)

OSCtxSwCtr++;(5)

OS_TASK_SW();(6)

}}

OS_EXIT_CRITICAL();}任務(wù)調(diào)度的關(guān)閉和打開調(diào)用任務(wù)調(diào)度關(guān)閉函數(shù)、任務(wù)調(diào)度打開函數(shù)實(shí)現(xiàn)1、調(diào)用任務(wù)調(diào)度關(guān)閉函數(shù)OSSchedLock()以后,不得使用任何能將現(xiàn)行任務(wù)掛起的系統(tǒng)調(diào)用,因?yàn)檫@些調(diào)用會導(dǎo)致該任務(wù)睡眠,使得任務(wù)調(diào)度程序無法重新打開。2、用戶可以在低優(yōu)先級任務(wù)在進(jìn)行事件發(fā)送期間,調(diào)用任務(wù)調(diào)度關(guān)閉函數(shù),禁止任務(wù)調(diào)度。確保事件發(fā)送過程不被中斷。

程序清單:任務(wù)調(diào)度程序關(guān)閉VoidOSSchedLock(void){

if(OSRunning==TRUE){

OS_ENTER_CRITICAL();

OSLockNesting++;

OS_EXIT_CRITICAL();

}}程序清單:任務(wù)調(diào)度程序打開voidOSSchedUnlock(void){

If(OSRunning==TRUE){

OS_ENTER_CRITICAL();

if(OSLockNesting>0){

OSLockNesting--;

if((OSLockNesting|OSIntNesting)==0){

OS_EXIT_CRITICAL();

OSSched();

}else{

OS_EXIT_CRITICAL();

}

}else{

OS_EXIT_CRITICAL();

}

}}(6)空閑任務(wù)(IdleTask)為了更好地控制多個實(shí)時任務(wù)運(yùn)行,μC/OS-Ⅱ內(nèi)核總是建立一個空閑任務(wù),這個任務(wù)在沒有其它任務(wù)進(jìn)入就緒態(tài)時運(yùn)行??臻e任務(wù)對應(yīng)的函數(shù)代碼為OSTaskIdle(),空閑任務(wù)永遠(yuǎn)設(shè)為最低優(yōu)先級,即OS_LOWEST_PRI0??臻e任務(wù)OSTaskIdle()的主要工作,只是在不斷地給一個32位的變量OSIdleCtr計數(shù)器加1

μC/OS-Ⅱ的空閑任務(wù)代碼VoidOSTaskIdle(void*pdata){

Pdata=pdata;

for(;;){

OS_ENTER_CRITICAL();

OSIdleCtr++;

OS_EXIT_CRITICAL();

}}在計數(shù)器OSIdleCtr加1時,中斷關(guān)閉,加1完成后中斷再打開。這是因?yàn)?,完?位和多數(shù)16位微處理器對一個32位變量加1操作,需要多條指令,要防止高優(yōu)先級任務(wù)或中斷服務(wù)子程序ISR中斷這個加1的指令執(zhí)行過程。統(tǒng)計任務(wù)

為了完成應(yīng)用程序代碼完成各種時間統(tǒng)計,μC/OS-Ⅱ內(nèi)核提供一個統(tǒng)計任務(wù),任務(wù)函數(shù)為OSTaskStat()。只當(dāng)在文件OS_CFG.H中,將符號常量OS_TASK_STAT_EN設(shè)為1,這個任務(wù)才會創(chuàng)建。一旦創(chuàng)建成功,統(tǒng)計任務(wù)OSTaskStat()每秒鐘運(yùn)行一次,計算當(dāng)前的CPU利用率。程序清單

4.12初始化統(tǒng)計任務(wù)Voidmain(void){

OSInit();/*1、初始化uC/OS-II*/

/*2、安裝uC/OS-II的任務(wù)切換向量(略)*/

/*3、創(chuàng)建用戶起始任務(wù)TaskStart()(略)*/

OSStart();/*4、開始多任務(wù)調(diào)度*/}VoidTaskStart(void*pdata){

/*5、安裝并啟動uC/OS-II的時鐘節(jié)拍(略)*/

OSStatInit();/*6、初始化統(tǒng)計任務(wù)*/

/*7、創(chuàng)建用戶應(yīng)用程序任務(wù)(略)*/

for(;;){

/*8、任務(wù)函數(shù)TaskStart()的代碼!*/

}}程序清單4.14統(tǒng)計任務(wù)VoidOSTaskStat(void*pdata){

INT32Urun;

INT8Susage;

pdata=pdata;

while(OSStatRdy==FALSE){ (1)

OSTimeDly(2*OS_TICKS_PER_SEC);

}}

for(;;){

OS_ENTER_CRITICAL();

OSIdleCtrRun=OSIdleCtr;

run=OSIdleCtr;

OSIdleCtr=0L;

OS_EXIT_CRITICAL();

if(OSIdleCtrMax>0L){

usage=(INT8S)(100L-100L*run/OSIdleCtrMax); (2)

if(usage>100){OSCPUUsage=100;

}elseif(usage<0){

OSCPUUsage=0;

}else{OSCPUUsage=usage;

}

}else{OSCPUUsage=0;

}

OSTaskStatHook(); (3)

OSTimeDly(OS_TICKS_PER_SEC);

}系統(tǒng)初始化期間創(chuàng)建的任務(wù)應(yīng)用程序必須先建立一個起始任務(wù),如TaskStart(),當(dāng)應(yīng)用程序運(yùn)行到main()中調(diào)用uC/OS-II內(nèi)核啟動函數(shù)OSStart(),μC/OS-Ⅱ內(nèi)核一般已創(chuàng)建3個任務(wù):TaskStart()、OSTaskIdle()和OSTaskStat()。μC/OS-Ⅱ?qū)⒖臻e任務(wù)優(yōu)先級設(shè)為最低,即OS_LOWEST_PRIO,統(tǒng)計任務(wù)優(yōu)先級設(shè)為次低,即OS_LOWEST_PRIO-1。啟動任務(wù)TaskStart()總是優(yōu)先級最高的任務(wù),比如,優(yōu)先級為0。(7)μC/OS中的中斷處理

中斷技術(shù)及其實(shí)現(xiàn)是任何一種實(shí)時內(nèi)核必須提供的應(yīng)用機(jī)制。實(shí)時內(nèi)核應(yīng)該能夠支持應(yīng)用程序設(shè)計實(shí)現(xiàn)自身需要的中斷及中斷處理子程序。μC/OS內(nèi)核中,中斷服務(wù)子程序要用匯編語言來寫。如果用戶使用的C語言編譯器支持內(nèi)置匯編語言,用戶可以直接將中斷服務(wù)子程序代碼放在C語言的程序文件中。程序清單

μC/OS-II中的中斷服務(wù)子程序用戶中斷服務(wù)子程序:

保存全部CPU寄存器;(1)

調(diào)用OSIntEnter或OSIntNesting直接加1;

(2)

執(zhí)行用戶代碼做中斷服務(wù);(3)

調(diào)用OSIntExit();

(4)

恢復(fù)所有CPU寄存器;

(5)

執(zhí)行中斷返回指令;

(6)程序清單4.16中斷進(jìn)入函數(shù):通知μC/OS-Ⅱ內(nèi)核,中斷服務(wù)子程序開始執(zhí)行voidOSIntEnter(void){OS_ENTER_CRITICAL();

OSIntNesting++;

OS_EXIT_CRITICAL();}程序清單

4.17中斷退出函數(shù):通知μC/OS-Ⅱ內(nèi)核,中斷服務(wù)子程序執(zhí)行完畢voidOSIntExit(void)

{OS_ENTER_CRITICAL();(1)

If((--OSIntNesting|OSLockNesting)==0){(2)

OSIntExitY=OSUnMapTbl[OSRdyGrp];(3)

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論