Skip to content

RTSP over UDP unicast, with fallback to TCP #67

Closed

Description

@compot-dev

Split out of #7.

RtspSession always sends Transport: RTP/AVP/TCP;unicast;interleaved=0-1 (video) and interleaved=2-3 (audio), see RtspSession.java:235 and :246. RTP over UDP gives lower latency on a clean LAN and avoids TCP head-of-line blocking on a lossy one.

Majestic already serves it (checked on 172.17.32.133 and .126, Lite SigmaStar, master+012cd47):

SETUP .../video  Transport: RTP/AVP;unicast;client_port=50000-50001
RTSP/1.0 200 OK
Transport: RTP/AVP/UDP;unicast;client_port=50000-50001;server_port=46666-46667

Scope

  • Per-slot transport setting: TCP (default) / UDP / Auto (UDP, fall back to TCP).
  • Ephemeral ports: one DatagramSocket pair (even RTP, odd RTCP) per track, video and audio. Never fixed ports (the bug from basic: track URLs, payload types and UDP ports are hard-coded #40 on basic).
  • Parse server_port (and source if present) from the SETUP reply; ignore datagrams from other sources.
  • Receive threads hand packets to the existing onPacket(CHANNEL_VIDEO/AUDIO, ...), so RtspClient / QuadCell and the depacketizer stay unchanged.
  • RTSP TCP connection stays open for keepalive (GET_PARAMETER / OPTIONS) and TEARDOWN.
  • UDP can reorder and drop: at least a small reorder window by RTP seq, or drop late packets and let NalAssembler discard broken access units. Raise SO_RCVBUF (1–2 MB).
  • Fallback to TCP: on 461 Unsupported Transport, or when no video datagram arrives within N s after PLAY (NAT/firewall). TEARDOWN, reconnect with interleaved TCP, remember the choice for that slot until the URL changes.
  • Optional: send an empty RTP/RTCP datagram to server_port after SETUP to open NAT/firewall pinholes.
  • Clean socket shutdown on stop / reconnect / slot change (Majestic had a UDP fd leak on its side, rtsp udp connection close error majestic#262; make sure we do not have one on ours).

Tests

  • Unit: parsing the Transport reply header (client_port, server_port, source, ssrc, a server that answers TCP to a UDP request).
  • Device (methodology of Device testing: v2 and open PRs (report + checklist) #53): group A cameras, H.264 + Opus and H.265 + Opus, single view and 3×3; fallback forced by blocking UDP; latency compared with TCP.

Activity

  1. compot-dev commented on Oct 12, 2026

    @compot-dev
    CollaboratorAuthor

    Reply formats seen so far, for the Transport parser:

    • Majestic: RTP/AVP/UDP;unicast;client_port=50000-50001;server_port=46666-46667 (no source, no ssrc).
    • XM stock firmware (H264DVR 1.0): RTP/AVP;unicast;mode=PLAY;source=172.17.32.53;client_port=50000-50001;server_port=40008-40009;ssrc=00001BCC (no /UDP, has mode, source, ssrc).
    • Both answer a multicast;client_port=... request with unicast, so the reply, not the request, decides the mode.

    Note that the XM camera allows only one RTSP connection at a time, so fallback must TEARDOWN / close the UDP session before reconnecting over TCP.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions