Linux一个健壮的信号接口

Linux提供了一个更见健壮的信号接口:sigaction。

#include<signal.h>

int sigaction( int sig, const struct sigaction *act , struct sigaction *ocat);

sigaction结构定义在文件signal.h中,它的作用是定义在接收到参数sig指定的信号后应该采用的行动。该结构至少应该包含一下

以下几个成员 。

void (*) (int ) sa_handler /*function, SIG_DFL or SIG_IGN*/

sigset_t sa_mask           /*signals to block in sa_handler*/

int sa_flags                       /* signal action modifiers*/

sigaction函数会在成功时返回0,失败时返回0.

在参数cat指向的sigaction结构中,sa_handler是一个函数指针,它指向信号sig时将被调用的信号处理函数。

sa_mask成员指定了一个信号集,在调用Sa_handler所指向的信号处理函数之前,该信号集将被加入到进程的信号屏蔽字中。

#include <signal.h>
#include <stdio.h>
#include <unistd.h>

void ouch(int sig)
{
    printf("OUCH! - I got signal %d\n", sig);
}

int main()
{
    struct sigaction act;

    act.sa_handler = ouch;
    sigemptyset(&act.sa_mask);
    act.sa_flags = 0;

    sigaction(SIGINT, &act, 0);

  while(1) {
    printf("Hello World!\n");
    sleep(1);
  }
}

信号集

头文件signal.h定义了类型sigset_t和用来处理信号集的函数。sigaction和其他函数将用这些信号集来修改进程在接收到信号时的行为。

#include<signal.h>
int sigaddset(sigset_t *set, int signo);
int sigemptyset(sigset_t *set);
int sigfillset(sigset_t *set);
int sigdelset(sigset_t *set ,  int signo);

sigempty将信号集初始化为空。sigfillset将信号处理化为包含所以已定义的信号。sigaddset和sigdelset从信号集中增加或删除给定的信号

(signo)。它们在成功时返回0,失败时返回-1并设置errno。

函数sigismember判断一个给定的信号是否是一个信号集的成员。如果是就返回1,如果不是,它就返回0.给定的信号无效,它就返回-1并

设置errno为EINVAL。

#include<signal.h>

int sigismember(sigset_t *set , int signo);

进程的信号屏蔽字的设置或检查工作由函数sigprocmask来完成。信号屏蔽字是指当前被阻塞的一组信号,他们不能被当前进程接收到

#include<signal.h>

int sigprocmask(int how , const sigset_t *set , sigset_t *oset);

sigprocmask函数可以根据参数how指定的方法修改进程的信号屏蔽字。新的信号屏蔽字由参数set指定。

参数how的取值可以是表11-6中的一个。

SIG_BLOCK                                          把参数set中的信号添加到信号屏蔽字中。

SIG_SETMASK                                     把信号屏蔽字设置为参数set中的信号。

SET_UNBLOCK                                  从信号屏蔽字中删除参数set中的信号。



如果一个信号被进程阻塞,它就不会传递给进程。但它停留在待处理状态,程序可以通过调用函数sigpending来查看它阻塞的信号中

有哪些正停留在待处理状态。

#include<signal.h>

int sigpending(sigset_t *set);

进程可以通过调用sigsuspend函数挂起自己的执行,知道信号集中的一个信号到达为止。

#include<signal.h>

int sigsuspend(const sigset_t *sigmask);

这个函数将自己的进程屏蔽字替换为由参数sigmask给出的信号集,然后挂起程序的执行。


1.sigaction标志

用在sigaction函数里的sigaction结构中的sa_flags

SA_NOCLDSTOP: 如果SA_NOCLDSTOP位被置位并且目标信号是SIGCHLD,除非子进程退出,而在子进程停止(stop)时父进程将不会收到通知。

SA_NOCLDWAIT: SA_NOCLDWAIT标志会阻止子进程成为僵尸进程。在目标信号是SIGCHLD的时候使用。如果进程设置了这个标志,接着调用某个wait系统调用,进程将被阻塞直到子进程全部终止,最后返回-1(译注:此处在APUE2ed中的解释是返回1),设置errno全局变量为ECHILD。

SA_ONSTACK: 一些时候需要在特定的堆栈上进行信号的处理。sigaction系统调用提供了这个方式。如果该位被置位,那么信号将会被交付到指定的堆栈上。

SA_NODEFER: 如果SA_NODEFER位被置位,那么当前信号正被处理时,系统不会屏蔽该信号以后的交付。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值