niom-turn/docs/mvp_gaps_and_rfc_notes.md

4.8 KiB

MVP Gaps & RFC Notes (STUN/TURN)

This document lists intentionally simplified / missing pieces in the current niom-turn MVP, with a short impact note and a code anchor for each.

Goal: clarity on what is already interoperable, and what still needs work for production / broader interop.


1) STUN Binding ist minimal

Current state

  • The server answers METHOD_BINDING with "Success" and includes XOR-MAPPED-ADDRESS (IPv4 + IPv6): src/stun.rs

Impact

  • This improves interop for STUN diagnostics / ICE NAT discovery.

2) IPv6 support (historical note)

Current state

  • XOR-Address encoding/decoding supports IPv4 and IPv6 (XOR key: magic cookie + transaction ID): src/stun.rs

Impact

  • TURN/STUN can correctly handle IPv6 addresses in XOR-ADDRESS attributes.

3) TURN Allocate is heavily simplified

Current state

  • allocate_for always binds a UDP relay on 0.0.0.0:0: src/alloc.rs
  • REQUESTED-TRANSPORT is not evaluated (there is only UDP relay).
  • Additional RFC TURN options (EVEN-PORT, RESERVATION-TOKEN, DONT-FRAGMENT, etc.) are not implemented.

Impact

  • The MVP covers the common UDP relay case, but not the full TURN feature matrix.

4) Data plane: UDP relay yes, TCP relay no

Current state

  • The relay data path is UDP-only (the relay socket is tokio::net::UdpSocket): src/alloc.rs
  • The TLS listener reuses the control-plane logic; there is no separate TCP relay: src/tls.rs

Impact

  • turns: (TLS) supports the control plane, and for stream clients the return path (server → client) is delivered over the stream as Data Indications / ChannelData.
  • However, the actual relay socket towards the peer is still UDP-only. A true TURN-over-TCP/TLS data plane with a dedicated TCP relay path is not implemented.

5) Allocation and timer behaviour is MVP-style

Current state

  • Allocation lifetime is set/clamped via refresh_allocation: src/alloc.rs
  • remove_allocation removes the entry.
  • The relay task (spawned in allocate_for) can continue running and primarily checks whether the allocation still exists: src/alloc.rs

Impact

  • With many allocations, this can lead to unnecessary background tasks (resource management / backpressure is minimal).

6) Permissions & channel bindings are minimal

Current state

  • Permission TTL is static (300s) and is only renewed by sending CreatePermission again: src/alloc.rs
  • Channel bindings use the same TTL value (PERMISSION_LIFETIME): src/alloc.rs

Impact

  • Functionally OK for an MVP, but not necessarily RFC-exact in all details (separate lifetime rules / refresh strategies are common).

7) MESSAGE-INTEGRITY/FINGERPRINT

Current state

  • MESSAGE-INTEGRITY is validated in an RFC-compatible way (HMAC-SHA1 over the message up to and including the MI attribute; the header length is set to the “end of MI”, which is compatible with subsequent attributes like FINGERPRINT): src/stun.rs
  • For TURN responses after successful authentication, the server appends MESSAGE-INTEGRITY and sets FINGERPRINT as the last attribute: src/server.rs, src/turn_stream.rs
  • FINGERPRINT is appended as the last attribute on all STUN messages built by the server, and validated on inbound messages (if present): src/stun.rs

Impact

  • Better browser/ICE interop and mild hardening (messages with invalid FINGERPRINT are dropped).

8) Observability / limits / hardening (still missing)

Current state

Impact

  • For production you likely want limits, persistent credentials, monitoring/metrics, and stricter error handling.

9) More RFC corners (not implemented)

Typical items that are missing / still open in the MVP:

  • Full attribute coverage (e.g. UNKNOWN-ATTRIBUTES, SOFTWARE, etc.)
  • Fully RFC-accurate STUN/TURN class/method encoding (here intentionally simplified via METHOD | CLASS_*): src/constants.rs
  • IPv6 hairpinning edge cases, NAT-related interop edge cases

What is already covered well

  • End-to-end UDP TURN core: AllocateCreatePermissionSend/ChannelData → return path as Data Indication/ChannelData.
  • Long-term auth (realm/nonce + MI) with clear 401/438/437/403 paths.
  • TLS listener (control plane) with STUN framing over TCP/TLS.

See also the integration tests: tests/udp_turn.rs and tests/tls_turn.rs.