检测内存泄漏在C + + Qt结合?

我有一个使用串行通信与外部设备交互的应用程序。 该设备有两个版本不同的实现。 – >一个由我的团队开发和testing – >另一个团队的另一个版本。 由于另一支队伍已经离队,我们的队伍正在维修。 在testing应用程序的前一天,我注意到应用程序在启动时占用了60Mb的内存,令人恐慌的是它的内存使用量开始以200Kb大小增长,在60小时内它增加到295Mb,尽pipe响应速度没有减慢和应用程序的使用。 我一次又一次地testing,并重复使用相同的内存使用模式。

该应用程序是在RHEL4上用C ++ Qt 4.2.1编写的。

我用mtrace来检查是否有内存泄漏,并且没有显示这样的泄漏。 然后我使用了valgrind memcheck工具,但是它给出的信息是神秘而不是非常确定的,它显示了Qt的graphics元素的泄漏,在审查时可以直接拒绝。

我正在修复哪些其他工具/方法可以用来查明这些内存泄漏的来源(如果有的话)。 – >另外,在更大的上下文中,我们如何检测和debuggingC ++ Qt应用程序中的内存泄漏? – >我们如何检查一个进程在Linux中使用多less内存?

我用gnome-system-monitor和top命令检查应用程序使用的内存,但是我听说上面提到的工具给出的结果不是绝对的。

编辑:

我用ccmalloc检测内存泄漏,这是closures应用程序后得到的错误报告。 在应用程序执行期间,没有错误消息。

| ccmalloc报告|

================================================== =====

| 总数| 分配| 释放| 垃圾|

+ ———– ————- + ————- + + ——— —- +

| 字节| 387325257 | 386229435 | 1095822 |

+ ———– ————- + ————- + + ——— —- +

|分配| 1232496 | 1201351 | 31145 |

+ ————————————————- —- +

| 检查次数:1

| 数量:2434332 |

| 检索地址的function名称…完成。 |

| 从gdb读取文件信息…完成。 |

| 按未收回的字节数进行sorting…完成。 |

| 呼叫链的数量:3 |

| 被忽略的呼叫链数量:0 |

| 报告的呼叫链数:3

| 内部呼叫链的数量:3 |

| 图书馆呼叫链的数量:1 |

================================================== =====

|

| 3.1%=在47次分配中分配的33.6 KB垃圾

| |

| | 0X ???????? 在

| |

| | 0x081ef2b6 in

| | 在src / wrapper.c:489

| |

| | 0x081ef169在<_realloc>中

| | 在src / wrapper.c:435

| |

| `—–> 0x081ef05c in

| 在src / wrapper.c:318

|

| 0.8%= 8722字节的垃圾分配在35个分配

| |

| | 0X ???????? 在

| |

| | 0x081ef134 in

| | 在src / wrapper.c:422

| |

| `—–> 0x081ef05c in

| 在src / wrapper.c:318

|

| 0.1%= 1144字节的垃圾分配在5个分配

| |

| | 0X ???????? 在

| |

| | 0x081ef1cb in

| | 在src / wrapper.c:455

| |

| `—–> 0x081ef05c in

| 在src / wrapper.c:318

|

`————————————————- —–

免费(0x09cb650c)报告后

(这可能发生在静态析构函数中。

当链接把`ccmalloc.o'放在末尾(对于gcc)或者

在目标文件列表的前面)。

报告后免费(0x09cb68f4)

报告后免费(0x09cb68a4)

报告后免费(0x09cb6834)

免费(0x09cb6814)报告后

报告后免费(0x09cb67a4)

免费(0x09cb6784)报告后

报告后免费(0x09cb66cc)

报告后免费(0x09cb66ac)

免费(0x09cb65e4)报告后

免费(0x09cb65c4)报告后

免费(0x09cb653c)报告后

ccmalloc_report()在非有效状态下调用

我不知道,这是什么意思,它似乎没有表明任何内存泄漏给我? 我可能是错的。 你们有没有遇到过这种情况? 链接|编辑|删除

如果你没有真正阅读手册或者其他文件,Valgrind可能是个婊子(初学者的手册页) – 但是它们是值得的。

基本上,你可以通过在你的应用程序中使用–gen-suppressions = all来运行valgrind,然后为源自QT本身的每个块创建一个抑制,然后使用抑制文件来阻止这些错误,你应该留下只有在你自己的代码中有错误。

另外,如果这样可以让事情变得更容易,你可以尝试使用valgrind通过一个alleyoop前端。

还有一些其他工具可以用来检测内存泄漏,Linux Journal在这里有文章: http : //www.linuxjournal.com/article/6556

最后,在某些情况下,一些静态分析工具也可以发现内存错误。

我想提出一个小问题,就是因为一个进程所使用的Meory越来越多,所以并没有出现内存泄漏。 以文字处理器为例 – 在写文本时,内存使用量增加了,但是没有泄漏。 实际上,大多数进程在运行时会增加它们的记忆用量,直到它们达到某种接近稳定的状态,在那里物体被创建时会被旧物体所破坏。

你说你尝试了Valgrind的memcheck工具; 你还应该尝试一下massif工具,它应该能够随时间绘制堆的使用情况,并告诉你从哪里分配内存。

测量内存使用量不是太有用的原因之一是,他们没有考虑到内存通常在进程之间共享。 为了最佳地了解进程分配内存的位置,我建议使用最新的Linux内核,并检查/proc/<pid>/maps作为您的进程。 这显示了什么内存映射到该进程和从哪里。 例如,这里是我的系统上konqueror的一个片段。

 b732a000-b7a20000 r-xp 00000000 fd:05 205437 /usr/lib/qt3/lib/libqt-mt.so.3.3.8
大小:7128 kB
 Rss:3456 kB
 Pss:347 kB
共享清理:3452 kB
共享脏:0 kB
私人清洁:4 kB
私人脏:0 kB
引用:3452 kB

这里最重要的是,虽然由于libqt-mt.so.3.3.8的加载而产生的驻留集合是3456kB,但是所有加载该库的进程之间共享的却是4kB,所以这是一个一次性的系统全部成本。 top不公开这个信息,所以从top阅读RSS是误导性的。