Network boot (PXE) server as an infraternal subcomponent — grill 2026-10-11 #156

Open
opened 2026-10-10 17:29:35 +00:00 by kayg · 32 comments
Owner

Owner request (2026-10-10): consider a network-boot (PXE) server as a possible infraternal subcomponent (D198 plugin). To be grilled with the owner on 2026-10-11; nothing is built until then.

Questions to bring to the grill:

  • Scope. DHCP proxy only (works next to an existing DHCP server) or full DHCP? TFTP and/or HTTP boot? UEFI and legacy BIOS? Secure Boot?
  • What it boots. OS installers (Debian/Ubuntu/Fedora/Proxmox/Talos), live images, diskless hosts, memory-test and rescue tools; a menu, or one target per host?
  • Hands-off installs. Answer files (preseed, autoinstall, kickstart), with an infraternal agent installed and enrolled on first boot, so a bare machine joins the mesh with no typing.
  • Where it runs. Which infraternal node serves a LAN; how it finds that LAN; several sites through the mesh; relay behaviour.
  • Images. Download, verify and cache (signed per D184/D224?), storage location (XDG/FHS per #34), and cache size.
  • Security. Booting is unauthenticated on most LANs. Enrolment secrets must not be readable over TFTP or HTTP; use per-host one-time tokens and MAC/UUID allowlists; enterprise default deny (D216).
  • UI. A "Boot a machine" flow on the canvas: pick a host by MAC or "next machine that asks", pick an image, and watch progress.
  • Measurements. Time to boot an installer over the LAN vs over the mesh, and memory per served client.
Owner request (2026-10-10): consider a network-boot (PXE) server as a possible infraternal subcomponent (D198 plugin). To be grilled with the owner on 2026-10-11; nothing is built until then. Questions to bring to the grill: - **Scope.** DHCP proxy only (works next to an existing DHCP server) or full DHCP? TFTP and/or HTTP boot? UEFI and legacy BIOS? Secure Boot? - **What it boots.** OS installers (Debian/Ubuntu/Fedora/Proxmox/Talos), live images, diskless hosts, memory-test and rescue tools; a menu, or one target per host? - **Hands-off installs.** Answer files (preseed, autoinstall, kickstart), with an infraternal agent installed and enrolled on first boot, so a bare machine joins the mesh with no typing. - **Where it runs.** Which infraternal node serves a LAN; how it finds that LAN; several sites through the mesh; relay behaviour. - **Images.** Download, verify and cache (signed per D184/D224?), storage location (XDG/FHS per #34), and cache size. - **Security.** Booting is unauthenticated on most LANs. Enrolment secrets must not be readable over TFTP or HTTP; use per-host one-time tokens and MAC/UUID allowlists; enterprise default deny (D216). - **UI.** A "Boot a machine" flow on the canvas: pick a host by MAC or "next machine that asks", pick an image, and watch progress. - **Measurements.** Time to boot an installer over the LAN vs over the mesh, and memory per served client.
Author
Owner

Starting research on branch research-pxe-mesh at base a5f744fbc1 (mesh slice 1). Issue #156 currently has 0 comments; its body contains no parent issue reference. Required repo docs, mesh dataplane contract, and requested decisions read.

Starting research on branch research-pxe-mesh at base a5f744fbc1d5e8966de46982b995d816e91baff5 (mesh slice 1). Issue #156 currently has 0 comments; its body contains no parent issue reference. Required repo docs, mesh dataplane contract, and requested decisions read.
Author
Owner

Measurement finding: on infraternal-dev (i9-9900K, 8 CPUs, Linux 6.12.111; load average 9.64/21.13/23.09 before and 21.97/20.67/22.52 after), two rootless namespaces ran the slice-1 kernel WireGuard fixture and a third represented a bare LAN client. /usr/sbin/tc netem applied 75 ms one-way delay + 5 ms jitter and 0.1% loss per underlay egress; 20 mesh pings measured 149 ms p50 RTT and 0% observed loss. The real Debian kernel/initrd (12,142,528 / 40,723,557 bytes) and bootable 792,723,456-byte netinst ISO were fetched by local HTTP and by a LAN proxy to the remote mesh node. Median local vs proxy TTFB / total / throughput: kernel 1.51 ms / 7 ms / 13,299 Mbps vs 313 ms / 3.624 s / 27.01 Mbps; initrd 0.96 ms / 22 ms / 14,939 Mbps vs 301 ms / 7.738 s / 42.14 Mbps; ISO 1.74 ms / 0.460 s / 13,785 Mbps vs 309 ms / 125.294 s / 50.62 Mbps. After warm-up, measured RSS increase for one concurrent client was ~0.5 MiB each in the LAN HTTP server, proxy and remote HTTP origin (idle RSS 29.3 / 31.7 / 29.4 MiB). Evidence and reproduction script: research/pxe-over-mesh/benchmark.py and README. QEMU and OVMF/SeaBIOS are absent here (qemu-system-x86_64 unresolved; firmware directories missing), so no VM firmware boot or DHCP packet exchange was measured; the simulated client used static LAN addressing.

Measurement finding: on infraternal-dev (i9-9900K, 8 CPUs, Linux 6.12.111; load average 9.64/21.13/23.09 before and 21.97/20.67/22.52 after), two rootless namespaces ran the slice-1 kernel WireGuard fixture and a third represented a bare LAN client. /usr/sbin/tc netem applied 75 ms one-way delay + 5 ms jitter and 0.1% loss per underlay egress; 20 mesh pings measured 149 ms p50 RTT and 0% observed loss. The real Debian kernel/initrd (12,142,528 / 40,723,557 bytes) and bootable 792,723,456-byte netinst ISO were fetched by local HTTP and by a LAN proxy to the remote mesh node. Median local vs proxy TTFB / total / throughput: kernel 1.51 ms / 7 ms / 13,299 Mbps vs 313 ms / 3.624 s / 27.01 Mbps; initrd 0.96 ms / 22 ms / 14,939 Mbps vs 301 ms / 7.738 s / 42.14 Mbps; ISO 1.74 ms / 0.460 s / 13,785 Mbps vs 309 ms / 125.294 s / 50.62 Mbps. After warm-up, measured RSS increase for one concurrent client was ~0.5 MiB each in the LAN HTTP server, proxy and remote HTTP origin (idle RSS 29.3 / 31.7 / 29.4 MiB). Evidence and reproduction script: research/pxe-over-mesh/benchmark.py and README. QEMU and OVMF/SeaBIOS are absent here (`qemu-system-x86_64` unresolved; firmware directories missing), so no VM firmware boot or DHCP packet exchange was measured; the simulated client used static LAN addressing.
Author
Owner

Protocol finding for #156: the client-side DHCP exchange starts on the local link; RFC 2131 describes pre-address DHCP broadcasts and the giaddr relay path. UEFI 2.11 §24.3.18.2 then has the client multicast a REQUEST to boot-server UDP/4011 after standard DHCP, receive a unicast reply, and fetch the NBP by TFTP; proxy DHCP supplies boot options without replacing the ordinary DHCP lease. UEFI 2.11 §24.7 describes HTTP Boot as client-initiated DHCP/DNS/HTTP retrieval and explicitly permits an endpoint server across networks or the Internet, with an optional proxy host. This means a bare host needs ordinary LAN IP setup and boot-service discovery on its LAN (typically a local proxy-DHCP/boot node, or DHCP configuration plus a relay); TFTP/HTTP(S) data can be remote if routed. Sources: https://www.rfc-editor.org/rfc/rfc2131/ ; https://uefi.org/specs/UEFI/2.11/24_Network_Protocols_SNP_PXE_BIS.html ; https://ipxe.org/appnote/proxydhcp

Protocol finding for #156: the client-side DHCP exchange starts on the local link; RFC 2131 describes pre-address DHCP broadcasts and the giaddr relay path. UEFI 2.11 §24.3.18.2 then has the client multicast a REQUEST to boot-server UDP/4011 after standard DHCP, receive a unicast reply, and fetch the NBP by TFTP; proxy DHCP supplies boot options without replacing the ordinary DHCP lease. UEFI 2.11 §24.7 describes HTTP Boot as client-initiated DHCP/DNS/HTTP retrieval and explicitly permits an endpoint server across networks or the Internet, with an optional proxy host. This means a bare host needs ordinary LAN IP setup and boot-service discovery on its LAN (typically a local proxy-DHCP/boot node, or DHCP configuration plus a relay); TFTP/HTTP(S) data can be remote if routed. Sources: https://www.rfc-editor.org/rfc/rfc2131/ ; https://uefi.org/specs/UEFI/2.11/24_Network_Protocols_SNP_PXE_BIS.html ; https://ipxe.org/appnote/proxydhcp
Author
Owner

Security/tooling finding for #156: RFC 1350 explicitly has no TFTP login/access control; UEFI Secure Boot authenticates UEFI images against db/dbx but does not authenticate DHCP or encrypt the path. iPXE requires explicit imgverify for an initrd even with imgtrust. The documented MAAS workflow boots an ephemeral image via TFTP and configures SSH keys with cloud-init; its API uses OAuth, but its public docs do not specify every credential's wire path, so they are evidence for staged enrollment, not a blanket secrecy guarantee. Reference Debian trixie amd64 package sizes (download / installed): dnsmasq-base 495.3/1,117 KB; Kea DHCPv4 577.3/1,520 KB; tftpd-hpa 43.1/125 KB; lighttpd 361.1/1,035 KB; iPXE 2,422.2/14,314 KB. Licenses vary by built artifact; iPXE documents per-target .licence analysis. The Debian tftpd-hpa copyright declares BSD-4 but deletes its advertising clause. Sources: https://www.rfc-editor.org/rfc/rfc1350 ; https://uefi.org/specs/UEFI/2.11/32_Secure_Boot_and_Driver_Signing.html ; https://ipxe.org/cmd/imgtrust ; https://maas.io/docs/about-commissioning-machines ; https://maas.io/docs/how-to-authenticate-to-the-maas-api ; https://packages.debian.org/trixie/dnsmasq-base ; https://packages.debian.org/trixie/kea-dhcp4-server ; https://packages.debian.org/trixie/tftpd-hpa ; https://packages.debian.org/trixie/lighttpd ; https://packages.debian.org/trixie/ipxe

Security/tooling finding for #156: RFC 1350 explicitly has no TFTP login/access control; UEFI Secure Boot authenticates UEFI images against db/dbx but does not authenticate DHCP or encrypt the path. iPXE requires explicit imgverify for an initrd even with imgtrust. The documented MAAS workflow boots an ephemeral image via TFTP and configures SSH keys with cloud-init; its API uses OAuth, but its public docs do not specify every credential's wire path, so they are evidence for staged enrollment, not a blanket secrecy guarantee. Reference Debian trixie amd64 package sizes (download / installed): dnsmasq-base 495.3/1,117 KB; Kea DHCPv4 577.3/1,520 KB; tftpd-hpa 43.1/125 KB; lighttpd 361.1/1,035 KB; iPXE 2,422.2/14,314 KB. Licenses vary by built artifact; iPXE documents per-target .licence analysis. The Debian tftpd-hpa copyright declares BSD-4 but deletes its advertising clause. Sources: https://www.rfc-editor.org/rfc/rfc1350 ; https://uefi.org/specs/UEFI/2.11/32_Secure_Boot_and_Driver_Signing.html ; https://ipxe.org/cmd/imgtrust ; https://maas.io/docs/about-commissioning-machines ; https://maas.io/docs/how-to-authenticate-to-the-maas-api ; https://packages.debian.org/trixie/dnsmasq-base ; https://packages.debian.org/trixie/kea-dhcp4-server ; https://packages.debian.org/trixie/tftpd-hpa ; https://packages.debian.org/trixie/lighttpd ; https://packages.debian.org/trixie/ipxe
Author
Owner

Owner goal (2026-10-11), for the research's second phase: "we want to have the convenience of ventoy basically, across our whole mesh or even just a subnet route or just a particular ip. very versatile and very easy".

So phase 2 covers: booting any image dropped into one place (ISO, IMG, WIM, VHD), with no extraction step and no per-image configuration; a menu that lists whatever is there; the same images reachable on every LAN where the mesh has a node, on a subnet route (D197 M3), or for one machine by IP or MAC; and measurements of how each image type boots (iPXE sanboot over HTTP range requests, memdisk, wimboot, loop-mounted ISO kernels), including which installers break when booted from a remote ISO.

Owner goal (2026-10-11), for the research's second phase: "we want to have the convenience of ventoy basically, across our whole mesh or even just a subnet route or just a particular ip. very versatile and very easy". So phase 2 covers: booting any image dropped into one place (ISO, IMG, WIM, VHD), with no extraction step and no per-image configuration; a menu that lists whatever is there; the same images reachable on every LAN where the mesh has a node, on a subnet route (D197 M3), or for one machine by IP or MAC; and measurements of how each image type boots (iPXE sanboot over HTTP range requests, memdisk, wimboot, loop-mounted ISO kernels), including which installers break when booted from a remote ISO.
Author
Owner

Gate finding for #156: with the required per-job CARGO_TARGET_DIR in scratch and the latency check passing (302.97 ms p50 / 318.88 ms p99), fmt, VT native fmt, clippy, workspace tests, and cargo-deny passed. scripts/verify fast fails at the existing x86_64 static binary size gate: 20,614,624 bytes vs 16,404,816 maximum; it therefore did not build/check the ARM binary. The only changes in this research lane are the Python benchmark harness and Markdown report, so this lane does not change the measured product binary.

Gate finding for #156: with the required per-job CARGO_TARGET_DIR in scratch and the latency check passing (302.97 ms p50 / 318.88 ms p99), fmt, VT native fmt, clippy, workspace tests, and cargo-deny passed. `scripts/verify fast` fails at the existing x86_64 static binary size gate: 20,614,624 bytes vs 16,404,816 maximum; it therefore did not build/check the ARM binary. The only changes in this research lane are the Python benchmark harness and Markdown report, so this lane does not change the measured product binary.
Author
Owner

Measurement harness completed and pushed: ee4b58fd71. Under a modeled 149 ms RTT, the 792,723,456-byte Debian installer ISO fetched through the LAN proxy over WireGuard in 125.294 s (50.62 Mbps); local same-host veth took 0.460 s. QEMU/OVMF and SeaBIOS are unavailable here, so these are HTTP transfer measurements, not firmware boot times.

Measurement harness completed and pushed: ee4b58fd713d184c46b9173c0406e3089008ffcc. Under a modeled 149 ms RTT, the 792,723,456-byte Debian installer ISO fetched through the LAN proxy over WireGuard in 125.294 s (50.62 Mbps); local same-host veth took 0.460 s. QEMU/OVMF and SeaBIOS are unavailable here, so these are HTTP transfer measurements, not firmware boot times.
Author
Owner

Fast gate rerun completed under the scoped CPU weight with build artifacts in scratch. RTT self-test, fmt, VT native fmt, clippy, workspace tests, and cargo-deny passed. Static x86_64 build failed the repository size budget: 20,614,624 bytes versus 16,404,816 allowed (baseline 16,142,672 + 262,144). The gate stops there before ARM/TS checks. This research-only branch changes no product binary.

Fast gate rerun completed under the scoped CPU weight with build artifacts in scratch. RTT self-test, fmt, VT native fmt, clippy, workspace tests, and cargo-deny passed. Static x86_64 build failed the repository size budget: 20,614,624 bytes versus 16,404,816 allowed (baseline 16,142,672 + 262,144). The gate stops there before ARM/TS checks. This research-only branch changes no product binary.
Author
Owner

Report committed and pushed: c04b0b06. research/pxe-over-mesh/README.md covers the link-local PXE discovery boundary, three mesh/public-URL designs, security facts, Debian package/license sizes, a Rust scope estimate, and owner decisions. The measurement table records local versus WireGuard-proxied kernel, initrd, and 792,723,456-byte ISO fetches plus per-process RSS; it states that QEMU/OVMF/SeaBIOS were unavailable.

Report committed and pushed: c04b0b06. research/pxe-over-mesh/README.md covers the link-local PXE discovery boundary, three mesh/public-URL designs, security facts, Debian package/license sizes, a Rust scope estimate, and owner decisions. The measurement table records local versus WireGuard-proxied kernel, initrd, and 792,723,456-byte ISO fetches plus per-process RSS; it states that QEMU/OVMF/SeaBIOS were unavailable.
Author
Owner

Finished. Head: c04b0b06a7; both commits are pushed to research-pxe-mesh.

Yes: network boot works when a joined node on the bare machine's LAN handles PXE discovery and serves, caches, or proxies the boot files. The bare machine cannot use mesh addresses before enrollment; direct HTTPS works only to a public or otherwise routable endpoint. At the modeled 149 ms RTT, the 792,723,456-byte Debian installer ISO fetched through the LAN proxy over WireGuard in 125.294 s at 50.62 Mbps; same-host local veth took 0.460 s. QEMU/OVMF/SeaBIOS were unavailable, so these are transfer measurements, not firmware boot times.

scripts/verify fast output (verbatim):

METRIC name=network_rtt_selftest configured_rtt_ms=300 jitter_ms=30 loss=unsupported transport=tcp-stream n=3 p50_ms=302.02 p99_ms=314.34 result=PASS
==> static builds
    Finished `release` profile [optimized] target(s) in 0.43s
/home/kayg/.cache/codex-scratch/research-pxe-mesh/verify-target/x86_64-unknown-linux-musl/release/infraternal: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), static-pie linked, stripped
PT_INTERP: absent; size: 20614624 bytes (baseline 16142672 + allowance 262144 = max 16404816)
binary exceeds the 16404816-byte size budget: 20614624 bytes

+---------------------------+--------------+
| Rust gate                 | Result       |
+---------------------------+--------------+
| fmt                       | PASS         |
| VT native fmt             | PASS         |
| clippy                    | PASS         |
| test                      | PASS         |
| cargo-deny                | PASS         |
| static builds             | FAIL (1)     |
+---------------------------+--------------+
Finished. Head: c04b0b06a7779911495263bf2e91d784da4d9c58; both commits are pushed to research-pxe-mesh. Yes: network boot works when a joined node on the bare machine's LAN handles PXE discovery and serves, caches, or proxies the boot files. The bare machine cannot use mesh addresses before enrollment; direct HTTPS works only to a public or otherwise routable endpoint. At the modeled 149 ms RTT, the 792,723,456-byte Debian installer ISO fetched through the LAN proxy over WireGuard in 125.294 s at 50.62 Mbps; same-host local veth took 0.460 s. QEMU/OVMF/SeaBIOS were unavailable, so these are transfer measurements, not firmware boot times. `scripts/verify fast` output (verbatim): ``` METRIC name=network_rtt_selftest configured_rtt_ms=300 jitter_ms=30 loss=unsupported transport=tcp-stream n=3 p50_ms=302.02 p99_ms=314.34 result=PASS ==> static builds Finished `release` profile [optimized] target(s) in 0.43s /home/kayg/.cache/codex-scratch/research-pxe-mesh/verify-target/x86_64-unknown-linux-musl/release/infraternal: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), static-pie linked, stripped PT_INTERP: absent; size: 20614624 bytes (baseline 16142672 + allowance 262144 = max 16404816) binary exceeds the 16404816-byte size budget: 20614624 bytes +---------------------------+--------------+ | Rust gate | Result | +---------------------------+--------------+ | fmt | PASS | | VT native fmt | PASS | | clippy | PASS | | test | PASS | | cargo-deny | PASS | | static builds | FAIL (1) | +---------------------------+--------------+ ```
Author
Owner

Starting phase 2 research on branch research-pxe-ventoy at base c04b0b06a7. Read the full #156 history; its body has no parent issue reference. This work measures real firmware/image boot behavior and documents whole-folder mesh scope. Prior phase-1 transfer evidence is retained as context, not substituted for VM timings.

Starting phase 2 research on branch research-pxe-ventoy at base c04b0b06a7779911495263bf2e91d784da4d9c58. Read the full #156 history; its body has no parent issue reference. This work measures real firmware/image boot behavior and documents whole-folder mesh scope. Prior phase-1 transfer evidence is retained as context, not substituted for VM timings.
Author
Owner

Source finding: iPXE HTTP sanboot requires server byte-range support (https://ipxe.org/sanuri), and therefore can read sectors on demand. It exposes a virtual boot disk; it is not an installer-wide guarantee that the OS can still read the ISO after kernel handoff. Debian live-boot documents fetch=/httpfs= and Ubuntu documents PXE using kernel+initrd with url=<ISO> (https://www.debian.org/releases/stable/amd64/ch05s03.en.html ; https://documentation.ubuntu.com/server/how-to/installation/netboot-the-server-installer-via-uefi-pxe-on-arm-aarch64-arm64-and-x86-64-amd64/). Windows' wimboot instructions use boot.wim plus boot files, and recommend serving the installer tree separately (https://ipxe.org/wimboot). The report will separate first-screen success from post-kernel medium availability.

Source finding: iPXE HTTP sanboot requires server byte-range support (https://ipxe.org/sanuri), and therefore can read sectors on demand. It exposes a virtual boot disk; it is not an installer-wide guarantee that the OS can still read the ISO after kernel handoff. Debian live-boot documents `fetch=`/`httpfs=` and Ubuntu documents PXE using kernel+initrd with `url=<ISO>` (https://www.debian.org/releases/stable/amd64/ch05s03.en.html ; https://documentation.ubuntu.com/server/how-to/installation/netboot-the-server-installer-via-uefi-pxe-on-arm-aarch64-arm64-and-x86-64-amd64/). Windows' wimboot instructions use boot.wim plus boot files, and recommend serving the installer tree separately (https://ipxe.org/wimboot). The report will separate first-screen success from post-kernel medium availability.
Author
Owner

Image-booting finding: Proxmox's 2026 PXE preparation path is distro-supported but not a direct unchanged-ISO boot. The accepted Proxmox installer change generates vmlinuz/initrd.img and overlays the ISO as /proxmox.iso; the installer expands it and needs about 6 GiB RAM. This makes Proxmox an explicit full-ISO-transfer exception for the requested “one folder” flow: https://lore.proxmox.com/pve-devel/20260331163353.1955212-1-c.heiss%40proxmox.com/

Image-booting finding: Proxmox's 2026 PXE preparation path is distro-supported but not a direct unchanged-ISO boot. The accepted Proxmox installer change generates vmlinuz/initrd.img and overlays the ISO as /proxmox.iso; the installer expands it and needs about 6 GiB RAM. This makes Proxmox an explicit full-ISO-transfer exception for the requested “one folder” flow: https://lore.proxmox.com/pve-devel/20260331163353.1955212-1-c.heiss%40proxmox.com/
Author
Owner

Image-booting finding: SystemRescue documents a direct PXE path that splits the ISO into kernel/initramfs and a squashfs rootfs fetched over HTTP/NFS/NBD (archiso_http_srv=). Its manual notes that HTTP/TFTP rootfs transfer is cached in client RAM, with about 1 GiB needed for that stage. This is a stronger “drop ISO, auto-detect profile” candidate than BIOS memdisk: https://www.system-rescue.org/manual/PXE_network_booting/ ; https://www.system-rescue.org/manual/Booting_SystemRescue/

Image-booting finding: SystemRescue documents a direct PXE path that splits the ISO into kernel/initramfs and a squashfs rootfs fetched over HTTP/NFS/NBD (`archiso_http_srv=`). Its manual notes that HTTP/TFTP rootfs transfer is cached in client RAM, with about 1 GiB needed for that stage. This is a stronger “drop ISO, auto-detect profile” candidate than BIOS memdisk: https://www.system-rescue.org/manual/PXE_network_booting/ ; https://www.system-rescue.org/manual/Booting_SystemRescue/
Author
Owner

Phase 2 measurement setup: /dev/kvm is present on the named perf VM; 75 ms netem delay was applied in each direction over WireGuard. Fourteen of fourteen tunnel pings replied, 150.571 ms mean RTT (150.408–150.764 ms, 0.107 ms mdev), recorded in /root/infraternal-bench/pxe/logs/wg-ping.txt. Verified local assets: Debian netinst 792,723,456 B, Ubuntu Server live 2,918,598,656 B, SystemRescue 1,381,629,952 B; checksum results are in /root/infraternal-bench/pxe/logs and assets.tsv. UEFI iPXE EFI payload is 996,864 B; legacy NBP is 108,847 B. Initial Range probes returned HTTP 206 with exactly 100 B from both cache and proxy.

Phase 2 measurement setup: `/dev/kvm` is present on the named perf VM; 75 ms netem delay was applied in each direction over WireGuard. Fourteen of fourteen tunnel pings replied, 150.571 ms mean RTT (150.408–150.764 ms, 0.107 ms mdev), recorded in `/root/infraternal-bench/pxe/logs/wg-ping.txt`. Verified local assets: Debian netinst 792,723,456 B, Ubuntu Server live 2,918,598,656 B, SystemRescue 1,381,629,952 B; checksum results are in `/root/infraternal-bench/pxe/logs` and `assets.tsv`. UEFI iPXE EFI payload is 996,864 B; legacy NBP is 108,847 B. Initial Range probes returned HTTP 206 with exactly 100 B from both cache and proxy.
Author
Owner

First real-firmware result: SeaBIOS + iPXE, Debian netinst kernel/initrd profile, local cache reached the installer language screen in 13.95 s. HTTP transferred 36,504,284 B (kernel 12,142,528 B + initrd 24,361,578 B + 178 B script); the ISO itself is 792,723,456 B. QEMU peak RSS was 270,491,648 B and the combined serving/origin Nginx tree peaked at 12,234,752 B; measured QEMU CPU was 9.4 s. KVM was enabled; load average at completion was 0.70/0.54/0.30. Per-run evidence: /root/infraternal-bench/pxe/logs/runs/seabios-debian-cache-profile.* and results.jsonl.

First real-firmware result: SeaBIOS + iPXE, Debian netinst kernel/initrd profile, local cache reached the installer language screen in 13.95 s. HTTP transferred 36,504,284 B (kernel 12,142,528 B + initrd 24,361,578 B + 178 B script); the ISO itself is 792,723,456 B. QEMU peak RSS was 270,491,648 B and the combined serving/origin Nginx tree peaked at 12,234,752 B; measured QEMU CPU was 9.4 s. KVM was enabled; load average at completion was 0.70/0.54/0.30. Per-run evidence: `/root/infraternal-bench/pxe/logs/runs/seabios-debian-cache-profile.*` and `results.jsonl`.
Author
Owner

Ubuntu live-server finding (SeaBIOS/iPXE, local cache, QEMU e1000, 4 GiB guest): the documented url= path began one HTTP GET for the 2,918,598,656 B ISO but transferred 1,327,433,482 B during the 360 s cap and did not reach Subiquity's first screen. The serial console was still in BusyBox wget's ISO download; QEMU peak RSS was 1,870,708,736 B and QEMU CPU 45.56 s. Evidence: /root/infraternal-bench/pxe/logs/runs/seabios-ubuntu-cache-profile.*; host load 1.36/1.06/0.66. I am checking whether the QEMU e1000 emulation is limiting the boot measurement before repeating the large-image runs.

Ubuntu live-server finding (SeaBIOS/iPXE, local cache, QEMU e1000, 4 GiB guest): the documented `url=` path began one HTTP GET for the 2,918,598,656 B ISO but transferred 1,327,433,482 B during the 360 s cap and did not reach Subiquity's first screen. The serial console was still in BusyBox wget's ISO download; QEMU peak RSS was 1,870,708,736 B and QEMU CPU 45.56 s. Evidence: `/root/infraternal-bench/pxe/logs/runs/seabios-ubuntu-cache-profile.*`; host load 1.36/1.06/0.66. I am checking whether the QEMU e1000 emulation is limiting the boot measurement before repeating the large-image runs.
Author
Owner

QEMU adapter control: SeaBIOS with QEMU virtio-net-pci and the supplied pxe-virtio.rom did not enter PXE (zero DHCP/TFTP/HTTP requests; screen ended at “No bootable device”), including a second attempt with legacy mode forced. Evidence: /root/infraternal-bench/pxe/logs/runs/seabios-virtio-debian-cache-profile.*; the firmware matrix therefore uses the working e1000 PXE ROM and records that adapter explicitly.

QEMU adapter control: SeaBIOS with QEMU `virtio-net-pci` and the supplied `pxe-virtio.rom` did not enter PXE (zero DHCP/TFTP/HTTP requests; screen ended at “No bootable device”), including a second attempt with legacy mode forced. Evidence: `/root/infraternal-bench/pxe/logs/runs/seabios-virtio-debian-cache-profile.*`; the firmware matrix therefore uses the working e1000 PXE ROM and records that adapter explicitly.
Author
Owner

Debian matrix completed with KVM, QEMU e1000, one client, and the 150.57 ms WireGuard proxy: the extracted kernel/initrd profile reached the language screen in 13.95 s (SeaBIOS/cache), 19.44 s (SeaBIOS/proxy), 19.43 s (OVMF/cache), and 24.41 s (OVMF/proxy); each transferred 36,504,284 HTTP B. HTTP SAN boot reached the Debian installer boot menu in 9.64 s local and 34.57 s proxied. It used 75 local ranges / 553,037 B from the 792,723,456 B ISO; proxy used 74 ranges / 552,960 B, plus 77 B local script, with 574,160 B received from origin and 633,668 B received over WireGuard. Per-run logs and QEMU screenshots are under /root/infraternal-bench/pxe/logs/runs/ with names seabios-e1000-debian-* and ovmf-e1000-debian-*. Host load ranged from 0.40 to 2.02 at run completion.

Debian matrix completed with KVM, QEMU e1000, one client, and the 150.57 ms WireGuard proxy: the extracted kernel/initrd profile reached the language screen in 13.95 s (SeaBIOS/cache), 19.44 s (SeaBIOS/proxy), 19.43 s (OVMF/cache), and 24.41 s (OVMF/proxy); each transferred 36,504,284 HTTP B. HTTP SAN boot reached the Debian installer boot menu in 9.64 s local and 34.57 s proxied. It used 75 local ranges / 553,037 B from the 792,723,456 B ISO; proxy used 74 ranges / 552,960 B, plus 77 B local script, with 574,160 B received from origin and 633,668 B received over WireGuard. Per-run logs and QEMU screenshots are under `/root/infraternal-bench/pxe/logs/runs/` with names `seabios-e1000-debian-*` and `ovmf-e1000-debian-*`. Host load ranged from 0.40 to 2.02 at run completion.
Author
Owner

SystemRescue local-cache profile finding (SeaBIOS/e1000, 2 GiB guest): HTTP delivered the kernel (16,425,472 B), initramfs (184,160,888 B), and full airootfs.sfs (1,154,875,392 B), plus the boot script: 1,355,462,023 B total. The rootfs transfer itself completed in about 15 s (serial curl rate 71.5 MB/s), but after 600 s the guest had not reached its shell; serial output stopped at Mounting /run/archiso/copytoram (tmpfs) filesystem, size=75%. QEMU peak RSS was 2,195,599,360 B. Logs/screens are /root/infraternal-bench/pxe/logs/runs/seabios-e1000-systemrescue-cache-profile.*. I will retry with 4 GiB guest RAM to distinguish a memory limit from a bad boot profile.

SystemRescue local-cache profile finding (SeaBIOS/e1000, 2 GiB guest): HTTP delivered the kernel (16,425,472 B), initramfs (184,160,888 B), and full airootfs.sfs (1,154,875,392 B), plus the boot script: 1,355,462,023 B total. The rootfs transfer itself completed in about 15 s (serial curl rate 71.5 MB/s), but after 600 s the guest had not reached its shell; serial output stopped at `Mounting /run/archiso/copytoram (tmpfs) filesystem, size=75%`. QEMU peak RSS was 2,195,599,360 B. Logs/screens are `/root/infraternal-bench/pxe/logs/runs/seabios-e1000-systemrescue-cache-profile.*`. I will retry with 4 GiB guest RAM to distinguish a memory limit from a bad boot profile.
Author
Owner

SystemRescue boot profile completed after raising client RAM to 4 GiB: SeaBIOS/e1000 reached the automatic root login in 59.63 s from cache and 156.71 s through the 150 ms WireGuard proxy. Both sent 1,355,462,023 HTTP B (kernel 16,425,472 B + initramfs 184,160,888 B + rootfs 1,154,875,392 B + script); QEMU peak RSS was 3,274,588,160 B local and 3,261,648,896 B proxied. Combined Nginx tree peak RSS was 12,234,752 B; CPU was 0.23 s local / 9.60 s proxied. The proxied run received 1,438,693,924 B over WireGuard and sent 7,877,892 B. Evidence: /root/infraternal-bench/pxe/logs/runs/seabios-e1000-systemrescue-{cache,proxy}-profile.*; host load at completion 0.61/0.25/0.29 and 1.72/0.80/0.48 respectively.

SystemRescue boot profile completed after raising client RAM to 4 GiB: SeaBIOS/e1000 reached the automatic root login in 59.63 s from cache and 156.71 s through the 150 ms WireGuard proxy. Both sent 1,355,462,023 HTTP B (kernel 16,425,472 B + initramfs 184,160,888 B + rootfs 1,154,875,392 B + script); QEMU peak RSS was 3,274,588,160 B local and 3,261,648,896 B proxied. Combined Nginx tree peak RSS was 12,234,752 B; CPU was 0.23 s local / 9.60 s proxied. The proxied run received 1,438,693,924 B over WireGuard and sent 7,877,892 B. Evidence: `/root/infraternal-bench/pxe/logs/runs/seabios-e1000-systemrescue-{cache,proxy}-profile.*`; host load at completion 0.61/0.25/0.29 and 1.72/0.80/0.48 respectively.
Author
Owner

Correction and completion of boot-menu timings: a frame audit showed the first OCR-based SAN figures included OCR completion time. Using the first captured frame containing the menu (2 s sample interval), Debian SAN boot reached its menu at 8.08 s local / 35.23 s proxied, reading 553,037 B in 75 requests / 552,960 B in 74 requests from the 792,723,456 B ISO. Ubuntu SAN boot reached “Try or Install Ubuntu Server” at 8.08 s local / 42.13 s proxied, reading 1,521,745 B in 62 requests / 1,652,736 B in 66 requests from the 2,918,598,656 B ISO. Proxy WireGuard receive deltas were 633,668 B Debian and 1,797,832 B Ubuntu. These first screens are boot menus; they do not demonstrate the installer can still read the ISO after kernel handoff. Captures and raw HTTP logs are in /root/infraternal-bench/pxe/logs/runs/seabios-e1000-{debian,ubuntu}-*sanboot.*.

OVMF SystemRescue also reached automatic root login: 55.57 s local and 156.76 s proxied, same 1,355,462,023 B payload; QEMU peak RSS 3.16 GB local / 3.15 GB proxy; serving Nginx tree peak RSS 12,234,752 B. Evidence: /root/infraternal-bench/pxe/logs/runs/ovmf-e1000-systemrescue-{cache,proxy}-profile.*.

Correction and completion of boot-menu timings: a frame audit showed the first OCR-based SAN figures included OCR completion time. Using the first captured frame containing the menu (2 s sample interval), Debian SAN boot reached its menu at 8.08 s local / 35.23 s proxied, reading 553,037 B in 75 requests / 552,960 B in 74 requests from the 792,723,456 B ISO. Ubuntu SAN boot reached “Try or Install Ubuntu Server” at 8.08 s local / 42.13 s proxied, reading 1,521,745 B in 62 requests / 1,652,736 B in 66 requests from the 2,918,598,656 B ISO. Proxy WireGuard receive deltas were 633,668 B Debian and 1,797,832 B Ubuntu. These first screens are boot menus; they do not demonstrate the installer can still read the ISO after kernel handoff. Captures and raw HTTP logs are in `/root/infraternal-bench/pxe/logs/runs/seabios-e1000-{debian,ubuntu}-*sanboot.*`. OVMF SystemRescue also reached automatic root login: 55.57 s local and 156.76 s proxied, same 1,355,462,023 B payload; QEMU peak RSS 3.16 GB local / 3.15 GB proxy; serving Nginx tree peak RSS 12,234,752 B. Evidence: `/root/infraternal-bench/pxe/logs/runs/ovmf-e1000-systemrescue-{cache,proxy}-profile.*`.
Author
Owner

Ubuntu url= full-ISO profile comparison (SeaBIOS/e1000, 4 GiB guest, 360 s cap): neither cache nor proxy reached Subiquity's first screen. The cache run sent 1,327,433,482 B of the 2,918,598,656 B ISO before timeout (1,444,431,525 B total HTTP including kernel/initrd/script). The proxy run sent 1,311,568,608 B of the ISO before timeout (1,428,566,424 B total HTTP including kernel/initrd/script); origin served 1,432,153,093 B and WireGuard received 1,519,101,912 B. QEMU peak RSS was 1,870,708,736 B cache / 1,873,281,024 B proxy; serving Nginx tree peaked at 12,234,752 B. Per-run evidence remains in results.jsonl; the latest proxy serial/HTTP logs are /root/infraternal-bench/pxe/logs/runs/seabios-e1000-ubuntu-proxy-profile.*. Host load at completion was 0.47/0.62/0.60.

Ubuntu `url=` full-ISO profile comparison (SeaBIOS/e1000, 4 GiB guest, 360 s cap): neither cache nor proxy reached Subiquity's first screen. The cache run sent 1,327,433,482 B of the 2,918,598,656 B ISO before timeout (1,444,431,525 B total HTTP including kernel/initrd/script). The proxy run sent 1,311,568,608 B of the ISO before timeout (1,428,566,424 B total HTTP including kernel/initrd/script); origin served 1,432,153,093 B and WireGuard received 1,519,101,912 B. QEMU peak RSS was 1,870,708,736 B cache / 1,873,281,024 B proxy; serving Nginx tree peaked at 12,234,752 B. Per-run evidence remains in `results.jsonl`; the latest proxy serial/HTTP logs are `/root/infraternal-bench/pxe/logs/runs/seabios-e1000-ubuntu-proxy-profile.*`. Host load at completion was 0.47/0.62/0.60.
Author
Owner

Measurement harness 5d42ede9 is committed and pushed on research-pxe-ventoy. It records real SeaBIOS/OVMF runs with local cache and a 150 ms WireGuard path, including time-to-screen, HTTP/tunnel bytes, QEMU and serving-process RSS/CPU, and per-run logs. Debian netinst profile reached its language screen in 13.950 s local / 19.435 s proxied for 36,504,284 B; Debian SANboot reached only its menu in 8.081 s after 553,037 B. SystemRescue reached its root console in 59.626 s local / 156.710 s proxied with a 4 GiB guest. The harness uses e1000 after virtio PXE did not receive boot traffic. Report commit follows.

Measurement harness `5d42ede9` is committed and pushed on `research-pxe-ventoy`. It records real SeaBIOS/OVMF runs with local cache and a 150 ms WireGuard path, including time-to-screen, HTTP/tunnel bytes, QEMU and serving-process RSS/CPU, and per-run logs. Debian netinst profile reached its language screen in 13.950 s local / 19.435 s proxied for 36,504,284 B; Debian SANboot reached only its menu in 8.081 s after 553,037 B. SystemRescue reached its root console in 59.626 s local / 156.710 s proxied with a 4 GiB guest. The harness uses e1000 after virtio PXE did not receive boot traffic. Report commit follows.
Author
Owner

Research report e868e961 is committed and pushed. Short answer: a one-folder catalog can boot a tested set of image families with automatic profiles and a local cache, but unchanged arbitrary ISOs cannot be guaranteed to remain available after kernel handoff. Every LAN still needs an enabled local responder or a verified router/DHCP relay; mesh subnet routing alone does not carry PXE broadcasts. The report includes the per-image behavior, SeaBIOS/OVMF measurements, scope/coexistence analysis, cache/integrity options, reference licenses/sizes, and owner decisions.

Research report `e868e961` is committed and pushed. Short answer: a one-folder catalog can boot a tested set of image families with automatic profiles and a local cache, but unchanged arbitrary ISOs cannot be guaranteed to remain available after kernel handoff. Every LAN still needs an enabled local responder or a verified router/DHCP relay; mesh subnet routing alone does not carry PXE broadcasts. The report includes the per-image behavior, SeaBIOS/OVMF measurements, scope/coexistence analysis, cache/integrity options, reference licenses/sizes, and owner decisions.
Author
Owner

PXE research phase 2 is published on research-pxe-ventoy; head e868e9615fade9c203e9c33978919b773dae4d8a.

Short answer: a one-folder catalog can boot a tested set of image families using automatic profiles and a local cache, but it cannot guarantee arbitrary unchanged media after kernel handoff. Every LAN needs an enabled local responder or a verified relay; a subnet route alone does not carry PXE broadcasts.

Evidence includes the per-image table, SeaBIOS/OVMF cache and 150 ms WireGuard measurements, checksums, component size/license references, and owner decisions. Debian netinst reached its language screen in 13.950 s local / 19.435 s proxied for 36,504,284 B client HTTP; Debian SANboot reached only the menu in 8.081 s after 553,037 B. SystemRescue reached its root console in 59.626 s local / 156.710 s proxied with a 4 GiB guest. Windows was not measured because the Debian VM had no Windows ADK build host.

The full-workspace test replay reproduced infraternal::agent_daemon::real_binary_preserves_input_and_output_across_24_abrupt_stops: the second terminal.open returned terminal open refused. This is outside the specified host-load baseline exceptions. The static x86_64 binary also exceeded its size budget. These commits change only research files; the product crates are unchanged. The failing core test and static-size budget need follow-up outside this research-only lane.

Initial scripts/verify fast final output (verbatim):

    Finished `release` profile [optimized] target(s) in 44m 05s
target/x86_64-unknown-linux-musl/release/infraternal: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), static-pie linked, stripped
PT_INTERP: absent; size: 20614656 bytes (baseline 16142672 + allowance 262144 = max 16404816)
binary exceeds the 16404816-byte size budget: 20614656 bytes

+---------------------------+--------------+
| Rust gate                 | Result       |
+---------------------------+--------------+
| fmt                       | PASS         |
| VT native fmt             | PASS         |
| clippy                    | PASS         |
| test                      | FAIL (101)   |
| cargo-deny                | PASS         |
| static builds             | FAIL (1)     |
+---------------------------+--------------+
PXE research phase 2 is published on `research-pxe-ventoy`; head `e868e9615fade9c203e9c33978919b773dae4d8a`. Short answer: a one-folder catalog can boot a tested set of image families using automatic profiles and a local cache, but it cannot guarantee arbitrary unchanged media after kernel handoff. Every LAN needs an enabled local responder or a verified relay; a subnet route alone does not carry PXE broadcasts. Evidence includes the per-image table, SeaBIOS/OVMF cache and 150 ms WireGuard measurements, checksums, component size/license references, and owner decisions. Debian netinst reached its language screen in 13.950 s local / 19.435 s proxied for 36,504,284 B client HTTP; Debian SANboot reached only the menu in 8.081 s after 553,037 B. SystemRescue reached its root console in 59.626 s local / 156.710 s proxied with a 4 GiB guest. Windows was not measured because the Debian VM had no Windows ADK build host. The full-workspace test replay reproduced `infraternal::agent_daemon::real_binary_preserves_input_and_output_across_24_abrupt_stops`: the second `terminal.open` returned `terminal open refused`. This is outside the specified host-load baseline exceptions. The static x86_64 binary also exceeded its size budget. These commits change only research files; the product crates are unchanged. The failing core test and static-size budget need follow-up outside this research-only lane. Initial `scripts/verify fast` final output (verbatim): ```text Finished `release` profile [optimized] target(s) in 44m 05s target/x86_64-unknown-linux-musl/release/infraternal: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), static-pie linked, stripped PT_INTERP: absent; size: 20614656 bytes (baseline 16142672 + allowance 262144 = max 16404816) binary exceeds the 16404816-byte size budget: 20614656 bytes +---------------------------+--------------+ | Rust gate | Result | +---------------------------+--------------+ | fmt | PASS | | VT native fmt | PASS | | clippy | PASS | | test | FAIL (101) | | cargo-deny | PASS | | static builds | FAIL (1) | +---------------------------+--------------+ ```
Author
Owner

Additional gate diagnostic: a later scripts/verify fast replay stopped at the latency preflight under higher shared-host load: configured 300 ms RTT did not arrive; p50=604.75 ms, p99=954.84 ms. The initial full gate invocation passed that preflight (p50=318.06 ms, p99=332.76 ms) before failing the test and static-build rows recorded above. No product files changed. Head remains e868e9615fade9c203e9c33978919b773dae4d8a; short answer remains that supported profiles can boot from one catalog, but arbitrary unchanged image handoff and remote-LAN PXE discovery are not universal.

Additional gate diagnostic: a later `scripts/verify fast` replay stopped at the latency preflight under higher shared-host load: configured 300 ms RTT did not arrive; p50=604.75 ms, p99=954.84 ms. The initial full gate invocation passed that preflight (p50=318.06 ms, p99=332.76 ms) before failing the test and static-build rows recorded above. No product files changed. Head remains `e868e9615fade9c203e9c33978919b773dae4d8a`; short answer remains that supported profiles can boot from one catalog, but arbitrary unchanged image handoff and remote-LAN PXE discovery are not universal.
Author
Owner

PXE grill round 1 — owner answers 2026-10-12:

  • P1 (b) curated profiles + "Try anyway" (may stop after the boot menu). Asked: Windows images legally; PXE over the mesh vs subnet routes.
  • P2 (a) cache on the LAN boot node + "Prepare for ".
  • P3 (a) a node on that LAN answers boot requests next to existing DHCP, off by default — asked how to make it reliable.
  • P4 agreed (next machine that asks / MAC, one-time, 1 h, one-time enroll token, Inbox quarantine; "any machine on " only as an explicit time-limited rule).
  • P5 asked how the infraternal agent gets onto the installed machine; wants it to join the mesh by itself.
  • P6 agreed (UEFI + BIOS first; Secure Boot and Windows later) — failures explained in plain human language.
  • P7 agreed: own Rust boot-request/TFTP/HTTP in the plugin, iPXE shipped as separate boot files with per-build licence check; measure against dnsmasq before shipping.
  • P8 the section is called "Boot Machines", off by default.
PXE grill round 1 — owner answers 2026-10-12: - P1 (b) curated profiles + "Try anyway" (may stop after the boot menu). Asked: Windows images legally; PXE over the mesh vs subnet routes. - P2 (a) cache on the LAN boot node + "Prepare for <LAN>". - P3 (a) a node on that LAN answers boot requests next to existing DHCP, off by default — asked how to make it reliable. - P4 agreed (next machine that asks / MAC, one-time, 1 h, one-time enroll token, Inbox quarantine; "any machine on <LAN>" only as an explicit time-limited rule). - P5 asked how the infraternal agent gets onto the installed machine; wants it to join the mesh by itself. - P6 agreed (UEFI + BIOS first; Secure Boot and Windows later) — failures explained in plain human language. - P7 agreed: own Rust boot-request/TFTP/HTTP in the plugin, iPXE shipped as separate boot files with per-build licence check; measure against dnsmasq before shipping. - P8 the section is called "Boot Machines", off by default.
Author
Owner

PXE grill round 2 — owner answers 2026-10-12:

  • P3 approved: one answering node per LAN, interference detection with plain messages, "Test this LAN" VM, live boot log, fallback (DHCP options or USB boot stick), firmware test list.
  • P5 approved, plus: show the installing machine live on the canvas (cherry on top).
  • P9 yes: we modify official images (answer file, infraternal agent) and must prevent tampering — verify the original against the signed upstream checksum list, build derived boot files locally, record their hashes, serve only those exact bytes; dropped-in images approved by hash once.
  • P10 approved: user images durable in /var/lib/infraternal/boot-images (rootless ~/.local/share/...), downloaded/cached images evictable in /var/cache/infraternal/boot (rootless ~/.cache/...), size limit configurable.
PXE grill round 2 — owner answers 2026-10-12: - P3 approved: one answering node per LAN, interference detection with plain messages, "Test this LAN" VM, live boot log, fallback (DHCP options or USB boot stick), firmware test list. - P5 approved, plus: show the installing machine live on the canvas (cherry on top). - P9 yes: we modify official images (answer file, infraternal agent) and must prevent tampering — verify the original against the signed upstream checksum list, build derived boot files locally, record their hashes, serve only those exact bytes; dropped-in images approved by hash once. - P10 approved: user images durable in /var/lib/infraternal/boot-images (rootless ~/.local/share/...), downloaded/cached images evictable in /var/cache/infraternal/boot (rootless ~/.cache/...), size limit configurable.
Author
Owner

Boot Machines, mockup round 1 (D162): branch mockup-boot-r1 (pushed, head d9564c89, from origin/mockup-mesh-r1). Mock only: everything runs against the test double behind the existing seam, with the MOCKUP and TEST DOUBLE badges. Nothing is wired to a backend. D253 item 3 is built as the owner changed it: the installing machine's screen streamed into an app window, not a text mirror.

URLs to open (on an owner preview of this branch, <preview> = e.g. 47401)

  • Boot Machines off, as the product ships it: <preview>/?mock=1&proto=clusters&scene=1&mesh=r1&boot=r1
  • lab-lan on, home-lan answering a problem: <preview>/?mock=1&proto=clusters&scene=1&mesh=r1&boot=r1-on
  • Extra switches: &boot-hold=1 (the imitated install waits where reviewers put it), &boot-speed=3 (faster), &mesh-default=deny (the Inbox preview changes sentence), &mesh-layout=list.

Where things are (all in the product's own places):

  • Settings view, the window right after Access: Boot Machines (admin only, listed only when a source provides it).
  • Boot a machine: ⌘K "Boot a machine"; the boot node's card in the Mesh (tap infraternal-dev or o2, then the "Boot a machine" button under its details, which also gain a "Boot server" row); and a toolbar item (Settings → Toolbar can show it, same as "Add host"). Pressing Start turns the same window into the live install window.
  • Inbox: the sidebar card, when the imitated machine finishes ("New machine: debian-7f3a"). A toast announces it once.
  • Reviewer moves: window.__tracerClusters.boot.state.jump('installing', 61) with boot-hold=1; .fail('secure-boot' | 'nic').

What each screen shows

  1. Settings → Boot Machines: one switch per node ("Boot server on lab-lan · infraternal-dev"), a health line per LAN (green Ready, or "Another boot server (192.168.1.5) is answering on home-lan. Turn it off, or let it handle booting." with both buttons), Test this LAN (steps, then "A test machine booted Debian's installer on lab-lan in 14 s"), the live boot log per LAN with the failures in plain words (Secure Boot; a network card that ignored the answer, the two DHCP settings as chips, "Or use a USB boot stick" Download), the images (curated "verified · signed by Debian", dropped-in "approved by you · sha256 9f3a07d2…c41e", an unknown ISO with "may stop after the boot menu" and Try anyway), cache size and limit per LAN, Prepare for lab-lan (fetching progress), and Get Windows from Microsoft (external link; "We never host Windows"). "PXE" appears once, in the first help line.
  2. Boot a machine: the add-host flow's own floating card (same classes, sign-in type values, 48 px fields, 42/44 px button). One field for "the next machine that asks" or a MAC address; With (select, unknown images marked "may stop after the boot menu", uncached ones "downloads first"); On (LAN with ready/off/needs attention); install choices folded under one line (whole disk, Europe/Berlin, your SSH key); the live sentence "The next machine that asks can boot Debian 13 on lab-lan for 1 hour. It installs, joins your mesh, then waits in your Inbox for approval."; Start. A LAN that is off shows the way forward in place ("Turn it on for lab-lan"); a LAN with a problem says so and links to Settings.
  3. Live install window (one window with the flow: Start turns it into this): six-segment progress line on top (Waiting for a machine → Booting (UEFI) → Downloading image 38% → Installing 61% → Adding infraternal agent → Joining), then a mock graphical installer drawn in the window (no vendor marks, light colours in every theme because it is another machine's display). Before an installer runs it says "The screen appears once the installer starts." View only until Take control; a small terminal button opens the text console as a second window. After approval: login screen and Open terminal (a shell window on the new machine).
  4. Live boot log: in Settings, newest first, new lines slide in ("02:7a:b3:7f:3a:19 asked to boot (UEFI) → sent Debian 13 → installing → joined as debian-7f3a, waiting in your Inbox").
  5. Inbox item: "New machine: debian-7f3a" with what approving allows (reads the mesh default: "reach every other machine on all ports, because machines reach each other until you add rules", or "no reach yet" with deny-by-default) and who can log in; Remove, Approve. After Approve the mesh gains debian-7f3a.

Captures

apps/tracer/captures/boot-r1/ (192 files: <state>-<size>-<theme>.png; sizes desktop 1440x900, phone 393x852, small 375x667 for the text-heavy screens; ink and paper). Absolute: /home/kayg/Developer/infraternal/.worktrees/mockup-boot-r1/apps/tracer/captures/boot-r1/.

  • s1 settings off · s2 images off · s3 on · s4 test running · s5 test result · s6 LAN problem · s7 images · s8 preparing · s9 dropped-in and Windows link
  • f1 flow · f2 image list · f3 unknown image + install choices · f4 bad MAC · f5 LAN problem · f6 LAN off, way forward · f7 turned on · f8 started
  • i1 waiting · i2 booting · i3 downloading 38% · i4 installing 61% · i5 adding agent · i6 joining · i7 take control · i8 text console · x1 Secure Boot · x2 network card
  • n1 approval + toast · n2 Inbox item · n3 approved · n4 Open terminal · n5 Inbox item with deny by default · n6 removed
  • m1 the boot node's card in the Mesh · m2 the flow from it, lab-lan preselected

Measurements

  • Frame times while an install runs (9 s in the page; the build host was shared and loaded, 12-30 on 12 cores): median 16.7 ms (60 fps) in all four runs. 95th percentile 16.7 ms on both phone runs, 33.3 ms desktop paper, 50 ms desktop ink (host load). Motion is transform and opacity only (segments, meter, picture fade).
  • Work per progress update (synchronous paint of the window and Settings, 300 samples): p50 0.5-1.1 ms, p95 1.0-4.2 ms; a step change p50 0.4-1.1 ms.
  • Controls: select field 48 px, Start 42 px desktop / 44 px touch, touch targets 44 px (asserted in the spec). Type roles are the add-host card's: title 21 px (23 px under 480), lede 14, label 13, field 14.
  • D188 budgets (bun run build && bun run transfer-budget.ts, exit 0, never raised). Against the round-1 Mesh tree: critical gzip 294,951 to 294,974 (+23 B, limit 307,200); deferred gzip 49,760 to 49,855 (+95 B, limit 51,200), brotli 43,943 to 44,049 (+106 B, limit 45,056). Only the product seams are in those (the section id, one icon, one toolbar item). No mock code in the production bundle (the mock and its stylesheet are copied only into preview builds).

Gates (verbatim)

bun run check                        -> tsc: no errors
bun test src                         -> 185 pass, 0 fail, 11032 expect() calls (5 new: boot-r1/state.test.ts)
bun run build && bun run transfer-budget.ts -> exit 0 (numbers above)
TRACER_TEST_PORT=4993 playwright test boot-r1-captures
   -> first full run 38 passed, 10 failed (thresholds of the new numbers tests, corrected in the spec);
   -> rerun after the fixes: 38 passed (numbers, install, inbox, small), 10 passed (small), 20 passed (flow, inbox; the final code)

scripts/verify fast was not run: this branch changes only TypeScript, CSS and capture files, and the Rust gates take over 40 minutes on the loaded build host (and an earlier run on this host failed on unrelated static-size and test items, see the research comments). The TypeScript half of it (tracer compiler, bun tests, build, budget) is what is quoted above.

TASTE.md rows checked, and how

No rings from mouse or keys (clicked every control; spec asserts the ring flag is off after clicks and on only after Tab) · selection is quiet (select rows: faint fill only; switches change only themselves) · no fake glass (flat fills and hairlines; the card uses the shared overlay material) · no settings inside a flow (install choices folded under one line, see question 2) · one input, not modes (one "which machine" field) · match the existing look (the add-host card's classes and the Access window's rows) · mono everywhere · typography (computed values logged by the spec) · platform-sized controls (measured) · icons over text (terminal button is an icon with a tooltip; other actions have no unambiguous icon and are named) · every state change animates (select list, install choices, status line morph, segments, cache meter, log lines, flow-to-install handoff; reduced-motion safe) · work is instant (update cost above) · a flow lives inside a window card and becomes the result (one window from Start to install) · plain wording (no "grant", "policy"; "PXE" once; "infraternal agent" in full) · text never collides (393 and 375 captures; a select-row overlap and a wrapped tick were found there and fixed) · the icon matches the news (waiting for approval is neutral, tick only when the machine is part of the mesh, failures use the alert mark) · pending actions come to the person (toast, then the Inbox until decided; the toast goes when it is) · offer the way forward (LAN off: "Turn it on for lab-lan" in place) · the inbox is one generic card (one item, same row) · errors sit by the action (failures above the actions that fix them) · no control looks dead (Test this LAN is disabled only with the reason right above it).

Found and fixed while reading the captures: select rows overlapping at 393 px, a select field overflowing its card, the way-forward notice below the fold on phones, a green tick for a machine that is only waiting, the tick wrapped onto its own line in the mock installer at 375 px, a stale toast after removal.

Design questions, with my recommendation

  1. Where does "Boot a machine" live? There is no "+ menu" in this build (the + opens a new shell). It is in ⌘K, the toolbar and the boot node's card. Recommend: make + a small menu (New window, Add host, Boot a machine) once there are two or more entries; until then keep the three paths above.
  2. Install choices (disk, timezone, SSH key) in the flow or in Settings? TASTE says no settings inside a flow. Recommend: defaults live in Settings → Boot Machines ("When a machine installs"), the flow shows only the summary line plus "Change for this one" (what is built now, folded).
  3. "Let it handle booting" next to another boot server. Built as: our node steps off. Recommend replacing it with "Show the two settings to add on 192.168.1.5" (what actually makes that server boot our images), keeping "Turn it off".
  4. Cache limit. Shown ("9.1 GB of 20 GB"), not editable. Recommend an inline "20 GB" field in that row, one per LAN, applied on blur.
  5. Boot log: Settings or its own window? Per LAN in Settings, because it is the answer to "why did that machine not boot". Recommend keeping it there and adding "Open as window" only if the owner wants it beside the install.
  6. Take control. Off by default, with the hint beside it. Recommend: Escape releases control, and the toggle turns itself off when the installer finishes.
  7. Remove. Burns the offer (one-time) and forgets the machine; the install window says so. Recommend keeping it that way, and offering "Boot a machine again" in the removed state.
  8. Inbox preview. Plain lines now. Recommend a ghost node with its would-be arrows in the Mesh while the item is open, as a second round.
  9. Unknown image, "Try anyway". Only in Settings (approve by hash). Recommend also offering "Approve this file" inline in the flow's image list, since that is where the person meets the warning.
  10. Offer countdown. The offer lasts one hour; the waiting state does not show it. Recommend "Offer ends in 58 minutes" under the progress line while waiting.
Boot Machines, mockup round 1 (D162): branch `mockup-boot-r1` (pushed, head d9564c89, from `origin/mockup-mesh-r1`). Mock only: everything runs against the test double behind the existing seam, with the MOCKUP and TEST DOUBLE badges. Nothing is wired to a backend. D253 item 3 is built as the owner changed it: the installing machine's screen streamed into an app window, not a text mirror. ## URLs to open (on an owner preview of this branch, `<preview>` = e.g. 47401) - Boot Machines **off**, as the product ships it: `<preview>/?mock=1&proto=clusters&scene=1&mesh=r1&boot=r1` - lab-lan **on**, home-lan answering a problem: `<preview>/?mock=1&proto=clusters&scene=1&mesh=r1&boot=r1-on` - Extra switches: `&boot-hold=1` (the imitated install waits where reviewers put it), `&boot-speed=3` (faster), `&mesh-default=deny` (the Inbox preview changes sentence), `&mesh-layout=list`. Where things are (all in the product's own places): - Settings view, the window right after Access: **Boot Machines** (admin only, listed only when a source provides it). - Boot a machine: ⌘K "Boot a machine"; the boot node's card in the Mesh (tap infraternal-dev or o2, then the "Boot a machine" button under its details, which also gain a "Boot server" row); and a toolbar item (Settings → Toolbar can show it, same as "Add host"). Pressing Start turns the same window into the live install window. - Inbox: the sidebar card, when the imitated machine finishes ("New machine: debian-7f3a"). A toast announces it once. - Reviewer moves: `window.__tracerClusters.boot.state.jump('installing', 61)` with `boot-hold=1`; `.fail('secure-boot' | 'nic')`. ## What each screen shows 1. **Settings → Boot Machines**: one switch per node ("Boot server on lab-lan · infraternal-dev"), a health line per LAN (green Ready, or "Another boot server (192.168.1.5) is answering on home-lan. Turn it off, or let it handle booting." with both buttons), **Test this LAN** (steps, then "A test machine booted Debian's installer on lab-lan in 14 s"), the live boot log per LAN with the failures in plain words (Secure Boot; a network card that ignored the answer, the two DHCP settings as chips, "Or use a USB boot stick" Download), the images (curated "verified · signed by Debian", dropped-in "approved by you · sha256 9f3a07d2…c41e", an unknown ISO with "may stop after the boot menu" and **Try anyway**), cache size and limit per LAN, **Prepare for lab-lan** (fetching progress), and **Get Windows from Microsoft** (external link; "We never host Windows"). "PXE" appears once, in the first help line. 2. **Boot a machine**: the add-host flow's own floating card (same classes, sign-in type values, 48 px fields, 42/44 px button). One field for "the next machine that asks" or a MAC address; With (select, unknown images marked "may stop after the boot menu", uncached ones "downloads first"); On (LAN with ready/off/needs attention); install choices folded under one line (whole disk, Europe/Berlin, your SSH key); the live sentence "The next machine that asks can boot Debian 13 on lab-lan for 1 hour. It installs, joins your mesh, then waits in your Inbox for approval."; Start. A LAN that is off shows the way forward in place ("Turn it on for lab-lan"); a LAN with a problem says so and links to Settings. 3. **Live install window** (one window with the flow: Start turns it into this): six-segment progress line on top (Waiting for a machine → Booting (UEFI) → Downloading image 38% → Installing 61% → Adding infraternal agent → Joining), then a mock graphical installer drawn in the window (no vendor marks, light colours in every theme because it is another machine's display). Before an installer runs it says "The screen appears once the installer starts." View only until **Take control**; a small terminal button opens the text console as a second window. After approval: login screen and **Open terminal** (a shell window on the new machine). 4. **Live boot log**: in Settings, newest first, new lines slide in ("02:7a:b3:7f:3a:19 asked to boot (UEFI) → sent Debian 13 → installing → joined as debian-7f3a, waiting in your Inbox"). 5. **Inbox item**: "New machine: debian-7f3a" with what approving allows (reads the mesh default: "reach every other machine on all ports, because machines reach each other until you add rules", or "no reach yet" with deny-by-default) and who can log in; Remove, Approve. After Approve the mesh gains debian-7f3a. ## Captures `apps/tracer/captures/boot-r1/` (192 files: `<state>-<size>-<theme>.png`; sizes desktop 1440x900, phone 393x852, small 375x667 for the text-heavy screens; ink and paper). Absolute: `/home/kayg/Developer/infraternal/.worktrees/mockup-boot-r1/apps/tracer/captures/boot-r1/`. - s1 settings off · s2 images off · s3 on · s4 test running · s5 test result · s6 LAN problem · s7 images · s8 preparing · s9 dropped-in and Windows link - f1 flow · f2 image list · f3 unknown image + install choices · f4 bad MAC · f5 LAN problem · f6 LAN off, way forward · f7 turned on · f8 started - i1 waiting · i2 booting · i3 downloading 38% · i4 installing 61% · i5 adding agent · i6 joining · i7 take control · i8 text console · x1 Secure Boot · x2 network card - n1 approval + toast · n2 Inbox item · n3 approved · n4 Open terminal · n5 Inbox item with deny by default · n6 removed - m1 the boot node's card in the Mesh · m2 the flow from it, lab-lan preselected ## Measurements - Frame times while an install runs (9 s in the page; the build host was shared and loaded, 12-30 on 12 cores): median 16.7 ms (60 fps) in all four runs. 95th percentile 16.7 ms on both phone runs, 33.3 ms desktop paper, 50 ms desktop ink (host load). Motion is transform and opacity only (segments, meter, picture fade). - Work per progress update (synchronous paint of the window and Settings, 300 samples): p50 0.5-1.1 ms, p95 1.0-4.2 ms; a step change p50 0.4-1.1 ms. - Controls: select field 48 px, Start 42 px desktop / 44 px touch, touch targets 44 px (asserted in the spec). Type roles are the add-host card's: title 21 px (23 px under 480), lede 14, label 13, field 14. - D188 budgets (`bun run build && bun run transfer-budget.ts`, exit 0, never raised). Against the round-1 Mesh tree: critical gzip 294,951 to 294,974 (+23 B, limit 307,200); deferred gzip 49,760 to 49,855 (+95 B, limit 51,200), brotli 43,943 to 44,049 (+106 B, limit 45,056). Only the product seams are in those (the section id, one icon, one toolbar item). No mock code in the production bundle (the mock and its stylesheet are copied only into preview builds). ## Gates (verbatim) ``` bun run check -> tsc: no errors bun test src -> 185 pass, 0 fail, 11032 expect() calls (5 new: boot-r1/state.test.ts) bun run build && bun run transfer-budget.ts -> exit 0 (numbers above) TRACER_TEST_PORT=4993 playwright test boot-r1-captures -> first full run 38 passed, 10 failed (thresholds of the new numbers tests, corrected in the spec); -> rerun after the fixes: 38 passed (numbers, install, inbox, small), 10 passed (small), 20 passed (flow, inbox; the final code) ``` `scripts/verify fast` was not run: this branch changes only TypeScript, CSS and capture files, and the Rust gates take over 40 minutes on the loaded build host (and an earlier run on this host failed on unrelated static-size and test items, see the research comments). The TypeScript half of it (tracer compiler, bun tests, build, budget) is what is quoted above. ## TASTE.md rows checked, and how No rings from mouse or keys (clicked every control; spec asserts the ring flag is off after clicks and on only after Tab) · selection is quiet (select rows: faint fill only; switches change only themselves) · no fake glass (flat fills and hairlines; the card uses the shared overlay material) · no settings inside a flow (install choices folded under one line, see question 2) · one input, not modes (one "which machine" field) · match the existing look (the add-host card's classes and the Access window's rows) · mono everywhere · typography (computed values logged by the spec) · platform-sized controls (measured) · icons over text (terminal button is an icon with a tooltip; other actions have no unambiguous icon and are named) · every state change animates (select list, install choices, status line morph, segments, cache meter, log lines, flow-to-install handoff; reduced-motion safe) · work is instant (update cost above) · a flow lives inside a window card and becomes the result (one window from Start to install) · plain wording (no "grant", "policy"; "PXE" once; "infraternal agent" in full) · text never collides (393 and 375 captures; a select-row overlap and a wrapped tick were found there and fixed) · the icon matches the news (waiting for approval is neutral, tick only when the machine is part of the mesh, failures use the alert mark) · pending actions come to the person (toast, then the Inbox until decided; the toast goes when it is) · offer the way forward (LAN off: "Turn it on for lab-lan" in place) · the inbox is one generic card (one item, same row) · errors sit by the action (failures above the actions that fix them) · no control looks dead (Test this LAN is disabled only with the reason right above it). Found and fixed while reading the captures: select rows overlapping at 393 px, a select field overflowing its card, the way-forward notice below the fold on phones, a green tick for a machine that is only waiting, the tick wrapped onto its own line in the mock installer at 375 px, a stale toast after removal. ## Design questions, with my recommendation 1. **Where does "Boot a machine" live?** There is no "+ menu" in this build (the + opens a new shell). It is in ⌘K, the toolbar and the boot node's card. Recommend: make + a small menu (New window, Add host, Boot a machine) once there are two or more entries; until then keep the three paths above. 2. **Install choices (disk, timezone, SSH key) in the flow or in Settings?** TASTE says no settings inside a flow. Recommend: defaults live in Settings → Boot Machines ("When a machine installs"), the flow shows only the summary line plus "Change for this one" (what is built now, folded). 3. **"Let it handle booting" next to another boot server.** Built as: our node steps off. Recommend replacing it with "Show the two settings to add on 192.168.1.5" (what actually makes that server boot our images), keeping "Turn it off". 4. **Cache limit.** Shown ("9.1 GB of 20 GB"), not editable. Recommend an inline "20 GB" field in that row, one per LAN, applied on blur. 5. **Boot log: Settings or its own window?** Per LAN in Settings, because it is the answer to "why did that machine not boot". Recommend keeping it there and adding "Open as window" only if the owner wants it beside the install. 6. **Take control.** Off by default, with the hint beside it. Recommend: Escape releases control, and the toggle turns itself off when the installer finishes. 7. **Remove.** Burns the offer (one-time) and forgets the machine; the install window says so. Recommend keeping it that way, and offering "Boot a machine again" in the removed state. 8. **Inbox preview.** Plain lines now. Recommend a ghost node with its would-be arrows in the Mesh while the item is open, as a second round. 9. **Unknown image, "Try anyway".** Only in Settings (approve by hash). Recommend also offering "Approve this file" inline in the flow's image list, since that is where the person meets the warning. 10. **Offer countdown.** The offer lasts one hour; the waiting state does not show it. Recommend "Offer ends in 58 minutes" under the progress line while waiting.
Author
Owner

Rebuilt on current dev for the owner's review. Branch mockups-2026-10-31, head 586cd2b13 (base dev 42ab33035, 2026-10-31). Test double only; nothing is real or saved. Not merged, not deployed. Old previews are gone; this replaces them.

Preview (NetBird, bound to infraternal-dev-02-std; index of every mockup: http://10.69.69.117:47650/mockups.html):

How: Palette: "Settings: Boot Machines" and "Boot a machine" (Start turns the window into the live install). boot=r1 is how the product ships it (off), boot=r1-on has lab-lan on.

Note: Not in this build: the boot node on the Mesh graph and its card action. Round 1 sat on the Mesh round 1 mockup, which cannot merge onto dev's rebuilt Mesh view without a new design round. Settings, the flow, the live install window and the Inbox item are all here.

Captures are Chromium on the production build of the mockup, taken by apps/tracer/test/capture-mockups.ts; I have read them for wrong states, not judged them as final.

Desktop 1440×900 @2x, ink

boot-a-machine
install-window
settings
settings-off

Desktop 1440×900 @2x, paper

boot-a-machine
install-window
settings
settings-off

Phone 393×852 @3x, ink

boot-a-machine
install-window
settings-off
settings

Phone 393×852 @3x, paper (first state only)

boot-a-machine
settings-off
settings

Rebuilt on current dev for the owner's review. Branch `mockups-2026-10-31`, head `586cd2b13` (base dev `42ab33035`, 2026-10-31). Test double only; nothing is real or saved. Not merged, not deployed. Old previews are gone; this replaces them. **Preview** (NetBird, bound to infraternal-dev-02-std; index of every mockup: http://10.69.69.117:47650/mockups.html): - http://10.69.69.117:47650/?mock=1&proto=clusters&scene=1&boot=r1 - http://10.69.69.117:47650/?mock=1&proto=clusters&scene=1&boot=r1-on **How:** Palette: "Settings: Boot Machines" and "Boot a machine" (Start turns the window into the live install). `boot=r1` is how the product ships it (off), `boot=r1-on` has lab-lan on. **Note:** **Not in this build:** the boot node on the Mesh graph and its card action. Round 1 sat on the Mesh round 1 mockup, which cannot merge onto dev's rebuilt Mesh view without a new design round. Settings, the flow, the live install window and the Inbox item are all here. Captures are Chromium on the production build of the mockup, taken by `apps/tracer/test/capture-mockups.ts`; I have read them for wrong states, not judged them as final. **Desktop 1440×900 @2x, ink** ![boot-a-machine](https://git.kayg.org/attachments/67f96f3b-c61a-475c-b3be-55114a5901fd) ![install-window](https://git.kayg.org/attachments/c376a158-11ab-4542-87a0-5c6c28d0501c) ![settings](https://git.kayg.org/attachments/1deb8e88-5048-4dff-9126-4dbe2456b996) ![settings-off](https://git.kayg.org/attachments/f357dd5a-eb0e-4e54-9f75-30f1c8a38e02) **Desktop 1440×900 @2x, paper** ![boot-a-machine](https://git.kayg.org/attachments/c9da9985-8ac2-44d8-9fd5-30f53d9272f6) ![install-window](https://git.kayg.org/attachments/a638ef87-5c38-4135-9234-9926b983ebae) ![settings](https://git.kayg.org/attachments/a9fc7502-b9d0-4252-8da7-23c9bd73fa6f) ![settings-off](https://git.kayg.org/attachments/b135f0ad-02c4-4a00-a1d3-3391f8068da2) **Phone 393×852 @3x, ink** ![boot-a-machine](https://git.kayg.org/attachments/1f9fe47b-f0a6-4c6a-b8c8-ef79000ae70d) ![install-window](https://git.kayg.org/attachments/b0123a16-6d49-4d50-aac0-6809a643dccc) ![settings-off](https://git.kayg.org/attachments/022ed651-8722-497a-9d23-f28ff4a52752) ![settings](https://git.kayg.org/attachments/b4382a56-267f-4028-bd2b-3bef295e0137) **Phone 393×852 @3x, paper (first state only)** ![boot-a-machine](https://git.kayg.org/attachments/859b5d3d-a642-4df9-ba09-751508a2be2e) ![settings-off](https://git.kayg.org/attachments/6444f76e-ff85-45b3-bf64-79cdd8fb53fb) ![settings](https://git.kayg.org/attachments/7ea3fc81-6192-4fd0-a970-718606a0ab30)
Author
Owner

Update to the comment above: the branch head is now 57871651f (the preview at http://10.69.69.117:47650/mockups.html runs it). The captures above were taken one build earlier; the only difference is that the window terminals there hide their cursor until attached, a production change that was since removed from the branch. Gate output, what is left out, and the budget finding: #272.

Update to the comment above: the branch head is now `57871651f` (the preview at http://10.69.69.117:47650/mockups.html runs it). The captures above were taken one build earlier; the only difference is that the window terminals there hide their cursor until attached, a production change that was since removed from the branch. Gate output, what is left out, and the budget finding: #272.
Sign in to join this conversation.
No labels
launch-qa
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
kayg/infraternal#156
No description provided.