linux-内存映射MMAP-lseek-dup-fifo-通信-IO多路复用

news2024/11/26 14:27:22

1、内存映射MMap:

        DMA:

可以用*/[]取代read和write;

限制:

1、文件大小固定不能改变;(ftruncate)

2、只能是磁盘文件;

3、建立映射之前先open

mmap函数:

mmap第一个参数填空指针,分配映射空间时将自动分配到堆空间;分配区域首地址作为返回值返回,

length大小要固定;

prot表示内存是否可读可写;

prot的可选项:可以用按位或连接

flages:属性(MAP_SHARED(多进程共享映射区));

fd:映射的文件;(文件描述符)

offfset偏移量:0;(直接写0);

然后通过munmap释放;

该函数只有length和fd要改变;

代码实现通过mmap函数再内存中直接通过映射修改文件内容:

#include <43func.h>
int main(int argc, char *argv[]){
    ARGS_CHECK(argc,2);
    int fd = open(argv[1],O_RDWR);
     ERROR_CHECK(fd,-1,"open");
     int ret = ftruncate(fd,5);
     ERROR_CHECK(ret,-1,"ftruncate");
     char *p = (char *)mmap(NULL,5,PROT_READ|PROT_WRITE,MAP_SHARED,fd,0);
    for (int  i = 0; i < 5; i++)
    {
        printf("%c",p[i]);

    }
    printf("\n");
    p[0] = 'H';
    p[1] = '1';
       for (int  i = 0; i < 5; i++)
    {
        printf("%c",p[i]);

    }
    munmap(p,5);
}

2、lseek:也可与诱发文件空洞

  • fd:文件描述符,指向要操作的文件。
  • offset:相对于whence的偏移量,可以是正数也可以是负数。
  • whence:偏移量的起始位置,它可以是以下常量之一:
    • SEEK_SET:文件的开头。
    • SEEK_CUR:当前的读写位置。
    • SEEK_END:文件的末尾。

内核态和用户态各有一个缓冲区,lseek修改内核态,而fseek修改用户态;

3、文件流也使用了文件对象:

int fileno():传入一个文件流指针则返回一个文件描述符;

用户,库作者,接口的关系:

        用户通过接口与系统进行交互,而库作者通过API提供库的功能和服务。接口和API是连接用户和库作者的桥梁。

为了降低耦合性,库作者把库代码进行封装,提供接口给用户;所以用户通过接口访问库;

代码即注释:

用有意义的符号取代固定的数字:


3、文件描述符的复制 dup

数值不同,偏移量共享

dup();选择一个最小可用的fd和oldfd同指向;

查看stdin,stdout,stderr的文件描述符

使用printf本质上往stdout写入数据;

printf对应的文件描述符为1:

往1号文件写入数据相当于往标准输出中写入数据;

遵循代码即注释原则:用STDERR_FILENO代替1

当文件通过close关闭标准输出时,再次用printf就相当于往重定向;

先打开open,还需要重定向文件描述符;可以使用dup();


用dup复制的文件描述符时,新的文件描述符和旧的文件描述符都共享同一个指针,(一个文件描述符写了,另一个接着写);

当关闭oldfd时,还可以继续用newfd进行操作;当文件描述符完全关闭后才会释放文件对象。

这种设计允许进程在需要时复制文件描述符,并在不同的线程或进程间传递它们,而不会导致底层资源的立即释放。(引用计数)

引用计数

是指将资源(如对象、内存或磁盘空间等)的被引用次数保存起来,当被引用次数变为零时,系统将自动释放该资源的过程。


重定向到目标文件:

先打开文件再把标准输出重定向到文件里;

重定向到testFile,当关闭标准输出时printf失效,把printf对应的输出对象改成了testFile;


从目标文件重定向回自定义目标:

int dup2(int oldfd,int newfd);

让newfd与oldfd指向同一个文件对象;

如果newfd已有指向就会自动close;

通过把dup2把标准输出的文件描述符改成savefd,再把标准输出的屏幕对象改成文件对象,最后再改回来,把屏幕定向到文件,再恢复;


4、有名管道(name pip / FIFO):先进先出;

进程间通信机制在文件系统的映射;

通信的传输方式:

单工:A->B

半双工:A->B    ,  B->A  不同时 (管道至少是半双工通信)

全双工:A<-------->B

mkfifo :创建管道

.

mkfifo  1.pip

管道不能存数据,只能暂存,不能持续存储;不能用vim打开


管道的半双工通信:用两个终端展示(右边取出数据,左边取消阻塞,把左边进程的数据传输到右边进程)

先读取数据,没有数据会进程阻塞,先传输,没有读也会阻塞;


用系统调用操作管道:

半双工通信管道

open:O_WRONLY(写端)

        O_RDONLY(读端)

(用open打开写端或读端);

管道实在open的时候阻塞的。当一个进程open管道一端的时候,进程处于阻塞状态,如果对端未被打开,进程处于阻塞状态,直到对端被另一个进程打开;(半双工通信)


全双工通信:(使用两个管道实现)
死锁的产生:

错误示范:

chat1 打开1pipe的读在等待chat2 在1pipe的写;

chat2 打开2pipe的写在等待chat2 在2pipe的读;

进入循环等待状态,产生死锁;占用资源的顺序出现了问题(调整顺序解决);

全双工通信:

        

通过死循环实现一直通信;

该程序只能实现一问一答:要等回复后才能看到下一条问题;

死循环读管道,读stdin,(目前代码给了固定的相应的读取顺序)

当B一直发,B的标准输入会堆积数据,但是A没有回复数据;

read fdr 和read stdin 存在先后顺序;(两个read的动作都会阻塞)

后面的数据就绪,但前面的程序阻塞了;数据串联(一个阻塞全部阻塞);

程序采用了一个阻塞式的读取循环,每次从管道读取数据并打印,然后清空缓冲区,接着从标准输入(STDIN_FILENO)读取数据并写入管道。问题在于,当从标准输入读取数据时,程序会阻塞直到有数据可读。这意味着,如果另一进程已经发送了第二条消息到管道中,但是当前进程没有从标准输入读取任何数据,那么它就不会处理管道中的第二条消息。

IO多路复用:(现代服务器的基础)

采用数据并联解决;


select:

fd_set : 监听集合;   

#include <sys/select.h>  
#include <sys/time.h>  
  
int select(int nfds, fd_set *readfds, fd_set *writefds,  
           fd_set *exceptfds, struct timeval *timeout);
  • nfds:这是一个整数值,指定了被监听的文件描述符集合中最大文件描述符值加 1。通常,它会被设置为集合中最大文件描述符的加一。
  • readfds:指向一个文件描述符集合的指针,该集合中的文件描述符被监视以检查是否可读。
  • writefds:指向一个文件描述符集合的指针,该集合中的文件描述符被监视以检查是否可写。
  • exceptfds:指向一个文件描述符集合的指针,该集合中的文件描述符被监视以检查是否有异常条件待处理。
  • timeout:指向一个 timeval 结构的指针,该结构指定了 select 的超时时间。如果设置为 NULL,则 select 会无限期地等待,直到某个文件描述符就绪。

fd_set 类型是一个位掩码,用于存储多个文件描述符的状态。在调用 select 之前,程序会使用如 FD_ZEROFD_SETFD_CLR 和 FD_ISSET 等宏来操作这些集合。

(1)创建监听集合

(2)设置合适的监听:FD_ZERO(清空)    FD_SET(加入监听){把会阻塞的文件描述符加入到监听}

(3)调用select函数,会让进程阻塞;

(4)当监听的文件描述符fd中有任何一个就绪时则select就绪;

(5)轮流询问(轮询)所有监听的fd是否就绪,FD_ISSET(询问)

使用IO多路复用实现进程之间聊天;

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

GAN论文阅读笔记(10)—— High-fidelity GAN Inversion with Padding Space

论文&#xff1a;High-fidelity GAN Inversion with Padding Space paper&#xff1a;136750036.pdf (ecva.net) code&#xff1a;EzioBy/padinv: [ECCV 2022] PadInv: High-fidelity GAN Inversion with Padding Space (github.com) 关键词&#xff1a;GAN, GAN 反演 ( GAN I…

MobPush HarmonyOS NEXT 版本集成指南

开发工具&#xff1a;DevEco Studio 集成方式&#xff1a;在线集成 HarmonyOS API支持&#xff1a;> 11 集成前准备 注册账号 使用MobSDK之前&#xff0c;需要先在MobTech官网注册开发者账号&#xff0c;并获取MobTech提供的AppKey和AppSecret&#xff0c;详情可以点击查…

React实战学习(一)_棋盘设计

需求&#xff1a; 左上侧&#xff1a;状态左下侧&#xff1a;棋盘&#xff0c;保证胜利就结束 和 下过来的不能在下右侧&#xff1a;“时光机”,保证可以回顾&#xff0c;索引 语法&#xff1a; 父子之间属性传递&#xff08;props&#xff09;子父组件传递&#xff08;写法上&…

第十三章 常用类

一、包装类 1. 包装类的分类 &#xff08;1&#xff09;针对八种基本数据类型相应的引用类型—包装类 &#xff08;2&#xff09;有了类的特点&#xff0c;就可以调用类中的方法。 2. 包装类和基本数据的转换 jdk5 前的手动装箱和拆箱方式&#xff0c;装箱&#xff1a;基本…

使用SpringBoot整合filter

SpringBoot整合filter&#xff0c;和整合servlet类似&#xff0c;也有两种玩儿法 1、创建一个SpringBoot工程&#xff0c;在工程中创建一个filter过滤器&#xff0c;然后用注解WebFilter配置拦截的映射 2、启动类还是使用ServletComponentScan注解来扫描拦截器注解WebFilter 另…

通过百度文心智能体创建STM32编程助手-实操

一、前言 文心智能体平台AgentBuilder 是百度推出的基于文心大模型的智能体&#xff08;Agent&#xff09;平台&#xff0c;支持广大开发者根据自身行业领域、应用场景&#xff0c;选取不同类型的开发方式&#xff0c;打造大模型时代的产品能力。开发者可以通过 prompt 编排的…

主从复制、哨兵以及Cluster集群

目录 1.Redis高可用 2.Redis主从复制 2.1 主从复制的作用 2.2 主从复制流程 2.3 搭建Redis主从复制 2.3.1 修改Redis配置文件&#xff08;Master节点操作&#xff09; 2.3.2 修改Redis配置文件&#xff08;Slave节点操作&#xff09; 2.3.2 验证主从复制结果 3.Redis哨…

Oracle新特性速递:未来数据库技术的无限可能

文章目录 一、自治数据库&#xff1a;智能化与自动化的革命二、机器学习集成&#xff1a;智能数据分析的新境界三、区块链技术&#xff1a;确保数据完整性与透明性四、云原生数据库&#xff1a;灵活扩展与快速部署五、人工智能优化器&#xff1a;智能查询执行计划《Oracle从入门…

Pow(x,n)快速冥算法

快速幂算法 快速幂算法是一种通过分治和递归的方式来计算幂运算的方法&#xff0c;其核心思想是利用分治和递归减少乘法的次数来显著提高效率。 基本原理&#xff1a; 给定 x 和 n&#xff0c;计算 x^n 的过程如下&#xff1a; 基本情况处理&#xff1a;如果指数 n 是 0&…

【STM32修改串口波特率】

STM32微控制器中的串口波特率调整通常涉及到USART&#xff08;通用同步接收器/发送器&#xff09;模块的配置。USART模块提供了多个寄存器来设置波特率&#xff0c;其中关键的寄存器包括BRR&#xff08;波特率寄存器&#xff09;和USART_CR1&#xff08;控制寄存器1&#xff09…

【嵌入式操作系统(Linux篇)】实验期末复习(1)

以下是关于嵌入式操作系统&#xff08;Linux篇&#xff09;的实验汇总&#xff0c;大概率都是会考的 特别是shell程序和文件IO的操作 嵌入式操作系统实验小结—涉及期末大题 &#xff08;一&#xff09;Linux操作系统的使用实验 1、认识Linux操作系统的目录结构 请进入自己…

【C++课程设计——演讲比赛系统】

文章目录 前言一、演讲比赛程序需求二、每个功能模块的实现1. 创建管理类(.h文件)2.1. 创建管理类(.cpp文件)3.创建参赛选手类(.h)4.将整体逻辑进行封装 测试项目总结 前言 在学习完C的stl容器后&#xff0c;我们来写一下小项目对其进行应用&#xff01; 项目名称为&#xff1…

cocos creator 调试插件

适用 Cocos Creator 3.4 版本&#xff0c;cocos creator 使用google浏览器调试时&#xff0c;我们可以把事实运行的节点以节点树的形式显示在浏览器上&#xff0c;支持运行时动态调整位置等、、、 将下载的preview-template插件解压后放在工程根目录下&#xff0c;然后重新运行…

day23-- 39. 组合总和+40.组合总和II + 131.分割回文串

一、 39. 组合总和 题目链接&#xff1a;https://leetcode.cn/problems/combination-sum/ 文章讲解&#xff1a;https://programmercarl.com/0039.%E7%BB%84%E5%90%88%E6%80%BB%E5%92%8C.html 视频讲解&#xff1a;https://www.bilibili.com/video/BV1KT4y1M7HJ 1.1 初见思路…

JAVA期末速成库(10)第十一章

一、习题介绍 Check Point&#xff1a;P416 11.1&#xff0c;11.6&#xff0c;11.7&#xff0c;11.8&#xff0c;11.12&#xff0c;11.17&#xff0c;11.24 Programming Exercise&#xff1a;11.1 二、习题及答案 Check Point&#xff1a; 11.1 True or false? A subcl…

Windows下activemq集群配置(broker-network)

1.activemq版本信息 activemq&#xff1a;apache-activemq-5.18.4 2.activemq架构 3.activemq集群配置 activemq集群配置基于Networks of Brokers 这种HA方案的优点&#xff1a;是占用的节点数更少(只需要2个节点),而且2个broker都可以响应消息的接收与发送。不足&#xff…

003-GeoGebra如何无缝嵌入到PPT里

GeoGebra无缝嵌入到PPT里真是一个头疼的问题&#xff0c;已成功解决&#xff0c;这里记录一下&#xff0c;希望可以帮助到更多人。 注意&#xff0c;后续所有的文章说的PPT都是Offce Power Point, 不要拿着WPS的bug来问我哦&#xff0c;我已经戒WPS了&#xff08;此处表示无奈&…

基于Spring Boot的校园失物招领系统

1 项目介绍 1.1 研究的背景及意义 在网络时代飞速发展的今天&#xff0c;随着网络技术日臻完善&#xff0c;我们的生活方式正经历深刻变革。在物质追求日益增长的同时&#xff0c;提升个人精神境界也成为了现代人的共同向往&#xff0c;而阅读则是滋养心灵、丰富精神世界的重…

Ubuntu Server 和 Ubuntu Desktop 组合使用

1.常见的组合使用方式 Ubuntu Server 和 Ubuntu Desktop 确实可以组合使用&#xff0c;但具体要看你的需求和使用场景。以下是一些常见的组合使用方式&#xff1a; 单一设备上安装&#xff1a;你可以在一台设备上同时安装 Ubuntu Server 和 Ubuntu Desktop。这样&#xff0c;你…

【SQL Server数据库】视图的使用

一、用SQL语句完成下列功能。 1&#xff0e;建立一视图View_CSTeacher&#xff0c;列出计算机系各个老师的资料(姓名、性别、职称)。 create view View_CSTeacher asselect Teac_name, Teac_sex, TechPostfrom Teacherwhere Depar_id in (select Depar_id from Deparment whe…