1. 首頁
  2. 科普知識

在C語言中用ASSERT除錯的八個技巧

在C語言中用ASSERT除錯的八個技巧

C語言中的ASSERT(斷言)宏是嵌入式軟體開發人員可以使用的最好的除錯工具之一。面小編給大家介紹在C語言中用ASSERT除錯的八個技巧,歡迎閱讀!

在C語言中用ASSERT除錯的八個技巧

技巧1:記住ASSERT的定義

對許多開發人員來說,斷言是一個令人困惑的話題,因為它們的許多使用方式與其設計初衷背道而馳。我見到的最清晰的斷言定義是這樣的:

“斷言是在程式某個特定點的一個布林表示式,除非程式中有缺陷(Bug),否則它的值將為真。”

想要理解上述斷言定義的開發人員應該留意下面三個要點:

·斷言會評估一個表示式是真還是假

·斷言是在程式碼中的某個點對系統狀態的一種假設

·斷言會驗證系統假設,如果不為真,就表明程式碼中有一個缺陷

技巧2:使用ASSERT驗證函式的先決條件

斷言非常適合契約式設計環境,在這種環境中,開發人員非常清晰地定義了某個函式的先決條件。斷言可以用來檢查該函式的輸入是否滿足先決條件。就拿圖1所示的程式碼片段為例:

圖1:函式的先決條件

函式的State輸入應該在定義的系統狀態範圍內。如果State不是有效的狀態值,那麼它就不是錯誤,而是缺陷!斷言可以用來驗證State是有效的假設,如圖2所示:

圖2:對函式先決條件應用斷言

在State不小於最大值的事件中,斷言表示式將被評估為假,程式於是將停止執行。停止程式執行可以讓開發人員很容易馬上看到哪裡的程式碼出錯,而不是過段時間以後才知道。

技巧3:使用ASSERT驗證函式的後置條件

斷言也能用來驗證契約式設計環境中對某個函式輸出的假設。例如,如果前面定義的System_StateSet函式返回SystemState變數,開發人員可以預計它也在期望的範圍之內。斷言可以用來對缺陷進行監視,如圖3所示。

圖3:對函式後置條件應用斷言

開發人員在檢視上述程式碼後可能會感到這些檢查毫無意義。剛剛才設定好的SystemState怎麼就會出現大於SYSTEM_STATE_MAX的值呢?答 案是這確實不應該出現,然而有時候會莫名其妙地發生改變,也許是透過中斷或並行執行緒,此時斷言可以立即標誌出這個缺陷。

技巧4:不要把ASSERT用於錯誤處理

在記住斷言定義之後,開發人員應該切記:斷言是用於檢測缺陷的,不能用於錯誤處理。錯誤處理是設計用於響應錯誤的使用者輸入和意外的事件順序的軟體。錯誤在系 統中預料是會發生的,但僅僅是因為有無效的輸入而並不意味著程式碼中有缺陷。錯誤處理應該與缺陷尋找分開來。錯誤使用斷言的一個典型例子是,在試圖開啟一個 檔案用於讀取時去檢查檔案的指標,如圖4所示。

圖4:ASSERT的不當使用

讀者可以清楚地看到,試圖開啟檔案的結果與檔案系統的狀態和使用者資料有關,而與程式碼中的缺陷一點關係也沒有。開發人員應該編寫錯誤處理程式,而不是用斷言,以便在檔案不存在時,錯誤處理程式可以用一些預設可用資料來建立它,以便後續程式碼繼續操作。

技巧5:ASSERT僅對開發有意義,不能用於生產

開發ASSERT宏的原始意圖是在開發過程中啟用它,在後面生產時要禁用。可以用NDEBUG宏啟用和禁用ASSERT。正確實施的斷言在被禁用後應該對嵌入式系統基本沒有影響。

問題是,如果測試是在斷言啟用的情況下進行的(為了捕捉任何缺陷,應該這樣做),那麼現在禁用斷言將導致交付的產品與測試的產品處於不同的狀態。斷言確實會 佔用一些程式碼空間,但更重要的是,它們需要佔用少量的時鐘週期來評估它們的布林表示式。禁用ASSERT可能對具有有限資源的裸機系統的執行時序產生很大 影響,從而導致在生產系統中產生新的缺陷。開發團隊需要判斷是否值得冒關閉斷言的風險。

一種替代方案是保留斷言在啟用狀態,而將它們的輸出重定向到一個系統日誌。這樣可以確保任何揮之不去的缺陷很容易被識別,而且能避免中止系統的執行,而中止系統可不是明智之舉。

技巧6:不允許斷言有副作用

ASSERT 的預設實現允許開發人員包含一段可執行程式碼作為布林表示式的一部分。舉例來說,一個狀態變數可以被實現為表示式的一部分並傳遞給ASSERT。但如果傳遞 給ASSERT的.表示式有副作用,也就是說,它會改變嵌入式系統的狀態,那麼禁用斷言將改變系統的行為。開發人員應該確保他們的表示式沒有副作用,否則他 們需要冒險在系統中增加只針對產品程式碼喚醒的休眠時間缺陷。

技巧7:斷言應該佔程式碼的1%至3%

每 個開發人員對於程式碼庫(Code Base)中應該有多少個斷言都有自己的主見。大家一致同意的一個數字是,程式碼庫中的斷言佔比應該大於0。斷言為開發人員提供了一種在程式碼庫中發生缺陷的 時刻發現它的好方法。除錯是在開發嵌入式系統中最浪費時間並令人沮喪的事情之一。不管開發人員認可的佔比是1%、3%還是5%,使用斷言肯定對你有利,並 會使開發嵌入式軟體變得多少有些趣味。

技巧8:將斷言用作可執行程式碼註釋

斷言可以生成極好的註釋!編寫出色的表示式可以確切地告訴開發人員在程式碼的某個給定點應該預料發生什麼事情。開發人員應該做好他們斷言的架構,幫助人們更清楚地理解系統中發生的事情,進而幫助減少缺陷。