• 信号有关的内容


    一、信号的概念

      信号时一种软件中断,很多应用程序应用的过程中都需要处理信号,也可以看作时进程与进程之间的一种通信方式。信号提供了一种处理异步事件的方法。

      常见的Linux系统的系统信号是可以查的到的。

    二、产生信号的条件

      1、通过按终端键,来引发终端产生的信号。比如UNIX系统下的Crtl+c键可以用来中断一个进程。

      2、硬件异常产生信号,比如除数为0,无效的内存引用等。

      3、用户调用kill,killall命令来发送信号给其他进程。

      4、进程调用kill、raise、alarm等函数来将任意信号发送给另一个进程或进程组。

      5、检测到某种软件条件已经发生,比如SIGALRM(进程设置的定时器已经超时)。

    三、信号的处理方式

      1、忽略此信号

        大都数的信号都是可以使用这种方式来进行处理的,但是有2种信号时不能被忽略的,分别是SIGKILL和SIGSTOP,因为它们向内核和超级用户提供了使进程结束和停止的可靠方法。

      2、捕捉信号

        这个需要通知内核在某种信号发生的时候,调用一个用户函数。在用户函数中,可执行用户希望对这种事件进行的处理。SIGKILL和SIGSTOP也是无法捕捉的。

      3、执行系统默认的动作

        对大多数的系统默认动作是终止该进程。还有一些是忽略和终止+core,这里的core文件是一种二进制文件,需要用一些高度工具才能解析。

        ubuntu 默认不产生core文件,需要使用命令设置:
          ulimit -c unlimited

    四、信号集

      多个信号的集合,数据类型是sigset_t,由128个二进制位组成,每个二进制代表的是一个信号,目前有大概64个信号。

      

    int sigemptyset(sigset_t *set); //清空信号集
    
    int sigfillset(sigset_t *set); //加满信号集
    
    int sigaddset(sigset_t *set, int signum);//加一个信号到信号集
    
    int sigdelset(sigset_t *set, int signum);//从信号集删除一个信号
    
    int sigismember(const sigset_t *set, int signum);//从信号集中查找某个信号,成功返回1,失败返回0  

      每一个进程都有一个信号掩码,也就是一个信号集用来包含进程屏蔽的信号。

      函数sigprocmask就是用来设置信号掩码的。

            sigset_t set,oldset;
        // 初始化信号集
        sigemptyset(&set);
        // 向信号集中添加信号
        printf("向信号集中添加%d %s\n",34,sigaddset(&set,34)?"失败":"成功");
        // 设置信号掩码
        printf("设置信号掩码%s\n",sigprocmask(SIG_SETMASK,&set,&oldset)?"失败":"成功");        

       以下是修改信号掩码的方式:

         SIG_BLOCK 向信号掩码当中添加信号
           SIG_UNBLOCK 从信号掩码当中删除信号
           SIG_SETMASK 用新的信号集替换旧的信号掩

      

    五、信号的捕捉处理的函数

      signal函数

      

     1 #include<stdio.h>
     2 #include<unistd.h>
     3 #include<signal.h>
     4 
     5         void sigsegv(int num)
     6         {
     7             printf("我捕获了一个信号%d\n",num);
     8             exit(0);
     9         }
    10         int main()
    11         {
    12             signal(SIGSEGV,sigsegv);
    13             int *p = NULL;
    14             *p =100;
    15             return 0;
    16         }            

      通过这个函数,就可以捕捉到这个代码产生的段错误的信号,也就是SIGSEGV(11);

    还有另外一个函数sigaction可以用来检查并修改指定信号相关联的处理动作

    int sigaction(int signum, const struct sigaction *act,struct sigaction *oldact);

    这个函数功能比较强大,同时也比signal复杂。

      

  • 相关阅读:
    使用spine骨骼动画制作的libgdx游戏
    【翻译】针对多种设备定制Ext JS 5应用程序
    【翻译】Ext JS最新技巧——2015-1-2
    Libgdx1.5.3发布
    Solr创建Core的两种方法
    Solr 7.7.0 部署到Tomcat
    CentOS7下安装JDK详细过程
    Linux常用命令总结
    Redis protected-mode属性解读
    使用RedisDesktopManager工具,解决连接失败问题
  • 原文地址:https://www.cnblogs.com/yyc954330712/p/9368233.html
Copyright © 2020-2023  润新知