【进程通信】之管道通信

摘要:

1、进程间通信的简介;

2、pipe管道通信;

3、pipe管道通信的特点;

4、管道通信过程中会遇到的四种情况;

5、fifo管道通信;

6、对比fifo管道与pipe管道;

7、管道  |;

8、管道的缓冲区的容量大小;

1、进程间通信

简称:IPC(InterProcess Communication) 
每个进程各自有不同的用户地址空间,任何一个进程的全局变量在另一个进程中都看不到;
所以进程之间要交换数据必须通过内核,在内核中开辟一块缓冲区,
进程1把数据从用户空间拷到内核缓 冲区,
进程2再从内核缓冲区把数据读走,
内核提供的这种机制称为进程间通信。
下面是一个图形解释进程间通信的形象图:

2、管道通信(pipe)

管道是一种最基本的的IPC机制,是有pipe函数来提供的。
函数的原型是:
 #include <unistd.h>//函数的头文件

 int pipe(int pipefd[2]);//函数原型
pipe函数参数与函数返回值简介:



在调用pipe函数时在内核中开辟一块缓冲区(也可看成是文件)(称为管道)用于通信;
它有一个读端一个写端,然后通过filedes参数传出给用户程序两个文件描述符;
filedes[0]指向管道的读端,filedes[1]指向管道的写端。
所以管道在用户程序看起来就像一个打开的文件,通过read(filedes[0]);或者write(filedes[1]);
向这个文件读写数据其实是在读写内核缓冲区。pipe函数调用成功返回0,调用失败返回-1。
上面的就是这个函数的大致的使用方法:
但是开辟管道之后要怎么来实现两个进程之间的通信,下面是一些使用的方法:
1、父进程创建管道

2、父进程fork生出子进程

3、父进程关闭读端,子进程关闭写端


完成上面的操作之后 ,现在的进程就是  一个进程来读,一个进程来写;
代码实现:

pipe管道通信的特点:

1、管道是依靠文件系统的,所以管道 的生命周期是 随进程的;
2、进程之间的管道通信是单向的。只能有一个进程读,另一个进程写;要么反过来;
3、这种只能用于有血缘关系的进程(常用于是兄弟进程),因为他们需要有相同的文件描述符表;
4、进程间的通信是按照 数据流的方式来通信,一个进程写了多少,则此进程就读多少;
5、管道之间的读写是按照同步的方式来进行的;(写完之后再读)

使用管道过程中需要注意的四种问题:

1、如果指向管道写端的文件描述符都关闭了,而仍然有进程从管道的读端读数据,那么管道中剩余的数据都被读取后,再次read会返回0,就像读到文件末尾一样。
代码验证:

代码中子进程来写,五次之后关闭写端 、、、、的输出结果:


2、如果有指向管道写端的文件描述符没关闭,而持有管道写端的 进程也没有向管道中写数据,这时有进程从管道读端读数据,那么管道中剩余的数据都被读取后,再次read会阻塞,直到管道中有数据可读了才读取数据并返回。
代码验证:

代码中的子进程每次写完之后,都会等上100秒,父进程读完之后都会 阻塞等待   :

3、如果指向管道读端的文件描述符都关闭了,这时有进程向管道的写端write,那么该进程会收到信号SIGPIPE,通常会导致进程异常终止。
代码验证:

代码中的父进程来读,五次之后关闭读端,父进程来接受自己成的退出信息

4、如果有指向管道读端的文件描述符没关闭,而持有管道读端的进程也没有从管道中读数据,这时有进程向管道写端写数据,那么在管道被写满时再次write会阻塞,直到管道中有空位置了才写入数据并返回。
代码验证:

代码中的 父进程读完之后,等待100秒   ,,,结果:

3、管道通信(FIFO)

概念:

pipe管道,一个不足之处是没有名字,因此,只能用于具有亲缘关系的进程间通信,在命名管道(named pipe或FIFO)提出后,该限制得到了克服。。
FIFO不同于管道之处在于它提供一个路径名与之关联,以FIFO的文件形式存储于文件系统中。命名管道是一个设备文件,因此,即使进程与创建FIFO的进程不存在亲缘关系,只要可以访问该路径,就能够通过FIFO相互通信。值得注意的是,FIFO(first input first output)总是按照先进先出的原则工作,第一个被写入的数据将首先从管道中读出。

管道的创建:

创建命名管道的系统函数有两个:mknod和mkfifo。两个函数均定义在头文件sys/stat.h。
我们这里主要介绍的mkfifo
函数原型如下:
#include <sys/types.h>
#include <sys/stat.h>

int mkfifo(const char *pathname, mode_t mode);
函数原型的解析:


代码的验证函数:
进程client  写:

进程server   读:

命名管道也被称为FIFO文件,它是一种特殊类型的文件,它在文件系统中以文件名的形式存在,但是它的行为却和之前所讲的没有名字的管道(匿名管道)类似。

4、管道(pipe)、命名管道(fifo)对比

对 上面两个管道的相同点:
1、依赖文件系统,生命周期随进程;
2、都是单向通信的;
3、按照数据流的方式通信;
4、读写之间都是按照同步机制来访问的。
不同点:
1、管道只能应用于有血缘关系的进程,命名管道可应用于所有的进程
2、管道依赖于文件描述符表,不需要明确的创建文件,命名管道需要明确的创建fifo文件存于文件系统中。

5、管道  |

很多的人都知道  |  这个符号是一种管道 ,但是学了上面的知识 ,我们就要知道  ;
|这是一种匿名的管道,
为什么呢?
首先、它没有穿件新的管道文件;
再者、它通信的进程虽然不是父子进程,但是可以看成是兄弟进程。  同是shell创建的子进程。

5、管道缓冲区的大小

每一个管道的缓冲区都是有大小的;
我们可以使用命令 
ulimit -a
来查看管道的容量:

我们在其来验证一下:

实现的结果:

pipe capacity  =  65536;

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值