信號致使的問題函數
不是任何信號咱們都須要的,若是遇到咱們不想處理的信號,咱們怎麼避免這個信號?spa
1. 信號屏蔽進程
intsigprocmask(int how,//操做方式io
SIG_BLOCK屏蔽信號ember
SIG_UNBLOCK剪除屏蔽信號查詢
SIG_SETMASK修改屏蔽信號集合
constsigset_t *sigs,//操做的信號集合di
sigset_t*oldsigs);//返回原來操做的信號集合co
返回值:執行成功返回0,失敗返回-1。阻塞
屏蔽信號的步驟:
1. 聲明信號集
sigset_t sigs;
2. 加入屏蔽信號
一組信號集合維護函數
2.1. 清空集合sigemptyset
int sigemptyset( sigset_t *set);
2.2. 添加信號到集合sigaddset
int sigaddset( sigset_t *set ,int signum);
2.3. 從集合刪除信號sigdelset
int sigdelset(sigset_t *set,int signum);
2.4. 添加全部信號到集合sigfillset
int sigfillset( sigset_t*set);
2.5. 斷定信號是否在集合sigismember
int sigismember(const sigset_t *set ,int signum);
3. 屏蔽信號
4. 接觸屏蔽
例子:
#include<stdio.h>
#include<signal.h>
void main()
{
int sum=0;
//聲明信號集
sigset_t sigs;
//清空信號集
sigemptyset(&sigs);
//添加信號到信號集
sigaddset(&sigs,SIGINT); //
//屏蔽信號
sigprocmask( SIG_BLOCK,&sigs,0);
for(i=1;i<=10;i++)
{
sum+=i;
sleep(1);
}
printf(「sum=%d\n」,sum);
//撿出屏蔽
sigprocmask(SIG_UNBLOCK,&sigs,0);//撿出屏蔽,信號當即觸犯,打印over不能//執行,若是沒有撿出屏蔽信號,over正常打印
printf(「OVER!\n」);
}
說明:當屏蔽了某個信號,這個信號將不會觸發,直到咱們撿出了該信號,信號纔會觸發。
2.查詢被屏蔽的信號
intsigpending(sigset_t *sets); 返回0成功,-1失敗
例子:
#include<stdio.h>
#include<signal.h>
void main()
{
int sum=0;
//聲明信號集
sigset_t sigs;
sigset_t sigp;
//清空信號集
sigemptyset(&sigs);
//添加信號到信號集
sigaddset(&sigs,SIGINT); //
//屏蔽信號
sigprocmask( SIG_BLOCK,&sigs,0);
for(i=1;i<=10;i++)
{
sum+=i;
sigpending(&sigp);//獲得屏蔽的信號
if(sigismemeber(&sigp,SIGINT))
{
printf(「信號SIGINT在排隊\n」);
}
sleep(1);
}
printf(「sum=%d\n」,sum);
//撿出屏蔽
sigprocmask(SIG_UNBLOCK,&sigs,0);
printf(「OVER!\n」);
}
2. 信號屏蔽的切換
int sigsuspend(sigset_t *sigs);
屏蔽新的信號,原來的信號失效.
sigsuspend是阻塞函數.對參數信號屏蔽.
對參數沒有指定的信號不屏蔽,但當沒有屏蔽信號處理函數調用完畢
sigsuspend返回條件:
1.信號發生,而且信號是非屏蔽信號
2.信號必需要處理,並且處理函數返回後,sigsuspend才返回.
sigsuspend設置新的屏蔽信號,保存舊的屏蔽信號
並且當sigsuspend返回的時候,恢復舊的屏蔽信號.
函數sigsuspend將進程的信號屏蔽碼設置爲sigs,而後與pause()函數同樣等待信號的發生並執行完信號處理函數。信號處理函數執行完後再把進程的信號屏蔽碼設置爲原來的屏蔽字,而後sigsuspend函數才返回。 Sigsuspend老是返回-1。
例子:
#include<stdio.h>
#include<unistd.h>
#include<signal.h>
void deal()
{
printf(「處理信號SIGINT\n」);
}
void main()
{
signal(SIGINT,deal);
int sum=0;
//聲明信號集
sigset_t sigs;
sigset_t sigp;
sigset_t newsig=NULL;
//清空信號集
sigemptyset(&sigs);
//添加信號到信號集
sigaddset(&sigs,SIGINT); //
//屏蔽信號
sigprocmask( SIG_BLOCK,&sigs,0);
for(i=1;i<=10;i++)
{
sum+=i;
sigpending(&sigp);//獲得屏蔽的信號
if(sigismemeber(&sigp,SIGINT))
{
printf(「信號SIGINT在排隊\n」);
sigsuspend(&newsig);//切換屏蔽信號,等待SIGINT信號,並調用處//理函數後函數返回。
}
sleep(1);
}
printf(「sum=%d\n」,sum);
}