磁盘性能分析工具

此脚本目前利用fio开源工具进行磁盘的性能分析和汇总

结果分析

fio使用说明

常用命令和解析

按时间快速测试类(--runtime=60 --time_based, 已runtime作为测试结果的基准,runtime指定测试60秒):

  • 顺序写fio --name=seqwrite --rw=write --bs=1M --size=10G --direct=1 --runtime=60 --time_based

结果分析

报告结果示例如下:

seqwrite: (g=0): rw=write, bs=(R) 1024KiB-1024KiB, (W) 1024KiB-1024KiB, (T) 1024KiB-1024KiB, ioengine=psync, iodepth=1
fio-3.41
Starting 1 process
seqwrite: Laying out IO file (1 file / 1024MiB)
Jobs: 1 (f=1): [W(1)][100.0%][w=207MiB/s][w=207 IOPS][eta 00m:00s]
seqwrite: (groupid=0, jobs=1): err= 0: pid=666122: Tue Jan 27 11:12:13 2026
  write: IOPS=198, BW=199MiB/s (209MB/s)(11.7GiB/60002msec); 0 zone resets
    clat (usec): min=2046, max=69590, avg=5008.98, stdev=4186.76
     lat (usec): min=2053, max=69602, avg=5021.56, stdev=4187.28
    clat percentiles (usec):
     |  1.00th=[ 2057],  5.00th=[ 2073], 10.00th=[ 2073], 20.00th=[ 2114],
     | 30.00th=[ 2147], 40.00th=[ 2180], 50.00th=[ 4178], 60.00th=[ 4621],
     | 70.00th=[ 5735], 80.00th=[ 7308], 90.00th=[10028], 95.00th=[13304],
     | 99.00th=[21103], 99.50th=[26084], 99.90th=[34866], 99.95th=[38011],
     | 99.99th=[57410]
   bw (  KiB/s): min=34816, max=456704, per=99.62%, avg=202941.31, stdev=116471.71, samples=119
   iops        : min=   34, max=  446, avg=198.18, stdev=113.74, samples=119
  lat (msec)   : 4=48.24%, 10=41.88%, 20=8.75%, 50=1.11%, 100=0.02%
  cpu          : usr=0.41%, sys=1.46%, ctx=12401, majf=0, minf=10
  IO depths    : 1=100.0%, 2=0.0%, 4=0.0%, 8=0.0%, 16=0.0%, 32=0.0%, >=64=0.0%
     submit    : 0=0.0%, 4=100.0%, 8=0.0%, 16=0.0%, 32=0.0%, 64=0.0%, >=64=0.0%
     complete  : 0=0.0%, 4=100.0%, 8=0.0%, 16=0.0%, 32=0.0%, 64=0.0%, >=64=0.0%
     issued rwts: total=0,11937,0,0 short=0,0,0,0 dropped=0,0,0,0
     latency   : target=0, window=0, percentile=100.00%, depth=1

Run status group 0 (all jobs):
  WRITE: bw=199MiB/s (209MB/s), 199MiB/s-199MiB/s (209MB/s-209MB/s), io=11.7GiB (12.5GB), run=60002-60002msec

Disk stats (read/write):
  sda: ios=158/15382, sectors=27472/24549824, merge=50/3354, ticks=2048/82469, in_queue=93576, util=96.45%

结果逐段分析:

  1. 基础测试信息(本次测试的测试项目和类型):
seqwrite: (g=0): rw=write, bs=(R) 1024KiB-1024KiB, (W) 1024KiB-1024KiB, (T) 1024KiB-1024KiB, ioengine=psync, iodepth=1
fio-3.41
Starting 1 process
  • seqwrite:: 作业名称,与 --name 参数对应。
  • (g=0): 表示这是第 0 组作业(group)。
  • rw=write: 显示实际使用的 I/O 模式是写入(write)。
  • bs=(R/W/T) ...: 显示读(R)、写(W)、总(T)的实际块大小范围。这里均为 1024KiB(即 1MB),与 --bs=1M 参数一致。
  • ioengine=psync: 显示使用的 I/O 引擎是 psync(POSIX 同步 I/O),这是 --direct=1 时的默认引擎之一,它会调用 pwrite() 等函数。psync 引擎发出一个 I/O 请求(pread/pwrite)后,调用会阻塞,直到该 I/O 操作在存储设备上完成才会返回。它不提供任何异步能力。
    • libaio (Linux Asynchronous I/O):Linux 原生的异步 I/O 接口。它可以真正实现并发 I/O,允许应用程序一次性提交多个 I/O 请求,然后通过事件通知机制(如 eventfd 或 io_getevents)获取完成状态。
    • io_uring: 高性能异步 I/O 框架,旨在克服传统 libaio 的一些限制,提供更低的延迟和更高的吞吐量。它使用共享环形缓冲区来高效地提交和完成 I/O 请求。(推荐内核版本5.1以上使用)
    • mmap: 将文件映射到内存地址空间, 然后像访问内存一样读写文件, 本质上是缓冲 I/O 的速度测试
  • iodepth=1: 显示队列深度为 1,即一次只发出一个 I/O 请求并等待其完成。模拟了一种同步、串行的 I/O 模式。在这种模式下,应用程序的行为是阻塞的,必须等待前一个 I/O 操作结束后才能继续下一个。
    • iodepth=N: 表示一次可以发出 N 个 I/O 请求而不必等待它们完成,然后等待队列中的第一个请求完成后,再发出第 N+1 个请求,以此类推,保持队列中有 N 个待处理的请求。更适合模拟多线程/多进程应用或数据库等高并发 I/O 场景下的吞吐量(IOPS/Bandwidth)和平均/百分位延迟。通常,随着 iodepth 的增加,IOPS 和带宽会提升(直到达到设备极限),而延迟可能会降低(因为请求可以被并行处理和优化)。
  1. 测试实时信息:(在测试途中会一直变化的信息,可以看成是fio的进度条信息)
seqwrite: Laying out IO file (1 file / 1024MiB)
Jobs: 1 (f=1): [W(1)][100.0%][w=207MiB/s][w=207 IOPS][eta 00m:00s]
  • fio 正在准备用于 I/O 的文件, 准备 1 个大小为 1024MiB(即 1GB)的文件, 并且开始测试的任务实时情况和进度
    • Jobs: 1 (f=1): 当前正在运行 1 个作业(f=1 通常表示正在运行的作业数)。
    • [W(1)]: 实时显示作业状态,W 表示正在进行写操作,(1) 表示 1 个作业处于此状态。
    • [100.0%]: 文件布局(pre-fill)进度或整体任务进度接近 100%(在这个实时更新行里,通常指布局完成度)。
    • [w=207MiB/s]: 实时写入带宽约为 207 MiB/s。[w=207 IOPS]: 实时写入 IOPS 约为 207。
    • [eta 00m:00s]: 预计剩余时间 0 秒,因为使用了--time_based--runtime=60,所以一旦达到 60 秒就会结束。
  1. 测试详细结果: 此项目内容较多,按照测试类型分类介绍

seqwrite: (groupid=0, jobs=1): err= 0: pid=666122: Tue Jan 27 11:12:13 2026

  • 第0组的第1个任务,0个错误,任务使用的pid和执行时间

write: IOPS=198, BW=199MiB/s (209MB/s)(11.7GiB/60002msec); 0 zone resets

  • 这是写操作的汇总统计; IOPS=198: 平均 IOPS(每秒输入/输出操作数)为 198。由于块大小是 1MB,这个数字也等于每秒完成的事务数。
  • BW=199MiB/s (209MB/s): 平均带宽(Bandwidth)为 199 Mebibytes/second (MiB/s),括号内是更常见的十进制单位 Megabytes/second (MB/s)。
  • (11.7GiB/60002msec): 总共写入了 11.7 GiB 的数据,在 60002 毫秒(约 60 秒)内完成。
  • 0 zone resets: 适用于 Zoned Block Device (ZBD) 或 SMR 硬盘,表示 Zone 重置次数。普通硬盘此项为 0。

clat (usec): min=2046, max=69590, avg=5008.98, stdev=4186.76lat (usec): ...

  • clat: Completion Latency,完成延迟。指从 I/O 请求发出到请求完成所花费的时间。
  • lat: Total Latency,总延迟。包括了 I/O 请求排队等待的时间加上实际处理时间(即 clat)。对于同步 I/O (iodepth=1),lat 和 clat 通常非常接近。
  • min/max/avg/stdev: 总延迟的最小值、最大值、平均值和标准差,单位微秒(μs)。

clat percentiles (usec): 1.00th=[ 2057], 5.00th=[ 2073] ... 90.00th=[10028], 99.00th=[21103], 99.90th=[34866], 99.99th=[57410]

  • 完成延迟百分位数统计。这是评估延迟分布的重要指标
  • 例如 90.00th=[10028]: 表示 90% 的 I/O 操作的完成延迟小于或等于 10028 微秒 (约 10ms)。

bw ( KiB/s): min=34816, max=456704, per=99.62%, avg=202941.31, stdev=116471.71, samples=119

  • bw ( KiB/s): 带宽统计,单位 KiB/s; min/max: 最小和最大瞬时带宽; avg: 平均带宽 (202941.31 KiB/s ≈ 198 MiB/s),与上面的 BW 值基本一致。
  • stdev: 带宽标准差,衡量带宽波动性; samples=119: 采样点数量; per=99.62%: 该作业在整个测试中占用的时间比例,在--section或多个作业时有意义。

iops : min=34, max=446, avg=198.18, stdev=113.74, samples=119

  • iops: 每秒输入/输出操作数统计; min/max/avg/stdev/samples: 最小、最大、平均 IOPS,IOPS 标准差,采样点数量。

lat (msec) : 4=48.24%, 10=41.88%, 20=8.75%, 50=1.11%, 100=0.02%

  • lat (msec): 总延迟分布统计,按毫秒分段展示。比如:4=48.24%: 表示 48.24% 的 I/O 操作总延迟小于 4 毫秒。100=0.02%: 表示 0.02% 的 I/O 操作总延迟在 50 到 100 毫秒之间。

cpu: usr=0.41%, sys=1.46%, ctx=12401, majf=0, minf=10

  • CPU 使用情况统计; usr、sys、ctx:用户态使用率、内核态使用率、Context Switches (上下文切换) 总数
  • majf=0: Major Page Faults (主要缺页错误) 数量。为 0 表示所有内存访问都命中了物理内存或缓存,无需从磁盘加载页面。
  • minf=10: Minor Page Faults (次要缺页错误) 数量。表示 10 次内存访问需要分配物理内存页,但不需要从磁盘读取。

IO depths: 1=100.0%, 2=0.0%, 4=0.0%, 8=0.0%, 16=0.0%, 32=0.0%, >=64=0.0%

  • IO depths: 实际达到的队列深度分布; 因为本示例测试iodepth=1, 所以结果符合预期

submit: 0=0.0%, 4=100.0%, 8=0.0%, 16=0.0%, 32=0.0%, 64=0.0%, >=64=0.0%, complete: ...

  • submit/complete: 提交和完成的 I/O 请求批量大小分布; 4=100.0% 表示时候 fio 全部都是以 4 个请求为一组提交或完成的,这反映了内部批处理机制。

issued rwts: total=0,11937,0,0 short=0,0,0,0 dropped=0,0,0,0

  • 发出的 I/O 类型统计 (Read, Write, Trim, Sync)。; total=0,11937,0,0: 总共发出了 0 个读、11937 个写、0 个 Trim、0 个 Sync 请求。
  • short=...: 短请求(未达到指定大小)的数量; dropped=...: 因为资源不足等原因被丢弃的请求数量。

latency: target=0, window=0, percentile=100.00%, depth=1

  • 延迟目标(Latency Target)和延迟百分位数(Percentile); depth: 命令中设置的 --iodepth=1
  • target: --latency_target参数设置延迟目标,确保大部分I/O操作的延迟低于这个目标值。(例如 --latency_target=10000 表示 10000 微秒,即 10ms)
  • window: --latency_window 参数 (单位微秒)测试中设置的延迟目标窗口,fio 可能会减缓 I/O 的发出速度,以努力满足延迟目标。
  • percentile: --latency_percentile 参数(例如 --latency_percentile=95)定义了在 --latency_window 内需要满足 --latency_target 的 I/O 比例。例如,95% 的 I/O 延迟需要低于--latency_target
  1. 按测试组分类的运行摘要
Run status group 0 (all jobs):
  WRITE: bw=199MiB/s (209MB/s), 199MiB/s-199MiB/s (209MB/s-209MB/s), io=11.7GiB (12.5GB), run=60002-60002msec
  • WRITE: 写操作汇总; bw=199MiB/s (209MB/s): 平均带宽; 199MiB/s-199MiB/s: 带宽范围(最小-最大),在这里两者相同。
  • io=11.7GiB (12.5GB): 总 I/O 量; run=60002-60002msec: 运行时间范围(最小-最大),均为 60002 毫秒(约 60 秒)。
  1. 磁盘读写统计汇总
Disk stats (read/write):
  sda: ios=158/15382, sectors=27472/24549824, merge=50/3354, ticks=2048/82469, in_queue=93576, util=96.45%
* ios=158/15382: 该设备上的读/写 I/O 操作总数。158 次读,15382 次写。读操作可能来自元数据、预读等。
* sectors=27472/24549824: 读/写的扇区总数。通常一个扇区是 512 字节。
* merge=50/3354: 读/写合并次数。操作系统将相邻的 I/O 请求合并成一个更大的请求,以提高效率。
* ticks=2048/82469: 读/写操作消耗的 "ticks" 时间。一个 tick 通常是 1 毫秒。这个值反映了设备处理 I/O 的总时间。
* in_queue=93576: I/O 请求在队列中的总时间(ticks)。
* util=96.45%: 设备利用率,表示在这 60 秒内,磁盘忙于处理 I/O 的时间占比为 96.45%。
Description
龙架构存储性能测试工具
Readme 66 KiB
Languages
Shell 100%