sigsuspend函数

#include <errno.h>
  2 #include <signal.h>
  3 #include "../../ourhdr.h"
  4
  5 void pr_mask (const char *str)
  6 {
  7         sigset_t sigset;
  8         int errno_save;
  9
 10         errno_save = errno;
 11         /*we can be called by signal handlers*/
 12
 13         if (sigprocmask (0, NULL, &sigset) < 0)
 14                 err_sys ("sigprocmask error");
 15
 16         printf ("%s/n",str);
 17         if (sigismember (&sigset, SIGINT))
 18                 printf ("SIGINT/n");
 19         if (sigismember (&sigset, SIGQUIT))
 20                 printf ("SIGQUIT/n");
 21         if (sigismember (&sigset, SIGUSR1))
 22                 printf ("SIGUSR1/n");
 23         if (sigismember (&sigset, SIGALRM))
 24                 printf ("SIGALRM/n");
 25
 26         /*remianing signals can go here*/
 27
 28         errno = errno_save;

29        }

 

 

 

  1 #include <signal.h>
  2 #include "../../ourhdr.h"
  3
  4 static void sig_int (int);
  5
  6 int main()
  7 {
  8         sigset_t newmask, oldmask, zeromask;
  9
 10         if (signal(SIGINT, sig_int) == SIG_ERR)
 11                 err_sys("signal (SIGINT) error");
 12         sigemptyset(&zeromask);
 13
 14         sigemptyset(&newmask);
 15
 16         sigaddset (&newmask, SIGINT);
 17         /*block SIGINT and save current signal mask*/
 18
 19         if (sigprocmask(SIG_BLOCK, &newmask, &oldmask) < 0)
 20                 err_sys("SIG_BLOCK error");
 21
 22         /*critocal region of code */
 23         pr_mask("in critical region :");
 24         sleep(4);
 25
 26
 27         if (sigsuspend(&oldmask) != -1)
 28                 err_sys("sigsuspend error");
 29         pr_mask("after return from sigsuspend");
 30
 31
 32         if (sigprocmask (SIG_SETMASK, &oldmask, NULL) < 0)
 33                 err_sys("SIG_SETMASK error");
 34         pr_mask("oldmask in proccess");
 35
 36         exit(0);
 37 }
 38
 39
 40 static void sig_int(int signo)
 41 {
 42         pr_mask("/nin sig_int:");
 43         return;
 44 }


sigsuspend  基本功能:

进程的信号屏蔽子设置为参数指向的值,在捕捉到一个信号或发生一个会终止该进程的信号之前,该进程被挂起
,如果捕捉到一个信号而且从该信号处理程序返回,则SIGSUSPEND返回,并且该进程的信号屏蔽子设置为调用SIGSUSPEND之前的值,

注意,此函数没有成功返回值,如果它返回到调用者,则总是返回-1 ,

这个程序这行结果

in critical region :
SIGINT
^C
in sig_int:
SIGINT
after return from sigsuspend
SIGINT
oldmask in proccess

这个结果可分析:

在程序调用sigprocmask期间,这个函数阻塞啦信号SIGINT,SLEEP(4)

在这4秒人内,SIGINT 信号是阻塞的茫然后过4秒

运行的是SIGSUSPEND这个函数解除啦对SIGINT 函数的阻塞,然后立即进入挂起状态,等待信号发生后从信号处理函数返回,

这样就体现出调用SIGSUSPENG函数的作用啦:这个函数是一个原子操作:

这样会避免在解除对SIGINT的阻塞和PAUSE之间发生的SIGINT信号被丢失的问题

/**********************************************************************************************************************/

sigsuspend的另一种应用是等待一个信号处理程序设置一个全局变量,下一个程序用于捕捉中断信号和退出信号 ,但是希望只有在捕捉到退出信号时再继续执行MAIN程序

 

 #include <signal.h>
  2 #include "../../ourhdr.h"
  3
  4 volatile sig_atomic_t quitflag = 1;
  5 /* set nonzero by signal handler*/
  6
  7 int main()
  8 {
  9         void  sig_int (int);
 10         sigset_t newmask, oldmask, zeromask;
 11
 12
 13         if (signal(SIGINT, sig_int) == SIG_ERR)
 14                 err_sys("signal SIGINT error");
 15         if (signal(SIGQUIT, sig_int) == SIG_ERR)
 16                 err_sys("signal SIGQUIT error");
 17
 18         sigemptyset (&zeromask);
 19
 20         sigemptyset (&newmask);
 21
 22         sigaddset (&newmask, SIGQUIT);
 23         /* block SIGQUIT and save current signal mask*/
 24         if (sigprocmask (SIG_BLOCK, &newmask, &oldmask) <0)
 25                 err_sys("SIG_BLOCK error");
 26
 27         while (quitflag == 0)
 28                 sigsuspend(&zeromask);
 29
 30         /*SIGQUIT has been caught and is now blocked;do whatever*/
 31
 32 /*      quitflag = 0;  */
 33         /*reset signal mask which unblocks SIGQUIT*/
 34
 35         if (sigprocmask (SIG_SETMASK,&oldmask, NULL) <0)
 36                 err_sys("SIG_SETMASK error");
 37         exit(0);
 38 }
 39
 40 void sig_int (int signo)
 41         /*onr signal handlet for SIGINT and SIGQUIT*/
 42 {
 43         if (signo == SIGINT )
 44                 printf ("/niniterrupt/n");
 45         else if (signo == SIGQUIT)
 46         {
 47                 quitflag = 1;
 48                 printf ("hellow/n");
 49         }
 50         /*set flag for main loop*/
 51
 52         return;
 53 }
-- 插入 --                                   

这个程序比较关键的就是WHILE循环的设置:。

这里32 /*      quitflag = 0;  */这一行没明白是什么作用,求高手指点

因为把它注释掉对程序没有影响。

你可能感兴趣的:(sigsuspend函数)