Skip to main content

Module above_codec_rules

Module above_codec_rules 

Source
Expand description

The rules an endpoint enforces that its own decoder cannot see, named once across the drafts that state them.

§Why these do not live in the codec

A decoder refuses a frame it cannot read. Every rule here is stated about a frame that reads perfectly well — an Object whose properties are legal bytes on a status that forbids properties, a GOAWAY that is a valid GOAWAY and is the second one, a Request ID that is a valid varint and belongs to the other endpoint’s half of the number space. Being an endpoint rather than an observer is what turns each of them into an error, so each is raised on a receive path and never in the decoder.

That placement is deliberate and it has a cost: a caller that reads crate::dispatch::ErrorCause::Codec to find out which rule a peer broke sees none of them, because the codec never raised anything. AboveCodecRule is the other half of that answer.

§Two groups, one enum

What one frame says about itself. Three rules, across six drafts, each comparing two fields of a single message: properties against a status, a payload against a status, a stream’s first message type against the set of types that may open one. They reach here through Connection::draft_specific_cause, which every draft implements over its own ConnectionError.

The drafts renamed two of the three and widened one, and none of the three changes altered what is required:

  • Properties on a non-Normal status. Drafts 15 and 16 call the block extension headers and drafts 17 through 20 call it properties. Same sentence, same consequence, one rule.
  • A bidirectional stream’s opening message. Draft-16 permits exactly two openers and names SUBSCRIBE_NAMESPACE as the second; drafts 17 through 20 permit any message that begins a request stream. The legal set grew, the requirement did not.
  • A payload on a status that permits none. Drafts 17 through 20 only, and the one of the three the drafts state without a close — see AboveCodecRule::PayloadOnStatusDatagram.

What a message says about the session it arrived in. The rest, across all the drafts, each comparing a message against state this endpoint has been keeping: a Request ID against the sequence the peer’s own ids follow, a GOAWAY against whether one has already arrived, a Track Alias against the track it already names, an Object’s Location against the one the track ended at. They reach here through EndpointError::fault, which every draft implements over its own EndpointError.

No frame carries the fact that decides any of them, so no decoder built for any draft could refuse one — the same reason the first group is here, one layer further out.

§Which draft states which is not asked here

It is answered per draft, beside the variant whose doc comment quotes that draft’s own sentence — the same division of labour Connection::codec_session_error_code already has for the decoder’s errors. A rule named here on ten drafts and not on the other four is not a claim that the other four permit it; it is a claim that this build enforces it where the text says to.

§And a second enum, for the rules the decoder did refuse

CodecRule is at the foot of this file and is the other half of the same job. Everything above is a rule no decoder could have caught; everything there is one a decoder caught and nothing carried the draft’s own sentence for. The two are kept apart because they are two kinds of evidence — see that enum’s own doc — and they share this file for one reason: scripts/check-drafts.py rule 8 reads RuleCitation rows out of this path, so a citation written anywhere else is a citation nothing checks.

Structs§

RuleCitation
One draft’s own words for one rule: the sentence, the section it sits in, and what that draft calls the code it answers the rule with.

Enums§

AboveCodecRule
A rule a peer broke that no decoder could have caught.
CodecRule
A rule a peer broke that the negotiated draft’s decoder did refuse, named once across the drafts that state it.
DraftSpecificCause
What one of a draft’s own ConnectionError variants is — the ones outside the ten every draft shares.
EndpointFault
Whose doing one of a draft’s EndpointError variants is.

Constants§

ALIAS_07 🔒
ALIAS_10 🔒
ALIAS_12 🔒
ALIAS_14 🔒
ALIAS_15 🔒
ALIAS_17 🔒
ALIAS_18 🔒
BIDI_OPENER_16 🔒
BIDI_OPENER_17 🔒
CEILING_07 🔒
CEILING_08 🔒
CEILING_10 🔒
CEILING_11 🔒
CEILING_12 🔒
CEILING_13 🔒
CEILING_14 🔒
CEILING_16 🔒
END_GROUP_WRAP_18 🔒
END_GROUP_WRAP_20 🔒
END_OF_TRACK_08 🔒
END_OF_TRACK_11 🔒
END_OF_TRACK_OBJECT_ID 🔒
EXTENSIONS_ON_NONEXISTENT_11 🔒
EXTENSIONS_ON_NONEXISTENT_14 🔒
EXTENSION_HEADERS_ON_STATUS 🔒
FETCH_TYPE_14 🔒
FETCH_TYPE_15 🔒
FILTER_PARAMETER_15 🔒
FILTER_TYPE_14 🔒
FILTER_TYPE_15 🔒
FIRST_RESPONSE 🔒
GOAWAY_AT_SERVER_07 🔒
GOAWAY_URI_CLOSE 🔒
GOAWAY_URI_MAX_11 🔒
GOAWAY_URI_MAX_14 🔒
GOAWAY_URI_MAX_17 🔒
GOAWAY_URI_TERMINATE 🔒
GOAWAY_URI_TERMINATE_14 🔒
INVALID_DATAGRAM_TYPE_16 🔒
INVALID_DATAGRAM_TYPE_20 🔒
INVALID_STREAM_TYPE_16 🔒
INVALID_STREAM_TYPE_20 🔒
KVP_FORMATTING_11 🔒
KVP_FORMATTING_14 🔒
KVP_FORMATTING_16 🔒
KVP_VALUE_MAX_11 🔒
KVP_VALUE_MAX_16 🔒
MAX_ID_07 🔒
MAX_ID_11 🔒
MAX_ID_14 🔒
MAX_ID_16 🔒
MIXED_PREFERENCE_07 🔒
MIXED_PREFERENCE_11 🔒
OBJECT_ID_WRAP 🔒
PARAMETER_LENGTH 🔒
PARAMETER_SCOPE 🔒
PROPERTIES_ON_STATUS 🔒
REASON_PHRASE_MAX_11 🔒
REASON_PHRASE_MAX_14 🔒
REASON_PHRASE_MAX_15 🔒
REDIRECT_TRACK_NAME 🔒
REDIRECT_URI_AT_SERVER 🔒
REPEATED_GOAWAY_07 🔒
REPEATED_GOAWAY_08 🔒
REPEATED_GOAWAY_10 🔒
REPEATED_GOAWAY_14 🔒
REPEATED_GOAWAY_16 🔒
REPEATED_GOAWAY_17 🔒
REPEATED_GOAWAY_18 🔒
REPEATED_GOAWAY_21 🔒
REQUEST_ID_11 🔒
REQUEST_ID_14 🔒
REQUEST_ID_15 🔒
REQUEST_ID_17 🔒
REQUIRED_REQUEST_ID_DELTA 🔒
STATE_NOTIFY 🔒
SUBSCRIBE_AFTER_CANCEL 🔒
SUBSCRIBE_ID_UNIQUE 🔒
TOO_MANY_UPDATES 🔒
TRACK_NAME_MAX_11 🔒
TRACK_NAME_MAX_14 🔒
TRACK_NAME_MAX_15 🔒
TRACK_NAME_MAX_16 🔒
TRACK_PROPERTIES 🔒
UNKNOWN_PARAMETER_16 🔒
UNKNOWN_PARAMETER_17 🔒
UPDATE_WRONG_12 🔒
UPDATE_WRONG_14 🔒
UPDATE_WRONG_15 🔒
UPDATE_WRONG_16 🔒
UPDATE_WRONG_19 🔒