valgrind如何工作?

有人可以提供Valgrind如何工作的快速顶级解释吗? 一个例子:它是如何知道内存何时分配和释放的?

Valgrind基本上在“沙箱”中运行你的应用程序。 在此沙箱中运行时,它可以插入自己的指令来进行高级debugging和分析。

从手册:

然后,您的程序将在Valgrind核心提供的合成CPU上运行。 当新代码第一次执行时,核心将代码交给选定的工具。 该工具将自己的工具代码添加到此,并将结果交还给核心,该核心协调了此仪表代码的继续执行。

所以基本上,valgrind提供了一个虚拟处理器来执行你的应用程序。 但是,在处理应用程序指令之前,它们被传递给工具(如memcheck)。 这些工具就像插件一样,在处理器上运行之前,它们可以修改应用程序。

这种方法的好处在于,您不必修改或重新链接您的程序就可以在valgrind中运行它。 它确实会导致程序运行速度变慢,但是valgrind并不意味着在正常执行应用程序时测量性能或运行,所以这不是问题。

Valgrind是一个dynamic二进制分析(DPA)工具,它使用dynamic二进制工具(DPI)框架来检查内存分配,检测死锁和分析应用程序。 DPI框架拥有自己的低级内存pipe理器,调度器,线程处理器和信号处理器。 Valgrind工具套件包括工具

  1. Memcheck – dynamic跟踪内存分配并报告内存泄漏。
  2. Helgrind – 检测并报告死锁,潜在的数据竞争和locking反转。
  3. Cachegrind – 模拟应用程序如何与系统caching交互并提供有关caching未命中的信息。
  4. Nulgrind – 一个简单的valgrind,从来没有做任何分析。 开发人员用于性能基准。
  5. Massif – 分析应用程序的堆内存使用情况的工具。

Valgrind工具使用反汇编和重新合成机制,将应用程序加载到进程中,反汇编应用程序代码,添加用于分析的检测代码,将其组装回来并执行应用程序。 它使用Just Intime Compiler(JIT)将应用程序embedded到检测代码中。

Valgrind Tool = Valgrind Core + Tool Plugin 

Valgrind核心分解应用程序代码,并将代码片段传递给工具插件进行检测。 工具插件添加分析代码并将其组装回来。 因此,Valgrind提供了在Valgrind框架之上编写我们自己的工具的灵活性。 Valgrind使用影子寄存器和影子存储器来读/写指令,读/写系统调用,堆栈和堆分配。

Valgrind提供了围绕系统调用的包装器,并为每个系统调用的前后callback寄存器来跟踪作为系统调用的一部分访问的内存。 因此,Valgrind是Linux操作系统和客户端应用程序之间的一个操作系统抽象层。

该图说明了Valgrind的8个阶段:

Valgrind的8个阶段

valgrind作为你的程序和操作系统之间的一个层,拦截调用操作系统的请求内存(de)的分配和logging之前正在处理的内容,然后实际分配内存并返回一个等价物。 这基本上是大多数代码分析器的工作原理,除非在更低层次上(系统调用而不是程序函数调用)。

Valgrind基本上是一个执行你的程序的虚拟机 。 这是一个虚拟体系结构,拦截每个分配/释放内存的调用。

在这里你可以find一些很好的信息:

除了熟悉LD_PRELOAD。