gdb
gcc 编译选项加上 –g ,这样生成的目标代码中就添加了调试信息。
gcc –g –o hello hello.c
redhat 6.3 默认是不安装gdb的,如果安装从系统光盘(ios镜像文件),将其解压在Packages文件夹下找到 gdb-7.2-56.el6.i686.rpm,然后执行以下命令:
rpm -ivh gdb-7.2-56.el6.i686.rpm(因为版本不同数字部分可能不同)
1. 启动GDB
指令:gdb 程序名[corefile]
corefile是可选的,但能增强gdb的调试能力
Linux默认是不生成corefile文件的,所以需要在.bashrc文件中添加一样代码 ulimit –c unlimited .bashrc文件在宿主目录下(修改玩.bashrc 文件后记得执行 ..bashrc让修改生效)
corefile 文件在程序运行出错的时候 保存程序的内存信息(gdb调试的是运行时候出现的错误,代码的错误由编译器负责)
先写一个有错的程序:
对其进行编译
编译器并没有报错
再看其运行的时候
由于操作了空指针,所以程序会出错,同时在当前目录下生产一个corefile文件
现在结合corefile 用gdb进行调试
加上 corefile 就可以知道错误的信息,以及发生错误的代码在哪里, 在不加上corefile的情况下,如下图
这里并没有提示错误信息,程序需要你一步一步的调试然后找到错误。
2. GDB常用命令
run
让程序直接运行,知道遇到断点或者错误
gdb能够看到程序错误的内存信息, 0x000000004004d4 表示内存地址。
where
test()函数到底出了什么问题?where命令,显示导致段错误的执行函数树
这个是函数调用的顺序,0号代表当前所在函数。1 号的意思就是 main 函数 调用了test函数所以test为零号,main为一号 函数的调用顺序通过栈来保存。
list
list[m,n] , m/n 是要显示包含错误代码出现位置的前吗m行和后n行。不带参数则显示附近十行
whatis
查询变量是什么类型 规则同print
gdb最有用的功能之一就是它可以显示被调试程序中任何表达式、变量的值
print变量\表达式
print ‘file’::变量\表达式, ‘ ’是必须的,以便让gdb知道指的是一个文件名
print funcname::变量,表达式
ptype
ptype告诉你结构的定义,注意是结构体
break
break命令设置断点:
breaklinenum
breakfuncname
breakfilename::linenum
breakfilename:funcname
额,这个可以翻译一下就理解了
infobreak 查看断点信息
continue运行到下一个断点
delete删除所有断点 , delete num 删除指定标号的断点
set variable
setvariable 改变一个变量的值
setvariable varname = value
单步调试 step next
step相比于continue step只运行行代码,并且step在遇到函数的时候会进入函数内部
next同等于step 但是不会进入函数,而是运行到下一行
return停止执行当前函数,讲value返回给调用者, step 在函数内部运行时用return跳出