进程间通信(IPC)的方法:命名管道

      使用管道时,一个进程的输出可成为另外一个进程的输入。
      命名管道(Named pipe或FIFO)是一种类似于管道的特殊文件,但在文件系统上有一个名称,它允许以先进先出(FIFO, first in, first out)的方式存储有限数量的数据。它的使用类似于消息传递,其中一个进程发送一条信息,其它进程接收它。数据以FIFO方式以高吞吐速度进入管道。但是,队列一次可以容纳的最大数据大小为16页(pages)或65536字节。它实际上使用了一块内核内存。
      命名管道是在文件系统中作为一个特殊的设备文件而存在。不同祖先的进程之间可以通过命名管道共享数据。当共享命名管道的进程执行完所有的I/O操作以后,命名管道将继续保存在文件系统中,以便以后使用,除非调用unlink。通过命名管道,不相关的进程也能交换数据。一旦已经用mkfifo函数创建了一个FIFO,就可用open打开它。实际上,一般的文件I/O函数(close、read、write、unlink等)都可用于FIFO。
      只要FIFO有空间,write函数就是非阻塞的,但read会阻塞当前线程。
      命名管道总结
      (1).同步(用于单向管道);
      (2).队列大小为16页(page),每页4096字节。只要数据消耗足够快,数据大小就没有限制;
      (3).单个管道的单向通信;
      (4).以线性方式读写;
      (5).自动内存管理。
      注:以上内容主要来自网络整理。
      如果父进程和子进程之间互相发送接收数据,需要两根管道,如以下测试代码:

#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <fcntl.h>
#include <string.h>
#include <error.h>
#include <iostream>
#include <thread>
#include <cctype>typedef struct message {int pid;char ch;
} message;int main(int argc, char **argv)
{const char *named_pipe1 = "/tmp/named_pipe1", *named_pipe2 = "/tmp/named_pipe22";unlink(named_pipe1); // deletes a name from the file systemunlink(named_pipe2);if (mkfifo(named_pipe1, 0666) < 0 || mkfifo(named_pipe2, 0666) < 0) { // make a FIFO special file(a named pipe), if the file exists, the call will failfprintf(stderr, "fail to mkfifo: %s\n", strerror(errno));return -1;}struct stat buffer1, buffer2;if (stat(named_pipe1, &buffer1) != 0 || stat(named_pipe1, &buffer2) != 0) { // retrieve information about the file pointed to by pathnamefprintf(stderr, "fail to stat: %s\n", strerror(errno));return -1;}pid_t pid = fork();if (pid < 0) {fprintf(stderr, "fail to fork\n");return -1;}if (pid == 0) { // child processauto fd1 = open(named_pipe1, O_RDONLY); // read onlyauto fd2 = open(named_pipe2, O_WRONLY); // write onlyif (fd1 < 0 || fd2 < 0) {fprintf(stderr, "fail to open: %d, %s\n", pid, strerror(errno));exit(1);}for (int i = 0; i < 5; ++i) {message msg;auto ret = read(fd1, &msg, sizeof(msg));if (ret < 0) {fprintf(stderr, "fail to read: %d, %d %s\n", pid, i, strerror(errno));exit(1);}msg.ch = std::toupper(msg.ch);ret = write(fd2, &msg, sizeof(msg));if (ret < 0) {fprintf(stderr, "fail to write: %d, %d, %s\n", pid, i, strerror(errno));exit(1);}std::this_thread::sleep_for(std::chrono::milliseconds(100));}close(fd1);close(fd2);exit(0);}if (pid > 0) { // parent processauto fd1 = open(named_pipe1, O_WRONLY); // write onlyauto fd2 = open(named_pipe2, O_RDONLY); // read onlyif (fd1 < 0 || fd2 < 0) {fprintf(stderr, "fail to open: %d, %s\n", pid, strerror(errno));exit(1);}for (unsigned char i = 0; i < 5; ++i) {message msg = {pid, 'a'+i};auto ret = write(fd1, &msg, sizeof(msg));if (ret < 0) {fprintf(stderr, "fail to write: %d, %d, %s\n", pid, i, strerror(errno));exit(1);}fprintf(stdout, "src char: %c\n", msg.ch);ret = read(fd2, &msg, sizeof(msg));if (ret < 0) {fprintf(stderr, "fail to read: %d, %d, %s\n", pid, i, strerror(errno));exit(1);}fprintf(stdout, "dst char: %c\n", msg.ch);std::this_thread::sleep_for(std::chrono::milliseconds(100));}close(fd1);close(fd2);int status;auto pid2 = wait(&status); // system call suspends execution of the calling thread until one of its children terminatesfprintf(stdout, "process ID of the terminated child: %d\n", pid2);if (WIFEXITED(status)) { // returns true if the child terminated normallyfprintf(stdout, "child process ended with: exit(%d)\n", WEXITSTATUS(status));}if (WIFSIGNALED(status)) { // returns true if the child process was terminated by a signalfprintf(stderr, "child process ended with: kill -%d\n", WTERMSIG(status));}}unlink(named_pipe1); // deletes a name from the file systemunlink(named_pipe2);fprintf(stdout, "====== test finish ======\n");return 0;
}

      build.sh内容如下:

#! /bin/bashif [ -d build ]; thenecho "build directory already exists, it does not need to be created again"
elsemkdir -p build
ficd build
cmake ..
makerc=$?
if [[ ${rc} != 0 ]];thenecho "#### ERROR: please check ####"exit ${rc}
fiecho "==== build finish ===="

      CMakeLists.txt内容如下:

cmake_minimum_required(VERSION 3.22)
project(samples_multi_process)set(CMAKE_BUILD_TYPE Release) # only works under linux
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -O2 -std=c++17")file(GLOB samples ${PROJECT_SOURCE_DIR}/test_*.cpp)
#message(STATUS "samples: ${samples}")foreach(sample ${samples})string(REGEX MATCH "[^/]+$" name ${sample})string(REPLACE ".cpp" "" exec_name ${name})#message(STATUS "exec name: ${exec_name}")add_executable(${exec_name} ${sample})
endforeach()

      执行结果如下图所示:

      GitHub:https://github.com/fengbingchun/Linux_Code_Test

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

http请求头部(header)详解

目录 常见的请求头部字段 GET方法的使用方法&#xff1a; POST方法的使用方法&#xff1a; Accept字段的使用方法 Content-Type字段的使用 总结 在互联网协议中&#xff0c;HTTP请求头部&#xff08;header&#xff09;是一个非常重要的组成部分。它们是客户端和服务器之…

Vue + Element UI 前端篇(十):动态加载菜单

Vue Element UI 实现权限管理系统 前端篇&#xff08;十&#xff09;&#xff1a;动态加载菜单 动态加载菜单 之前我们的导航树都是写死在页面里的&#xff0c;而实际应用中是需要从后台服务器获取菜单数据之后动态生成的。 我们在这里就用上一篇准备好的数据格式Mock出模…

Spring boot 第一个程序

新建工程 选择spring-boot版本 右键创建类TestController&#xff1a; 代码如下&#xff1a; package com.example.demo; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springf…

【图卷积神经网络】1-入门篇:为什么使用图神经网络(下)

为什么使用图神经网络? 在本书中,我们将重点介绍图学习技术中的深度学习家族,通常称为图神经网络。GNNs是一种新的深度学习架构类别,专门设计用于处理图结构化数据。与主要用于文本和图像的传统深度学习算法不同,GNNs明确地用于处理和分析图数据集(见图1.4)。 图1.4 - …

内网穿透:FRP(Forwarding Remote Proxy)反向代理

frp 是一个可用于内网穿透的高性能的反向代理应用&#xff0c;支持 tcp, udp 协议&#xff0c;为 http 和 https 应用协议提供了额外的能力&#xff0c;且尝试性支持了点对点穿透 下载地址 https://github.com/fatedier/frp/releases 选择最新的就行&#xff0c;linux和windo…

ac7260网卡不能连5g

之前路由器是双频&#xff0c;最近为了连物联网一堆&#xff0c;把双频拆成两个wifi 结果电脑上装的pdd网卡就罢工了&#xff0c;连4g可以&#xff0c;但是连5g网络就不行&#xff0c;连上却没网&#xff0c;导致网盘下东西慢。刚开始以为是tplink的易展问题&#xff0c;结果看…

无涯教程-Flutter - 数据库

SQLite" class"css-1occaib">SQLite数据库是基于事实和标准SQL的嵌入式数据库引擎&#xff0c;它是小型且经过时间考验的数据库引擎&#xff0c;sqflite软件包提供了许多函数&#xff0c;可以有效地与SQLite数据库一起使用&#xff0c;它提供了操作SQLite数据…

sql:SQL优化知识点记录(十)

&#xff08;1&#xff09;慢查询日志 Group by的优化跟Order by趋同&#xff0c;只是多了一个having 开启慢查询日志&#xff1a; 演示一下慢sql&#xff1a;4秒之后才会出结果 查看一下&#xff1a;下方显示慢查询的sql &#xff08;2&#xff09;批量插入数据脚本 函数和存…

【广州华锐互动】智慧园区3D数据可视化系统有什么作用?

随着科技的不断发展&#xff0c;智慧园区3D数据可视化系统已经成为了现代园区管理的重要组成部分。它通过将大量的数据进行整合、分析和展示&#xff0c;为企业提供了一个直观、高效的数据管理平台&#xff0c;帮助企业实现精细化管理&#xff0c;提高运营效率&#xff0c;降低…

Python实操 PDF自动识别并提取Excel文件

最近几天&#xff0c;paddleOCR开发了新的功能&#xff0c;通过将图片中的表格提取出来&#xff0c;效果还不错&#xff0c;今天&#xff0c;作者按照步骤测试了一波。 首先&#xff0c;讲下这个工具是干什么用的&#xff1a;它的功能主要是针对一张完整的PDF图片&#xff0c;可…

uni-app 可视化创建的项目 移动端安装调试插件vconsole

可视化创建的项目&#xff0c;在插件市场找不到vconsole插件了。 又不好npm install vconsole 换个思路&#xff0c;先创建一个cli脚手架脚手架的uni-app项目&#xff0c;然后再此项目上安装vconsole cli脚手架创建uni-app项目 安装插件 项目Terminal运行命令&#xff1a;npm…

Docker-基础命令使用

文章目录 前言命令帮助命令执行示意图docker rundocker psdocker inspectdocker execdocker attachdocker stopdocker startdocker topdocker rmdocker prune参考说明 前言 本文主要介绍Docker基础命令的使用方法。 命令帮助 Docker命令获取帮助方法 # docker -h Flag shor…

python library reference

文章目录 1. 标准库2. Python标准库介绍3. 示例 1. 标准库 https://docs.python.org/zh-cn/3/library/ https://pypi.org/ https://pypi.org/search/ 2. Python标准库介绍 Python 语言参考手册 描述了 Python 语言的具体语法和语义&#xff0c;这份库参考则介绍了与 Pytho…

网络协议从入门到底层原理学习(一)—— 简介及基本概念

文章目录 网络协议从入门到底层原理学习&#xff08;一&#xff09;—— 简介及基本概念一、简介1、网络协议的定义2、网络协议组成要素3、广泛的网络协议类型网络通信协议网络安全协议网络管理协议 4、网络协议模型对比图 二、基本概念1、网络互连模型2、计算机之间的通信基础…

7.Xaml Image控件

1.运行图片 2.运行源码 a.xaml源码 <!--Source="/th.gif" 图像源--><!--Stretch="Fill" 填充模式--><Image x:Name

OpenCV 04(通道分离与合并 | 绘制图形)

一、通道的分离与合并 - split(mat)分割图像的通道 - merge((ch1,ch2, ch3)) 融合多个通道 import cv2 import numpy as npimg np.zeros((480, 640, 3), np.uint8)b,g,r cv2.split(img)b[10:100, 10:100] 255 g[10:100, 10:100] 255img2 cv2.merge((b, g, r))cv2.imshow…

0401hive入门-hadoop-大数据学习.md

文章目录 1 Hive概述2 Hive部署2.1 规划2.2 安装软件 3 Hive体验4 Hive客户端4.1 HiveServer2 服务4.2 DataGrip 5 问题集5.1 Could not open client transport with JDBC Uri 结语 1 Hive概述 Apache Hive是一个开源的数据仓库查询和分析工具&#xff0c;最初由Facebook开发&…

stm32之31.iic

iic双线制。一根是SCL&#xff0c;作为时钟同步线;一根是SDA&#xff0c;作为数据传输线 SDN #include "iic.h"#define SCL PBout(8)#define SDA_W PBout(9) #define SDA_R PBin(9)void IIC_GPIOInit(void) {GPIO_InitTypeDef GPIO_InitStructure;//使能时钟GR…

vue: 使用下拉树组件@riophae/vue-treeselect

前言: 在vue中, 因为element-ui 2.X是没有tree-select组件的&#xff0c;到了element-plus就有了 riophae/vue-treeselect是一个基于 Vue.js 的树形选择器组件&#xff0c;可以用于选择树形结构的数据。它支持多选、搜索、异步加载等功能&#xff0c;可以自定义选项的样式和模…

php版 短信跳转微信小程序

实现这功能首先&#xff0c;小程序端添加业务域名 php代码 <?php declare (strict_types1);namespace app\controller\Admin;use app\model\Set; use app\Request;class Admin_Url_Scheme {public function getScheme(Request $request) {$appid 小程序appid;$secret 小…