省流版:md journal 不是把 HDD 随机写变成 NVMe 随机写的魔法。它只负责 write-hole 保护和让回写更接近全条带写,持续的随机写能力仍由 HDD 自己决定。
1. 背景与假设:想用 NVMe 给 RAID6 续命
问题现场:底层是一组 12 LUN 的 RAID6,来自 6 块物理盘(双致动器,每块盘切出两个 LUN)。小随机写实测 10-17MB/s,业务入写基线约 18MB/s。入写大于落盘,脏数据持续累积,这是后续所有测试的起点。
现场有一块 256G NVMe,计划用它验证 md 的 journal 机制(raid5-cache):随机小写先顺序写入快速 journal 设备,md 应答后再批量落盘。按该机制,小随机写的前端速度应接近 journal 设备,即接近 NVMe 速度;18MB/s 的入写基线低于 NVMe 写入能力,RAID6 的 RMW 写惩罚预期被削弱。
2. 实验设计
实验环境为 Rocky 8.10 + kernel 7.1.4(elrepo),mdadm 支持 --add-journal。计划:给 md0 挂 256G NVMe 分区做 journal,用 fio 直接压 /dev/md0,对比加 journal 前后的随机写表现。
先跑峰值测试:
fio --filename=/dev/md0 --rw=randwrite --bs=4k --size=8G \
--iodepth=64 --numjobs=4 --direct=1 --ioengine=libaio--size=8G 用来测「纯 journal 峰值」——数据量小于 journal 容量时,最能体现 journal 的吸收速度。更极限的参数是:
fio --filename=/dev/md0 --rw=randwrite --bs=4k \
--iodepth=128 --numjobs=8 --norandommap --direct=1 --randrepeat=0配合 63.7T 全盘随机打范围,逼近真实压力。
监控同时开两条线:
iostat -x /dev/nvme1n1p1 1看 journal 设备的吞吐;再采样 /sys/block/nvme1n1/nvme1n1p1/stat 的第 3、7 字段,分别对应「排水读 / 吸收写」两个方向。
3. 踩坑:journal 不是想加就能加
第一坑:journal 只支持 RAID5/6。RAID10 不支持,也不需要,镜像语义天然没有 RMW 和 write-hole 问题。本次实验在 RAID6 上操作,不涉及该限制;同一思路套到 RAID10 上无法执行。
第二坑:加 journal 要求阵列 readonly。直接执行:
mdadm --add-journal /dev/md0 /dev/nvme1n1p1报错:
/dev/md0 is not readonly, cannot add journal正确操作是先 umount、停掉上层的 bcache0,再执行:
mdadm --grow /dev/md0 --bitmap=none
mdadm --readonly /dev/md0
mdadm --add-journal /dev/md0 /dev/nvme1n1p1bitmap 与 journal 互斥,必须先拆掉 bitmap。成功后 mdadm 会自动把阵列切回 read-write。等价做法是在建阵时用 --write-journal 指定 journal 设备,省去后续操作。
4. 9MB/s 与 write-through 假象
挂上 journal 后第一次峰值测试为 9MB/s,低于不挂 journal 的表现,也远低于 NVMe 速度。
该结果符合 write-through 模式的特征:journal 只记 intent,真正的写仍走 RAID6 RMW 路径,多一层簿记开销,因此更慢。查看:
cat /sys/block/md0/md/journal_mode当前模式不是 write-back。手动切换:
echo write-back > /sys/block/md0/md/journal_mode5. 更深的坑:缓冲不是产能
切到 write-back 后,短期峰值上升:journal 先吸收再排水,小随机写短暂贴近 journal 设备的吸收速度。
用户现场给出关键判断:write-back 下 journal 仍是「先吸收再排水」的缓冲。持续入写大于 HDD 落盘能力时,journal 会填满,填满后性能回到 HDD 原有水平。缓冲能削峰,不能增产。
监控数据与此一致:journal 采样时,吸收写为 2-24MB/s,排水读为 0。journal 未写满,压力不在 journal 容量侧,而在 HDD 侧的持续落盘能力。
6. 结论与边界
md journal 的价值是 write-hole 保护,以及让回写更接近全条带写、减少 RMW 惩罚。它不会把小随机写变成 NVMe 速度,小随机写的持续能力仍由 HDD 层决定。
真正削峰需要更大的缓存(如 1.2T bcache cache),前提是平均入写 < 平均落盘;否则再大的缓存也只是延后崩溃点。本项目最终放弃 journal,重建 RAID10。
复盘要点
- 测 journal 先确认
journal_mode=write-back,否则测到的是 write-through 的 9MB/s 假象 - 区分「峰值吸收」和「持续排水」两个指标:峰值看 journal 吸收速度,持续看 HDD 落盘速度
- 任何缓冲类方案都先算「平均入写 vs 平均落盘」这笔账:入写长期大于落盘,缓冲必满,满了就打回原形
- md journal 的价值是 write-hole 保护 + 让回写更接近全条带写,不是把小随机写变成 NVMe 速度
- 加 journal 的姿势:仅 RAID5/6、阵列 readonly、bitmap 与 journal 互斥