为什么在 initrd 和 initramfs 中使用 nash 而不是 busybox?
我只是想了解两者的优缺点(以及具有类似功能的其他应用程序)。我目前倾向于 busybox 是更好的选择,但我不禁想知道为什么 redhat 和 fedora 在他们的 initrd 中使用 nash。
这纯粹是出于商业原因,还是技术原因?
谢谢,Chenz
答案1
Busybox 似乎更多才多艺的。我以前曾将其用于 initrd。您可以选择只编译几个应用程序或编译大量应用程序,具体取决于您在初始启动阶段需要多少功能。这允许您在启动阶段自定义很多东西。
答案2
事实证明,“nash”在幕后做了很多“事情”,而使用“busybox”一体机时,您必须自己完成大部分艰苦的工作。就我而言,我们有一个自定义 Centos-5 内核,它必须启动到无盘(root-on-nfs)环境,以及带有 Sata、SAS、MPT raid 控制器、Megaraid* 等附加磁盘的基于磁盘的系统。内核配置是如此自定义,以至于标准 RH/Centos .spec 构建过程在尝试处理它并构建内核 RPM 时会出错。我大量破解了分布式 .spec 文件以解决这些问题,而这本身就是一个大问题。在尝试恢复到尽可能标准的内核时,我做了以下事情,并遇到了许多问题,我将描述其中一些问题-
a) 使用 busybox 和 initramfs 进行网络启动
这很好用。我的 initramfs.cpio 存档包含静态链接的 bb、lvm 和自定义轻量级 dhcp 客户端,以及该系统将使用系统 BIOS PXE 启动代码启动的所有以太网驱动程序。NFS 客户端模块(sunrpc、nfs、lockd 等)也在 cpio 存档中,并由 bb 加载。注意:在我拥有的戴尔系统上,通过 PXE/TFTP 启动的 vmlinuz 映像的大小限制为 8MB。该过程是加载列表中的驱动程序,直到出现 eth0,然后运行 dhcp 客户端以获取 IP 地址、网络掩码、主机名和网关。然后启动网络,通过“nfsroot=server:remote-root-fs”命令行参数指定的根 f/s 将 NFS 安装到 rootfs (/newroot) 中的目录上,然后使用“switch_root -c /dev/console /newroot /sbin/init”从 initramfs 传输到基于 NFS 的根 f/s。
这里唯一的区别是我提供了一个 cpio 存档来构建到内核中。在其他所有方面,内核映像和模块都由 RH/Centos 提供。所有可以构建为模块的东西(几乎所有东西)都是如此!
b) 通过 initramfs 和 nash 进行磁盘启动
为什么在启动到本地(无 iSCSI/FC/等)附加磁盘或 raid/LVM 设置时要从 busybox 切换到“nash”。简单的答案是,我无法弄清楚仅使用 bb 完成这项工作的方法,因此我的 cpio 存档还包括 nash 二进制文件以及简化的 init.nash 启动脚本。一旦我确定我们不是通过网络启动(内核命令行中没有“nfsroot=...”),我只需加载相应的模块,然后“执行”nash 脚本并让它完成启动的最后阶段。我无法弄清楚如何使用 busybox 复制 nash 所做的部分是:
项目清单
- mkrootdev -t ext3 -o defaults,ro /dev/VolGroup00/NAS_ROOTFS
- echo 挂载根文件系统。
- 挂载/sysroot
- echo 设置其他文件系统。
- 设置root
- echo 切换到新的根并运行 init。
- 根交换机
特别是,最后两个 nash 内置命令“setuproot”和“switchroot”做了一些我无法复制的事情,尽管我尝试过。特别是,如果我忽略“setuproot”所做的工作并执行我认为应该做的事情(为 /sysroot 挂载创建一个 fstab 条目,将任何逻辑卷/设备映射器信息从 /dev -> /sysroot/dev 传输等),然后执行“switch_root /sysroot /sbin/init”,它似乎可以工作,但一旦 rc.sysinit 进入处理启动命令的捷径,它就会崩溃。在紧急 shell 中,我看到“/dev/mapper/”除了控制文件外是空的,并且通常具有指向 /dev/mapper/ 中的 LVM 设备节点的软链接的“/dev/VolGroup00/”目录已完全消失。我不知道为什么这种情况会发生在 busybox 上而不会发生在 nash 上,目前我只能执行一个最小的 nash 脚本来执行最后的 setuproot 和 switchroot 到真实磁盘根 f/s 的操作。