WebRTC相关

一.浏览器中的协议栈

左侧为http协议的协议栈,右侧为WebRTC协议栈

img

1.http相关协议栈

  • API层:提供了XHR、SSE、WebSocket
  • 应用层:提供了http1.x/2.0https协议
  • 会话层:使用了TLS协议(可选),对于https需要这个协议,对于http并不需要
  • 传输层:底层使用TCP传输,流传输
  • 网络层:IP协议

2.WebRTC协议栈

  • API层:提供了RTCPeerConnection和DataChannel
  • 应用层:对于PeerConnection使用了SRTP协议,对于DataChannel使用了SCTP协议(流控传输协议)
  • 会话层:使用了DTLS协议(仿照TLS),对于SRTP可选,对于SCTP为必须
  • 链路检测层:ICE/STUN/TURN检测端到端之间的通路,进行连通性检测
  • 传输层:底层使用UDP传输,报文传输
  • 网络层:IP协议

二.WebRTC传输协议分析

1. RTP/SRTP

区别在于传输内容是否加密,同样对于RTCP/SRTCP一样。如下图(前12字节固定 + (0~15)个32位的CSRC标识符)

img

其中:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
V (2bits):   RTP协议的版本号,当前协议版本号为2。
P (1bit): 填充标志,如果设置填充位P=1,在包尾将包含附加填充字节,它不属于有效载荷。填充的最后一个八进制包含应该忽略的八进制计数。某些加密算法需要固定大小的填充字节,或为在底层协议数据单元中携带几个RTP包。
X (1bit): 扩展标志,如果X=1,则在RTP报头后跟有一个扩展报头
CC(4bits): CSRC计数器,指示CSRC 标识符的个数。

M (1bit): 标记位(不同载荷含义不同,视频标记一帧的最后一个分片slice则=1,其他=0)标识帧边界
PT (7bits): 载荷类型RTP_PAYLOAD_RTSP,记录后面资料使用哪种 Codec , receiver 端找出相应的 decoder 解碼出來。例如H264=96---用于区分不同的编解码器
序列号(16bits): 用于标识发送者所发送的 RTP 报文的序列号(初始值随机),每发送一个报文,序号增加 1

时间戳(32bits): 时间戳反映了该 RTP 报文的第一个八位组的采样时刻。 接受者使用时间戳来计算延迟和抖动, 并进行同步控制。如果帧分包后,如何组合?通过时间戳和序列号判断,同一个帧的timestamp相同,并且序列号连续。还可以通过M标记位
SSRC(32bits): 区分是在和谁通信。值随机选择,参加同一视频会议的两个同步信源的SSRC要相同。音视频源各有自己的ssrc,如果已经存在一个SSRC,则后面产生的不允许重复,后面的需要重新更改SSRC

贡献源(CSRC)标识符(32bits):每个CSRC标识符占32位,可以有0~15个。每个CSRC标识了包含在该RTP报文有效载荷中的所有特约信源。
应用场景:多路混音、混流时使用,多人通信时,将音频进行混音后,其贡献者有多人,每一个的ssrc都放入一个CSRC当中去

2. RTP/RTCP

RTP协议定义流媒体数据在互联网上传输的数据包格式,而RTCP协议则负责可靠传输、流量控制和拥塞控制等服务质量保证。

3. DTLS

在对SRTP/SRTCP数据进行加密之前,需要对证书进行检测,算法协商,通过DTLS实现。

DTLS协议在UDP提供的socket之上实现了客户机与服务器双方的握手连接,并且在握手过程中通过使用PSK或ECC实现了加密,并且利用cookie验证机制和证书实现了通信双方的身份认证,并且用在报文段头部加上序号,缓存乱序到达的报文段和重传机制实现了可靠传送。

大体来说分成三个过程:明文通信过程、非对成加密通信过程、对称加密通信过程;

  1. 明文通信过程:在通信两端首次向对方发送 Hello 消息时,由于双方都没有协商好要使用哪种加密方式,因此这个过程中的消息都是使用明文进行发送的。
    a. Client Hello:客户端首先向服务端发起握手,在握手消息中告诉对方自己支持的 SSL/TLS 版本、加密套件(包括非对称加密时使用的算法与、非对称加密时使用的算法、产生密钥的伪随机函数 PRF)与数据压缩算法(TLS1.3之后就已经没有这个字段)等;还会携带一个 Session ID,因为握手流程的开销比较大,使用 Session ID 可以在下一次与 TLS 握手的过程跳过后续繁琐的握手流程,重用之前的握手结果(如版本号、加密算法套件、master-key 等);并产生一个随机数 A,也告诉给对方;

    b. Server Hello:服务端响应一个 Server Hello 消息,携带协商出来的 TLS/SSL 版本号、加密套件和数据压缩算法,如果服务端同意客户端重用上次的会话,就返回一个相同的 Session ID,否则就填入一个全新的 Session ID;

    c. Server Certificate(可选):携带服务端数字证书(CA)以验证服务端身份,里面携带了服务端非对称加密所使用的公钥;这步虽然是可选的,但是一般来说客户端都会要求验证服务端的身份,在大多数情况下这步都会执行;

    d. Server Key Exchange(可选):在使用某些非对称加密算法(例如 DH 算法)的情况下,Server Certificate 里的信息是不足够的,或者 Server Certificate 在某些通信过程中直接被省略了(没有验证服务端身份),需要 Server Key Exchange 里的额外信息来帮助客户端生成 pre-master key;

    e. Client Sertificate Request(可选):在有些安全性要求高的场景,例如银行支付等,不仅需要验证服务端的身份,还需要验证客户端的身份,这时候服务端就会要求客户端提供客户端的身份证书;

    f. Server Hello Done:表明 Server Hello 结束;

    g. Client Certificate(可选):如果服务端要求客户端提供数字证书以验证身份,则客户端发送自己的身份证书给服务端;

  2. 非对称加密通信过程:由于非对称加密通信的性能较差,在实际的通信过程中其实使用的是对称加密通信,为了保证对称加密通信过程的安全性,也就是需要避免对称加密密钥被窃取,这个密钥在协商过程中使用非对称加密来进行加密。

    a. Client Key Exchange:客户端在验证服务端的身份证书后,会取出其中的服务端公钥,产生一个随机数 C,作为 pre-master key,在本地使用之前的随机数 A、B 和这次生成的 C 共同生成对称加密密钥 master-key;使用服务端公钥对 pre-master key 加密后发送给服务端;

    b. Certificate Verify(可选):如果服务端要求客户端提供客户端证书,那么客户端在发送 Client Key Exchange 之后必须马上发送 Certificate Verify,其中的内容是客户端使用自己的私钥加密的一段数据,提供给服务端用客户端的公钥来进行解密验证。之所以需要这一步是为了确保客户端发送的证书确实是它自己的证书;

    c. Client Change Cipher Spec:提示服务端随后使用 master key 来进行对称加密通信;

    d. Client Handshake Finished: 表明客户端侧 SSL/TLS 握手结束;

    e. Server Change Cipher Spec:提示客户端随后使用 master key 来进行对称加密通信;

    f. Server Handshake Finished:表明服务端侧 SSL/TLS 握手结束;

  3. 对称加密通信过程:通过上述握手过程协商出对称加密算法及使用的对称加密密钥之后,随后的通信过程,也就是实际的应用通信过程,都使用的是对称加密。


WebRTC相关
https://jing-jiu.github.io/jing-jiu/2021/12/05/其他/WebRTC/
作者
Jing-Jiu
发布于
2021年12月5日
许可协议