跟踪C ++内存分配

我正在寻找一种方法来跟踪C ++程序中的内存分配。 我对内存泄漏感兴趣,这似乎是大多数工具试图find的东西,而是为应用程序创build内存使用情况configuration文件。 理想的输出可能是一个大的函数名称列表,加上最大分配的字节数,或者更好,随着时间的推移堆的graphics表示。 横轴是时间,纵轴堆空间。 每个函数都会得到它自己的颜色,并根据分配的堆字节来绘制线条。 用于标识分配的对象types的奖励点也是如此。

这个想法是find内存瓶颈/可视化哪些function/线程消耗最多的内存,应瞄准进一步优化。

我简要地看了一下Purify,BoundsChecker和AQTime,但是他们似乎并不是我所追求的。 Valgrind看起来合适,但是,我在Windows上。 Memtrack看上去很有希望,但是需要对源代码进行重大改变。

我的谷歌技能一定是失败了,因为它似乎并不是一个不寻常的要求? 所有需要的信息来创build一个这样的工具应该可以从程序的debugging符号加上运行时API调用 – 不是吗?

使用Valgrind及其工具Massif。 它的示例输出(它的一部分):

99.48% (20,000B) (heap allocation functions) malloc/new/new[], --alloc-fns, etc. ->49.74% (10,000B) 0x804841A: main (example.c:20) | ->39.79% (8,000B) 0x80483C2: g (example.c:5) | ->19.90% (4,000B) 0x80483E2: f (example.c:11) | | ->19.90% (4,000B) 0x8048431: main (example.c:23) | | | ->19.90% (4,000B) 0x8048436: main (example.c:25) | ->09.95% (2,000B) 0x80483DA: f (example.c:10) ->09.95% (2,000B) 0x8048431: main (example.c:23) 

所以,你会得到详细的信息:

  • 世卫组织分配了上述例子中的记忆(函数:g(),f()和main()); 你也会得到完整的回溯导致分配function,
  • 到WHICH数据结构存储器去了(在上面的例子中没有数据结构),
  • 发生的时候,
  • 所有分配内存的PERCENTAGE(g:39.7%,f:9.95%,主要:49.7%)。

这里是Massif手册

您可以跟踪堆分配以及堆栈分配(默认closures)。

PS。 我刚刚读到你在Windows上。 但是我会留下答案,因为它给出了一个你可以从一个可能的工具中获得的图片。

微软拥有良好的文档记忆追踪function。 但是,由于某种原因,他们在开发人员社区中并不是很出名。 这些是CRTdebuggingfunction。 好的起点将是CRT Debug Heap函数 。

检查以下链接了解更多详情

  1. 堆状态报告function
  2. 跟踪堆分配请求 。 可能这是你正在寻找的function。

对于通用的C ++内存跟踪器,您将需要重载以下内容:

 global operator new global operator new [] global operator delete global operator delete [] any class allocators any in-place allocators 

棘手的一点是获取有用的信息,重载操作符只有分配器的大小信息和删除的内存指针。 一个答案是使用macros。 我知道。 讨厌。 一个例子 – 放在所有源文件包含的头文件中:

 #undef new void *operator new (size_t size, char *file, int line, char *function); // other operators #define new new (__FILE__, __LINE__, __FUNCTION__) 

并创build一个源文件:

 void *operator new (size_t size, char *file, int line, char *function) { // add tracking code here... return malloc (size); } 

以上只适用于没有任何在类范围内定义的操作符的情况。 如果你有一些在课堂上的范围,做:

 #define NEW new (__FILE__, __LINE__, __FUNCTION__) 

并用“新types”replace“新types”,但这需要潜在地更改大量的代码。

因为这是一个macros,删除内存跟踪器是非常简单的,头成为:

 #if defined ENABLED_MEMORY_TRACKER #undef new void *operator new (size_t size, char *file, int line, char *function); // other operators #define NEW new (__FILE__, __LINE__, __FUNCTION__) #else #define NEW new #endif 

和执行文件:

 #if defined ENABLED_MEMORY_TRACKER void *operator new (size_t size, char *file, int line, char *function) { // add tracking code here... return malloc (size); } endif 

监控您的电脑的内存使用情况对于游戏开发包含一个我正在寻找的几乎完美的例子。 它花了一段时间才能运行,但文章的作者是非常有帮助的。 你可以在这里find工具的源代码Memtracer 。

我也在SWENG (软件工程邮件列表)上得到了很多有用的答案。 该线程被称为“[Sweng-Gamedev]监视C ++内存使用情况?”。

试试这个也是: Memory Validator

在Mac OS X上,您可以使用代码分析工具Shark来完成这项工作,IIRC。

在Xcode上,您可以使用Instruments来跟踪分配,虚拟机使用情况以及其他一些参数。 在iOS开发者中很受欢迎,但值得一试。

英特尔(R)单一事件API中实现了“随时间变化的堆的graphics表示” – 接近您正在寻找的内容,详细信息可以在本文中find(其相当大的一部分放在此处)。 内存块分配随着时间的推移

它显示每个块大小的分配时间线,并允许添加额外的标记到您的代码,以更好地了解整个图片。