2、IO流程总结

一、什么是IO

 IO是冯·诺依曼结构结构重要单元(运算器、控制器、存储器、输入设备、输出设备),也是一个使用频率最高的计算机资源,我们编程其实就是处理各种I/O的过程。

I/O输入/输出(Input/Output),分为IO设备和IO接口两个部分。 在POSIX兼容的系统上,例如Linux系统 [1] ,I/O操作可以有多种方式,比如DIO(Direct I/O),AIO(Asynchronous I/O,异步I/O),Memory-Mapped I/O(内存映射I/O)等,不同的I/O方式有不同的实现方式和性能,在不同的应用中可以按情况选择不同的I/O方式。

二、IO模型区分

按照IO模型定义大概可以分为,同步阻塞IO、同步非阻塞 IO、异步阻塞 IO、异步非阻塞 IO。

1、同步异步

同步 指进程触发IO操作后会阻塞用户进程,用户等待请求数据到达的过程。异步 指进程触发IO操作后不会阻塞用户进程。两者区别,进程触发IO操作是否会阻塞用户进程,用户的cup此时是否释放,所以同步异步针对的是用户进程

2、阻塞非阻塞

阻塞 指用户进程触发IO操作后,触发read()等待内核将数据copy到用户空间的过程(select 也是一种阻塞IO)。非阻塞 指用户进程触发IO操作后,触发read(),系统内核会立刻返回成功,当read响应完成,系统内核会产生一个信号或者基于一个线程回调函数完成IO过程。两者区别,触发read()操作后,系统内核是否会立刻返回状态还是等待, 所以阻塞非阻塞是针对操作系统内核

三、按系统内核区分

直接IO概念:程序访问数据不经过内核缓存区,直接访问磁盘、网卡等其他设备的IO过程。缓存IO概念:程序访问数据,先将数据copy到系统内核,然后从系统内核copy到用户空间。两种区别:程序访问数据,数据是否进过系统内核,操作系统为了系统安全和缓存的需要,用户读取数据需要先读取到系统内核,然后从系统内核copy到用户空间,这种模式隔离用户空间和系统空间提高系统的安全,数据缓存到系统内核,不必每次读取数据都从磁盘读取提高程序的性能,但是在不需要反复数据读取处理的场景(比如kafka),缓存I/O会多一层读取内核操作,浪费cpu和内存资源。关于直接I/O Linux使用很多技术待I/O模型技术实现分解。

四、按机械硬盘区分

线性结构概念:程序存储数据时,申请一块连续的磁盘空间,然后将数据顺序写入磁盘,此种模式硬盘无需寻址,写入性能接近内存写入速度。链式结构概念:程序存储数据时候,申请一块非连续的磁盘空间,写入磁盘时候程序需要寻址速度慢。两种区别:程序存储时候申请硬盘是连续磁盘空间,还是逻辑连续的磁盘空间,连续的磁盘空间程序写入性能好,但是硬盘空间利用率差,逻辑连续的硬盘资源反之。

五、按linux系统实现区分

1、BIO (同步阻塞IO)

操作系统和应用客户端通讯,彼此各自拿出一个线程,线程只能为操作系统、客户端使用。就算中途无任何通讯彼此等待这,这样造成极大的资源浪费。 这种方式在linux实现叫BIO。BIO对应的就是同步阻塞IO模型

2、Nio(同步非阻塞IO)

1、select方案

select工作方式是轮询文件描述符。

1、监听文件描述符限制 - 单个进程可监视的fd数量被限制

  一般来说这个数目和系统内存关系很大,具体数目可以cat /proc/sys/fs/file-max察看。32位机默认是1024个。64位机默认是2048.

2、 轮询法扫描性能能差 - 对socket进行扫描时是线性扫描,即采用轮询的方法效率较低

当套接字比较多的时候,每次select()都要通过遍历FD_SETSIZE个Socket来完成调度,不管哪个Socket是活跃的,都遍历一遍。这会浪费很多CPU时间。如果能给套接字注册某个回调函数,当他们活跃时,自动完成相关操作,那就避免了轮询,这正是epoll与kqueue做的。

select 优点

1、跨平台,几乎所有平台都支持; 2、时间精度高延时纳秒级别。

select缺点

1、最大限制:单个进程能够监视的文件描述符的数量存在最大限制。一般来说这个数目和系统内存关系很大,具体数目可以cat /proc/sys/fs/file-max察看。它由FD_SETSIZE设置,32位机默认是1024个。64位机默认是2048.

2、时间复杂度: 对socket进行扫描时是线性扫描,即采用轮询的方法,效率较低,时间复杂度O(n)。当套接字比较多的时候,每次select()都要通过遍历FD_SETSIZE个Socket来完成调度,不管哪个Socket是活跃的,都遍历一遍。这会浪费很多CPU时间。它仅仅知道有I/O事件发生了,却并不知道是哪那几个流(可能有一个,多个,甚至全部),我们只能无差别轮询所有流,找出能读出数据,或者写入数据的流,对他们进行操作。所以select具有O(n)的无差别轮询复杂度,同时处理的流越多,无差别轮询时间就越长。

3、内存拷贝:需要维护一个用来存放大量fd的数据结构,这样会使得用户空间和内核空间在传递该结构时复制开销大。

2、poll方案

poll本质上和select没有区别,它将用户传入的数组拷贝到内核空间,然后查询每个fd对应的设备状态,如果设备就绪则在设备等待队列中加入一项并继续遍历,如果遍历完所有fd后没有发现就绪设备,则挂起当前进程,直到设备就绪或者主动超时,被唤醒后它又要再次遍历fd。这个过程经历了多次无谓的遍历。

1、无最大连接数的限制 - 它没有最大连接数的限制,原因是它是基于链表来存储的,

2、存在性能浪费

1、大量的fd的数组被整体复制于用户态和内核地址空间之间,而不管这样的复制是不是有意义。

2、poll还有一个特点是“水平触发”,如果报告了fd后,没有被处理,那么下次poll时会再次报告该fd。

3、linux不存在(异步阻塞IO)

这种io场景很少见到

4、AIO(异步非阻塞 IO)

三、系统IO概念模型

1、同步阻塞IO

用户发起IO操作后,用户进程阻塞等待内核响应,此时系统内核发生上下文切换,等待内核将数据copy到用户空间,这个过程看似紧密有序,但是有用户线程和内核线程等待,所以同步阻塞I/O是一种低效I/O。

图 1. 同步阻塞 I/O 模型流程

2、同步非阻塞IO

用户发起IO操作后,用户进程阻塞等待内核响应,此时系统内核立刻返回成功,当read()响应完成,系统内核会产生一个信号或者基于一个线程回调函数完成IO过程。框架支持 目前没有见过支持同步非阻塞I/O模型产品

Linux同步非阻塞I/O模型:当用户发起IO请求,用户进程阻塞,此时read()响应错误代码,内核响应未就绪,程序需要多次请求确认内核就绪,严格意义上讲此时内核是阻塞的,在等待内核响应有一定的时间间隔,所以同步非阻塞I/O也是一种低效I/O。

图 2. Linux 同步阻塞 I/O 模型流程

3、异步阻塞IO

当用户发起IO请求,此时用户进程不被阻塞,此时内核配置的I/O是非阻塞的I/O,操作系统会阻塞select来监视内核是否就绪,如果内核就绪就通知应用处理。此I/O模型也叫多路复用I/O模型,只是缓解内核阻塞,但是高性能的I/O操作仍然会有性能问题。

总结:此I/O模型是Linux最成熟稳定的I/O模型,Linux做大量的技术优化(比如:select、poll),许多高性能框架都是基于此I/O模型,比如 netty,mina等。

图 3. Linux 异步阻塞 I/O 模型流程

4、异步非阻塞IO

当用户发起IO请求,此时用户进程不被阻塞,此时内核配置的I/O是非阻塞的I/O,当内核就绪后回调通知用户线程完成I/O处理流程,Linux epoll基于此模型。

图 4. Linux 异步非阻塞 I/O 模型流程

四、Linux实现IO类型

1、BIO

BIO模型:bio按照IO模型属于同步并阻塞IO模型,是最古老可靠的通讯模型。 这种模型缺点就是性能低导致cpu等待不能充分的利用系统资源。

线程池方式伪异步IO模型:伪异步IO模型属于同步非阻塞IO模型。这种IO模型利用线程池复用的方式实现非阻塞的效果。

2、NIO

3、AIO

五、IO模型与硬件

IO读流程:用户空间读请求-->Linux内核空间-->在pageCache查询缓存-->未查询到os内核在内存映射的目标数据(缺页)-->获取逻辑地址(获取page对应块地址)-->块地址获取磁盘物理地址-->通过SASI指令操作硬盘读取物理地址内容-->数据返回到系统内核(此过程通过DMA技术直接copy到内存,不需要cup参与)-->数据通过内核返回到用户空间

IO写流程:用户空间写请求-->将文件写入pageCache-->获取逻辑地址(获取page对应块地址)-->块地址获取磁盘物理地址-->通过SASI指令操作硬盘读取物理地址内容-->pageCache在合适的时机将脏页刷新到磁盘

图 5. Linux 一次写入I/O宏观流程图(包含硬件部分)

I/O读写流程总结: 系统在读写的时候参与方可能有 cup、内存、硬盘、网卡、显卡等等外接设备,分析过程发现三个特点。

  1. 这个读写过程都有经过操作系统内核
  2. 读写过程都经过用户空间
  3. 通过DMA技术对第三方外设进一步抽象,让CPU无需关注外设copy数据到系统内核过程。

四、名词解释

1、硬件名词解释

DMA技术:它允许某些电脑内部的硬件子系统(外设),可以独立地直接读写系统内存,而不需中央处理器介入处理,同等情况下降低cup负担。

PIC总线:cpu访问其他pic设备的通道。

SAS控制器:一种新型的磁盘链接技术。

MCU微控单元:一种微型计算机简称单片机。

MMU内存管理单元:分页内存管理单元,功能包括虚拟地址到物理地址的转换(即虚拟内存管理)、内存保护、中央处理器高速缓存的控制。

LBA逻辑地址块:存储设备物理地址与逻辑地址映射关系

2、Linux名词解释

Linux内核存储单元:

脏页:被修改过的页

扇区:磁盘存储的最小单位

磁盘块:文件系统读写数据的最小单位

页:内存存储的最小单位,他是位于内存和文件系统之间的缓存区域,操作系统通过地址映射将文件系统映射为页的级别。

pageCache:页高速缓冲存储器,简称页高缓。page cache的大小为一页,通常为4K。在linux读写文件时,它用于缓存文件的逻辑内容,从而加快对磁盘上映像和数据的访问。

机型硬盘容量:硬盘容量大小=磁头数×柱面数×扇区数×每扇区字节数

  • 2
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值