如果將所有任務都設定在相同的優先順序,那麼在系統跑起來之後,所有任務將進行輪盤式的排程。如果任務僅僅具有不同的優先順序而沒有經過其他處理時。高優先順序的任務將一直重複執行,將低優先順序的任務「餓死(starved))」。
事件驅動:
為了使我們的任務切實有用,我們需要通過某種方式來進行事件驅動。乙個事件驅動任務只會在事件發生後觸發工作(處理),而在事件沒有發生時是不能進入執行態的。排程器總是選擇所有能夠進入執行態的任務中具有最高優先順序的任務。乙個高優先順序但不能夠執行的任務意味著不會被排程器選中,而代之以另乙個優先順序雖然更低但能夠執行的任務。因此,採用事件驅動任務的意義就在於任務可以被建立在許多不同的優先順序上,並且最高優先順序任務不會把所有的低優先順序任務餓死。
1 阻塞態 blocked:
任務可以進入阻塞態以等待以下兩種不同型別的事件:
1. 定時(時間相關)事件——這類事件可以是延遲到期或是絕對時間到點。比如說某個任務可以進入阻塞態以延遲10ms。
2. 同步事件——源於其它任務或中斷的事件。比如說,某個任務可以進入阻塞態以等待佇列中有資料到來。同步事件囊括了所有板級範圍內的事件型別。
任務可以在進入阻塞態以等待同步事件時指定乙個等待超時時間,這樣可以有效地實現阻塞狀態下同時等待兩種型別的事件。
我們可以利用阻塞態進行相應的延時操作提高系統的效率,原來使用for迴圈或者while迴圈進行延時,處理器進行的都是很多無用的操作。使用阻塞態進行延時時,處理器可以處理其他任務。從而提高了系統的效率。呼叫vtaskdelay() api 函式來代替空迴圈即可。
void vtaskdelay( portticktype xtickstodelay );
xtickstodelay 延遲多少個心跳週期。呼叫該延遲函式的任務將進入阻塞態,經延遲指定的心跳週期數後,再轉移到就緒態。
舉個例子,當某個任務呼叫vtaskdelay( 100 )時,心跳計數值為10,000,則該任務將保持在阻塞態,直到心跳計數計到10,100。
常數 porttick_rate_ms 可以用來將以毫秒為單位的時間值轉換為以心跳週期為單位的時間值。
2 掛起狀態 (suspended))
。讓乙個任務進入掛起狀態的唯一辦法就是呼叫vtasksuspend() api 函式;而把乙個掛起狀態的任務喚醒的唯一途徑就是呼叫vtaskresume() 或vtaskresumefromisr() api 函式。大部分應用程式都不需要進入掛起狀態。不在詳細贅述。
3 就緒狀態 (ready)
任務處於非執行狀態,但既沒有阻塞也沒有掛起,則這個任務處於就緒(ready,準備或就緒)狀態。處於就緒態的任務能夠被執行,但是沒有執行。當前狀態的任務已經具有了所有可執行的條件,只等待處理器將他進行排程。
其他延時函式:
vtaskdelayuntil() api 函式的引數就是用來指定任務離開阻塞態進入就緒態那一刻的精確心跳計數值。api 函式vtaskdelayuntil()可以用於實現乙個固定執行週期的需求(當你需要讓你的任務以固定頻率週期性執行的時候)。由於呼叫此函式的任務解除阻塞的時間是絕對時刻,比起相對於呼叫時刻的相對時間更精確(即比呼叫vtaskdelay()可以實現更精確的週期性)。
FreeRTOS學習(二)任務基礎
2.任務基礎知識 在嵌入式開發中,有兩種常見的開發方式 前後臺系統和嵌入式作業系統。1.1 前後臺系統 前台 就是中斷,可以多級巢狀,處於處理一些實時性要求比較高的事件,比如按鍵的狀態獲取。後台 乙個無限迴圈,在迴圈中呼叫相關函式完成相應操作。這種程式設計方式的主要缺陷在於兩方面 1 複雜度方面 無...
FreeRTOS學習(三)任務管理
2.任務刪除 3.任務掛起與恢復 4.任務相關api freertos 提供了多種任務建立的api,這裡主要列舉了動態建立和靜態建立 函式 api 功能描述 xtaskcreate 動態建立,堆疊由 freertos 動態分配 xtaskcreatestatic 靜態建立,堆疊由使用者指定分配 1....
FreeRTOS學習(五) 任務相關API函式
宣告及感謝 跟隨正點原子資料學習,在此作為學習的記錄和總結 環境 keil stm32f103 api函式預覽 1.ubasetype t uxtaskpriorityget taskhandle t xtask 獲取某個任務的優先順序 引數 xtask 傳入任務控制代碼 unsigned port...