Rocky Linux / RHEL 9/10 使用 grubby 管理内核启动参数(关闭 IOMMU)
适用系统:Rocky Linux 9/10、RHEL 9/10、AlmaLinux 9/10、CentOS Stream 9/10
一、背景知识
1.1 什么是 IOMMU?
IOMMU(Input-Output Memory Management Unit)是设备直接内存访问(DMA)的地址翻译与保护单元,Intel 平台对应 VT-d(内核日志中表现为 DMAR),AMD 平台对应 AMD-Vi。
| 场景 | 是否需要关闭 IOMMU |
|---|---|
| 普通物理机、虚拟机宿主 | ❌ 保持开启(安全性更好) |
| 旧硬件兼容性问题 | ✅ 考虑关闭 |
| 某些 PCIe 直通 / GPU 透传异常 | ✅ 临时关闭调试 |
| 性能敏感且无虚拟化需求 | ⚠️ 评估后决定 |
1.2 为什么要用 grubby 而不是改配置文件?
在 RHEL 8 之前,修改内核参数的标准做法是编辑 /etc/default/grub 后执行 grub2-mkconfig 重新生成引导配置。而在 RHEL 9/10 系列中,官方推荐直接使用 grubby:
flowchart LR
subgraph 传统方式["传统方式(步骤多、易出错)"]
A[编辑<br>/etc/default/grub] --> B[grub2-mkconfig<br>重新生成配置] --> C[重启生效]
end
subgraph grubby方式["grubby 方式(直接、安全)"]
D[grubby --update-kernel<br>一条命令] --> E[重启生效]
end
核心优势:
- ✅ 直接修改 BTF / BLS(Boot Loader Specification)条目,无需重新生成引导配置;
- ✅ 自动适配 BIOS/Legacy 与 UEFI 的引导配置路径差异(无需记忆
grub.cfg到底在/boot/grub2/还是/boot/efi/EFI/rocky/); - ✅ 支持精确到单个内核条目或全部内核的操作,可脚本化;
- ✅ 配合
--remove-args可干净回滚。
1.3 关键参数说明
| 参数 | 作用 | 适用平台 |
|---|---|---|
intel_iommu=off |
关闭 Intel VT-d | Intel |
amd_iommu=off |
关闭 AMD-Vi | AMD |
iommu=off |
彻底禁用 IOMMU 子系统(一刀切,影响面大) | 通用 |
iommu=pt |
直通模式:仅对直通设备启用 IOMMU(折中方案,推荐优先尝试) | 通用 |
⚠️ 建议:生产环境优先尝试
iommu=pt(直通模式),既保留安全性又避免翻译开销;确认无需求后再考虑完全关闭。
二、操作前检查
# 1. 确认系统中有多个可回退的内核条目(防止改错后无法启动)
sudo grubby --info=ALL | grep -E "^(index|title|kernel)="
# 2. 查看当前正在运行的内核及其启动参数
uname -r
cat /proc/cmdline
# 3. 确认当前 IOMMU 状态(有 DMAR / AMD-Vi 输出即为开启)
sudo dmesg | grep -i -E "iommu|DMAR|AMD-Vi"
💡 安全原则:操作前确保系统至少保留 2 个内核条目,万一新参数导致无法启动,可在 GRUB 菜单中选择旧内核进入系统后回滚。
三、使用 grubby 关闭 IOMMU(完整流程)
3.1 流程总览
flowchart TD
S([开始]) --> A["① 查看当前内核参数<br>cat /proc/cmdline"]
A --> B["② 添加关闭 IOMMU 参数<br>grubby --update-kernel=ALL --args='...'"]
B --> C["③ 验证参数已写入<br>grubby --info"]
C --> D["④ 重启系统<br>reboot"]
D --> E["⑤ 验证运行时生效<br>cat /proc/cmdline + dmesg"]
E --> F{IOMMU 已关闭?}
F -- 是 --> G([✅ 完成])
F -- 否 --> H[检查是否漏改内核 /<br>GRUB 菜单选择错误] --> B
3.2 步骤详解
① 查看当前内核启动参数
# 方式一:查看运行时生效的参数
cat /proc/cmdline
# 方式二:查看当前内核条目的完整配置(args 行即启动参数)
sudo grubby --info /boot/vmlinuz-$(uname -r)
# 方式三:查看所有内核条目
sudo grubby --info=ALL
② 添加关闭 IOMMU 的参数
# Intel + AMD 平台参数同时写入(保留对应项即可,多余的参数无害)
sudo grubby --update-kernel=ALL --args="intel_iommu=off amd_iommu=off"
# 或者:彻底禁用 IOMMU 子系统
sudo grubby --update-kernel=ALL --args="iommu=off"
参数说明:
--update-kernel=ALL—— 修改所有已安装内核的条目,保证切换旧内核时参数依然生效;--update-kernel=DEFAULT—— 只修改默认启动的内核,适合临时调试;--update-kernel=/boot/vmlinuz-<版本>—— 精确修改指定内核。
③ 验证参数已添加(重启前)
sudo grubby --info /boot/vmlinuz-$(uname -r) | grep args
输出示例(注意末尾已出现新参数):
args="ro crashkernel=1G-4G:192M,4G-64G:256M,64G-:512M resume=/dev/mapper/rl-swap rd.lvm.lv=rl/root rd.lvm.lv=rl/swap rhgb quiet intel_iommu=off amd_iommu=off"
④ 重启系统
sudo reboot
⑤ 验证生效(重启后)
# 确认参数已进入运行时内核命令行
cat /proc/cmdline
# 确认 IOMMU 已被禁用:无 DMAR / AMD-Vi 初始化输出即为成功
sudo dmesg | grep -i -E "iommu|DMAR|AMD-Vi"
✅ 成功标志:dmesg 中不再出现 DMAR: Host address width ...(Intel)或 AMD-Vi: ...(AMD)初始化日志。
四、grubby 常用操作速查表
| 操作 | 命令 |
|---|---|
| 查看默认内核索引 | sudo grubby --default-index |
| 查看默认内核路径 | sudo grubby --default-kernel |
| 查看所有内核条目 | sudo grubby --info=ALL |
| 查看指定内核条目 | sudo grubby --info /boot/vmlinuz-<版本> |
| 给所有内核加参数 | sudo grubby --update-kernel=ALL --args="参数" |
| 只给默认内核加参数 | sudo grubby --update-kernel=DEFAULT --args="参数" |
| 移除参数(回滚) | sudo grubby --update-kernel=ALL --remove-args="参数" |
| 设置默认启动内核 | sudo grubby --set-default /boot/vmlinuz-<版本> |
⚠️
--remove-args必须与添加时的参数值完全一致(包括=和值),否则无法匹配移除。
五、grubby vs 手动编辑配置对比
| 维度 | grubby | 手动编辑 /etc/default/grub + grub2-mkconfig |
|---|---|---|
| 操作步骤 | 一条命令 | 编辑文件 + 重新生成配置 + 重启 |
| UEFI/BIOS 路径差异 | 自动处理 | 需手动区分 grub.cfg 路径 |
| 粒度控制 | 可精确到单个内核 | 对所有内核统一生效 |
| 参数管理 | 分散在各内核条目中 | 集中在一处,可读性好 |
| 回滚 | --remove-args 一键回滚 |
需再次编辑并重新生成 |
| 脚本化 / 自动化 | ✅ 友好 | ❌ 繁琐 |
| 误操作风险 | 低 | 较高(配置写错可能导致无法启动) |
结论:在 Rocky / RHEL 系列中,优先使用 grubby 修改内核参数;仅当需要统一管理大量参数或维护多发行版通用配置时,才考虑手动编辑方式。
六、故障排查(Troubleshooting)
| 现象 | 可能原因 | 解决方法 |
|---|---|---|
| 重启后参数未生效 | 只改了默认内核,实际启动的是其他内核 | grubby --info=ALL 检查各条目,用 --update-kernel=ALL 统一修改 |
cat /proc/cmdline 有参数但 dmesg 仍有 DMAR |
参数写法错误(如 iommu=0) |
确认使用 =off 而不是 =0/=false |
--remove-args 移除失败 |
参数值与添加时不一致 | 先用 grubby --info 查看当前 args 的准确值 |
| 系统无法启动 | 参数与其他配置冲突 | 在 GRUB 菜单按 e 编辑启动项临时删除参数进入系统,再执行回滚命令 |
七、学习笔记与最佳实践
- 先小范围测试,再全量应用:新参数先用
--update-kernel=DEFAULT验证稳定,再--update-kernel=ALL铺开; - 保留回退路径:操作前确认存在 ≥2 个内核条目;
- 优先折中方案:IOMMU 问题优先尝试
iommu=pt,而非直接iommu=off; - grubby 修改即时写入 BLS 文件(
/boot/loader/entries/*.conf),可查看该目录辅助排查; - 自动化场景(Ansible / Kickstart 脚本)中优先使用 grubby,保证幂等性。
八、参考链接
- RHEL 8 官方文档 — 在 GRUB 菜单条目中添加和删除参数
- RHEL 10 官方文档 — 使用 GRUB 配置文件更改引导条目
- Linux Kernel Parameters 文档:`Documentation/admin-guide/kernel-parameters.txt

浙公网安备 33010602011771号