Prototype Shepherd PID 1 boot on FreeBSD

This commit is contained in:
2026-04-02 13:29:17 +02:00
parent c62c89b078
commit f5ffd111ee
5 changed files with 655 additions and 14 deletions

View File

@@ -2421,3 +2421,68 @@ Next recommended step:
1. begin the next post-Phase-10 cleanup/polish pass outside the plan milestones
2. prioritize replacing the current Guile / Shepherd compatibility-prefix shims with a more native store-path-aware runtime arrangement
3. consider adding richer deploy/vm-oriented `fruix` commands beyond the now-canonical `system build/rootfs/image` path
## 2026-04-02 — Post-Phase-10: local Shepherd-as-PID-1 prototype booted on FreeBSD
Completed work:
- began the next post-Phase-10 runtime-integration pass by exploring a Shepherd-as-PID-1 boot mode for Fruix on FreeBSD
- compared the approach with Guix's root Shepherd design in:
- `~/repos/guix/gnu/services/shepherd.scm`
- wrote the subphase report:
- `docs/reports/postphase10-shepherd-pid1-qemu-freebsd.md`
- extended the declarative FreeBSD operating-system model in:
- `modules/fruix/system/freebsd.scm`
- added an `init-mode` field with:
- `freebsd-init+rc.d-shepherd`
- `shepherd-pid1`
- generated loader configuration now sets:
- `init_exec="/run/current-system/boot/fruix-pid1"`
when `init-mode` is `shepherd-pid1`
- generated systems in PID 1 mode now include:
- `boot/fruix-pid1`
- the generated activation script now treats `cap_mkdb` / `pwd_mkdb` as best-effort so immutable store-backed config files do not abort this early boot path
- added a dedicated Shepherd-PID-1 operating-system template:
- `tests/system/phase11-shepherd-pid1-operating-system.scm.in`
- added a dedicated local QEMU/UEFI validation harness:
- `tests/system/run-phase11-shepherd-pid1-qemu.sh`
Important findings:
- FreeBSD's `init(8)` already has a suitable handoff mechanism for this experiment via:
- `init_exec`
- compared with Guix, the current Fruix implementation is still much more imperative, but it now follows the same broad direction:
- boot into Shepherd directly as PID 1 rather than merely starting Shepherd late from rc.d
- the first PID 1 attempt failed because the generated Shepherd config imported a repo-side module:
- `(fruix shepherd freebsd)`
that was not present inside the guest runtime; the fix was to inline the small helper procedures needed by the generated config itself
- the early PID 1 path also exposed that store-backed `/etc/login.conf` and `/etc/master.passwd` updates must be best-effort rather than fatal on this bootstrap path
- for the current locally built runtime artifacts, the compatibility-prefix shims are still needed; this subphase did not eliminate them yet, but it did remove the larger `rc.d` boot-manager dependency from the local prototype path
Validation:
- `tests/system/run-phase11-shepherd-pid1-qemu.sh` now passes
- passing run workdir:
- `/tmp/pid1-qemu6-1775128407`
- validated local guest state included:
- `ready_marker=ready`
- `shepherd_pid=1`
- `shepherd_socket=present`
- `shepherd_status=running`
- `sshd_status=running`
- `boot_backend=qemu-uefi-tcg`
- `init_mode=shepherd-pid1`
Current assessment:
- Fruix now has a working local FreeBSD prototype where Shepherd itself is PID 1
- this is not yet the new mainline boot path, but it proves that the project can move beyond the earlier `freebsd-init+rc.d-shepherd` bridge architecture
- the PID 1 process image appears as Guile because Shepherd is launched as a Guile script, but the decisive validation point is that:
- `/var/run/shepherd.pid` contains `1`
- this subphase was validated locally under QEMU/TCG + UEFI; the next meaningful test is the real XCP-ng VM
Next recommended step:
1. try the `shepherd-pid1` image on the real XCP-ng VM
2. if it boots there too, decide whether to keep `shepherd-pid1` as an experimental selectable boot mode or advance it further toward the main Fruix boot path
3. continue reducing the remaining Guile / Shepherd compatibility-prefix shims now that the broader `rc.d` boot-manager dependency has been locally bypassed