RTMP 协议格式

Published: by Creative Commons Licence

  • Categories:

最近在处理直播相关的问题,推流端采用 RTMP 协议,因此花了些时间学习 RTMP 协议。

以下大部分内容都可以从 RTMP 协议规范中获得: RTMP Specification 1.0

RTMP 协议基于 TCP,由两部分构成,一部分是 RTMP Chunks,一部分是 RTMP Message。Message 会被拆分成多个 Chunks 进行传输,这主要是为了在单条通信链路上实现不同 Message 的发送优先级控制。比如要发送 1M 的视频数据,为了避免耗时太长,所以把数据拆分为每个 10K 大小的多个 Chunk。Message 和 Chunk 的关系如下图所示(图片来自这里):

rtmp chunk stream

关于 RTMP 还需要了解以下几部分内容:

  • 握手机制(Handshake): 用于建立 RTMP 连接;
  • RTMP Chunk Stream: 用于承载 Message 的发送;
  • RTMP Message Stream: 用于发送 RTMP 业务数据(比如音视频)及控制指令;
  • RTMP Message Type: 区分不同的 Message 类型,比如 VIDEO/AUDIO 表示音视频数据等;

关于各个部分更详细的信息推荐阅读这篇文档: What is RTMP and how it's used in live-streaming

其他:

  • 标准的 RTMP 只支持 H264/AAC 格式的音视频,金山扩展了 RTMP 使它支持 H265,见这里;
  • RTMP Chunk Stream 允许传输自定义的 Chunk 数据;
  • RTMP Message 不依赖 RTMP Chunk,可以替换掉 RTMP Chunk 层而只使用 RTMP Message,比如 RTMFP 使用 UDP 来传输 RTMP Message;
  • RTMP Chunk 不仅可以使用 TCP 进行传输,也支持其他传输协议,比如 RTMPS 使用 TLS/SSL,RTMPT 使用 HTTP。
  • 使用 rtmpdump 或者 flvstreamer 可以从 RTMP 中提取音视频数据;
  • Wireshark 支持对 RTMP 协议数据进行解析;

下面是一个典型的 RTMP 数据流:

Client >> << Server

>> TCP Connection Establish <<
>> RTMP Handshake <<

>> COMMAND_AMF0 ("connect", tx1, ...) >>
<< WINDOW_ACKNOWLEDEMENT_SIZE         <<
<< SET_PEER_BANDWIDTH                 <<
<< COMMAND_AMF0 ("_result", tx1, ...) <<

>> COMMAND_AMF0 ("createStream", tx2,...) >>
<< COMMAND_AMF0 ("_result", tx2, ...)     <<

>> COMMAND_AMF0 ("publish", tx3, ... streamId, live, ...)            >>
<< COMMAND_AMF0 ("onStatus", tx3, ...code="NetStream.Publish.Start") <<

>> DATA_AMF0 ("@setDataFrame", "onMetaData", ...) >>
>> VIDEO (AVCDecoderConfigurationRecord)          >>
>> AUDIO (AAC Sequence header)                    >>
   ...
>> VIDEO  >>
>> AUDIO  >>
   ...
>> COMMAND_AMF0 ("deleteStream")   >>

>> TCP Connection Drop <<

参考文档: