← back

2018-12-29: preparing Ubuntu Server 18.04.2 for the Raspberry Pi 3B+


The Raspberry Pi 3B+ was the leading version of the small yet effective computer system in 2018. While it was not too large a change from the previous Pi 3B, it introduced a number of minor firmware changes that broke support for existing OS images.

Since the current phase of my career features quite a lot of system administration duties, small computers like the Pi make it easy to run simple tasks in a non-containerized environment.

However I was recently dismayed during my attempts to migrate the SD cards from Pi 3B to 3B+ resulted in a litany of errors. In addition, there was no meaningful upgrade path from Ubuntu 16.04 to 18.04 on the Pi since quite a lot of people use the standard Raspian so everything else tends to be out of date.

Understandably, many clients however prefer having the maximum possible compatibility with desktop Ubuntu LTS, so I was forced to do some more digging.

An image of Ubuntu 18.04.2 LTS for the Raspberry Pi 3B exists and can be found here, however, it does not support some minor variants of 3B, notably the 3B+ is not supported.

Looking at the Raspberry Pi spec sheets carefully, I figured since the physical CPU had not changed between 3B and 3B+ that there was no Linux limitation against it working. So I proceeded to write the image to the SD card as per usual:

sudo unxz ubuntu-18.04.2-preinstalled-server-arm64+raspi3.img.xz

sudo dd if=ubuntu-18.04.2-preinstalled-server-arm64+raspi3.img \
    of=/dev/sdc bs=4M conv=fsync status=progress

I plugged that into my Pi and, sadly, it was unable to boot. It remained stuck at the rainbow colour palette startup screen. So my guess was the bootloader had failed somehow.

Plugging the SD back into my desktop, I did a lsblk to determine /boot partition location. Then I did a ls to see what what files were present. Mostly firmware blobs and vmlinuz and the infamous config.txt which controls the Pi boot process. So I opened it with vim noticed that kernel was pointing to a uboot file which was not present. Bingo!

Thankfully the Broadcom CPU used in the Pi has been pushed to kernel upstream, which is what Ubuntu LTS relies on, so I could just delete the device_tree_address line used by u-boot and adjust several lines in the config.txt to point to the plain ol' Linux vmlinuz.

kernel=vmlinuz
initramfs initrd.img followkernel
arm_control=0x200
device_tree_address=0x0200000 # -- delete this line --

As an aside, I noticed many of the Raspberry Pi blobs for the other devices were missing. So if you need those, you'll want to obtain them via the official GitHub repo. In my case I only needed the ComputeModule3 blob, which is bcm2710-rpi-cm3.dtb, so I copied that into the boot partition.

With that, my Raspberry Pi 3B+ was able to boot the latest Ubuntu 18.04.2 LTS. Since this is Ubuntu, the normal username and password combo is 'ubuntu' for both, and I was able to login just fine.

Finally, for a 4-core computer with only 1GB of RAM, the commandline use was quite fast and it didn't need more than about 150Mb at any given time. I was able to trim that by quite a bit removing the cloud-init services and got it down to about 110Mb.

Thus I was able to use the humble Raspberry Pi for semi-important business goals and so wraps up this blog post.