docs: suppress reviewed write-good.Passive false positives

133 hits across 38 files, all previously classified during #4548's sweep
and deliberately left un-rewritten (predicate-adjective state/necessity
description, design-intent idiom, structural/type-description idiom,
no-single-actor topology claim, parallel-triple exception, vale
substring-match artifact — see hyperhive#4548's per-PR bodies for the
per-hit reasoning).

Wraps each one in a scoped <!-- vale write-good.Passive = NO/YES -->
pair (the supported mechanism — TokenIgnores has a known offset-drift
bug) rather than a blanket per-file or per-rule silence, so a *new*
passive-voice hit anywhere in these files still fails once the rule
gates CI (next commit). Table/list false positives (docs/swarm/credentials.md's
renewal-table cells) wrap the whole block, not each cell.

Part of #4546.
This commit is contained in:
iris 2026-09-20 15:07:46 +02:00
commit 04e27c4fb6
38 changed files with 368 additions and 71 deletions

View file

@ -1,10 +1,14 @@
# The operator/agent boundary
<!-- vale write-good.Passive = NO -->
Design rationale for hyperhive's two-principal trust model. The
_implementation_ work — container network isolation, the unifying
gateway, core-daemon privsep — is tracked as `area:ops` issues on
the forge.
<!-- vale write-good.Passive = YES -->
The operator/agent boundary is technically enforced, not just a
convention: containers run in private netns (network isolation is
always on), the gateway proxies all operator-facing traffic, and
@ -109,6 +113,8 @@ The last two land in "other," so the dir is **`0751`, owned by the
agent's container uid/gid** — `o=--x` is traverse without listing, and
both sockets are `0666`, which is all a dialer needs.
<!-- vale write-good.Passive = NO -->
**Ownership is declared, not repaired.** The tmpfiles.d entry written by
`SyncAgentTmpfiles` names the uid/gid directly. Don't add a chown
alongside it: `d` re-applies on every boot _and_ every agent
@ -116,6 +122,8 @@ spawn/destroy, and reverts any ownership set afterwards the next time
any agent changes — which is exactly how this dir spent a long time at
`0777 root root` while a privileged chown appeared to be fixing it.
<!-- vale write-good.Passive = YES -->
The mode is load-bearing, not cosmetic. Write permission on a
_directory_ is what confers the right to unlink its entries, whoever owns
them, and the sticky bit is the only thing that would restrain that (it

View file

@ -10,6 +10,8 @@ agent capability X?."
### The trust boundary is the container, not credential storage
<!-- vale write-good.Passive = NO -->
An agent is **trusted code running inside its own nspawn container**. The
boundary that matters is the container: a sub-agent can't see the host
netns, another agent's container, or another agent's state dir. Within its
@ -22,10 +24,16 @@ below stops a build's nixbld user reading the agent's own forge token, and the
state-file endpoint stops one agent proxying another's files. Those harden the
boundary; they don't sandbox the agent from itself.)
<!-- vale write-good.Passive = YES -->
<!-- vale write-good.Passive = NO -->
The corollary: **don't reason about security as "can the agent be stopped from
touching its credentials." Reason about it as "what's the blast radius if this
agent does the worst possible thing with everything it can reach."**
<!-- vale write-good.Passive = YES -->
### Scoped tokens bound the blast radius
Each agent gets its own scoped credentials, never shared:
@ -34,10 +42,14 @@ Each agent gets its own scoped credentials, never shared:
collaborator grants; can't act as another agent or as `core`).
- **matrix token** → that agent's matrix account only.
<!-- vale write-good.Passive = NO -->
_Its own_ account's scope bounds a compromised/confused agent's reach on the
forge or matrix, not the swarm's. This is the main thing standing
between "one agent does something dumb" and "the whole hive is affected."
<!-- vale write-good.Passive = YES -->
**Identity vs. secret (matrix).** The scoping is on the _secret_, not the
_identity_: an agent's matrix **token** is private to its own account, but its
matrix **identities** — the public handles (`name`, `user_id` `@user:server`,
@ -222,7 +234,7 @@ token policy bounds file reads; network isolation bounds network reach.
The proper fix is to enable user namespaces inside nspawn containers
(`--private-users=inherit` in `EXTRA_NSPAWN_FLAGS`) so nix can set up its real
sandbox and `sandbox-fallback` becomes a true last resort. This requires verifying
bind-mount compatibility with user namespace UID mapping and is tracked as a TODO.
bind-mount compatibility with user namespace UID mapping first.
## hive-c0re privilege separation