为了账号安全,请及时绑定邮箱和手机立即绑定

仍然可达的泄漏检测

仍然可达的泄漏检测

C C++
蝴蝶刀刀 2019-07-11 16:21:33
仍然可达的泄漏检测这个块中提到的所有函数都是库函数。我如何纠正这个内存泄漏?它列在“仍可达“类别。(还有4种,它们非常相似,但大小不同)。” 630 bytes in 1 blocks are still reachable in loss record 5 of 5     at 0x4004F1B: calloc (vg_replace_malloc.c:418)     by 0x931CD2: _dl_new_object (dl-object.c:52)     by 0x92DD36: _dl_map_object_from_fd (dl-load.c:972)     by 0x92EFB6: _dl_map_object (dl-load.c:2251)     by 0x939F1B: dl_open_worker (dl-open.c:255)     by 0x935965: _dl_catch_error (dl-error.c:178)     by 0x9399C5: _dl_open (dl-open.c:584)     by 0xA64E31: do_dlopen (dl-libc.c:86)     by 0x935965: _dl_catch_error (dl-error.c:178)     by 0xA64FF4: __libc_dlopen_mode (dl-libc.c:47)     by 0xAE6086: pthread_cancel_init (unwind-forcedunwind.c:53)     by 0xAE61FC: _Unwind_ForcedUnwind (unwind-forcedunwind.c:126)捕获:一旦我运行了我的程序,它就不会产生内存泄漏,但是它在Valrun输出中有一个额外的行,这在以前是不存在的:在/lib/libgcc_s-4.4.4-20100630.so.1中丢弃0x5296fa0-0x52af438中的Syms,原因是munmap()如果泄漏无法纠正,至少有人能解释munmap()行为什么导致Val差尔报告0“仍然可以到达”泄漏吗?
查看完整描述

3 回答

?
芜湖不芜

TA贡献1796条经验 获得超7个赞

定义“内存泄漏”的方法不止一种。特别是,“内存泄漏”有两个主要的定义,它们是程序员常用的。

“内存泄漏”的第一个常用定义是,“在程序结束之前,内存被分配,随后未被释放。”然而,许多程序员(正确地)认为,符合这个定义的某些类型的内存泄漏实际上并不构成任何类型的问题,因此不应该考虑。千真万确“记忆泄漏”。

可以说,“内存泄漏”的一个更严格(也更有用)的定义是,“内存被分配了,并且不可能随后释放,因为程序不再有指向已分配内存块的指针。“换句话说,您不能释放不再有指针的内存。因此,这种内存是”内存泄漏“。Val差伦对”内存泄漏“一词使用了更严格的定义。这是一种可能导致堆耗尽的类型,特别是对于长期存在的进程。

Val差尔泄漏报告中的“仍然可达”类别指的是只符合“内存泄漏”的第一个定义的分配。这些块没有被释放,但是它们可以被释放(如果程序员愿意的话),因为程序仍然在跟踪指向这些内存块的指针。

一般来说,没有必要担心“仍然可以到达”块。他们不会提出这样的问题千真万确内存泄漏会导致。例如,通常没有可能从“仍然可达”的块中耗尽堆。这是因为这些块通常是一次分配,对其的引用在整个过程的生存期内保持不变。而您可以通过并确保您的程序释放分配内存时,这样做通常没有实际好处,因为在进程终止后,操作系统将回收进程的所有内存。对比一下千真万确内存泄漏,如果没有固定,如果保持足够长的运行时间,可能会导致进程耗尽内存,或者只会导致进程消耗比所需的内存多得多的内存。

确保所有分配都具有匹配的“frees”可能唯一有用的情况是,如果您的泄漏检测工具无法判断哪些块“仍可访问”(但Val差尔可以做到这一点),或者如果您的操作系统没有回收终止进程的所有内存(所有平台都已被移植以完成此操作)。


查看完整回答
反对 回复 2019-07-11
?
米脂

TA贡献1836条经验 获得超3个赞

由于底部有一些来自p线程家族的例程(但我不知道具体的例程),我猜您已经启动了一些可连接的线程,该线程已经终止了执行。

在调用之前,该线程的退出状态信息是可用的。pthread_join..因此,内存保存在程序终止时的丢失记录中,但由于您可以使用pthread_join去访问它。

如果此分析是正确的,则启动这些分离的线程,或者在终止程序之前加入它们。

编辑:我运行了您的示例程序(经过一些明显的更正后),我没有错误,但如下所示

==18933== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 4 from 4)--18933-- --18933-- used_suppression:     
 2 dl-hack3-cond-1--18933-- used_suppression:      2 glibc-2.5.x-on-SUSE-10.2-(PPC)-2a

因为dl-事情很像你所看到的,我猜你看到了一个已知的问题,它有一个抑制文件的解决方案。valgrind..也许您的系统不是最新的,或者您的发行版没有维护这些东西。(我的是ubuntu 10.4,64位)


查看完整回答
反对 回复 2019-07-11
?
拉莫斯之舞

TA贡献1820条经验 获得超10个赞

以下是对“仍然可达”的适当解释:

“仍然可达”是分配给全局和静态局部变量的泄漏。因为valcher跟踪全局和静态变量,所以它可以排除分配给“一次性遗忘”的内存分配。分配一次且从不重新分配的全局变量分配通常不是“泄漏”,因为它不会无限期地增长。从严格意义上讲,这仍然是一个漏洞,但除非你是学究的,否则通常是可以忽略的。

分配而不是自由分配的局部变量几乎总是泄漏。

下面是一个例子

int foo(void){
    static char *working_buf = NULL;
    char *temp_buf;
    if (!working_buf) {
         working_buf = (char *) malloc(16 * 1024);
    }
    temp_buf = (char *) malloc(5 * 1024);

    ....
    ....
    ....}

瓦兰德将报告Work_BUF为“仍然可达-16k”,temp_BUF报告为“绝对丢失-5k”。


查看完整回答
反对 回复 2019-07-11
  • 3 回答
  • 0 关注
  • 423 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信