溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

SylixOS的信號(hào)屏蔽淺析

發(fā)布時(shí)間:2020-07-16 03:44:38 來源:網(wǎng)絡(luò) 閱讀:510 作者:qq58f47049ce44d 欄目:開發(fā)技術(shù)

1.信號(hào)介紹

   信號(hào)是一種軟中斷,用于通過異步的方式對(duì)進(jìn)程進(jìn)行事件通知。信號(hào)分為實(shí)時(shí)信號(hào)和非實(shí)時(shí)信號(hào),各個(gè)進(jìn)程對(duì)于信號(hào)的處理方式不一,處理方式分為三類:忽略,捕捉,執(zhí)行系統(tǒng)默認(rèn)動(dòng)作。進(jìn)程可以選擇屏蔽某個(gè)或某些信號(hào)。

2.信號(hào)屏蔽

   SylixOS可以通過sigprocmask函數(shù)對(duì)某個(gè)信號(hào)集內(nèi)的信號(hào)進(jìn)行屏蔽。在信號(hào)被屏蔽的期間,進(jìn)程對(duì)所屏蔽的大部分信號(hào)不會(huì)進(jìn)行響應(yīng),只有解除屏蔽后才會(huì)響應(yīng)。

2.1 sigprocmask函數(shù)

   sigprocmask函數(shù)原型如程序清單 2-1所示。

程序清單 2-1  sigprocmask函數(shù)原型

#include<signal.h>

int sigprocmask (intiCmd,constsigset_t *psigset,sigset_t *psigsetOld);

   函數(shù)sigprocmask原型分析:

   1、此函數(shù)成功時(shí)返回0,失敗時(shí)返回-1并設(shè)置錯(cuò)誤號(hào);

   2、參數(shù) iCmd是信號(hào)集命令;

   3、參數(shù) psigset是新的信號(hào)集;

   4、輸出參數(shù) psigsetOld保存先前的信號(hào)集。

   sigprocmask設(shè)置信號(hào)屏蔽字時(shí)iCmd對(duì)應(yīng)3個(gè)命令:

   1、SIG_BLOCK:新的信號(hào)集以或的形式添加到當(dāng)前的信號(hào)屏蔽字中

   2、SIG_UNBLOCK:從當(dāng)前的信號(hào)屏蔽字中刪除新的信號(hào)集中包含的信號(hào)

   3、SIG_SETMASK:將新的信號(hào)集賦值給當(dāng)前信號(hào)屏蔽字

2.1 sigprocmask函數(shù)

   SylixOS可以通過四個(gè)函數(shù)對(duì)信號(hào)集進(jìn)行操作,具體函數(shù)如程序清單 2-2所示。

程序清單 2-2  信號(hào)集操作函數(shù)

#include<signal.h>

int sigemptyset (sigset_t *psigset);

int sigfillset (sigset_t *psigset);

int sigaddset (sigset_t *psigset,intiSigNo);

int sigdelset (sigset_t *psigset,intiSigNo);

   1、sigemptyset函數(shù)用于初始化一個(gè)信號(hào)集,使其不包含任何信號(hào);

   2、sigfillset用于初始化一個(gè)信號(hào)集,使其包含所有信號(hào);

   3、sigaddset用于向一個(gè)信號(hào)集中添加某個(gè)信號(hào);

   4、sigdelset用于從一個(gè)信號(hào)集中刪除某個(gè)信號(hào)。

   SylixOS可以設(shè)置進(jìn)程屏蔽任意的信號(hào),但是某些信號(hào)即使被設(shè)置屏蔽也無法生效,無法被屏蔽的信號(hào)如表 2-1所示。

表 2-1  無法屏蔽的信號(hào)

信號(hào)名

信號(hào)描述

SIGKILL

強(qiáng)迫進(jìn)程結(jié)束

SIGABRT

異常結(jié)束

SIGSTOP

停止進(jìn)程執(zhí)行

SIGFPE

協(xié)處理器出錯(cuò)

SIGILL

非法指令

SIGBUS

bus error

SIGSEGV

無效內(nèi)存引用

2.1 信號(hào)屏蔽測(cè)試

   設(shè)置進(jìn)程屏蔽所有的信號(hào)后,向進(jìn)程發(fā)送任意的信號(hào),可以查看到信號(hào)是否被屏蔽,具體的信號(hào)屏蔽測(cè)試代碼如程序清單 2-3所示。

程序清單 2-3  信號(hào)屏蔽測(cè)試代碼

#include<stdio.h>

#include<signal.h>

 

int  main (int argc,char  **argv)

{

    int      iSigNo;              /*  信號(hào)ID                      */

    sigset_t  newMask;           /*  新的信號(hào)集                  */

    sigset_t  oldMask;            /*  舊的信號(hào)集                  */

    sigset_t  pendMask;          /*  阻塞的信號(hào)集                */

 

    sigfillset(&newMask);          /* 信號(hào)集包含所有信號(hào)          */

   

/*

     *  設(shè)置新的信號(hào)掩碼,并保存舊的信號(hào)掩碼

     */

    if (sigprocmask(SIG_SETMASK, &newMask, &oldMask) < 0) {

        fprintf(stderr,"Sigprocmask error.\n");

        return  (PX_ERROR);

    }

 

    sleep(5);                    /* 休眠等待信號(hào)                */

 

    sigpending(&pendMask);       /* 獲取未決的信號(hào)集            */

    /*

     *  打印出未決信號(hào)集中的信號(hào)

     */

    for (iSigNo =SIGHUP;iSigNo <=SIGRTMAX;iSigNo++)

    {

        if (sigismember(&pendMask,iSigNo) ==TRUE) {

            fprintf(stdout,"Signal %d pending.\n",iSigNo);

        }

    }

 

    /*

     *  恢復(fù)舊的信號(hào)掩碼

     */

    if (sigprocmask(SIG_SETMASK, &oldMask,NULL) < 0) {

      fprintf(stderr,"resume mask error.\n");

      return  (PX_ERROR);

    }

 

    return  (ERROR_NONE);

}

   運(yùn)行代碼后,可以通過kill命令向進(jìn)程發(fā)送除表 2-1以外的任意的信號(hào)后,信號(hào)無法被響應(yīng),運(yùn)行結(jié)果具體如圖 2-1所示。

SylixOS的信號(hào)屏蔽淺析

圖 2-1  測(cè)試代碼的運(yùn)行結(jié)果

   若發(fā)送無法被屏蔽的信號(hào),則會(huì)執(zhí)行與信號(hào)相關(guān)聯(lián)的處理動(dòng)作。

3.參考資料

   《SylixOS應(yīng)用開發(fā)手冊(cè)》


向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI