简体   繁体   English

C ++程序立即使用2 GB的RAM:如何找到罪魁祸首?

[英]C++ Program immediately using 2 GB of RAM: how to find culprit?

I have a program that, when queried on initialisation, is immediately using > 2 GB of RAM. 我有一个程序,在初始化时被查询,立即使用> 2 GB的RAM。 Basically the code is like this: 基本上,代码是这样的:

#include <blah>

int main() {
    cout << get_mem_usage() << endl;
    //Lots of things happen, but no significant memory usage
    return 0;
}

Output: [2013-02-15 18:38:05.865283] 2147.71 Mb 输出:[2013-02-15 18:38:05.865283] 2147.71 Mb

I am, however, linking to a lot of different shared object files: I checked ldd and I am linking to 58 libraries, with a combined .so size of 66 MB. 但是,我链接到许多不同的共享对象文件:我检查了ldd,并链接到58个库,.so的总大小为66 MB。

I'm pretty sure that the get_mem_usage program is returning the correct values: these agree with top and massif output. 我很确定get_mem_usage程序会返回正确的值:这些值与top和massif输出一致。

I should also mention that I am linking against the ROOT framework for High Energy Physics analysis. 我还应该提到,我与ROOT框架进行了高能物理分析。

I am using Linux x86_64, and the get_mem_usage() function is homegrown. 我使用的是Linux x86_64,并且get_mem_usage()函数是本地开发的。

I would like to reduce the memory usage of the program, if at all possible. 如果可能的话,我想减少程序的内存使用量。

My first guess: static initizations in some of the libraries you are linking. 我的第一个猜测:您正在链接的某些库中的静态初始化。

Insert a long pause as the very first line of main() and look through the /proc/<pid>/ to see where the memory is allocated. main()第一行插入一个较长的停顿,然后浏览/ proc / <pid> /以查看分配内存的位置。 For example: 例如:

  • /proc/12345/task/12345/maps / proc / 12345 / task / 12345 / maps
  • /proc/12345/task/12345/smaps / proc / 12345 / task / 12345 / smaps

I could not find any documentation on get_mem_usage() . 我在get_mem_usage()上找不到任何文档。

What kind of memory usage is it reporting? 它报告哪种内存使用情况?

Determining memory usage in a virtual memory system is quite a challenge. 确定虚拟内存系统中的内存使用量是一个很大的挑战。

The actual amount of memory used is your resident set size . 实际使用的内存量是您的resident set size That is basically any physical memory you are using. 这基本上就是您正在使用的任何物理内存。 Although with shared libraries (libc for an example), that memory consumption is (partially) shared with other applications as well. 尽管使用共享库(例如libc),但该内存消耗也(部分)与其他应用程序共享。

Then there is a virtual set size - the total of any virtual memory mapped, any anonymous mappings, any other mapped files. 然后有一个虚拟集大小-映射的任何虚拟内存,任何匿名的映射,任何其他映射的文件的总和。 Much of that will not really be backed with physical memory (ie not resident) and may be shared amongst other programs. 其中大部分将不会真正由物理内存(即不驻留)支持,并可能在其他程序之间共享。

pmap -x <pid> will give you a neat table, including resident/dirty parts. pmap -x <pid>将给您一个整洁的表,包括居民/肮脏的部分。

Overall, it is worth researching what 'uses' all that memory, but it might not be that much a problem at all. 总体而言,值得研究“使用”所有内存的内容,但这可能根本不是一个问题。 If you are running on a 32bit system, things might get a little tight anyway later on (as your virtual address space is limited). 如果您在32位系统上运行,则稍后可能会变得有些紧张(因为您的虚拟地址空间有限)。

Another possibility: if you have shared memory between your apps, then that shared memory counts against every app that accesses the shared memory segment, even though it is only allocated once. 另一种可能性:如果您的应用程序之间有共享内存,则该共享内存将计入访问共享内存段的每个应用程序,即使该共享内存仅分配一次。 So if a 2gb shared memory segment is allocated somewhere, and 20 different applications use that shared memory, all 20 applications will seem as if they're using 2+gb of memory, making it look as if 40+gb of memory has been allocated. 因此,如果在某处分配了2gb共享内存段,并且有20个不同的应用程序使用该共享内存,则所有20个应用程序似乎都在使用2 + gb的内存,从而看起来好像已经分配了40 + gb的内存。

In this case, it turned out to be a single library (that I wasn't directly using) that allocated 1.9 G memory. 在这种情况下,原来是分配了1.9 G内存的单个库(我没有直接使用)。 I found it by looking through /proc/12345/smaps 我通过浏览/ proc / 12345 / smaps找到了它

2aaab2197000-2aab2ba86000 rw-p 2aaab2197000 00:00 0 
Size:           1991612 kB

Looking up the address in /proc/12345/maps I found 在我发现的/ proc / 12345 / maps中查找地址

2aaab2174000-2aaab2197000 rw-p 0016c000 4f9:2c566 59607963               /mnt/lustre/epp_scratch/atlas/sm442/Irvex/lhapdf-5.8.8/lib/.libs/libLHAPDF.so.0.0.0

This is a fortran library that was doing an enormous amount of static initialisation. 这是一个进行大量静态初始化的fortran库。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM