Unlike the initrd
, Linux does not allow to unmount the initramfs
. Apparently this helped keep the kernel code simple.
Instead of pivot_root
, you can use the switch_root
command. It implements the following procedure. Notice that switch_root
deletes all the files on the old root, to free the initramfs memory, so you need to be careful where you run this command.
initramfs is rootfs: you can neither pivot_root
rootfs, nor unmount it. Instead delete everything out of rootfs to
free up the space (find -xdev / -exec rm '{}' ';'), overmount rootfs
with the new root (cd /newmount; mount --move . /; chroot .), attach
stdin/stdout/stderr to the new /dev/console, and exec the new init.
Note the shell commands suggested are only rough equivalents to the C code. The commands won't really work unless they are all built in to your shell, because the first command deletes all the programs and other files from the initramfs :-).
Rootfs is a special instance of ramfs (or tmpfs, if that's enabled), which is always present in 2.6 systems. You can't unmount rootfs for approximately the same reason you can't kill the init process; rather than having special code to check for and handle an empty list, it's smaller and simpler for the kernel to just make sure certain lists can't become empty.
https://github.com/torvalds/linux/blob/v4.17/Documentation/filesystems/ramfs-rootfs-initramfs.txt