为啥我的代码中断线程泄漏?
Posted
技术标签:
【中文标题】为啥我的代码中断线程泄漏?【英文标题】:Why does my code that interrupts a thread leak?为什么我的代码中断线程泄漏? 【发布时间】:2017-10-05 08:19:59 【问题描述】:这是一个非常简单的例子,所以请稍等片刻......
#include <boost/thread/thread.hpp>
struct foo
boost::thread t;
void do_something() std::cout << "foo\n";
void thread_fun()
try
boost::this_thread::sleep(boost::posix_time::seconds(2));
boost::this_thread::disable_interruption di;
do_something();
catch (boost::thread_interrupted& e)
void interrupt_and_restart()
t.interrupt();
//if (t.joinable()) t.join(); // X
t = boost::thread(&foo::thread_fun,this);
;
int main()
foo f;
for (int i=0;i<1000;i++)
f.interrupt_and_restart();
boost::this_thread::sleep(boost::posix_time::seconds(3));
当我在 linux 上运行此代码并使用 top
查看内存消耗时,我看到使用的虚拟内存不断增加(并且我的实际代码有时会崩溃)。只有当我在中断线程后加入线程时,内存使用量才会保持不变。这是为什么?
【问题讨论】:
所有线程都需要一些内存来记账(比如存储 real 线程函数的返回值)。如果您不join
线程,则该内存将永远不会被回收。
@Someprogrammerdude 出于某种原因,我的印象是,如果线程以thread_fun
结束,无论我是否加入,它都会干净地终止。我已经知道错了,但不完全理解
@Someprogrammerdude 这个问题的题外话:我还观察到这个特定线程(我的意思是真实代码中的那个,但它看起来很相似)令我惊讶的是,它使用的内存比任何其他线程都多我的系统和我知道的唯一区别是我中断了它,但那将是一个完全不同的问题......
@user5226582 您链接的问题是关于 C# 的。是的,只有睡眠应该被打断,而不是实际工作(调用doSomething
)
【参考方案1】:
您没有加入线程:因此,跟踪线程所需的一些资源保持分配状态。
一个未加入的线程即使已被终止(例如它的线程 id 仍然有效),仍会使用一些系统资源。
此外,系统可能会对同时分配的线程数施加限制,并且未加入的线程数计入该限制。
在我的 Linux VM 上使用 cat /proc/sys/kernel/threads-max
可以得到 23207 个线程。
当您销毁可连接线程对象时,最新版本的 boost 实际上应该会崩溃,而旧版本很乐意遵守销毁请求。
【讨论】:
以上是关于为啥我的代码中断线程泄漏?的主要内容,如果未能解决你的问题,请参考以下文章
当我在 Thread 对象上调用 run() 时,为啥我的 Java 程序会泄漏内存?