本文主要介绍WinDbg的入门知识,包括:下载安装、启动、配置和简单的用户模式调试示例。在我学习WinDbg的过程,主要参考了“WinDbg软件自带的用户手册”和http://www.dbgtech.net/blog/。其中,dbgtech网站的作者还制作了“http://www.dbgtech.net/windbghelp/”,在线的中文windbg帮助文档。
一、下载安装
1,搜索网址
通过Mircrosoft的bing搜索“windbg”即可获取windbg的下载地址:
https://developer.microsoft.com/en-us/windows/hardware/windows-driver-kit
2,安装“VS2015+WDK10”
该网址提供了VS2015和WDK10的下载链接。在win10系统下,需要先安装VS2015,选择自定义安装,并主动选择安装C++相关组件,然后再安装WDK10。windbg已经集成到了windows kits中,通过这样的安装形式,即可在开始菜单的“Windows Kits”中找到windbg的启动项。
3,windows键启动
此外,安装好“VS2015+WDK10”后,也可以通过“win+R”,直接输入“windbg”启动windbg.exe。在win10 64位系统下,默认启动的是64位的windbg.exe,而在开始菜单中,是可以选择启动32位的windbg.exe的。
二、配置
WinDbg的环境配置包括:符号、源码和可执行映像的路径设置,如下图,点开WinDbg的File菜单,即可设置。在使用调试器之前,我们需要先配置好这些路径,以便调试器能够识别调试目标中的各种变量、函数等等,这样我们在调试器中看到的就不是一堆二进制和汇编代码,而是更易理解的函数和变量。
1,symbol file path
我们知道,程序运行需要将相关二进制文件(包括.exe和.dll文件)加载到内存地址空间,即内存映射文件。内存映射文件包含的是二进制信息,我们在调试时看起来会比较困惑,所以,我们需要一批跟这些二进制文件配套的符号文件(后缀名为“*.pdb”)供调试时使用,它包含函数名、变量名等各种符号和调试信息,实际程序运行并不需要它。
百度百科:http://baike.baidu.com/view/3788304.htm
symbol file一般包括两类,一类是我们自己的程序的.exe和.dll文件的对应.pdb文件,另一类是系统dll的符号文件,如kernel32.dll等。我们把系统dll的符号文件称为“Mircrosoft公共符号文件”。
1)Symbol Server
对于Mircrosoft公共符号文件,我们一般使用“ cache* + srv* ”,即设置为在线服务器,并缓存部分文件到本地主机。这样就不用每次都从在线服务器去下载符号文件了,而只是更新部分符号文件。
为此,我们需要先新建一个本地缓存文件夹,我的是:F:\SymbolCache
然后,将该路径设置为系统环境变量,这样可以省去每次都重新设置的麻烦。
a. 将windbg的安装路径添加到系统path中
该路径下需要包含“symsrv.dll”和“symstore.exe”两个文件,分别用于symbol server和cache。
b. 新增系统环境变量项:_NT_SYMBOL_PATH 值为: SRV*F:\SymbolCache*http://msdl.microsoft.com/download/symbols
具体可以在help文档中搜“symbol”,查看“symbol file and symbol path”。
2)目标程序符号文件
直接通过命令“.sympath+ ”设置目标程序符号文件路径即可。
2,源码路径
直接通过命令“.srcpath ”设置目标程序源码文件路径即可。
3,可执行映像文件(Image File)
主要用于调试dump文件,可以直接通过命令“.exepath ”,将待调试的.exe、.dll或.sys的路径设置进去即可。
注:当各个路径设置好后,需要运行“.reload”命令来加载各个符号和源码。
三、启动
我在次先以最简单的用户模式应用程序为例,参考help文档的“Getting Started withWinDbg(User-Mode)”这一篇。
一般地,我们只需配置上面的环境变量(公共符号文件路径)即可。其他的东西,可以在调试时,手动输入命令。
1,选择可执行文件
启动windbg -> 点开File菜单 -> 选择“Open Executable...”,选中待调试的exe文件即可。
2,输入下列三个命令
.sympath srv*
.sympath+ C:\MyAPP\x64\Debug
.srcpath C:\MyApp\MyApp
.reload
注:windbg中以“点号,.”开头的命令,都是配置环境的命令。
3,用“x MyApp!*”检查相关符号的加载情况
“*”,星号在windbg中属于通配符。
“!”,叹号在windbg,一般位于模块名后,其分隔模块名和模块内符号名的作用。
叹号在最前面,表示这是一个扩展命令,如:“!analyze -v”。
4,清屏“.cls”
四、调试help文档中的MyApp.exe示例
参考help文档的“Getting Started withWinDbg(User-Mode)”这一篇的示例,我新建了一个win32 console程序,名为“TestDebug2”。
1,打开TestDebug2.exe
从上图可以看到,执行到汇编命令“int 3”。google汇编命令int,可知,它是一条中断命令,其中后面的数字表示中断类型。(int - interrupt)
2,输入下面三个命令
.sympath srv*
.sympath+ ...
.srcpath ...
0:000> .sympath srv*
Symbol search path is: srv*
Expanded Symbol search path is: cache*;SRV*https://msdl.microsoft.com/download/symbols
************* Symbol Path validation summary **************
Response Time (ms) Location
Deferred srv*
0:000> .sympath+ D:\DriverDev\WinDbg\Exercise\TestDebug2\x64\Debug
Symbol search path is: srv*;D:\DriverDev\WinDbg\Exercise\TestDebug2\x64\Debug
Expanded Symbol search path is: cache*;SRV*https://msdl.microsoft.com/download/symbols;d:\driverdev\windbg\exercise\testdebug2\x64\debug
************* Symbol Path validation summary **************
Response Time (ms) Location
Deferred srv*
OK D:\DriverDev\WinDbg\Exercise\TestDebug2\x64\Debug
0:000> .srcpath D:\DriverDev\WinDbg\Exercise\TestDebug2\TestDebug2
Source search path is: D:\DriverDev\WinDbg\Exercise\TestDebug2\TestDebug2
************* Symbol Path validation summary **************
Response Time (ms) Location
OK
从上面的log可以看出,每次输入配置命令,调试器都会检查symbol path。其中,deferred表示延迟载入。也就是说,暂时先不载入这些模块,待调试到了该模块内的符号时,才真正载入该模块。
4,载入
.reload
5,设断点并运行
bu TestDebug!main
bl
g
通过Go命令,运行后,右边的汇编窗口可以看反汇编代码(它是调试器从二进制代码推测出来的),同时会打开源码窗口。左边的命令窗口可以看到当前执行的命令。
6,单步调试
按F10或F11进行单步调试,同VS的调试器。
在单步过程中,可以通过view菜单打开“Locals”窗口查看局部变量,“Watch”窗口监视某变量,“Memory”窗口看内存,“Call Stack”窗口看调用堆栈,等等。这些功能都类是VS的调试器。
7,通过命令方式
k —— 查看堆栈
dv —— 查看变量 d -display
注:所有的这些命令,都可以在help文档中进行搜索。
8,bug分析
该示例程序,设计了一个被0除的bug,运行到该处时,调试器会中断,这时,可以输入扩展命令
“!analyze -v”
查看调试器对该bug的详细分析信息,包括:
1)bug类型
2)bug发生的位置
3)当前堆栈
等等