blktrace —— 块设备 I/O 全链路追踪(从提交到落盘)
这个工具是做什么的
iostat 只能看到设备级聚合(IOPS/延迟),回答"盘忙不忙";blktrace 直接在内核块设备层打点,追踪每个 I/O 请求从"谁提交 → 进入队列 → 合并 → 派发 → 完成"的全过程,能回答"谁在向盘发什么请求、请求在哪个环节被卡住"。配合 btt 归因,是磁盘延迟分析最深的一档工具。
可以回答什么问题
| 问题 | 怎么用 |
|---|---|
| 某块盘 I/O 慢在哪一环(队列/派发/完成)? | btt 汇总各环节耗时(Q2G/G2I/I2D/D2C) |
| 谁(进程)在向盘发请求? | blkparse 的 COMM 字段;配合 -a issue 过滤 |
| I/O 是否在排队、队列多深? | Q 事件(入队)与 D 事件(派发)之间的间隔 |
| 请求多大、读还是写、落在哪个扇区? | blkparse 每行的 sector/nbytes/rw |
| 有没有大量合并? | Q→M(合并)事件比例 |
数据来源
- 来源接口:内核块设备层 tracepoint(
block:*),由blk_mq的 I/O 路径埋点触发。 - 采集方式:
blktrace -d <dev>在内核侧记录事件到文件(relayfs),blkparse解析并输出可读日志,btt做时间线归因分析。 - 由此决定的特性:打点本身有开销——高 IOPS 环境下采集会产生额外 CPU 与存储消耗,不宜长时间全量开启;事件文件巨大,建议配合
-a按动作过滤只抓关心的阶段。
一、基本用法
bash
yum install blktrace / apt install blktrace
# 1. 采集(后台运行,记录到 ./nvme0n1.blktrace.* 文件)
blktrace -d /dev/nvme0n1 -o - | blkparse -i - > trace.txt # 在线管道输出
blktrace -d /dev/nvme0n1 & # 落盘模式(Ctrl-C 结束)
# 2. 只抓特定阶段(如只关心派发和完成)
blktrace -d /dev/nvme0n1 -a issue -a complete &
# 3. 解析
blkparse nvme0n1 # 解析并打印可读事件
blkparse -i nvme0n1 -o out.txt
# 4. 时间线归因(最有用)
blktrace -d /dev/nvme0n1 -w 30 & sleep 31; blkparse -i nvme0n1 | btt -i -二、blkparse 事件解读
text
8,0 1 1 0.000000000 1234 A R 123456 + 16 <- (8,0) 123456
8,0 1 2 0.000001100 1234 Q R 123456 + 16 [nginx]
8,0 1 3 0.000003200 1234 M R 123456 + 32 [nginx]
8,0 1 4 0.000005400 1234 D R 123456 + 32 [nginx]
8,0 1 5 0.000050100 0 C R 123456 + 32 ( 45000us )| 事件 | 含义 |
|---|---|
A | Remap(映射) |
Q | 请求进入队列(入队) |
M | 与已有请求合并 |
D | 派发给设备(下盘) |
C | 完成(us 是完成耗时) |
三、btt 各环节延迟
| 环节 | 含义 | 判读 |
|---|---|---|
Q2G | 入队到拿到请求 | 调度等待 |
G2I / I2D | 排队/派发前等待 | 队列深度高则大 |
D2C | 派发到完成 | 设备真实服务时间 |
Q2C | 入队到完成全链路 | 用户可感知延迟 |
一句话总结:iostat 说"盘慢",blktrace+btt 说"慢在哪一环、是谁发的"——
D2C大是盘本身慢,Q2D大是队列/调度在排队。