Current needs of my band for web storage turned us to hosting Nextcloud instance. I wanted to self-host it on my RPi4, my current home server. So, I configured it to use my SD card as storage, but it didn’t work out. SD card was too slow for usage as web storage. Then, I moved to B2 as a storage. And as you can see from the title, it didn’t work out as well. B2 turned out to be too clanky and unresponsive as primary storage for the Nextcloud instance.
That was the moment of my decision to buy an SSD. I bought a cheap 250GB Crucial 2.5″ SSD and a USB 3.0 to SATA 3 adapter (Unitek Y-1096). Whole purchase was under $50. There is no need for an external power outlet for the SSD. So, once I got home, I plugged it right away into the RPi4.
At the start I confirmed that the SSD is visible at the OS level.
$ sudo fdisk -l Disk /dev/sda: 223.57 GiB, 240057409536 bytes, 468862128 sectors Disk model: 00SSD1 Units: sectors of 1 * 512 = 512 bytes Sector size (logical/physical): 512 bytes / 512 bytes I/O size (minimum/optimal): 512 bytes / 33553920 bytes Disklabel type: dos Disk identifier: 0xeb8a9682 # The rest of the output is removed by me, because it was too long.
Usually, after connecting new disk to the Linux device, it is visible as a file in
/dev directory is special place for devices and device files in Linux systems. Disk devices usually get a name like
sdc, etc. As a funny example of how it works: If you have a USB connected speakers, you can send an file directly to a device file of your speakers. It will, of course, play some sound.
Prepare partition table
To format the disk before using, it has to get a partition table. I’m used to use
fdisk tool for that purpose.
$ sudo fdisk /dev/sda
While inside the program you can use
m command to display list of available commands. If there’s a partition on a disk, you can use
d command to delete it. You can check it by using
Command (m for help): p Disk /dev/sda: 223.57 GiB, 240057409536 bytes, 468862128 sectors Disk model: 00SSD1 Units: sectors of 1 * 512 = 512 bytes Sector size (logical/physical): 512 bytes / 512 bytes I/O size (minimum/optimal): 512 bytes / 33553920 bytes Disklabel type: dos Disk identifier: 0xeb8a9682 Device Boot Start End Sectors Size Id Type /dev/sda1 65535 468862127 468796593 223.5G 83 Linux
After removing the partition, you can use
n command to create a new one. At this case I needed only one partition, so I just took all the defaults from the command prompts and entered
w to write the changes.
w command writes the changes to the disk permanently. Our new partition is now visible as a
Format the partition
Then, the partition is ready to be formatted to the
ext4 file system.
$ sudo mkfs -t ext4 /dev/sda1
Create mount point
I’m used to mount the disks to the
/mnt/ directory in the Linux file system. It’s a generic mount point for mounting disks. First, I need to create a mount point directory.
$ sudo mkdir /mnt/ssd
Then, I can mount the partition to the directory. But, I have to make sure that after the reboot my mounted partition remain mounted. For that, I’m going to use
/etc/fstab configuration file. Before changes it looks like this:
$ sudo cat /etc/fstab # <file system> <dir> <type> <options> <dump> <pass> LABEL=writable / ext4 defaults 0 0 LABEL=system-boot /boot/firmware vfat defaults 0 1
Format of this file is very simple. More information about it can be found in here: wiki.debian.org/fstab.
After adding my entry to mount the
/dev/sda1 partition to the
/mnt/ssd directory, it looks like this:
# <file system> <dir> <type> <options> <dump> <pass> LABEL=writable / ext4 defaults 0 0 LABEL=system-boot /boot/firmware vfat defaults 0 1 /dev/sda1 /mnt/ssd ext4 defaults 0 0
Finally, I can mount the partition. The
mount command will mount the partition to the directory configured in the
$ sudo mount /mnt/ssd
It can be verified by
$ df | grep /dev/sda1 /dev/sda1 229669796 1021996 216911504 1% /mnt/ssd
I’m not a benchmarking expert yet, but I’m going to use
hdparm to show you the difference between SD card and SSD.
$ sudo hdparm -Tt /dev/mmcblk0 /dev/mmcblk0: Timing cached reads: 1664 MB in 2.00 seconds = 833.99 MB/sec Timing buffered disk reads: 126 MB in 3.02 seconds = 41.74 MB/sec
sudo hdparm -Tt /dev/sda /dev/sda: Timing cached reads: 1764 MB in 2.00 seconds = 883.68 MB/sec Timing buffered disk reads: 764 MB in 3.11 seconds = 245.39 MB/sec
Writes are tested by writing a 2GB file to the disk.
$ dd if=/dev/zero of=/tmp/output.img bs=8k count=256k 262144+0 records in 262144+0 records out 2147483648 bytes (2.1 GB, 2.0 GiB) copied, 95.2907 s, 22.5 MB/s
$ dd if=/dev/zero of=/mnt/ssd/output.img bs=8k count=256k 262144+0 records in 262144+0 records out 2147483648 bytes (2.1 GB, 2.0 GiB) copied, 11.2758 s, 190 MB/s
That’s not a surprise that SD card is slower than SSD. But, those numbers are interesting. The SSD outperforms the SD card in writes by a factor of 10. Reading from the SD card can be 6 times slower than reading from the SSD. Honestly I expected much better performance from the SSD. But, it’s not a much expensive benchmark of some Samsung EVO SSD.
At the moment, the Ubuntu system on my RPi is still runnning from the SD card. I moved MySQL and Redis to use storage on the SSD, and mounted
/var/www/html catalog from my Nextcloud container to the
/mnt/ssd/nextcloud/html directory. I resolved all of the performance problems I had with my Nextcloud instance. No more timeouts or slow processing of files. All of the users, including me are happy now.
Looking back in time, I now wonder why I haven’t used the SSD from the start. It’s a real game changer for old PCs, so what stops us from speeding up our Raspberry-Pies? Next thing I want to do, is to move the OS to entirely to the SSD, but that’s a lot of work at the moment.