3

I'm using tcmalloc in one of my application in which the heap grow and shrink in very large amount, obviously I faced the issue where tcmalloc is not releasing the memory back to OS. Now I tried using the api to do that using MallocExtension::instance()->ReleaseFreeMemory();. It worked fine and released the memory. But when I keep my process running after some time (say 5 mins) the memory is still increasing to the initial level (sometimes more). The weird thing is application is idle.

Here is my code

#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   

Appreciate any help.

trincot
  • 317,000
  • 35
  • 244
  • 286
sarath
  • 513
  • 6
  • 18
  • I gave up on tcmalloc and switched to tbbmalloc because tcmalloc in some cases doesn't free up memory. tbbmalloc offered similar performance and behaved better. – egur Jan 01 '14 at 09:32
  • @Sarath You have an error here: `(char**)malloc(numTimes)` -> `malloc(numTimes*sizeof(char*))` otherwise memory not enought, you allocate only numTimes bytes but need to stored numTimes pointer (dword, i.e. 4 bytes each, as for x86 platform). Also your not freeing names itself after the free-loop. – mblw May 01 '14 at 13:04
  • @Alexei Thanks for that. I was just concentrated on tcmalloc issue. Edited the question. – sarath May 01 '14 at 13:32

1 Answers1

3

You can try including malloc.h and wrapping malloc_stats() around your call to MallocExtension::instance()->ReleaseFreeMemory(), like so....

malloc_stats();
MallocExtension::instance()->ReleaseFreeMemory();
malloc_stats();

You should then see something like this:

Before:

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)

After:

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)

If nothing else this will verify that the memory's actually being freed by from the page heap freelist and is now unmapped.

mctwynne
  • 91
  • 2
  • 5
  • Here's my results Before MALLOC: + 316915712 ( 302.2 MiB) Bytes in page heap freelist MALLOC: = 330051736 ( 314.8 MiB) Actual memory used (physical + swap) MALLOC: + 0 ( 0.0 MiB) Bytes released to OS (aka unmapped) After MALLOC: + 0 ( 0.0 MiB) Bytes in page heap freelist MALLOC: = 13136024 ( 12.5 MiB) Actual memory used (physical + swap) MALLOC: + 316915712 ( 302.2 MiB) Bytes released to OS (aka unmapped) This is fine. But still after 4-5 mins the memory is growing up like the same. – sarath Mar 04 '14 at 06:30