Automated builder for custom Arch Linux ARM images for Raspberry Pi 4 and 5, with pre-configured networking, SSH access, and USB serial console support.
- Automated GitHub Actions CI/CD - Build images automatically on push or manually via workflow dispatch
- Raspberry Pi 4 & 5 Support - Choose your target model during build
- USB Serial Console - Access your Pi via USB power cable (no keyboard/monitor needed)
- Pre-configured Networking - Systemd-networkd with optional WiFi support
- SSH Access - Automated SSH key deployment from GitHub
- ZeroTier Support - Built-in mesh networking capability
- Custom Package Set - Pre-installed tools including Tailscale, ZeroTier, and development utilities
- Fork or clone this repository
- Go to Actions → Build Archlinux aarch64 Raspberry Pi Image
- Click Run workflow
- Select Raspberry Pi model (4 or 5)
- Optionally enable S3 upload
- Download the compressed
.img.zstfile from workflow artifacts
Build locally using act to test GitHub Actions workflows:
# Install act (macOS)
brew install act
# Run the build workflow
./run-act.shNote: Local builds require a VM (not LXC containers) and privileged access for loop device manipulation.
# Extract the compressed image
cd /tmp
unzstd archlinux-rpi-aarch64-*.img.zst
# Identify your SD card/USB device
diskutil list
# Unmount the device (replace disk4 with your device)
sudo diskutil unmountDisk /dev/disk4
# Write the image (use rdisk for faster writes)
sudo dd if=/tmp/archlinux-rpi-aarch64-*.img of=/dev/rdisk4 bs=4m status=progress
# Eject when complete
sudo diskutil eject /dev/disk4# Extract the compressed image
unzstd archlinux-rpi-aarch64-*.img.zst
# Identify your device
lsblk
# Write the image (replace sdX with your device)
sudo dd if=archlinux-rpi-aarch64-*.img of=/dev/sdX bs=4M status=progress conv=fsync
# Sync and eject
sync
sudo eject /dev/sdXThis image comes pre-configured with USB serial gadget mode, allowing console access via the USB-C power cable.
-
Connect: Plug USB-C cable from Raspberry Pi to your computer
-
Identify Device:
- Linux/macOS:
/dev/ttyACM0(or/dev/ttyACM1) - Windows:
COMx(check Device Manager)
- Linux/macOS:
-
Connect with Terminal Software:
Linux/macOS:
# Using screen screen /dev/ttyACM0 115200 # Using minicom minicom -D /dev/ttyACM0 -b 115200 # Using picocom picocom -b 115200 /dev/ttyACM0
Windows:
- Baud rate: 115200
- Data bits: 8
- Parity: None
- Stop bits: 1
- Flow control: None
Run usb-console-info or usb-info on the Pi for detailed connection information and status.
- Hostname:
sz-<commit>-rpi<model>(e.g.,sz-f471ba3-rpi5) - Default User:
root - Root Password: Generated randomly during build (saved in workflow artifacts)
- Locale:
en_US.UTF-8 - Keymap:
us-acentos - Timezone: UTC (default, can be changed)
- Wired: DHCP enabled on all Ethernet interfaces
- WiFi: Optional (configure via environment variables)
- SSH Port:
34522(not standard 22) - SSH: Root login with key authentication only
- Base system + development tools
- Networking: iwd, wireless-regdb, Tailscale, ZeroTier
- Utilities: git, neovim, rsync, sudo, zsh, qrencode
- Firmware: linux-firmware, raspberrypi-bootloader, firmware-raspberrypi
- Raspberry Pi Specific:
- RPi 5:
linux-rpi-16k,rpi5-eeprom - RPi 4:
linux-rpi,rpi4-eeprom
- RPi 5:
Edit .github/workflows/rpi_aarch64_image_builder.yml to customize:
env:
LOOP_IMAGE_SIZE: 4G # Image size (increase for more space)
OS_PACKAGES: > # Add/remove packages
base base-devel git neovim ...
OS_DEFAULT_LOCALE: en_US.UTF-8 # System locale
OS_KEYMAP: us-acentos # Console keymap
OS_TIMEZONE: UTC # System timezone
SSH_PUB_KEY_URL: https://github.com/username.keys # SSH public keysSet repository secrets:
WIFI_SSID: Your WiFi network nameWIFI_PASSWORD: Your WiFi password
Set repository secret:
ZT_NETWORK_ID: Your ZeroTier network ID
- Boot Partition (512MB, FAT32): Bootloader, kernel, device tree blobs
- Root Partition (remaining space, ext4): System files
-
Check if services are running on Pi:
systemctl status usb-serial-gadget.service systemctl status [email protected]
-
Check device on Pi:
ls -la /dev/ttyGS0
-
View logs:
journalctl -u usb-serial-gadget.service
-
Restart service:
systemctl restart usb-serial-gadget.service
-
Check SSH service:
systemctl status sshd
-
Remember custom port:
ssh -p 34522 root@<pi-ip-address>
-
Check iwd service:
systemctl status iwd
-
Manually configure WiFi:
iwctl station wlan0 scan station wlan0 get-networks station wlan0 connect <SSID>
The automated build process:
- Downloads latest Arch Linux ARM base image
- Creates 4GB disk image with 512MB boot + ext4 root partitions
- Extracts base system to partitions
- Configures QEMU for ARM64 emulation
- Installs Raspberry Pi specific kernel and firmware
- Installs custom package set
- Configures system settings (locale, timezone, hostname)
- Sets up networking and SSH
- Configures USB serial gadget
- Compresses final image with zstd
- GitHub account with Actions enabled
- Optional: S3-compatible storage credentials for artifact uploads
- Docker or Podman
- Act installed
- VM environment (not LXC)
- Privileged access for loop device operations
This project is open source. The generated images contain Arch Linux ARM, which is governed by its own licenses.
- Arch Linux ARM - Base distribution
- Raspberry Pi Foundation - Hardware support
- Community contributors