【发布时间】:2011-09-14 01:02:01
【问题描述】:
有没有办法在 perl (>=5.012) 线程中获得警报(或其他一些超时机制)?
【问题讨论】:
标签: multithreading perl timeout
有没有办法在 perl (>=5.012) 线程中获得警报(或其他一些超时机制)?
【问题讨论】:
标签: multithreading perl timeout
在您的主线程中运行 alarm,并使用信号处理程序向您的活动线程发出信号。
use threads;
$t1 = threads->create( \&thread_that_might_hang );
$t2 = threads->create( \&thread_that_might_hang );
$SIG{ALRM} = sub {
if ($t1->is_running) { $t1->kill('ALRM'); }
if ($t2->is_running) { $t2->kill('ALRM'); }
};
alarm 60;
# $t1->join; $t2->join;
sleep 1 until $t1->is_joinable; $t1->join;
sleep 1 until $t2->is_joinable; $t2->join;
...
sub thread_that_might_hang {
$SIG{ALRM} = sub {
print threads->self->tid(), " got SIGALRM. Good bye.\n";
threads->exit(1);
};
... do something that might hang ...
}
如果您需要为每个线程设置不同的警报,请查看一个允许您设置多个警报的模块,例如Alarm::Concurrent。
编辑:评论者指出threads::join 会干扰SIGALRM,因此您可能需要测试$thr->is_joinable 而不是调用$thr->join
【讨论】:
alarm 永远不会关闭。 join 似乎阻止了 SIGALRM。这是过去 5 年的新行为吗?
thr->join(),但没有,所以现在我正在考虑用thr->is_joinable() 轮询线程状态,所以我不阻塞SIGALRM