Build Fedora aarch64 images for the Lenovo Yoga C630

Assembles a ready-to-write disk image via Gitea Actions. Mainline has carried
sdm850-lenovo-yoga-c630.dts since 5.5 and Fedora ships it in kernel-core, so
unlike aarch64-laptops/build there is no kernel or GRUB to compile — what is
left is producing an image that boots on firmware which hands Linux no device
tree.

The build runs in an aarch64 container under qemu-user and builds filesystems
from directory trees with mke2fs -d and mcopy rather than mounting loop
devices, so it works on runners that will not hand out /dev/loop-control.

A kernel-install hook writes the devicetree line into each BLS entry; without
it the first `dnf update kernel` would produce an unbootable system.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01XWRjNJMistCy6ngXH5aJLS
This commit is contained in:
2026-07-27 11:24:53 +03:00
commit 280874f564
21 changed files with 1294 additions and 0 deletions

61
docs/runner-setup.md Normal file
View File

@@ -0,0 +1,61 @@
# Gitea runner setup
The build runs on runners labelled `metal`, executing directly on the host
rather than in a runner-provided container, because it needs to drive podman
itself.
## One-time host preparation
On each runner host:
```sh
sudo dnf install -y podman qemu-user-static-aarch64
sudo systemctl restart systemd-binfmt
```
Verify:
```sh
cat /proc/sys/fs/binfmt_misc/qemu-aarch64
```
The `flags:` line must contain `F`. That flag makes the kernel open the
interpreter at registration time and keep the reference, so `qemu-aarch64-static`
resolves even inside a container that does not have it. Without it, every
aarch64 binary inside the build container fails with `exec format error`.
`qemu-user-static-aarch64` registers it correctly; plain `qemu-user` does not.
The workflow attempts this install itself, but that only works if the runner
account has passwordless sudo. Run `probe-runner.yaml` to find out.
## Checking what a runner can do
The `probe runner` workflow is manual-dispatch only and reports architecture,
user, sudo, podman, emulation status and free disk. Run it once per runner
before debugging a build failure.
## Disk space
The build stages a full root filesystem and three filesystem images alongside
the final disk image, under the job workspace. Budget roughly:
- `minimal` — about 20 GiB
- `workstation` — about 45 GiB
## Runtime
Every aarch64 binary runs under qemu-user emulation, and rpm scriptlets are the
worst case. Expect roughly 4590 minutes for `minimal` and several hours for
`workstation`. The workflow's `timeout-minutes` is set to 600 accordingly.
If this becomes tiresome, the fix is a native aarch64 runner. Register one with
an `aarch64` label and change `runs-on: metal` to `runs-on: aarch64` in
`.gitea/workflows/build-image.yaml`; `build/build-image.sh` already skips the
emulation check when the host is already the target architecture.
## Changing which runners are used
All nine current runners carry `metal` and `podman`. `runs-on: metal` therefore
matches any of them. To pin the build to a subset, give those runners a distinct
label and use it — Gitea requires a runner to carry every label listed in
`runs-on`.