函数setjmp,longjmp和sigsetjmp,siglongjmp

来源:互联网 发布:在线影视站源码 编辑:程序博客网 时间:2024/06/16 22:26

int sigsetjmp(sigjmp_buf env,int savemask);

                                                      返回值:若直接调用则返回0,若从siglongjmp调用返回则返回非0值;

int siglongjmp(sigjmp_buf env,int val);

setjmp和longjmp的使用如下:

#include<stdio.h>#include<stdlib.h>#include<unistd.h>#include<signal.h>#include<setjmp.h>#define MAXLINE 1024void sig_alarm(int signo);jmp_buf env_alrm;int main() {int n;char buf[MAXLINE];if (signal(SIGALRM, sig_alarm) == SIG_ERR) {printf("can't catch sigalrm\n");exit(0);}if (setjmp(env_alrm) != 0) {printf("longjump called\n");exit(0);}alarm(5);if ((n = read(STDIN_FILENO, buf, MAXLINE)) < 0) {printf("read error\n");exit(0);}alarm(0);write(STDOUT_FILENO, buf, n);}void sig_alarm(int signo) {longjmp(env_alrm, 1);}


 

也可以用在sleep函数中:

 

#include<setjmp.h>#include<signal.h>#include<unistd.h>static jmp_buf env_alrm;static void sig_alrm(int signo) {longjmp(env_alrm, 1);}unsigned int sleep2(unsigned int secs) {if (signal(SIGALRM, sig_alrm) == SIG_ERR) {return (nsecs);}if (setjmp(env_alrm) == 0) {alarm(nsecs);pause();}return (alarm(0));}


sigsetjmp和siglongjmp使用基本相同,只是siglongjmp比setjmp多一个参数,若savemask为非0值,则sigsetjmp在env中保存进程的当前屏蔽字。若调用siglongjmp时,如果带非0 savemask的sigsetjmp调用已经保存了env,则siglongjmp从其中回复保存的信号屏蔽字。

#include<stdio.h>#include<stdlib.h>#include<unistd.h>#include<signal.h>#include<setjmp.h>//SIGINT,SIGQUIT,SIGUSR1,SIGALRM//siglongjmp longjmp//siglongjmp can handle singal automaticvoid sig_alarm(int signo);void sig_usr1(int signo);void pr_mask(const char *str);jmp_buf jmp_aaa;static int canjmp = 0;int main() {pr_mask("start pro");if (signal(SIGALRM, sig_alarm) == SIG_ERR) {printf("can't catch sigalrm\n");exit(0);}if (signal(SIGUSR1, sig_usr1) == SIG_ERR) {printf("can't catch sigusr1\n");exit(0);}if (sigsetjmp(jmp_aaa, 1) != 0) {//if (setjmp(jmp_aaa) != 0) {pr_mask("end pro");exit(0);}canjmp = 1;raise(SIGUSR1);return 0;}void sig_alarm(int signo) {pr_mask("in sig_alarm");}void sig_usr1(int signo) {if (canjmp == 0) {return;}pr_mask("before sigalrm");alarm(3);sleep(5);pr_mask("after sigalrm");siglongjmp(jmp_aaa, 1);//longjmp(jmp_aaa, 1);}void pr_mask(const char *str) {printf("%s\n", str);sigset_t curset;if (sigprocmask(0, NULL, &curset) < 0) {printf("call sigprocmask error\n");}if (sigismember(&curset, SIGINT))printf("SIGINT\n");if (sigismember(&curset, SIGQUIT))printf("SIGQUIT\n");if (sigismember(&curset, SIGUSR1))printf("SIGUSR1\n");if (sigismember(&curset, SIGALRM))printf("SIGALRM\n");}