fn check_discriminators(message: &ControlMessage) -> Result<(), CodecError>Expand description
Refuse a message whose discriminator disagrees with the fields beside it.
One draft-20 message carries a field that says which of the following fields
are on the wire: REQUEST_ERROR’s Error Code, whose REDIRECT value (0x34) is
what puts the Redirect structure on the wire. This codec holds the
alternative in an Option, so a value can say one thing in its
discriminator and another in its body, and the two sides of the codec
resolve that differently — the encoder writes whatever the body holds, and
the decoder reads whatever the discriminator announces.
A REQUEST_ERROR with code REDIRECT and no Redirect body encodes to a message that ends where the decoder expects a Connect URI length, so the peer reads the redirect out of whatever follows or runs off the end. The mirror case is quieter and no better: a Redirect body under any other error code is written out and then skipped by a decoder that was never told to look for it, so the sender believes it redirected a peer that never saw a redirect.
Draft-19 had a second discriminator here, FETCH’s Fetch Type, choosing
between a standalone body and a joining pair. Draft-20 deleted the field and
both bodies (Section 10.13), so FETCH has nothing left to disagree with
itself about.
Refusing at the encoder keeps the two readings from ever diverging on the wire.