日期:2014-05-16 浏览次数:20430 次
之前想验证一些关于堆栈的问题,但是没什么好方法,printf实在局限,流于表面,只间表象(值、范围、规律)不见真身(地址、寄存器、过程),所以想到了gdb——一个强大的调试工具,还能看汇编代码,现在先把这两天学的常用的命令做一个小结,以后有用到的可能再来更新一下:
括号内为全称补全,缩写全称均可用。
例:(e)x(amine)表示既可以用x又可以用examine
(gdb)代表gdb环境命令行提示符。
关于缩写,非常类似Linux的shell中的tab功能,但是与shell不同的是有默认选择:
你不一定要写全,也不一定只写首字母,比如(gdb) layout 命令,如果写个l,那么缺省的是list,抢不过,写layout——又太麻烦,你只要写上la、lay、layo都行,抢不上槽没关系,只要有一点不同,就默认是你了。
1.进入gdb:
#gdb test -q(uiet)
其中test为目标可执行文件,-q代表不打印那一大串版本版权信息之类的刷屏字幕。
这里有个小常识就是用gcc编译目标文件test时,记得-g,表示可调试。
另外,直接进入gdb而未加载可执行文件,或者加载了目标文件,想换一个其他的——可以使用
(gdb)file test2
或者
(gdb)exec(-file) test2
2.断点的设立:
(gdb)b(reakpoints) <rowNums...>
<rowNums...>代表想要设立断点的行数
忘了哪行是什么?没关系,你可以用list
(gdb) list 1 #include<stdio.h> 2 int main() 3 { 4 int i = 10; 5 i = 11; 6 printf("the address of i is %p and the value of i is %d\n",&i,i); 7 } 8
另外,list也可以设置显示行数和指定位置的
(gdb)list
(gdb)list 10
(gdb)list 5,10
(gdb)func
比如默认显示10行,可以指定第5到第10行,指定显示某函数代码,等等。
不过最好的建议还是开俩终端,一边看代码,一边调试,看着舒服。
另外(gdb) layout
也可以显示程序代码,还是用框子圈起来的,高大上。
(gdb)b func
(gdb)b *func
在函数func()设立断点,星号代表进入前,插结果——一目了然~!
(gdb) b *main Breakpoint 1 at 0x80483e4: file testPC.c, line 3. (gdb) b main Breakpoint 2 at 0x80483ed: file testPC.c, line 4. (gdb) info b Num Type Disp Enb Address What 1 breakpoint keep y 0x080483e4 in main at testPC.c:3 2 breakpoint keep y 0x080483ed in main at testPC.c:4其中
(gdb)info b(reakpoints)
相当于列表打印所有已设立的断点。有了断点,当然也可以删掉断点,看到列表中左边的”Num“了么,用得上:
(gdb) d 1 (gdb) info b Num Type Disp Enb Address What 2 breakpoint keep y 0x080483ed in main at testPC.c:4 (gdb)(gdb)d(elete) Num
代表删除第Num个断点。可以看到第一个断点被删了。
3.基本调试流程:
有了断点,就该用上了。
第一步,开始运行程序:
(gdb)r(un)
(gdb)n(ext)
(gdb)s(tep)
和其他调试相仿,这两条分别代表step over和step in,
(gdb)c(ontinue)
run和continue功能其实差不多,都是继续往下运行,直到下一个断点停下来,不过场合不一样罢了:run是开始运行前的启动命令,continue是运行中的命令。
4.汇编style: