MoQ Interconnect Exchange (MIX)
draft-nandakumar-moq-mix-00
This document is an Internet-Draft (I-D).
Anyone may submit an I-D to the IETF.
This I-D is not endorsed by the IETF and has no formal standing in the
IETF standards process.
| Document | Type | Active Internet-Draft (individual) | |
|---|---|---|---|
| Authors | Suhas Nandakumar , Cullen Fluffy Jennings | ||
| Last updated | 2026-11-02 | ||
| RFC stream | (None) | ||
| Intended RFC status | (None) | ||
| Formats | |||
| Stream | Stream state | (No stream defined) | |
| Consensus boilerplate | Unknown | ||
| RFC Editor Note | (None) | ||
| IESG | IESG state | I-D Exists | |
| Telechat date | (None) | ||
| Responsible AD | (None) | ||
| Send notices to | (None) |
draft-nandakumar-moq-mix-00
Media Over QUIC S. Nandakumar
Internet-Draft C. Jennings
Intended status: Informational Cisco
Expires: 6 May 2027 2 November 2026
MoQ Interconnect Exchange (MIX)
draft-nandakumar-moq-mix-00
Abstract
This document specifies MoQ Interconnect Exchange (MIX), a protocol
that allows Media Over QUIC (MoQ) relays to discover each other,
exchange reachability and subscription information, and forward MoQ
objects across administrative and topological boundaries. MIX
carries its control state as MoQ tracks.
This work is outside the scope of the IETF Media Over QUIC (MoQ)
working group. It is discussed on that working group's mailing list,
moq@ietf.org, because that is where the people interested in MoQ
relay interconnection are.
About This Document
This note is to be removed before publishing as an RFC.
The latest revision of this draft can be found at
https://suhasHere.github.io/moq-relay-interconnect/draft-nandakumar-
moq-mix.html. Status information for this document may be found at
https://datatracker.ietf.org/doc/draft-nandakumar-moq-mix/.
Discussion of this document takes place on the Media Over QUIC
Working Group mailing list (mailto:moq@ietf.org), which is archived
at https://mailarchive.ietf.org/arch/browse/moq/. Subscribe at
https://www.ietf.org/mailman/listinfo/moq/.
Source for this draft and an issue tracker can be found at
https://github.com/suhasHere/moq-relay-interconnect.
Status of This Memo
This Internet-Draft is submitted in full conformance with the
provisions of BCP 78 and BCP 79.
Internet-Drafts are working documents of the Internet Engineering
Task Force (IETF). Note that other groups may also distribute
working documents as Internet-Drafts. The list of current Internet-
Drafts is at https://datatracker.ietf.org/drafts/current/.
Nandakumar & Jennings Expires 6 May 2027 [Page 1]
Internet-Draft mix November 2026
Internet-Drafts are draft documents valid for a maximum of six months
and may be updated, replaced, or obsoleted by other documents at any
time. It is inappropriate to use Internet-Drafts as reference
material or to cite them other than as "work in progress."
This Internet-Draft will expire on 6 May 2027.
Copyright Notice
Copyright (c) 2026 IETF Trust and the persons identified as the
document authors. All rights reserved.
This document is subject to BCP 78 and the IETF Trust's Legal
Provisions Relating to IETF Documents (https://trustee.ietf.org/
license-info) in effect on the date of publication of this document.
Please review these documents carefully, as they describe your rights
and restrictions with respect to this document. Code Components
extracted from this document must include Revised BSD License text as
described in Section 4.e of the Trust Legal Provisions and are
provided without warranty as described in the Revised BSD License.
Table of Contents
1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 4
1.1. Why MOQT for Relay Control . . . . . . . . . . . . . . . 4
1.2. Terminology . . . . . . . . . . . . . . . . . . . . . . . 5
2. MIX Overview . . . . . . . . . . . . . . . . . . . . . . . . 7
3. Node Identity . . . . . . . . . . . . . . . . . . . . . . . . 10
4. Node, Publisher, and Subscriber Tables . . . . . . . . . . . 11
4.1. Sequence Comparison . . . . . . . . . . . . . . . . . . . 11
4.2. Candidate Paths and Unreachability . . . . . . . . . . . 12
4.3. Publisher and Subscriber Table Lifetime . . . . . . . . . 14
4.4. Path Selection . . . . . . . . . . . . . . . . . . . . . 15
4.5. Delivery Node Sets . . . . . . . . . . . . . . . . . . . 16
5. Control-Plane Track Layout . . . . . . . . . . . . . . . . . 17
5.1. Track Semantics . . . . . . . . . . . . . . . . . . . . . 18
5.1.1. nodes Track . . . . . . . . . . . . . . . . . . . . . 19
5.1.2. publishers and subscribers Tracks . . . . . . . . . . 19
5.1.3. delivery-node-sets Track . . . . . . . . . . . . . . 20
5.1.4. Bootstrap announce Track . . . . . . . . . . . . . . 21
5.1.5. announce Refresh and Timeout . . . . . . . . . . . . 22
6. Peering Establishment . . . . . . . . . . . . . . . . . . . . 23
6.1. Peering Scope . . . . . . . . . . . . . . . . . . . . . . 24
6.2. Subscribing to Node, Publisher, and Subscriber Tables . . 25
6.3. Simultaneous-Peer Tiebreaker . . . . . . . . . . . . . . 26
6.4. Peering State Machine . . . . . . . . . . . . . . . . . . 26
6.5. Loss of a Reflection Peering . . . . . . . . . . . . . . 28
7. Data Plane . . . . . . . . . . . . . . . . . . . . . . . . . 28
Nandakumar & Jennings Expires 6 May 2027 [Page 2]
Internet-Draft mix November 2026
7.1. Forwarding Modes . . . . . . . . . . . . . . . . . . . . 29
7.1.1. Native Mode . . . . . . . . . . . . . . . . . . . . . 29
7.1.2. Pipelined Mode . . . . . . . . . . . . . . . . . . . 30
7.1.3. Route Failure Semantics . . . . . . . . . . . . . . . 31
7.2. Data Header . . . . . . . . . . . . . . . . . . . . . . . 31
7.3. Delivery Node Set Fan-Out . . . . . . . . . . . . . . . . 33
8. Control Messages . . . . . . . . . . . . . . . . . . . . . . 34
8.1. Advertisement and Withdrawal Messages . . . . . . . . . . 36
8.2. CONNECT . . . . . . . . . . . . . . . . . . . . . . . . . 36
8.3. NODE_INFO_ADVERTISEMENT and NODE_INFO_WITHDRAWAL . . . . 36
8.3.1. node_info Structure . . . . . . . . . . . . . . . . . 37
8.4. NODE_UNREACH . . . . . . . . . . . . . . . . . . . . . . 39
8.5. PUBLISH_INFO_ADVERTISEMENT and PUBLISH_INFO_WITHDRAWAL . 40
8.5.1. publish_info Structure . . . . . . . . . . . . . . . 40
8.6. SUBSCRIBE_INFO_ADVERTISEMENT and
SUBSCRIBE_INFO_WITHDRAWAL . . . . . . . . . . . . . . . . 41
8.6.1. subscribe_info Structure . . . . . . . . . . . . . . 41
8.7. DELIVERY_NODE_SET_ADVERTISEMENT and
DELIVERY_NODE_SET_WITHDRAWAL . . . . . . . . . . . . . . 42
9. Track Hashing . . . . . . . . . . . . . . . . . . . . . . . . 42
9.1. Namespace and Name Hashes . . . . . . . . . . . . . . . . 43
9.2. Rationale . . . . . . . . . . . . . . . . . . . . . . . . 43
10. Originator Authentication . . . . . . . . . . . . . . . . . . 44
10.1. Signature Input . . . . . . . . . . . . . . . . . . . . 44
10.2. Replay Guard . . . . . . . . . . . . . . . . . . . . . . 46
10.3. Public Key Distribution . . . . . . . . . . . . . . . . 46
11. Convergence and Flood Minimization . . . . . . . . . . . . . 46
12. Deployment Models . . . . . . . . . . . . . . . . . . . . . . 47
12.1. Integrated model . . . . . . . . . . . . . . . . . . . . 47
12.2. Split model . . . . . . . . . . . . . . . . . . . . . . 48
12.2.1. Publisher and Subscriber Table Reflection . . . . . 50
13. Extensions . . . . . . . . . . . . . . . . . . . . . . . . . 51
14. Extension: Path Aggregation . . . . . . . . . . . . . . . . . 52
14.1. Aggregation Token . . . . . . . . . . . . . . . . . . . 52
14.2. Construction Rules . . . . . . . . . . . . . . . . . . . 52
14.3. Loop Detection . . . . . . . . . . . . . . . . . . . . . 53
14.4. Selection Semantics . . . . . . . . . . . . . . . . . . 53
14.5. Policy and Configurability . . . . . . . . . . . . . . . 53
15. Extension: MRAI Flood Damping . . . . . . . . . . . . . . . . 54
15.1. Timer . . . . . . . . . . . . . . . . . . . . . . . . . 55
15.2. Withdrawal Bypass . . . . . . . . . . . . . . . . . . . 55
15.3. Interaction With Other Mechanisms . . . . . . . . . . . 55
15.4. Convergence Bound . . . . . . . . . . . . . . . . . . . 55
16. Security Considerations . . . . . . . . . . . . . . . . . . . 56
17. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 56
18. References . . . . . . . . . . . . . . . . . . . . . . . . . 56
18.1. Normative References . . . . . . . . . . . . . . . . . . 56
18.2. Informative References . . . . . . . . . . . . . . . . . 56
Nandakumar & Jennings Expires 6 May 2027 [Page 3]
Internet-Draft mix November 2026
Appendix A. Change Log . . . . . . . . . . . . . . . . . . . . . 57
A.1. draft-nandakumar-moq-mix-00 . . . . . . . . . . . . . . . 57
Acknowledgments . . . . . . . . . . . . . . . . . . . . . . . . . 57
Authors' Addresses . . . . . . . . . . . . . . . . . . . . . . . 57
1. Introduction
Media Over QUIC Transport [MoQTransport] (MOQT) defines how endpoints
publish and subscribe to media tracks through relays. MOQT itself is
scoped to a single relay: it does not specify how relays exchange the
reachability and subscription information they need to forward
objects between their respective subscriber populations.
Related work ([MOQ-CLUSTER]) addresses relay coordination within a
single cluster or CDN but does not define cross-domain discovery,
peering negotiation, or policy-governed fan-out.
This document specifies MoQ Interconnect Exchange (MIX), which closes
that gap by reusing MOQT for the inter-relay control plane and
defining a data plane that operates both within a single
administrative domain and across administrative boundaries.
1.1. Why MOQT for Relay Control
MIX uses MOQT facilities where their existing semantics fit the
control plane, so the request, fan-out, scheduling, and object-
retrieval behavior of the control plane comes directly from MOQT.
MIX does not assume that every MOQT relay caches objects or that MOQT
itself supplies relay-to-relay routing.
* Namespace discovery and separate tracks. Relays publish MIX
namespaces with PUBLISH_NAMESPACE and discover peers via
SUBSCRIBE_NAMESPACE / NAMESPACE / NAMESPACE_DONE. nodes,
publishers, and subscribers are independent tracks so a peer can
subscribe to only the state it needs and MIX can apply distinct
retention, priority, and admission policy to each.
* Live updates plus state repair. SUBSCRIBE carries live updates.
Draft 22's FILL_PARAMETERS mechanism, when backed by a cache,
recovers retained objects after a reconnect or missed update.
Because MOQT caching is optional, MIX needs its own recovery for
the case where a fill is incomplete (Section 6.2).
Nandakumar & Jennings Expires 6 May 2027 [Page 4]
Internet-Draft mix November 2026
* Priority scheduling and delivery deadlines. MOQT subgroup streams
and datagrams, publisher priorities, and OBJECT_DELIVERY_TIMEOUT /
SUBGROUP_DELIVERY_TIMEOUT let MIX prioritize routing-critical
state and bound how long an advertisement consumes delivery
effort. Priorities influence scheduling only, and deadlines may
drop state (Section 6.2).
* Direct use of MOQT controls. MIX uses these MOQT controls as
defined, without re-encoding them in MIX messages. MIX-specific
messages carry only what MOQT does not represent: originator
identity, freshness, path, and target-set information.
1.2. Terminology
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT",
"SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and
"OPTIONAL" in this document are to be interpreted as described in
BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all
capitals, as shown here.
The following terms are used throughout this document:
Node: A MIX-capable MOQT relay. Each Node is identified by a
128-bit Node ID, described in Section 3.
MIX Edge Node: A Node that connects MOQT application publishers or
subscribers to the inter-relay network. It originates publish and
subscribe state for its local clients and injects or delivers
their objects through MIX.
MIX Transit Node: A Node that carries relay reachability and
forwarding state and forwards objects along selected inter-relay
paths. It typically does not terminate application publisher or
subscriber sessions.
MIX Control Node: A Node that exchanges Publisher and Subscriber
Table state on behalf of other Nodes and does not forward objects.
Control Nodes are used in the split deployment model
(Section 12.2) and advertise type = 2 in node_info
(Section 8.3.1).
Forwarding Node: A MIX Edge Node or MIX Transit Node; any Node that
is not a Control Node.
Control Session: A QUIC connection between two Nodes used to
Nandakumar & Jennings Expires 6 May 2027 [Page 5]
Internet-Draft mix November 2026
exchange MIX control-plane tracks, including announce, nodes,
publishers, and subscribers (Section 5). This connection also
carries the MOQT control messages needed to establish and manage
its subscriptions and publications.
Data Session: A separate QUIC connection between two Nodes used to
forward inter-relay data (Section 7). It also uses MOQT control
messages to establish the session and its delivery-node-sets track
subscription. Those MOQT messages manage the transport session;
they do not make it a MIX control Session.
Peering: A MIX relationship between two Nodes. It consists of a
Control Session carrying the Node, Publisher, and Subscriber
Table tracks in the peering's scope (Section 6.1) and, when that
scope includes the Node Table and data is to be forwarded, a
separate Data Session. Each connection has its own MOQT session
state. An delivery-node-sets track is associated with the Data
Session whose downstream targets it describes.
Session: In this document, an unqualified Session means a Control
Session. When the Data Session is intended, it is named
explicitly.
Node Table: The Nodes this Node knows about, one entry per Node ID.
Each entry holds that Node's attributes and public key, and one
candidate path to it from each peer. It answers "which Nodes
exist, and how do I reach each one?" It is filled by
NODE_INFO_ADVERTISEMENT and NODE_INFO_WITHDRAWAL.
Publisher Table: The tracks that are published, one entry per
originating Edge Node and track. Each entry says that the Edge
Node has a local publisher for the track, and which forwarding
mode it wants. It answers "where does track T come from?" It is
filled by PUBLISH_INFO_ADVERTISEMENT and PUBLISH_INFO_WITHDRAWAL.
Subscriber Table: The tracks that are wanted, one entry per
originating Edge Node and track. Each entry says that the Edge
Node has local subscribers for the track. It answers "who wants
track T?" It is filled by SUBSCRIBE_INFO_ADVERTISEMENT and
SUBSCRIBE_INFO_WITHDRAWAL.
Together, the Publisher Table says where a track comes from, the
Subscriber Table says where it must go, and the Node Table says how
to get between them. Full details are in Section 4.
Originator: The Node that a Node, Publisher, or Subscriber
Nandakumar & Jennings Expires 6 May 2027 [Page 6]
Internet-Draft mix November 2026
Table entry describes, and the only Node that can create or
withdraw it. For a Node Table entry it is the Node itself
(node_info.id). For a Publisher or Subscriber Table entry it is
the Edge Node whose local publisher or subscriber the entry
describes (source_node_id). The originator signs the entry
(Section 10); other Nodes only re-publish it. The term follows
BGP route reflection [RR], where ORIGINATOR_ID names the router
that injected a route.
Advertisement / Withdrawal: An advertisement installs or updates an
entry in a Node, Publisher, or Subscriber Table; a withdrawal
removes it. Both are signed by the entry's originator. The
messages for each table are defined in Section 8.1.
Delivery Node Set: Forwarding state for one track on one Data
Session: the Edge Nodes with subscribers for the track that it
must reach by way of that Data Session's downstream Node. Each
Data Session has one Delivery Node Set per track it carries. The
upstream Node builds it from its Subscriber Table (who wants the
track) and its Node Table (which next hop leads to each of them),
and sends it on the Data Session's delivery-node-sets track. Each
downstream Node splits it for its own next hops, so the set
narrows at every hop and the track is copied only where paths
split. For example, if track T has subscribers behind B1 and B2,
both reached through Transit X, the Delivery Node Set for T on the
Data Session to X lists {B1, B2}; X then sends {B1} toward B1 and
{B2} toward B2. See Section 4.5.
Delivery Node Set Id: A 32-bit label that the upstream Node of a
Data Session assigns to one Delivery Node Set on that Data
Session. In pipelined mode it travels with every forwarded object
(Section 7.2), so the downstream Node can find the set without
parsing the track identity. It has meaning only on one Data
Session. See Section 4.5.
2. MIX Overview
This section is informative.
Each MIX participant is a Node: an MOQT relay that also implements
MIX. A Node uses two kinds of Session, each a separate QUIC
connection. A Control Session carries MIX state as MOQT tracks: each
Node publishes its Node, Publisher, and Subscriber Tables as tracks
to which its peers subscribe. A Data Session carries forwarded
objects and is opened only when a track needs to flow to a downstream
peer, and only between Nodes that exchange Node Tables. Whether a
peering also carries the Publisher and Subscriber Tables depends on
the deployment: every peering carries all three when every Node runs
Nandakumar & Jennings Expires 6 May 2027 [Page 7]
Internet-Draft mix November 2026
both planes, while a large deployment can move the exchange of the
Publisher and Subscriber Tables to a small set of Control Nodes
(Section 12).
A track flows through MIX as follows:
1. Discovery. Each Node publishes an announce track under a well-
known namespace prefix. Nodes learn each other's Node IDs by
subscribing to that prefix (Section 5).
2. Peering. Two Nodes subscribe to each other's Node, Publisher,
and Subscriber Table tracks over a Control Session. Which of
Node, Publisher, and Subscriber Tables a peering carries is its
scope (Section 6.1).
3. Flooding. Each Node advertises its own Node Table entry and re-
advertises entries learned from peers, appending itself to the
path. Publishers originate Publisher Table entries and
subscribers originate Subscriber Table entries (Section 4). Each
advertisement is signed by the Node that originated it
(Section 10).
4. Path selection. Each Node selects a best egress Session per
destination Node, considering only paths on which every hop
supports the track's requested forwarding mode (Section 4.4).
5. Fan-out setup. For each track it forwards, a Node groups the
track's destination Nodes by their best egress. It opens (or
reuses) a Data Session to each of those next hops and publishes
on it the track's Delivery Node Set: the destinations to be
reached through that next hop, labelled with a Delivery Node Set
Id (Section 5.1.3).
6. Delivery. Objects follow the selected path in the track's
forwarding mode (Section 7.1). At each hop, the downstream Node
finds the Delivery Node Set for an arriving object (by its Id in
pipelined mode, by track in native mode), repeats the grouping of
step 5 for its own next hops, and forwards the object under its
own Delivery Node Set Ids (Section 7.3).
Each entry in the Node, Publisher, and Subscriber Tables then moves
through a few simple states:
Nandakumar & Jennings Expires 6 May 2027 [Page 8]
Internet-Draft mix November 2026
Node Table entry: is there a path to its Node?
| advertisement
v
+-------------+
+--| REACHABLE |
| +-------------+
| | ^
| | path | path
| | lost | back
| v |
| +-------------+
withdrawal | | UNREACHABLE |
| +-------------+
| |
| | ORIGINATOR_UNREACH_HOLD expires
| v
| +-------------+
+->| REMOVED |
+-------------+
Publisher or Subscriber Table entry: is its originator reachable?
| advertisement
v
+-------------+
+--| ACTIVE |
| +-------------+
| | ^
| | lost | back
| | |
| v |
withdrawal | +-------------+
or | | UNUSABLE |
restart | +-------------+
| |
| | ORIGINATOR_UNREACH_HOLD expires
| v
| +-------------+
+->| REMOVED |
+-------------+
Figure 1: Lifecycle of Node, Publisher, and Subscriber Table entries
A Publisher or Subscriber Table entry is UNUSABLE exactly while its
originator's Node Table entry is UNREACHABLE. "Restart" means the
originator came back with a newer origin_epoch. Both holds are
ORIGINATOR_UNREACH_HOLD. In a split deployment, a Forwarding Node
Nandakumar & Jennings Expires 6 May 2027 [Page 9]
Internet-Draft mix November 2026
also removes reflected entries if it has had no Control Node for
CONTROL_STALE_HOLD. The full rules are in Section 4.2 and
Section 4.3.
3. Node Identity
Each Node has an Ed25519 [RFC8032] signing key pair. The Node ID is
a 128-bit value derived from the Node's Ed25519 public key:
node_id = first 16 bytes of SHA-256(ed25519_public_key),
as a 128-bit value in network byte order
Figure 2: Node ID derivation
Because the Node ID is bound to the Node's public key, no separate
identity-to-key mapping is required: a receiver that has the Node's
public key can verify that any Node ID claim is authentic. This
makes MIX originator authentication (Section Section 10) self-
verifying: an originating advertisement carries a signature by the
Ed25519 private key whose derived Node ID matches the advertisement's
source_node_id.
On receipt, a Node MUST verify that the public key in node_info
(Section 8.3.1) derives the advertised ID using the formula above, in
addition to verifying the signature and local trust policy. A valid
signature by an unrelated key MUST NOT authenticate a claimed Node
ID.
The canonical textual form of a Node ID is four groups of eight
lowercase hexadecimal digits separated by colons; the colons MAY be
omitted for a compact form. Groups MUST NOT be shortened by trimming
leading zeros.
<group> ::= 8HEXDIG
<canonical> ::= <group> ":" <group> ":" <group> ":" <group>
<compact> ::= 32HEXDIG
Figure 3: Node ID textual form
Examples: 1a2b3c4d:5e6f7081:9200aabb:ccddeeff,
1a2b3c4d5e6f70819200aabbccddeeff.
Nodes MAY be configured with a static Ed25519 key pair or MAY
generate one at startup. Once generated, the key pair SHOULD be
persisted across restarts to preserve Node ID stability.
Nandakumar & Jennings Expires 6 May 2027 [Page 10]
Internet-Draft mix November 2026
4. Node, Publisher, and Subscriber Tables
Each Node maintains a Node Table, a Publisher Table, and a Subscriber
Table and, for each of its Data Sessions, a set of Delivery Node
Sets:
+============+============+==================+===================+
| State | Describes | Keyed by | Stores |
+============+============+==================+===================+
| Node Table | Reachable | Node ID | Most recent |
| | Nodes | | node_info, one |
| | | | candidate path |
| | | | per peer, and the |
| | | | computed best |
| | | | egress Session |
+------------+------------+------------------+-------------------+
| Publisher | Published | (source_node_id, | Most recent |
| Table | tracks | full_name_hash) | publish_info |
+------------+------------+------------------+-------------------+
| Subscriber | Requested | (source_node_id, | Most recent |
| Table | tracks | full_name_hash) | subscribe_info |
+------------+------------+------------------+-------------------+
| Delivery | Where each | (Data Session, | Track and |
| Node Set | forwarded | Delivery Node | destination Node |
| | track must | Set Id) | IDs (Section 4.5) |
| | go, per | | |
| | Data | | |
| | Session | | |
+------------+------------+------------------+-------------------+
Table 1: State held by each Node
Each of these tables is filled by the advertisement and withdrawal
messages defined in Section 8.1. On Session teardown a Node MUST
remove every Node Table candidate learned from the departing peer
(Section 4.2). Publisher and Subscriber Table entries are not
withdrawn on Session teardown; their lifetime follows the
reachability of their originator (Section 4.3).
Best-egress selection is computed per Node Table entry using the
algorithm in Section 4.4.
4.1. Sequence Comparison
Every advertisement and withdrawal carries two freshness fields, both
set by its originator:
Nandakumar & Jennings Expires 6 May 2027 [Page 11]
Internet-Draft mix November 2026
* origin_epoch (64 bits) identifies the originator's current
incarnation (Section 10.2).
* sequence (64 bits) counts the advertisements and withdrawals the
originator has published for one key in its Node, Publisher, or
Subscriber Table (Section 4). It increases with every message for
that key and MUST NOT wrap or be reused within an epoch.
An originator MUST either persist its epoch and per-key sequences
across restarts or advance origin_epoch before it publishes again.
A receiver orders messages for the same originator and key by the
pair (origin_epoch, sequence), comparing origin_epoch first. It
accepts a message only if its pair is greater than the stored one,
and re-floods only messages it accepts.
For a NODE_INFO_ADVERTISEMENT (Section 8.3), this comparison covers
only the originator-signed fields of node_info. Its path is unsigned
and tracked per peer (Section 4.2), so an advertisement whose pair
equals the stored one is not accepted as new but still replaces the
sending peer's candidate path.
4.2. Candidate Paths and Unreachability
A Node can usually reach another Node through more than one peer.
For each Node Table entry E, it therefore keeps one candidate path
per peer: the most recent path that peer advertised for E.id. Path
selection (Section 4.4) chooses the best egress among these
candidates. When the best one disappears, the Node fails over to the
next without waiting for the originator to re-advertise.
A candidate changes only on one of four events, each tied to a single
peer S:
Nandakumar & Jennings Expires 6 May 2027 [Page 12]
Internet-Draft mix November 2026
+=========================+====================================+
| Event on Session S | Effect |
+=========================+====================================+
| NODE_INFO_ADVERTISEMENT | S's candidate becomes the received |
| for E.id (Section 8.3) | path. If that path contains the |
| whose (origin_epoch, | local Node ID, S reaches E.id only |
| sequence) equals or | through this Node, so S's |
| exceeds the stored one | candidate is removed instead. |
+-------------------------+------------------------------------+
| NODE_UNREACH for E.id | S's candidate is removed. |
| (Section 8.4) | |
+-------------------------+------------------------------------+
| S enters CLOSED | S's candidate is removed from |
| | every entry. |
+-------------------------+------------------------------------+
| NODE_INFO_WITHDRAWAL | E is removed with all its |
| from E.id (Section 8.3) | candidates, and the withdrawal is |
| | re-flooded. |
+-------------------------+------------------------------------+
Table 2: Events that change Node Table candidates
After any of these events, the Node re-runs path selection for E and
tells its own peers what changed:
* If the best path changed materially, it re-publishes E on its
nodes track with its own element appended.
* If no candidate is left, E is unreachable. If the Node had
advertised E, it publishes NODE_UNREACH for E.id on its nodes
track, so that its peers remove their path through it.
The same rules then apply at each peer, so the loss of a path spreads
hop by hop and stops at Nodes that still have another candidate.
An unreachable entry keeps its originator-signed fields for
ORIGINATOR_UNREACH_HOLD (default 90 s) and is then removed. If a
path returns within that time, an advertisement with the same
(origin_epoch, sequence) restores a candidate without the originator
having to re-advertise.
NODE_UNREACH needs no signature because it can only remove the
candidate of the Session it arrived on, which is the path the sender
itself advertised. The sender could have the same effect by never
advertising that path, so accepting an unsigned NODE_UNREACH gives it
no new power.
Nandakumar & Jennings Expires 6 May 2027 [Page 13]
Internet-Draft mix November 2026
Holding one candidate per peer costs memory in proportion to the
number of Nodes times the number of peers. A Node MAY keep fewer
candidates than it has peers, at the cost of slower failover.
4.3. Publisher and Subscriber Table Lifetime
Publisher and Subscriber Table entries describe their originator, not
the path they arrived on. A Publisher Table entry says that the
originator publishes a track; a Subscriber Table entry says that the
originator has subscribers for one. A Node therefore keeps an entry
when the peer that delivered it goes away. It removes the entry only
when the originator's statement is no longer true, or the Node can no
longer count on hearing about it if it changes.
The originator ends an entry in one of two ways:
* Withdrawal. The originator sends PUBLISH_INFO_WITHDRAWAL
(Section 8.5) or SUBSCRIBE_INFO_WITHDRAWAL (Section 8.6) when its
last local publisher or subscriber for the track leaves. The
withdrawal floods like any other message, and each Node removes
the entry when it accepts the withdrawal.
* Restart. When a Node accepts a NODE_INFO_ADVERTISEMENT from the
originator with a newer origin_epoch, it removes every Publisher
and Subscriber Table entry from that originator with an older
epoch. The restarted originator re-advertises the entries that
are still valid.
A Node also ends entries on its own when it can no longer rely on
hearing from the originator:
* Originator unreachable. While the originator's Node Table entry
is unreachable (Section 4.2), the originator's entries are kept
but not used for path setup. If the originator is still
unreachable after ORIGINATOR_UNREACH_HOLD, they are removed.
* No Control Node. In a split deployment, a Forwarding Node that
has had no ESTABLISHED Reflection peering for CONTROL_STALE_HOLD
removes every entry it did not originate, because it may have
missed withdrawals (Section 6.5).
These local removals are not flooded. Every Node reaches the same
conclusion from its own Node Table or peering state.
When an unreachable originator comes back, no special recovery is
needed. The Sessions that re-form across the repaired link fill from
each other (Section 6.2), the Nodes there accept the originator's
entries as new, and normal flooding carries the entries on.
Nandakumar & Jennings Expires 6 May 2027 [Page 14]
Internet-Draft mix November 2026
4.4. Path Selection
Path selection chooses, for each destination Node E.id, the peer
through which this Node sends data toward it: E's best egress. It
works on E's candidates (Section 4.2), one per peer, and runs again
whenever they change.
A candidate is eligible unless:
* its peer is a Control Node, which never forwards data; or
* it is being considered for a track whose Publisher Table entry
requests pipelined mode, and some hop on its path does not set the
pipelined bit (bit 1) of data_modes (Section 8.3.1). Every
Forwarding Node supports native mode, so a native-mode track can
use any eligible candidate.
Among eligible candidates, the Node prefers:
1. the shortest path, counted as the sum of hop_count over its
elements. Without path aggregation (Section 14) this is the
number of elements; then
2. the lowest cumulative smoothed round-trip time (sRTT): the sum of
srtt_us over the path plus the Node's own sRTT to the peer that
advertised it.
Hop count decides first, and sRTT only breaks ties.
The chosen peer's Session is cached on E as its best egress. The
Node recomputes it when that Session closes, when its candidate is
removed, or when a materially better candidate arrives. A change of
best egress moves E.id from the Delivery Node Set on the old egress
Data Session to the Delivery Node Set on the new one, for every track
forwarded toward it (Section 7.3) and can lead the Node to re-publish
E (Section 4.2).
To judge "materially better", implementations SHOULD round sRTT
values (for example, to whole milliseconds) before comparing them, so
that sub-millisecond jitter does not make the best egress, and the
advertisements that depend on it, oscillate.
Nandakumar & Jennings Expires 6 May 2027 [Page 15]
Internet-Draft mix November 2026
4.5. Delivery Node Sets
The Node, Publisher, and Subscriber Tables say which Nodes exist,
which tracks are published, and which Edge Nodes have subscribers.
To forward a track, a Node also needs to know, on each Data Session,
where the objects it sends there must end up. That is the Delivery
Node Set.
An Delivery Node Set belongs to one track on one Data Session. It
names the destination Nodes, the Edge Nodes with subscribers for the
track, that the track must reach through the downstream Node of that
Data Session.
Delivery Node Sets are built hop by hop. The publisher's Edge Node
takes the destinations for the track from its Subscriber Table,
groups them by best egress (Section 4.4), and creates one Delivery
Node Set per egress Data Session. Each downstream Node receives that
Delivery Node Set, groups its destinations again by its own best
egress, and creates its own Delivery Node Sets. At each hop a
Delivery Node Set keeps only the destinations still ahead on that
branch, so a track is copied exactly where its destinations' paths
diverge:
E1's Subscriber Table: track T has subscribers behind B1, B2, B3
{B1,B2} {B1}
[E1] --------------> [X] ------------> [B1]
| |
| | {B2}
| +--------------> [B2]
|
| {B3}
+------------------------------------> [B3]
Figure 4: Delivery Node Sets for one track, built hop by hop
Each Delivery Node Set is labelled with an Id that the upstream Node
chooses and that is unique on that Data Session. In pipelined mode
every forwarded object carries the Delivery Node Set Id
(Section 7.2), so the downstream Node finds the Delivery Node Set
with one lookup instead of parsing the track identity. Delivery Node
Set Ids have no meaning beyond their Data Session: each hop assigns
its own on its egress Data Sessions.
An Delivery Node Set changes when a destination is added or removed
(a Subscriber Table change) or when a destination's best egress
changes (a Node Table change). The upstream Node then publishes the
updated Delivery Node Set under the same Id, or withdraws it when no
Nandakumar & Jennings Expires 6 May 2027 [Page 16]
Internet-Draft mix November 2026
destinations remain. Delivery Node Sets are published on each Data
Session's delivery-node-sets track (Section 5.1.3) as
DELIVERY_NODE_SET_ADVERTISEMENT and DELIVERY_NODE_SET_WITHDRAWAL
(Section 8.7). How a Node forwards objects using them is specified
in Section 7.3.
5. Control-Plane Track Layout
MIX carries all of its state as MOQT tracks. Every track sits under
the namespace prefix ("mix","v1"). The rest of the namespace tuple
says whose state the track holds and, for delivery-node-sets, which
Data Session it belongs to:
+==============================+============+=========+=======+==============+
|Namespace |Track |Published|Carried|Contents |
| | |by |on | |
+==============================+============+=========+=======+==============+
|("mix","v1","announce","<node-|announce |Every |Control|The Node's |
|id>") | |Node |Session|CONNECT, for |
| | | | |discovery |
| | | | |(Section 8.2) |
+------------------------------+------------+---------+-------+--------------+
|("mix","v1","<node-id>") |nodes |Every |Control|Node Table |
| | |Node |Session|advertisements|
| | | | |and |
| | | | |withdrawals, |
| | | | |and |
| | | | |NODE_UNREACH |
| | | | |(Section 8.3, |
| | | | |Section 8.4) |
+------------------------------+------------+---------+-------+--------------+
|("mix","v1","<node-id>") |publishers |Every |Control|Publisher |
| | |Node |Session|Table |
| | | | |advertisements|
| | | | |and |
| | | | |withdrawals |
| | | | |(Section 8.5) |
+------------------------------+------------+---------+-------+--------------+
|("mix","v1","<node-id>") |subscribers |Every |Control|Subscriber |
| | |Node |Session|Table |
| | | | |advertisements|
| | | | |and |
| | | | |withdrawals |
| | | | |(Section 8.6) |
+------------------------------+------------+---------+-------+--------------+
|("mix","v1","<node-id>") |publishers- |Control |Control|Publisher and |
| |mesh, |Nodes |Session|Subscriber |
| |subscribers-|only | |Table entries |
Nandakumar & Jennings Expires 6 May 2027 [Page 17]
Internet-Draft mix November 2026
| |mesh | | |reflected to |
| | | | |other Control |
| | | | |Nodes (Section|
| | | | |12.2.1) |
+------------------------------+------------+---------+-------+--------------+
|("mix","v1","<node- |delivery- |Upstream |That |One Delivery |
|id>","<sid>") |node-sets |Node of |Data |Node Set per |
| | |the Data |Session|track |
| | |Session | |forwarded on |
| | | | |that Data |
| | | | |Session |
| | | | |(Section 8.7) |
+------------------------------+------------+---------+-------+--------------+
Table 3: MIX tracks
<node-id> is the textual form of the publishing Node's ID
(Section 3). <sid> is a 128-bit Data Session Identifier, chosen by
the Node that opens the Data Session (Section 6) and written in the
same textual form. The publishers-mesh and subscribers-mesh tracks
carry the same objects as publishers and subscribers and follow the
same track semantics.
Each Data Session has its own namespace, so its delivery-node-sets
track is kept apart from every other Data Session's while the track
name stays the fixed literal "delivery-node-sets". A Node MAY list
its active Data Sessions by issuing a MOQT SUBSCRIBE_NAMESPACE on its
own prefix ("mix","v1","<node-id>"): it receives one NAMESPACE
message per Data Session and a NAMESPACE_DONE when one is withdrawn.
Discovery uses the separate announce prefix, so a Node can find every
other Node without a directory service. A MOQT SUBSCRIBE_NAMESPACE
on ("mix","v1","announce") returns one NAMESPACE message per Node in
the mesh, and a NAMESPACE_DONE when a Node withdraws. A MOQT
SUBSCRIBE to a Node's announce track then retrieves its CONNECT
(Section 6).
How each track numbers its groups and objects, its priority, and how
to subscribe to it are given in Section 5.1.
5.1. Track Semantics
Each MIX control track specifies an Object priority value for its
objects. MOQT uses lower numeric priority for higher scheduling
precedence, with 0 the highest ([MoQTransport]). Priority 0 is
reserved for MOQT control traffic, and MIX tracks MUST NOT use it.
Nandakumar & Jennings Expires 6 May 2027 [Page 18]
Internet-Draft mix November 2026
The nodes and delivery-node-sets tracks use priority 1, because they
gate forwarding: path selection cannot proceed without reachability,
and data egress is held back until the target set is known. The
publishers and subscribers tracks carry per-track demand that does
not gate delivery, and use priority 2. The bootstrap announce track
also uses priority 2; after initial discovery, its refresh is a
liveness heartbeat rather than a routing decision.
5.1.1. nodes Track
The nodes track distributes reachability. A Node publishes on it its
own NODE_INFO advertisement and the advertisements it has accepted
from peers, so that every Node learns which other Nodes exist, the
path to each, and the per-hop sRTT along that path.
Group ID: A monotonically increasing epoch, incremented when self-
info materially changes (Node type, contact, geo) and at process
start. Advertisements for other Nodes reuse the current epoch.
Subgroup ID: 0.
Object payload: A single MIX control message (Section 8) tagged
NODE_INFO_ADVERTISEMENT, NODE_INFO_WITHDRAWAL, or NODE_UNREACH.
Object priority: 1. Node Table gates path selection.
Subscription filter: As in Section 6.2.
Loop prevention is inherited from the payload: an advertisement whose
path contains the receiver's own Node ID removes the sending peer's
candidate instead of adding one (Section 4.2). When a Node re-
publishes an advertisement on its own nodes track, it appends its own
element to the path (Section 8.3.1).
A Control Node MUST NOT re-publish Node Table advertisements it has
accepted from peers. It accepts them to learn public keys
(Section 10.3), but it never appears in a data-plane path.
5.1.2. publishers and subscribers Tracks
The publishers track distributes publications: each entry states that
a track is available at its originator and the forwarding mode
requested for it. The subscribers track distributes demand: each
entry states that a Node has subscribers for a track. A Node
publishes on these tracks the entries it originates and the entries
it has accepted from peers. Together they let each Node determine
which tracks need to flow toward it and from where. In the split
deployment model, which accepted entries a Node re-publishes depends
Nandakumar & Jennings Expires 6 May 2027 [Page 19]
Internet-Draft mix November 2026
on its role (Section 12.2.1).
Group ID: A monotonically increasing MOQT Group ID assigned by the
Node publishing this track. It is a local transport location,
separate from the MIX freshness fields, and MUST NOT wrap or be
reused during the track's lifetime. A Node that re-publishes an
entry assigns its own MOQT locations and preserves the signed MIX
payload fields.
Subgroup ID: 0.
Object payload: A MIX control message tagged
SUBSCRIBE_INFO_ADVERTISEMENT, SUBSCRIBE_INFO_WITHDRAWAL,
PUBLISH_INFO_ADVERTISEMENT, or PUBLISH_INFO_WITHDRAWAL.
Object priority: 2.
MOQT Group IDs and Object IDs are local transport locations, not MIX
sequence numbers (Section 4.1); this keeps MOQT location ordering and
FETCH ranges independent of per-originator freshness.
5.1.3. delivery-node-sets Track
The delivery-node-sets track carries one Delivery Node Set for each
track forwarded on its Data Session: the destination Nodes that the
track must reach through the downstream Node, labelled with a
Delivery Node Set Id. The track is scoped to that Data Session:
<sid> in the namespace tuple identifies the Data Session, and both
endpoints agree on it when that session is opened (Section 6). The
track name is the fixed literal "delivery-node-sets".
Group ID: The 32-bit Delivery Node Set Id assigned by the sender,
carried in the low 32 bits of the MOQT Group ID (upper bits zero).
MIX reuses the same Delivery Node Set Id when the target set
changes, so each Delivery Node Set Id maps to one MOQT group whose
most recent object is the current set.
Subgroup ID: 0.
Object ID within a group: A monotonically increasing counter
starting at 0 for the first object in the group and incremented by
one for each subsequent update to the set. Consumers treat the
object with the greatest Object ID in the group as the current
state for that Delivery Node Set Id.
Object payload: DELIVERY_NODE_SET_ADVERTISEMENT or
DELIVERY_NODE_SET_WITHDRAWAL.
Nandakumar & Jennings Expires 6 May 2027 [Page 20]
Internet-Draft mix November 2026
Delivery Node Set Id encoding: The Delivery Node Set Id is a 32-bit
identifier. It is carried as a 32-bit field in
DELIVERY_NODE_SET_ADVERTISEMENT payloads (Section 8) and as a
variable-length integer ([RFC9000]) in the data-plane MIX Data
Header (Section 7.2). Both forms carry the same 32-bit value.
Subscription filter: As in Section 6.2.
Object priority: 1. Data cannot be forwarded until its Delivery
Node Set is known.
Track lifetime: Tied to the Data Session. On teardown the publisher
unpublishes the track and the subscriber implicitly loses its
subscription.
5.1.4. Bootstrap announce Track
The announce track lets Nodes discover each other. Each Node
publishes on it a CONNECT message describing itself, including its
Node ID and public key, so that a prospective peer can identify the
Node and verify its signed advertisements before subscribing to its
Node, Publisher, and Subscriber Table tracks.
Group ID: A monotonically increasing epoch, bumped whenever the
publisher publishes a new CONNECT object (see Section 5.1.5). The
initial group after process start is 0.
Subgroup ID: 0.
Object ID within a group: A monotonically increasing counter reset
to 0 at each new group.
Object payload: A CONNECT message (Section 8) carrying the
publisher's node_info.
Object priority: 2.
Subscription filter: As in Section 6.2; the fill yields the current
CONNECT.
Object expiry: See Section 5.1.5.
A Node discovers peers by issuing a MOQT SUBSCRIBE_NAMESPACE with
prefix ("mix","v1","announce") and receiving one NAMESPACE message
per known peer, followed by NAMESPACE_DONE on withdrawal. It then
attaches to each peer's announce track with a MOQT SUBSCRIBE (see
Section 6).
Nandakumar & Jennings Expires 6 May 2027 [Page 21]
Internet-Draft mix November 2026
If a peer withdraws its announce namespace while A still holds an
ESTABLISHED peering with that peer, the withdrawal is treated as an
intent-to-depart signal. A SHOULD begin the CLOSED transition
(Section 6.4) for that peering unless a replacement CONNECT arrives
on a re-published namespace within the staleness window defined in
Section 5.1.5. The peering's Control Session and any Data Sessions
remain open until the state machine completes the transition; this
prevents a flapping announce from immediately tearing down in-flight
data.
5.1.5. announce Refresh and Timeout
A CONNECT object is a soft-state advertisement: subscribers use it to
learn the publisher's public key, contact, geo, and capability bits,
and they need a bounded assurance that the currently held object
still reflects the publisher. Two rules govern the publisher's
rewrite schedule:
1. Timer-driven refresh. A publisher MUST re-publish its CONNECT
object at least once per ANNOUNCE_REFRESH_INTERVAL. The default
value is 30 s; deployments MAY use a shorter interval where
faster detection of stale peers matters, or a longer interval on
resource-constrained deployments, provided all peers agree via
configuration.
2. Change-driven refresh. A publisher MUST re-publish its CONNECT
object as soon as any field of node_info covered by the
originator signature (Section 10) changes — Node type, contact
string, geo coordinates, public key, data_modes, or origin_epoch.
Path accumulation is not a change (path is not signed).
Each rewrite advances the MOQT Group ID by one and resets Object ID
to 0. Because the announce track is latest-state oriented, older
groups need not be retained beyond the configured recovery window.
A subscriber MUST treat a CONNECT object as stale when it has not
observed a new group within ANNOUNCE_STALE_MULTIPLIER *
ANNOUNCE_REFRESH_INTERVAL (default multiplier 3, giving a 90 s
default staleness bound). A stale CONNECT on an active peering is a
hint that the peer is unhealthy; the subscriber SHOULD initiate
CLOSED transition (Section 6.4) if no refresh arrives within one
additional interval.
The CONNECT refresh has a monotonically increasing MIX sequence
within the current originator epoch. origin_epoch changes only when
the Node starts a new incarnation that may reuse sequence state.
Subscribers use the (origin_epoch, sequence) pair for replay defence
independently of MOQT group progression.
Nandakumar & Jennings Expires 6 May 2027 [Page 22]
Internet-Draft mix November 2026
6. Peering Establishment
Peering between two Nodes A and B is established using standard MOQT
control messages. The mapping below is normative; any additional
MOQT messages required by [MoQTransport] for these exchanges (SETUP,
REQUEST_OK / REQUEST_ERROR, PUBLISH_OK / PUBLISH_ERROR, and so on)
are used as defined there.
1. Publish namespaces and tracks. On startup, each Node issues a
MOQT PUBLISH_NAMESPACE for its per-Node namespace
("mix","v1","<node-id>") and a second PUBLISH_NAMESPACE for the
bootstrap namespace ("mix","v1","announce","<node-id>"). It then
issues MOQT PUBLISH requests for nodes, publishers, subscribers,
and announce tracks and publishes its CONNECT message as an
object on announce. PUBLISH_NAMESPACE announces namespace
availability; it does not by itself publish a track or its
objects.
2. Discover peers. To find peers, Node A issues a MOQT
SUBSCRIBE_NAMESPACE with prefix ("mix","v1","announce"). It
receives one NAMESPACE message per Node currently in the mesh
(and a NAMESPACE_DONE when a peer's namespace is subsequently
withdrawn), learning each peer's Node ID.
3. Attach control-plane tracks. To peer with B, Node A:
1. Issues a MOQT SUBSCRIBE with FILL_PARAMETERS for the announce
track of B (("mix","v1","announce","<B-node-id>") /
"announce") to obtain B's current CONNECT body and receive
later refreshes.
2. Issues MOQT SUBSCRIBE requests for the tracks under
("mix","v1","<B-node-id>") that the peering's scope calls for
(Section 6.1), drawn from nodes, publishers, and subscribers,
to receive current state and live updates (Section 6.2). A
needs no further discovery for this: B's namespace follows
from the Node ID that A learned in step 2, and the track
names are fixed by this document (Section 5). MOQT allows a
subscriber to subscribe to a track without first receiving a
PUBLISH_NAMESPACE for its namespace ([MoQTransport]).
Nandakumar & Jennings Expires 6 May 2027 [Page 23]
Internet-Draft mix November 2026
3. When the peering's scope includes the Node Table and A
selects B as the egress for a track, A opens a separate Data
Session to B and chooses its <sid>. On that connection, A
issues a MOQT PUBLISH_NAMESPACE for ("mix","v1","<A-node-
id>","<sid>") and a PUBLISH for its delivery-node-sets track,
and B subscribes to that track (Section 6.2). The MOQT
control messages for this run on the Data Session. A opens
the Data Session when a track first needs to flow to B and
reuses it for later tracks.
6.1. Peering Scope
The scope of a peering is the set of Node, Publisher, and Subscriber
Table tracks that each Node subscribes to from the other. Scope is
set by local configuration for each peering and is not negotiated on
the wire. Three scopes are defined:
+============+===========================+=============+==========+
| Scope | A subscribes to B's | Used | Data |
| | | between | Sessions |
+============+===========================+=============+==========+
| Full | nodes, publishers, | Forwarding | Yes |
| | subscribers | Nodes, | |
| | | integrated | |
| | | model | |
+------------+---------------------------+-------------+----------+
| Topology | nodes | Forwarding | Yes |
| | | Nodes, | |
| | | split model | |
+------------+---------------------------+-------------+----------+
| Reflection | Forwarding Node and | A | No |
| | Control Node: publishers, | Forwarding | |
| | subscribers, plus nodes | Node and a | |
| | when A is the Control | Control | |
| | Node. Two Control Nodes: | Node, or | |
| | publishers-mesh, | two Control | |
| | subscribers-mesh | Nodes | |
+------------+---------------------------+-------------+----------+
Table 4: Peering scopes
The following rules apply regardless of deployment model:
* A Forwarding Node MUST NOT subscribe to the nodes track of a
Control Node.
Nandakumar & Jennings Expires 6 May 2027 [Page 24]
Internet-Draft mix November 2026
* A Node MUST open a Data Session to a peer only over an ESTABLISHED
peering with Full or Topology scope. Path selection (Section 4.4)
yields only such peers.
* A Control Node MUST NOT open or accept Data Sessions.
A Control Node's subscription to a Forwarding Node's nodes track lets
the Control Node learn the public keys of every Forwarding Node that
Forwarding Node can reach, which it needs to verify the Publisher and
Subscriber Tables entries it receives (Section 10).
6.2. Subscribing to Node, Publisher, and Subscriber Tables
For the nodes, publishers, and subscribers tracks, subscribers SHOULD
issue a MOQT SUBSCRIBE whose Location Filter starts at the Next
Object. To also acquire retained state, the initial SUBSCRIBE SHOULD
include FILL_PARAMETERS with a location filter ending at Largest
Object. The fill range and the live subscription filter are distinct
in draft 22. Implementations MUST process both fill-delivered and
subscription-delivered objects using the same MIX freshness and
duplicate-suppression rules. A relay MAY return an incomplete fill
when objects are unavailable; MIX therefore requires a full-state
snapshot or equivalent recovery mechanism after a cache miss (see the
editor's note below).
The same pattern applies to the announce track and to the per-Data-
Session delivery-node-sets track (Section 5.1.3). The delivery-node-
sets cache lifetime SHOULD cover expected peer setup and recovery
intervals.
Priorities influence scheduling only. A Node MUST NOT treat an
advertisement whose delivery timed out under OBJECT_DELIVERY_TIMEOUT
or SUBGROUP_DELIVERY_TIMEOUT ([MoQTransport]) as delivered.
Editor's note: This document does not yet define how a Node
recovers full state when a fill is incomplete because the
publishing relay has no usable cache.
B performs the subscriptions to A that the peering's scope calls for
(Section 6.1). For Full and Topology scope these mirror A's.
Nandakumar & Jennings Expires 6 May 2027 [Page 25]
Internet-Draft mix November 2026
6.3. Simultaneous-Peer Tiebreaker
Two Nodes MAY open Control Sessions to each other at the same time.
A pair of Nodes keeps at most one Control Session. Once each Node
has received the other's CONNECT, the connection opened by the Node
with the numerically lower Node ID is kept and the other is closed.
Both directions of subscription then run over the kept connection.
Closing the duplicate connection is not a peering close: neither Node
removes state learned from the other (Section 6.4).
6.4. Peering State Machine
Each peering (an ordered pair of Nodes A and B, viewed from A's side)
progresses through a small state machine. States describe the
control-plane relationship only; data-plane subscriptions (Section 6
step 3) are opened independently once ESTABLISHED is reached on a
peering whose scope includes the Node Table.
+---------+
| INIT |
+---------+
|
| subscribe to B's announce track
v
+---------+
| OPENING |
+---------+
|
| receive B.CONNECT object
v
+---------+
| HELLO |-------> REJECTED
| RECVD | signature / policy reject
+---------+
|
| subscribe to tracks in scope
|
v
+-------------+
| ESTABLISHED |
+-------------+
| | |
| | | signature failure at ingress
| | | / peer close / QUIC error
v v v
+-------------+
| CLOSED |
+-------------+
Nandakumar & Jennings Expires 6 May 2027 [Page 26]
Internet-Draft mix November 2026
Figure 5: Peering state machine
State transitions:
* INIT -> OPENING: A issues a MOQT SUBSCRIBE for B's announce track
(("mix","v1","announce","<B-node-id>") / "announce").
* OPENING -> HELLO_RECVD: A receives B's CONNECT object on the
announce track. A does not yet trust B; the object's signature
MUST verify against a pubkey that either (a) is derived from B's
Node ID (Section 3) or (b) was already installed as a trusted key.
* HELLO_RECVD -> ESTABLISHED: A applies the simultaneous-peer
tiebreaker and issues MOQT SUBSCRIBE requests with FILL_PARAMETERS
for the B tracks in the peering's scope (Section 6.1) as specified
in Section 6.2. B receives A's advertisements through its own
subscriptions to A.
* HELLO_RECVD -> REJECTED: signature verification failed, the peer
pubkey does not match A's local pinning policy, or admission
control declines the peering. A cancels its subscription to B's
announce track and does not subscribe to B's Node, Publisher, or
Subscriber Table tracks. The state is terminal from A's
perspective; B may retry after a backoff.
* ESTABLISHED -> CLOSED: A observes any of (i) a MOQT PUBLISH_DONE
on any control-plane track from B, an explicit cancellation of A's
SUBSCRIBE, or, when the peering's scope includes Node Table, a
STOP_SENDING on a Data Session to B; (ii) QUIC transport failure;
(iii) sustained signature failure at ingress; or (iv) a local
admin action. A connection closed by the simultaneous-peer
tiebreaker (Section 6.3) does not close the peering. On entry to
CLOSED, A removes every Node Table candidate it learned from B
(Section 4.2). Publisher and Subscriber Table entries follow
Section 4.3, and those learned over a Reflection peering also
follow Section 6.5.
Tying a Topology or Full peering to its Data Sessions keeps Node
Table and the data plane in step: a peer that can no longer forward
is withdrawn from path selection rather than left as a black hole. A
Reflection peering has no Data Sessions, so data-plane events never
close it.
CLOSED is a terminal state; recovery is a fresh INIT on a new session
identifier. The Node ID of the peer is unchanged, so any previously
distributed originator pubkey remains valid across reconnection.
Nandakumar & Jennings Expires 6 May 2027 [Page 27]
Internet-Draft mix November 2026
6.5. Loss of a Reflection Peering
Losing a Reflection peering does not by itself remove any Publisher
or Subscriber Table entry. The entries are signed by their
originators and stay valid while those originators are reachable
(Section 4.3), and a Forwarding Node peered with more than one
Control Node keeps receiving updates from the others.
Reachability here comes from the Node Table, not from the Control
Nodes. An originator is reachable while the Node's Node Table entry
for it has at least one candidate (Section 4.2). A Forwarding Node
builds its Node Table over its Topology peerings with its data-plane
neighbors, so it keeps tracking originators even when it has no
Control Node at all. A Control Node builds its Node Table from its
subscriptions to the nodes tracks of the Forwarding Nodes it serves
(Section 6.1).
A Forwarding Node that has no ESTABLISHED Reflection peering receives
no updates, and so misses any withdrawals issued in the meantime. To
bound that, a Forwarding Node that has had no ESTABLISHED Reflection
peering for CONTROL_STALE_HOLD removes every Publisher and Subscriber
Table entry it did not originate. The default is 90 s. It SHOULD
exceed the time needed to re-establish a Reflection peering and
complete its fill (Section 6.2). The fill on the next Reflection
peering restores the entries.
7. Data Plane
The data plane between two Nodes uses a Data Session: a QUIC
connection separate from the Control Session of the peering between
them, whose scope includes the Node Table (Section 6.1). Keeping the
two connections separate prevents media flow control from delaying
control-plane updates, allows a Data Session to be opened only when a
track needs to flow, and lets each connection use its own congestion
control and priority settings. Each Data Session uses MOQT control
messages to set up and manage its delivery-node-sets track
subscription, but carries forwarded objects separately from the MIX
control-state tracks. Two forwarding modes are defined
(Section 7.1), and each Publisher Table entry carries the mode
requested by its originator. A Node MUST select an end-to-end path
only if every hop supports the mode requested for the track.
Nandakumar & Jennings Expires 6 May 2027 [Page 28]
Internet-Draft mix November 2026
7.1. Forwarding Modes
MIX defines two ways to carry a track's objects between Nodes. In
native mode every hop forwards whole MOQT objects. In pipelined mode
every hop forwards bytes as they arrive, behind a small MIX Data
Header. The track's originator picks the mode in its Publisher
Table entry, and a path is usable for pipelined mode only if every
hop on it supports it.
+==============+=======================+==========================+
| | Native mode | Pipelined mode |
+==============+=======================+==========================+
| What crosses | A MOQT object, framed | A MIX Data Header, then |
| each hop | per hop | the object's bytes |
+--------------+-----------------------+--------------------------+
| Publisher's | Forwards MOQT objects | Re-frames each object |
| Edge Node | | with an delivery_set_id |
+--------------+-----------------------+--------------------------+
| Transit | Receive whole objects | Forward bytes before the |
| Nodes | and MAY cache them | object boundary is known |
+--------------+-----------------------+--------------------------+
| Subscriber's | Delivers MOQT objects | Rebuilds the MOQT object |
| Edge Node | | |
+--------------+-----------------------+--------------------------+
| Support | Required of every | OPTIONAL, advertised in |
| | Forwarding Node | data_modes |
+--------------+-----------------------+--------------------------+
Table 5: Native and pipelined forwarding between relays
7.1.1. Native Mode
In native mode, the inter-relay data-plane connection runs the same
MOQT [MoQTransport] object framing that is used between application
publishers/subscribers and their edge relays. Each application
object is forwarded as a MOQT object, preserving its track identity
and location (group_id, subgroup_id, object_id) across hops. Track
Aliases and request IDs are local to each MOQT session and MUST be
mapped per hop. Publisher priority is preserved as the priority of
the forwarded object subject to relay policy. The MOQT stream
mapping is:
* A subgroup maps to a QUIC unidirectional stream per hop, as
defined by [MoQTransport]. Each relay may use a different stream
and local Track Alias on egress while preserving the object
locations.
* Objects delivered via QUIC datagrams remain in datagrams.
Nandakumar & Jennings Expires 6 May 2027 [Page 29]
Internet-Draft mix November 2026
* FETCH responses ([MoQTransport]) traverse each hop as a single
unidirectional stream carrying the FETCH object sequence.
Intermediate relays MAY cache objects and serve retained ranges with
FETCH or fill fetch streams when supported. MOQT does not require a
relay to cache, so a peer must be able to repair state after a cache
miss; this is not yet defined (see the editor's note in Section 6.2).
Priority scheduling and delivery-timeout behavior follow
[MoQTransport] on each session; ordering is per subgroup or as
otherwise specified by a request's Group Order, not a global order
across tracks or streams.
Native mode is the default. Forwarding Nodes MUST support native
mode.
7.1.2. Pipelined Mode
In pipelined mode, the inter-relay data-plane connection replaces
MOQT subgroup framing with the MIX Data Header (Section 7.2) followed
by verbatim application bytes. The stream mapping is:
* Each MOQT subgroup arriving at the publisher's Edge Node is re-
framed into one unidirectional QUIC stream on the inter-relay
connection. The stream carries a new_stream_header (Section 7.2)
followed by back-to-back object bodies from the subgroup, each
later one preceded by its own existing_stream_header.
Intermediate relays forward the stream's bytes hop by hop,
rewriting only the Delivery Node Set Id in each header, since
Delivery Node Set Ids are local to a Data Session. The terminal
edge relay reconstructs a MOQT subgroup stream toward each local
subscriber, preserving the subgroup identifier.
* Objects that the publisher's Edge Node received in MOQT datagrams
are re-emitted as QUIC datagrams, each beginning with a
datagram_header. Each hop rewrites the Delivery Node Set Id and
re-enqueues the datagram.
* FETCH responses are always carried in native framing regardless of
the track's forwarding_mode, because FETCH requires bounded cache-
and-replay semantics at every hop.
Intermediate relays MUST forward bytes as they arrive: they SHOULD
NOT wait for MOQT-level object boundaries. Intermediate relays do
not maintain a per-object cache and cannot replay a partially-
forwarded object.
Nandakumar & Jennings Expires 6 May 2027 [Page 30]
Internet-Draft mix November 2026
Pipelined mode is OPTIONAL. Support is signalled per Node via the
data_modes field in node_info (Section 8.3.1) and requested per track
via the forwarding_mode field in publish_info (Section 8.5.1).
A route from the publisher's Edge Node to a subscriber is admissible
for a pipelined-mode track only if every intermediate Node advertises
pipelined-mode support in its Node Table entry. If no such path
exists at the time of a SUBSCRIBE (or a PUBLISH in publisher-
initiated tracks), the publisher's Edge Node MAY downgrade the track
to native mode for that subscriber and MUST record the downgrade in
its local subscribe state so that the subscriber sees stock MOQT
object framing.
7.1.3. Route Failure Semantics
When a Data Session terminates mid-stream, the upstream Node re-runs
path selection (Section 4.4) and opens a Data Session on the
replacement path. If a peering closes, the Node removes the Node
Table candidates learned over it (Section 4.2), and path selection
uses the remaining candidates.
In native mode, each affected relay MAY replay cached MOQT objects
onto the new egress subgroup stream so that subscribers see a small
gap rather than a lost group. A subscriber MAY also recover the
missing range with a bounded FETCH ([MoQTransport]) served by any
relay whose cache still contains the range.
In pipelined mode, bytes that were in-flight beyond the last
completed MIX stream boundary are lost; the receiving relay MUST NOT
attempt to re-assemble a partially-received MOQT object. The
terminal edge relay signals the loss to the subscriber by advancing
to a new group or object_id as defined by MOQT.
7.2. Data Header
In pipelined mode, every datagram and every stream between Nodes
begins with a MIX Data Header. A stream also carries one before each
later object on it. The header tells the receiving Node which
Delivery Node Set the bytes belong to, so it can forward them before
the object ends. There are three types of header, using the notation
of Section 1.3 of [RFC9000]:
Nandakumar & Jennings Expires 6 May 2027 [Page 31]
Internet-Draft mix November 2026
datagram_header {
type (8) = 0x00,
header_length (8),
delivery_set_id (i),
data_length (i),
}
new_stream_header {
type (8) = 0x02,
header_length (8),
delivery_set_id (i),
priority (8),
ttl_us (i),
data_length (i),
}
existing_stream_header {
type (8) = 0x01,
header_length (8),
delivery_set_id (i),
}
Figure 6: MIX Data Header types
type: Which header this is. 0x00 begins a QUIC datagram. 0x02 begins
a QUIC stream and precedes its first object. 0x01 precedes each
later object on the same stream.
header_length: The number of bytes in the header after this field.
A receiver that does not need every field can use it to skip to
the payload.
delivery_set_id: The Id of the track's Delivery Node Set on this
Data Session (Section 4.5). The receiving Node looks it up to
find where to forward the bytes (Section 7.3).
priority: The MOQT publisher priority of the subgroup carried on the
stream ([MoQTransport]).
ttl_us: A lifetime for the stream's objects, in microseconds.
data_length: The number of payload bytes that follow the header: the
datagram's payload, or the first object on a new stream.
Editor's note: The meaning of ttl_us is not yet specified. An
existing_stream_header carries no length, so a receiver cannot yet
find where each later object on a stream ends.
Nandakumar & Jennings Expires 6 May 2027 [Page 32]
Internet-Draft mix November 2026
Native-mode streams do not carry a MIX Data Header; they carry MOQT
object frames as defined in [MoQTransport].
7.3. Delivery Node Set Fan-Out
Each Node derives its egress Delivery Node Sets from its ingress
Delivery Node Sets as described in Section 4.5; a destination that is
the Node itself is delivered locally. The result maps each ingress
Delivery Node Set Id to a set of egress Data Sessions and their
Delivery Node Set Ids.
For each ingress unidirectional stream, a Node looks up the ingress
delivery_set_id in that mapping (Section 5.1.3), then opens one
egress unidirectional stream per selected downstream Data Session.
Egress streams are opened lazily, on the first byte of the ingress
stream, so that a relay does not consume QUIC flow-control budget on
peers that have no active subscribers.
ingress stream for track T, delivery_set_id = 42
|
v
+---------------------------+
| Delivery Node Sets for |
| the ingress Data Session: |
| Id 42 -> {B2, C1} |
| Id 57 -> {D1} |
+-------------+-------------+
|
+---------+---------+
v v
egress to B2 egress to C1
Figure 7: Delivery Node Set lookup and fan-out at a Node
Datagrams are fanned out by rewriting the Delivery Node Set Id per
egress and queuing a fresh QUIC datagram frame on each downstream
Data Session.
In native mode the Delivery Node Set is found by track
(full_name_hash) rather than by Delivery Node Set Id, and selects the
set of downstream Data Sessions in the same way, but the egress
carries a MOQT subgroup stream (or datagram, or FETCH response) as
defined by [MoQTransport] rather than a MIX Data Header stream. The
relay preserves track identity and object locations on egress. Track
Alias and request state are mapped to the local MOQT session.
Nandakumar & Jennings Expires 6 May 2027 [Page 33]
Internet-Draft mix November 2026
8. Control Messages
All MIX control messages appear as MOQT object payloads. Structures
in this section use the notation of Section 1.3 of [RFC9000], as
[MoQTransport] does. Each object carries exactly one message:
mix_control_message {
tag (8),
body (..),
}
Figure 8: MIX control message
tag identifies the message type, and body is the structure listed for
that type below. Because MOQT frames each object with a length, the
body needs no length prefix of its own.
Nandakumar & Jennings Expires 6 May 2027 [Page 34]
Internet-Draft mix November 2026
+====+===============================+===========+======================+=======+
|Tag |Name |Track |Body |Defined|
| | | | |in |
+====+===============================+===========+======================+=======+
|0x01|CONNECT |announce |node_info |Section|
| | | | |8.2 |
+----+-------------------------------+-----------+----------------------+-------+
|0x04|NODE_INFO_ADVERTISEMENT |nodes |node_info |Section|
| | | | |8.3 |
+----+-------------------------------+-----------+----------------------+-------+
|0x05|NODE_INFO_WITHDRAWAL |nodes |node_info (empty path)|Section|
| | | | |8.3 |
+----+-------------------------------+-----------+----------------------+-------+
|0x06|SUBSCRIBE_INFO_ADVERTISEMENT |subscribers|subscribe_info |Section|
| | | | |8.6 |
+----+-------------------------------+-----------+----------------------+-------+
|0x07|SUBSCRIBE_INFO_WITHDRAWAL |subscribers|subscribe_info (empty |Section|
| | | |subscribe_data) |8.6 |
+----+-------------------------------+-----------+----------------------+-------+
|0x08|PUBLISH_INFO_ADVERTISEMENT |publishers |publish_info |Section|
| | | | |8.5 |
+----+-------------------------------+-----------+----------------------+-------+
|0x09|PUBLISH_INFO_WITHDRAWAL |publishers |publish_info (empty |Section|
| | | |parameters) |8.5 |
+----+-------------------------------+-----------+----------------------+-------+
|0x0A|DELIVERY_NODE_SET_ADVERTISEMENT|delivery- |delivery_node_set_info|Section|
| | |node-sets | |8.7 |
+----+-------------------------------+-----------+----------------------+-------+
|0x0B|DELIVERY_NODE_SET_WITHDRAWAL |delivery- |empty |Section|
| | |node-sets | |8.7 |
+----+-------------------------------+-----------+----------------------+-------+
|0x0C|NODE_UNREACH |nodes |node_unreach |Section|
| | | | |8.4 |
+----+-------------------------------+-----------+----------------------+-------+
Table 6: MIX control message types
All fixed-width integers are in network byte order. A 128-bit field
holds either a Node ID (Section 3) or a track hash (Section 9).
Fields marked (i) use the QUIC variable-length integer encoding
(Section 16 of [RFC9000]).
Nandakumar & Jennings Expires 6 May 2027 [Page 35]
Internet-Draft mix November 2026
8.1. Advertisement and Withdrawal Messages
The Node, Publisher, and Subscriber Tables each have one
advertisement and one withdrawal message: NODE_INFO_ADVERTISEMENT and
NODE_INFO_WITHDRAWAL for Node Table, PUBLISH_INFO_ADVERTISEMENT and
PUBLISH_INFO_WITHDRAWAL for Publisher Table, and
SUBSCRIBE_INFO_ADVERTISEMENT and SUBSCRIBE_INFO_WITHDRAWAL for
Subscriber Table. The following rules apply to all six:
* The entry's originator creates and signs the message (Section 10)
and publishes it on its own nodes, publishers, or subscribers
track.
* A Node that accepts the message (Section 4.1) re-publishes it on
its own track of the same kind without changing any signed field,
unless its role rules this out: Control Nodes do not re-publish
Node Table entries, and in a split deployment Forwarding Nodes do
not re-publish Publisher or Subscriber Table entries
(Section 12.2.1).
* A withdrawal uses the same body as the advertisement with its
variable-length part emptied, as stated for each message below.
8.2. CONNECT
Announces a Node to prospective peers. Each Node publishes a CONNECT
on its announce track at startup and refreshes it as described in
Section 5.1.5. Peers use it to discover the Node and to learn its
public key before subscribing to its Node, Publisher, and Subscriber
Table tracks (Section 6).
The body is the Node's node_info (Section 8.3.1). CONNECT and
NODE_INFO_ADVERTISEMENT share the same body and signature input
(Section 10) and differ only in the tag byte and the track they
appear on.
8.3. NODE_INFO_ADVERTISEMENT and NODE_INFO_WITHDRAWAL
A NODE_INFO_ADVERTISEMENT states that a Node exists, gives its
attributes and public key, and gives one path to it. A Node
originates its own NODE_INFO_ADVERTISEMENT at startup and again
whenever a signed field of its node_info changes. A Forwarding Node
that accepts one re-publishes it, with its own path element appended,
whenever its best path to the originator changes (Section 4.2). A
receiver stores the signed fields in the Node Table entry for the
originator and the path as the sending peer's candidate.
Nandakumar & Jennings Expires 6 May 2027 [Page 36]
Internet-Draft mix November 2026
A NODE_INFO_WITHDRAWAL states that a Node is leaving the mesh. Only
the Node itself sends it, with an empty path. A receiver removes the
Node Table entry and all its candidates and re-floods the withdrawal.
A Node that has only lost its path to another Node sends NODE_UNREACH
instead (Section 8.4).
8.3.1. node_info Structure
The node_info structure is:
node_info {
id (128),
type (8),
contact_len (8),
contact (..),
longitude (64),
latitude (64),
pubkey (256),
origin_epoch (64),
sequence (64),
data_modes (8),
path_len (i),
path (..) ...,
origin_sig (512),
}
path_element {
flags (8),
node_id_or_token (128),
srtt_us (64),
hop_count (16),
}
Figure 9: node_info encoding
id: The Node ID of the Node this entry describes (Section 3).
type: 0 for a MIX Transit Node, 1 for a MIX Edge Node, 2 for a MIX
Control Node. Other values are reserved.
contact_len, contact: An optional UTF-8 contact string of
contact_len bytes (0 to 253), without a NUL terminator.
longitude, latitude: Optional location, each an IEEE 754 binary64
value in network byte order.
pubkey: The originator's Ed25519 public key (Section 10).
Nandakumar & Jennings Expires 6 May 2027 [Page 37]
Internet-Draft mix November 2026
origin_epoch, sequence: Freshness fields (Section 4.1,
Section 10.2).
data_modes: The forwarding modes the Node supports (see below).
path_len, path: The number of path elements (0 to 32), followed by
that many path_element structures, ordered from the originator to
the most recent hop (see below).
origin_sig: The originator's Ed25519 signature (Section 10).
flags: Path element flags (see below).
node_id_or_token: The Node ID of this hop, or an aggregation token
when flags bit 0 is set (Section 14).
srtt_us: The hop's sRTT to the previous hop, in microseconds, or the
sum over an aggregated run.
hop_count: The number of Nodes this element represents: 1, or more
for an aggregated element.
The data_modes byte advertises which inter-relay forwarding modes the
Node supports:
+=====+================================+
| Bit | Meaning |
+=====+================================+
| 0 | Native mode (see Section 7.1). |
| | Set by every Forwarding Node. |
+-----+--------------------------------+
| 1 | Pipelined mode (see |
| | Section 7.1). |
+-----+--------------------------------+
| 2-7 | Reserved; MUST be sent as 0 |
| | and ignored on receive. |
+-----+--------------------------------+
Table 7: data_modes bitmap
A Forwarding Node MUST set bit 0. A Control Node does not forward
objects and MUST send data_modes = 0. A receiver MUST treat a Node
whose type is a value other than 0, 1, or 2 as a Control Node for
path selection. Bit 1 is set only if the Node's implementation
performs MIX Data Header framing and byte-pipeline forwarding on the
data plane.
The flags byte in each path element encodes:
Nandakumar & Jennings Expires 6 May 2027 [Page 38]
Internet-Draft mix November 2026
+=====+=============================================================+
| Bit | Meaning |
+=====+=============================================================+
| 0 | Aggregated: node_id_or_token |
| | is an opaque aggregation token |
+-----+-------------------------------------------------------------+
| 1-7 | Reserved; MUST be sent as 0 |
| | and ignored on receive |
+-----+-------------------------------------------------------------+
Table 8: Path element flags
hop_count gives the number of Nodes represented by the element. For
non-aggregated elements it is always 1. For aggregated elements it
records the interior hop count so downstream selection can still
compute a meaningful path length. See Section 14.
The originator publishes its own NODE_INFO_ADVERTISEMENT with a
single path element for itself (srtt_us = 0, hop_count = 1). Each
Node that re-publishes the advertisement appends its own element,
with srtt_us set to its sRTT to the peer it received the
advertisement from. Elements therefore run from the originator to
the most recent hop.
The 32-element maximum on path_len bounds propagation diameter and
functions as a hop-count TTL. A Node that receives a
NODE_INFO_ADVERTISEMENT whose path_len is 32 MUST NOT re-flood it
(appending its own hop would exceed the maximum); the entry is still
accepted locally. A receiver MUST discard any advertisement that
arrives with path_len > 32 as malformed.
8.4. NODE_UNREACH
States that the sender no longer has a path to the Node named by
node_id, and retracts the path it last advertised for that Node. A
Node sends it on its own behalf, not an originator's, so it is not
signed. When a Node sends it and how a receiver applies it are
specified in Section 4.2.
node_unreach {
node_id (128),
}
Figure 10: node_unreach encoding
node_id: The Node ID of the Node that is no longer reachable.
Nandakumar & Jennings Expires 6 May 2027 [Page 39]
Internet-Draft mix November 2026
8.5. PUBLISH_INFO_ADVERTISEMENT and PUBLISH_INFO_WITHDRAWAL
A PUBLISH_INFO_ADVERTISEMENT states that a track is available at its
originator, and the forwarding mode the originator requests for it
(Section 7.1). An Edge Node originates one when a local MOQT
publisher makes a track available. A receiver stores it in its
Publisher Table.
A PUBLISH_INFO_WITHDRAWAL states that the track is no longer
available at the originator. The originator sends it when its local
publisher stops publishing. A receiver removes the Publisher
Table entry.
8.5.1. publish_info Structure
The publish_info structure is:
publish_info {
sequence (64),
source_node_id (128),
origin_epoch (64),
track_full_name_hash (..),
forwarding_mode (8),
parameters_len (i),
parameters (..),
origin_sig (512),
}
track_full_name_hash {
namespace_hashes_len (16),
namespace_hashes (128) ...,
name_hash (128),
}
Figure 11: publish_info encoding
sequence, origin_epoch: Freshness fields (Section 4.1,
Section 10.2).
source_node_id: The Node ID of the originator.
track_full_name_hash: The per-component hashes of the track's
namespace tuple (namespace_hashes_len of them) and of its name
(Section 9), so receivers can do prefix matching. The single-
value full_name_hash used in Publisher and Subscriber Table keys
is derived from these components.
forwarding_mode: The mode the originator selected for this track: 0
Nandakumar & Jennings Expires 6 May 2027 [Page 40]
Internet-Draft mix November 2026
for native, 1 for pipelined (Section 7.1). It is covered by the
originator signature (Section 10), and an intermediate Node MUST
NOT rewrite it.
parameters_len, parameters: Additional MOQT PUBLISH /
PUBLISH_NAMESPACE parameters as defined in [MoQTransport], opaque
to MIX.
origin_sig: The originator's Ed25519 signature (Section 10).
A PUBLISH_INFO_WITHDRAWAL uses the same encoding with parameters_len
= 0; receivers ignore its forwarding_mode field.
8.6. SUBSCRIBE_INFO_ADVERTISEMENT and SUBSCRIBE_INFO_WITHDRAWAL
A SUBSCRIBE_INFO_ADVERTISEMENT states that its originator has local
subscribers for a track. An Edge Node originates one when its first
local subscriber for the track subscribes. A receiver stores it in
its Subscriber Table.
A SUBSCRIBE_INFO_WITHDRAWAL states that the originator no longer has
subscribers for the track. The originator sends it when its last
local subscriber leaves. A receiver removes the Subscriber
Table entry.
8.6.1. subscribe_info Structure
The subscribe_info structure is:
subscribe_info {
sequence (64),
source_node_id (128),
origin_epoch (64),
track_full_name_hash (..),
subscribe_data_len (i),
subscribe_data (..),
origin_sig (512),
}
Figure 12: subscribe_info encoding
sequence, source_node_id, origin_epoch, track_full_name_hash, and
origin_sig are as in publish_info (Section 8.5.1).
subscribe_data_len, subscribe_data: Subscription data of
subscribe_data_len bytes.
Nandakumar & Jennings Expires 6 May 2027 [Page 41]
Internet-Draft mix November 2026
A SUBSCRIBE_INFO_WITHDRAWAL uses the same encoding with
subscribe_data_len = 0.
8.7. DELIVERY_NODE_SET_ADVERTISEMENT and DELIVERY_NODE_SET_WITHDRAWAL
A DELIVERY_NODE_SET_ADVERTISEMENT carries one Delivery Node Set: for
one track on the Data Session whose delivery-node-sets track carries
it (Section 5.1.3), the destination Nodes the track must reach
through the downstream Node. The upstream Node of the Data Session
sends it, and a later advertisement for the same Delivery Node Set Id
replaces the earlier one. A DELIVERY_NODE_SET_WITHDRAWAL removes the
Delivery Node Set whose Id is given by the MOQT group it appears in;
its body is empty. Both are local to one Data Session and are not
signed.
The delivery_node_set_info structure is:
delivery_node_set_info {
delivery_set_id (32),
full_name_hash (128),
nodes_len (i),
nodes (128) ...,
}
Figure 13: delivery_node_set_info encoding
delivery_set_id: The Id this Delivery Node Set is published under
(Section 4.5).
full_name_hash: The track this Delivery Node Set applies to
(Section 9).
nodes_len, nodes: The number of destination Nodes, followed by their
Node IDs.
9. Track Hashing
All MIX track identifiers (namespace hash, name hash, full-name hash)
are 128-bit values computed with keyed SipHash-2-4 [SipHash] in two-
word output mode. The SipHash key is a fixed 16-byte value shared by
every MIX Node:
MIX_SIPHASH_KEY = 4d 49 58 74 72 61 63 6b 68 61 73 68 4b 31 00 00
("MIXtrackhashK1" zero-padded to 16 bytes)
Figure 14: MIX track-hash SipHash key
Nandakumar & Jennings Expires 6 May 2027 [Page 42]
Internet-Draft mix November 2026
A single fixed key across the network suffices because MIX's security
posture treats track hashes as _identifiers_, not as capabilities: an
attacker who can guess a track name learns the corresponding hash and
gains nothing beyond what they'd gain by observing an advertisement
on the wire. The key is fixed to guarantee interoperability.
Deployments MAY additionally rekey by rolling a new protocol version.
9.1. Namespace and Name Hashes
MOQT track identifiers are tuples: an ordered list of namespace
strings plus a name string. MIX hashes each component individually.
For a namespace tuple ns = (ns_0, ns_1, ..., ns_k-1) and a name
string nm:
namespace_hash_i = SipHash-2-4-128(MIX_SIPHASH_KEY, ns_i)
name_hash = SipHash-2-4-128(MIX_SIPHASH_KEY, nm)
The namespace_hashes[] field of publish_info and subscribe_info is
exactly this per-component sequence.
For contexts that require a single value (Publisher and Subscriber
Table keys, Delivery Node Set lookup), the full_name_hash is:
full_name_hash = SipHash-2-4-128(
MIX_SIPHASH_KEY,
ns_0 || 0x00 || ns_1 || 0x00 || ... || ns_{k-1} || 0x00 || nm)
The 0x00 separator prevents boundary-injection attacks (namespaces
("ab","c") and ("a","bc") produce distinct hashes).
9.2. Rationale
MIX hashes identify tracks; they are not authenticators. Compared to
the 64-bit FNV-1a64 used in earlier designs, SipHash-128 raises the
cost of accidental or adversarial collisions by many orders of
magnitude: FNV-1a64 collisions can be constructed in seconds, whereas
constructing a 128-bit SipHash collision requires on the order of
2^64 work (birthday bound).
The SipHash key is a published constant, so MIX hashes offer no
secret-key protection against chosen inputs. Authorization of
advertisements is handled separately by originator signatures
(Section 10) and operator-level ACLs. Implementations MUST NOT treat
MIX hashes as capabilities, authenticators, or authorization tokens.
Implementations SHOULD validate their SipHash output against the test
vectors in [SipHash].
Nandakumar & Jennings Expires 6 May 2027 [Page 43]
Internet-Draft mix November 2026
10. Originator Authentication
Originator authentication is a core requirement of MIX. Every
CONNECT, NODE_INFO_ADVERTISEMENT, SUBSCRIBE_INFO_ADVERTISEMENT,
PUBLISH_INFO_ADVERTISEMENT, and their respective _WITHDRAWAL variants
MUST carry a 64-byte Ed25519 [RFC8032] signature produced by the
originating Node's private key. There is no unsigned encoding of
these messages. NODE_UNREACH (Section 4.2) is not an originator's
advertisement: it retracts only the sender's own path and is not
signed. Every Node MUST verify the signature before installing the
entry in its Node, Publisher, or Subscriber Table and before re-
flooding. Advertisements that fail signature verification MUST be
discarded and MUST NOT be re-flooded.
Signature verification restricts trust in the peering fabric to the
_originator_ of each advertisement rather than to every transit peer.
A compromised transit Node can suppress or delay advertisements it
receives (a routing availability failure) but cannot forge NODE_INFO,
SUBSCRIBE_INFO, or PUBLISH_INFO on behalf of another Node.
10.1. Signature Input
The signature covers a canonical byte string over the immutable
portion of the advertisement. The mutable portion of a
NODE_INFO_ADVERTISEMENT — its path accumulated during propagation —
is excluded from signature input. Specifically:
For CONNECT, NODE_INFO_ADVERTISEMENT, and NODE_INFO_WITHDRAWAL:
node_info_sig_input {
domain_separator (..) = "MIX/node_info/v1",
tag (8),
id (128),
type (8),
contact_len (8),
contact (..),
longitude (64),
latitude (64),
pubkey (256),
origin_epoch (64),
sequence (64),
data_modes (8),
}
Figure 15: Signature input for node_info
Nandakumar & Jennings Expires 6 May 2027 [Page 44]
Internet-Draft mix November 2026
Note that path is not part of the signature input: paths accumulate
during propagation and cannot be pre-signed by the originator.
Therefore, the originator signature does not protect path contents or
metrics. MIX implementations MUST treat path data as an assertion by
the immediate authenticated peer unless a future version defines per-
hop integrity. Inter-provider deployments MUST NOT use an unsigned
path as a sole authorization or policy signal. Path aggregation does
not solve this integrity limitation.
For SUBSCRIBE_INFO_ADVERTISEMENT and SUBSCRIBE_INFO_WITHDRAWAL:
subscribe_info_sig_input {
domain_separator (..) = "MIX/subscribe_info/v1",
tag (8),
sequence (64),
source_node_id (128),
origin_epoch (64),
track_full_name_hash (..),
subscribe_data_len (i),
subscribe_data (..),
}
Figure 16: Signature input for subscribe_info
For PUBLISH_INFO_ADVERTISEMENT and PUBLISH_INFO_WITHDRAWAL:
publish_info_sig_input {
domain_separator (..) = "MIX/publish_info/v1",
tag (8),
sequence (64),
source_node_id (128),
origin_epoch (64),
track_full_name_hash (..),
forwarding_mode (8),
parameters_len (i),
parameters (..),
}
Figure 17: Signature input for publish_info
Each field takes its value from the message being signed, and tag is
that message's tag (Section 8). domain_separator is the ASCII string
shown, with no length prefix or terminator; it prevents a signature
over one message type from being reused for another. Variable-length
integers appear in their shortest encoding.
Nandakumar & Jennings Expires 6 May 2027 [Page 45]
Internet-Draft mix November 2026
10.2. Replay Guard
Every advertisement includes a 64-bit origin_epoch set by the
originating Node. It identifies a Node incarnation and MUST increase
before that Node publishes after a restart that could reuse a
sequence. It MUST NOT be derived solely from an unsynchronized wall
clock. The pair (origin_epoch, sequence) distinguishes a new process
incarnation from successive updates in that incarnation; sequence is
wide enough to avoid modular comparison and wrap handling.
Freshness comparison is defined in Section 4.1. Withdrawals carry
the same originator, key, and freshness fields and an originator
signature, so a stale withdrawal cannot erase newer state.
10.3. Public Key Distribution
The CONNECT object includes the Node's public key and signed
node_info. A receiver MUST check both the signature and the binding
between the public key and Node ID before using the key to validate
advertisements. Deployments MAY also distribute trusted keys out of
band.
An implementation MUST NOT install a signed advertisement whose
signature verifies against a public key it has never confirmed for
that Node ID via at least one of:
* A prior CONNECT object received over an authenticated, authorized
MOQT session.
* An out-of-band configuration source (for example, a peering
registry).
* A first-flight trust-on-first-use policy, if local policy
explicitly permits it.
Deployments in inter-provider settings SHOULD NOT rely on trust-on-
first- use.
11. Convergence and Flood Minimization
As in BGP [BGP], the Node, Publisher, and Subscriber Tables at each
Node hold the most recent advertisement it has accepted for each key,
and the mesh has converged when no Node has anything new to publish.
To keep re-flooding to a minimum and avoid oscillation, Nodes SHOULD:
Nandakumar & Jennings Expires 6 May 2027 [Page 46]
Internet-Draft mix November 2026
* Suppress repeats. Keep a sent-state record: for each key, the
last advertisement or withdrawal the Node published on its own
nodes, publishers, or subscribers track. BGP calls the equivalent
state the Adj-RIB-Out. A Node does not publish a message that
matches its sent-state record.
* Ignore sRTT jitter when deciding whether a best path changed
materially (Section 4.4).
* Rate-limit what it publishes on those tracks; a token bucket
suffices.
* Damp flapping keys with the Minimum Route Advertisement Interval
(MRAI) extension (Section 15) where it is deployed.
These techniques are informative. Conforming implementations MAY use
other mechanisms provided that convergence is guaranteed in finite
time in the absence of continuing topology change.
12. Deployment Models
This section is informative, except Section 12.2.1, which is
normative for Nodes in a split deployment. It describes the two
deployment shapes for MIX and the trade-offs between them.
MIX separates topology state (the Node Table), which grows with the
number of Nodes, from per-track state (the Publisher and Subscriber
Tables), which grows with the number of tracks and subscribers. The
Node Table has to follow the data-plane topology because path
selection runs over it; the Publisher and Subscriber Tables do not.
Operators can therefore exchange all three tables among the
Forwarding Nodes, the simplest shape to operate, or move the exchange
of the Publisher and Subscriber Tables to a small, dedicated set of
Control Nodes in front of a larger forwarding fabric. The choice
shapes failure blast radius, the trust model between control and data
roles, and which parts of the operational toolchain are involved in a
given MIX event.
12.1. Integrated model
In the integrated model, every Node is a Forwarding Node and every
peering has Full scope (Section 6.1). The same pair of Nodes
exchanges Node, Publisher, and Subscriber Tables over a Control
Session and, when a track needs to flow, forwards objects over a
separate Data Session.
Nandakumar & Jennings Expires 6 May 2027 [Page 47]
Internet-Draft mix November 2026
--- Control Session: Node, Publisher, and Subscriber Tables
=== Data Session: Delivery Node Sets and objects
+---------+ +---------+ +---------+ +---------+
| Edge A1 |---|Transit X|---|Transit Y|---| Edge B1 |
| |===| |===| |===| |
+---------+ +---------+ +---------+ +---------+
Every Node exchanges all three tables and forwards objects.
Figure 18: Integrated deployment
Properties:
* One role per Node. Each Node holds its own Node, Publisher, and
Subscriber Tables and forwards objects for the Delivery Node Set
Ids it is responsible for.
* Failure blast radius = the relay. Losing a Node withdraws its
table entries and tears down its data-plane peerings together.
* Simplest to operate. No Control Nodes to place or provision.
Typical use: small-to-medium meshes within a single operator, pre-
production environments, and reference implementations.
12.2. Split model
In the split model, a small, redundant set of Control Nodes holds and
distributes Publisher and Subscriber Table state for a larger fabric
of Forwarding Nodes. Forwarding Nodes exchange only their Node
Tables with their data-plane neighbors, so path selection
(Section 4.4) runs over the data-plane topology. Publisher and
Subscriber Table entries reach Forwarding Nodes through the Control
Nodes. Each entry names its originator in source_node_id, and a
Forwarding Node finds the path toward that originator in its own Node
Table. Control Nodes never appear in a data-plane path.
Peerings are configured as follows:
* Each Forwarding Node holds Topology peerings with its data-plane
neighbors, and Reflection peerings with at least one Control Node.
It SHOULD hold Reflection peerings with at least two, so that the
loss of one is covered by Section 6.5.
* Control Nodes hold Reflection peerings with each other and with
the Forwarding Nodes they serve.
Nandakumar & Jennings Expires 6 May 2027 [Page 48]
Internet-Draft mix November 2026
--- Control Session === Data Session
Publisher and
+------+ Subscriber Tables +------+ Control Nodes:
| C1 |--------------------| C2 | Publisher and
+------+ +------+ Subscriber Tables only,
| | no objects
+------+------+-------------+------+------+
| | | |
+---------+ +---------+ +---------+ +---------+
| Edge A1 |---|Transit X|---|Transit Y|---| Edge B1 |
| |===| |===| |===| |
+---------+ +---------+ +---------+ +---------+
Reflection peerings (to C1 and C2): Publisher and Subscriber
Tables, plus the Node Table toward the Control Nodes. Topology
peerings between Forwarding Nodes: Node Table only. Data
Sessions: Delivery Node Sets and objects.
Figure 19: Split deployment
Properties:
* Two roles. Control Nodes hold Publisher and Subscriber Tables for
the whole domain. Forwarding Nodes hold the full Node Table,
which grows only with the number of Nodes, plus the Publisher and
Subscriber Table entries the Control Nodes send them.
* Failure blast radius is split. Losing one Control Node is covered
by the remaining ones (Section 6.5). Losing a Forwarding Node
closes its Topology peerings; its neighbors withdraw it from Node
Table and re-run path selection without involving the Control
Nodes.
* Independent scaling. Per-track state scales on the Control Nodes;
Forwarding Nodes scale with the number of Nodes and concurrent
flows. In the integrated model every Node carries both.
Typical use: large multi-site deployments, operators who already
separate control and forwarding planes elsewhere in their stack, and
inter-provider interconnects where the control-plane trust surface is
intentionally smaller than the forwarding fabric.
Three things a split deployment needs are out of scope for this
specification and are left to configuration or other specifications:
how a Forwarding Node finds the Control Nodes for its domain and
replaces one it has lost; how a Control Node verifies that a
Forwarding Node may inject Publisher and Subscriber Table entries for
Nandakumar & Jennings Expires 6 May 2027 [Page 49]
Internet-Draft mix November 2026
its local publishers and subscribers, beyond the originator
signature; and which Publisher and Subscriber Table entries a Control
Node sends to which Forwarding Nodes, since sending every entry to
every Forwarding Node scales poorly.
12.2.1. Publisher and Subscriber Table Reflection
Control Nodes reflect Publisher and Subscriber Table entries in a
single hop over a full mesh, in the manner of BGP route reflection
[RR]. The Control Nodes serving a domain MUST hold a Reflection
peering with every other Control Node in that domain.
A Control Node publishes two tracks in addition to publishers and
subscribers: publishers-mesh and subscribers-mesh (Section 5). Its
Forwarding Node peers subscribe to publishers and subscribers; its
Control Node peers subscribe to publishers-mesh and subscribers-mesh
(Section 6.1). Which accepted entries a Node re-publishes depends on
its role and where it learned the entry:
+============+===================+==================================+
| Node | Entry learned | Re-published on |
| | from | |
+============+===================+==================================+
| Control | A Forwarding Node | publishers/subscribers |
| Node | | and publishers-mesh/ |
| | | subscribers-mesh |
+------------+-------------------+----------------------------------+
| Control | A Control Node | publishers/subscribers |
| Node | (publishers-mesh/ | only |
| | subscribers-mesh) | |
+------------+-------------------+----------------------------------+
| Forwarding | Any Reflection | Not re-published |
| Node | peering | |
+------------+-------------------+----------------------------------+
Table 9: Publisher and Subscriber Tables re-publication in the
split model
A Control Node needs two pairs of tracks because a MOQT track
delivers the same objects to every subscriber. Its clients need
every entry it holds, while other Control Nodes need only the entries
learned from its own clients. If other Control Nodes subscribed to
publishers and subscribers instead, each would re-publish what it
received, and every Control Node would receive every entry once from
each of the others. Nothing would loop, because copies that are not
newer are dropped (Section 4.1), but each copy still costs a
signature check. With the mesh tracks, an entry from Edge A, a
client of C1, travels as follows:
Nandakumar & Jennings Expires 6 May 2027 [Page 50]
Internet-Draft mix November 2026
+---------+
| Edge A | originator, a client of C1
+---------+
| publishers
v
+---------+
+----------| C1 |-----------+
| +---------+ |
| publishers publishers-mesh |
v v
+-------------+ +-------------+
| C1's other | | C2, C3 |
| clients | +-------------+
+-------------+ | publishers only,
| never publishers-mesh
v
+-------------+
| C2's and |
| C3's clients|
+-------------+
Figure 20: One-hop reflection through the mesh tracks
Because entries learned from another Control Node never return to the
mesh, every entry crosses at most two Control Nodes on its way from
originator to Forwarding Node. A Forwarding Node that holds a
Reflection peering MUST NOT hold Full peerings, so its publishers and
subscribers tracks carry only the entries it originates.
The same entry normally arrives more than once: a Control Node
receives it from each Control Node that serves its originator, and a
Forwarding Node receives it from each Control Node it peers with. A
copy whose (origin_epoch, sequence) equals the stored one is not
accepted as new (Section 4.1) and is not re-flooded.
13. Extensions
The sections before this one, other than those marked informative,
form the mandatory MIX core. Every conforming implementation MUST
implement them, except for features marked OPTIONAL where they are
defined. The sections that follow define OPTIONAL extensions; a Node
MAY implement any subset. Each extension is self-describing on the
wire (via existing capability bits, path-element flags, or policy
configuration) so that a Node without a given extension interoperates
unchanged with a Node that has it.
Nandakumar & Jennings Expires 6 May 2027 [Page 51]
Internet-Draft mix November 2026
14. Extension: Path Aggregation
This extension allows a Transit Node to replace a contiguous run of
path elements with a single aggregated element. The aggregated
element carries an aggregator-scoped token (Section 14.1) in place of
the interior Node IDs, and the sum of the interior sRTTs in place of
the per-hop values. Loop detection (Section 14.3) and best-path
selection continue to work across the aggregated element.
Path aggregation is intended for an operator that provides transit
for third parties and does not want to reveal the interior topology
of its network to external peers. It also shortens path on
advertisements sent across wide-area peerings. In a single-operator
mesh it provides no benefit and SHOULD be disabled.
A Transit Node MAY aggregate a contiguous run of path elements that
it originated or transited, provided all of those elements belong to
a single administrative aggregation domain recognized by local
policy.
14.1. Aggregation Token
The aggregation token is a 128-bit HMAC-SHA-256 output truncated to
the first 16 bytes so that it shares the wire slot with a Node ID:
agg_token = truncate128(HMAC-SHA-256(
key = aggregator_secret,
input = "MIX/agg/v1" || aggregator_scope_id))
aggregator_secret is a per-aggregator 32-byte value SHOULD be rotated
periodically. aggregator_scope_id is a 128-bit value identifying the
aggregation domain (typically the aggregator's own Node ID, but a
distinct value MAY be used when a single operator runs multiple
disjoint aggregation domains).
agg_token is stable per aggregator for the lifetime of
aggregator_secret, which allows a downstream Node to detect a loop
that transits the aggregator twice: the same agg_token reappears in
the accumulating path.
14.2. Construction Rules
When a Transit Node V receives a NODE_INFO_ADVERTISEMENT and re-
floods it to peer P, V MAY apply aggregation:
1. Let interior be the contiguous suffix of path whose elements V
considers part of its own aggregation domain, followed by V's own
about-to-be-appended element.
Nandakumar & Jennings Expires 6 May 2027 [Page 52]
Internet-Draft mix November 2026
2. If aggregation to P is permitted by local policy AND |interior| >
1, V replaces interior in the outbound path with a single
element:
flags = 0x01 ; aggregated bit set
node_id_or_token = agg_token ; V's aggregation token
srtt_us = sum(srtt_us over interior)
hop_count = sum(hop_count over interior)
3. Otherwise, V appends its own element unchanged:
flags = 0x00
node_id_or_token = V.node_id
srtt_us = observed sRTT to previous hop
hop_count = 1
Aggregation MUST NOT re-order path elements outside the aggregated
suffix. Aggregation MUST NOT alter path elements that are already
aggregated by a different aggregator (recognizable by their flags
being set with a different node_id_or_token).
14.3. Loop Detection
A receiver detects a loop as follows:
* For a non-aggregated element (flags bit 0 clear), the receiver
checks whether node_id_or_token equals its own Node ID.
* For an aggregated element (flags bit 0 set), the receiver checks
whether node_id_or_token equals any agg_token derived from its own
aggregator_secret and any aggregator_scope_id it uses.
If either check matches, the advertisement is a loop: it removes the
sending peer's candidate instead of adding one (Section 4.2).
14.4. Selection Semantics
Best-path selection (Section 4.4) SHOULD use the sum of hop_count
across path elements as the "path length" comparison metric, not
path_len (the number of encoded elements). This keeps aggregated and
non-aggregated advertisements comparable.
14.5. Policy and Configurability
Aggregation is a local policy decision at each Transit Node.
Implementations MUST provide operator control over:
* Whether aggregation is enabled at all.
Nandakumar & Jennings Expires 6 May 2027 [Page 53]
Internet-Draft mix November 2026
* Which peers receive aggregated advertisements (typically peers
outside the aggregator's administrative domain).
* The aggregator_secret and its rotation schedule.
A downstream Node cannot un-aggregate an aggregated path element.
Its best-current selection algorithm operates on the aggregated
metrics directly.
15. Extension: MRAI Flood Damping
This extension, named after BGP's Minimum Route Advertisement
Interval (MRAI) [BGP], limits how often a Node re-advertises a key to
a peer. After sending an advertisement for a key to a peer, the Node
holds further advertisements for that key to that peer until a timer
of mrai_ms milliseconds expires (Section 15.1). Each key therefore
changes at most 1000 / mrai_ms times per second on each peering. The
sent-state record (Section 11) alone does not provide this bound,
because a key that genuinely flaps differs from the record on every
transition. Withdrawals are not delayed (Section 15.2), so failures
still propagate immediately, and the worst-case convergence time is
bounded (Section 15.4).
MRAI is intended for inter-provider peering and for any deployment in
which advertisement flaps from a peer could impose measurable work on
the receiver. In a single-operator mesh, a Node MAY omit this
extension.
An implementation of this extension maintains a per-peer
configuration value mrai_ms, an integer number of milliseconds.
Deployment guidance:
+==============================+=====================+
| Deployment | Recommended mrai_ms |
+==============================+=====================+
| Closed-mesh, single operator | 0 (disabled) |
+------------------------------+---------------------+
| Inter-provider peering | >= 250 |
+------------------------------+---------------------+
Table 10: MRAI deployment guidance
mrai_ms = 0 disables damping and reduces MRAI behavior to that of the
sent-state record plus the token-bucket rate limiter alone. Closed-
mesh deployments MAY use mrai_ms = 0 since keys are unlikely to be
adversarially flapped and every millisecond of extra latency matters.
Nandakumar & Jennings Expires 6 May 2027 [Page 54]
Internet-Draft mix November 2026
15.1. Timer
For each peer P and each key K (a Node ID for Node Table, or a
(source_node_id, full_name_hash) pair for Publisher and Subscriber
Tables), a Node maintains one timer T[P,K].
* On sending an advertisement to P for K, the Node records the
current time as the last-send time.
* Before sending any subsequent advertisement to P for K, the Node
checks now - last_send >= mrai_ms. If not, the send is deferred
until the timer expires; only the most recent deferred state (if
any) is transmitted when it does.
If the sent-state record (Section 11) suppresses the send outright
(state unchanged from last transmitted), the timer is not restarted.
15.2. Withdrawal Bypass
A NODE_INFO_WITHDRAWAL, NODE_UNREACH, SUBSCRIBE_INFO_WITHDRAWAL, or
PUBLISH_INFO_WITHDRAWAL MUST NOT be held by the MRAI timer.
Withdrawals are sent immediately and reset T[P,K] so that a
subsequent advertisement for the same key is delayed by mrai_ms (this
preserves the anti-flap property even across a withdrawal-
advertisement cycle).
15.3. Interaction With Other Mechanisms
MRAI, the sent-state record, and the token-bucket rate limiter
compose:
1. Sent-state record: identical state → suppressed. Applied first.
2. MRAI: different state, timer not expired → deferred. Applied
second.
3. Token bucket: send admitted → consume token; empty bucket →
dropped without updating the sent-state record (retry on next
state change).
15.4. Convergence Bound
For a network with maximum diameter D hops and MRAI mrai_ms, the
worst-case convergence time for a single state change is D * mrai_ms
+ propagation. Operators SHOULD size mrai_ms with this in mind; a
value larger than one round-trip across the mesh may cause observable
stall during correlated failures.
Nandakumar & Jennings Expires 6 May 2027 [Page 55]
Internet-Draft mix November 2026
16. Security Considerations
TODO
17. IANA Considerations
TODO
18. References
18.1. Normative References
[MoQTransport]
Nandakumar, S., Vasiliev, V., Swett, I., and A. Frindell,
"Media over QUIC Transport", Work in Progress, Internet-
Draft, draft-ietf-moq-transport-22, 1 October 2026,
<https://datatracker.ietf.org/doc/html/draft-ietf-moq-
transport-22>.
[RFC2119] Bradner, S., "Key words for use in RFCs to Indicate
Requirement Levels", BCP 14, RFC 2119,
DOI 10.17487/RFC2119, March 1997,
<https://www.rfc-editor.org/rfc/rfc2119>.
[RFC6234] Eastlake 3rd, D. and T. Hansen, "US Secure Hash Algorithms
(SHA and SHA-based HMAC and HKDF)", RFC 6234,
DOI 10.17487/RFC6234, May 2011,
<https://www.rfc-editor.org/rfc/rfc6234>.
[RFC8032] Josefsson, S. and I. Liusvaara, "Edwards-Curve Digital
Signature Algorithm (EdDSA)", RFC 8032,
DOI 10.17487/RFC8032, January 2017,
<https://www.rfc-editor.org/rfc/rfc8032>.
[RFC8174] Leiba, B., "Ambiguity of Uppercase vs Lowercase in RFC
2119 Key Words", BCP 14, RFC 8174, DOI 10.17487/RFC8174,
May 2017, <https://www.rfc-editor.org/rfc/rfc8174>.
[RFC9000] Iyengar, J., Ed. and M. Thomson, Ed., "QUIC: A UDP-Based
Multiplexed and Secure Transport", RFC 9000,
DOI 10.17487/RFC9000, May 2021,
<https://www.rfc-editor.org/rfc/rfc9000>.
18.2. Informative References
Nandakumar & Jennings Expires 6 May 2027 [Page 56]
Internet-Draft mix November 2026
[BGP] Rekhter, Y., Ed., Li, T., Ed., and S. Hares, Ed., "A
Border Gateway Protocol 4 (BGP-4)", RFC 4271,
DOI 10.17487/RFC4271, January 2006,
<https://www.rfc-editor.org/rfc/rfc4271>.
[LAPS] "Latency-Aware Peering for Streaming (LAPS) Relay
Protocol", 2025,
<https://github.com/Quicr/laps/blob/main/docs/relay-
protocol.md>.
[MOQ-CLUSTER]
Curley, L., "MoQ Cluster Extension", Work in Progress,
Internet-Draft, draft-lcurley-moq-cluster-01, 21 September
2026, <https://datatracker.ietf.org/doc/html/draft-
lcurley-moq-cluster-01>.
[RR] Bates, T., Chen, E., and R. Chandra, "BGP Route
Reflection: An Alternative to Full Mesh Internal BGP
(IBGP)", RFC 4456, DOI 10.17487/RFC4456, April 2006,
<https://www.rfc-editor.org/rfc/rfc4456>.
[SipHash] Aumasson, J. and D. J. Bernstein, "SipHash: a fast short-
input PRF", 2012,
<https://www.aumasson.jp/siphash/siphash.pdf>.
Appendix A. Change Log
A.1. draft-nandakumar-moq-mix-00
* Initial version.
Acknowledgments
The design of MIX was informed by earlier work on inter-relay
peering, in particular [LAPS], which explored path-appending Node
Table, sequence-gated PIB/SIB, and session-scoped Subscribe Node Set
(SNS) concepts. The authors thank the LAPS authors for their
contributions to the problem space.
Authors' Addresses
Suhas Nandakumar
Cisco
Email: snandaku@cisco.com
Cullen Jennings
Cisco
Nandakumar & Jennings Expires 6 May 2027 [Page 57]
Internet-Draft mix November 2026
Email: fluffy@iii.ca
Nandakumar & Jennings Expires 6 May 2027 [Page 58]