五、网络编程之网络 IO 模型的本质.md

2023-11-17

IO 网络模型的本质

前置概念

(1)用户空间和内核空间

学习 Linux 或者 IO 网络模型时,经常可以看到两个词:User space(用户空间)和 Kernel space(内核空间)。

简单说,Kernel space 是 Linux 内核的运行空间,User space 是用户程序的运行空间。具体来说,虚拟内存被操作系统划分成两块:内核空间和用户空间,内核空间是内核代码运行的地方用户空间是用户程序代码运行的地方。当进程运行在内核空间时就处于内核态,当进程运行在用户空间时就处于用户态。

为了安全,它们是隔离的,即使用户的程序崩溃了,内核也不受影响。Kernel space 可以执行任意命令,调用系统的一切资源;User space 只能执行简单的运算,不能直接调用系统资源,必须通过调用系统接口(又称 system call),才能向内核发出指令。

(2)进程切换

为了控制进程的执行,内核必须有能力挂起正在 CPU 上运行的进程,并恢复以前挂起的某个进程的执行。这种行为被称为进程切换。因此可以说,任何进程都是在操作系统内核的支持下运行的,是与内核紧密相关的。

(3)进程的阻塞

正在执行的进程,由于期待的某些事件未发生,如请求系统资源失败、等待某种操作的完成、新数据尚未到达或无新工作做等,则由系统自动执行阻塞原语(Block),使该进程由运行状态变为阻塞状态

可见,进程的阻塞是进程自身的一种主动行为,也因此只有处于运行态的进程(获得 CPU),才可能将其转为阻塞状态。当进程进入阻塞状态的进程是不占用 CPU 资源的

(4)文件描述符

Linux 系统中,把一切都看做是文件,当进程打开现有文件或创建新文件时,内核向进程返回一个文件描述符,文件描述符就是内核为了高效管理已被打开的文件所创建的索引,用来指向被打开的文件,所有执行I/O操作的系统调用都会通过文件描述符。文件描述符在形式上是一个非负整数

(5)内存与缓冲区

缓冲区是内存空间的一部分,也就是说,在内存空间中预留了一定的存储空间,这些存储空间用来缓冲输入或输出的数据,这部分预留的空间就叫做缓冲区。缓冲区根据其对应的是输入设备还是输出设备,分为输入缓冲区和输出缓冲区。

**为什么要引入缓冲区?**比如我们从磁盘里取信息,我们先把读出的数据放在缓冲区,计算机再直接从缓冲区中取数据,等缓冲区的数据取完后再去磁盘中读取,这样就可以减少磁盘的读写次数,再加上计算机对缓冲区的操作速度远高于对磁盘的操作速度,故应用缓冲区可大大提高计算机的运行速度。

网络 IO 本质

什么是 IO?

I/O 其实就是 input 和 output 的缩写,即输入/输出。那输入输出啥呢?比如我们用键盘来敲代码其实就是输入,那显示器显示图案就是输出,这其实就是 I/O。

大多数文件系统的默认 IO 操作都是缓存 IO,又被称作标准I/O。其读写过程如下:

  • 读操作:操作系统检查内核的缓冲区有没有需要的数据,如果已经缓存了,那么就直接从缓存中返回;否则从磁盘、网卡等中读取,然后缓存在操作系统的缓存中;
  • 写操作:将数据从用户空间复制到内核空间的缓存中。这时对用户程序来说写操作就已经完成,至于什么时候再写到磁盘、网卡等中由操作系统决定,除非显示地调用了 sync 同步命令。

假设内核空间缓存无需要的数据,用户进程从磁盘或网络读数据分两个阶段:

  • 阶段一: 内核程序从磁盘、网卡等读取数据到内核空间缓存区(内存);
  • 阶段二: 用户程序从内核空间缓存(内存)拷贝数据到用户空间。

缓存 IO 的缺点:数据在传输过程中需要在应用程序地址空间和内核空间进行多次数据拷贝操作,这些数据拷贝操作所带来的CPU以及内存开销非常大。

什么是网络 IO?

IO 有内存 IO、网络 IO和磁盘 IO(又称磁盘 I/O)三种,通常我们说的 IO 指的是后两者:

  • 磁盘 I/O 指的是硬盘和内存之间的输入输出:读取本地文件的时候,要将磁盘的数据拷贝到内存中,修改本地文件的时候,需要把修改后的数据拷贝到磁盘中。

    在这里插入图片描述

  • 网络 I/O 指的是网卡与内存之间的输入输出:当网络上的数据到来时,网卡需要将数据拷贝到内存中。当要发送数据给网络上的其他人时,需要将数据从内存拷贝到网卡里。

    在这里插入图片描述

那为什么都要跟内存交互呢?,因此都是和内存交互。当然假设没有内存,让 CPU 直接和外部设备交互,那也算 I/O,只是交互速度会慢很多。

总结下:I/O 就是指内存与外部设备之间的交互(数据拷贝),网络 IO 就是指内存与网卡之间的交互

什么是网络 IO 模型?

(1)阻塞与非阻塞

阻塞与非阻塞,用于描述调用者在等待返回结果时的状态

  • 阻塞:调用者发起请求后,会一直等待返回结果,这期间当前线程会被挂起(阻塞)。
  • 非阻塞:调用者发起请求后,会立刻返回,当前线程也不会阻塞。该调用不会立刻得到结果,调用者需要定时轮询查看处理状态。

(2)同步与异步

同步与异步,用于描述调用结果的返回机制(或者叫通信机制)。

  • 同步:调用者发起请求后,会一直等待返回结果,即由调用者主动等待这个调用结果。
  • 异步:调用者发起请求后,会立刻返回,但不会立刻得到这个结果,而是由被调者在执行结束后主动通知(如 Callback)调用者。

(3)网络 IO 模型

网络 IO 模型:用什么样的通道或者说是通信模式进行数据的传输,这很大程序上决定了程序通信的性能。

网络 IO 会涉及到两个系统对象,一个是用户空间调用 IO 的进程或者线程,另一个是内核空间:

  • 第一阶段:等待数据。即应用进程发起 IO 系统调用后,会一直等待数据;当有数据传入服务器,会将数据放入内核空间,此时数据准备好。
  • 第二阶段:将数据从内核空间复制到用户空间,并返回给应用程序成功标识。

因为在以上两个阶段上各有不同的情况,所以出现了多种网络 IO 模型。Linux 系统为我们提供五种可用的 IO 模型:

其中同步阻塞 IO、同步非阻塞 IO、多路复用 IO、信号驱动 IO 模型的第二阶段是相同的,都是处于阻塞状态,所以这四种 IO 都属于同步IO,它们主要区别在第一阶段。而异步 IO 模型则不同,应用进程在这两个阶段是完全不阻塞的。

IO 模型 第一阶段 第二阶段
阻塞式IO 阻塞 阻塞
非阻塞式IO 非阻塞 阻塞
IO多路程复用 阻塞(Select、Poll、Epoll) 阻塞
信号驱动式IO 异步 阻塞
异步IO 异步 异步
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

五、网络编程之网络 IO 模型的本质.md 的相关文章

  • 为什么默认情况下不启用 arp 忽略/通告 [关闭]

    Closed 这个问题是无关 help closed questions 目前不接受答案 我有一个需要经验才能回答的具体问题 为什么 arp ignore arp announce 在 Linux 安装 例如 debian 上默认不启用 有
  • 运行 shell 命令并将输出发送到文件?

    我需要能够通过 php 脚本修改我的 openvpn 身份验证文件 我已将我的 http 用户设置为免通 sudoer 因为这台机器仅在我的家庭网络中可用 我目前有以下命令 echo shell exec sudo echo usernam
  • 如何使用 go1.6.2 构建 linux 32 位

    有没有任何组合GOARCH and GOOS我可以设置哪些值来构建 ELF 32 位二进制文 件 GOOS linux and GOARCH 386 更多示例 架构 32 bit gt GOARCH 386 64 bit gt GOARCH
  • 在用户程序中使用 或在驱动程序模块代码中使用 ...这有关系吗?

    我正在开发一个设备驱动程序模块和关联的用户库来处理ioctl 来电 该库获取相关信息并将其放入一个结构中 该结构被传递到驱动程序模块中并在那里解压 然后进行处理 我省略了很多步骤 但这就是总体思路 一些数据通过结构体传递ioctl is u
  • 如何从程序内部获取指向程序的特定可执行文件部分的指针? (也许是诽谤)

    我在 Linux 环境中 需要编写一个程序来检索放置在其可执行文件的某个部分中的一些数据 那么 如何从程序内部获取指向程序某个部分 通过其名称 的指针呢 我知道可以使用elf getdata 将节的索引作为参数传递给 get 和Elf Da
  • 如何指定配置脚本的包含目录

    我的工作场所有一个 Linux 系统 其中包含相当旧的软件包 并且没有 root 访问权限 我正在从源代码编译我需要的包 prefix somewhere in homedir 我的问题是我只是不知道如何说服配置在特定目录中查找头文件 源码
  • 如何使用 VSCode 调试 Linux 核心转储?

    我故意从我使用 VSCode 编写的 C 应用程序生成核心转储 我不知道如何调试核心转储 有没有人愿意分享这方面的经验 更新 我相信我现在已经可以使用了 我为核心文件创建了第二个调试配置 我需要添加指向生成的转储文件的 coreDumpPa
  • 打印本周星期一的日期(在 bash 中)

    我想获取本周星期一的 YYYYMMdd 格式的日期 例如 今天是 20110627 从明天到周日 我仍然想打印周一 今天 的日期 然后下周重复这个过程 monday date dmonday Y m d last monday date d
  • 为什么无论 -rdynamic 如何,backtrace 都不包含 Objective-C 符号?

    Update 我正在 Linux 上使用 GNU 运行时 问题是not发生在带有 Apple 运行时的 MacOS 上 更新2 我在 MacOS 上编译了 GNU 运行时并用它构建了示例 该错误确实not发生在带有 GNU 运行时的 Mac
  • 在 vimrc 中切换匹配

    我的 vimrc 文件中有以下几行 hi ExtraWhitespace cterm NONE ctermbg green ctermfg green guibg green guifg green match ExtraWhitespac
  • 当在 python linux 中执行命令 os.system() 时,在 python 中给出响应 yes/no

    考虑一个像这样的命令 yum install boto 当我在终端中执行时 要继续 会询问我是 否 我可以像这样用 python 回应它吗 os system yum install boto Next Yes 将通过相同的 python
  • C++ Linux GCC 应用程序中的 GUID

    我有很多服务器运行这个 Linux 应用程序 我希望他们能够生成一个碰撞概率较低的 GUID 我确信我可以从 dev urandom 中提取 128 个字节 这可能没问题 但是有没有一种简单易用的方法来生成与 Win32 更等效的 GUID
  • 在 Linux 服务器上创建和编辑 MS-Word 文档?

    希望开发处理文档的服务器端应用程序 源文档大多是MS Word 2003 2007 即MS版本的Docx 希望服务器应用程序能够在linux或windows上运行 想知道在linux下读写MS Word文件最好的工具或库是什么 兼容性是最重
  • 在 Windows / Linux 中创建 Mac 包

    我自己努力制作一个 r 包 我按照 stackoverflow 中上一个问题的说明进行操作如何为外行开发软件包 http cran r project org bin windows Rtools 以下是我根据上一个问题采取的步骤 在新的
  • PHP mail() 函数不发送邮件

    我有一个小问题 我正在使用一个工作脚本 在我的测试帐户 共享服务器上工作 使用 mail 函数通过 PHP 发送邮件 我刚刚得到了一个专用服务器 但我还无法让该功能发挥作用 在过去的 10 个小时左右的时间里 我阅读了有关 BIND 用于
  • sudo pip install python-Levenshtein 失败,错误代码 1

    我正在尝试在 Linux 上安装 python Levenshtein 库 但每当我尝试通过以下方式安装它时 sudo pip install python Levenshtein 我收到此错误 命令 usr bin python c 导入
  • tar.gz 和 tgz 是同一个东西吗? [关闭]

    Closed 这个问题不符合堆栈溢出指南 help closed questions 目前不接受答案 我创建了 tgz 文件tar czvf filecommand then 我最终得到了一个 tgz 文件 我想知道它和tar gz 之间的
  • PHP 日志文件颜色

    我正在编写一个 PHP 日志文件类 但我想为写入文件的行添加颜色 我遇到的问题是颜色也会改变终端的颜色 我想要实现的是仅更改写入日志文件的行的颜色 class logClass extends Singleton private funct
  • 使用 hcitool 扫描低功耗蓝牙?

    当我运行此命令时 BLE 设备扫描仅持续 5 秒 sudo timeout 5s hcitool i hci0 lescan 输出显示在终端屏幕中 但是 当我将输出重定向到文件以保存广告设备的地址时 每次运行该命令时 我都会发现该文件是空的
  • php56 - CentOS - Remi 仓库

    我刚刚在测试盒上安装了 php 5 6 正常的 cli php 解释器似乎不存在 gt php v bash php command not found gt php56 v PHP 5 6 13 cli built Sep 3 2015

随机推荐

  • [从零开始学DeepFaceLab-15]: 使用-命令行八大操作步骤-第6步:模型的选择与训练 - 进阶 - 打开Windows的GPU加速开关

    目录 前言 第1章 来自DeepFaceLab模型训练的提醒 第2章 打开该开关的意义
  • 2017校招 360 笔试题 编程题 内存管理

    内存管理 时间限制 C C 语言 1000MS 其他语言 3000MS 内存限制 C C 语言 65536KB 其他语言 589824KB 题目描述 物联网技术的蓬勃发展 各种传感器纷纷出现 小B所在的项目组正在开发一个物联网项目 她们在研
  • 基线检查工具_高效液相色谱法35问35答,鬼峰、基线漂移、拖尾、分叉峰等系列问题一步到位!(上篇)...

    按分离机制的不同 高效液相色谱法可以分为液固吸附色谱法 液液分配色谱法 正相与反相 离子交换色谱法 离子对色谱法及分子排阻色谱法 这些方法在使用的过程中往往会遇到诸如鬼峰 基线漂移 拖尾 分叉峰 保留时间漂移 柱压过高等系列问题 该如何解决
  • 线段树Segment tree(1):单点修改,区间查询

    问题描述 给定数列a 1 a 2 a N 依次进行Q次操作 操作有两类 1 i x 给定i x 将a i 加上x 2 l r 给定i x 求 i l r
  • 两年外包生涯做完,感觉自己废了一半....

    先说一下自己的情况 大专生 17年通过校招进入湖南某软件公司 干了接近2年的点点点 今年年上旬 感觉自己不能够在这样下去了 长时间呆在一个舒适的环境会让一个人堕落 而我已经在一个企业干了五年的功能测试 已经让我变得不思进取 谈了1年的女朋友
  • 国内外自然语言处理(NLP)研究组

    博客地址 http blog csdn net wangxinginnlp article details 44890553 排名不分先后 收集不全 欢迎留言完善 中国大陆地区 腾讯人工智能实验室 Tencent AI Lab https
  • linux自增窗口状态——KwindowSystem篇

    前言 之前曾翻译过 X Desktop Group 今天分享一下如何自定义状态 此篇讲述如何通过kwindowsystem新增状态 以及设置状态的过程 窗口有不同的属性 状态 允许Action等等信息 以使窗口管理器来确定窗口的装饰 堆叠位
  • STM32之NVIC

    STM32 Cortex M3 中NVIC 嵌套向量中断控制 的理解 一 STM32 Cortex M3 中的优先级概念 STM32 Cortex M3 中有两个优先级的概念 抢占式优先级和响应优先级 也把响应优先级称作 亚优先级 或 副优
  • jinfo如何使用

    jinfo是一个用于查看和调整Java虚拟机 JVM 配置参数的命令行工具 它可以在运行时获取和修改JVM的配置信息 包括内存分配 垃圾回收 运行时编译和其他设置 要使用jinfo 需要在命令行中输入以下命令 jinfo options
  • C# 学生成绩管理系统

    学生成绩管理系统 前言 一 我是一个菜鸟 二 已经有快一年没有发文章 一直在忙着毕业和找工作的事 如今生活逐渐趋于稳定 那么 勤劳的博主又开始更新了 哈哈 本次更新的是非常经典的学生成绩管理系统 这作为一个计算机专业的你来说 可能在大一 大
  • 让chatgpt从一个查询接口写接口测试用例

    要求 一个查询接口 入参有currPage order pageSize sortBy 所有入参为非必须 请帮我写出这个接口所有接口用例 根据你提供的信息 下面是该查询接口所有可能的接口用例 当所有参数都不传递时 查询接口会返回所有符合条件
  • UE44如何使用Geometry(BSP)笔刷,快速创建游戏原型?

    游戏原型搭建 如何快速搭建场景 一 好处1 防止同时也放大了对应的网格 如果像unity里面一样 R放大缩小以后 网格也会对应拉伸 失真 导致了材质会被拉伸或者缩小 1 选择Geometry 在BrushSetting里面 将X Y Z对应
  • ubuntu 20.04 安装 pycharm 2022.1 .3 及其卸载

    下载 官网下载 https www jetbrains com pycharm 安装 下载好的文件显示如下 打开终端 进入你刚下载的文件所在的文件夹目录 例如我的放在Downloads这个文件夹 cd Downloads 查看文件夹里的文件
  • ROS navigation分析:navigation框架

    前言 ROS navigation stack是ROS提供的一个非常重要且常用的模块 它的主要作用是实现机器人的定位 导航和避障功能 在ROS wiki上 Maintainer把它的功能归纳为 It takes in information
  • 从零实现DevOps(五):Jenkins+SSH远程部署SpringBoot项目

    上篇文章 我从安装Jenkins插件开始 给大家讲解了如何从Jenkis本地环境中 以启动jar包脚本的方式部署SpringBoot项目 但是呢 以咱们日常的开发来说 所有服务都部署在一台服务器上根本就不是一个合理的方案 更不可能在所有服务
  • 基于FPGA的一维卷积神经网络CNN的实现(五)数据量化(附代码)

    数据量化 环境 Pytorch Pycham Matlab 订阅后有问题 或者需要该节的文件直接加微信 Crazzy M 说明 上一节已经通过Matlab中基础的乘加运算进行了CNN网络的前向计算过程 该节利用Matlab将导出的CNN网络
  • Object365数据/论文说明

    总览 1 目标检测数据 365类 约600k训练图片 超过一千万的bboxes 迄今为止最大的目标检测数据集 全注释的 2 服务于更好的未来研究 局部敏感类型的任务 如目标检测 语义分割 3 在COCO测试下 Objects365上预训练的
  • IDEA插件系列(33):RestfulTool插件——Restful服务开发辅助工具集

    1 插件介绍 RestfulTool插件 一套 Restful 服务开发辅助工具集 提供了一个 Services tree 的显示窗口 双击 URL 直接跳转到对应的方法定义 一个简单的 http 请求工具 支持 Spring 体系 Spr
  • npm install安装依赖总结

    node下载地址 https nodejs org en download releases 可以看到node版本 npm版本 node module版本 1 npm的全局安装路径 查看默认值 npm get prefix 默认是C Use
  • 五、网络编程之网络 IO 模型的本质.md

    IO 网络模型的本质 前置概念 1 用户空间和内核空间 学习 Linux 或者 IO 网络模型时 经常可以看到两个词 User space 用户空间 和 Kernel space 内核空间 简单说 Kernel space 是 Linux