tcmalloc ReleaseFreeMemory()未正确释放内存

3
我正在使用tcmalloc在我的应用程序中,其中堆在非常大的范围内增长和收缩,显然我面临tcmalloc未将内存释放回操作系统的问题。现在我尝试使用API MallocExtension::instance()->ReleaseFreeMemory(); 来解决这个问题。它可以正常工作并释放内存。但是,当我让进程运行一段时间后(比如5分钟),内存仍然会增加到初始水平(有时更多)。奇怪的事情是应用程序是空闲的。
以下是我的代码:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include "google/malloc_extension.h"

int main(int argc, char* argv[])
{

    char** names;
    printf("\nBefore starting the execution. Press enter to start.... \n");
    getchar();
    if (argc < 3)
    {
        printf("Usage: ./a.out <numTimes> <allocsize>\n");
        exit(1);
    }
    int numTimes = atoi(argv[1]);
    int allocSize = atoi(argv[2]);
    names = (char**) malloc(numTimes * sizeof(char*));
    for (int i = 0; i < numTimes; i++)
    {
        names[i] = (char*)malloc(allocSize);
    }
    printf("\nDone with the execution. Press enter to free the memory.... \n");
    getchar();
    for (int i = 0; i < numTimes; i++)
    {
        free(names[i]);
    }
    free(names);
    printf("\nDone with the freeing. Press enter to release the memory.... \n");
    getchar();
    MallocExtension::instance()->ReleaseFreeMemory();
    printf("\nDone with the execution. Press enter to exit.... \n");
    getchar();
    return 0;
}



./a.out 10000 30000

after release

  PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND            
18823 sarath    20   0  332m 4568 1268 S  0.0  0.2   0:00.05 a.out  

after sometimes(4-5 mins)

  PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND            
18823 sarath    20   0  332m 129m 1268 S  0.0  6.5   0:00.05 a.out   

感谢任何帮助。

我放弃了使用tcmalloc,转而使用tbbmalloc,因为在某些情况下,tcmalloc不能释放内存。tbbmalloc提供了类似的性能,并且表现更好。 - egur
@Sarath,你这里有一个错误:(char**)malloc(numTimes) -> malloc(numTimes*sizeof(char*)),否则内存不够,你只分配了numTimes个字节,但需要存储numTimes个指针(dword,即每个指针4个字节,如x86平台)。此外,在释放循环后,你没有释放names本身。 - mblw
@Alexei 谢谢你。我只是专注于 tcmalloc 问题。已经编辑了问题。 - sarath
1个回答

3
您可以尝试包含malloc.h并在调用MallocExtension :: instance() -&gt; ReleaseFreeMemory()时将malloc_stats()包装起来,就像这样...
malloc_stats();
MallocExtension::instance()->ReleaseFreeMemory();
malloc_stats();

您应该看到类似这样的内容:

之前:

4997120 (    4.8 MiB) Bytes in page heap freelist
7434392 (    7.1 MiB) Actual memory used (physical + swap)
0 (    0.0 MiB) Bytes released to OS (aka unmapped)

之后:

0 (    0.0 MiB) Bytes in page heap freelist
2437272 (    2.3 MiB) Actual memory used (physical + swap)
4997120 (    4.8 MiB) Bytes released to OS (aka unmapped)

如果没有其他问题,这将验证内存是否从页面堆的空闲列表中被释放,并且现在已经被取消映射。

这是我的结果 之前 MALLOC:+ 316915712(302.2 MiB)页面堆空闲列表中的字节 MALLOC:= 330051736(314.8 MiB)实际使用的内存(物理+交换) MALLOC:+ 0(0.0 MiB)字节释放到操作系统(也称为未映射) 之后 MALLOC:+ 0(0.0 MiB)页面堆空闲列表中的字节 MALLOC:= 13136024(12.5 MiB)实际使用的内存(物理+交换) MALLOC:+ 316915712(302.2 MiB)字节释放到操作系统(也称为未映射) 这很好。但仍然在4-5分钟后,内存会像以前一样增长。 - sarath

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接