C 需要解释这些问题
我需要澄清一下这个话题。 我有一个简单的例子C 需要解释这些问题,c,unix,process,signals,C,Unix,Process,Signals,我需要澄清一下这个话题。 我有一个简单的例子 sigset_t mask, oldmask; sigemptyset (&mask); sigaddset (&mask, SIGRTMIN+1); sigprocmask (SIG_BLOCK, &mask, &oldmask); sigsuspend(&oldmask); sigprocmask (SIG_UNBLOCK, &mask, NULL); 我是这样理解的: SIGEPTYSET
sigset_t mask, oldmask;
sigemptyset (&mask);
sigaddset (&mask, SIGRTMIN+1);
sigprocmask (SIG_BLOCK, &mask, &oldmask);
sigsuspend(&oldmask);
sigprocmask (SIG_UNBLOCK, &mask, NULL);
我是这样理解的:
while(1){
sigsuspend(&oldmask)
printf("recieved signal");
}
因此,对于我打印的每一个“接收信号”,上一版答案的主要部分都是错误的。我为我的错误道歉。谢谢你指出错误
POSIX对SIGSSUSPEND()的定义
POSIX标准相当清楚地描述了:
#包括
int-sigssuspend(const-sigset\u t*sigmask)代码>
描述
SIGSTAND()
函数应使用SIGSMASK
所指向的一组信号替换调用线程的当前信号掩码,然后暂停线程,直到发送信号为止,该信号的作用是执行信号捕获函数或终止进程。这不会导致任何其他可能在进程上挂起的信号在线程上挂起
如果操作是终止进程,则sigsupspend()
将永远不会返回。如果操作是执行信号捕获函数,则在信号捕获函数返回后,sigsupspend()
应返回,信号掩码恢复到调用sigsupspend()
之前的设置
无法阻止无法忽略的信号。这是由系统强制执行的,不会导致指示错误
返回值
由于sigssuspend()
无限期挂起线程执行,因此没有成功完成返回值。如果发生返回,则应返回-1,并设置errno以指示错误
错误
如果出现以下情况,SIGSSUSPEND()
功能将失败:
[EINTR]
调用进程捕获信号,并从信号捕获函数返回控制
此外,POSIX说:
每个线程都有一个“信号掩码”,用于定义当前阻止向其传递的信号集
将应用程序添加到代码片段中
sigssuspend()
函数是旧函数的现代模拟
主要变化:两个代码块颠倒
它允许您将线程发送到睡眠状态,直到其中一个选定的信号出现。如果希望它一直休眠到SIGRTMIN+1到达,可以使用:
sigfillset(&mask);
sigdelset(&mask, SIGRTMIN+1);
sigsuspend(&mask);
sigemptyset(&mask);
sigaddset(&mask, SIGRTMIN+1);
sigsuspend(&mask);
这将阻止除SIGRTMIN+1之外的所有信号
如果您想一直睡眠到SIGRTMIN+1以外的信号到达,可以使用:
sigfillset(&mask);
sigdelset(&mask, SIGRTMIN+1);
sigsuspend(&mask);
sigemptyset(&mask);
sigaddset(&mask, SIGRTMIN+1);
sigsuspend(&mask);
这仅阻止SIGRTMIN+1
除非在末尾添加换行符,否则循环将无法可靠地打印接收到的信号
(甚至可能不会;您可能需要fflush(stdout)
或等效文件)。但是,如果您在正常事件过程中阻止了SIGRTMIN+1,然后将&oldmask
设置为仅允许SIGRTMIN+1,则当您的代码处于SIGSSUSPEND()
时,您的信号将可靠地传递
您对的描述不正确:
sigprocmask
设置要阻止的mask+oldsmask
中的所有信号
当您这样做时:
sigset_t mask, oldmask;
sigemptyset(&mask);
sigaddset(&mask, SIGRTMIN+1);
sigprocmask(SIG_BLOCK, &mask, &oldmask);
您将SIGRTMIN+1添加到阻塞信号列表中(因为您使用了SIG_BLOCK,并且掩码
仅包含SIGRTMIN+1)。oldmask
中的输出是添加SIGRTMIN+1之前的信号掩码。它可能包含也可能不包含SIGRTMIN+1。进程的信号掩码将从当前值更改为包含SIGRTMIN+1的新值(如果需要为线程设置信号掩码,则使用pthread\u sigprocmask()
),然后您会被告知旧值
从评论中
那么,如果我想阻止SIGRTMIN+1,那么在我的第一个示例中使用sigssuspend(&oldsmask)
是错误的吗
重大变化
是的,这是错误的。调用sigssuspend(&oldsmask)
会将线程发送到睡眠状态,直到收到oldsmask
中的一个信号为止。oldmask
的内容是在添加SIGRTMIN+1之前被阻止的信号集。
是的,这是错误的。调用sigssuspend(&oldsmask)
会将线程发送到睡眠状态,直到收到oldsmask
中未包含的信号之一。oldmask
的内容是在添加SIGRTMIN+1之前被阻止的信号集
以下两段被撤回,而不一定被谴责为错误。我认为两者都有道理,尽管两者都有改进的余地
您不使用sigsupspend()
来阻止信号本身;您使用它来等待一组指定的信号中的一个到达
如果您想忽略SIGRTMIN+1,那么您需要使用sigaction()
,或者您可以像以前那样使用sigprocmask()
;它专门阻止SIGRTMIN+1以及所有其他已被阻止的信号。
我是否正确理解,它会像以前那样阻止相同的信号
假设“it”是sigssuspend()
,则它将阻止oldsmask
中没有的任何信号,并等待oldsmask
中的一个信号到达。
假设“it”是sigssuspend()
,则它将阻止oldsmask
中的任何信号,并等待oldsmask
中没有的信号之一到达
如果我做了sigsupspend(&mask)