在嵌入式设备上,使用ramfs出现内核死机: 无法挂载根文件系统

3

我正在处理运行Linux(内核版本为3.10)的嵌入式ARM设备,并使用NAND存储器进行存储。我正在尝试构建一个迷你版Linux系统,该系统将驻留在其自己的分区中,并执行主固件的更新。

内核使用非常小的根文件系统,该文件系统存储在ramfs中。但是,我无法使其启动。我遇到了以下错误:

[    0.794113] List of all partitions:
[    0.797600] 1f00             128 mtdblock0  (driver?)
[    0.802669] 1f01            1280 mtdblock1  (driver?)
[    0.807697] 1f02            1280 mtdblock2  (driver?)
[    0.812735] 1f03            8192 mtdblock3  (driver?)
[    0.817761] 1f04            8192 mtdblock4  (driver?)
[    0.822794] 1f05            8192 mtdblock5  (driver?)
[    0.827820] 1f06           82944 mtdblock6  (driver?)
[    0.832850] 1f07           82944 mtdblock7  (driver?)
[    0.837876] 1f08           12288 mtdblock8  (driver?)
[    0.842906] 1f09           49152 mtdblock9  (driver?)
[    0.847928] No filesystem could mount root, tried:  squashfs
[    0.853569] Kernel panic - not syncing: VFS: Unable to mount root fs on unknown-block(1,0)
[    0.861806] CPU: 0 PID: 1 Comm: swapper Not tainted 3.10.73 #11
[    0.867732] [<800133ec>] (unwind_backtrace+0x0/0x12c) from [<80011a50>] (show_stack+0x10/0x14)
(...etc)

根文件系统是通过构建过程构建的,使用以下内容(为了清晰起见进行了简化):
# [Copy some things to $(ROOTFS_OUT_DIR)/mini_rootfs]
cd $(ROOTFS_OUT_DIR)/mini_rootfs && find . | cpio --quiet -o -H newc > $(ROOTFS_OUT_DIR)/backup.cpio
gzip -f -9 $(ROOTFS_OUT_DIR)/backup.cpio

这将创建 $(ROOTFS_OUT_DIR)/backup.cpio.gz。
然后按照以下方式构建内核:
@$(MAKE) -C $(LINUX_SRC_DIR) O=$(LINUX_OUT_DIR) \
             CONFIG_INITRAMFS_SOURCE="$(ROOTFS_OUT_DIR)/backup.cpio.gz" \
             CONFIG_INITRAMFS_ROOT_UID=0 CONFIG_INITRAMFS_ROOT_GID=0

我认为这意味着它使用与主固件相同的配置(在其他地方构建),但使用CONFIG_INITRAMFS_SOURCE提供最小的ramfs映像。根据Kernel.Org,始终会构建ramfs,并且只需要CONFIG_INITRAMFS_SOURCE指定预先制作的根文件系统即可。没有构建错误来指示创建ramfs时存在问题,生成的内核大小看起来正常。backup.cpio.gz约为3.6 MB;最终的zImage为6.1 MB;镜像写入大小为8 MB的分区。要使用此映像,我设置了一些标志,用于告诉(自定义) 启动加载程序从最小分区引导,并为内核设置不同的命令行。这是用于引导的命令行:
console=ttyS0 rootfs=ramfs root=/dev/ram rw rdinit=/linuxrc mem=220M

请注意,最小根文件系统包含“/linuxrc”,其实是指向“/bin/busybox”的符号链接。
lrwxrwxrwx  1 root root   11 Nov  5  2015 linuxrc -> bin/busybox

为什么这个启动不了呢?为什么它尝试使用"squashfs"文件系统,这样做是否有误?

PS:我阅读了这篇文章:http://www.linuxquestions.org/questions/linux-embedded-and-single-board-computer-78/no-filesystem-could-mount-root-873864/,并确认在配置文件中设置了CONFIG_BLK_DEV_INITRD=y和CONFIG_RD_GZIP=y。 - Jeremy
1
你不应该在命令行中指定 rootfs=。一个正确配置的内核总是会使用一个正确附加的 initramfs(并忽略任何 rootfs= 参数)。你不需要压缩 cpio 归档,因为它会在 zImage 中再次被压缩。我很久以前就手动构建了一个 initramfs,并将其与内核合并。现在有了 Buildroot,这就是我使用的工具。 - sawdust
@sawdust 我从cmdline参数中删除了"rootfs=ramfs",但是我仍然得到相同的错误。 - Jeremy
1
“但是我仍然得到同样的错误”——一点也不奇怪。你的initramfs出了问题,导致内核忽略了它。根据文档,在initramfs中必须找到“/init”程序文件,否则内核会去寻找根分区。 - sawdust
1
不要使用 rootfs=ramfs root=/dev/foobar rw,而是需要传递 rootfstype=ramfs。确保已启用所有必要的内核选项。此外,rdinit=/something_standard 是多余的。 - 0andriy
1个回答

1
已解决! 原来是由于(自定义)构建系统使用的文件名在更新中发生了更改,因此它没有将正确的内核映像放入固件包中。实际上,我试图使用“rootfs=ramfs”参数引导错误的内核,其中没有ramfs。
因此,供以后参考,如果您指定了“rootfs=ramfs”,但您的内核没有构建任何内置的rootfs(未指定CONFIG_INITRAMFS_SOURCE=...),则会出现此错误。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接