(Should work in CentOS / RHEL or any system using dracut too)
http://reboot.pro/topic/14547-linux-load-your-root-partition-to-ram-and-boot-it/
https://forums.centos.org/viewtopic.php?t=46678
- Fedora 33 on external HDD with /home and /boot/efi as separate mountpoints and formatted in BTRFS.
- Kernel 5.9.14-200.fc33.x86_64
- 24 GB RAM
- SELinux enforced
https://people.redhat.com/harald/dracut.html#id537497
https://fedoraproject.org/wiki/How_to_debug_Dracut_problems
https://man7.org/linux/man-pages/man7/dracut.bootup.7.html
https://www.amazon.com/Hands-Booting-Learn-Process-Windows/dp/1484258894
Any source that explains how systemd works
Make a backup of the following paths content:
/boot/loader/entries
/usr/lib/dracut/modules.d/
/usr/lib/dracut/modules.d/45ifcfg/
Files:
/etc/selinux/config
/etc/fstab
A backup of your actual initramfs might come handy, it should be located under /boot and looks like this:
initramfs-<KERNEL_VERSION>.img (e.g. initramfs-5.9.14-200.fc33.x86_64.img)
- Change the line specifying the root partition in /etc/fstab to:
none / tmpfs defaults 0 0
Now we have to take advantage of the pre-privot hooks
- Navigate to
/usr/lib/dracut/modules.d/45ifcfg/
and add a new script calledbootram.sh
with the following content:
#!/usr/bin/sh
type getarg >/dev/null 2>&1 || . /lib/dracut-lib.sh
type det_fs >/dev/null 2>&1 || . /lib/fs-lib.sh
#Load to RAM
umount "$NEWROOT"
mkdir /ramboottmp
mount -t <ROOTFS> -o <FLAGS> "${root#block:}" /ramboottmp
mount -t tmpfs -o size=<ROOTFS + 20%> none "$NEWROOT"
cd "$NEWROOT"
cp -rfa /ramboottmp/* "$NEWROOT"
umount /ramboottmp
- In a separate window, open your backup /etc/fstab. In
bootram.sh
, replace ROOTFS and FLAGS with your previous root system entry options. Mine used to look like this:
UUID=0fe781fd-4c2d-4096-9622-b3e7eb30f10c / btrfs subvol=root 0 0
I replaced ROOTFS with btrfs and FLAGS with subvol=root, so now the script line is:
mount -t btrfs -o subvol=root "${root#block:}" /ramboottmp
- Calculate the size of your / . I used
ncdu
for this. Modify ROOTFS + 20% with a reasonable space. My root occupies about 6.5GB, so now my script looks like this:
mount -t tmpfs -o size=8G none "$NEWROOT"
You are free to give as much memory as you want. Just make sure you give the system at least 4GB of addressable RAM. Or whatever keeps your system stable.
- Save your changes. In the same directory you will find a
module-setup.sh
. Edit the following inside:
install() {
inst_binary awk
inst_hook pre-pivot 85 "$moddir/write-ifcfg.sh"
}
to
install() {
inst_binary awk
inst_hook pre-pivot 84 "$moddir/bootram.sh"
inst_hook pre-pivot 85 "$moddir/write-ifcfg.sh"
}
- Generate the new initramfs. In your Terminal, execute:
sudo dracut --fstab --add-fstab /etc/fstab -f /boot/initramfs-ramboot-<CURRENT_KERNEL>.img
where CURRENT_KERNEL is the output of uname -r
. In my case:
sudo dracut --fstab --add-fstab /etc/fstab -f /boot/initramfs-ramboot-5.9.14-200.img
- Open your bootloader entries folder in /boot/loader/entries/. There should be a couple of entries already. Find the one with your current boot option. Save it under a different name in the same folder and update its initrd:
My original entry:
title Fedora (5.9.14-200.fc33.x86_64) 33 (Xfce)
version 5.9.14-200.fc33.x86_64
linux /root/boot/vmlinuz-5.9.14-200.fc33.x86_64
initrd /root/boot/initramfs-5.9.14-200.fc33.x86_64.img
options root=UUID=XXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXX ro rootflags=subvol=root resume=UUID=f1ac06be-a2a3-46e5-9b6e-7a8d59f3bf7e rhgb quiet
grub_users $grub_users
grub_arg --unrestricted
grub_class kernel
New modified entry:
title Fedora-To-RAM (5.9.14-200.fc33.x86_64) 33 (Xfce)
version 5.9.14-200.fc33.x86_64
linux /root/boot/vmlinuz-5.9.14-200.fc33.x86_64
initrd /root/boot/initramfs-ramboot-5.9.14-200.fc33.x86_64.img
options root=UUID=XXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXX ro rootflags=subvol=root resume=UUID=f1ac06be-a2a3-46e5-9b6e-7a8d59f3bf7e selinux=0
grub_users $grub_users
grub_arg --unrestricted
grub_class kernel
If you care about SELinux: Notice how I appended selinux=0
at the end of the options line? The magic of this trick is any change will not be permanent, so any policy you specify on the kernel command line is going vanish after rebooting. No need of relabeling either!
(You can either set selinux=0 or enforcing=0. Unfortunately you cannot use SELinux in enforced mode with this method)
-
Revert
module-setup.sh
in/usr/lib/dracut/modules.d/45ifcfg/
to its original state (copy from backup). -
Save and reboot. You should now see a new entry in GRUB. If everything was successful, the system will take a while to load since it will start copying your root filesystem to the newly created tmpfs.