UNIX sigaction函数详解

sigaction函数的功能是检查或修改与指定信号相关联的处理动做(可同时两种操做)。是POSIX的信号接口,而signal()是标准C的信号接口(若是程序必须在非POSIX系统上运行,那么就应该使用这个接口)函数

给信号signum设置新的信号处理函数act, 同时保留该信号原有的信号处理函数oldactspa

 

int sigaction(int signo,const struct sigaction *restrict act,指针

 

              struct sigaction *restrict oact);rest

 

结构sigaction定义以下:接口

struct sigaction{进程

   void (*sa_handler)(int);io

    sigset_t sa_mask;软件

   int sa_flag;程序

   void (*sa_sigaction)(int,siginfo_t *,void *);margin

};

注:

sa_handler字段包含一个信号捕捉函数的地址

sa_mask字段说明了一个信号集,在调用该信号捕捉函数以前,这一信号集要加进进程的信号屏蔽字中。仅当从信号捕捉函数返回时再将进程的信号屏蔽字复位为原先值。

sa_flag是一个选项,主要理解两个

SA_INTERRUPT 由此信号中断的系统调用不会自动重启

SA_RESTART 由此信号中断的系统调用会自动重启

SA_SIGINFO 提供附加信息,一个指向siginfo结构的指针以及一个指向进程上下文标识符的指针

 

最后一个参数是一个替代的信号处理程序,当设置SA_SIGINFO时才会用他。

例子:

 

 #include <stdio.h>

 #include <signal.h>

 #include <unistd.h>

 

 void show_handler(int sig)

 {

     printf("I got signal %d\n", sig);

     int i;

     for(i = 0; i < 5; i++) {

         printf("i = %d\n", i);

         sleep(1);

     }

 }

 

 int main(void)

 {

     int i = 0;

     struct sigaction act, oldact;

     act.sa_handler = show_handler;

     sigaddset(&act.sa_mask, SIGQUIT); //见注(1)

     act.sa_flags = SA_RESETHAND | SA_NODEFER; //见注(2)

    //act.sa_flags = 0; //见注(3)

 

     sigaction(SIGINT, &act, &oldact);

     while(1) {

         sleep(1);

         printf("sleeping %d\n", i);

         i++;

     }

 }

注:

(1)    若是在信号SIGINT(Ctrl + c)的信号处理函数show_handler执行过程当中,本进程收到信号SIGQUIT(Crt+\),将阻塞该信号,直到show_handler执行结束才会处理信号SIGQUIT。

(2)    SA_NODEFER       通常状况下, 当信号处理函数运行时,内核将阻塞<该给定信号 -- SIGINT>。可是若是设置了SA_NODEFER标记, 那么在该信号处理函数运行时,内核将不会阻塞该信号。 SA_NODEFER是这个标记的正式的POSIX名字(还有一个名字SA_NOMASK,为了软件的可移植性,通常不用这个名字)    

        SA_RESETHAND    当调用信号处理函数时,将信号的处理函数重置为缺省值。 SA_RESETHAND是这个标记的正式的POSIX名字(还有一个名字SA_ONESHOT,为了软件的可移植性,通常不用这个名字)   

 (3)    若是不须要重置该给定信号的处理函数为缺省值;而且不须要阻塞该给定信号(无须设置sa_flags标志),那么必须将sa_flags清零,不然运行将会产生段错误。可是sa_flags清零后可能会形成信号丢失!

相关文章
相关标签/搜索