I'm writing a multithreaded program which needs to be terminated with the following bash line:
killall -QUIT -w procname
I decided to use a thread to receive some signals I need to handle, like SIGQUIT and SIGUSR1, and to ignore SIGQUIT in the others. To ignore the signal I wrote this:
struct sigaction s;
s.sa_handler=SIG_IGN;
if((sigaction(SIGQUIT,&s,NULL))==-1) {
perror("sigaction");
return -1;
}
And I wrote the following code in the thread designated to wait for signals (handlerrno is a function to check errno and exit):
sigset_t threadset;
int err, sig;
if(sigfillset(&threadset)==-1) handlerrno("Sigfillset thread stats");
if(sigdelset(&threadset,SIGQUIT)==-1) handlerrno("Sigdelset thread stats");
if(sigdelset(&threadset,SIGINT)==-1) handlerrno("Sigdelset thread stats");
if(sigdelset(&threadset,SIGTERM)==-1) handlerrno("Sigdelset thread stats");
if(sigdelset(&threadset,SIGUSR1)==-1) handlerrno("Sigdelset thread stats");
if((err=pthread_sigmask(SIG_SETMASK,&threadset,NULL))!=0)
handlerror(err,"Set sigmask thread stats");
if((err=sigwait(&threadset,&sig))!=0) handlerror(err,"Sigwait");
//I handle the signals here
However, when I launch SIGQUIT from the shell, the thread designated to wait for the signals seems to be stuck in sigwait(), so I don't really know what happens and which thread gets the signal. Is anything wrong with the code? Thank you!
答案 0 :(得分:1)
忽略蒙版是整个过程。 sigaction
调用后,SIQUIT
永远不会在任何帖子中处于待处理状态,因此sigwait
会永久阻止。
你应该做的是在创建任何线程之前阻塞主线程中的信号,以便子线程也阻塞它(child threads inherit the signal mask of their parent thread)。
然后处理线程应该能够在信号被阻塞的情况下使信号出列。
(我不确定您选择的终止信号是否合适。SIQUIT
通常是通过Ctrl+\
发送的,并且应该在终止之前创建核心转储。也许{{1}将是一个更好的选择。)