技术知识库

CONFIG_BLK_DEV_INITRD 与 initramfs

CONFIG_BLK_DEV_INITRD 与 initramfs

摘要

CONFIG_BLK_DEV_INITRD 决定内核是否支持接收并加载由 bootloader 或 QEMU 单独传入的 initramfs/initrd。它不是 BusyBox 的配置,也不负责生成根文件系统;它让内核具备“打开外部启动包”的能力。使用 QEMU 的 -initrd rootfs.cpio.gz 时需要启用它。

为什么内核需要根文件系统

内核启动完成后只提供进程、内存、驱动、文件系统等机制,本身没有 sh、ls、mount 等用户空间程序。为了进入可操作的 Linux 环境,内核需要一个根目录 /,并从中执行第一个用户空间程序。对于 initramfs,这个程序通常是 /init,它成为 PID 1。

BusyBox 提供 /bin/sh 和大量基础命令;将 BusyBox、软链接、目录和 /init 打包后,就得到最小 initramfs。

启动链路

QEMU
  ├─ -kernel Image          → 把 ARM64 内核放入内存
  └─ -initrd rootfs.cpio.gz → 把 BusyBox CPIO 包放入内存
             ↓
Linux 内核启动
             ↓
CONFIG_BLK_DEV_INITRD=y:识别外部 initramfs
             ↓
gzip 解压(需要 CONFIG_RD_GZIP=y)
             ↓
CPIO 内容展开到内存中的 rootfs
             ↓
执行 /init(或 rdinit= 指定的程序)
             ↓
进入 BusyBox shell

is not set 的含义

.config 中:

# CONFIG_BLK_DEV_INITRD is not set

不是报错,而是 Kconfig 表示布尔选项关闭的标准写法,等价于“功能未编进内核”。启用后变为:

CONFIG_BLK_DEV_INITRD=y

在 Linux 5.0 源码中,init/Kconfig 将它描述为 Initial RAM filesystem and RAM disk (initramfs/initrd) support。usr/Kconfig 中的 CONFIG_RD_GZIP 依赖此选项,并负责解压 gzip 格式的 ramdisk/CPIO 数据。

外部与内置 initramfs

  • 外部方式:根文件系统是单独的 rootfs.cpio.gz,由 QEMU/bootloader 传入;便于反复修改 BusyBox 内容而不重编内核。
  • 内置方式:通过 CONFIG_INITRAMFS_SOURCE 把目录或 CPIO 编进 Image;部署文件少,但每次修改根文件系统都要重新构建内核。

当前实验选择外部方式,因此需要 CONFIG_BLK_DEV_INITRD=y。

2026-08-29 的对照实验进一步验证了内置方式:将 BusyBox 安装树配置为 CONFIG_INITRAMFS_SOURCE 后,ARM64 Image 增加约 1.125 MiB;QEMU 完全省略 -initrd 仍成功执行 /init 并进入 PID 1 shell。详见 将 BusyBox initramfs 内置到 Linux 5.0 ARM64 Image。

源码证据

  • init/Kconfig:1082:定义 CONFIG_BLK_DEV_INITRD。
  • usr/Kconfig:55:CONFIG_RD_GZIP 依赖 BLK_DEV_INITRD。
  • init/initramfs.c:602:populate_rootfs() 解包内置 initramfs,并在存在时解包 bootloader 提供的 initrd/initramfs。
  • init/main.c:360:注册 rdinit= 内核命令行参数。

关联