5.2 握手

一个RTMP连接以握手开始。这里的握手和其他协议的握手不同, 这里的握手由3个固定大小的块组成, 而不是可变大小的块加上头。

5.2.1 握手流程

握手由客户端发送 C0C1块开始。

客户端必须等接收到S1之后才可以发送C2。 客户端必须等接收到S2之后才可以发送其他数据。

服务器必须等接收到C0之后才可以发送S0S1, 也可能是接收到C1之后发送。 服务器必须等接收到C1之后才可以发送S2。 服务器必须等接收到C2之后才可以发送其他数据。

5.2.2 C0S0格式

C0S0是单独的一个字节, 可以当做一个8bit的整数字段来对待。

以下是COS0包的字段解释:

  • 版本号(8位): 在C0包中, 该字段表示客户端请求的RTMP版本。 在S0中, 该字段表示服务器选择的RTMP版本。 本规范所定义的版本是3。 可选值中, 0-2是早期版本所用的, 已被丢弃; 4-31保留在未来使用; 32-255不允许使用(为了区分其他以某一可见字符开始的文本协议)。 如果服务器不能识别客户端请求的版本, 应该返回3, 客户端可能选择降级到版本3, 也可能放弃握手。

5.2.3 C1S1格式

C1S1包的长度固定为1536字节, 包含以下字段:

  • 时间戳(4字节): 该字段承载一个时间戳, 该时间戳应该作为发送端点所有后续块的时间戳起始时间。 可以是0, 也可以是其他的任意值。 为了同步多个块流, 端点可能会发送其他块流时间戳的当前值。
  • 零值(4字节): 该字段所有值都必须为0。
  • 随机数据(1528字节): 该字段可以是任意值。 因为每个端点都需要区分自己和其他端点初始化的握手响应, 所以此数据应该有充分的随机性, 但是没必要使用加密安全的随机值或动态值。

5.2.4 C2S2格式

C2S2包的长度固定为1536字节, 基本上分别是S1C1的回显, 包含以下字段:

  • 时间戳(4字节): 该字段必须包含对等端发来的时间戳(对C2来说是S1, 对S2来说是C1
  • 时间2(4字节): 该字段必须包含先前发送的并被对端读取的包的时间戳。(C1S1)。
  • 随机数据回显(1528字节):该字段必须包含对端发送过来的随机数据字段值(对C2来说是S1, 对S2来说是C1)。 任何一端都可以用时间戳和时间戳2两个字段值和当前时间戳来快速的估算带宽和延迟, 但这样可能并不实用。

5.2.5 握手流程示意图

下面是对图中提到的状态的解释:

  • Uninitialized: 未初始化状态。 在该阶段发送协议版本, 客户端和服务端都未初始化。 客户端在C0包中发送RTMP协议版本, 如果服务器支持此版本, 服务器将在响应中发送S0S1;如果不支持, 服务器采用适当的行为作为响应, 在RTMP规范中是终止连接。
  • Version Send: 版本已发送状态。在未初始化状态之后客户端和服务端都进入版本已发送状态。 客户端等待接收S1包, 服务端等待接收C1包。 收到所等待的包后, 客户端发送C2包, 服务端发送S2包。 之后状态进入发送确认状态。
  • Ack Send: 客户端和服务端等待接收S2C2包, 收到后进入握手完成状态。
  • Handshake Done: 握手完成, 客户端和服务端开始交换消息。

results matching ""

    No results matching ""