【Linux:IO多路复用(select、poll函数)

目录

什么是IO多路复用?

select:

参数介绍:

 select函数返回值:

fd_set类型:

内核如何更新集合中的标志位 

处理并发问题

处理流程的步骤: 

 poll:

 poll的函数原型:

参数介绍:

select与poll的区别:


什么是IO多路复用?

一种网络通信的手段,IO多路复用可以同时监测多个文件描述符,且这个过程是阻塞的,当检测有文件描述符就绪,程序的阻塞就会解除,就可以通过这些就绪的文件描述符进行通信。通过这种方式在单线程/进程的场景下也可以在服务器端实现并发。常见的IO多路转接方式有:select、poll、epoll。

select:

该函数是跨平台的,检测文件描述符的读写状态

 这三个指针是指向三个文件描述符集合的指针。

参数介绍:

  • nfds:是在这三个文件描述符集合中找出一个最大的文件描述符再+1
    • 内核中需要线性遍历这些集合中的文件描述符,该值是循环结束的条件
    • 该参数在windows中无效,指定为-1即可
  • readfds:读集合一般都是需要进行检测的,这样才能知道哪些文件描述符可以接收数据
  • writefds:内核只检测这个集合中的文件描述符对应的写缓冲区,如果不使用该参数可以用NULL指定
  • exceptfds:内核只检测这个集合中的文件描述符是否有异常状态,如果不使用该参数可以用NULL指定
  • timeout:是表示检测文件描述符的时间,超过该时间函数返回。超长时长,用来解除select函数的阻塞
    • 等待固定时长:如果函数检测不到就绪的文件描述符,在指定时长过后就会解除堵塞
    • 如果设定为NULL:检测不到就绪的文件描述符就会一直阻塞
    • 不等待时长:检测不到就绪的文件描述符就会直接返回,不会阻塞

 select函数返回值:

  • >0:返回集合中就绪的文件描述符的个数
  • =0:超时,没有检测到就绪的文件描述符
  • <1:函数调用失败

fd_set类型:

fd_set类型的数据拥有1024个字节,也就是128个比特位,这个可以把他想象成一个整型的数组,大小为32。 fd_set中存储了要委托内核检测读缓冲区的文件描述符集合。

  • 如果集合中的标志位为0表示不检测这个文件描述符状态
  • 如果集合中的标志位为1表示检测这个文件描述符状态

内核如何更新集合中的标志位 

  

  • 假设需要检测读集合是否有文件描述符触发
  • 传入内核中的集合在此之前做初始化之后再传入
  • 内存中的数据拷贝到内核中
  • 内核检测拷贝的数据,检测完后,把满足条件的文件描述符重新写入到该内存中(可以理解为内核需要更新fd_set中的数据)

  • 把文件描述符中fd3,fd5,fd6,fd8,fd9,fd10,fd11设置到fd_set文件描述符集合中
  • 再通过select函数将文件描述符集合传递给内核
  • 内核把传入的集合拷贝一份(数据拷贝的过程)
  • 内核基于拷贝出来的集合做线性检测
  • 内核通过拷贝的集合与文件描述符表做对比
  • 文件描述符表的每个文件描述符具有两个缓冲区:读和写的缓冲区
  • 检测读缓冲区是否有数据
  • 内核基于拷贝的该线性表把需要检测的文件描述符的读缓冲区检验一遍
  • 把满足条件的文件描述符再重新写入指定的内存中

写集合也是一样的道理

以上函数能够实现把文件描述符存储到fd_set这个集合中/把已经存储的文件描述符从集合中删除等对该表的一系列增删查改 

处理并发问题

处理流程的步骤: 

  1. 创建套接字
  2. 绑定本地IP端口
  3. 建立监听
  4. 对需要检测的文件描述符做初始化(前三步完成后拥有一个监听的文件描述符)
    1. 监听的文件描述符用于检测是否有客户端连接
    2. 若客户端有连接请求,文件描述符会把发送进来存储到用于监听的文件描述符的读缓冲区中
  5. 创建一个fd_set的读集合并初始化(把标记为初始化为0)
  6. 再通过fd_set把监听的文件描述符对应的标志位设置为1
  7. 调用select进行检测
    1. select调用一次只检测一次
    2. 需要多次检测需要写入到循环中
    3. 返回值为-1或者0,即可做异常处理
      1. >0:文件描述符如果是监听的描述符,大于0表示有新的客户端连接到达
        1. 调用accept与客户端建立连接(不会阻塞,内核已检测完并知道文件描述符中是有数据的)得到通信的文件描述符
        2. 把得到的文件描述符放入读集合中,如果不进行下一轮的检测,服务端则不知道客户端有新的数据到达
  8. 检测到通信的文件描述符,调用recv接收数据
    1. 返回值:
      1. <0:客户端断开连接,调用close关闭通信的套接字,紧接着调用fd_clr函数删除
      2. >0:接收到数据,调用send函数发送数据

 poll:

 poll的函数原型:

参数介绍:

  • fds:struct pollfd类型的数组,里边存储了待检测的文件描述符的信息
  • nfds:第一个参数数组中最后一个有效元素的下标+1
  • timeout:指定poll函数的阻塞时长
    • -1:一直阻塞,直到检测的集合有就绪的文件描述符,解除阻塞
    • 0:不阻塞,不论检测集合是否有就绪的文件描述符,函数立刻返回

select与poll的区别:

  • select一次检测需要两次拷贝,效率低
  • 内核对select函数传递的待测集合的检测方式为线性(效率高低取决于检测的文件描述符的个数)
  • select检测的最大文件描述符个数有上限 
  • selec可以跨平台,poll不能开平台。

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

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

相关文章

容器内的Jenkins使用docker部署服务,服务数据文件挂载问题

问题 docker 容器运行服务更推荐是那种无状态的服务&#xff0c;这样可以做到 “ 开箱即用 ”&#xff0c;需要持久化存储的话使用存储卷挂载数据库文件即可&#xff0c;这都是基于在宿主机上执行的&#xff1b; 现在Jenkins是在docker容器中运行&#xff0c;并需要使用docker部…

六、volatile

volatile 能保证内存可⻅性 运行下面的例子&#xff1a; package Demo03;import java.util.Scanner;public class demo01 {private static int flag 0;public static void main(String[] args) {Thread t1 new Thread(() -> {while (flag 0) {}System.out.println(&quo…

LSTM(长短期记忆网络)详解

1️⃣ LSTM介绍 标准的RNN存在梯度消失和梯度爆炸问题&#xff0c;无法捕捉长期依赖关系。那么如何理解这个长期依赖关系呢&#xff1f; 例如&#xff0c;有一个语言模型基于先前的词来预测下一个词&#xff0c;我们有一句话 “the clouds are in the sky”&#xff0c;基于&…

Servlet⽣生命周期超级细(笔记)

简介: 讲解Servlet的⽣生命周期 Servlet 接⼝口⾥里里⾯面有5个⽅方法&#xff0c;其中三个⽣生命周期⽅方法和两个普通⽅方法 1. 加载和初始化阶段 过程&#xff1a; 当一个 Servlet 第一次被客户端请求时或者服务器启动时&#xff0c;Servlet 容器会加载该 Servlet 类&…

HBuilder(uniapp) 配置android模拟器

HBuilder&#xff08;uniapp&#xff09; 配置android模拟器 选择完成之后&#xff0c;点击ok&#xff0c;再次点击Configure—》AVD Manager

基于麒麟服务器操作系统V10版本,部署Nginx服务、MySql服务搭建PHP环境,实现静态网站平台的搭建。

一、环境准备 关闭防火墙。 查看当前防火墙的状态 systemctl status firewalld Copy 如果防火墙的状态参数是inactive,则防火墙为关闭状态。 如果防火墙的状态参数是active,则防火墙为开启状态。 关闭防火墙。 如果您想临时关闭防火墙,需要运行以下命令: systemctl…

用OMS进行 OceanBase 租户间数据迁移的测评

基本概念 OceanBase迁移服务&#xff08;&#xff0c;简称OMS&#xff09;&#xff0c;可以让用户在同构或异构 RDBMS 与OceanBase 数据库之间进行数据交互&#xff0c;支持数据的在线迁移&#xff0c;以及实时增量同步的复制功能。 OMS 提供了可视化的集中管控平台&#xff…

Hadoop生态圈框架部署(六)- HBase完全分布式部署

文章目录 前言一、Hbase完全分布式部署&#xff08;手动部署&#xff09;1. 下载Hbase2. 上传安装包3. 解压HBase安装包4. 配置HBase配置文件4.1 修改hbase-env.sh配置文件4.2 修改hbase-site.xml配置文件4.3 修改regionservers配置文件4.4 删除hbase中slf4j-reload4j-1.7.33.j…

108. UE5 GAS RPG 实现地图名称更新和加载关卡

在这一篇里&#xff0c;我们将实现对存档的删除功能&#xff0c;在删除时会有弹框确认。接着实现获取玩家的等级和地图名称和存档位置&#xff0c;我们可以通过存档进入游戏&#xff0c;玩家在游戏中可以在存档点存储存档。 实现删除存档 删除存档需要一个弹框确认&#xff0…

移除元素(leetcode 27)

给定一个数组&#xff0c;在数组中删除等于这个目标值的元素&#xff0c;然后返回新数组的大小 数组理论&#xff1a; 数组是一个连续的类型相近的元素的一个集合&#xff0c;数组上的删除是覆盖&#xff0c;只能由后面的元素进行覆盖&#xff0c;而不能进行真正意义上的地理位…

【征稿倒计时!华南理工大学主办 | IEEE出版 | EI检索稳定】2024智能机器人与自动控制国际学术会议 (IRAC 2024)

#华南理工大学主办&#xff01;#IEEE出版&#xff01;EI稳定检索&#xff01;#组委阵容强大&#xff01;IEEE Fellow、国家杰青等学术大咖领衔出席&#xff01;#会议设置“优秀论文”“优秀青年学者报告”“优秀海报”等评优奖项 2024智能机器人与自动控制国际学术会议 &#…

【React】状态管理之Zustand

&#x1f308;个人主页: 鑫宝Code &#x1f525;热门专栏: 闲话杂谈&#xff5c; 炫酷HTML | JavaScript基础 ​&#x1f4ab;个人格言: "如无必要&#xff0c;勿增实体" 文章目录 状态管理之Zustand引言1. Zustand 的核心特点1.1 简单直观的 API1.2 无需 Provi…

【ict基础软件赛道】真题-50%openGauss

题目取自赛前测试链接 OpenGauss安装前使用哪个工具检查环境是否符合安装哪个功能不是gs_guc工具提供的opengauss数据库逻辑复制的特点描述正确的是opengauss的全密态数据库等值查询能力描述正确的是哪个不属于ssh客户端工具opengauss三权分立说法正确的是opengauss wdr snapsh…

Python酷库之旅-第三方库Pandas(218)

目录 一、用法精讲 1021、pandas.DatetimeIndex.inferred_freq属性 1021-1、语法 1021-2、参数 1021-3、功能 1021-4、返回值 1021-5、说明 1021-6、用法 1021-6-1、数据准备 1021-6-2、代码示例 1021-6-3、结果输出 1022、pandas.DatetimeIndex.indexer_at_time方…

【miniMax开放平台-注册安全分析报告-无验证方式导致安全隐患】

前言 由于网站注册入口容易被机器执行自动化程序攻击&#xff0c;存在如下风险&#xff1a; 暴力破解密码&#xff0c;造成用户信息泄露&#xff0c;不符合国家等级保护的要求。短信盗刷带来的拒绝服务风险 &#xff0c;造成用户无法登陆、注册&#xff0c;大量收到垃圾短信的…

树状数组+概率论,ABC380G - Another Shuffle Window

目录 一、题目 1、题目描述 2、输入输出 2.1输入 2.2输出 3、原题链接 二、解题报告 1、思路分析 2、复杂度 3、代码详解 一、题目 1、题目描述 2、输入输出 2.1输入 2.2输出 3、原题链接 G - Another Shuffle Window 二、解题报告 1、思路分析 不难用树状数组计…

MySQL:表设计

表的设计 从需求中获得类&#xff0c;类对应到数据库中的实体&#xff0c;实体在数据库中表现为一张一张的表&#xff0c;类中的属性就对应着表中的字段&#xff08;也就是表中的列&#xff09; 表设计的三大范式&#xff1a; 在数据库设计中&#xff0c;三大范式&#xff0…

网盘聚合搜索项目Aipan(爱盼)

本文软件由网友 刘源 推荐&#xff1b; 简介 什么是 Aipan&#xff08;爱盼&#xff09; ? Aipan&#xff08;爱盼&#xff09;是一个基于 Vue 和 Nuxt.js 技术构建的开源网盘搜索项目。其主要目标是为用户提供一个能够自主拥有和管理的网盘搜索网站。该项目持续维护和更新&a…

当微软windows的记事本被AI加持

1985年&#xff0c;微软发布了Windows 1.0&#xff0c;推出了一款革命性的产品&#xff1a;记事本&#xff08;Notepad&#xff09;。这款软件旨在鼓励使用一种未来主义的新设备——鼠标&#xff0c;并让人们可以不依赖VI等键盘工具就能书写文本和编写代码。记事本因其简洁和高…

Dubbo 3.x源码(25)—Dubbo服务引用源码(8)notify订阅服务通知更新

基于Dubbo 3.1&#xff0c;详细介绍了Dubbo服务的发布与引用的源码。 此前我们学习了接口级的服务引入订阅的refreshInterfaceInvoker方法&#xff0c;当时还有最为关键的notify服务通知更新的部分源码没有学习&#xff0c;本次我们来学习notify通知本地服务更新的源码。 Dubb…