linux信号

来源:互联网 发布:火龙女电影知乎 编辑:程序博客网 时间:2024/05/18 18:42
信号就是一个整数。
 linux操作系统的信号共有64个。
  32个     不可重用信号   有固定含义
  32个  可重复   可设置意义
 信号发送者:信号源
  shell kernel 进程 硬件驱动程序
 信号接收者:
  shell kernel 进程 硬件驱动程序  
 接收到信号后:每个信号定义了一种含义,接收到信号后会自动做对应的操作。
 可以自定义信号处理。
 信号处理注册函数:signal
 注册了一个信号后,进程会接收信号,并用进程设定的信号处理函数取代其原本的对应操作。
 函数指针变量:保存了一个函数的地址的指针变量。

 #include <signal.h>
    typedef    void (*sighandler_t)(int);
    sighandler_t signal(
    int signum,//信号 
    sighandler_t   handler);//信号处理函数

    signal函数可以让进程捕获注册了的信号,并用自定义的函数来设置对信号的反馈。
    一个信号只能注册一次,只能有一个信号处理函数去处理这个信号的反馈。
    一个信号处理函数可以作为多个信号的反馈处理。
    中断,当一个信号处理函数被调用时,会中断调用信号处理函数的进程,等信号处理函数返回后再继续进程。
    发送信号:
     kill命令
     kill函数
#include <stdio.h>#include <signal.h>void hand(int s){int i;if(s == 2){printf("想杀我,你还嫩了点~~~~~~~\n");for(i=0;i<20;i++){sleep(1);printf("hand:%d\n",i);}}else if(s == 3)printf("换了高手啊,还是杀不死我!\n");else if(s == 28)printf("^o^\n");}int main(){int n = 1;signal(2,hand);signal(3,hand);signal(28,hand);printf("%d\n",getpid());while(1){printf("我还活得好好的:%d!\n",n++);sleep(1);}return 0;}
如果希望进程不被某些信号中断,屏蔽某些信号。
    sigprocmask   signal process mask
    int   sigprocmask(
    int    how,//行为
    const sigset_t *set, //用来设置哪些信号需要屏蔽
    sigset_t *oldset);//保存被屏蔽的信号
    信号集:保存多个信号的数组。
    信号集操作函数
    int      sigemptyset(//清空信号集
    sigset_t *set);
 int       sigfillset(//把所有信号填入信号集中
 sigset_t *set);
    int sigaddset(//把signum信号加入信号集中
    sigset_t  *set,
    int signum);
    int  sigdelset(//把signum从信号集中移除
    sigset_t *set,
    int signum);
    int sigismember(//测试signum是否在信号集中
    const sigset_t *set,
    int signum);
    信号屏蔽只是忽略信号的处理,进程还是接收到了信号,等到解除屏蔽后再处理。
    然后不会保存接收信号的次数,只是保存最后一次接收。
#include <stdio.h>#include <signal.h>void hand(int s){int i;if(s == 2){for(i=0;i<20;i++){printf("哈哈:%d\n",i);sleep(1);}}else{printf("hand:%d\n",s);}}int main(){struct sigaction act = {0};sigset_t set;sigaddset(&set,3);act.sa_handler = hand;act.sa_mask = set;signal(3,hand);sigaction(2,&act,NULL);while(1){printf("-----------------------\n");sleep(1);}return 0;}
高级信号注册函数:sigaction
    int sigaction(
    int signum,
    const struct sigaction *act,
    struct sigaction *oldact);
    struct sigaction {
     void (*sa_handler)(int);
     void (*sa_sigaction)(int, siginfo_t *, void *);//高级信号处理函数
     sigset_t sa_mask;//屏蔽的信号集
     int  sa_flags;//方式
     void (*sa_restorer)(void);
    }
    signal在接收信号的时候不能接收其他信息。
    sigaction可以使用高级的信号处理函数,在处理信号的时候接收信息。
    SA_SIGINFO : 使用高级的信号处理函数,接收信号之外的其他数据

#include <stdio.h>#include <signal.h>void hand(int s){printf("接收到信号%d\n",s);}int main(){int i;sigset_t set;//定义一个信号集setsigset_t o_set;sigfillset(&set);//把所有信号加入信号集中signal(2,hand);for(i=0;i<100;i++){if(i == 10)sigprocmask(SIG_BLOCK,&set,&o_set);if(i == 50)sigprocmask(SIG_UNBLOCK,&set,NULL);printf("go on:i = %d\n",i);sleep(1);}return 0;}



0 0