linux通过信号进程间通信实例理解
来源:互联网 发布:知无涯者怎么解释 编辑:程序博客网 时间:2024/05/18 06:36
在linux系统编程的学习中,通过信号进行进程简编译是一大重点
本文通过一个实例加强对sigemptyset、sigprocmask的理解
int sigaction(int signum, const struct sigaction *act,struct sigaction *oldact);
其中 signum 为收到的信号
其中
struct sigaction{ void (*sa_handler)(int); // } void (*sa_sigaction)(int, siginfo_t *, void *);// } 两个函数指针仅有一个有效 sigset_t sa_mask; //阻塞信号集 int sa_flags; //若sa_flags==0则*sa_handler;有效,若sa_flags==SA_SIGINFO则*sa_sigaction有效 void (*sa_restorer)(void);//扩展}
其中sigset_t 为一个结构体,信号在int __val[32] 中以掩码储存,有32位二进制数,以对应一位标‘1’来储存对应信号
我们也可以通过
int sigprocmask(int how, const sigset_t *set, sigset_t *oldset);// 在进程阻塞信号集里,增加或删除信号
其中int how 有如下三种参数,均针对oldset SIG_BLOCK //增加 SIG_UNBLOCK //删除 SIG_SETMASK //先清空进程阻塞集号,再增加
值得一提的是信号在信号集中的存储并非简单赋值,而是以掩码的形式储存,2进制数不同位标‘1’表示不同命令的存储。在此并不详谈。
当进程信号集中存在某一信号SIG***时,向该进程发送此信号则会被阻塞,直至sa_flags对应的函数被执行完成为止。
以下为实例方便理解:
实例一:
#include <stdio.h>#include <signal.h>#include <stdlib.h>#include <unistd.h>pid_t i,j;void f(int sig){ if(kill(i,SIGINT)<0) { perror("kill fail"); } if(kill(j,SIGINT)<0) { perror("kill fail"); } wait(i,NULL,0); wait(j,NULL,0); printf("Parent process exit!\n"); exit(0);}void f_1(int sig){ printf("Child process 1 is killed by parent!\n");}void f_2(int sig){ printf("Child process 2 is killed by parent!\n");}int main(){ i = fork(); if(i<0) { perror("fork fail"); return -1; } else if(i==0) { signal(SIGINT,f_1); pause(); } else if(i>0) { j = fork(); if(j<0) { perror("fork fail"); return -1; } if(j==0) { signal(SIGINT,f_2);//收到SIGINT信号则执行f_2动作 pause(); } if(j>0) { signal(SIGINT,f); pause(); } }}
实例二:
#include<stdio.h>#include<signal.h>#include<stdlib.h>int output(sigset_t set){ printf("set.val[0]=%x\n",(int)set.__val[0]);}void handler(int sig){ int i; sigset_t sysset; printf("\n nin hadler sig=%d\n",sig); sigprocmask(SIG_SETMASK,NULL,&sysset); output(sysset); printf("return\n");}int main(){ struct sigaction act; sigset_t set,sysset,newset;//自定义信号集合 sigemptyset(&set); sigemptyset(&newset);//清空 sigaddset(&set,SIGUSR1);//向进程阻塞信号集中发送信号SIGUSR1 sigaddset(&newset,SIGUSR2); printf("\nadd sigusr1,the value of set"); output(set);//测试 printf("\nadd sigusr2,the value of newset"); output(newset); printf("\nafter set proc block set ,and then read to sysset\n"); sigprocmask(SIG_SETMASK,&set,NULL); //将系统阻塞信号集清空,然后拷贝信号集set的内容到系统阻塞信号集中; sigprocmask(SIG_SETMASK,NULL,&sysset); //将信号集sysset中的内容清空,然后拷贝系统阻塞信号集中的内容到sysset printf("system mask is:\n"); output(sysset);//测试,此时系统阻塞信号集的内容为SIGUSR1 printf("set mask is:\n"); output(set); printf("install sigalrm,and the act.sammask is newset(siguser2)\n"); act.sa_handler=handler;//在另一终端中输入kill -SIGUSR1 [该进程pid] 并不会立刻执行该信号相应动作,直到handler函数执行完毕 act.sa_flags=0; act.sa_mask=newset; sigaction(SIGALRM,&act,NULL);//pause中断进程,直至收到“SIGALRM”信号重新激活,运行act所包含的动作。 pause(); printf("after exec isr\n"); sigemptyset(&sysset);//清空sysset sigprocmask(SIG_SETMASK,NULL,&sysset); output(sysset);}
0 0
- linux通过信号进程间通信实例理解
- Linux进程间通信——信号应用实例
- 深入理解Linux进程间通信(IPC)-- 信号signal
- Linux 进程间通信 信号
- linux进程间通信--信号
- Linux进程间通信--信号
- Linux进程间通信 -- 信号
- Linux进程间通信-信号
- Linux进程间信号通信
- Linux 进程间通信 --- 信号通信 --- signal
- linux进程间通信-信号通信
- linux进程间通信-信号通信
- 唯快不破:Linux 进程间通信 --- 信号通信
- 进程间通信系列 之 信号实例
- 深入理解进程间通信之信号
- Linux进程通信--信号
- linux 进程信号通信
- linux 进程信号通信
- 手机屏幕分辨率、PPI像素密度科普知识大全
- 数据类型、存储区字节数、占位符、sizeof、输入输出、二进制相关、操作符(++,--)、主函数参数
- css样式学习笔记五
- IT近年最新技术一览
- 补偿
- linux通过信号进程间通信实例理解
- 一、REST架构风格:
- IOS-调用系统资源
- 代码重定位
- Markdown之MON
- Codeforces Beta Round #82 (Div. 2) 动态规划
- SSH框架中报错org.springframework.beans.factory.BeanCreationException或者NotWritablePropertyException
- MongoDB学习笔记(一) MongoDB介绍及安装
- 密码安全