int sigemptyset(sigset_t* set); // 清空信号集
int sigfillset(sigset_t* set); // 包含所有信号集
sigaddset/sigdelset/sigismember;
sigprocmask用来检测或改变调用进程的信号屏蔽。
int sigprocmask(int how, const sigset_t* set, sigset_t* oset);
How: SIGBLOCK SIG_UNBLOCK SIG_SETMASK
如果调用sigprocmask放开某个信号而导致任何悬挂信号被解除阻塞,则函数返回前,这些信号中至少有一个被交付。
检查悬挂信号:int sigpending(sigset_t* set);
等待信号:int pause(void);
悬挂调用进程直到有一个信号到达。仅当句柄执行并返回时,pause函数才返回:此时返回-1,并设置errno为EINTR。所有其他情况下pause不返回。
如果多个相同信号在信号句柄运行前发给了进程,则句柄只被运行一次。换句话说,默认情况下unix信号是非排队的,只有当实现支持实时信号并且sa_flags设置SA_SIGINFO时,由sigqueue生成的后续信号才排队。
I/O执行期间,有可能到达信号,此时有两种情况:重新开始系统调用还是返回失败.
早期unix特征为,进程执行慢系统调用期间捕获信号时,该调用被中断并设置errno为EINTR。
现代unix增加了sa_flags选项SA_RESTART可对单个信号要求自动恢复被中断的系统调用。
原则如下:如果进程阻塞于慢系统调用,并且进程捕获信号且该信号句柄返回,系统调用可能返回EINTR。 虽然有些unix能自动恢复系统调用,但是为了兼容性,我们必须准备慢系统调用返回EINTR,当检测到EINTR,要么重新开始系统调用,要么做其他处理。
Again:
if (n=read(fd,buff, BUFSIZE) < 0) {
if (errno ==EINTR)
goto Again;
else
…}