Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
“是什么意思?”;“回收储存”;关于螺纹';pthread_join()&;pthread_detach()?_C_Multithreading_Memory Leaks_Valgrind - Fatal编程技术网

“是什么意思?”;“回收储存”;关于螺纹';pthread_join()&;pthread_detach()?

“是什么意思?”;“回收储存”;关于螺纹';pthread_join()&;pthread_detach()?,c,multithreading,memory-leaks,valgrind,C,Multithreading,Memory Leaks,Valgrind,我编写了一个简单的线程程序: #include <stdio.h> #include <pthread.h> #include <unistd.h> #include <stdint.h> #define THREADS 5 void* HelloWorld(void *t) { printf("Thread ID #%lu: (%lu) Hello World !!\n", pthread_self(), (unsigned

我编写了一个简单的线程程序:

#include <stdio.h>
#include <pthread.h>
#include <unistd.h>
#include <stdint.h>

#define THREADS     5

void* HelloWorld(void *t) 
{
    printf("Thread ID #%lu: (%lu) Hello World !!\n", pthread_self(), (unsigned long)t);         

    return NULL;
}

int main()
{
    pthread_t thread[THREADS];
    uint32_t i;
    int err;

    for(i = 0; i < THREADS; ++i)
    {   
        err = pthread_create(&thread[i], NULL, &HelloWorld, (void*)(unsigned long long)i);
        if(err != 0)
        {   
            printf("Error %d: Thread %d Creation Unsuccessful !!\n", err, i); 
        }   
        printf("Thread %lu in main()\n", pthread_self());
    }   
/*
    for(i = 0; i < THREADS; ++i)
    {
        pthread_join(thread[i], NULL);  // Error checking implemented
    }
*/
    return 0;
}
无论程序中是否使用
pthread\u join()
,它都会显示相同的内存使用/泄漏输出

请在我阅读时解释这种行为:

对于使用设置为pthread_CREATE_JOINABLE的detachstate属性创建的每个线程,最终应调用pthread_join()或pthread_detach()函数,以便回收与该线程关联的存储


如果我不调用
pthread\u join()

如何回收存储从我的理解中提出了两个问题。一个是为什么
valgrind
在调用
pthread_join()
或不调用
pthread_join()
的情况下报告相同的内存泄漏,另一个是如果调用
pthread_join()
实际上没有释放任何内存,如何回收存储

这两个问题的一个可能解释是,在调用
pthread_join()
后,线程库实际上并没有释放任何内存,而是将分配的资源放在“如果我在将来创建另一个线程,则可用”容器中。让我们将该容器称为池。下一次调用
pthread\u create()
可以重用池中的任何资源。如果池为空,则分配新内存

如果不调用
pthread\u join()
,与退出线程关联的任何资源都不会返回到池中。因此,这些资源将保持不可用,池将保持为空,因此新的
pthread_create()
将为线程创建请求分配更多资源


这意味着
pthread\u join()
不一定会释放任何内存。它可以简单地将收获的资源放入由线程库维护的池中。因此,无论是否调用
pthread_join()
valgrind
都会显示相同数量的“泄漏”内存。但是,内存是由
pthread\u join()
回收的,因为它被放在一个池中,以便将来调用
pthread\u create()

据我所知,有两个问题。一个是为什么
valgrind
在调用
pthread_join()
或不调用
pthread_join()
的情况下报告相同的内存泄漏,另一个是如果调用
pthread_join()
实际上没有释放任何内存,如何回收存储

这两个问题的一个可能解释是,在调用
pthread_join()
后,线程库实际上并没有释放任何内存,而是将分配的资源放在“如果我在将来创建另一个线程,则可用”容器中。让我们将该容器称为池。下一次调用
pthread\u create()
可以重用池中的任何资源。如果池为空,则分配新内存

如果不调用
pthread\u join()
,与退出线程关联的任何资源都不会返回到池中。因此,这些资源将保持不可用,池将保持为空,因此新的
pthread_create()
将为线程创建请求分配更多资源


这意味着
pthread\u join()
不一定会释放任何内存。它可以简单地将收获的资源放入由线程库维护的池中。因此,无论是否调用
pthread_join()
valgrind
都会显示相同数量的“泄漏”内存。但是,内存是由
pthread\u join()
回收的,因为它被放在池中,以便将来调用
pthread\u create()

如果线程被连接,我无法重现任何泄漏。我在最近的一个Debian Stable上测试了这个。@alk:所以无论如何,我应该使用
pthread\u join()
,对吧!!是的,通过
pthread\u attr\u setdetachstate()
或调用
pthread\u detachstate()
将线程的分离状态显式设置为
pthread\u CREATE\u detachstate
,应为每个线程调用
pthread\u join()
。如果线程已连接,我无法复制任何泄漏。我在最近的一个Debian Stable上测试了这个。@alk:所以无论如何,我应该使用
pthread\u join()
,对吧!!是的,通过
pthread\u attr\u setdetachstate()
或通过调用
pthread\u detachstate()将线程的分离状态显式设置为
pthread\u CREATE\u detachstate
的每个线程调用
pthread\u join()
。但是我在
pthread\u create
@nishant之后在单独的循环中执行了
pthread\u join
:你问我为什么在使用
pthread\u join()和不使用
pthread\u join()时内存会显示相同的泄漏。很抱歉,我不理解你的答案,请解释更多。好的,我扩展了答案。好的!快速总结我的理解:内存总是分配给
pthread\u create
调用,但是如果我使用
pthread\u join
,预先分配的资源也可以被新线程使用,但在
pthread\u create
@nishant之后,我在单独的循环中完成了
pthread\u join
:你问为什么在
pthread\u join()和
pthread\u join()的情况下内存会显示相同的泄漏。很抱歉,我不理解你的答案,请解释更多。好的,我扩展了答案。好的!快速总结我的理解:内存总是分配给
pthread\u create
调用,但是如果我使用
pthread\u join
,预先分配的资源也可以被新线程使用,否则将无法使用。
valgrind --tool=memcheck --leak-check=full --show-reachable=yes ./hello