還在用延時函數嗎——那你就out了
就像每一個開始學習編程語言的人寫的第一個程序都是“Hello World!”一樣,幾乎每一個學習單片機的同學接觸到的第一個程序都是點燈程序,幾乎每一本介紹單片機學習的教材也都是從這樣一個程序開始,幾乎每一個工程師學習一類新的單片機時也是從這個程序開始的。如下圖所示,就是一個典型的單片機點燈程序的框架,LED以一秒為周期循環閃爍下去。還有很多以此程序拓展開來的,如流水燈,呼吸燈等等。
本文引用地址:http://www.104case.com/article/233787.htm
延時函數結構簡單,條理清晰,這個程序作為單片機初學者或者初學一類單片機來說,無疑是非常好的,但在實際使用過程中使用這樣的程序框架,程序的執行效率肯定不會很高,程序99%以上的時間都在忙著空轉。
那么,我們怎樣才能將這些無用功節省掉,把浪費掉的時候收回來做一些有益的事情呢?下面是筆者的一些思路。
一、前后臺程序
前后臺模式的程序是大家最常用到的,也是最簡單的嵌入式程序架構。它分為前臺程序和后臺程序。應用程序采用一個無限循環,在循環中調用相應和函數,來完成相應的操作,這部分程序可看作是后臺行為。前臺程序通過中斷來實現,即中斷服務程序。一般情況下,后臺程序也叫任務級程序,前臺程序也叫事件處理級程序。
前后臺程序也可以與程序調度相結合,在程序運行時,后臺程序檢查每個任務是否具備運行條件,通過一定的調度算法來完成相應的操作。對于實時性要求特別嚴格的操作通常由中斷來完成,僅在中斷服務程序中標記事件的發生,不再做任何工作就退出中斷,經過后臺程序的調度,轉由前臺程序完成事件的處理,這樣就不會造成在中斷服務程序中處理費時的事件而影響后續和其他中斷。
狀態機是軟件領域中的一個重要概念,在嵌入式裸機編程中,狀態機的地位尤其重要。幾乎所有的嵌入式任務都可以被看做狀態機來處理。比如一個按鍵處理過程,可以看做一個狀態機,一個細小的擊鍵動作包含了:釋放、抖動、閉合、抖動和重新釋放等狀態,每個狀態對應不同的處理程序,狀態切換可以通過每隔一段時間(定時器)去檢查按鍵狀態來實現。每個狀態之間的時間間隔可以去處理其他任務,而不必采用延時函數函數來等待下一個狀態的到來。
三、合作式調度器
調度器,一方面可以看作一個簡單的操作系統,允許以周期性或(很少地)單次方式來調用任務。另一方面,從底層來看,調度器可以看作是一個由許多不同任務共享的定時器中斷服務程序,多個不同的任務,可以使用同一個調度器來調度完成。調度器主要分了兩大類:合作式調度器和搶占式調度器。
合作式調度器是一種單任務的系統結構,在任一時刻只有一個任務是活動的,直到這一任務運行完成之后,調度器控制調用下一個任務。在合作式調度器中,任務在特定的時刻被調度運行;當一個任務需要運行時,會被添加到等待隊列;當CPU空閑時,運行等待隊列中的下一個任務;任務一旦被執行,不被中斷,直到任務執行完成;此后CPU交還調度器控制,去執行下一個任務。
一、搶占式調度器
搶占式調度器是一種多任務的系統結構,我們平常接觸到的商用嵌入式操作系統如UCOS等一般屬于搶占式調度系統。在搶占式調度器中,任務在特定的時刻被調度運行;當任務需要運行時,被添加到等待隊列中;等待的任務運行一段固定的時間,如果沒有完成,將被暫停并放回到等待隊列中,然后下一個等待任務將運行一段固定的時間。
這類調度器相對復雜,通常作為一個獨立的操作系統來處理,它可以對外部事件快速響應,可“并行地”處理多個不同任務。
本文簡單介紹了幾種不同的單片機程序框架,由于篇幅問題,不能一一詳細解釋,以后有機會將詳細解釋,并一一給出實例。
評論