Booting Linux to a Ram Disk

Yeah! I just got a linux machine to copy the whole system into a ramdisk and then boot from it. Talk about fast! Read on to find out how I did it.

Introduction:
My friend who owns A Byte Better Computers (www.byte-better.com) just built himself a new machine to play spades with. It has a 2.6 GHz Core 2 Duo, 4 x 500 GB SATA2 hard drives with 16 MB cache on each (2 TB total), DVD+R DL CD burn everything drive, floppy, and currently has 4 GB of RAM, soon to be upgraded to 8 GB. It currently runs Windows XP on one drive,and Gentoo linux on a second drive. The other two drives are for data. We thought about several RAID options, but for now they are all separate drives. So we thought to ourselves "We have this great system, how can we make it even faster? Ah! Run the OS from RAM!" So we decided to try it. While we were installing the OSes on the big box, I was using my laptop to build a prototype to work out the bugs. After a lot of research, much trial-and-error, and many hours I finally have the prototype working.

The basic idea is that GRUB boots a kernel with an initial ramfs image that creates a ramdisk, copies the whole system from the hard drive to the ramdisk, umounts the hard drive, and then boots linux from the ramdisk. The hard drive is free to be mounted in the ramdisk system to save files.


The system:

I happen to be using Gentoo and DSL, but this should work for any distribution with a 2.6 kernel because it does not use any gentoo or DSL specific tools. The box is a Compaq Presario 2500 with a 2.5 GHz Pentium 4-m, and 512 MB RAM. Since this machine does not have very much RAM, I installed DSL to a partition for the "Running in RAM system." Installed, DSL took up about 240 MB on the drive. I used gentoo to build the initial ramfs image (initrd) because the big machine is running gentoo.

The process:
In this section I will describe what I did to make this work. First I set up two linux systems, one with Gentoo and a 2.6 kernel, and the other with DSL installed to the hard drive. I wanted to do it with only one distro, but DSL does not come with a 2.6 kernel, so I did two different distros. Here is what you need on your 2.6 distro:

  • All the tools to recompile the kernel and the kernel source code
  • busybox
The 2.6 kernel has an option that allows you to link the initrd right into the kernel itself so you don't need a separate initrd file. It also has all the tools to generate the initrd, so this way is pretty convenient. First, you need to make sure busybox is compiled with all the options you need. Once it is compiled and installed, you need to make a file that will tell the what to put in your initrd image. I use the following setup and save it as /root/makefile. The makefile gets read by the /usr/src/linux/usr/gen_init_cpio program during the kernel compile process.

#
# Files needed for early userspace.
# Placed in the public domain.
#

dir /bin 0755 0 0
file /bin/busybox /bin/busybox 0755 0 0
slink /bin/sh /bin/busybox 0755 0 0
slink /bin/ash /bin/busybox 0755 0 0
slink /bin/[ /bin/busybox 0755 0 0
slink /bin/[[ /bin/busybox 0755 0 0
slink /bin/test /bin/busybox 0755 0 0
slink /bin/mount /bin/busybox 0755 0 0
slink /bin/umount /bin/busybox 0755 0 0
slink /bin/cat /bin/busybox 0755 0 0
slink /bin/echo /bin/busybox 0755 0 0
slink /bin/false /bin/busybox 0755 0 0
slink /bin/ls /bin/busybox 0755 0 0
slink /bin/mountpoint /bin/busybox 0755 0 0
slink /bin/mkdir /bin/busybox 0755 0 0
slink /bin/sed /bin/busybox 0755 0 0
slink /bin/true /bin/busybox 0755 0 0
slink /bin/tr /bin/busybox 0755 0 0
slink /bin/wc /bin/busybox 0755 0 0
dir /sbin 0755 0 0
slink /sbin/mdev /bin/busybox 0755 0 0
slink /sbin/fsck /bin/busybox 0755 0 0
slink /sbin/fsck.ext2 /bin/busybox 0755 0 0
slink /sbin/fsck.ext3 /bin/busybox 0755 0 0
slink /sbin/switch_root /bin/busybox 0755 0 0
file /init /root/init 0755 0 0

# supporting directories
dir /proc 0755 0 0
dir /sys 0755 0 0
dir /mnt 0755 0 0
dir /hd 0755 0 0
dir /etc 0755 0 0
file /etc/fstab /root/fstab 0644 0 0

# initial device files required
dir /dev 0755 0 0
nod /dev/console 0600 0 0 c 5 1
nod /dev/null 0666 0 0 c 1 3
nod /dev/hda 0660 0 6 b 3 0
nod /dev/tty 0666 0 5 c 5 0
nod /dev/hda1 0660 0 0 b 3 1
nod /dev/hda2 0660 0 0 b 3 2
nod /dev/hda3 0660 0 0 b 3 3

Unfortunately, all my files for this project have been corrupted somehow, so I can't finish the article for now. Perhaps I will recreate the project and then post it here.

Comments

Popular posts from this blog

iChat IRC transport with OpenFire and Kraken

Save kerberos password in keychain for use with kinit on MacOS (was OS X) for use with network drives

Recording the iPhone screen and Mac screen at the same time in one video