《软件调试的艺术》笔记--预备知识

1.gcc的-g选项

如果要使用gdb进行调试,必须在编译时在gcc中加入-g选项,使用参数 -g 表示将源代码信息编译到可执行文件中。

如果不使用-g选项:

#include <stdio.h>

int main(void)
{
	int i = 1;
	i = i + 1;
	printf("i = %d\n",i);
	return 0;
}

gcc main.c

gdb a.out

(gdb) b main

Breakpoint 1 at 0x4004f8

(gdb) r

Starting program: /home/yanwenjie/ctest/a.out

warning: no loadable sections found in added symbol-file system-supplied DSO at 0x7ffff7ffa000

Breakpoint 1, 0x00000000004004f8 in main ()

(gdb) n

Single stepping until exit from function main,

which has no line number information.

i = 2

0x00007ffff7a3b76d in __libc_start_main () from /lib/x86_64-linux-gnu/libc.so.6

(gdb)

如果使用-g选项:

gcc -g main.c

[email protected]:~/ctest$ gdb a.out

(gdb) b main

Breakpoint 1 at 0x4004fc: file main.c, line 5.

(gdb) r

Starting program: /home/yanwenjie/ctest/a.out

warning: no loadable sections found in added symbol-file system-supplied DSO at 0x7ffff7ffa000

Breakpoint 1, main () at main.c:5

5 int i = 1;

(gdb) n

6 i = i + 1;

(gdb)

7 printf("i = %d\n",i);

(gdb)

i = 2

8 return 0;

(gdb)

可以看到程序语句信息。

2.TUI(terminal User Interface)

从版本6.1开始,GDB已经以名为TUI的模式提供基于文本交互和图形交互之间的折中方法。命令为:

gdbtui a.out

如上图显示,上方为显示对应的代码语句,下方为通常gdb的命令模式。其他操作与命令行gdb一致。

3.上下移动调用栈

在函数调用期间,与调用关联的运行信息存储在栈帧的内存区域中。帧中包含函数的局部变量的值、其形参,以及调用该函数的

位置记录。每次发生函数调用时,都会创建一个新帧,并将其推到一个系统维护的栈上,栈最上方的帧表示正在执行的函数,当

函数推出时,这个帧被弹出栈,并且被释放。

在GDB中可以用如下命令查看以前的帧:

frame 1

当执行GDB的frame命令时,当前正在执行的函数的帧被编号为0,其父帧被编号为1,父帧的父帧被编号为2,以此类推。GDB

的up命令将你带到调用帧中的下一个父帧,down则引向相反方向。这样的操作非常有用,因为根据以前的一部分栈帧中的局部

变量的值。

GDB的backtrace命令会显示整个栈,即当前存在的所有帧的集合。

main.c:

#include <stdio.h>

void display(int i)
{
	printf("i = %d\n",i);
}

int main(void)
{
	int i = 1;
	i = i + 1;
	display(i);
	return 0;
}

对上面的程序进行gdb调试。

(gdb) b display

Breakpoint 1 at 0x4004ff: file main.c, line 5.

(gdb) frame

No stack.

(gdb) r

Starting program: /home/yanwenjie/ctest/a.out

warning: no loadable sections found in added symbol-file system-supplied DSO at 0x7ffff7ffa000

Breakpoint 1, display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb) frame

#0  display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb) frame 0

#0  display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb) frame 1

#1  0x0000000000400535 in main () at main.c:12

12 display(i);

(gdb) frame 0

#0  display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb) up

#1  0x0000000000400535 in main () at main.c:12

12 display(i);

(gdb) down

#0  display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb) bt

#0  display (i=2) at main.c:5

#1  0x0000000000400535 in main () at main.c:12

4.gdbinit

使用gdb调试程序的时候,有时候需要设定多个断点,重复执行某些操作,而这些操作写起来比较麻烦,这时候可以使用gdbinit脚本。

在有如下脚本:

#filename: .gdbinit
b display
r

有两种方式来使用这个脚本:

1)启动gdb时候

gdb在启动的时候,会在当前目录下查找".gdbinit"这个文件,并把它的内容作为gdb命令进行解释,所以如果我把脚本命名为".gdbinit",

这样在启动的时候就会处理这些命令。

将脚本保存为.gdbinit,放在main.c同一目录下,执行gdb命令:

[email protected]:~/ctest$ gdb a.out

Breakpoint 1, display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb)

2)gdb运行期间

可以使用 source script-file 来解释gdb命令脚本script-file

将脚本保存为gdbscript,放在main.c同一目录下:

[email protected]:~/ctest$ gdb a.out

(gdb) source gdbscript

Breakpoint 1 at 0x4004ff: file main.c, line 5.

Breakpoint 1, display (i=2) at main.c:5

5 printf("i = %d\n",i);

(gdb)

《软件调试的艺术》笔记--预备知识,布布扣,bubuko.com

时间: 2024-12-25 03:58:46

《软件调试的艺术》笔记--预备知识的相关文章

《软件调试的艺术》笔记--停下来环顾程序

1.断点列表 创建的每个断点(包括断电.监视点和捕获点)都标识为从1开始的唯一整数标识符.这个标识符用来执行该断点上的各种 操作.调试器还包含一种列出所有断点及其属性的方法. 调试下面的代码:(代码1) #include <stdio.h> void display(int i) { i = i + 1; printf("i = %d\n",i); } int main(void) { int i = 1; display(i); return 0; } 设置断点--显示断

《软件调试的艺术》笔记--调试多线程程序

下面是于线程相关的GDB命令用法汇总: info threads:给出关于当前所有线程的信息. thread 3:改成线程3. break 88 thread 3 :当线程到达源代码88时停止执行. break 88 thread 3 if i == 2 当线程3到达源代码行88行,并且变量i的值为2时停止执行. 对下面的多线程进行调试: #include <stdio.h> #include <pthread.h> #include <string.h> #inclu

《软件调试的艺术》笔记--检查和设置变量

1.使用print命令查看变量值 使用print命令(简写为p)可以查看变量值. 使用如下的程序1进行测试. #include <stdio.h> struct node{ int index; struct node* next; }; int main(void) { struct node head; head.index = 1; head.next = NULL; int i; for(i=0; i<3; i++){ head.index++; } return 0; } (g

《软件调试的艺术》笔记--使用其他调试工具

1.splint splint是一个开源的静态代码检查工具,使用方法如下: 待检测的程序程序如下: #include <stdio.h> static void display(int i) { printf("i = %d\n",i); } int main(void) { int i,j; i = 1; i = i + 1; display(i); return 0; } 调试如下: $ splint main.c Splint 3.1.2 --- 03 May 200

《软件调试的艺术》学习笔记——GDB使用技巧摘要

<软件调试的艺术>学习笔记——GDB使用技巧摘要 <软件调试的艺术>,因为名是The Art of Debugging with GDB, DDD, and Eclipse. 作者是美国的Norman Matloff和Peter Jay Salzman,中文版由张云翻译.是人邮出版社图灵程序设计丛书初版.这里称为"艺术",个人觉得有点过了,但是其中关于gdb以及在gdb基础之上集成的DDD和Eclipse调试技巧的整理确实是做的很好,对于Linux/开源社区下的

《软件调试的艺术The Art of Debugging with GDB,DDD,and Eclipse》

#第1章 **使用TUI模式的GDB**指定-tui或者CTRL+X+A #第2章 停下来环顾程序# **断点**通知GDB暂停程序的执行 **监视点**通知GDB当特定内存位置(或者涉及一个或多个位置的表达式)的值发生变化时暂停执行. **捕获点**通知GDB当特定事件发生时暂停执行. ###2.4.1在GDB中设置断点### ●break *function* ●break *line_number* ●break *filename:function* ●break *filename:l

《软件调试》读书笔记:第13章 硬错误和蓝屏

会话管理器进程SMSS.exe是系统启动后的第一个用户态进程,负责启动和监护windows子系统进程:CSRSS.exe和登陆管理进程:WinLogon SMSS.exe从注册表中查询子系统exe文件的位置,并且启动它 CSRSS是windows子系统进程,自NT4以后窗口管理和GDI的主体实现被移出了CSRSS放到了win32k.sys中. CSRSS监管着所有windows线程和进程,每个进程在创建后都要到这里登记才能运行,退出时也要报告注销. CSRSS具有桌面管理.终端登录.控制台管理.

《软件调试艺术》读后感一

1.预备知识 在进入正题之前要对GDB有一个大概的了解,GDB能干什么?GDB现在的实用性还有多少?等问题,我们带着这样的问题去书中探索,这样会使我们学到更多的东西. 首先,我看一张图,这张图不是我画的,但是这张图基本涵盖了<软件调试艺术>这本书的所有内容.也就是这本书的浓缩版,精华版. 这本书主要以GDB调试软件为基础进行讲解,可能在此之前我们大家对调试并不关注,或者都没有觉得调试有多重要.我们总是写代码,这些代码的工程比较小,代码量少,所以调试工具没有太大的帮助.如果我们的程序非常的大,并

最大熵学习笔记(一)预备知识

  生活中我们经常听到人们说"不要把鸡蛋放到一个篮子里",这样可以降低风险.深究一下,这是为什么呢?其实,这里边包含了所谓的最大熵原理(The Maximum Entropy Principle).本文为一则读书笔记,将对最大熵原理以及由此导出的最大熵模型进行介绍,重点给出其中所涉及数学公式的理解和详细推导. 相关链接 最大熵学习笔记(零)目录和引言 最大熵学习笔记(一)预备知识 最大熵学习笔记(二)最大熵原理 最大熵学习笔记(三)最大熵模型 最大熵学习笔记(四)模型求解 最大熵学习笔