Linux----信号的阻塞

本文介绍了信号处理函数sigaction和Signal,它们用于设置和获取信号处理方式。同时讲解了如何使用sigprocmask函数来修改进程的信号屏蔽字,控制哪些信号会被阻塞。此外,还提供了打印当前进程被屏蔽的信号以及挂起的信号的函数,帮助理解信号的处理状态。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1. sigaction函数

#include <signal.h>
int sigaction(int signum, struct sigaction *act, struct sigaction * oldact)
											Return: 0 for OK, -1 on error
handler_t *Signal(int signum, handler_t *handler)
{
	struct sigaction action, old_action;
	
	action.sa_handler = handler;
	sigemptyset&action.sa_mask);	/* Block sigs of type being handled */
	action.sa_flags = SA_RESTART;	/* Restart syscalls if possible */
	
	if(sigaction(signum, &action, &old_action) < 0)
		unix_error("Signal error");
		return(old_action.sa_handler);
}

2. 信号打印函数

/* Print list of signals within a signal set */
void printSigset(FILE *of, const char *prefix, const sigset_t *sigset)
{
	int sig cnt;
    
    cnt = 0;
    for(sig = 1; sig < NSIG; sig++){
        if(sigismember(sigset sig)){
            cnt++;
            fprintf(of, ""%s%d\n", prefix, sig, strsignal(sig));
        }
    }
    if(cnt == 0)
    	fprintf(of, "%s<empty signal set>\n", prefix);
}

3. sigprocessmask函数

一个进程的信号屏蔽字规定了当前阻塞而不能递送给该进程的信号集。调用函数sigprocmask可以检测或更改其信号屏蔽字,或者在一个步骤中同时执行这两个操作

#include <signal.h>
int sigprocmask( int how, const sigset_t *restrict set, sigset_t *restrict oset );
返回值:若成功则返回0,若出错则返回-1

首先,若oset是非空指针,那么进程的当前信号屏蔽字通过oset返回。

其次,若set是一个非空指针,则参数how指示如何修改当前信号屏蔽字。

下表用sigprocmask更改当前信号屏蔽字的方法

how说明
SIG_BLOCK该进程新的信号屏蔽字是其当前信号屏蔽字和set指向信号集的并集。set包含了我们希望阻塞的附加信号
SIG_UNBLOCK该进程新的信号屏蔽字是其当前信号屏蔽字和set所指向信号集补集的交集。set包含了我希望解除阻塞的信号
SIG_SETMASK该进程新的信号屏蔽字将被set指向的信号集的值代替

如果set是空指针,则不改变该进程的信号屏蔽字,how的值也无意义

在调用sigprocmask后如果有任何未决的、不再阻塞的信号,则在sigprocmask返回前,至少会将其中一个信号递送给该进程。

sigprocmask是仅为单线程的进程定义的。

4. 阻塞信号打印函数

/* Print mask of blocked signals for this process */
int printSigMask(FILE *of, const char *msg)
{
	sigset_t currMask;
    
    if(msg != NULL)
        fprintf(of, "%s", msg);
    //第一个参数为SIG_BLOCK就是指该进程新的信号屏蔽字是其当前信号屏蔽字和set指向信号集的并集
    //第二个参数为NULL时,不改变该进程的信号屏蔽字,即不增加额外的信号屏蔽字。
    //那么此时第三个参数指向的就是被屏蔽的信号。
    if(sigprocmask(SIG_BLOCK, NULL, &currMask) == -1)
        return -1;

    printSigset(of, "\t\t", &currMask);
    
    return 0;
}

5. 挂起队列信号打印函数

/* Print signals currently pending for this process */
int printPendingSigs(FILE *of, const char *msg)
{
	sigset_t pendingSigs;
    
    if(msg != NULL)
        fprintf(of, "%s", msg);
    if(sigpending(&pendingSigs) == -1)
        return -1;
    
    printSigset(of, "\t\t", &pendingSigs);
    
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值