Chinaunix
标题:
有关sigsuspend函数的一个测试,疑惑?
[打印本页]
作者:
flikelinux
时间:
2012-03-30 10:24
标题:
有关sigsuspend函数的一个测试,疑惑?
这个测试例子,是APUE p270页的一个例子,但我对执行结果不太理解,代码如下
#include<stdio.h>
#include<unistd.h>
#include<signal.h>
#include<error.h>
void pr_mask(const char* str)
{
sigset_t sigset;
int errno_save;
if(sigprocmask(SIG_BLOCK,NULL,&sigset)<0)
printf("sigprocmask error\n");
printf("%s:",str);
if(sigismember(&sigset,SIGINT))
printf("SIGINT ");
if(sigismember(&sigset,SIGQUIT))
printf("SIGQUIT ");
if(sigismember(&sigset,SIGUSR1))
printf("SIGUSR1 ");
if(sigismember(&sigset,SIGALRM))
printf("SIGALRM ");
printf("\n");
}
//
void sig_int(int signo)
{
pr_mask("\nin sig_int");
}
int main()
{
sigset_t newmask,oldmask,waitmask;
if(signal(SIGINT,sig_int)==SIG_ERR)
printf("error 1");
sigemptyset(&waitmask);
sigaddset(&waitmask,SIGUSR1);
sigemptyset(&newmask);
sigaddset(&newmask,SIGINT);
if(sigprocmask(SIG_BLOCK,&newmask,&oldmask)<0)
printf("error 2");
pr_mask("in critial region");
if(sigsuspend(&waitmask)!=-1)
printf("error 3");
pr_mask("after return from sigsuspend");
if(sigprocmask(SIG_SETMASK,&oldmask,NULL)<0)
printf("error 4");
pr_mask("program exit");
return 0;
}
复制代码
执行结果是:
in critial region:SIGINT
^C
in sig_int:SIGINT SIGUSR1
after return from sigsuspend:SIGINT
program exit:
网上说sigsuspend执行的步骤是:
(1) 设置新的mask阻塞当前进程;
(2) 收到信号,恢复原先mask;
(3) 调用该进程设置的信号处理函数;
(4) 待信号处理函数返回后,sigsuspend返回。
那么根据第二条,我觉得在in sig_int:不应该有SIGUSR1,因为已经恢复以前的mask了,且以前的mask并不阻塞SIGUSR1。有人能给我指点一下吗?
作者:
flikelinux
时间:
2012-03-30 16:21
没人知道吗?求指点!
作者:
kinfinger
时间:
2012-03-30 21:42
http://blog.chinaunix.net/uid-22334392-id-3069347.html
可能会对你有帮助
作者:
suqin0802
时间:
2012-04-01 16:54
本帖最后由 suqin0802 于 2012-04-01 17:14 编辑
我也被这个问题困扰了~~
我将网上下载的源代码拷贝了一份建立文件10-15.c,编译执行后的结果是没有SIGINT的
这个是可以想得通的!
但是以前在网上下载了源代码包整体编译后得出的可执行文件/apue.2e/signals/suspend1,运行这个得出结果是跟书上的一致,实在是费解啊,求解释!!!我真的只是复制粘贴了一下代码而已,为什么结果会不同呢?
代码如下:
#include "apue.h"
static void sig_int(int);
int
main(void)
{
sigset_t newmask, oldmask, waitmask;
pr_mask("program start: ");
if (signal(SIGINT, sig_int) == SIG_ERR)
err_sys("signal(SIGINT) error");
sigemptyset(&waitmask);
sigaddset(&waitmask, SIGUSR1);
sigemptyset(&newmask);
sigaddset(&newmask, SIGINT);
/*
* Block SIGINT and save current signal mask.
*/
if (sigprocmask(SIG_BLOCK, &newmask, &oldmask) < 0)
err_sys("SIG_BLOCK error");
/*
* Critical region of code.
*/
pr_mask("in critical region: ");
/*
* Pause, allowing all signals except SIGUSR1.
*/
if (sigsuspend(&waitmask) != -1)
err_sys("sigsuspend error");
pr_mask("after return from sigsuspend: ");
/*
* Reset signal mask which unblocks SIGINT.
*/
if (sigprocmask(SIG_SETMASK, &oldmask, NULL) < 0)
err_sys("SIG_SETMASK error");
/*
* And continue processing ...
*/
pr_mask("program exit: ");
exit(0);
}
void pr_mask(const char *str)
{
sigset_t sigset;
int errno_save;
errno_save = errno;
if(sigprocmask(0,NULL,&sigset) <0) err_sys("sigprocmask error");
printf("%s",str);
if(sigismember(&sigset,SIGINT)) printf("SIGINT ");
if(sigismember(&sigset,SIGQUIT)) printf("SIGQUIT ");
if(sigismember(&sigset,SIGUSR1)) printf("SIGUSR1 ");
if(sigismember(&sigset,SIGALRM)) printf("SIGALRM ");
printf("\n");
errno = errno_save;
}
static void
sig_int(int signo)
{
pr_mask("\nin sig_int: ");
}
复制代码
作者:
flikelinux
时间:
2012-04-02 21:31
回复
4#
suqin0802
嗯,我也比较费解。不懂啊。。。
欢迎光临 Chinaunix (http://bbs.chinaunix.net/)
Powered by Discuz! X3.2