内核升级后 dracut “Don‘t know how to handle ’root='” 的模块缺失补救

9次阅读

根本原因是initramfs未打包处理root=参数所需的模块,因内核升级后dracut默认裁剪了NVMe/RaiD/LVM/DM等驱动,需显式指定–modules重生成并验证parse-root.sh存在。

内核升级后 dracut “Don‘t know how to handle ’root='” 的模块缺失补救

dracut 报错 “Don’t know how to handle ‘root='” 的根本原因

这个错误不是 grub 配置写错了,而是 initramfs 里压根没打包处理 root= 参数所需的模块。内核升级后,dracut 默认生成的 initramfs 可能跳过了某些关键驱动或解析逻辑——尤其当新内核启用了 CONFIG_BLK_DEV_NVMECONFIG_MD_RAID* 或 LVM/DM 加密子系统,但 dracut 没被明确告知要包含对应模块时。

典型触发场景包括:从老内核(如 5.15)升到新内核(如 6.8+),且 root 分区在 NVMe 设备、RAID 阵列或 LUKS 容器中;或者系统启用了 rd.lvm=0rd.md=0 这类禁用标志,导致 dracut 主动裁剪了相关模块。

补救:强制重生成 initramfs 并显式启用必需模块

别直接跑 dracut -f——它会沿用旧的配置缓存和裁剪策略。必须显式声明 root 设备类型和依赖模块:

  • 先确认 root 所在设备类型:findmnt / | awk '{print $2}' 看是否为 /dev/nvme0n1p2/dev/md0/dev/mapper/vg0-root
  • 根据设备类型加参数重生成:
    – NVMe root:dracut -f --regenerate-all --force --kver $(uname -r) --modules "nvme base"
    – LVM root:dracut -f --regenerate-all --force --kver $(uname -r) --modules "lvm base"
    – RAID root:dracut -f --regenerate-all --force --kver $(uname -r) --modules "mdraid base"
    – LUKS root:dracut -f --regenerate-all --force --kver $(uname -r) --modules "crypt lvm base"
  • 确保 /etc/dracut.conf.d/ 下没有冲突配置(比如某文件写了 omit_drivers+="nvme"

验证 initramfs 是否真包含了 root 解析能力

光看 dracut 输出“Done”不保险。得进 initramfs 里查实际内容:

  • 解包当前 initramfs:mkdir /tmp/initramfs && cd /tmp/initramfs && zcat /boot/initramfs-$(uname -r).img | cpio -id
  • 检查关键文件是否存在:
    ls usr/lib/dracut/modules.d/ | grep -E "(nvme|lvm|mdraid|crypt)"(应有对应目录)
    grep -r "root=" usr/lib/dracut/modules.d/*/parse-root.sh 2>/dev/null(必须有至少一个匹配)
  • 若缺失 parse-root.sh,说明模块未正确加载——此时需检查内核 config 中对应功能是否编译为 m(模块)而非 y(内置),因为 dracut 只打包 m 类型的驱动

GRUB 启动参数与 dracut 模块的协同要求

dracut 模块只是“能处理”,但能否真正识别 root,还取决于 GRUB 传参格式和内核支持是否对齐:

  • root=UUID=xxx 是最稳妥的写法;避免用 root=/dev/sda2(设备名在 initramfs 中可能未就绪)
  • 若用 LVM,必须同时加 rd.lvm.vg=vg0(否则 dracut 不主动扫描该卷组)
  • 若用 LUKS,rd.luks.uuid=xxx 必须与 cryptdevice 参数一致,且 rd.luks.options=allow-discards 等额外选项不能拼错
  • 新内核(6.6+)默认启用 init_on_alloc=1,可能导致某些老旧 dracut 版本(init_on_alloc=0

最易被忽略的是:内核升级后,/lib/modules/$(uname -r) 下的 modules.builtinmodules.order 文件可能不全,导致 dracut 无法推导依赖链。遇到反复失败,先运行 depmod -a $(uname -r) 再重试 dracut。

text=ZqhQzanResources