深刻理解 Linux 进程间七大通信(IPC)

前言

网络编程是 Linux C/C++的面试重点,今天我就来聊一聊进程间通信的问题,文章末尾列出了参考资料,希望帮助到大家。

篇幅有点长,希望大家耐心阅读。

Linux 下的进程通信手段基本上是从 Unix 平台上的进程通信手段继承而来的。

如图所示:

​其中,最初 Unix IPC 包括:管道、FIFO、信号;

System V IPC 包括:System V 消息队列、System V 信号灯、System V 共享内存区;

Posix IPC 包括: Posix 消息队列、Posix 信号灯、Posix 共享内存区。

简单说明一下,现有大部分 Unix 和流行版本都是遵循 POSIX 标准的,而 Linux 从一开始就遵循 POSIX 标准。

图一给出了 Linux 所支持的各种 IPC 手段,在本文接下来的讨论中,

为了避免概念上的混淆,在尽可能少提及 Unix 的各个版本的情况下,所有问题的讨论最终都会归结到 Linux 环境下的进程间通信上来。

进程间通信

进程间的七大通信方式

signal、file、pipe、shm、sem、msg、socket。

下面分别介绍。

1、信号(Signal)

信号本质

信号是在软件层次上对中断机制的一种模拟,在原理上,一个进程收到一个信号与处理器收到一个中断请求可以说是一样的。信号是异步的,一个进程不必通过任何操作来等待信号的到达,事实上,进程也不知道信号到底什么时候到达。

信号是进程间通信机制中唯一的异步通信机制,可以看作是异步通知,通知接收信号的进程有哪些事情发生了。

信号机制经过 POSIX 实时扩展后,功能更加强大,除了基本通知功能外,还可以传递附加信息。

信号来源

信号事件的发生有两个来源:硬件来源(比如我们按下了键盘或者其它硬件故障);软件来源,

最常用发送信号的系统函数是 kill, raise, alarm 和 setitimer 以及 sigqueue 函数,软件来源还包括一些非法运算等操作。

进程对信号的响应

进程可以通过三种方式来响应一个信号:

(1)忽略信号,即对信号不做任何处理,其中,有两个信号不能忽略:SIGKILL 及 SIGSTOP;

(2)捕捉信号。定义信号处理函数,当信号发生时,执行相应的处理函数;

(3)执行缺省操作,Linux 对每种信号都规定了默认操作。

信号的发送

发送信号的主要函数有:

kill()、raise()、 sigqueue()、alarm()、setitimer() 以及abort()。

1、 kill 函数

对指定的进程发送什么信息。

pid>0 进程 ID 为 pid 的进程;

pid=0 同一个进程组的进程;

pid<0 pid!=-1进程组 ID 为 -pid 的所有进程;

pid=-1 除发送进程自身外,所有进程 ID 大于1的进程。

#include <sys/types.h> 
#include <signal.h> 
int kill(pid_t pid,int signo) 

2、raise 函数

向进程本身发送信号,参数为即将发送的信号值。

调用成功返回 0;否则,返回 -1。

#include <signal.h> 
int raise(int signo) 

3、sigqueue 函数

调用成功返回 0;否则,返回 -1。

第一个参数是指定接收信号的进程 ID,第二个参数确定即将发送的信号,第三个参数是一个联合数据结构 union sigval,指定了信号传递的参数,sigqueue() 比 kill() 传递了更多的附加信息,但 sigqueue() 只能向一个进程发送信号,而不能发送信号给一个进程组。

#include <sys/types.h> 
#include <signal.h> 
int sigqueue(pid_t pid, int sig, const union sigval val) 

4、 alarm 函数

专门为 SIGALRM 信号而设,在指定的时间 seconds 秒后,将向进程本身发送 SIGALRM 信号,又称为闹钟时间。

进程调用 alarm 后,任何以前的 alarm() 调用都将无效。

如果参数 seconds 为零,那么进程内将不再包含任何闹钟时间。 返回值,如果调用 alarm 前,进程中已经设置了闹钟时间,则返回上一个闹钟时间的剩余时间,否则返回 0。

#include <unistd.h> 
unsigned int alarm(unsigned int seconds) 

5、setitimer 函数

比 alarm功能强大,支持3种类型的定时器:

ITIMER_REAL:  设定绝对时间;经过指定的时间后,内核将发送SIGALRM信号给本进程;
ITIMER_VIRTUAL 设定程序执行时间;经过指定的时间后,内核将发送SIGVTALRM信号给本进程;
ITIMER_PROF    设定进程执行以及内核因本进程而消耗的时间和,经过指定的时间后,内核将发送ITIMER_VIRTUAL信号给本进程;

#include <sys/time.h> 
  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值