24 / 07 / 09

「一生一芯」Learn C the hard way - Ex 4

练习 4:Valgrind 介绍

#include <stdio.h> /* Warning: This program is wrong on purpose. */ int main() { int age = 10; int height; printf("I am %d years old.\n"); printf("I am %d inches tall.\n", height); return 0; }
$ valgrind ./ex4

附加题 1

按照上面的指导,使用Valgrind和编译器修复这个程序。

分析输出

编译器警告和 Valgrind 的输出会提示我们以下问题:

  • 使用未初始化的变量 height

  • printf 缺少格式化占位符对应的参数。

修复代码

我们需要:

  1. 初始化变量 height

  2. 修正 printf 调用中的格式化占位符。

附加题 2

在互联网上查询Valgrind相关的资料。

Valgrind 是一个强大的工具,用于调试和分析 Linux 程序,广泛用于检测内存管理和线程错误,以及进行性能分析。以下是 Valgrind 提供的一些关键功能及其优势:

主要功能和工具

  1. Memcheck:检测内存错误,例如非法内存访问、使用未初始化的内存和内存泄漏,使程序更加健壮。

  2. Cachegrind:分析缓存使用和分支预测,帮助优化程序性能。

  3. Callgrind:生成调用图,提供函数调用和执行路径的详细信息。

  4. Helgrind:识别线程错误,如数据竞争和锁顺序违规,确保代码线程安全。

  5. DRD:另一种线程错误检测工具,采用不同的分析方法,发现不同类型的线程问题。

  6. Massif:分析堆内存使用情况,帮助优化内存分配和使用。

  7. DHAT:分析堆块生命周期和利用率,提供内存效率的见解。

优势

  • 节省时间:Valgrind 可以自动检测许多手动难以发现的错误,节省开发人员的调试时间。

  • 性能分析:详细的分析有助于识别性能瓶颈,优化代码以提高速度和效率。

  • 免费开源:Valgrind 以 GNU 通用公共许可证 (GPL) 发布,用户可以自由修改和共享该工具。

  • 跨语言支持:虽然主要针对 C 和 C++ 程序,Valgrind 也适用于各种语言编写的程序,包括 Java、Perl、Python 等。

  • 易于使用:Valgrind 的工具可以在不修改或重新编译目标应用程序的情况下使用,使其易于集成到开发工作流程中。

使用场景

  • 持续测试:在自动化测试过程中运行 Valgrind 工具可以确保代码更改不会引入新错误。

  • 开发后期:在发布软件之前运行 Valgrind 可以帮助捕获潜在问题,从而发布更稳定的版本。

  • 按需调试:在怀疑存在错误或需要详细性能分析时,使用 Valgrind。

附加题 3

下载另一个程序并手动构建它。尝试一些你已经使用,但从来没有手动构建的程序。

感谢 Verilator。

附加题 4

看看Valgrind的源码是如何在目录下组织的,并且阅读它的Makefile文件。不要担心,这对我来说没有任何意义。

顶层目录结构

  • AUTHORS: 列出项目的主要贡献者。

  • COPYINGCOPYING.DOCS: 包含项目的许可协议和文档的许可协议。

  • FAQ.txt: 常见问题解答。

  • Makefile: 顶层 Makefile,定义了编译和链接整个项目的规则。

  • NEWSNEWS.old: 更新日志,记录项目的更新历史。

  • README 和其他 README 文件: 提供项目的总体介绍和特定平台的说明。

主要子目录

  • coregrind/: 包含 Valgrind 核心部分的代码。

  • VEX/: 包含 VEX(Valgrind 的翻译引擎)的代码。

  • include/: 包含公共头文件。

  • docs/: 文档目录,包含用户手册、开发者文档等。

  • tests/: 测试目录,包含各种测试用例和测试脚本。

工具和模块子目录

  • cachegrind/: Cachegrind 工具的代码,用于缓存分析。

  • callgrind/: Callgrind 工具的代码,用于调用图生成。

  • dhat/: DHAT 工具的代码,用于堆分析。

  • drd/: DRD 工具的代码,用于检测线程错误。

  • helgrind/: Helgrind 工具的代码,用于检测线程错误。

  • massif/: Massif 工具的代码,用于堆内存分析。

  • memcheck/: Memcheck 工具的代码,用于内存错误检测。

  • exp-bbv/: 实验性工具 BBV 的代码,用于生成基本块向量。

构建系统文件

  • Makefile.amMakefile.in : Automake 和 Autoconf 使用的文件,用于生成 Makefile

  • configureconfigure.ac: 配置脚本和配置脚本的输入文件,用于检测系统环境和生成 Makefile

  • config.hconfig.h.in: 配置头文件,用于定义配置选项。

  • compile, install-sh, depcomp 等: 辅助脚本,用于构建系统的各种任务。

平台支持文件

  • darwin.supp*, freebsd.supp*, solaris.supp* 等: 各平台的支持文件,定义了特定平台的补充规则和配置。

其他工具和模块

  • auxprogs/: 辅助程序目录,包含各种辅助工具。

  • gdbserver_tests/: GDB 服务器测试目录,包含与 GDB 相关的测试用例。

  • mpi/: MPI 支持文件,包含与消息传递接口相关的代码。