Alright, this is a bit lengthy, but it attempts to describe a reproducible process to edit the 96boards Linaro image while hopefully minimizing complexity. This is a rough (unrefined) process, so if anyone has good input I’d be happy to amend. I was able to:
- Download the Linaro
rootfs
from http://releases.linaro.org/96boards/dragonboard410c/linaro/debian/latest/linaro-buster-developer-dragonboard-410c-528.img.gz (note this image lacks a GUI)
- Expand and convert from sparse to raw with
simg2img rootfs.img rootfs.img.raw
- Mount with
sudo mount -o loop rootfs.img.raw mountpoint
- Modify
rootfs
- Repackage
- Flash and boot the target
If you’re going to be adding to the image you’ll probably want to expand its size lest you run out of disk (file) space. The method I used was (with rootfs
umounted):
- Append data (zeros) to the end of your raw image file. In this case we add 1GB:
dd if=/dev/zero bs=1G count=1 >> rootfs.img.raw
. I have also seen some use fallocate
.
- Run filesystem check:
e2fsck -f rootfs.img.raw
- Resize the fs to match the new file size:
resize2fs rootfs.img.raw
Alternatively you could mount a temp folder from your host inside the chroot jail and avoid expanding and shrinking your image. This seems like a good idea when building things from source as it’s easy to control where your build products go, but it seems a bit more complicated when you need more room for other OS related stuff (like running apt).
If you haven’t already, set up QEMU as described in @danielt’s link (QemuUserEmulation - Debian Wiki). The takeaway is that you’ll be able to execute chroot mountpoint
which will run qemu under the hood for you, or something.
Now you are in your emulated arm64 environment and can run aarch64 binaries, including apt-get to manipulate packages, “natively” build and install your own program, etc. I proved it to myself by cross-compiling a “hello world” in the host environment, copying it over to the chroot, running file
on it to get something like ELF 64-bit LSB shared object, ARM aarch64
, then running it.
Now it’s time to button everything up and get it on your DB410c. After cleaning up any unwanted files, unmounting, and reconverting to sparse, I used fastboot to flash only the rootfs leaving the bootloader and that other thing alone.
I lack the background knowledge to know exactly which parts of the following are required and which aren’t. In particular I’m not extremely clear on how to re-shrink the altered rootfs
gracefully. It seems that converting to a sparse image “handles” the free space with its metadata magic. I did:
- Unmount everything related to
rootfs
. I wanted to do an apt upgrade to have the latest-greatest and openjdk made me mount /proc (mount -t proc proc /proc
) in the chroot. You’ll have to unmount any nested mounts before unmounting rootfs
.
- Convert to sparse:
img2simg rootfs.img.raw rootfs.img
. Caution: you might overwrite your original rootfs.img
.
- Put your Dragonboard in fastboot mode with these instructions and flash with fastboot using the microUSB host on the DB410c:
fastboot flash rootfs rootfs.img
.
- Boot the Dragonboard and cry tears of joy while not having to compile for hours!
The enterprising engineer can now crate a development pipeline that uses the ARM architecture without having to compile on the target as well as (perhaps crudely) generating a customized image that can be flashed to many targets.
Alright, now it’s time for someone take this apart.