Skip to content

humd: refuse a hello that does not declare a compatible protoVersion - #65

Merged
adiled merged 1 commit into
mainfrom
socket/capability-gate
Oct 4, 2026
Merged

adiled merged 1 commit into
mainfrom
socket/capability-gate

Conversation

@adiled

@adiled adiled commented Oct 4, 2026 •

Copy link
Copy Markdown
Owner

First slice of the socket admission work. The spec already required protoVersion; the tree did not enforce it.

The hole

WIRE.md said bee and protoVersion were required in a hello, and that a mismatch was "a warning, not a hard error". Neither statement matched the code:

let proto = tone.get("protoVersion").and_then(Value::as_str)
    .unwrap_or(thrum_core::THRUM_VERSION).to_string();

An absent protoVersion was read as agreement with whatever humd currently speaks, and proto was never compared to anything at all — not even to emit the documented warning. So the warning did not exist either.

Consequence: any process that can open $XDG_RUNTIME_DIR/hum/thrum.sock can present any hello and be admitted on any terms, including declaring no protocol version. The socket is the whole third-party surface, and it had no admission contract.

This is not hypothetical. damanfi/bridge connects today and sends a hello with no protoVersion. Under this PR it is disconnected with a stated reason instead of being silently assumed current.

What this PR does

  • protoVerdict compares a declared version to THRUM_VERSION: exact, same-major, or incompatible.
  • No protoVersion → refused. Different major → refused. Unparseable → refused.
  • Minor/patch drift → admitted with thrum.hello.proto-drift.
  • A refused bee is not registered, not announced to the ensemble, and is disconnected via a new thrum_close. It cannot go on to send tones it was never admitted for.
  • WIRE.md updated to describe what the tree now does.

All four first-party hives (bp7, ollama-server, paid-oracle, gsm-modem) already send protoVersion, so none of them are affected.

Proof

sim/tests/admission_gate.rs — three cases: no version refused, wrong major refused, minor drift admitted.

Removing the gate and running the same file:

test result: FAILED. 1 passed; 2 failed

Restored: 3 passed. Full sim suite (18 binaries) and humd --lib (42 tests) green; clippy clean on humd and sim.

Not in this PR

Deliberately, because each needs its own decision and blast radius:

  • gating non-hello tones on admission (sim's synthetic clients inject without a hello, so this needs a real-vs-synthetic distinction first)
  • chi-scoped delivery — declared chis is recorded and gossiped but never filters anything
  • binding bee identity to a key the socket cannot forge
  • revocation via HumdRegistry

Tracked in #66.

Kernel, not library: this closes admission for anyone writing a bee against the socket without hum knowing they exist.

WIRE.md already said bee and protoVersion were required in a hello, and
that a mismatch was a warning. Neither was true: the field was parsed
with unwrap_or(THRUM_VERSION), so an absent declaration was silently
read as agreement with whatever humd currently speaks, and the value was
never compared to anything. Any process that could open the socket could
claim any protocol version, including none at all.

Now a hello with no protoVersion is refused, and so is one whose major
differs or that fails to parse. Minor and patch drift is admitted with a
warning. A refused bee gets an echo naming the reason, is not registered,
is not announced to the ensemble, and is disconnected via thrum_close --
so it cannot go on to send tones it was never admitted for.

Verified by sim/tests/admission_gate.rs. With the gate removed, the
no-version and wrong-major cases both leave the client connected.

WIRE.md updated: it described the policy that was intended, not the one
in the tree.
@adiled
adiled merged commit 97b041c into main Oct 4, 2026
8 checks passed
@adiled
adiled deleted the socket/capability-gate branch October 4, 2026 19:24
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant