天天看點

Visual Studio調試之斷點進階篇

總之,這裡我們隻要知道,CPU在執行程式指令過程中,碰到INT 3中斷程式的執行,CPU然後去IDT表裡面找到處理斷點的例程入口。這個例程要做的事情就是:

1.       先看看機器裡面是不是安裝了一個調試器—記住,這一步很重要,之是以重要以後的文章裡面會介紹。

2.       如果機器裡面沒有安裝調試器,那麼作業系統就會終止程式的執行。

3.       否則作業系統啟動調試器,并将調試器附到程序上。

4.       這樣,我們才能在調試器裡面檢查程式内部變量的值。

前面文章裡面的INT 3 (或者DebugBreak(),或者Debugger.Break())指令是我們自己在代碼裡面寫死進去的,是以我們在Visual Studio裡,在相應的代碼行裡面點一下,出現一個小紅球,也就是說Visual Studio在程式指令集某個地方動态地添加了一個INT 3指令。現在的問題來了,Visual Studio是如何在程式中正确找到插入INT 3指令的位置的?

或者更具體一些,我們在源代碼(文本檔案)裡面設定斷點的,Visual Studio需要把代碼行翻譯成在程式指令集中的位置。Visual Studio之是以需要做翻譯,是因為通常一行C++或者 C#代碼都會對應好幾行彙編指令。

是以,Visual Studio需要一個額外的檔案來執行這個翻譯過程,這個額外的檔案叫做調試符号檔案(Symbols),是由編譯器生成的。Visual Studio系列的編譯器,不論是C#、VB.NET還是C++編譯器都會生成這個調試符号檔案,.pdb 檔案。是以如果你花一點時間看看Debug檔案夾的話,你就會發現這個檔案。

是以我們來看看Visual Studio支援的各種斷點,并解釋各種斷點的實作方式

首先我們先看看如何設定條件斷點,條件斷點有兩種,一種是根據觸發的次數來設定,另外一種是根據一條預置的條件來設定。

根據觸發次數設定

比如說,你有一個循環,循環1000次,你知道有一個BUG總是在500次之後才會出現,是以肯定希望在循環内設定一個斷點,但是前面500次都不會觸發這個斷點,否則連續按500次的F5的确不是一件輕松的差事。

根據預置條件來設定

如果你已經知道一些條件可能會引發Bug,那麼根據條件來設定則最合适不過了。如下圖所示:

在“斷點條件(Breakpoint Condition)”對話框裡面,隻需要輸入一條正常的C#、C++或者VB.NET的語句就可以了(當然,文法是根據你項目裡面的源代碼文法一緻),這條語句的要求是必須傳回bool值—否則就不是一個條件了。

第三個還有斷點過濾器,當你在斷點上,右鍵點選彈出的菜單裡面,會有一個“過濾(Filter)”菜單,它允許你限制将斷點僅設定在特定的線程上。這裡我就不細講了,有興趣的話,可以自己寫一個多線程或者多程序程式試試這個功能。

知道斷點的原理以後,了解條件斷點應該就不會是問題了。

有的時候,你可能需要檢視程式内部一些變量的值,但是你又不希望中斷程式的執行。例如你在調試一個網絡協定棧,一個程式可能在接收資料包,你想看看資料包的格式,但如果中斷程式的執行,會導緻後續的資料包丢失。

是以,我們一般的做法就是在源代碼裡面加一些日志記錄代碼,這樣可以将一些變量的值記錄下來,以便後續分析。如果日志在産品釋出以後還需要的話,在源代碼裡面加入這些日志代碼固然是一個好主意,但是如果你隻是想臨時看看一些變量的值呢?

這個時候,監視斷點就很有用了,Visual Studio的監視斷點就可以讓你做到在不修改程式源代碼的前提下,在調試器視窗中列印一些變量的值。

下圖示範了監視斷點的用法:

設定監視斷點的步驟,或者說是注意事項吧:

1.       設定一個普通的斷點

2.       右鍵單擊剛剛設定的斷點,在彈出菜單裡面選擇“When Hit…”

3.       鈎選 第一個“列印一條消息(Print a message)”複選框,輸入一串文本,預設情況下,你輸入的文本會被直接列印到調試的輸出視窗裡面來。除了:

a.       以$符号開頭的幾個關鍵字。比如$FUNCTION就會被替換成斷點所在的函數名。其他有一些關鍵字在“When Breakpoints Is Hit”視窗當中有詳細的說明。

b.      使用 大括号 {}包含起來的變量名,這樣的字元串會被替換成變量的值。

這下面就是監視斷點的效果,注意,你隻能在Visual Studio的“輸出(Output)”視窗中檢視結果。

監視斷點相對于日志記錄的好處是,你不需要改動源代碼,并且重新編譯代碼。實際上Visual Studio實作監視斷點的原理也很簡單,就是插入一個普通的斷點,斷點觸發之後處理并且列印在“When Breakpoints Is Hit”視窗輸出的表達式,最後自動恢複程式的執行。

本文轉自 donjuan 部落格園部落格,原文連結:http://www.cnblogs.com/killmyday/archive/2009/09/27/1574919.html   ,如需轉載請自行聯系原作者