0

我用 C++ 编写了一个需要大量内存的计算机模拟。它在迭代中运行,并且在每次迭代中分配大量应该在迭代结束时释放的内存。它还使用 c++11 的实现<thread>来并行运行东西。

当我在我的台式机上测试程序时,它表现良好:它永远不会超过我允许的内存,并且在时间和迭代期间,没有任何东西堆积。然而,当我将程序提交到我们的计算集群时,使用的内存(我只能通过排队软件访问)随着时间的推移而增长,并且远远超过了我机器上使用的内存。

首先让我非常粗略地向您展示该软件的结构:

for thread in n_threads:
    vector<Object> container;
    for iteration in simulation:
        container.clear()
        container.resize(a_large_number)
        ... do stuff ...

比方说,在我的机器上,容器占用2GB了内存。我可以同时看到htop这些valgrind --tool=massif永远2GB不会超过。什么都没有堆积。然而,在集群上,我可以看到内存不断增长,直到它变得远远超过2GB(并且作业被杀死/计算节点冻结......)。请注意,我限制了两台机器上的线程数,并且可以确保它们是相等的。

我所知道的是,libc集群上的 非常旧。要编译我的程序,我需要在集群的前端节点上编译g++并更新新版本。libc该软件在计算节点上运行良好(除了这个内存问题),但 libc 在那里要旧得多。这可能是内存分配的问题,特别是与线程一起使用吗?我怎么能调查呢?

4

1 回答 1

1

是的,根据 GNU libc 的使用年限,您可能会遗漏一些重要的内存分配优化。以下是一些可以尝试的事情(不用说,冒着性能损失的风险):

  1. 您可以尝试通过调整 malloc/free 行为mallopt();使用M_MMAP_MAXM_MMAP_THRESHOLD选项 鼓励 更多 的 分配 进行mmap(), 这样 内存 就 保证 之后 还给 系统free().

  2. 尝试将容器的分配器设置为__gnu_cxx::malloc_allocator,以确保mallopt()调整影响容器。

  3. 尝试在调整大小后调用container.shrink_to_fit(),以确保向量没有保留比严格需要更多的内存。

于 2013-10-16T08:07:24.270 回答