The world is more malleable than you think, and it is waiting for you ti hammer it into shape.--------这个世界的可塑性比你想的还要大,而它正等着你去敲打成型
文章目录
今天我们将要使用命名管道实现小黑与小白的聊天功能哦。
1,管道以及无名管道回顾
在这之前,小黑写了一篇管道还有无名管道的博客:
https://blog.youkuaiyun.com/weixin_46027505/article/details/105151719
2,为什么叫做命名管道?
-
它提供一个路径名与之关联,以FIFO的文件形式存在于文件系统中。这样,即使与FIFO的创建进程不存在亲缘关系的进程,只要可以访问该路径,就能够彼此通过FIFO相互通信(能够访问该路径的进程以及FIFO的创建进程之间),
-
它在磁盘上有对应的节点,但 没有数据块——换言之,只是拥有一个名字和相应的访问权限,通过mknode()系统调用或者mkfifo()函数来建立的。一旦建 立,任何进程都可以通过文件名将其打开和进行读写,而不局限于父子进程,当然前提是进程对FIFO有适当的访问权。当不再被进程使用时,FIFO在内存中释放,但磁盘节点仍然存在。
-
因此,通过FIFO不相关的进程也能交换数据。值得注意的是,FIFO严格遵循先进先出(first in first out),对管道及FIFO的读总是从开始处返回数据,对它们的写则把数据添加到末尾。它们不支持诸如lseek()等文件定位操作。
3,FIFO文件和普通文件区别
有名管道又称为FIFO 文件,我们对有名管道的操作可以采用操作文件的方法,如使用 open, read,write 等,有名管道适用于任何两个进程间通信。
FIFO 文件和普通文件的区别
-
读取FIFO文件的进程只能以“O_RDONLY”方式打开FIFO 文件。
-
写FIFO文件的进程只能以“O_WRONLY”的方式打开FIFO文件。
-
FIFO文件里面的内容被读取后,就消失了,但是普通文件的内容读取后还存在。
4,有名管道相关操作API函数
mkfifo()创建管道(fifo 文件)
#include <sys/types.h>
#include <sys/stat.h>
int mkfifo(const char * pathname,mode_t mode)
函数功能:创建一个FIFO文件(有名管道)
返回值:成功 :0
失败:-1
参数说明:
pathname:创建的fifo文件名字(带路径)
mode_t :文件的操作权限
删除管道unlink()
#include<unistd.h>
int unlink(const char * pathname);
函数功能:删除文件(包括fifo文件)
返回值:
成功 :0
失败 :-1
参数:
pathname:要删除的文件名字(带路径)
其他API函数
下面的就是文件i/o的函数,一样的用法,就不阐明。
- 打开管道 open()
- 关闭管道 close()
- 读/写管道 read/write
5,简单代码,用于理解(使用命名管道实现单向通信)
下面实现两个任意进程间通信,创建两个进程,一个是读进程,另一个写进程;
写进程:主要是创建fifio 文件;并将数据写入文件, 退出;
读进程: 主要读取fifo 文件的数据,并打印出来,退出

- 写进程代码:a.c
#include <sys/types.h>
#include<sys/fcntl.h>
#include<sys/stat.h>
#include <unistd.h>
#define FIFO_PATH "/home/xuxiaohei/FIFO/.file"
int main()
{
int fd;
char buf[1024]="HELLO, B proccss. I am A proccess";
mkfifo(FIFO_PATH , 0777);
fd=open(FIFO_PATH , O_WRONLY);//写进程打开方式只能以O_WRONLY方式
write(fd, buf, sizeof(buf));
close(fd);
}
- 读进程范例代码:b.c
#include<sys/types.h>
#include<sys/fcntl.h>
#include<unistd.h>
#include<stdio.h>
#define FIFO_PATH "/home/xuxiaohei/FIFO/.file"
int main()
{
int fd;
char buf[1024]={
0};
fd =open(FIFO_PATH ,O_RDONLY);//读进程只能以O_RDONLY方式打开fifo文件
read(fd,buf,1024);
printf("read data from A proccess:%s\n",buf);
close(fd);
unlink(FIFO_PATH );
}
运行程序:
首先运行 a 程序,会处于阻塞状态,直到运行b程序读取fife文件数据;
这个容易理解:水管的另一端都没打开,你又怎么可能往里面注水呢? 所以你写端只能阻塞等待读端打开,才能连接

- 然后我们打开另外一个终端,ls 后发现多了一个文件,这个文件就是管道文件。

6,复杂代码,实现双向通信(实现类似QQ聊天的小应用)
6.1 简单介绍
其实这个小应用就是上面代码的升级版本,只不过上面的代码只能单向通信,其实如何实现双向通信,之前在无名管道的博客中

本文深入探讨了命名管道(FIFO)的概念,详细解释了其工作原理、与无名管道的区别,以及如何通过命名管道实现进程间通信。文章提供了创建、读写、删除命名管道的API函数说明,并附有单向和双向通信的代码示例。
最低0.47元/天 解锁文章
681

被折叠的 条评论
为什么被折叠?



