THREADX操作系統(tǒng)各模塊詳解第一部分_第1頁
THREADX操作系統(tǒng)各模塊詳解第一部分_第2頁
THREADX操作系統(tǒng)各模塊詳解第一部分_第3頁
THREADX操作系統(tǒng)各模塊詳解第一部分_第4頁
已閱讀5頁,還剩65頁未讀, 繼續(xù)免費閱讀

下載本文檔

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

文檔簡介

1、THREADX深入學(xué)習(xí)簡介最近在做 THREADX 移植項目,所以在開始學(xué)習(xí) THREADX 操作系統(tǒng)。想把自己學(xué)到的東西總結(jié)一下。 學(xué)習(xí)操作系統(tǒng)時, 按照領(lǐng)導(dǎo)的意思把操作系統(tǒng)進(jìn)行模塊劃分。通過查找資料將操作系統(tǒng)劃分為任務(wù)調(diào)度模塊、 任務(wù)管理模塊、 任務(wù)間同步和通信模塊、內(nèi)存管理模塊、中斷管理模塊、時鐘管理模塊。下面將分別對各個模塊進(jìn)行分析和研究。 我將深入介紹各個模塊的工作原理, 通過此文檔能對操作系統(tǒng)的工作原理有深入的了解。 首先得我的分析是針對 MIPS、ARM 、251內(nèi)核進(jìn)行分析。我移植的平臺是 16 位的 251 平臺。個人認(rèn)為移植一個操作系統(tǒng),首先對操作系統(tǒng)的內(nèi)核調(diào)度原理必須十分

2、清楚, 然后對你的移植平臺架構(gòu)、 指令集也要十分清楚,比如說下面幾個方面:1、子程序調(diào)用時 PC 值是怎么被保存得( MPIS,將子程序的返回值存放在了 RA 寄存器中,251 是 PC 自動入棧(ECALL 指令)退出時使用 ERET 等指令, ARM 是在 LR 寄存器中要計算相應(yīng)減去的數(shù)值) 。2、中斷發(fā)生時( 251PC 自動入棧但順序和子程序調(diào)用壓入順序不一樣,中斷返回使用 RETI 指令。 MIPS, PC 是被存入了 EPC 寄存器中,使用eret 指令。ARM , LR 中數(shù)值的計算,賦值給PC 即可)2. 任務(wù)調(diào)度操作系統(tǒng)的核心模塊就是內(nèi)核調(diào)度。首先要弄清楚其調(diào)度原理。帶著下

3、面幾個問題去思考。1、任務(wù)入口函數(shù)第一次是怎么被執(zhí)行的。2、任務(wù)是怎么被切換的。3、任務(wù)是怎么被搶占的。以上幾個問題是任務(wù)調(diào)度的核心。帶著這幾個問題去看內(nèi)核源碼發(fā)現(xiàn)任務(wù)調(diào)度使用的方法就是任務(wù)棧和系統(tǒng)棧,內(nèi)核利用入棧和出棧完成對任務(wù)的調(diào)度和切換。而任務(wù)被調(diào)度起來是依靠timer 驅(qū)動來工作。基于此分析可以得出內(nèi)核調(diào)度重點是以下幾個方面:1、明白任務(wù)棧的構(gòu)建方式,即任務(wù)創(chuàng)建時初始化任務(wù)堆棧時保存的數(shù)據(jù)。這些數(shù)據(jù)要根據(jù)具體的硬件平臺去實現(xiàn),這個棧的初始化就是解決上面的第一個問題的。因為在內(nèi)核調(diào)度時,任務(wù)第一次被執(zhí)行是出此棧來執(zhí)行對應(yīng)的入口函數(shù)的。對于棧我們要明白任務(wù)棧和系統(tǒng)棧的區(qū)別,要針對不同的硬件

4、平臺而做不同的設(shè)計。任務(wù)棧有兩種類型,一種叫做中斷類型棧,是在產(chǎn)生中斷保存任務(wù)上下文到任務(wù)??臻g的數(shù)據(jù),其出棧方式是要利用中斷返回時的出棧方式;另外一種棧叫做用任務(wù)棧是任務(wù)在執(zhí)行過程中自掛起時需要把 CPU 控制權(quán)重新交給調(diào)度器的時候需要把當(dāng)前的任務(wù)上下文進(jìn)行保護(hù),在任務(wù)出此棧的時候要用子程序返回的方式去出棧。系統(tǒng)棧主要系統(tǒng)內(nèi)核自己需要使用的棧。 移植過程中我們可能要不斷的切換 SP 在這兩個棧之間。 也可能只用系統(tǒng)的 SP,不切換只是來回的復(fù)制兩個??臻g的內(nèi)容 (如 51 系列)。這里移植的時候可能會出現(xiàn)以下幾個問題:a、TIMER 中斷產(chǎn)生后,任務(wù)調(diào)度任務(wù)第一次執(zhí)行出棧時,是按照子程序返回

5、的方式去出棧。這樣中斷將永遠(yuǎn)不會被返回。這樣就有問題了,這個在任務(wù)切換的時候經(jīng)常遇到就是任務(wù)入口函數(shù)第一次被執(zhí)行的時候。解決的辦法是初始化任務(wù)棧的時候初始化成中斷類型的棧。b、要明白硬件平臺的壓棧方式。發(fā)生中斷時的壓棧方式和子程序調(diào)用時的壓棧方式是不同的。像MIPS 這樣產(chǎn)生中斷和子程序調(diào)用時都有相應(yīng)的寄存器保存相應(yīng)的值,這樣的平臺實現(xiàn)起來比較簡單。而251 平臺確沒有,251 不管是中斷還是子程序調(diào)用都是把PC 值壓入棧中,而且壓入得順序也不一樣。( 251 中產(chǎn)生中斷和子程序調(diào)用時PC 值入棧的順序是不一樣的, PC 分三次入棧,見具體的芯片手冊)c、任務(wù)的出棧方式。任務(wù)出棧是在任務(wù)調(diào)度后

6、恢復(fù)優(yōu)先級最高的任務(wù)時執(zhí)行的,先判斷任務(wù)棧類型然后采用相應(yīng)的出棧方式。251 平臺任務(wù)棧和中斷棧保護(hù)的數(shù)據(jù)一樣,但出棧的方式也就是子程序返回的方式是RETI 和ERET。子程序調(diào)用可以采用RETI 而中斷產(chǎn)生時不能采用ERET 否則會中斷一直無法返回。d、入棧的方式:對于 mips 把相應(yīng)的寄存器數(shù)據(jù)壓入到任務(wù)棧就OK 了。而 251 平臺是系統(tǒng)自動壓棧, 出棧的時候要出對應(yīng)的 PC 值才 OK 。因此在產(chǎn)生中斷時先進(jìn)行入棧操作,然后調(diào)用子程序。由于是在子程序中把棧數(shù)據(jù)拷貝到任務(wù)棧中,因此要把 SP 減去相應(yīng)的值,要看子程序調(diào)用壓入了幾個數(shù)據(jù)。ECALL 是減 3。切記不要在任務(wù)棧中存入額外的

7、數(shù)據(jù)。否則出棧就出錯了。2、TIMER 產(chǎn)生中斷執(zhí)行timer 中斷處理函數(shù), timer 中斷會對當(dāng)前任務(wù)的時間片進(jìn)行計時,時間到期后會調(diào)用任務(wù)切換函數(shù),切換下一個更高優(yōu)先級的任務(wù)。任務(wù)切換函數(shù)只是把當(dāng)前任務(wù)切換到同一個優(yōu)先級列表的最后,并沒有去執(zhí)行下一個任務(wù)。這個工作交給了任務(wù)上下文恢復(fù)函數(shù),此函數(shù)會比較當(dāng)前正在執(zhí)行的任務(wù)和下一個要執(zhí)行的任務(wù)控制塊指針。如果兩個控制塊指針的值不一樣就要去回到調(diào)度接口去重新調(diào)度了。正好上面的2 問題。3、任務(wù)在執(zhí)行過程中釋放信號量、中斷等操作時使一個更高優(yōu)先級任務(wù)就緒時就會發(fā)生搶占。此時當(dāng)前任務(wù)上下文會被保存同時高優(yōu)先級任務(wù)的控制塊指針會賦值給更高下一個要被

8、執(zhí)行的控制塊指針。如果是中斷產(chǎn)生的下面的操作如同 2 中的一樣。如果是任務(wù)間同步等操作導(dǎo)致則會調(diào)用轉(zhuǎn)交CPU 控制權(quán)到調(diào)度接口去重新調(diào)度。這樣更高優(yōu)先級的任務(wù)就被執(zhí)行了。這個就是上面的 3 問題。4、任務(wù)調(diào)度流程圖。力求詳細(xì)而明了。圖 1 是任務(wù)調(diào)度流程圖。事件(同步中斷 創(chuàng)建任務(wù))系統(tǒng)啟動就緒列表創(chuàng)建任務(wù)更新就緒列表啟動調(diào)度器獲取高優(yōu)先級任務(wù)獲取高優(yōu)先級任務(wù)高優(yōu)先級任務(wù)就緒啟動調(diào)度器獲取高優(yōu)先級任務(wù)調(diào)度器任務(wù)切換TIMER設(shè)置時間片值開始執(zhí)行任務(wù)TIMER 計時時間片數(shù)值到更新就緒列表重新啟動調(diào)度器開始執(zhí)行任務(wù)開始執(zhí)行任務(wù)圖 1.任務(wù)調(diào)度流程圖2.1 任務(wù)調(diào)度接口圖 2.是 THREADX

9、操作系統(tǒng)函數(shù)總體框架示意圖。系統(tǒng)啟動任務(wù)管理調(diào)度器中斷管理TIMER任務(wù)切換調(diào)用任務(wù)創(chuàng)建接口tx_thread_create任務(wù)創(chuàng)建完成sys_timer0調(diào)用任務(wù)調(diào)度器接口_tx_thread_scheduleISR_tx_thread_context_save調(diào)用 TimerHandler_tx_timer_interrupt時間片到時調(diào)用任務(wù)切換接口_tx_thread_time_slice任務(wù)切換完成調(diào)用任務(wù)上下文恢復(fù)接口_tx_thread_context_restore調(diào)用調(diào)度器接口_tx_thread_schedule定時器到時調(diào)用任務(wù)恢復(fù)接口_tx_thread_resume任

10、務(wù)恢復(fù)完成調(diào)用任務(wù)上下文恢復(fù)接口_tx_thread_context_restore調(diào)用調(diào)度器接口_tx_thread_schedule圖 2.THREADX操作系統(tǒng)函數(shù)總體框架示意圖調(diào)度器接口1、 _tx_thread_schedule 調(diào)(度器 )函數(shù)原形Void _tx_thread_schedule( void)返回值無參數(shù)無說明調(diào)度任務(wù)去執(zhí)行調(diào)度器接口主要負(fù)責(zé)從就緒列表中獲取優(yōu)先級最高的任務(wù)去執(zhí)行。開始開中斷獲取要被執(zhí)行任務(wù)控制塊N是否有就緒任務(wù)Y關(guān)中斷保存任務(wù)被調(diào)度次數(shù)設(shè)置時間片標(biāo)志判斷用戶棧類型中斷棧請求棧開中斷開中斷出中斷?;謴?fù)任務(wù)運行出請求?;謴?fù)任務(wù)運行結(jié)束中斷接口2、 _t

11、x_timer_interrupt (timer 中斷處理函數(shù) )函數(shù)原形Void _tx_timer_interrupt (void)返回值無參數(shù)無說明Timer 中斷處理函數(shù),負(fù)責(zé)時間片和定時器計時YN將當(dāng)前定時器控制塊指針指向下個節(jié)點已到定時器列表末尾Y將當(dāng)前定時器控制塊指針指向開始節(jié)點時間片切換任務(wù)任務(wù)切換成功重新設(shè)置當(dāng)前任務(wù)時間片開始系統(tǒng)時鐘加1當(dāng)前線程的時間片=0?N時間片減 1時間片 =0?Y設(shè)置時間片到時標(biāo)志N定時器到期?Y設(shè)置時鐘到期標(biāo)志N檢測到時標(biāo)志定時器沒有到時標(biāo)志恢復(fù)定時器處理任務(wù)N結(jié)束任務(wù)切換接口1、 _tx_thread_time_slice (任務(wù)切換函數(shù) )函數(shù)

12、原形UINT_tx_thread_time_slice(VOID)返回值True,任務(wù)已經(jīng)切換False,任務(wù)沒有切換參數(shù)無說明進(jìn)行任務(wù)切換,任務(wù)時間片到時進(jìn)行同一個優(yōu)先級任務(wù)切換開始獲取當(dāng)前任務(wù)控制塊關(guān)中斷當(dāng)前任務(wù)狀態(tài)是否為就緒狀態(tài)Y當(dāng)前任務(wù)是否為可以被搶占YN當(dāng)前任務(wù)優(yōu)先級列表是否有其它任務(wù)YN把當(dāng)前任務(wù)控制塊放在同一優(yōu)先級N就緒列表的末尾。Y設(shè)置下一個要被調(diào)度的任務(wù)開中斷結(jié)束定時器任務(wù)入口函數(shù)2、 _tx_timer_thread_entry (定時器任務(wù)入口函數(shù) )函數(shù)原形VOID_tx_timer_thread_entry(ULONGtimer_thread_input)返回值無參數(shù)

13、ULONG timer_thread_input任務(wù)處理參數(shù)說明定時器任務(wù)處理函數(shù)開始從當(dāng)前定時器控制塊指針指向的定時器控制塊并保存清空當(dāng)前定時器控制塊指針中的數(shù)據(jù)當(dāng)前定時器控制塊指針指向下一個定時器列表當(dāng)前定時器控制塊指針是否已經(jīng)到定時器列表末尾Y將當(dāng)前定時器控制塊指針指向到定時器列表開始N清除定時器過期標(biāo)志Y獲取到得到期定時器控制塊是否為0N列表中定時器控制塊是否只有一個N從列表中刪除當(dāng)前處理的定時器控制塊,并獲取下一個到期的定時器控制塊Y判斷定時時間平是否>32Y獲取入口函數(shù)并執(zhí)行將定時時間片值減去32Y是否需要再次定時Y再次激活該定時器N是否新的定時器到期掛起該任務(wù)3任務(wù)管理任務(wù)

14、管理主要有任務(wù)創(chuàng)建、任務(wù)掛起、任務(wù)恢復(fù)、睡眠、等接口組成。一、注意問題:1、就緒列表的組成以及獲取下一個可以執(zhí)行的最高優(yōu)先級任務(wù)的方式。THREADX 支持的優(yōu)先級為32 個,任務(wù)個數(shù)為任意,視具體資源而定。具有一32 個元素的就緒鏈表,是按照任務(wù)優(yōu)先級進(jìn)行排序存放的。還有一個最低位映射表 thread_lowest_bit。3.1 任務(wù)初始化任務(wù)初始化主要是對任務(wù)的一些全局變量做初始化。主要包括以下變量和數(shù)組:_tx_thread_current_ptr:當(dāng)前正在運行的任務(wù)。_tx_thread_execute_ptr:下一個要執(zhí)行的任務(wù)。_tx_thread_priority_map:記錄

15、任務(wù)優(yōu)先級的位置,每一位對應(yīng)一位優(yōu)先級。_tx_thread_highest_priority:就緒任務(wù)中最高的優(yōu)先級值。_tx_thread_lowest_bit:優(yōu)先級最低位映射表。_tx_thread_priority_list :就緒鏈表優(yōu)先級鏈表。_tx_thread_created_ptr:創(chuàng)建的任務(wù)鏈表的頭指針。_tx_thread_created_count:創(chuàng)建任務(wù)的數(shù)量。_tx_thread_preempt_disable:禁止搶占標(biāo)志。具體含義詳細(xì)解釋見附錄A 。3.1 任務(wù)創(chuàng)建注意點:1、初始化任務(wù)的定時器超時入口函數(shù)。這個入口函數(shù)很有作用,在定時器到時時會調(diào)用這個接口

16、。所有的任務(wù)延時到時間時最終由定時器處理任務(wù)來調(diào)用。2、如果禁止搶占,則在調(diào)用tx_tcr.s 時判斷如果禁止搶占,則直接從中斷中退出,不會再發(fā)生搶占。開始初始化任務(wù)棧為 0xEF初始化任務(wù)控制塊為 0給任務(wù)控制塊賦值建立任務(wù)棧禁止中斷將任務(wù)控制塊加入任務(wù)創(chuàng)建時形成的鏈表中創(chuàng)建的任務(wù)數(shù)加 1禁止搶占恢復(fù)中斷N是否立即執(zhí)行?Y禁止中斷調(diào)用任務(wù)恢復(fù)接口恢復(fù)搶占是否發(fā)生搶占Y恢復(fù)中斷重新調(diào)度結(jié)束3.2 任務(wù)超時處理函數(shù)在任務(wù)采用延時掛起時, 定時器如果到期則調(diào)用該處理函數(shù)。 該處理函數(shù)的入口參數(shù)就是任務(wù)自己的控制塊。任務(wù) cleanup 函數(shù)為任務(wù)掛起時相應(yīng)導(dǎo)致任務(wù)掛起的模塊,如信號量、消息隊列等。

17、3.3 任務(wù)掛起注意問題:1、任務(wù)正在掛起標(biāo)志設(shè)置為TRUE 代表任務(wù)正在掛起,任務(wù)還在就緒鏈表中,當(dāng)被設(shè)置為 FALSE 的時候,已經(jīng)從就緒鏈表中刪除了此任務(wù),在從鏈表中刪除任務(wù)時,操作時是關(guān)閉中斷的,所以是不可能是被搶占的。2、因為任務(wù)要被掛起,所以獲取下一個能被執(zhí)行的任務(wù),就是從就緒鏈表中獲取下一個優(yōu)先級最高的任務(wù)去執(zhí)行。判斷和被掛起的任務(wù)同一個優(yōu)先級就緒鏈表中是否還有其它任務(wù)。如果這個鏈表中有其它任務(wù)存在并且掛起任務(wù)為鏈表的頭,從就緒鏈表中刪除此任務(wù)并直接把這個鏈表的頭指針指向掛起任務(wù)的下一個任務(wù),判斷下個要執(zhí)行的任務(wù)是否為掛起任務(wù),如果是則獲取下一個就緒鏈表中優(yōu)先級最高的任務(wù); 如果

18、不是鏈表的頭就直接從鏈表中刪除此任務(wù)就好了。如果同一個優(yōu)先級的就緒鏈表中就只有一個任務(wù),要做兩個方面的工作:a、把此優(yōu)先級的就緒鏈表的頭指針指向為空。b、獲取下一個要執(zhí)行的任務(wù)。c、清楚掛起任務(wù)在優(yōu)先級位映射標(biāo)志的對應(yīng)位。d、獲取優(yōu)先級位映射標(biāo)志。e、獲取掛起任務(wù)所在的優(yōu)先級組和優(yōu)先級組中對應(yīng)的數(shù)據(jù),即這個優(yōu)先級組對應(yīng)的 8 位數(shù)據(jù)。獲取優(yōu)先級組對應(yīng)的位數(shù)據(jù)的方法為優(yōu)先級位映射表向右移動組號乘以 8 位,priority_group =(UINT) (priority_map >> TX_THREAD_GROUP_1);。如果系統(tǒng)只創(chuàng)建了一個任務(wù),則掛起任務(wù)后,系統(tǒng)就會進(jìn)入調(diào)度接口

19、的死循環(huán)。f、獲取任務(wù)就緒鏈表中最高優(yōu)先級。g、判斷下一個要執(zhí)行的任務(wù)是否為掛起任務(wù),如果不是則執(zhí)行i。如果是則先利用最高優(yōu)先級值獲取下一個要執(zhí)行的任務(wù),然后再判斷是否有閾值搶占的情況發(fā)生。h、如果沒有則執(zhí)行i,如果有,利用 _tx_thread_preempted_map值獲取閾值搶占的最高優(yōu)先級任務(wù), 平判斷該任務(wù)的閾值和最高優(yōu)先級值得大小。如果優(yōu)先級大于等于閾值則設(shè)置下一個要執(zhí)行的任務(wù)為閾值搶占發(fā)生時的任務(wù)。具體解釋看_tx_thread_preempted_map變量解析。i 、判斷是否有搶占發(fā)生。有重新調(diào)度,沒有則退出。3、_tx_thread_priority_map 此標(biāo)志是用來

20、記錄優(yōu)先級對位的位的。如果就緒鏈表中同一個優(yōu)先級還有其它任務(wù),則此優(yōu)先級對應(yīng)位不用清除, 如果鏈表中只有掛起任務(wù)自己就得清除此位。開始禁止中斷恢復(fù)搶占N任務(wù)正在掛起標(biāo)志true?Y設(shè)置任務(wù)掛起標(biāo)志位false獲取掛起任務(wù)的優(yōu)先級恢復(fù)中斷N和掛起任務(wù)同一優(yōu)先級的就緒鏈表中是否還有其它任務(wù)Y設(shè)置同個優(yōu)先級就緒鏈表頭指針為空清楚掛起任務(wù)對應(yīng)優(yōu)先級映射位獲取優(yōu)先級位映射位標(biāo)志值判斷掛起任務(wù)優(yōu)先級所在優(yōu)先級組組 0組 1組2組 3其它設(shè)置臨時優(yōu)設(shè)置臨時優(yōu)設(shè)置臨時優(yōu)先設(shè)置臨時優(yōu)先先級組值為 0先級組值為 8級組值為 16級組值為 24獲取優(yōu)先級組獲取優(yōu)先級組獲取優(yōu)先級組獲取優(yōu)先級組對應(yīng)的 8位數(shù)據(jù)對應(yīng)的

21、8位數(shù)據(jù)對應(yīng)的 8位數(shù)據(jù)對應(yīng)的 8位數(shù)據(jù)設(shè)置最高優(yōu)先級為標(biāo)志為最低設(shè)置下個要執(zhí)行的任務(wù)為空獲取相應(yīng)組中對應(yīng)的最高優(yōu)先級恢復(fù)中斷系統(tǒng)狀態(tài)是否為 0AY重新調(diào)度N結(jié)束從就緒鏈表中刪除掛起任務(wù)掛起任務(wù)是否為同一個優(yōu)先級就緒鏈表中的頭Y鏈表頭指向掛起任務(wù)的下個任務(wù)判斷下個要執(zhí)行的任務(wù)是否為掛起任務(wù)Y從就緒鏈表中獲取下個優(yōu)先級最高的任務(wù)N恢復(fù)中斷N是否發(fā)生搶占Y重新調(diào)度NA下一個要執(zhí)行的任務(wù)是否為要掛起的任務(wù)利用最高優(yōu)先級值獲取下一個要執(zhí)行的任務(wù)是否有閾值搶占發(fā)生的情況利用閾值搶占映射變量獲取閾值搶占發(fā)生的任務(wù)中優(yōu)先級最高的任務(wù)最高優(yōu)先級值>= 閾值搶占優(yōu)先級最高任務(wù)的閾值NN 設(shè)置下一個要執(zhí)行的

22、任務(wù)為閾值搶占發(fā)生的優(yōu)先級最高任務(wù)清除閾值搶占優(yōu)先級映射變量對應(yīng)位N恢復(fù)中斷是否發(fā)生搶占Y重新調(diào)度N結(jié)束3.4 任務(wù)恢復(fù)注意問題:1、任務(wù)恢復(fù)接口主要是把掛起任務(wù)恢復(fù)到就緒狀態(tài)。2、一般是在發(fā)生任務(wù)搶占的時候會調(diào)用此接口。3、用于調(diào)用任務(wù)恢復(fù)接口。4、調(diào)用該接口前都會把禁止搶占標(biāo)志加1 操作,也就是禁止搶占。但是在該接口里面會設(shè)置完成是否發(fā)生搶占標(biāo)志后進(jìn)行減1 操作,恢復(fù)搶占。N恢復(fù)任務(wù)狀態(tài)為就緒態(tài)?NY任務(wù)是否為延時掛起N設(shè)置延時掛起標(biāo)志為false設(shè)置恢復(fù)任務(wù)狀態(tài)為就緒態(tài)設(shè)置恢復(fù)任務(wù)狀態(tài)為掛起態(tài)獲取恢復(fù)任務(wù)的優(yōu)先級獲取在此優(yōu)先級的就緒鏈表的頭指針此優(yōu)先級的就緒鏈表是否為空Y恢復(fù)任務(wù)做為就緒

23、鏈表的頭設(shè)置優(yōu)先級映射表YY下一個要執(zhí)行的任務(wù)是否為空N設(shè)置下一個要執(zhí)行的任務(wù)為恢復(fù)任務(wù)恢復(fù)任務(wù)優(yōu)先級是否高于任務(wù)最高優(yōu)先級設(shè)置最高優(yōu)先級標(biāo)志為恢復(fù)任務(wù)優(yōu)先級Y設(shè)置最高優(yōu)先級為恢復(fù)任務(wù)優(yōu)先級恢復(fù)任務(wù)優(yōu)先級是否高于下一個要執(zhí)行任務(wù)的閾值Y下一個要執(zhí)行的任務(wù)的優(yōu)先級等于閾值Y下一個要執(zhí)行的任務(wù)為恢復(fù)任務(wù)恢復(fù)中斷是否發(fā)生搶占開始是否發(fā)生搶占標(biāo)志為false禁止中斷禁止搶占標(biāo)志減一檢測恢復(fù)的任務(wù)是否正在掛起Y恢復(fù)任務(wù)的狀態(tài)為完成或終止N設(shè)置任務(wù)正在掛起標(biāo)志為false設(shè)置任務(wù)狀態(tài)為就緒態(tài)N在鏈表末尾插入恢復(fù)任務(wù)YN設(shè)置任務(wù)搶占映射標(biāo)志設(shè)置發(fā)生搶占標(biāo)志為true結(jié)束3.5 任務(wù)睡眠睡眠只能在任務(wù)中調(diào)用。

24、 必須有時間片的支持。 在定時器到時的時候會調(diào)用睡眠任務(wù)的超時處理函數(shù), 超時處理函數(shù)會判斷是什么導(dǎo)致任務(wù)掛起計時,如果是睡眠就直接恢復(fù)任務(wù)。開始當(dāng)前是否有任務(wù)在執(zhí)行且執(zhí)行的任務(wù)不是Y定時器任務(wù)且系統(tǒng)初始化已經(jīng)完成直接錯誤返回NY睡眠的時間是否為0?N直接成功返回禁止中斷設(shè)置任務(wù)狀態(tài)為睡眠狀態(tài)設(shè)置任務(wù)正在掛起標(biāo)志為true設(shè)置任務(wù)掛起狀態(tài)為success禁止搶占恢復(fù)中斷設(shè)置當(dāng)前任務(wù)定時器控制塊定時時間為睡眠時間激活定時器調(diào)用掛起任務(wù)接口返回掛起狀態(tài)3.6 創(chuàng)建任務(wù)棧就是根據(jù)要保存的硬件資源主要是一些在被中斷打斷時必須要保存的寄存器在建立一個足夠大小的任務(wù)棧空間。3.7 轉(zhuǎn)換控制權(quán)就是如果發(fā)生了

25、搶占當(dāng)前任務(wù)掛起時就要把CPU 控制權(quán)提交給調(diào)度接口重新去調(diào)度。注意:1、對于 251 平臺而言,調(diào)用子函數(shù)時PC 是自動入棧的。執(zhí)行ERET 和 RETI時恢復(fù) PC 的順序還不一樣。本系統(tǒng)運行在中斷中釋放信號量,因此所有子函數(shù)調(diào)用也執(zhí)行 RETI ,所以在此接口一進(jìn)來,要重新修改PC 的入棧順序。2、如果任務(wù)掛起時,本身的時間片是0 則不重新設(shè)置時間片,否則重新設(shè)置為新的時間片。就是說,任務(wù)如果時間片不為0,執(zhí)行了一段時間后掛起恢復(fù)的時候時間片會重新開始。開始關(guān)中斷按照 RETI 方式修改 PC入棧順序PUSH 入棧操作獲取當(dāng)前N任務(wù)控制塊N保存 SP到任務(wù)控制塊獲取任務(wù)時間片時間片是否為

26、0N重新設(shè)置任務(wù)時間片清除時間片標(biāo)志值為0Y清除當(dāng)前任務(wù)控制塊為0調(diào)用調(diào)度接口4任務(wù)同步4.1 互斥量互斥量具有的功能是優(yōu)先級繼承,永遠(yuǎn)只能有一個任務(wù)占有互斥量。一、注意:如果互斥量不支持優(yōu)先級繼承,線程獲取時, 如果獲取成功就直接將互斥量的占有著記錄為當(dāng)前任務(wù)。否則直接掛起就可以了mutex_ptr -> tx_mutex_suspension_list =thread_ptr -> tx_suspended_next;。只有互斥量支持優(yōu)先級繼承的時候,任務(wù)的占有互斥量鏈表才進(jìn)行保存互斥量。thread_ptr -> tx_owned_mutex_list 指向任務(wù)占有互斥

27、量鏈表。因為優(yōu)先級繼承時要考慮占有任務(wù)優(yōu)先級恢復(fù)問題, 因為每一個互斥量都有可能使占有任務(wù)的優(yōu)先級發(fā)生改變。二、重要接口描述_tx_mutex_priority_change互斥量優(yōu)先級改變接口, 把占有任務(wù)優(yōu)先級改變?yōu)樾碌膬?yōu)先級_tx_mutex_put釋放互斥量接口_tx_mutex_get獲取互斥量接口獲取互斥量1、一個任務(wù)可以占用多個互斥量。2、同一個互斥量只能被同一個任務(wù)占有。3、同一個任務(wù)可以多次占有同一個信號量。4、互斥量的計數(shù)值為0 時,方可被獲取到。獲取到后設(shè)置為1。如果被同一個任務(wù)多次獲取后,則互斥量計數(shù)值做簡單的加1 操作。開始關(guān)中斷互斥信號量的計數(shù)值是否為 0?NY將互

28、斥量計數(shù)值設(shè)置為 1任務(wù)占有該互斥量?NY記錄占有該互斥量的任務(wù)互斥量計數(shù)值加 1支持優(yōu)先級繼承任務(wù)掛起?YY獲取當(dāng)前任務(wù),并設(shè)置 cleanup函數(shù)互斥量記錄當(dāng)前任務(wù)優(yōu)先級設(shè)置導(dǎo)致任務(wù)掛起的控制塊任務(wù)占有其它其它互斥信號量YN將任務(wù)存入互斥量掛起鏈表將該互斥量插入任務(wù)占有互將互斥信號量存入任務(wù)擁有的互斥量鏈表末尾斥量鏈表頭位置,并讓任務(wù)互斥量掛起任務(wù)數(shù)量加 1記錄自己的原始優(yōu)先級設(shè)置任務(wù)狀態(tài)為互斥量掛起N設(shè)置任務(wù)正在掛起標(biāo)志為 TRUE任務(wù)擁有的互斥量數(shù)量加 1禁止搶占互斥量最高等待優(yōu)先級設(shè)置為最低設(shè)置互斥量掛起方式就是定時tick 時間值設(shè)置返回狀態(tài)設(shè)置返回狀態(tài)設(shè)置返回狀態(tài)恢復(fù)中斷為SUC

29、CESS為 SUCCESS為 ERROR支持優(yōu)先級繼承Y互斥量優(yōu)先級是否高恢復(fù)中斷于掛起任務(wù)優(yōu)先級N結(jié)束設(shè)置互斥量的最高等待優(yōu)先級為掛起任務(wù)優(yōu)先級NY互斥量占有任務(wù)的優(yōu)先低于掛起任務(wù)優(yōu)先級Y設(shè)置占有任務(wù)的優(yōu)先級為掛起任務(wù)的優(yōu)先級任務(wù)掛起方式一直掛起NY啟動定時器調(diào)用掛起任務(wù)接口返回任務(wù)掛起狀態(tài)值釋放互斥量一、釋放互斥量要考慮幾個問題。5、是否支持優(yōu)先級繼承。6、恢復(fù)占有線程的優(yōu)先級。7、支持優(yōu)先級繼承和不支持的處理的區(qū)別。8、占有互斥量的線程的處理和互斥量本身的處理。9、線程什么時候恢復(fù)到原始優(yōu)先級。二、回答:問題 2:如果支持優(yōu)先級繼承, 則要考慮該互斥量被釋放后, 該互斥量的占有任務(wù)要恢復(fù)

30、的優(yōu)先級。 因為優(yōu)先級已經(jīng)被改變過了。 又因為一個任務(wù)可能占有多個互斥量。因此在支持優(yōu)先級的情況下, 占有任務(wù)要恢復(fù)到該任務(wù)剩余占有互斥量的最高等待優(yōu)先級?;コ饬康牡却齼?yōu)先級是任務(wù)在互斥量時被掛起時設(shè)置的。問題 3:支持優(yōu)先級繼承則要進(jìn)行恢復(fù)占有任務(wù)的優(yōu)先級, 然后恢復(fù)在該互斥量掛起的任務(wù), 同時使掛起任務(wù)中優(yōu)先級最高的任務(wù)先被執(zhí)行。不支持則不執(zhí)行恢復(fù)優(yōu)先級工作,直接恢復(fù)掛起任務(wù),把掛起的任務(wù)按順序恢復(fù)。問題 5:占有任務(wù)的優(yōu)先級, 會先被恢復(fù)到剩余占有的互斥量的最高等待優(yōu)先級, 然后釋放完所有占有的互斥量后,會被恢復(fù)到原始的優(yōu)先級。三、工作原理:1、先判斷當(dāng)前任務(wù)是否占有該互斥量并且該互斥量

31、值大于 0,如果不是就直接退出??梢?,不占有該互斥量的任務(wù)不能釋放互斥量, 且互斥量等于 0 的時候也不能釋放互斥量。2、滿足 1 的條件,則將互斥量值減1 操作。3、判斷減 1 后的互斥量值是否大于0,如果大于 0 說明該任務(wù)還要繼續(xù)占有此互斥量,則簡單的返回就可以了。4、如果等于 0,說明該任務(wù)釋放互斥量后不再占有互斥量。則要進(jìn)行相應(yīng)的操作了。5、如果等于 0,則要判斷該互斥量是否支持優(yōu)先級繼承。6、如果支持優(yōu)先級繼承則進(jìn)行下面的操作。如不支持優(yōu)先級繼承則從第7 部開始執(zhí)行。a、占有任務(wù)占用的互斥量數(shù)值減1 操作b、判斷任務(wù)占有的互斥量數(shù)量是否大于0c、如果等于0,則直接把占有任務(wù)指向的占

32、有的互斥量鏈表頭指針設(shè)置為0。如果不為 0,則把當(dāng)前的互斥量節(jié)點互斥量鏈表中刪除。同時修改頭指針指向的位置。d、獲取占有任務(wù)的原始優(yōu)先級。禁止搶占,恢復(fù)中斷。e、獲取占有任務(wù)占有的下一個互斥量。判斷此互斥量的等待優(yōu)先級是否高于占有任務(wù)的原始優(yōu)先級。如果高于則將要恢復(fù)的任務(wù)優(yōu)先級設(shè)置為當(dāng)前的獲取的互斥量的等待優(yōu)先級。如此直到查詢完畢。f、 禁止中斷,恢復(fù)搶占。g、互斥量掛起的任務(wù)數(shù)量是否大于1?如果是禁止搶占、恢復(fù)中斷。調(diào)用按優(yōu)先級排序掛起任務(wù)接口,保證優(yōu)先級最高的掛起任務(wù)先被執(zhí)行。禁止中斷、恢復(fù)搶占。h、如果小于等于 1。按第 7 部開始執(zhí)行。7、判斷互斥量掛起的任務(wù)數(shù)量是否為0?如果為 0

33、按下面步驟執(zhí)行: 不為 0 按照第 8 部開始執(zhí)行。a、如果為 0,禁止搶占,恢復(fù)中斷。b、判斷是否支持優(yōu)先級繼承,如果支持互斥量的最高等待優(yōu)先級設(shè)置為最低,同時把占有任務(wù)的優(yōu)先級恢復(fù)到上面獲取到得剩余互斥量的最高等待優(yōu)先級。當(dāng)然如果當(dāng)前占有任務(wù)的優(yōu)先級和要恢復(fù)的一樣,就不用調(diào)用改變優(yōu)先級接口,否則調(diào)用互斥量改變優(yōu)先級接口。c、禁止中斷,恢復(fù)搶占?;謴?fù)中斷。d、判斷是否會發(fā)生搶占,如果發(fā)生則重新調(diào)度。不能發(fā)生則返回。8、如果不為 0,則掛起的任務(wù)要被恢復(fù)到就緒列表中。要恢復(fù)的任務(wù)則相當(dāng)于要占有剛才釋放的互斥量, 因此要進(jìn)行類似獲取互斥量的操作,要判斷優(yōu)先級是否繼承。進(jìn)行下面的操作。a、獲取掛起

34、鏈表中的第一個任務(wù)。b、判斷該互斥量是否支持優(yōu)先級繼承。c、如果支持優(yōu)先級繼承,保護(hù)互斥量的先前占有任務(wù)?;コ饬坑涗浕謴?fù)任務(wù)的優(yōu)先級和閾值。判斷恢復(fù)任務(wù)占有的互斥量數(shù)量是否大于0。如果大于 0,將互斥量插入互斥量鏈表的末尾。如果占有的互斥量等于0,則直接插入鏈表頭,并且恢復(fù)任務(wù)保護(hù)自己的原始優(yōu)先級和閾值。然后將恢復(fù)任務(wù)占有的互斥量數(shù)量加1,同時設(shè)置互斥量最高等待優(yōu)先級為最低。然后從 d 開始執(zhí)行。d、如果不支持優(yōu)先級繼承,將互斥量的計數(shù)值設(shè)置為1。記錄互斥量的擁有者。9、判斷掛起的任務(wù)數(shù)是否只有一個, 如果只有一個設(shè)置互斥量掛起任務(wù)鏈表頭指針為 0。如果不只有一個,則從互斥量鏈表刪除恢復(fù)任務(wù)節(jié)

35、點。10、設(shè)置 cleanup為 null11、禁止搶占?;謴?fù)中斷。12、如果恢復(fù)任務(wù)啟動了定時器停止定時器。13、設(shè)置恢復(fù)任務(wù)的掛起狀態(tài)為success14、檢測互斥量是否支持優(yōu)先級繼承。如果支持優(yōu)先級繼承則做如下操作:a、互斥量掛起任務(wù)數(shù)量是否大于0?如果大于執(zhí)行b。等于 0 執(zhí)行 d。b、檢測任務(wù)掛起的數(shù)量是否大于1,大于 1 則調(diào)用互斥量優(yōu)先級排序接口改變優(yōu)先級。就是要把優(yōu)先級最高的任務(wù)放置到排序鏈表頭位置。然后向下執(zhí)行 c。c、如果等于 1,禁止中斷。判斷互斥量的掛起任務(wù)是否為0,如果不為 0,則設(shè)置互斥量最高等待優(yōu)先級為掛起任務(wù)的第一個任務(wù)。因為第一個任務(wù)已經(jīng)調(diào)用互斥量優(yōu)先級排序接

36、口,其優(yōu)先級已經(jīng)被設(shè)置為最高?;謴?fù)中斷。d、恢復(fù)占有任務(wù)的優(yōu)先級,恢復(fù)到占有任務(wù)占有的剩余互斥量中等待優(yōu)先級最高的優(yōu)先級。15、恢復(fù)任務(wù),是否發(fā)生搶占。16、發(fā)生搶占,則重新調(diào)度。17、不發(fā)生搶占,返回結(jié)束。開始關(guān)中斷當(dāng)前任務(wù)是否占有該互斥量并且互斥量數(shù)值大于1NY將互斥量計數(shù)值減 1互斥量計數(shù)值 >0?YY支持優(yōu)先級N繼承Y從占有任務(wù)占有的互斥量鏈表中刪除第此互斥量節(jié)點,同時修改頭指針位置恢復(fù)中斷獲取占有任務(wù)原始優(yōu)先級Y結(jié)束將互斥信號量存入任務(wù)擁有互斥量鏈表A禁止搶占禁止搶占恢復(fù)中斷恢復(fù)中斷獲取任務(wù)占有的下一個互斥量支持優(yōu)先級繼承判斷獲取到得下個互斥量值為 0YN改變互斥量最高等待優(yōu)先

37、級設(shè)置為最低互斥量的等待優(yōu)先級是否高于占有任務(wù)的原始優(yōu)先級Y要恢復(fù)的占有任務(wù)的優(yōu)先級和設(shè)置為占有任務(wù)恢復(fù)優(yōu)先級為更高的優(yōu)先級占有任務(wù)當(dāng)前優(yōu)先級是否一樣NNNY繼續(xù)獲取任務(wù)占有的下一個互斥量N調(diào)用互斥量改變優(yōu)先級接口改變占有任務(wù)優(yōu)先級Y禁止中斷關(guān)中斷從箭頭開始是對互斥量掛起的任務(wù)開始處理。上面處理是針恢復(fù)搶占恢復(fù)搶占對占有任務(wù)的處理恢復(fù)中斷互斥量掛起的任務(wù)數(shù) > 1?Y是否發(fā)生搶占調(diào)用互斥量優(yōu)先級排序接口Y重新調(diào)度禁止中斷NN恢復(fù)搶占結(jié)束B互斥量掛起的任務(wù)數(shù) = 0?YAN將互斥量設(shè)置為恢復(fù)任務(wù)占有互斥量鏈表中的第一個節(jié)點,并且恢復(fù)任務(wù)記錄自己的原始優(yōu)先級和閾值Y將互斥量掛起鏈表頭指針設(shè)置

38、為0N清除剩余 tick 值B獲取掛起鏈表中的第一個任務(wù)支持優(yōu)先級繼承Y保護(hù)互斥量以前的占有任務(wù)互斥量記錄恢復(fù)任務(wù)的優(yōu)先級和閾值判斷恢復(fù)任務(wù)占有的互斥量數(shù)量>0?Y將該互斥量插入到恢復(fù)任務(wù)占有的互斥量鏈表中N恢復(fù)任務(wù)占有的互斥量數(shù)量加1互斥量最高等待優(yōu)先級設(shè)置為最低互斥量計數(shù)值設(shè)置為 1記錄互斥量占有者掛起的任務(wù)只有 1個N從互斥量掛起鏈表中刪除恢復(fù)任務(wù)C互斥量掛起任務(wù)數(shù)量減 1禁止搶占禁止中斷恢復(fù)中斷設(shè)置互斥量的最高等待優(yōu)先級為掛起任務(wù)鏈表頭節(jié)點恢復(fù)任務(wù)啟動定時器恢復(fù)中斷Y停止定時器Y恢復(fù)占有任務(wù)的優(yōu)先級N恢復(fù)任務(wù)設(shè)置任務(wù)掛起狀態(tài)為成功支持優(yōu)先級繼承是否發(fā)生搶占YY互斥量掛起任務(wù)數(shù)量

39、=0重新調(diào)度N互斥量掛起任務(wù)數(shù)量 >1?NY調(diào)用優(yōu)先級排序接口結(jié)束CN將互斥量設(shè)置為恢復(fù)任務(wù)占有互斥量鏈表中的第一個節(jié)點,并且恢復(fù)任務(wù)記錄自己的原始優(yōu)先級和閾值Y將互斥量掛起鏈表頭指針設(shè)置為0N清除剩余 tick 值.互斥量優(yōu)先級改變接口B獲取掛起鏈表中的第一個任務(wù)支持優(yōu)先級繼承Y保護(hù)互斥量以前的占有任務(wù)互斥量記錄恢復(fù)任務(wù)的優(yōu)先級和閾值判斷恢復(fù)任務(wù)占有的互斥量數(shù)量>0?Y將該互斥量插入到恢復(fù)任務(wù)占有的互斥量鏈表中N恢復(fù)任務(wù)占有的互斥量數(shù)量加1互斥量最高等待優(yōu)先級設(shè)置為最低互斥量計數(shù)值設(shè)置為 1記錄互斥量占有者掛起的任務(wù)只有 1個N從互斥量掛起鏈表中刪除恢復(fù)任務(wù)C互斥量掛起任務(wù)數(shù)量減

40、 1禁止搶占禁止中斷恢復(fù)中斷設(shè)置互斥量的最高等待優(yōu)先級為掛起任務(wù)鏈表頭節(jié)點恢復(fù)任務(wù)啟動定時器恢復(fù)中斷Y停止定時器Y恢復(fù)占有任務(wù)的優(yōu)先級N恢復(fù)任務(wù)設(shè)置任務(wù)掛起狀態(tài)為成功支持優(yōu)先級繼承是否發(fā)生搶占YY互斥量掛起任務(wù)數(shù)量 =0重新調(diào)度N互斥量掛起任務(wù)數(shù)量 >1?NY調(diào)用優(yōu)先級排序接口結(jié)束C這個接口會在優(yōu)先級繼承時用到,改變占有任務(wù)的優(yōu)先級, 主要是任務(wù)獲取互斥量時若被掛起且掛起任務(wù)優(yōu)先級高于占有任務(wù),則要改變占有任務(wù)的優(yōu)先級到掛起任務(wù)。任務(wù)釋放互斥量時, 占有任務(wù)要恢復(fù)到原始優(yōu)先級或者是占有任務(wù)占有的剩余互斥量的最高等待優(yōu)先級時,也會調(diào)用此接口。此接口需要注意的幾點問題:1、要看要改變的任務(wù)狀態(tài)是否處于就緒狀態(tài)。2、如果任務(wù)不處于就緒態(tài),直接改變其優(yōu)先級即可。3、如果任務(wù)處于就緒態(tài),則此任務(wù)要從就緒態(tài)中刪除,同時設(shè)置下一個要執(zhí)行的任務(wù)。如果和該任務(wù)處于同一個優(yōu)先級的任務(wù)有多個則這個任務(wù)將會被恢復(fù)到同一個優(yōu)先級鏈表的末尾。 如果該任務(wù)優(yōu)先級鏈表中只有一個任務(wù),則此任務(wù)會被恢復(fù)到同一個優(yōu)先級鏈表的頭位置。4、此函數(shù)接口不會導(dǎo)致任務(wù)發(fā)生搶占。只是會改變下一個要被執(zhí)行的任務(wù),當(dāng)然下一個被執(zhí)行的任務(wù)有可能是剛剛被改變優(yōu)先級完成后的任務(wù),因為最后還要調(diào)度任

溫馨提示

  • 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

提交評論