磁盘I/O流程

本文详细介绍了Linux系统中的四种I/O调度策略——NOOP、CFQ、DEADLINE和ANTICIPATORY,分析了它们的工作原理和适用场景。CFQ为每个进程创建单独的I/O队列,力求公平分配带宽,而DEADLINE在保证响应时间的同时避免I/O请求饿死。ANTICIPATORY则尝试优化随机与顺序I/O的混合场景。对于依赖磁盘性能的应用如Kafka,选择合适的调度算法至关重要。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

FIFO (Read) > FIFO (Write) > CFQ 从编程角度而已,一般磁盘I/O的场景有以下四种:

(1)用户调用标准C库进行I/O操作,数据流为:应用程序buffer->C库标准IObuffer->文件系统页缓存->通过具体文件系统到磁盘

(2)用户调用文件I/O,数据流问:应用程序buffer->文件系统页缓存->通过具体文件系统到磁盘

(3)用户打开文件时使用O_DIRECT,绕开页缓存直接读写磁盘

(4)用户使用类似dd工具,并使用direct参数,绕过系统cache与文件系统直接写磁盘。

发起I/O请求的步骤可以表述为如下的内容(以最长链路为例)

写操作:用户调用fwrite把数据写入C库标准IObuffer后就返回,即写操作通常是异步操作;

数据写入C库标准IObuffer后,不会立即刷新到磁盘,会将多次小数据量相邻写操作先缓存起来合并,最终调用write函数一次写入(或者将大块数据分解多次write调用)页缓存;数据到达页缓存后也不会立即刷新到磁盘,内核有pdflush线程在不停地检测脏页,判断是否要写回到磁盘,如果是则发起磁盘I/O请求。

读操作:用户调用fread到C库标准IObuffer中读取数据,如果成功则返回,否则继续;发起I/O请求,读取数据后缓存buffer和C库标准IObuffer并返回。可以看出,读操作是同步请求。

I/O请求处理:通用块层根据I/O请求构造一个或多个bio结构并提交给调度层;调度器将bio结构进行排序和合并组织成队列且确保写操作合并到一起写,尽可能变随机为顺序(因为随机读写比顺序读写要慢),读必须优先满足,而写也不能等太久。

 针对不同的应用场景,I/O调度处理也会影响I/O的读写性能,目前linux系统中的I/O调度策略有4种,分布是NOOP、CFQ、DEADLINE和ANTICIPATORY,默认为CFQ。

1.NOOP

NOOP算法的全写为No Operation.该算法实现了最简单的FIFO队列,所有I/O请求大致按照先来后到的顺序进行操作。之所以说“大致”,原因是NOOP在FIFO的基础上还做了相邻I/O请求的合并,并不是完全按照现金先出的规则满足I/O请求。

假设有如下的I/O请求序列:

100,500,101,10,56,1000

NOOP将会按照如下顺序满足I/O请求:

100(101),500,10,56,1000

2.CFQ

CFQ算法的全写为Completely Fair Queuing。该算法的特定是按照I/O请求的地址进行排序,而不是按照先来后到的顺序进行响应。

假设有如下的I/O请求序列:

100,500,101,10,56,1000

CFQ将会按照如下顺序满足:

100, 101,500,1000,10,56

CFQ是默认的磁盘调度算法,对于通用服务器来说是最好的选择。它试图均匀地分布对I/O带宽的访问。CFQ为每个进程单独创建一个队列来管理该进程所产生的请求,也就是说,每个进程一个队列,各队列之间的调度使用时间片段进行调度,以此来保证每个进程都能被很好第分配到I/O带宽。I/O调度器每次执行一个进程的4次请求。在传统的SAS盘上,磁盘寻道花去了绝大多数的I/O响应时间。CFQ的出发点是对I/O地址进行排序,以尽量少的磁盘旋转次数来满足尽可能多的I/O请求。在CFQ算法下,SAS盘的吞吐量大大提高了。相比于NOOP的缺点是,先来的I/O请求并不一定能被满足,可能会出现“饿死”的情况。

3.DEADLINE

DEADLINE在 CFQ 的基础上,解决了 I /0 请求“饿死”的极端情况。除了 CFQ 本身具有 I/0 排序队列, DEADLINE 额外分别为读 I/O 和写I /0 提供了 FIFO 队列。读 FIFO 队列的最
大等待时间为 500ms ,写 FIFO 队列的最大等待时间为5 s。  FIFO 队列内的I/O 请求优先级要比
CFQ 队列中的高,而读 FIFO 队列的优先级又比写 FIFO 队列的优先级高。优先级可以表示如下
FIFO (Read) > FIFO (Writ e) > CFQ
4、ANTICIPATORY
CFQ和 DEADLINE 考虑的焦点在于满足零散 I/O 请求上 对于连续的 I/O 请求,比如顺序读
并没有做优化,  为了满足随机 I/O 和顺序I/O 混合的场, Linux 还支持 ANTICIPATORY
调度算法。  ANTICIPATORY在 DEADLINE 的基础上,为每个读 I/O 都设置了 6ms 的等待时间
窗口。 如果在 6ms内 OS 收到了相邻位置的读 I/O 请求,就可以立即满足。 ANTICIPATORY 算
法通过增加等待时间来获得更高的性能,假设一 个块设备只有一 个物理查找磁头(例如 1  个单
独的 SATA 硬盘),将多个随机的小写入流合并成 个大写入流(相当于将随机读写变顺序读
写),通 过这个原 理来使用读取/写入的延时换取最大的读取/写入吞 量。适用于大多数环境
特别是读取/写入较多的环境
不同的磁盘调度算法(以及相应的 I/O 优化手段〉对 Kafka 这类依赖、磁盘运转的应用的影
响很大,建议根据不同的业务需求来测试并选择合适的磁盘调度算法。
从文件系统层面分析, Kafka 操作的都是普通文件,并没有依赖于特定的文件系统,但是
依然推荐使用 EXT4 XFS 尤其是对 XFS 而言,它通常有更好的性能 ,这种性能的提升 主要
影响的是 Kafka 写入性能

<think>好的,用户现在问的是如何判断磁盘I/O延迟。之前他提到系统操作卡顿但日志监控不卡,现在可能是在深入排查资源瓶颈中的磁盘I/O问题。我需要回顾之前的回答,确保内容一致,同时更详细地解释如何判断磁盘I/O延迟。 首先,用户可能不太熟悉Linux命令,需要给出具体的命令和解读方法。比如用iostat,但要解释每个参数和指标的意义,比如await、svctm、%util这些。此外,用户可能需要了解其他工具,比如iotop、sar,或者更高级的工具如blktrace,这样他们可以选择适合自己的方法。 另外,用户可能遇到不同场景,比如物理机、虚拟机或云环境,需要指出不同环境下的注意事项。比如云环境中可能受到共享磁盘的影响,这时候需要看AWS的CloudWatch或者其他云服务提供的监控指标。 还要考虑用户的实际操作步骤,是否需要分步骤说明,从基础命令到高级分析,逐步深入。比如先使用iostat快速查看,如果发现问题再用更详细的工具进一步排查。 用户可能还想知道哪些指标是关键的阈值,比如await一般超过多少算有问题,%util达到多少表示磁盘繁忙。这些具体的数值可以帮助用户快速判断。 此外,结合之前的案例,比如MySQL的binlog写入问题,可以举一个实际例子,说明如何通过这些工具发现并解决问题,这样用户更容易理解。 还要注意用户的潜在需求,比如他们可能不仅想知道如何判断延迟,还想知道如何解决。虽然问题没有直接问解决方法,但可能在回答中简要提及,比如调整IO调度器、优化应用写入模式等,这样回答会更全面。 最后,确保语言通俗易懂,避免太多专业术语,或者在必要时解释术语,比如解释什么是await,什么是IOPS,这样用户即使没有很深的技术背景也能理解。</think>判断磁盘I/O延迟的完整方法体系(附关键指标阈值): --- **一、基础诊断工具** 1. **iostat黄金参数法** ```bash $ iostat -xmdz 1 # -x 扩展统计 -m MB单位 -d 设备详情 -z 过滤空闲设备 ``` **核心指标解读**: - `await` = (读写等待时间)/IO次数 *机械 >15ms | SSD >5ms* 即异常 - `svctm` = 磁盘处理IO的平均时间 *该值持续接近await说明无排队* - `%util` = 磁盘繁忙度百分比 *>70% 表示接近饱和* *案例:MySQL写入卡顿时,发现`await=320ms`,`%util=98%`,定位到RAID卡缓存故障* 2. **进程级IO监控** ```bash $ iotop -oPa # -o 只显示活跃进程 -P 只显示进程 -a 累计统计 ``` - 重点关注`SWAPIN`和`IO>`列,>10MB/s的进程需审查 --- **二、高级追踪手段** 1. **blktrace全链路追踪** ```bash $ blktrace -d /dev/sda -o trace | blkparse -i trace ``` **关键阶段耗时分析**: ``` Q2S: 从IO进入队列到开始服务的时间(调度延迟) S2C: 磁盘实际服务时间(物理延迟) Q2C: 总延迟 = Q2S + S2C ``` *当Q2S占比>30%时,说明存在排队瓶颈* 2. **BCC工具集实时分析** ```bash $ /usr/share/bcc/tools/biolatency -m Tracing block I/O... Hit Ctrl-C to end. usecs : count distribution 0 -> 1 : 0 | | 2 -> 3 : 0 | | 4 -> 7 : 0 | | 8 -> 15 : 2 |**** | 16 -> 31 : 3 |******* | 32 -> 63 : 6 |*************** | 64 -> 127 : 12 |****************************** | 128 -> 255 : 24 |*******************************************************| ``` - 直方图显示64-127μ秒的IO占主流(SSD正常范围) --- **三、云环境特殊考量** 1. AWS EBS监控要点: - `VolumeQueueLength` > 64 表示排队严重 - `BurstBalance` < 80% 时性能会下降 2. 阿里云云: ```bash # 查看预配置IOPS利用率 $ aliyun ecs DescribeDisks --DiskId=d-xxx ``` - 当`IOPSConsumption` > 90% 需扩容 --- **四、性能基线参考值** | 存储类型 | 随机读延迟 | 顺序写延迟 | |---------------|-----------|------------| | 7200转SATA | 8-12ms | 120MB/s | | NVMe SSD | 150-250μs | 2.5GB/s | | AWS gp3 | <3ms | 1000MB/s | | Azure Premium | <2ms | 750MB/s | --- **五、根因诊断流程** 1. 区分应用模式: ```bash # 查看读写比例 $ iostat -x 1 | grep -v "^$" | awk '/sd[a-z]/ {print $6/$5}' ``` - 随机读写密集型(OLTP)关注IOPS - 顺序读写型(日志服务)关注吞吐量 2. LVM层检查: ```bash $ dmsetup status stripe-vol: 0 209715200 striped 3 64 8:16 384 8:32 384 8:48 384 ``` - 条带不均匀会导致热点 3. 文件系统检测: ```bash $ tune2fs -l /dev/sda1 | grep 'Filesystem features' Filesystem features: has_journal ext_attr resize_inode dir_index filetype needs_recovery extent 64bit flex_bg sparse_super large_file huge_file uninit_bg dir_nlink extra_isize ``` - `has_journal`开启会增加约10%写开销 --- **典型案例**:某视频网站转码集群出现周期性卡顿: 1. 通过`$ pidstat -d 1`发现ffmpeg进程IO占用率达98% 2. `$ iostat -x 1`显示`%util`持续100%,但`await`波动在5ms-30
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值