@进程间通信IPC(inter process communication)
信号(signal)
信号是一种比较复杂的通信方式,通知接收进程某个事件已经发生。
信号是linux系统中用于进程间通信或者操作的一种机制,可以在任何时候发送给某一个进程,不需要知道该进程的状态。
kill - l
linux系统提供了几十种信号,代表着不同含义。
常用的信号
信号名 | 信号说明 |
---|---|
SIGINT | Ctrl+C按键终止程序运行的信号,程序终止 |
SIGILL | 非法指令,程序终止 |
SIGKILL | 强制杀死程序信号,不可捕捉,程序终止 |
SIGUSR1 | 用户自定义信号1 |
SIGUSR2 | 用户自定义信号2 |
SIGSEGV | 段错误系统给程序发送的信号,程序终止 |
SIGPIPE | 管道破裂,程序终止 |
SIGALRM | alarm系统调用发送的信号,定时,时间到了,程序终止 |
SIGTERM | kill命令默认发送的信号,程序终止 |
SIGCHLD | 子进程退出的信号,忽略该信号 |
安装信号
linux下有两种安装信号
signal()函数原型。
#include <signal.h>
typedef void (*sighandler_t)(int);
sighandler_t signal(int signum, sighandler_t handler);
例子
我们知道,父进程在创建子进程之后,究竟是父进程先运行还是子进程先运行没有规定,由操作系统的调度来决定。
当我们需要确保运行的顺序时,可以使用信号来实现进程间的同步问题。
描述:1.、如果父进程先运行,则进入休眠等待状态,等待子进程给他发送信号才苏醒,这样就可以确保子进程先执行任务。
2、子进程完成任务后,等待父进程给他发送信号才退出,父进程调用wait等待子进程退出后再退出。
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <signal.h>
int g_child_stop = 0;
int g_parent_run = 0;
void sig_child(int signum)
{
if( SIGUSR1 == signum )
{
int g_child_stop = 1;
}
}
void sig_parent(int signum)
{
if( SIGUSR2 == signum )
{
int g_parent_run = 1;
}
}
int main(int argc ,char **argv)
{
int pid;
int wstatus;
signal(SIGUSR1,sig_child);
signal(SIGUSR2,sig_parent);
if( (pid=fork()) <0 )
{
printf("Create child processcfailure:%s\n",strerror(errno));
return -2;
}
else if(pid==0)
{
/*子进程在这里运行,并告诉父进程开始运行*/
printf("Child process start running and send parent a signal\n");
kill(getppid(),SIGUSR2);//给父进程发信号
while( !g_child_stop )
{
sleep(1);
}
printf("Child process receive signal from parent and exit now\n");
return 0;
}
printf("Parent process hangs up until receive signal from child\n");
while( !g_parent_run )
{
sleep(1);
}
/*父进程在这里运行,并告诉子进程退出*/
printf("Parent process start running and send child a signal to exit\n");
kill(pid,SIGUSR1);
/*父进程等待子进程退出*/
wait(&wstatus);
printf("Parent process wait child process die and exit now\n");
return 0;
}