Linux--信号屏蔽

我们知道一个信号从产生(Generation)到实际执行这个信号的处理动作称为信号递达(Delivery),信号从产生到递达之间的状态,称为信号未决(Pending)。进程可以选择阻塞(Block )某个信号。被阻塞的信号产生时将保持在未决状态,直到进程解除对此信号的阻塞,才执行递达的动作。
需要注意的的是:阻塞和忽略是不同的,只要信号被阻塞就不会递达,而忽略是在递达之后可选的一种处理动作。

画一个简单的示意图总结如下:
这里写图片描述

我们还知道在每个进程的PCB中有三张表来描述和记录信号的相关信息,其中block表记录被当前进程阻塞的信号,用pending表记录在当前进程下处于未决状态的信号,用handler表记录对应信号的处理函数地址(包括用户自定义函数),所以由于他们的功能我们可以确定pending表和block表的数据结构都是位图,比特位的编号对应信号的办好,比特位的值对应是否接收到信号,而handler 是一个函数指针数组,数组的每个元素存放着一个函数指针,用以递达信号。

认识一下信号的相关操作函数(以下函数都在signal.h头文件中):

int sigempty(sigset_t *set);     // 清空信号集set

int sigfillset(sigset_t *set);   // 填满信号集,即让set包含所有的信号

int sigaddset(sigset_t *set, int signo);  
    // 在set中增加signo信号

int sigdelset(sigset_t *set, int signo);   
    // 在set中去掉signo信号


int sigprocmask(int how, const sigset_t set, sigset_t oset); 
 // 若oset非空,则进程的当前信号屏蔽字通过oset返回,若set是一个
 // 非空指针,着参数how指示如何修改当前信号的屏蔽字,how可以取三个值:
    SIG_BLOCK:增加一个信号。
    SIG_UNBLOCK:解除一个信号。
    SIG_SETMASK:该进程的信号将被set信号集取代。

int sigismember(const sigset_t *set, int signo);  
    // 判断信号是否在set所指向的集合中
int sigpengding(sigset_t *set);  
    // 该函数返回信号集,该信号通过set参数返回。

现在我们编写如下代码:

这里写图片描述

结果为:
这里写图片描述
程序运行时,每秒钟把各信号的未决状态打印一遍,由于我们阻塞SIGINT信号,按Ctrl-C将会使SIGINT信号处于未决状态,按Ctrl-\仍然可以终止程序,因为SIGQUIT信号没有阻塞。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值