隊列是為了任務(wù)與任務(wù)、任務(wù)與中斷之間的通信而準備的,可以在任務(wù)與任務(wù)、任務(wù)與中斷之間傳遞消息,隊列中可以存儲有限的、大小固定的數(shù)據(jù)項目。任務(wù)與任務(wù)、任務(wù)與中斷之間要交流的數(shù)據(jù)保存在隊列中,叫做隊列項目。隊列所能保存的最大數(shù)據(jù)項目數(shù)量叫做隊列的長度,創(chuàng)建隊列的時候會指定數(shù)據(jù)項目的大小和隊列的長度。
通常隊列采用先進先出(FIFO)的存儲緩沖機制,也就是往隊列發(fā)送數(shù)據(jù)的時候(也叫入隊)永遠都是發(fā)送到隊列的尾部,而從隊列提取數(shù)據(jù)的時候(也叫出隊)是從隊列的頭部提取的。但是也可以使用
LIFO 的存儲緩沖,也就是后進先出,FreeRTOS 中的隊列也提供了 LIFO 的存儲緩沖機制。
數(shù)據(jù)發(fā)送到隊列中會導(dǎo)致數(shù)據(jù)拷貝,也就是將要發(fā)送的數(shù)據(jù)拷貝到隊列中,這就意味著在隊列中存儲的是數(shù)據(jù)的原始值,而不是原數(shù)據(jù)的引用(即只傳遞數(shù)據(jù)的指針),這個也叫做值傳遞。UCOS
的消息隊列采用的是引用傳遞,傳遞的是消息指針。采用引用傳遞的話消息內(nèi)容就必須一直保持可見性,也就是消息內(nèi)容必須有效,那么局部變量這種可能會隨時被刪掉的東西就不能用來傳遞消息,但是采用引用傳遞會節(jié)省時間??!因為不用進行數(shù)據(jù)拷貝。
采用值傳遞的話雖然會導(dǎo)致數(shù)據(jù)拷貝,會浪費一點時間,但是一旦將消息發(fā)送到隊列中原始的數(shù)據(jù)緩沖區(qū)就可以刪除掉或者覆寫,這樣的話這些緩沖區(qū)就可以被重復(fù)的使用。FreeRTOS中使用隊列傳遞消息的話雖然使用的是數(shù)據(jù)拷貝,但是也可以使用引用來傳遞消息啊,我直接往隊列中發(fā)送指向這個消息的地址指針不就可以了!這樣當我要發(fā)送的消息數(shù)據(jù)太大的時候就可以直接發(fā)送消息緩沖區(qū)的地址指針,比如在網(wǎng)絡(luò)應(yīng)用環(huán)境中,網(wǎng)絡(luò)的數(shù)據(jù)量往往都很大的,采用數(shù)據(jù)拷貝的話就不現(xiàn)實。
1、多任務(wù)訪問
隊列不是屬于某個特別指定的任務(wù)的,任何任務(wù)都可以向隊列中發(fā)送消息,或者從隊列中提取消息。
2、出隊阻塞
當任務(wù)嘗試從一個隊列中讀取消息的時候可以指定一個阻塞時間,這個阻塞時間就是當任務(wù)從隊列中讀取消息無效的時候任務(wù)阻塞的時間。出隊就是就從隊列中讀取消息,出隊阻塞是針對從隊列中讀取消息的任務(wù)而言的。
比如任務(wù) A 用于處理串口接收到的數(shù)據(jù),串口接收到數(shù)據(jù)以后就會放到隊列 Q 中,任務(wù) A 從隊列 Q 中讀取數(shù)據(jù)。但是如果此時隊列 Q
是空的,說明還沒有數(shù)據(jù),任務(wù) A 這時候來讀取的話肯定是獲取不到任何東西,那該怎么辦呢?任務(wù) A
現(xiàn)在有三種選擇,一:二話不說扭頭就走,二:要不我在等等吧,等一會看看,說不定一會就有數(shù)據(jù)了,三:死等,死也要等到你有數(shù)據(jù)!選哪一個就是由這個阻塞時間決定的,這個阻塞時間單位是時鐘節(jié)拍數(shù)。阻塞時間為
0 的話就是不阻塞,沒有數(shù)據(jù)的話就馬上返回任務(wù)繼續(xù)執(zhí)行接下來的代碼,對應(yīng)第一種選擇。如果阻塞時間為 0~
portMAX_DELAY,當任務(wù)沒有從隊列中獲取到消息的話就進入阻塞態(tài),阻塞時間指定了任務(wù)進入阻塞態(tài)的時間,當阻塞時間到了以后還沒有接收到數(shù)據(jù)的話就退出阻塞態(tài),返回任務(wù)接著運行下面的代碼,如果在阻塞時間內(nèi)接收到了數(shù)據(jù)就立即返回,執(zhí)行任務(wù)中下面的代碼,這種情況對應(yīng)第二種選擇。當阻塞時間設(shè)置為portMAX_DELAY
的話,任務(wù)就會一直進入阻塞態(tài)等待,直到接收到數(shù)據(jù)為止!這個就是第三種選擇。
3、入隊阻塞
入隊說的是向隊列中發(fā)送消息,將消息加入到隊列中。和出隊阻塞一樣,當一個任務(wù)向隊列發(fā)送消息的話也可以設(shè)置阻塞時間。比如任務(wù) B 向消息隊列 Q
發(fā)送消息,但是此時隊列 Q 是滿的,那肯定是發(fā)送失敗的。此時任務(wù) B 就會遇到和上面任務(wù) A 一樣的問題,這兩種情況的處理過程是類似的,只不過一個是向隊列 Q
發(fā)送消息,一個是從隊列 Q 讀取消息而已。
4、隊列操作過程圖示
-
嵌入式
+關(guān)注
關(guān)注
5082文章
19104瀏覽量
304796 -
數(shù)據(jù)
+關(guān)注
關(guān)注
8文章
7002瀏覽量
88940 -
FreeRTOS
+關(guān)注
關(guān)注
12文章
484瀏覽量
62139
發(fā)布評論請先 登錄
相關(guān)推薦
評論