diff --git a/FABRIC-3.md b/FABRIC-3.md index 033029e..c559263 100644 --- a/FABRIC-3.md +++ b/FABRIC-3.md @@ -1528,3 +1528,70 @@ partial write (READ10's PASS/FAILED logic likely transfers unchanged, not indepe verified); whether a write needs a follow-up `TEST UNIT READY` or cache-flush SCSI command before the transfer is considered durable on real media (QEMU's `usb-storage` backend may mask this — a real-hardware-only question, revisit at Milestone 8). + +### F.2 — `ACLKEY` (the "bumps and holes" comparison semantics) + +Traced against the actual code before asking anything: `acl_mode`/`acl_allow`/`acl_pinned` +(`include/vm.h:343-346`, `src/word_source/acl_words.c`) are **`DictEntry` fields — per word, +not per VM.** There is no VM-level ACL structure anywhere today. So D.3/D.4's "reuse the +existing ACL primitive" resolution can only ever have meant reuse the *pattern* (a cached +decision plus a C-enforced one-way ratchet — `if (e->acl_pinned) return;` at every mutating +primitive) — the actual data has to live somewhere new. `sk_repl_set_active_vm()` +(`starkernel/repl.c:64`) is confirmed to be exactly what its own doc comment says: an +unguarded raw pointer swap, no credential concept at all. + +**Decisions made 2026-08-27 (iterative Q&A pass):** + +1. **Where the lock lives.** A new dedicated type in its own header — + `include/starkernel/vm_identity.h`, a `VMIdentity { uint8_t owner_pubkey[32]; uint8_t + installed; }` — embedded by value as a field on `struct VM`, exactly the way `VMUuid + stadium_vm_id` (`vm_uuid.h`, its own header, embedded field) already does. **Explicit + standing instruction from Captain Bob**: don't grow `struct VM`/`vm.h` feature-by-feature + with more inline fields — when a feature's data has real shape, it gets its own header and + gets *integrated* as a field, not inlined ad hoc. `VMUuid` was already the right precedent; + `VMIdentity` follows it. Deliberately holds only the public key, not a seed — unlike + Zuse's own `zuse_cert_seed`/`zuse_cert_pubkey` pair, a regular VM's lock never needs to + sign anything itself, so no private material belongs on it at all. +2. **Zuse override.** Zuse keeps an always-allowed override to attach to any VM (consistent + with the existing `emergency_console`/`zuse_session` bypass precedent, and avoids the + bricking risk of Zuse ever being locked out of a VM by its own cert state) — **but the + override must be a distinct, explicit call path** (e.g. a separate function/word, not a + silently-taken branch inside the normal bind check), so invoking it requires a deliberate + acknowledgment rather than happening as a side effect of an ordinary bind attempt. Exact + acknowledgment UX (a confirm prompt? a two-step word?) is not designed yet — the + architectural commitment is only that it can't be silent. +3. **Binding pin.** No pin. `sk_repl_set_active_vm()` stays freely retargetable — matches + today's Tripod-fleet `USE`-word behavior, and is needed for real cases where a single + console legitimately moves between VMs mid-session (Zuse doing maintenance work in another + service VM; a user's console retargeting to update something in a second VM they own). The + credential check runs at each bind call, not just once at first attach. + +**Not yet scoped (deferred within this node):** the exact acknowledgment UX for the Zuse +override path; whether `VMIdentity.installed` needs its own one-way fuse semantics (probably +yes — the *lock itself* being immutable once set at a VM's birth is a different axis from +"binding stays retargetable," and shouldn't be conflated with decision 3 above) — worth a +dedicated look when this is actually built, not decided in this pass. + +### D.5 — Scope expansion (2026-08-27): identity is common to every VM, not just users + +Surfaced while scoping `ACLKEY`, stated directly: *"the whole object is to deliver a +functional Tripod plus identities common to all VM's... this means now that we have to +create certificates for Hermes, Artemis and Console along with Zuse and CaptBob's +'thumbdrives.'"* This reframes `VMIdentity` (F.2 above) from a user-VM-specific mechanism into +the **general per-VM identity primitive** — every node in the pentagon (Hera, Hermes, +Artemis, a user's own VM, the Console) is expected to eventually carry one, not only VMs born +from an attached thumbdrive. Doesn't change F.2's design, just its intended reach — worth +remembering when `VMIdentity` actually gets built, so it isn't accidentally scoped narrower +than this. + +**Two new standing items that came with this, both explicitly deferred (not part of the +current iterative pass, recorded so they aren't lost):** +- **A full codebase audit pass**, using this same iterative Q&A workflow, to scavenge for more + "same gap hiding in two places" opportunities the way `ACLKEY` turned out to be one gap + wearing two names (Milestone 5's "key/lock shape" and D.4's "bumps and holes"), and the way + `WRITE(10)` turned out to gate four separate-looking fronts at once. Not scoped, not + started — a future pass of its own. +- **v2.0.0 release target**: once Tripod is functional end to end, every VM has its identity + mechanism, and the codebase/documentation are clean per the above audit, tag a v2.0.0 + release. Stated as the destination this whole planning arc is walking toward, not an + immediate next step.