Moving from my hacked ReadyNAS to a Raspberry Pi

I used to have a hacked/rooted RNRX4000 (ReadyNAS 2100) in which I had replaced the original operating system with VoidLinux, having the boot partition on the integrated flash memory (100MB). Due to it being noisy and power-consuming, I wanted to replace it and found the solution in Argon40’s Argon EON, in which a Raspberry Pi is meant to manage SATA-drives connected to it over USB3.

Image disk.png

My initial plan was to use a ZFS setup on the Pi, but I quickly realized that this would be a problem. Specifically, ZFS is incompatible with the latest kernel version of the Raspberry Pi OS. I could, of course, have chosen another distribution with an older kernel version, or have locked the release of the kernel in the packet manager. But having this issue early on with the knowledge of being forced to manage kernel releases manually and at the same time being aware of security concerns of not running updated kernels made me think of other solutions.

So, why not run a simple md solution using the kernel module dm-integrity for detection and mitigation of bit rot? Sounds simple, right? No! Every distribution for Raspberry Pi I looked at lacked any support for dm-integrity out of the box. So, it was either back to manual kernel management, including compiling with support for dm-integrity, or find another solution.

I think I have found a good enough solution. By using md for raid and redundancy together with internal and external backup using borg, I had a pretty solid solution for disk failure and historical archiving. I only lacked a solution for bit rot protection.

So, I did what I usually do and implemented my own solution instead. With the inspiration of the corruption detecting program shatag and its previous C-reimplemented alternative cshatag (now implemented in Go), I wrote acst, or the Actual C-implementation of a Simple shaTag. Well, it’s not really an implementation of shatag as I have chosen some alternative ways of implementing it. But it is simple and written in C, so there is that.

The idea is to have acst running on a scheduled basis, making sure to compute checksums of each and every file on the NAS and, at the same time, detect any change or corruption to the actual data. If any such corruption is detected, I can use borg to verify the corruption and, at the same time, ideally, restore the non-corrupted version of the file in question.

I also stumbled upon another problem as I had created and successfully assembled and mounted the raid system using mdadm. When restarting the NAS, one of the disks would never assemble. After some time, too much time in fact, I realised that the disk was too slow to be initialized before the operating system tried to assemble the raid set. The simple solution to this problem was to add a 5 second delay when booting using the /boot/cmdline.txt file. I just appended rootdelay=5 at the end of the command line for booting Linux and — voilà — both disks were now assembling correctly.

This is the story of me moving from a noisy and power hungry ReadyNAS to an arm-based Raspberry Pi, while at the same time writing the code for acst.