当前位置: 首页 > news >正文

Linux 有名管道fifo进程间通信

函数原型

/** * int mkfifo(const char *pathname, mode_t mode); * * @brief 用于创建有名管道。该函数可以创建一个路径为pathname的FIFO专用文件,mode指定了FIFO的权限,FIFO的权限和它绑定的文件是一致的。FIFO和pipe唯一的区别在于创建方式的差异。一旦创建了FIFO专用文件,任何进程都可以像操作文件一样打开FIFO,执行读写操作。 * * @param pathname 有名管道绑定的文件路径 * @param mode 有名管道绑定文件的权限 * @return int */

接下来写一段发送端代码,以及接收端代码演示

发送端代码:

#include <stdio.h> #include <unistd.h> #include <sys/types.h> #include <sys/stat.h> #include <stdlib.h> #include <fcntl.h> #include <errno.h> /** * int mkfifo(const char *pathname, mode_t mode); * * @brief 用于创建有名管道。该函数可以创建一个路径为pathname的FIFO专用文件,mode指定了FIFO的权限,FIFO的权限和它绑定的文件是一致的。FIFO和pipe唯一的区别在于创建方式的差异。一旦创建了FIFO专用文件,任何进程都可以像操作文件一样打开FIFO,执行读写操作。 * * @param pathname 有名管道绑定的文件路径 * @param mode 有名管道绑定文件的权限 * @return int */ int main(int argc, char const *argv[]) { char* fifo_path = "/tmp/myfifo"; //fifo专用文件 //创建有名管道 if(mkfifo(fifo_path,0664) != 0) { if (errno != EEXIST) { // 如果不是因为文件已存在,才是真错误 perror("mkfifo failed"); exit(EXIT_FAILURE); } } //打开有名管道用于写入 int fd = open(fifo_path,O_WRONLY); if(fd == -1) { perror("open fail"); exit(EXIT_FAILURE); } char write_buf[100]; ssize_t read_num; //从控制台读取输入 while((read_num = read(STDIN_FILENO,write_buf,sizeof(write_buf))) > 0) { //写入fifo管道 write(fd,write_buf,read_num); } if(read_num < 0) { perror("read"); close(fd); exit(EXIT_FAILURE); } close(fd); printf("发送端退出\n"); unlink(fifo_path); return 0; }

接收端代码:

#include <stdio.h> #include <unistd.h> #include <sys/types.h> #include <sys/stat.h> #include <stdlib.h> #include <fcntl.h> /** * int mkfifo(const char *pathname, mode_t mode); * * @brief 用于创建有名管道。该函数可以创建一个路径为pathname的FIFO专用文件,mode指定了FIFO的权限,FIFO的权限和它绑定的文件是一致的。FIFO和pipe唯一的区别在于创建方式的差异。一旦创建了FIFO专用文件,任何进程都可以像操作文件一样打开FIFO,执行读写操作。 * * @param pathname 有名管道绑定的文件路径 * @param mode 有名管道绑定文件的权限 * @return int */ int main(int argc, char const *argv[]) { char* fifo_path = "/tmp/myfifo"; //fifo专用文件 //打开有名管道用于读取 int fd = open(fifo_path,O_RDONLY); if(fd == -1) { perror("open fail"); exit(EXIT_FAILURE); } char read_buf[100]; ssize_t read_num; //从管道文件描述符中读取 while((read_num = read(fd,read_buf,sizeof(read_buf))) > 0) { //输出到控制台 write(STDOUT_FILENO,read_buf,read_num); } if(read_num < 0) { perror("read"); close(fd); exit(EXIT_FAILURE); } close(fd); printf("接收端退出\n"); return 0; }

运行两个程序演示通信

左边为发送端,右边为接收端

动画讲解

这边用ai 生成动画以便大家理解

1. "有名" 的意义 (The Name is the Rendezvous Point)

无名管道(pipe)之所以只能在父子进程间使用,是因为它只存在于内存中,没有名字,其他进程根本“指不到”它。

  • FIFO 的突破:mkfifo在文件系统中创建了一个节点(/tmp/myfifo)。

  • 这个文件就像一个公开的接头地点。

  • 发送端和接收端不需要互为父子,它们只要大家都约定好去/tmp/myfifo这个地方,就能建立连接。

  • 注意:虽然它在磁盘上有个文件,但数据本身是不存硬盘的。那个文件只是一个“路标”,数据依然是在内核内存中流动。

2. 打开时的阻塞机制 (Blocking on Open)

这是代码中最容易让人困惑的地方(动画步骤 3):

  • 规则:FIFO 必须读写两端同时打开才能开始工作。

  • 如果你写了一个程序只调用open(path, O_WRONLY),而没有另一个程序去O_RDONLY,那么open函数会卡住(阻塞),直到另一个程序出现。

  • 这是一种天然的同步机制,保证了在写入数据之前,接收端已经准备好接收了。

3. 像操作文件一样操作管道

代码中使用了open,read,write,close,这些全是标准的文件 I/O 操作。

  • Linux 的哲学是"一切皆文件"。

  • 内核把管道伪装成了一个文件,让程序员可以用熟悉的文件操作接口来收发数据,而不需要学习新的 API。

无名管道 vs 有名管道
特性无名管道 (Pipe)有名管道 (FIFO)
存在形式仅存在于内存,无文件路径在文件系统中有路径(如/tmp/myfifo)
通信范围仅限父子、兄弟等有亲缘关系的进程任意两个进程,只要能访问该文件路径
创建方式pipe()mkfifo()命令或函数
数据流单向字节流单向字节流
持久性进程结束即销毁文件节点一直存在,直到unlink
http://www.cnnetsun.cn/news/23618.html

相关文章:

  • 36、Linux 系统安全防护全攻略
  • React Native语音识别终极指南:让你的应用听懂用户心声
  • 水银温度计淘汰不用慌!健康一体机:测温只是开始,多项目检测才是核心
  • 突然发布!GPT-5.2深夜来袭,3个版本碾压人类专家,打工人该怎么选?
  • 字符串特性解析:Python不可变性引发的错误
  • 【万字长文】大模型与智能体本质区别解析:系统级架构与模型升级的对比与应用指南!
  • 从零开始构建Agentic RAG:结合RAG与AI Agent的大模型新范式实战指南!
  • EasyPoi 数据脱敏
  • 收藏必备!GPT-5.2震撼发布:OpenAI反击战,职场程序员的AI新神器
  • 3步上手Sparta:让网络安全渗透测试变得像玩游戏一样简单
  • Android媒体画廊应用终极指南:轻量级隐私保护的完美选择
  • FT8371A,FT8371B,FT8371C 次边同步整流芯片典型应用资料分析
  • 智慧文旅信创落地新标杆:四川省文旅厅完成MySQL 5.7平滑替换,筑牢省级管理平台自主可控底座
  • 7、Unix/Linux 网络监控与日志管理全解析
  • 11、数据备份与系统安装全攻略
  • 12、Unix/Linux 系统设置与生产准备全攻略
  • 5步掌握网页数据采集:零代码工具完全操作手册
  • 15、测试系统与“安全”系统
  • TradingAgents-CN实战指南:从零开始构建你的AI交易智能体团队
  • 18、系统与网络安全全解析
  • 检索增强生成(RAG)在Java应用中的实践指南
  • 机器学习测试神器TensorFlow Model Analysis实战
  • Monitorian:多显示器亮度调节的终极解决方案,一键掌控视觉舒适度
  • 2025 主流 GEO 优化服务商 TOP4,助力 ToB 精准选型
  • 影刀RPA×AI双剑合璧!小红书商品图片批量上传,效率提升50倍![特殊字符]
  • 从中国出发,向世界展示!AI开发者亚马逊云科技狂欢专属攻略!
  • WPF SynchronizationContext的使用
  • 影刀RPA实战:AI智能生成小红书销售日报,3分钟搞定全天数据![特殊字符]
  • Sossoldi跨平台部署完全指南:从开发到上线的财富管理应用构建
  • 终极韩语NLP指南:快速掌握KoNLPy核心功能