筆記|軟體除錯的技巧

javaadu發表於2019-07-07

這篇文章是《除錯九法:軟硬體錯誤的排查之道》的閱讀筆記。這本書的主旨,是介紹如何修復bug:找出bug發生的原因、並給出修復方案。

除錯bug的九個規則列舉如下,建議將這個清單列印出來,擺放在工作時候能看到的地方。除錯九法

除錯規則

接下來一次看下每個規則的核心理念,從名字上來看,每個規則看起來都比較明顯(PS:由於翻譯的問題,有些詞可能沒那麼容易理解),但是理解這些規則和應用這些規則中間還是差了很多距離的。

規則1:理解系統

你必須掌握系統的工作原理以及它是如何設計的,在某些情況下還要知道為什麼這樣設計。如果你沒有理解系統中的某個部分,那麼這通常是出問題的地方。(這不僅僅是墨菲定律的問題,如果你不能理解你所設計的系統,你的工作可能會變得一團糟)。

如何理解系統呢?

  • 閱讀手冊
  • 逐字逐句閱讀手冊,仔細理解每個細節
  • 知道什麼是正常的,知道什麼是正常的可以幫助你注意到什麼是不正常的
  • 知道工作流程,要理解業務,要講系統的工作過程對應到具體要解決的現實問題
  • 選擇合適的工具,選擇合適的輔助(監控、插樁)工具可以幫你理解系統
  • 查閱細節,經驗有時候會騙人,記憶有時候會出錯

規則2:製造失敗

這一點比較容易理解,就是問題復現,在日常工作中,你在排查一個問題的過程中,最重要的一步就是復現問題——能復現的問題都能解決。

這裡有幾個要點需要注意:

  • 引發失敗,而不要模擬失敗,不要嘗試用不同的方式去模擬問題,而要模擬和構建引發bug發生的條件
  • debug的動作,不要影響錯誤的發生方式,可以影響錯誤的發生頻率
  • 從頭開始,需要有一個正常的狀態到不正常的狀態的過程,從開始正常的狀態開始觀察,直到問題發生;
  • 終極方案,控制變數法,將可能引發錯誤的因素依次排除;排除所有可能的原因後,剩下那個答案,無論多麼不可思議,都是事實。

規則3:不要想,而要看

親眼看到底層的失敗是非常重要的,如果你猜測失敗是如何發生的,那常常會修復一些根本不是bug的問題。

在軟體世界裡,觀察意味著設定斷點、新增除錯語句、監視程式值以及檢查記憶體;在醫學領域,需要測試血樣和進行X光透視。

對細節的觀察應該到什麼程度合適呢?簡單的答案是:一直觀察,直到把問題的原因鎖定在幾種可能之內。

在系統設計的時候,就要考慮到將來除錯、排查問題的情況,將日誌視為系統設計的一部分—列印一些關鍵日誌,或者設計一些開啟日誌的開關,以便在生產環境針對某個case進行除錯。

日常生活中有很多插樁的case:

  • 體溫計測量體溫
  • 自行車輪胎漏氣時,都是將輪胎打滿氣,然後放在水裡檢查哪裡漏氣
  • 天然氣中加入了臭雞蛋的氣味

規則4:分而治之

反覆將問題分成好的一半和壞的一半,然後縮小搜尋範圍,然後進一步研究有問題的那一半鏈路。

規則5:一次只改一個地方

初中就學過的控制變數法。
在修改bug時候,如果某個改動沒有修復bug,就應該立即把它改回來。

規則6: 保持審計跟蹤

記下你的每步操作、順序和結果;
魔鬼藏在細節中;
將一些事情關聯起來思考;
好記性不如爛筆頭;

規則7:檢查插頭

一些顯而易見的假設可能是錯誤的;是不是執行了正確的程式碼?是不是打了正確的包?插頭是不是掉了?從一些最基本的問題開始確認,很多時候問題就出在這裡。對自己使用的工具進行測試,因為工具也是一種軟體,難保不會出問題。

規則8:獲得全新觀點

“要想重新理清一個案子的頭緒,最好的方法就是把它講給別人聽。” ——福爾摩斯,《銀色馬》

向別人解釋問題的過程,會讓你對問題進行重新的梳理和理解,這時候可能發現之前沒有發現的問題。

bug發生了,以除掉bug為自豪,而不是非得以自己除掉bug才自豪。

不管你是跟什麼人求助,或者需要別人什麼樣的幫助(徵求意見、獲取專業知識、聽取經驗),在向別人描述問題的時候,一定要記住一件事——報告症狀、而不是講你的理論;另外,有些症狀你可能不是十分確定,也可以描述出來。

規則9:如果你不修復bug,它將依然存在

“當危險已經離你很近時,拒絕承認它並不是勇敢的表現,而是愚蠢。” ——福爾摩斯,《最後一案》

如果你不修復bug,它不會自動消失。按照前面的規則解決問題後,要進行一次迴歸驗證,確保已經修復問題,並且沒有引入新的問題。

我的感想

這本書裡的很多案例都是是硬體相關的,對於軟體開發工程師來說不太熟悉,不過在閱讀的過程中,建議可以想想自己在工作中排查問題的場景,是不是按照一定的章法去排查的?有沒有從最基本的假設開始確認?有沒有查閱文件?有沒有關注本次變更的內容?有沒有按照二分法進行排除?

作為軟體開發工程師,在實際工作中很少有機會從0開始構建一個系統,更常見的情況是接手維護一個已經執行了幾年、經歷了幾代的系統。寫程式碼只是工作中的一部分,還有很多其他的事情需要做:修復bug、需求評審、系分評審、專案排期等等。

修復bug(解決問題)的能力,是軟體工程師的核心競爭力之一。在最開始的工作中,有時候會羨慕老司機的“直覺”——看到一個錯誤日誌,就大概知道是哪裡有問題,後來自己查問題查得多了之後,自己也get到了這種“直覺”,也理解了——這不是直覺,這是已經被實踐驗證過很多次的經驗,即使這樣,我也會告誡自己——不能完全依賴這種經驗,經驗有助於縮小待驗證的範圍,還是需要事實(重現問題)去證實前面的猜測。


本號專注於後端技術、JVM問題排查和優化、Java面試題、個人成長和自我管理等主題,為讀者提供一線開發者的工作和成長經驗,期待你能在這裡有所收穫。javaadu

相關文章