嵌入式軟件中基于棧的錯誤追蹤機制設計
嵌入式軟件開發往往缺乏必要的調試工具和調試手段,同時需要有較高的容錯處理能力,程序正常運行過程中盡量不因為出現異常而導致系統停止。一旦發生錯誤或異常,開發人員需要盡量多的錯誤環境信息來查找問題的原因。從程序編寫的角度來講,一般嵌入式軟件都采用C語言開發。C語言本身的特點決定了無法利用語言本身的功能實現對異常的跟蹤與處理,只能通過良好的編程模型與習慣,以及后期的大量測試,來發現和解決異常。因此,如何進一步提升程序開發中的可調試性,對于運行中的異常如何保存現場,從而方便進行異常追蹤等,是開發者需要考慮的重要問題。本文針對嵌入式C語言開發的特點,提出一種基于堆棧模式的異常追蹤編程模型,能夠實現有效的異,F場保存與恢復,并為后期的問題分析與解決打好基礎。同時,本文所提出的思路亦可作為實際運行階段提升可調試性的一種手段應用于嵌入式軟件編程中,最大限度實現對于異常發生環境的保存與定位,提升系統的可維護性! 1 建立全局錯誤代碼表 對于嵌入式軟件來說,盡量節省內存資源、降低程序代碼量是十分重要的。因此,將程序中所有錯誤、異常情況都進行了統一編碼,提高了錯誤處理代碼的規范化與可讀性。設計8位整數編碼格式如下: 每個錯誤代碼在程序中僅需要1個字節進行存儲。對于程序中每個可能異常的地方(如COM1沒打開),都設定1個唯一編號,當出現錯誤或異常時根據該編號可以直接定位到源程序對應文件和程序段,并確定錯誤類型! 〔捎缅e誤代碼的形式存儲錯誤信息,不僅可以精確描述錯誤的類型、位置等信息,還可以最大限度地節省寶貴的可執行內存資源,降低程序對內存的需求。 2 建立全局異常堆棧 在一個復雜的嵌入式實時系統中,程序處理流程復雜,不同資源之間往往在操作上存在著交叉。當出現程序錯誤或異常時,不能簡單地退出程序,而是應當盡量將錯誤處理掉,實在無法處理的錯誤應進行記錄,但整個程序的運行不應當中斷。對此,使用1個錯誤堆棧來保存錯誤信息。該棧用下面數組定義: ERROR_STACK為全局錯誤棧類型定義,MainErrStack為全局棧實例,其元素個數由ERR_STACK_SIZE確定。ErrorParm為字符數組,當錯誤發生時可以依次保存函數的人口參數以及異常發生之前局部變量的值等。實際數組長度ERR_ENV_LEN可以根據情況調整,一般情況下開發階段可以設置大一些,保證存放更多的錯誤信息用于調試;進入實際運行階段可以適當縮小該錯誤環境棧長度,減少內存空間的占用! 榱舜_保錯誤處理機制本身不會給程序引入新的異常,因此將堆棧的操作完全封裝為Push和Pop兩個函數,并引入當前堆棧指針stackCu-rrentPos(初始為一1表示堆棧為空,有效取值范圍為一1~ERR_STlACK_SIZE一1,該指針始終指向棧頂元素)。算法說明如下: 3 建立統一的錯誤描述字典表 為了進一步提高代碼規范化程度并降低內存需求,可以將每種類型的錯誤定義一個錯誤描述保存在單獨的文件或緩沖區中。當發生錯誤時,系統根據錯誤代碼取出該錯誤的詳細描述并顯示給用戶。以上操作可以封裝為ShowErrorMessage函數,定義為Char*ShowErrorMessage(int errorId)。在錯誤發生位置并不直接描述錯誤信息的方法,不僅可以降低可執行內存需求,而且避免了由于不同開發者對錯誤文字描述的差異而導致對用戶的提示信息不統一。例如錯誤提示“數組越下界!代碼:53017010”,530即表示數組越下界異常,17表示編號為“17”的C源程序文件,010表示文件中第10個錯誤位置。部分錯誤代碼描述示例如表1所列。 4 應用說明 下面以1個簡單的例子來說明本文方法的運行。假設程序需要提供1個通過GPRS發送數據的函數GprsSendData(char*ip,char*buf,int size),實現將buf緩沖區指定長度為size的字符串通過TCP方式發送到給定IP地址。示例代碼如下: 由上面可以看出,可能出現錯誤的位置都加入了錯誤壓棧操作,當GprsSendData函數的返回值為假時,上級調用函數會繼續將其異常時的運行狀態(局部變量、參數等)繼續壓棧,以此類推直到需要處理該異常的最頂級。開發人員后期調試時可以將棧頂元素依次出棧,構成一條完整的函數調用鏈,比較容易找出上述產生ip為空串的根本原因! ≡谲浖_發階段及運行的初期階段,適當加大錯誤堆棧容量,可以儲存更多信息輔助調試。隨著設備軟件可靠性、穩定性的增加,在正式投入運行后可以將異常棧設定為較小的容量,以降低存儲需求。 可以設想,若整個嵌入式軟件在開發中嚴格按照本文思路處理異常,應當可以很方便地進行異常的查找與處理。當嵌入式設備投入運行后,定期對該設備的錯誤棧進行分析,對于棧中存儲的錯誤信息進行及時處理,可以迅速有效地增加設備軟件的運行可靠性。一個經過嚴格測試的設備在絕大多數情況下錯誤棧應為空! 〗Y語 本文對于基于C語言的嵌入式軟件開發中的錯誤追蹤機制進行了詳細描述。該機制可以有效地降低軟件異常發生的概率,提升軟件的可靠性,減少開發成本。同時,該機制亦可以用于正常開發階段的輔助調試中,在關鍵程序段將環境信息壓棧實現后期分析,也為改進嵌入式軟件的調試手段提供了新的輔助思路。文中所述機制已經在作者主持的電力GPRS集抄終端的軟件設計中得到了實際應用,取得了良好的效果。 |