Overlay Filesystem on Raspi



Embedded systems should be resilient. I mean really resilient. They need to survive power cycles, accidental power loss, harsh environments and a lot of other unexpected stuff. In this regard SD card used by Raspberry Pi can be a little problematic. Especially since there are a lot of "useless"  write operations that can be avoided, thus significantly prolonging memory card's life. Following on that, a read-only filesystem on Raspbian can be configured as there is already support for the Overlay Filesystem since the kernel version 3.18.8.

Let's get down to bussiness. I am working on Raspi 2, running the following kernel.

pi@raspberrypi:~$ uname -a
Linux raspberrypi 4.1.13-v7+ #826 SMP PREEMPT Fri Nov 13 20:19:03 GMT 2015 
armv7l GNU/Linux

Overlay Filesystem must be loaded at boot time, therefore we need to build Initial Ramdisk Filesystem (initramfs) image & enable it. Luckily support for this is also included in the kernel :-) First we add needed modules to the config.

# install initramfs tools if needed
apt-get install initramfs-tools
# Add the folowing lines at the bottom of /etc/initramfs-tools/modules
# Use your preffered text editor
# overlay filesystem

Next, we need to add the bash script that will mount root filesystem as read-only to the initramfs. The script should also load overlays to the appropriate mount points and create directories if needed. Now, we could invent the square wheel here, but I have tested this script here and it works like a charm. Let's include it in the initramfs directory structure.

# let's say you downloaded from the link above to the home directory 
sudo cp root-ro.txt /etc/initramfs-tools/scripts/init-bottom/root-ro

Now we're ready to build initramfs image. The command below will create an image file in the /boot directory of your filesystem. The image will be built against the current running kernel version. The configured modules in the config file above must therefore be found in the current kernel module directory. In our case this is /lib/modules/4.1.13-v7+/kernel.

sudo mkinitramfs -o /boot/initrd.img-$(uname -r)

If you have come successfully so far, you're almost done. You might even take a break should you need one :-). Finally, we enable initramfs in the /boot/config.txt file. Just add at the bottom.

# initial ramdisk definition
initramfs initrd.img-4.1.13-v7+

At the same time, we must also add driver parameter to the kernel command line. I would also suggest adding a debug parameter for the initramfs.

# this is my /boot/cmdline.txt file
# debug parameter will create 
# /run/initramfs/initramfs.debug file
dwc_otg.lpm_enable=0 console=ttyAMA0,115200 console=tty1 root=/dev/mmcblk0p2
rootfstype=ext4 elevator=deadline rootwait root-ro-driver=overlay debug

Now do a reboot and you should be done. After a login, you should see a screen similar to this. Note the read-only root filesystem and the overlay type filesystem with appropriate parameters lowerdir and upperdir.