Invariants / CN-PROTO-06

CN-PROTO-06

CN derived enforced

The producer-side session orchestrator can only construct outgoing mini-protocol messages tagged with Server agency. Client-originated messages from the server-role pump are unrepresentable in the public API; misuse is a compile error (closed ServerReply wrapper).

Source

docs/planning/phase4-n-a-successor-invariants.md §1 (I-4)

Cluster
PHASE4-N-G
Authority surface
producer-side server-role mini-protocol reply surface

Enforcement trace

Tests 7

  • chain_sync_server_reply_round_trips_through_codec
  • chain_sync_server_reply_into_message_only_yields_server_variants
  • block_fetch_server_reply_round_trips_through_codec
  • block_fetch_server_reply_into_message_only_yields_server_variants
  • accepted_block_header_bytes_equals_validator_split_on_corpus
  • accepted_block_header_bytes_is_subslice_of_as_bytes
  • accepted_block_header_bytes_rejects_malformed_envelope

Cross-references

Strengthened in

Attack rationale

A producer that can construct client-originated server-pump messages can confuse a peer's state machine or impersonate a peer to itself.

Evidence notes

Enforcement is type-level: the ServerReply wrappers' inner enum field is private and no constructor exists for client-agency variants. Adding such a constructor in future would require explicit modification of the wrapper's public API surface and would surface in code review + the n2n_server CI gate planned for S6.

Evidence

  • ServerReply structs in chain_sync/server.rs and block_fetch/server.rs have private inner enums; no public constructor exists for client-agency variants (RequestNext, FindIntersect, Done for chain-sync; RequestRange, ClientDone for block-fetch). into_message() projects only to server-agency wire variants; exhaustive match tests prove the closure.

  • ci_check_no_parallel_header_splitter.sh enforces single-authority header projection: the only pub fn *_header_bytes in the workspace lives at crates/ade_ledger/src/block_validity/header_input.rs.