valgrind快速入门手册

最近空闲时间比较多,于是,决定自行研究点东西。

话不多说,这个系列是翻译valgrind官网的文档手册,第一次做这样的事情,尽量吧~

先介绍下valgrind是什么东东:

Valgrind是一款用于内存调试、内存泄漏检测以及性能分析软件开发工具。Valgrind这个名字取自北欧神话英灵殿的入口(摘自wiki百科)

那么下面就开始吧。

valgrind快速入门指南

1、介绍:

这个valgrind工具系列提供若干调试和分析工具以帮助你的程序更快、更健壮。这其中的佼佼者就是memcheck了,它能检测到许多内存相关的错误,这些错误存在于你写的c/c++程序当中,并且这些错误可能导致程序崩溃或者出现一些不可预知的行为。

本指引提供让你运用memcheck上手去检测你编写的程序的内存错误的最少的信息,如果要了解更多关于Memcheck的文档信息或者其它工具,请参考官网的user manual。

2、准备你的程序:

让你的程序带有-g的编译选项,这样可以让memcheck工具能精准的标识行号等信息。如果你能容忍程序稍微慢点,加上-00就更好了。如果是-01选项,那么行号的错误信息可能不是很准确,虽然整体来说memcheck工具在这个编译选项下也工作的很好并且相比-00速度更快。-02的编译选项就不推荐了,因为这样会容易导致memcheck误报错。

3、让你的程序在memcheck下运行:

如果你是这样运行你的程序的:

myprog arg1 arg2

那么可以运行这个命令行

valgrind --leak-check=yes myprog arg1 arg2

memchekc是默认的工具,--leak-chekc选项是打开具体的内存泄漏探测器。

运行memcheck之后,你的程序会比原来的慢20-30倍,并且占用更多内存,memcheck会对探测到的内存错误或者泄漏进行消息显示。

4、打断memcheck的输出:

这里有一个示例程序叫a.c,有内存错误和内存泄漏

#include <stdlib.h>

void f(void)  
 {    
  int* x = malloc(10 * sizeof(int));     
   x[10] = 0;        // problem 1: heap block overrun   
 // problem 2: memory leak -- x not freed   


 }                 
  
 int main(void)   {      f();      return 0;   }










多数错误信息如下所示,用来描述problem 1的,堆内存越界。

  ==19182== Invalid write of size 4  
  ==19182==    at 0x804838F: f (example.c:6)  
  ==19182==    by 0x80483AB: main (example.c:11)   
  ==19182==  Address 0x1BA45050 is 0 bytes after a block of size 40 alloc'd   
  ==19182==    at 0x1B8FF5CD: malloc (vg_replace_malloc.c:130)  
  ==19182==    by 0x8048385: f (example.c:5)   
  ==19182==    by 0x80483AB: main (example.c:11)
以下事项是需要注意的:

这里有大量的错误信息,需要仔细读。

19182是进程id,通常这是没有用的。

第一行的 错误提示(invalid write)告诉你这是什么样的错误,这里是指程序写了堆中的越界非法内存。

第一行以下的是这个错误发生的一些堆栈跟踪信息。这些堆栈跟踪可能很大,可能让你迷惑,尤其是你运用了c++ STL之后。

代码地址比如 0x804838F通常是没用的,但是有时对一些奇怪的错误又是关键性的信息。


但是,memcheck泄漏信息却是类似这样的:

  ==19182== 40 bytes in 1 blocks are definitely lost in loss record 1 of 1  
 ==19182==    at 0x1B8FF5CD: malloc (vg_replace_malloc.c:130)   
 ==19182==    by 0x8048385: f (a.c:5)   ==19182==    by 0x80483AB: main (a.c:11)

这里的堆栈跟踪告诉你泄漏的内存是在哪里分配的,很遗憾的是,memcheck不能告诉你为什么会造成内存泄漏。

这里可能有几种内存泄漏,最重要的两种如下所示:

definitely lost:那么这表明你的程序存在内存泄漏,修复它

probably lost:那么这表明你的程序存在内存泄漏,除非是你正在使用指针(比如用指针向堆中内存move数据)

memchekc同样会报对未初始化变量的使用,一般会显示这样的信息“"Conditional jump or move depends on uninitialised value(s)"”,这很难定位错误根源,可以尝试使用--track-origins=yes来得到额外的信息,不过这会导致程序运行的更慢,不过这些额外的信息能帮助你比较快速定位的未初试化变量的来源。


5、警告:

memcheck不是完美的,它偶尔会报错误的错,不过这里有机制压抑它,详细见user manual。

不过,它能保证99%的正确率,所以你应该警惕它的报错信息,毕竟,就像你不会忽略编译器的错误信息,对吗?

memchekc不能侦探到程序的每个内存错误,举例说明,它不能检测到越界读写栈中静态分配的数组的错误,但是它还是可以帮助你找到很多可能导致你程序崩溃的内存错误的

努力尝试使你的程序很干净,让memcheck都不会报任何错误信息。一旦你达到这个状态,当你的程序发生变更 ,你就很容易知道memcheck报的新错误了。几年以上的memcheck使用经验可以让你,即使很大的程序都能做到memcheck 不报任何错误,也就是memcheck-clean.这里有不少这样的例子,比如BSD/Firefox/OpenOffice.org,这些项目都是memcheck-clean.

6、更多信息:

更多信息请咨询FAQ或者浏览User manual。链接为:http://valgrind.org/docs/manual/manual.html,英文版,有时间继续翻译。




 


 

 
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值