Detached pthreads and memory leak



  • Can somebody please explain to me why this simple code leaks memory?

    I believe that since pthreads are created with detached state their resources should be released inmediatly after it's termination, but it's not the case.

    My environment is Qt5.2.

    @#include <QCoreApplication>
    #include <windows.h>

    void *threadFunc( void *arg )
    {
    printf("#");
    pthread_exit(NULL);
    }

    int main()
    {
    pthread_t thread;
    pthread_attr_t attr;

    while(1)
        {
        printf("\nStarting threads...\n");
        for(int idx=0;idx<100;idx++)
            {
            pthread_attr_init(&attr);
            pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
            pthread_create( &thread, &attr, &threadFunc, NULL);
            pthread_attr_destroy ( &attr );
            }
        printf("\nSleeping 10 seconds...\n");
        Sleep(10000);
        }
    }@
    

    !http://www.reservascentral.com.ar/leak.png(Memory Consumption Graph)!

    Thanks in advance!



  • I agree with you here. There is no Qt code here. It is all basic operating system pthread calls. Also where are you releasing the memory allocated 'thread' ? Probably this causing the memory leak.



  • Hello Dheerendra, thank you for your answer.

    I believe that each thread's resources are (should be) released after pthread_exit() call.

    How do I suposse to release the memory allocated by "thread"?



  • Deerendra, don't know if you were referring to this, but I tried it and the leak persist:

    @#include <QCoreApplication>
    #include <windows.h>

    void *threadFunc( void *arg )
    {
    printf("#");
    pthread_exit(NULL);
    }

    int main()
    {
    while(1)
    {
    printf("\nStarting threads...\n");
    for(int idx=0;idx<1000;idx++)
    {
    //pthread_t thread;
    pthread_t * thread = (pthread_t *) malloc(sizeof(pthread_t));
    pthread_attr_t * attr = (pthread_attr_t *) malloc(sizeof(pthread_attr_t));

            pthread_attr_init(attr);
            pthread_attr_setdetachstate(attr, PTHREAD_CREATE_DETACHED);
            pthread_create( thread, attr, &threadFunc, NULL);
            pthread_attr_destroy ( attr );
    
            free(thread);
            free(attr);
            }
        printf("\nSleeping 10 seconds...\n");
        Sleep(10000);
        }
    }@


  • I discovered that if I add a slight delay of 5 milliseconds inside the for loop the leak is WAY slower:

    @ for(int idx=0;idx<100;idx++)
    {
    pthread_attr_init(&attr);
    pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
    pthread_create( &thread, &attr, &threadFunc, NULL);
    pthread_attr_destroy ( &attr );
    Sleep(5); /// <--- 5 MILLISECONDS DELAY ///
    }@

    !http://reservascentral.com.ar/leak-dl.png(Memory leak graph with slight delay)!

    This is freaking me out, could somebody please tell me what is happening? How this slight delay may produce such a significant change? (or alter the behavior in any way)

    Any advice would be greatly appreciated.

    Thanks.



  • It definitely makes sense that the slight delay shows less memory usage, as there are less multiple threads running simultaneously. What is also dangerous is your call "free(thread);", as you don't know whether the thread has really finished yet (pthread_join)...
    A thread itself has some memory usage just because it is alive and although you don't have any variables in your threadFunc. So there actually is no memory leakage.
    See http://www.sourceware.org/pthreads-win32/manual/pthread_attr_setstacksize.html for the stack size that each thread does own ...



  • P.S. Under Linux the default stack size per thread seems to be 2 MBytes ... Maybe it's similar under Windows... So yes, I guess there is no memory leakage at all. ;)



  • vidar thank you for your answer, I agree with you when you say that more active threads means more memory ussage.

    But please note that I'm creating 100 threads that do nothing (exit inmediatly) and waiting 10 seconds, that is an eternity for all threads to finish and the memory to be recovered.

    And also please note that I'm creating detached threads and not joined, so I believe I can securely call free after thread creation. But anyway this leak is happening with dynamic thread and attr variables but also with static, it was only a test after what Dheerendra suggest.

    About your second comment: Again, all the threads should liberate all the resources when they finish in this 10 seconds eternity, so it doesn't matter how much memory they take but the fact that they have to give back this memory to the system as soon as they finish.

    I feel that I'm missing something that is stupid but I'm blind now.



  • Hi Fracu, you are right, I didn't notice that the x axis is really big.


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.