以下面的代码为例:
void *sample_run(void *arg)
{
for () {
}
return NULL
}
int main(int argc, char* argv[])
{
// suppress warnings
(void)argc(void)argv
pthread_t thdid = 0
pthread_create(&thdid, NULL, sample_run, NULL)
printf("Hello World!\n")
for () {
}
return 0
}
编译出的可执行程序假定为hello,
那么在命令行输入gdb hello
输入 b pthread_create
再输入r,可以看到程序暂停在pthread_create,
然后再输入b sample_run,输入c,可以看到程序进一步暂停在sample_run。
输入bt,可以看到调用栈。
请采纳,谢谢!
目前常用的gdb与内核的通信是基于串口的kgdboc模块来连接的,所以本文就以串口的kgdboc来讲解。文章分两个部分来解释这个问题,一部分是gdb端对ctrl+c *** 作做的一些处理,另外一部分则是内核和KGDB对停止指令处理。1: gdb端:在Linux console程序中,ctrl+c是用来终止当前在终端窗口中运行的命令或脚本。
下面的有两个C文件。(并没有bug。我们使用gdb来查看程序运行的细节)程序的一个为test.c,其中有主程序main()。mean.c程序中定义了mean()函数,并在main()中调用。
test.c
#define ARRAYSIZE 4
float mean(float, float)
int main()
{
int i
float a=4.5
float b=5.5
float rlt=0.0
float array_a[ARRAYSIZE]={1.0, 2.0, 3.0, 4.0}
float array_b[ARRAYSIZE]={4.0, 3.0, 2.0, 1.0}
float array_rlt[ARRAYSIZE]
for(i = 0i <ARRAYSIZE - 1i++) {
array_rlt[i] = mean(array_a[i], array_b[i])
}
rlt = mean(a, b)
return 0
}
mean.c
float mean(float a, float b)
{
return (a + b)/2.0
}
使用gcc同时编译上面两个程序。为了使用gdb对进行调试,必须使用-g选项(在编译时生成debugging信息):
$gcc -g -o test test.c mean.c
生成main可执行文件。
(如有必要,使用:
$chmod +x test
来增加用户的执行权限。)
进入gdb,准备调试程序:
$gdb test
进入gdb的互动命令行。
显示程序
我们可以直接显示某一行的程序,比如查看第9行程序:
(gdb) list 9
将显示以第9行为中心,总共10行的程序。我们实际上编译了两个文件,在没有说明的情况下,默认为主程序文件test.c:
4
5int main()
6{
7int i
8float a=4.5
9float b=5.5
10float rlt=0.0
11
12float array_a[ARRAYSIZE]={1.0, 2.0, 3.0, 4.0}
13float array_b[ARRAYSIZE]={4.0, 3.0, 2.0, 1.0}
如果要查看mean.c中的内容,需要说明文件名:
(gdb) list mean.c:1
可以具体说明所要列出的程序行的范围:
(gdb) list 5, 15
即显示5-15行的程序。
显示某个函数,比如:
(gdb) list mean
设置断点
我们可以运行程序:
(gdb) run
程序正常结束。
运行程序并没有什么有趣的地方。gdb的主要功能在于能让程序在中途暂停。
断点(break point)是程序执行中的一个位置。在gdb中,当程序运行到该位置时,程序会暂停,我们可以查看此时的程序状况,比如变量的值。
我们可以在程序的某一行设置断点,比如:
(gdb) break 16
将在test.c的第16行设置断点。
你可以查看自己设置的断点:
(gdb) info break
每个断点有一个识别序号。我们可以根据序号删除某个断点:
(gdb) delete 1
也可以删除所有断点:
(gdb) delete breakpoints
查看断点
设置断点,并使用run运行程序,程序将运行到16行时暂停。gdb显示:
Breakpoint 1, main () at test.c:16
16for(i = 0i <ARRAYSIZE - 1i++) {
查看断点所在行:
(gdb) list
查看断点处的某个变量值:
(gdb) print a
(gdb) print array_a
查看所有的局部变量:
(gdb) info local
查看此时的栈状态 (反映了函数调用,见Linux从程序到进程):
(gdb) info stack
可以更改变量的值。
(gdb) set var a=0.0
(gdb) set var array_a={0.0, 0.0, 1.0, 1.0}
当程序继续运行时,将使用更改后的值。
如果我们将断点设置在:
(gdb) break mean.c:2
此时栈中有两个a,一个属于main(),一个属于mean()。我们可以用function::variable的方式区分:
(gdb) print mean::a
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)