软件调试实战(软件调试权威指南)

本书样章免费读:http://www.china-pub.com/193196

定价 : ¥39.00会员价 : ¥29.25(75折)

基本信息
作者: (德)Thorsten Grotker    Ulrich Holtmann    Holger Keding    Markus Wloka    [作译者介绍]
译者: 赵俐[同译者作品]
丛书名: 图灵程序设计丛书
出版社:人民邮电出版社
ISBN:9787115218858
上架时间:2010-1-4
出版日期:2010 年1月
开本:16
所属分类: 计算机 > 软件工程及软件方法学 > 软件质量、软件测试及维护

【编辑推荐】
Amazon五星图书
Synopsys公司专家的调试经验总结
软件调试权威指南

【内容简介】
C/C++程序的调试和分析,书中的调试技术也可以应用于其他语言编写的程序。本书在讲述简单的源代码分析和测试的基础上,讲述了现实的程序中经常遇到的一些问题(如程序链接、内存访问、并行处理和性能分析)并给出了解决方案。
本书适合软件开发人员、调试人员阅读和使用

目录

第1章 谁编写软件,谁制造bug(为什么需要本书) 1
第2章 系统性调试方法 3
2.1 为什么要遵循结构化的过程 3
2.2 充分利用机会 3
2.3 13条黄金规则 5
2.3.1 理解需求 5
2.3.2 制造失败 6
2.3.3 简化测试用例 6
2.3.4 读取恰当的错误消息 6
2.3.5 检查显而易见的问题 6
2.3.6 从解释中分离出事实 7
2.3.7 分而治之 7
2.3.8 工具要与bug匹配 8
2.3.9 一次只做一项更改 9
2.3.10 保持审计跟踪 9
2.3.11 获得全新观点 9
2.3.12 bug不会自己修复 9
2.3.13 用回归测试来检查bug修复 10
2.4 构建一个好的工具包 10
2.4.1 工具箱 11

.2.4.2 每天运行测试,防止出现bug 11
2.5 认清敌人——遇到bug家族 13
2.5.1 常见bug 13
2.5.2 偶发性bug 13
2.5.3 Heisenbug 13
2.5.4 隐藏在bug背后的bug 14
2.5.5 秘密bug——调试与机密性 14
2.5.6 更多读物 15
第3章 查找根源——源代码调试器 17
3.1 可视化程序行为 17
3.2 准备简单的可预测的示例 18
3.3 使调试器与程序一起运行 18
3.4 学习在程序崩溃时执行栈跟踪 21
3.5 学习使用断点 21
3.6 学习在程序中导航 22
3.7 学习检查数据:变量和表达式 22
3.8 一个简单示例的调试会话 23
第4章 修复内存问题 27
4.1 C/C++中的内存管理——功能强大但很危险 27
4.1.1 内存泄漏 27
4.1.2 内存管理的错误使用 28
4.1.3 缓冲区溢出 28
4.1.4 未初始化的内存bug 28
4.2 有效的内存调试器 28
4.3 示例1:检测内存访问错误 29
4.3.1 检测无效的写访问 30
4.3.2 检测对未初始化的内存的读取操作 30
4.3.3 检测内存泄漏 31
4.4 示例2:对内存分配/释放的不完整调用 31
4.5 结合使用内存调试器和源代码测试器 33
4.6 减少干扰,排查错误 33
4.7 何时使用内存调试器 34
4.8 约束 34
4.8.1 测试用例应该有很好的代码覆盖率 34
4.8.2 提供更多计算机资源 35
4.8.3 可能不支持多线程 35
4.8.4 对非标准内存处理程序的支持 35
第5章 剖析内存的使用 37
5.1 基本策略——主要步骤 37
5.2 示例:分配数组 38
5.3 第1步:查找泄漏 38
5.4 第2步:设置期望值 38
5.5 第3步:测量内存使用 39
5.5.1 使用多个输入 39
5.5.2 在固定时间间隔停止程序 39
5.5.3 用简单工具测量内存使用 40
5.5.4 使用top 40
5.5.5 使用Windows Task Manager 41
5.5.6 为testmalloc选择相关输入值 42
5.5.7 确定机器上的内存是如何被释放的 42
5.5.8 使用内存剖析工具 43
5.6 第4步:查明大部分内存被哪些数据结构占用了 44
5.7 综合练习——genindex示例 45
5.7.1 核实没有大的内存泄漏 46
5.7.2 估计内存使用 46
5.7.3 测量内存使用 46
5.7.4 查找使用内存的数据结构 47
第6章 解决性能问题 51
6.1 分步查找性能bug 51
6.1.1 执行前期分析 51
6.1.2 使用简单的时间测量方法 52
6.1.3 创建测试用例 52
6.1.4 使测试用例具有可再现性 53
6.1.5 检查程序的正确性 53
6.1.6 创建可扩展的测试用例 53
6.1.7 排除对测试用例的干扰 54
6.1.8 用time命令测量时可能会发生错误和偏差 54
6.1.9 选择一个能够揭示运行时间瓶颈的测试用例 55
6.1.10 算法与实现之间的差异 56
6.2 使用剖析工具 58
6.2.1 不要编写自己的剖析工具 58
6.2.2 剖析工具的工作原理 58
6.2.3 了解gprof 59
6.2.4 了解Quantify 63
6.2.5 了解Callgrind 64
6.2.6 了解VTune 66
6.3 分析I/O性能 68
第7章 调试并行程序 71
7.1 用C/C++编写并行程序 71
7.2 调试竞争条件 72
7.2.1 使用基本调试器功能来查找竞争条件 73
7.2.2 使用日志文件来查找竞争条件 74
7.3 调试死锁 76
7.3.1 如何确定正在运行的是哪个线程 77
7.3.2 分析程序的线程 78
7.4 了解线程分析工具 78
7.5 异步事件和中断处理程序 80
第8章 查找环境和编译器问题 83
8.1 环境变更——问题的根源 83
8.1.1 环境变量 83
8.1.2 本地安装依赖 84
8.1.3 当前工作目录依赖 84
8.1.4 进程ID依赖 84
8.2 如何查看程序正在做什么 84
8.2.1 用top来查看进程 84
8.2.2 用ps来查找应用程序的多个进程 85
8.2.3 使用/proc/[pid]来访问进程 85
8.2.4 使用strace跟踪对操作系统的调用 85
8.3 编译器和调试器也有bug 87
8.3.1 编译器bug 87
8.3.2 调试器和编译器兼容性问题 88
第9章 处理链接问题 89
9.1 链接器的工作原理 89
9.2 构建并链接对象 89
9.3 解析未定义的符号 91
9.3.1 丢失链接器参数 91
9.3.2 搜索丢失的符号 91
9.3.3 链接顺序问题 92
9.3.4 C++符号和名称改编 93
9.3.5 符号的反改编 94
9.3.6 链接C和C++代码 94
9.4 具有多个定义的符号 95
9.5 信号冲突 96
9.6 识别编译器和链接器版本不匹配 96
9.6.1 系统库不匹配 97
9.6.2 对象文件不匹配 97
9.6.3 运行时崩溃 98
9.6.4 确定编译器版本 98
9.7 解决动态链接问题 100
9.7.1 链接或载入DLL 100
9.7.2 无法找到DLL文件 101
9.7.3 分析载入器问题 102
9.7.4 在DLL中设置断点 103
9.7.5 提供DLL问题的错误消息 104
第10章 高级调试 107
10.1 在C++函数、方法和操作符中设置断点 107
10.2 在模板化的函数和C++类中设置断点 109
10.3 进入C++方法 110
10.3.1 用step-into命令进入到隐式函数中 112
10.3.2 用step-out命令跳过隐式函数 112
10.3.3 利用临时断点跳过隐式函数 113
10.3.4 从隐式函数调用返回 113
10.4 条件断点和断点命令 114
10.5 调试静态构造/析构函数 116
10.5.1 由静态初始化程序的顺序依赖性引起的bug 117
10.5.2 识别静态初始化程序的栈跟踪 118
10.5.3 在静态初始化之前连接调试器 118
10.6 使用观察点 119
10.7 捕捉信号 120
10.8 捕获异常 122
10.9 读取栈跟踪 124
10.9.1 带调试信息编译的源代码的栈跟踪 124
10.9.2 不带调试信息编译的源代码的栈跟踪 124
10.9.3 不带任何调试信息的帧 125
10.9.4 实际工作中的栈跟踪 125
10.9.5 改编后的函数名称 126
10.9.6 被破坏的栈跟踪 126
10.9.7 核心转储 127
10.10 操纵正在运行的程序 128
10.10.1 修改变量 130
10.10.2 调用函数 131
10.10.3 修改函数的返回值 132
10.10.4 中止函数调用 132
10.10.5 跳过或重复执行个别语句 133
10.10.6 输出和修改内存内容 133
10.11 在没有调试信息时进行调试 135
10.11.1 从栈读取函数参数 137
10.11.2 读取局部/全局变量和用户定义的数据类型 138
10.11.3 在源代码中查找语句的大概位置 139
10.11.4 走查汇编代码 140
第11章 编写可调试的代码 143
11.1 注释的重要性 143
11.1.1 函数签名的注释 144
11.1.2 对折中办法的注释 144
11.1.3 为不确定的代码加注释 144
11.2 采用一致的编码风格 144
11.2.1 仔细选择名称 145
11.2.2 不要使用“聪明过头”的结构 145
11.2.3 不要压缩代码 145
11.2.4 为复杂表达式使用临时变量 145
11.3 避免使用预处理器宏 146
11.3.1 使用常量或枚举来替代宏 146
11.3.2 使用函数来替代预处理器宏 148
11.3.3 调试预处理器输出 149
11.3.4 使用功能更强的预处理器 150
11.4 提供更多调试函数 151
11.4.1 显示用户定义的数据类型 151
11.4.2 自检查代码 152
11.4.3 为操作符创建一个函数,以便帮助调试 153
11.5 为事后调试做准备 153
第12章 静态检查的作用 155
12.1 使用编译器作为调试工具 155
12.1.1 不要认为警告是无害的 156
12.1.2 使用多个编译器来检查代码 158
12.2 使用lint 158
12.3 使用静态分析工具 158
12.3.1 了解静态检查器 158
12.3.2 将静态检查器检测到的错误减至(接近)零 160
12.3.3 完成代码清理后重新运行所有测试用例 160
12.4 静态分析的高级应用 161
第13章 结束语 163
附录A 调试命令 165
附录B 工具资源 167
附录C 源代码 179
参考文献 189

【译者序】

软件并不是从一开始就完美无缺,它包含各种各样的缺陷和错误,因此需要不断调试,找到问题,然后修改代码。好的调试技巧可以帮助我们创建高质量的软件,因此在软件开发项目中,花时间进行全面而细致的调试工作是非常值得的。
软件调试早已经不是什么陌生的字眼了,大多数开发人员都或多或少做过一些调试工作,例如源代码调试、内存调试、性能调试等。然而要在实际工作中出色地完成调试工作却并不容易,因为调试需要耗费大量时间,而且具有很大的不确定性。在很多情况下,我们很难预知修复一个bug需要多长时间,甚至根本不知道能否修复它。由于这些原因,我们必须采用系统性的调试方法并配备正确的工具,这正是本书的核心。
本书主要以C和C++程序为例详解如何通过调试来分析和改进程序代码。书中揭示了大量的软件缺陷并介绍了各种调试技术,同时给出了如何编写可调试代码的建议。相信所有开发人员,特别是调试人员,都能够从本书中获益匪浅。
翻译从来都是一项充满挑战和趣味性的工作,本书的翻译更是如此,每当我字斟句酌地思考应该如何用最准确简练的语言表达几位作者思想的时候,总是能够从他们的智慧和洞察力中得到启示,从而对调试有了越发深刻的认识,这使得北京炎热的夏天也成了最美好的时光。我把这本书当成了我的老师,也希望它能够成为各位读者的老师,把几位作者的思想精华传授给你们。
最后,衷心感谢北京双飞软件公司的同仁们在翻译中给予的帮助,以及在一些高级调试主题方面的技术支持。由于译者水平有限,在翻译过程中难免会出现一些错误,恳请读者批评指正。
2009年9月

转载于:https://www.cnblogs.com/china-pub/archive/2010/01/07/1641042.html

软件调试实战(软件调试权威指南)相关推荐

  1. 《挖掘管理价值:企业软件项目管理实战》一2.4 软件设计过程

    本节书摘来异步社区<挖掘管理价值:企业软件项目管理实战>一书中的第2章,第2.4节,作者: 徐勤 责编: 杨海玲, 更多章节内容可以访问云栖社区"异步社区"公众号查看. ...

  2. 拍案惊奇——软件调试实战训练营

    随着软件复杂度的不断增加,软件调试的难度越来越大.以调试器为核心的调试技术是征服软件世界的一把利剑.要想成为软件高手,认真修炼软件调试这门剑法是再多也不为过的.本训练营通过12个精选案例让参与者在实战 ...

  3. 拍案惊奇——软件调试实战训练营暑期特别班(v2.1)

    随着软件复杂度的不断增加,软件调试的难度越来越大.以调试器为核心的调试技术是征服软件世界的一把利剑.要想成为软件高手,认真修炼软件调试这门剑法是再多也不为过的.本训练营通过12个精选案例让参与者在实战 ...

  4. 基础零信任服务相关软件的安装和调试

    慢慢写,已经是第二周了可是看上去好像一时半会儿也写不完-- 最近在做零信任相关软件的安装和调试,主要使用系统为linux的CentOS 7.Windows7和Win Server 2008 R2 64 ...

  5. 嵌入式软件调试之软件断点

    关注.星标公众号,直达精彩内容 来源:CSDN | maomao171314 整理:技术让梦想更伟大 | 李肖遥 软件断点 INT 3 指令,即通常所说的"软件断点",一条X86系 ...

  6. 基于Qt的Windows平台桌面蓝牙调试器软件

    基于Qt的Windows平台桌面蓝牙调试器软件 在进行嵌入式的调试时,我们经常需要下位机给主机打印数据来观察数据变化.绘制波形等进行调试.一般的做法可以是直接通过串口与PC进行数据通信(USB to ...

  7. 中文书籍对《人月神话》的引用(20211105更新161-165本):大师品软件、JavaScript开发框架权威指南

    中文书籍对<人月神话>的引用(第001到160本)>> <人月神话>于1975年出版,1995年出二十周年版.自出版以来,该书被大量的书籍和文章引用,直到现在热潮不 ...

  8. Jetbrains系列软件常用快捷键/模板/调试

    Jetbrains开发软件常用快捷键/模板/调试 一.Jetbrains常用快捷键 Ctrl+Alt+L:代码的格式 Ctrl+F:打开的文件中查找 两次Shift:调出快速搜索框 Ctrl+Shif ...

  9. keil软件调试(Debug)仿真教程(软件调试和硬件调试的区别)及常用调试按键详解

    文章目录 前言 一.什么是软件调试(Debug),有什么用? 二.keil Debug常用按钮 总结 前言 单片机的调试分为两种,一种是使用软件模拟调试,第二种是硬件调试,两种调试方式各有不同,软件模 ...

  10. 日立HGP03调试软件日立HGP03调试软件

    日立HGP03调试软件日立HGP03调试软件 id=607173799283&

最新文章

  1. 网络工程师计算机类吗,机房网络工程师 | 网络工程专业的你知道吗?
  2. 前微博副总私房干货:微博平台与架构从零到IPO的打磨经验
  3. python实现共空间模式CSP
  4. Node.js Event loop 图解
  5. 后端代码之服务端 - MongoDB数据库的连接、重启测试与(Studio3T)查看 - 讲解篇
  6. 设置固定高度_防排烟系统的设置,前室、楼梯间、避难层!设置要求全记住!...
  7. WebService 工作原理及实例教程
  8. vscode代码对比差异视图窗口切换方法(左右文件位置切换)
  9. android 放大镜功能,Android 做一个放大镜的效果(转)
  10. TensorFlow中CNN的两种padding方式“SAME”和“VALID”
  11. 安卓ViewBinding详解
  12. xposed定位插件_模拟位置xposed
  13. 业务单据堆积如山?如何提升会计做账效率?
  14. app启动优化耗时分析
  15. 长风破浪会有时,直挂云帆济沧海——纪念2020,展望2021
  16. Ubuntu14.04停留在开机logo界面
  17. 爲什麽一个标准的反相器中PMOS管的寬長比要比N管大
  18. tomcat 历史版本下载
  19. 学富五车的你,敢迎战Python开发的成语接龙游戏吗?
  20. Rx第四部分--并发

热门文章

  1. linux nvidia显卡驱动安装教程,LINUX的NVIDIA显卡驱动安装
  2. 独自研发3年,双平台上线,我是如何从零开始做这款独立游戏的?
  3. 弱水三千,该取几瓢饮?
  4. 设计模式java装饰模式范例_Java设计模式中外观模式和装饰器模式的介绍(代码示例)...
  5. 2021高考成绩查询数学和物理,2021高考成绩什么时候几点可以查
  6. php qps是什么意思,tps和qps的区别和理解
  7. 高效技巧篇:化繁为简、高效使用金蝶K3WISE(金蝶K3WISE-主控台编辑)
  8. ClickHouse和Elasticsearch压测对比,谁是yyds?
  9. 哪些客户群体适合使用云服务器?
  10. 一点一滴开始搭建自己的项目框架之支付宝篇 支付宝提现