scripts/e2e.sh is a testbed lifecycle regression (modeled on cocoon’s), in two tiers.
[DUMMY] — file-level, no macOS bootRuns on any x86 Linux/KVM host against a tiny throwaway qcow2 (no macOS boot):
pull-less list/rm).vm create overlay-on-shared-base.--random-smbios serial/MAC uniqueness + MAC == ROM.snapshot/restore (qcow2-internal tag rollback).clone (CoW on the shared base + distinct identity + clone-of-clone backing).stop PID-reuse-safe teardown.--net bridge auto-TAP create + tap_owned + teardown-on-rm + user---tap preservation +
negative paths.Post-conditions assert no leaked TAPs/procs and backing-chain integrity. The --random-smbios rows
need root + nbd + a real CM_OPENCORE; the --net rows need root + a test bridge (they SKIP,
not FAIL, otherwise).
[REAL] — boots the golden imageBoots tahoe:26 from the store, passes the OpenCore picker over the HMP monitor, and asserts
SSH-ready (sw_vers 26.x) + in-guest serial == injected. Testbed-only.
sudo CM_BIN=./cocoon-macos CM_OPENCORE=.../OpenCore.qcow2 ./scripts/e2e.sh # [DUMMY] (30 rows)
sudo CM_HOME=~/cm-demo CM_OPENCORE=... CM_OVMF_CODE=... CM_OVMF_VARS=... \
./scripts/e2e.sh --real-only
The [DUMMY] tier is the behavioral gate today’s CI structurally can’t give (CI is pure go test /
vet / build — nothing opens /dev/kvm or mutates netlink); it belongs on a privileged self-hosted
KVM runner. [REAL] stays a manual/nightly testbed run (~15 GB + cold boot).