WebRTC技术研究二网络传输NAT/STUN/TURN/ICE知识
摘要
目录
三,STUN(Simple Traversal of UDP Through NAT)
音视频通话 = 音视频处理 + 网络传输,而公共互联网不是为了实时通信设计的。所以说开发真正可用的实时音视频服务,从demo到生产上线,中间还差1万个WebRTC。
一,WebRtc协议栈
二,NAT定义及类型
NAT(Network Address Translation,网络地址转换)是1994年提出的。当在专用网内部的一些主机本来已经分配到了本地IP地址(即仅在本专用网内使用的专用地址),但现在又想和因特网上的主机通信(并不需要加密)时,可使用NAT方法。这种通过使用少量的公有IP 地址代表较多的私有IP 地址的方式,将有助于减缓可用的IP地址空间的枯竭,同时保护了局域网内主机的安全。
- NAT实现方式:即静态转换Static Nat、动态转换Dynamic Nat和端口多路复用OverLoad
- NAT穿透方法:目前常用的针对UDP的NAT 穿透(NAT Traversal)方法主要有:STUN、TURN、ICE、uPnP等。
- 其中ICE方式由于其结合了STUN和TURN的特点,所以使用最为广泛。
我们生活中大部分主机都在网关之后,他有自己的内网IP地址,并不知道自己的外网IP在网关上有个NAT功能,可以将内网地址映射成外网地址他就是一个四元组,经过映射后,将内网IP和端口映射成外网IP和端口,其他主机可以通过公网IP地址通信了。
三,STUN(Simple Traversal of UDP Through NAT)
两台外网主机之间也不能直接通信,它需要第三方服务做介绍,即STUN服务
将各自公网信息进行交换,使他们彼此认识
NAT产生原因
- 由于IPV4的地址不够
一个内网中可能有上千台主机,但映射到外网时只有一个或几个IP地址,通过端口号来区分每台主机
这样就形成了一对几百,一对几千,大大减少了公网IP地址的使用 - 出于网络安全的原因
所有办公内的主机都在内部,他有自己的内网IP地址,但是没有外网IP地址,外面的主机就很难攻击到内网的某一台主机,必须要经过防火墙,经过NAT转换,才能找到内网中的主机
四,NAT种类以及穿越原理
当经过NAT转换时,内网的主机出外网的时候形成的映射,并不是一个IP地址和端口,会形成多个IP地址和端口,
和不同的主机连接时都会形成对应的IP地址和端口,限制会更加严格,安全性自然也比前面几种类型要高很多。
五,NAT穿越组合
一旦客户端得知了Internet端的UDP端口,通信就可以开始了。如果NAT是完全圆锥型的,那么双方中的任何一方都可以发起通信。如果NAT是受限圆锥型或端口受限圆锥型,双方必须一起开始传输。
需要注意的是,要使用STUN RFC中描述的技术并不一定需要使用STUN协议——还可以另外设计一个协议并把相同的功能集成到运行该协议的服务器上。
SIP之类的协议是使用UDP分组在Internet上传输音频和/或视频数据的。不幸的是,由于通信的两个末端往往位于NAT之后,因此用传统的方法是无法建立连接的。这也就是STUN发挥作用的地方。
STUN是一个客户机-服务器协议。一个VoIP电话或软件包可能会包括一个STUN客户端。这个客户端会向STUN服务器发送请求,之后,服务器就会向STUN客户端报告NAT路由器的公网IP地址以及NAT为允许传入流量传回内网而开通的端口。
以上的响应同时还使得STUN客户端能够确定正在使用的NAT类型——因为不同的NAT类型处理传入的UDP分组的方式是不同的。四种主要类型中有三种是可以使用的:完全圆锥型NAT、受限圆锥型NAT和端口受限圆锥型NAT——但大型公司网络中经常采用的对称型NAT(又称为双向NAT)则不能使用。
STUN(Simple Traversal of User Datagram Protocol through Network Address Translators (NATs),NAT的UDP简单穿越)是一种网络协议,它允许位于NAT(或多重NAT)后的客户端找出自己的公网地址,查出自己位于哪种类型的NAT之后以及NAT为某一个本地端口所绑定的Internet端端口。这些信息被用来在两个同时处于NAT 路由器之后的主机之间建立UDP通信。该协议由RFC 3489定义。
六,NAT类型检测
STUN 使用下列的算法(取自 RFC 3489)来发现 NAT gateways 以及防火墙(firewalls):
一旦路经通过红色箱子的终点时,UDP的沟通是没有可能性的。一旦通过黄色或是绿色的箱子,就有连线的可能。
七,STUN 方式
- STUN存在的目的就是进行NAT穿越
- STUN是典型的客户端/服务器模式。客户端发送请求,服务器进行响应
解决穿透NAT问题的另一思路是,私网中的VOIP终端通过某种机制预先得到出口NAT上的对外地址,然后在净载中所填写的地址信息直接填写出口 NAT上的对外地址,而不是私网内终端的私有IP地址,这样净载中的内容在经过NAT时就无需被修改了,只需按普通NAT流程转换报文头的IP地址即可,净载中的 IP地址信息和报文头地址信息是一致的。STUN协议就是基于此思路来解决应用层地址的转换问题。
STUN的全称是Simple Traversal of UDP Through Network Address Translators,即 UDP对NAT的简单穿越方式。 应用程序(即STUN CLIENT)向NAT外的STUN SERVER通过UDP发送请求STUN 消息, STUN SERVER收到请求消息,产生响应消息,响应消息中携带请求消息的源端口,即STUN CLIENT在NAT上对应的外部端口。然后响应消息通过NAT发送给STUN CLIENT,STUN CLIENT通过响应消息体中的内容得知其NAT上的外部地址,并将其填入以后呼叫协议的UDP负载中,告知对端,本端的RTP接收地址和端口号为NAT 外部的地址和端口号。由于通过STUN协议已在NAT上预先建立媒体流的NAT映射表项,故媒体流可顺利穿越NAT.
STUN协议最大的优点是无需现有NAT/FW设备做任何改动。由于实际应用中,已有大量的NAT/FW,并且这些NAT/FW并不支持VoIP的应用,如果用MIDCOM或NAT/ALG方式来解决此问题,需要替换现有的NAT/FW,这是不太容易的。而采用STUN方式无需改动NAT/FW,这是其最大优势,同时STUN方式可在多个NAT串联的网络环境中使用,但MIDCOM方式则无法实现对多级NAT的有效控制。
STUN的局限性在于需要VOIP终端支持STUN CLIENT的功能,同时STUN并不适合支持TCP连接的穿越,因此不支持H323.另外 STUN方式不支持对防火墙的穿越,不支持对称NAT (Symmetric NAT)类型(在安全性要求较高的企业网中,出口NAT通常是这种类型)穿越。
八、TURN方式
- 其目的是解决对称NAT无法穿越的问题
- 其建立在STUN之上,消息格式使用STUN格式消息
- TURN Client 要求服务端分配一个公共IP和Port用于接收或发送数据
在上图的传输过程中 TURN Client端到 TURN server端可以使用 UDP、TCP、TLS over TCP
TURN server端到 peer端 统一使用UDP。
TURN方式解决NAT问题的思路与STUN相似,也是私网中的VOIP终端通过某种机制预先得公网上的服务地址(STUN方式得到的地址为出口 NAT上外部地址,TURN方式得到地址为TURN Server上的公网地址),然后在报文净载中所要求的地址信息就直接填写该公网地址。
TURN的全称为Traversal Using Relay NAT,即通过Relay方式穿越NAT.TURN应用模型通过分配 TURN Server的地址和端口作为私网中VOIP终端对外的接受地址和端口,即私网终端发出的报文都要经过TURN Server进行Relay转发,这种方式除了具有STUN方式的优点外,还解决了STUN应用无法穿透对称NAT(Symmetric NAT)以及类似的Firewall设备的缺陷,同时TURN支持基于TCP的应用,如H323协议。此外TURN Server控制分配地址和端口,能分配RTP/RTCP地址对(RTCP端口号为RTP端口号加1)作为私网终端用户的接受地址,避免了STUN方式中出口NAT对RTP/RTCP地址端口号的任意分配,使得客户端无法收到对端发来的RTCP报文(对端发RTCP报文时,目的端口号缺省按RTP端口号加 1发送)。
TURN的局限性在于需要VOIP终端支持TURN Client,这一点同STUN一样对网络终端有要求。此外,所有报文都必须经过TURN Server转发,增大了包的延迟和丢包的可能性。
九,TURN的使用步骤
- STUN binding
客户端到服务端打通,拿到映射的IP地址 - Caller TURN allocation
发起方(Caller)调用 allocation,让TURN server开辟一个服务,接收发送数据的IP地址和端口 - Caller sends offer
Caller 通过信令 SDP的offer 将媒体信息,网络信息等发送给被调用者 - Callee TURN allocation
对方(Callee)接到信息后也要发送给TURN服务发送 allocation - Callee answers OK
Callee 回复OK - Exchange candidate IP addresses
交换 IP地址 - ICE check for P2P connection
首先检查 P2P是否能打通NAT - If P2P unsuccessful, make relay connection
不成功的话,通过中继服务
参考文章:
https://my.oschina.net/mye/blog/129921
https://webrtc.github.io/samples/