ubuntu下valgrind的安装与调试记录

在这里插入图片描述

一、ubuntu环境下valgrind的安装

ubuntu下安装很简单

sudo apt-get install valgrind

二、valgrind快速使用

2.1 valgrind介绍

Valgrind工具套件提供了许多调试和分析工具,可帮助您加快程序运行速度
更正确。这些工具中最流行的是Memcheck。它可以检测到许多与内存相关的错误
在C和C++程序中很常见,这可能导致崩溃和不可预测的行为。
本指南的其余部分提供了开始检测程序中内存错误所需的最低信息
Memcheck。有关Memcheck和其他工具的完整文档,请阅读用户手册

2.2 代码准备

当准备您的程序时,请使用-g编译程序以包括调试信息,这样Memcheck的错误消息将包含精确的行号。如果可以容忍速度降低,使用-O0也是一个好主意。使用-O1时,错误消息中的行号可能不准确,尽管一般来说在-O1上编译的代码运行Memcheck效果相当不错,并且与在-O0上运行相比速度提升相当显著。不建议使用-O2及以上,因为Memcheck有时会报告不存在的未初始化值错误。

2.3 valgrind运行待测程序

当您通常这样运行程序:

myprog arg1 arg2

请使用以下命令行:

valgrind --leak-check=yes myprog arg1 arg2

Memcheck是默认工具。–leak-check选项打开了详细的内存泄漏检测器。
您的程序将比正常情况下运行慢得多 (例如,20到30倍),并且会使用更多内存。Memcheck将发出有关它检测到的内存错误和泄漏的消息。

2.4 查看valgrind输出报告

这里提供一个测试程序,里面有两个错误,内存泄漏,越界访问

#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;
}

使用gcc编译,加入-g -O0编译选项

gcc -g -O0 main.c -o main

valgrind输出报告


(base) jordi@jordi-PowerEdge-T30:~/workspace/3rdlibary/valgrind/test/1_memoryerr$ valgrind --leak-check=yes ./main 
==54644== Memcheck, a memory error detector
==54644== Copyright (C) 2002-2017, and GNU GPL'd, by Julian Seward et al.
==54644== Using Valgrind-3.15.0 and LibVEX; rerun with -h for copyright info
==54644== Command: ./main
==54644== 
==54644== Invalid write of size 4
==54644==    at 0x401164: f (main.c:6)
==54644==    by 0x401175: main (main.c:10)
==54644==  Address 0x4a63068 is 0 bytes after a block of size 40 alloc'd
==54644==    at 0x483B7F3: malloc (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_memcheck-amd64-linux.so)
==54644==    by 0x401157: f (main.c:5)
==54644==    by 0x401175: main (main.c:10)
==54644== 
==54644== 
==54644== HEAP SUMMARY:
==54644==     in use at exit: 40 bytes in 1 blocks
==54644==   total heap usage: 1 allocs, 0 frees, 40 bytes allocated
==54644== 
==54644== 40 bytes in 1 blocks are definitely lost in loss record 1 of 1
==54644==    at 0x483B7F3: malloc (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_memcheck-amd64-linux.so)
==54644==    by 0x401157: f (main.c:5)
==54644==    by 0x401175: main (main.c:10)
==54644== 
==54644== LEAK SUMMARY:
==54644==    definitely lost: 40 bytes in 1 blocks
==54644==    indirectly lost: 0 bytes in 0 blocks
==54644==      possibly lost: 0 bytes in 0 blocks
==54644==    still reachable: 0 bytes in 0 blocks
==54644==         suppressed: 0 bytes in 0 blocks
==54644== 
==54644== For lists of detected and suppressed errors, rerun with: -s
==54644== ERROR SUMMARY: 2 errors from 2 contexts (suppressed: 0 from 0)

需要注意的事项:

  • 错误消息中包含大量信息,请仔细阅读。
  • 54644是进程ID,通常不重要。
  • 第8行(“无效写入…”)告诉您错误类型。在这里,程序写入了一些不应属于它的内存,这是由于堆块溢出造成的。
  • 第8行以下是堆栈跟踪,它会告诉您问题发生的位置。堆栈跟踪可能会非常大,并且可能会很混乱,尤其是在使用C++ STL时。从底部向上阅读可以帮助理解它。如果堆栈跟踪不够大,请使用 --num-callers 选项来扩大它。
  • 代码地址(例如 0x401164)通常不重要,但偶尔对于追踪更奇怪的错误至关重要。
  • 一些错误消息会显示内存越界访问。

根据错误报告的顺序修复错误是值得的,因为后面的错误可能是由早期的错误引起的。

内存泄漏消息类似于:

==54644== 40 bytes in 1 blocks are definitely lost in loss record 1 of 1
==54644==    at 0x483B7F3: malloc (in /usr/lib/x86_64-linux-gnu/valgrind/vgpreload_memcheck-amd64-linux.so)
==54644==    by 0x401157: f (main.c:5)
==54644==    by 0x401175: main (main.c:10)

堆栈跟踪告诉您泄漏的内存是在哪里分配的。遗憾的是,Memcheck 不能告诉您为什么内存泄漏了。(忽略“vg_replace_malloc.c”,这是实现细节。)

泄漏有几种类型,其中最重要的两个类别是:

  • “肯定丢失”:您的程序正在泄漏内存 - 请修复它!
  • “可能丢失”:除非您正在使用指针做一些有趣的事情(例如将它们移动到指向堆块的中间),否则您的程序正在泄漏内存。

Memcheck还会报告未初始化的值的使用,最常见的是以下消息:“Conditional jump or move depends on uninitialised value(s)”。

2.5 注意事项

Memcheck并不完美,偶尔会产生误报,并且存在控制这些误报的机制(请参见Valgrind用户手册中的Suppressing errors)。但是,它通常99%的时间内是正确的,所以你应该谨慎地忽略其错误消息。毕竟,你不会忽略编译器产生的警告消息,对吧?如果Memcheck报告您无法更改的库代码中的错误,则抑制机制非常有用。默认抑制设置隐藏了很多这些,但你可能会遇到更多。
Memcheck无法检测到程序中存在的每个内存错误。例如,它不能检测到范围之外的读取或写入到静态分配或堆栈上的数组。但是,它应该能够检测到许多可能使程序崩溃的错误(例如,导致分段错误)。
尽量使您的程序保持清洁(笔者认为有内存泄漏说明有垃圾没有清除,是不干净的),以使Memcheck不报告任何错误。
理想状态

==59371== Memcheck, a memory error detector
==59371== Copyright (C) 2002-2017, and GNU GPL'd, by Julian Seward et al.
==59371== Using Valgrind-3.15.0 and LibVEX; rerun with -h for copyright info
==59371== Command: ./main
==59371== 
==59371== 
==59371== HEAP SUMMARY:
==59371==     in use at exit: 0 bytes in 0 blocks
==59371==   total heap usage: 0 allocs, 0 frees, 0 bytes allocated
==59371== 
==59371== All heap blocks were freed -- no leaks are possible
==59371== 
==59371== For lists of detected and suppressed errors, rerun with: -s
==59371== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)

一旦达到这种状态,当对程序进行更改导致Memcheck报告新错误时,就可以更容易地看到。使用Memcheck几年的经验表明,即使是庞大的程序也可以保持清洁。例如,KDE,OpenOffice.org和Firefox的很大一部分是清洁的,或者非常接近它。
好,最后希望的加写的程序无BUG,无泄漏。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

CONNY~

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值