进程间通信,有名管道(pipe)与无名管道(fifo)的解析与运用,以及代码实现

 

 🎊【进程通信与并发】专题正在持续更新中,进程,线程,IPC,线程池等的创建原理与运用✨,欢迎大家前往订阅本专题,获取更多详细信息哦🎏🎏🎏

🪔本系列专栏 -  进程通信与并发

🍻欢迎大家  🏹  点赞👍  评论📨  收藏⭐️

📌个人主页 - 勾栏听曲_0的博客📝

🔑希望本文能对你有所帮助,如有不足请指正,共同进步吧🏆

🎇善治病者,必医其受病之处;善救弊者,必塞其起弊之源。📈

无名管道(pipe)

介绍

        它在文件系统中没有名字(没有inode),它的内容在内核中,访问pipe的方式都是通过文件系统的API(read/write)

        它不能用open,但是read/write又需要一个文件描述符!!!

        所以在创建这个pipe的时候,就必须要返回文件描述符!!!

        pipe在创建时,在内核中开辟一块缓冲区,作为pipe文件的内容的存储空间,同时返回两个文件描述符(一个用来读,一个时用来写)

特点

           (1)pipe有两端,一端时用来写,一端是用来读;

           (2)按顺序读;不支持lseek(光标移动)

           (3)内容读走了,就没有啦

           (4)pipe(无名管道) 随内核持续性

接口

    头文件

#include <unistd.h>

    函数功能

       pipe用来在内核中创建一个无名管道,pipefd用来保存创建好的无名管道的两个文件描述符,pipe创建的管道,默认是"阻塞方式"

    函数原型

       int pipe(int pipefd[2]);

    函数参数

       int pipefd[2]     //数组。 

              pipefd[0] 保存读的文件描述符;

              pipefd[1] 保存写的文件描述符;

          

    函数返回值

       成功返回0 

       失败返回-1,同时errno被设置。

注意事项

    pipe(无名管道)的使用范围:只要两个进程可以获取这个pipe(无名管道)的文件描述符,就可以使用pipe(无名管道)来通信。

    pipe(无名管道)本身是全双工通信,但是两个进程使用一个管道进行全双工通信就必须要有某种方式同步,否则就可能自己读到自己写入的数据。所以在工程项目中,我们一般使用两个或以上的管道来实现全双工通信,一个读,一个写,人为的把它看成半双工通信。

    上面说到了pipe(无名管道)的使用范围,而这个使用范围一般又是进程间有亲缘关系的进程,除非通过某些方式将pipe(无名管道)告知其他进程。因此pipe(无名管道)一般都用于有亲缘关系的进程间通信。为什么呢?其原因就是pipe(无名管道)它没有名字,只能靠创建pipe(无名管道)时的文件描述符来确定pipe(无名管道)。记住这个特点,我们再看FIFO(有名管道)。

代码实例

    一下代码实现创建一个pipe(无名管道),子进程先往pipe(无名管道)中写入数据,然后再由父进程向pipe(无名管道)读取子进程写入的数据。

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>


int main(int argc, char * argv [])
{	
	int fd[2]; 
	int p = pipe(fd);
	if(p == -1)
	{
		perror("pipe failed\n");
	}

	pid_t pid = fork();
	if(pid == -1)
	{
		perror("fork failed\n");
	}
	if(pid > 0) 
	{	
		int statues;
		int w = wait(&statues);
		if(w == -1)
		{
			perror("wait failed\n");
			return -1;
		}

		char buf[6] = {0};
		int r = read(fd[0],buf,5);
		if(r != 5)
		{
			perror("read fd[0] failed\n");
		}
		printf("read's content is %s\n",buf);
	}
	else if(pid == 0)
	{	
		int w = write(fd[1],"hello",5);
		if(w != 5)
		{
			perror("write fd[1] failed\n");
		}
	
	}
	return 0;
}

有名管道(fifo)

介绍

fifo是在pipe的基础上,给fifo在文件系统中创建一个inode(它会在文件系统中有一个文件名),但是fifo文件的内容却是在内核中!!!

           fifo的文件名随文件系统持续性的;

           fifo的文件内容存在于内核,随内核持续性的。

           fifo同pipe一样,出除了fifo在文件系统中有一个文件名。所以特点也与pipe(无名管道)一样。

接口

fifo文件怎么创建呢?

    通过mkfifo函数接口 

    头文件

       #include <sys/types.h>

       #include <sys/stat.h>

    函数功能

       用来在文件系统中创建一个fifo(有名管道)

    函数原型

       int mkfifo(const char *pathname, mode_t mode);

    函数参数

       const char *pathname     //要创建的有名管道,在文件系统中的名字

       mode_t mode                 //创建的有名管道的权限,有两种方式指定:

                         (1)0660 0777 ...

                         (2)S_IRUSR   

    函数返回值

        成功:返回0

       失败:返回-1,同时errno被设置。

注意事项

    FIFO(有名管道)它和PIPE(无名管道)类似,除了它再文件系统中有一个名字。它可以被多个进程打开用来读或写。当进程用FIOF来交换数据时,内核根本没有把数据写到文件系统中去,而是保存在内核的内部,因此FIFO在文件系统中没有内容,它仅作为文件系统的一个引用入口,提供一个文件名,给其它进程去open它。

    在数据交换前,FIFO的两端(read,write)必须都被打开。通常情况下,你打开FIFO的一端,会阻塞,直到另外一端也被打开。

一个进程也可能以"非阻塞"方式(O_NONBLOCK)去打开。

    在这种情况下(以“非阻塞方式”),只读打开总会成功,即便写端没有被打开;只写打开总会失败,并且errno == EENXIO,除非读端已经打开。

阻塞与非阻塞

阻塞方式: 

    阻塞地读或写 

       读的时候,如果没有数据,则read会阻塞

       写的时候,如果没有空间,则write会阻塞 

             

非阻塞方式

    以非阻塞方式读或写 

       读的时候,如果没有数据,立即返回,设置相应的错误码

       写的时候,如果没有空间,立即返回,设置相应的错误码

代码实例

    一下代码实现两个无亲缘关系的进程间使用FIFO(有名管道)进程通信。一个进程用于读,一个进程用于写。

        第一个进程,用于将数据写进管道。

#include <stdio.h>
#include <sys/stat.h>	   
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>

int main(int argc, char * argv [ ])
{
	//创建一个fifo有名管道文件
	int m =  mkfifo("./test.fifo", 0660);
	if(m == -1)
	{
		perror("mkfifo failed\n");
	}
	//打开管道文件
	int fd = open("./test.fifo",O_RDWR);
	if(fd == -1)
	{
		perror("open failed\n");
	}
	
	//写数据到管道文件
	char buf[11] = "I LOVE YOU";
	int w = write(fd, buf, 11);
	if(w != 11)
	{
		perror("write failed\n");
	}
	//关闭文件
	int c = close(fd);
	if(c == -1)
	{
		perror("close failed\n");
	}
	return 0;
}

        第二个进程,用于将管道中的数据读出来。

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <fcntl.h>

int main(int argc, char * argv [ ])
{	
	int fd = open("./test.fifo",O_RDONLY);
	if(-1 == fd)
	{
		perror("open failedn");
	}

	char buf[6] = {0};
	int r = read(fd,buf,5);
	if(r != 5)
	{
		perror("read fd failed\n");
	}
	printf("read's content is %s\n",buf);
	itn c = close(fd);
	if(c == -1)
	{
		perror("close fd failed\n");
	}
	return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/14074.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

命令执行漏洞概述

命令执行漏洞概述 命令执行定义命令执行条件命令执行成因命令执行漏洞带来的危害远程命令执行漏洞相关函数assert()preg_replace()call_user_func() a ( a( a(b)可变函数远程命令执行漏洞的利用系统命令执行漏洞相关函数system()exec()shell_exec()passthru&#xff08;&#x…

Node【Global全局对象】之【Process】

文章目录 &#x1f31f;前言&#x1f31f;Process&#x1f31f;process属性&#x1f31f;process.env &#x1f31f;process方法&#x1f31f;process事件&#x1f31f;uncaughtException &#x1f31f;写在最后 &#x1f31f;前言 哈喽小伙伴们&#xff0c;新的专栏 Node 已开…

八、vue-基础之列表渲染v-for、v-for中的key属性的作用

一、v-for列表渲染 在真实开发中&#xff0c;我们往往会从服务器拿到一组数据&#xff0c;并且需要对其进行渲染。 这个时候我们可以使用v-for来完成&#xff1b;v-for类似于JavaScript的for循环&#xff0c;可以用于遍历一组数据&#xff1b; 二、v-for基本使用 &#xff0…

轻松掌握k8s的kubectl使用命令行操作Service知识点02

1、Service将同类型一组应用统一IP访问 将一组 Pods 网络服务的抽象方法。统一Ip后&#xff0c;默认就实现了负载均衡。 1、只在Pod内部任意机器访问的ClusterIp类型 在命令行操作生成一个ClusterIp地址。这种ClusterIp只能在Pod内部访问。 生成了ClusterIp之后&#xff0…

学生成绩管理系统【GUI/Swing+MySQL】(Java课设)

系统类型 Swing窗口类型Mysql数据库存储数据 使用范围 适合作为Java课设&#xff01;&#xff01;&#xff01; 部署环境 jdk1.8Mysql8.0Idea或eclipsejdbc 运行效果 本系统源码地址&#xff1a;https://download.csdn.net/download/qq_50954361/87700420 更多系统资源库…

【机智云物联网低功耗转接板】+模拟MCU快速上手

GE211是机智云自研的定制化转接板&#xff0c;使用 ESP32-C3-WROOM-02 通讯模块&#xff0c;适用于白色智能家电等设备应用。 转接板已经烧录了机智云连云的最新GAgent固件&#xff0c;所以不需要烧写任何软件就可以快速上手使用。 GE211板卡带有一个串口&#xff0c;一般是把这…

58 openEuler搭建Mariadb数据库服务器-管理数据库

文章目录 58 openEuler搭建Mariadb数据库服务器-管理数据库58.1 创建数据库58.2 查看数据库58.3 选择数据库58.4 删除数据库58.5 备份数据库58.6 恢复数据库 58 openEuler搭建Mariadb数据库服务器-管理数据库 58.1 创建数据库 可以使用CREATE DATABASE语句来创建数据库。 CR…

多线程并发编程学习笔记9(小滴课堂)------线程池及Executor框架

它只会使用10个线程。因为我们设置了它的容量。 我们现在把这个队列容量设置为20. 我们可以看到这里它使用了20个线程。但是出了异常&#xff0c;这个后面我们会学习。 我们现在使用一下我们的callable&#xff1a; 一般我们如果是想在线程执行完以后&#xff0c;获得一个返回…

SpringBoot第 17 讲:SpringBoot+JWT

关于JWT的讲解请参考&#xff1a;SpringCloud第14讲&#xff1a;&#xff08;番外篇&#xff09;JWT 一、项目演示 没有登陆直接请求列表接口&#xff0c;系统会要求先进行登录 登录成功后请求列表接口&#xff0c;可以正常响应数据 二、后台开发 2.1、pom.xml 添加redis…

网口通讯与串口通讯

目录 一、简介以及数据格式&#xff1a; 二、网口通讯与串口通讯主要区别&#xff1a; 三、工具小助手&#xff1a; 一、简介以及数据格式&#xff1a; 网口通讯&#xff08;Ethernet&#xff09;和串口通讯&#xff08;Serial&#xff09;都是用于数据传输的通信协议。 1、…

Linux基础——DNS服务器原理及搭建

Linux基础——DNS服务器原理及搭建 一、DNS服务器原理1.DNS系统分布式数据结构2.DNS查询类型3.DNS服物器类型 二、搭建DNS域名解析服务器步骤1.安装bind软件包2. 查看需要修改的配置文件所在路径3. 修改主配置文件4. 修改区域配置文件&#xff0c;添加正向区域配置5.配置正向区…

iptables表、链、规则

netfilter/iptables&#xff08;也就是常说的iptables&#xff09;组成Linux平台下的包过滤防火墙&#xff0c;具有完成封包过滤、封包重定向和网络地址转换&#xff08;NAT&#xff09;等功能。 netfilter是Linux 核心中一个通用架构&#xff0c;它提供了一系列的"表&quo…

POLARDB 从一个使用者的角度来说说,POALRDB 怎么打败 MYSQL RDS

开头还是介绍一下群&#xff0c;如果感兴趣polardb ,mongodb ,mysql ,postgresql ,redis 等有问题&#xff0c;有需求都可以加群群内有各大数据库行业大咖&#xff0c;CTO&#xff0c;可以解决你的问题。加群请联系 liuaustin3 &#xff0c;在新加的朋友会分到2群&#xff08;共…

【云原生|Docker】14-Dokcer Harbor高可用部署

【云原生Docker】14-Dokcer Harbor高可用部署 文章目录 【云原生Docker】14-Dokcer Harbor高可用部署前言Harbor高可用方案单主复制双主复制多Harbor共享后端存储 Harbor高可用部署方案说明环境说明部署步骤安装nfs安装redis和PostgreSQL安装harbor配置nginx访问测试 总结 前言…

Docker harbor私有仓库部署与管理

目录 1.Docker搭建本地私有仓库 1.首先下载 registry 镜像 2.在 daemon.json 文件中添加私有镜像仓库地址 3. 运行 registry 容器 4.为镜像打标签 5.上传到私有仓库 6.列出私有仓库的所有镜像 7.列出私有仓库的centos镜像有哪些tag 8.先删除原有的centos的镜像&#xf…

TCP协议的相关特性(续)

TCP协议的相关特性 &#x1f50e;滑动窗口&#x1f50e;流量控制&#x1f50e;拥塞控制&#x1f50e;延时应答&#x1f50e;捎带应答&#x1f50e;面向字节流(粘包问题)&#x1f50e;异常情况&#x1f50e;总结 关于 确认应答 超时重传, 连接管理 请参考: 点击这里 &#x1f5…

【场景生成与削减】基于蒙特卡洛法场景生成及启发式同步回带削减风电、光伏、负荷研究(Matlab代码实现)

&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜密&#xff0c;逻辑清晰&#xff0c;为了方便读者。 ⛳️座右铭&a…

无人机遥感影像应用

目录 一、无人机遥感技术 二、无人机遥感影像数据生产 三、无人机遥感影像应用 一、无人机遥感技术 1.无人机遥感系统组成 1.1无人机遥感系统组成—无人机平台 1.2无人机遥感系统组成—传感器 2.无人机遥感技术的特点 高时效性&#xff1a;准确并快速获取地表数据 高分辨率…

[强化学习]学习路线和关键词拾零

强化学习学习方法和路线 学习路线 先从基础教材开始&#xff0c;构建RL的知识框架&#xff0c;熟悉关键名词和公式推导&#xff0c;扩展到Model-Free的Value-Based和Policy-Based方法&#xff0c;同时参考github的代码练习。接下来精读几篇经典论文&#xff0c;如DQN,PPO等。…

Python高光谱遥感数据处理与机器学习

Python高光谱遥感数据处理与机器学习 第一章、高光谱基础 高光谱遥感简介 什么是高光谱遥感&#xff1f; 高光谱遥感为什么重要&#xff1f; 高光谱遥感与其他遥感技术的区别是什么&#xff1f; 高光谱遥感的历史和发展 高光谱传感器与数据获取 高光谱传感器类型 如何获…