P2P的NAT穿透解析

[TOC]

NAT背景

NAT(Network Address Translation,),称为网络地址转换或者网络地址掩蔽。NAT是一种网络地址翻译技术,主要是将内部的私有IP地址(private IP)转换成可以在公网使用的公网IP(public IP)。

由于现有的IPv4地址编码只有32位空间,最多可容纳2的32次幂台终端设备连入互联网;再加上IPv4地址空间被按照不同前缀长度划分为A,B,C,D类地址网络和保留地址,更加剧了IP地址的不足。NAT出现的背景正是源于IPv4地址不够用,所以才会采取这种地址转换的策略。可见,NAT的本质就是让一群机器共用同一个IP,这种方案暂时解决了IP短缺的问题。

NAT类型

在RFC3489中定义了4种NAT类型(如下),即早期的STUN协议。STUN(Simple Traversal of User Datagram Protocol Through Network Address Translators),即简单的用UDP穿透NAT,是个轻量级的协议,是基于UDP的完整的穿透NAT的解决方案,最早定义在RFC3489。它允许应用程序发现它们与公共互联网之间存在的NAT和防火墙及其他类型。后来在新的RFC5389修订中把STUN协议定位于为穿透NAT提供工具,而不是一个完整的解决方案,英文全称为Session Traversal Utilities for NAT,即NAT会话穿透工具。

  • 完全锥型NAT(Full Cone NAT)
    即一对一(one-to-one)NAT。一旦一个内部地址(iAddr:port1)映射到外部地址(eAddr:port2),所有发自iAddr:port1的包都经由eAddr:port2向外发送。任意外部主机都能通过给eAddr:port2发包到达iAddr:port1。
完全锥型NAT
  • 受限锥型NAT(Address-Restricted Cone NAT)
    限制地址,即只接收曾经发送到对端的IP地址来的数据包。一旦一个内部地址(iAddr:port1)映射到外部地址(eAddr:port2),所有发自iAddr:port1的包都经由eAddr:port2向外发送。任意外部主机(hostAddr:any)都能通过给eAddr:port2发包到达iAddr:port1的前提是:iAddr:port1之前发送过包到hostAddr:any. "any"也就是说端口不受限制。
受限锥型NAT
  • 端口受限型NAT(Port Restricted Cone NAT)
    类似受限制锥形NAT(Address-Restricted cone NAT),但是还有端口限制。一旦一个内部地址(iAddr:port1)映射到外部地址(eAddr:port2),所有发自iAddr:port1的包都经由eAddr:port2向外发送。一个外部主机(hostAddr:port3)能够发包到达iAddr:port1的前提是:iAddr:port1之前发送过包到hostAddr:port3。
端口受限型NAT
  • 对称型NAT(Symmetric NAT)
    对每个外部主机或端口的会话(session)都会映射为不同的端口。只有来自同一内部IP:PORT、且针对同一外部目标IP:PORT的请求才被NAT转换至同一个公网(外部)IP:PORT,否则的话,NAT将为之分配一个新的外部(公网)IP:PORT。并且,只有曾经收到过内部主机请求的外部主机才能向内部主机发送数据包。重点在于NAT设备会分配不同的外部port来区分不同的会话(session)。
对称型NAT

NAT穿透之UDP打洞

UDP打洞技术是通过中间服务器的协助在各自的NAT网关上建立相关的表项,使P2P连接的双方发送的报文能够直接穿透对方的NAT网关,从而实现P2P客户端互连。如果两台位于NAT设备后面的P2P客户端希望在自己的NAT网关上打个洞,那么他们需要一个协助者——中间服务器,并且还需要一种用于打洞的Session建立机制。目前通用的就是使用STUN协议。

P2P建立Session的通用过程

假定客户端A要发起对客户端B的直接连接,具体的“打洞”过程如下:

  1. A最初不知道如何向客户端B发起连接,于是A向集中服务器发送消息,请求中间服务器S帮助建立与客户端B的UDP连接。
  2. 中间服务器S将含有B的外网和内网的地址二元组发给A,同时,中间服务器S将包含有A的外网和内网的地址二元组信息的消息也发给B。这样一来, A与B就都知道对方外网和内网的地址二元组信息了。
  3. 当A收到由中间服务器S发来的包含B的外网和内网的地址二元组信息后, A开始向B的地址二元组发送UDP数据包,并且A会自动锁定第一个给出响应的B的地址二元组。同理,当B收到由中间服务器S发来的A的外网和内网地址二元组信息后,也会开始向A的外网和内网的地址二元组发送UDP数据包,并且自动锁定第一个得到A回应的地址二元组。由于A与B互相向对方发送UDP数据包的操作是异步的,所以A和B发送数据包的时间先后并没有时序要求。

P2P的3种典型NAT穿透场景

  • 两客户端位于同一NAT设备后面(即相同内网中)
场景1
1. A向中间服务器S请求与B进行连接,S将B的外网以及内网的地址二元组发给A
2. 中间服务器S把A的外网以及内网的地址二元组信息发给B
3. A和B各自给对方公网以及内网地址二元组信息各发送UDP数据包
4. 选择最先响应的地址二元组信息进行常规P2P通信

我们注意到这时里的公网地址其实只有一个,只是目标端口不同。往公网地址发送的UDP数据如果想成功穿透,NAT设备需要支持Hairpin技术。Hairpin技术又被称为Hairpin NAT、Loopback NAT或Hairpin Translation。它能够让两台位于同一台NAT设备后面的主机,通过对方的公网地址和端口相互访问,NAT设备会根据一系列规则,将对内部主机发往其NAT公网IP地址的报文进行转换,并从私网接口发送给目标主机,类似一种中继(relay)。目前有很多NAT设备不支持该技术,这种情况下,NAT网关在一些特定场合下将会阻断P2P穿越NAT的行为,打洞的尝试是无法成功的。

  • 两客户端位于不同的NAT设备后面(分属不同的内网)
场景2
1. A向中间服务器S请求与B进行连接,S将B的外网以及内网的地址二元组发给A
2. 中间服务器S把A的外网以及内网的地址二元组信息发给B
3. A和B各自给对方公网以及内网地址二元组信息各发送UDP数据包
4. 由于内网不存在对端机器,所以内网不会有响应,只有外网响应后才可以通信
  • 两客户端位于两层(或多层)NAT设备之后(分属不同的内网)
场景3

假定NAT C是由ISP提供的NAT设备,NAT C提供将多个用户节点映射到有限的几个公网IP的服务,NAT A和NAT B作为NAT C的内网节点将把用户的内部网络接入NAT C的内网,用户的内部网络就可以经由NAT C访问公网了。从这种拓扑结构上来看,只有服务器S与NAT C是真正拥有公网可路由IP地址的设备,而NAT A和NAT B所使用的公网IP地址,实际上是由ISP服务提供商设定的(相对于NAT C而言)内网地址(我们将这种由ISP提供的内网地址称之为“伪”公网地址)。同理,隶属于NAT A与NAT B的客户端,它们处于NAT A,NAT B的内网,以此类推,客户端可以放到到多层NAT设备后面。客户端A和客户端B发起对服务器S的连接的时候,就会依次在NAT A和NAT B上建立向外的Session,而NAT A、NAT B要联入公网的时候,会在NAT C上再建立向外的Session。

现在假定客户端A和B希望通过UDP“打洞”完成两个客户端的P2P直连。最优化的路由策略是客户端A向客户端B的“伪公网”IP上发送数据包,即ISP服务提供商指定的内网IP,NAT B的“伪”公网地址二元组,{10.0.1.2:55000}。由于从服务器S的角度只能观察到真正的公网地址,也就是NAT A,NAT B在NAT C建立session的真正的公网地址{155.99.25.11:62000}以及{155.99.25.11:62005},非常不幸的是客户端A与客户端B是无法通过服务器S知道这些“伪”公网的地址,而且即使客户端A和B通过某种手段可以得到NAT A和NAT B的“伪”公网地址,我们仍然不建议采用上述的“最优化”的打洞方式,这是因为这些地址是由ISP服务提供商提供的或许会存在与客户端本身所在的内网地址重复的可能性(例如:NAT A的内网的IP地址域恰好与NAT A在NAT C的“伪”公网IP地址域重复,这样就会导致打洞数据包无法发出的问题)。

因此客户端别无选择,只能使用由公网服务器S观察到的A,B的公网地址二元组进行“打洞”操作,用于“打洞”的数据包将由NAT C进行转发,此时如果NAT C不支持Hairpin转换,打洞将失败。

P2P做NAT穿透的约束条件

  • 一制性映射
    在4种NAT类型中,目前只有完全锥型NAT(Full Cone NAT)符合这个要求,可以成功在Peer之间做穿透,其它3种类型基本都无法做穿透;只能依赖Relay服务器做中继(relay)才可完成Peer之间的通信。
    但也有一些例外情况,如一些NAT设备的对称型NAT(Symmetric NAT)在给连续的会话(session)分配外部端口时也会是连续的,这样分配的外部端口就具有高度可预测性;所有穿透算法就可以利用这个特性在穿透时用估算的端口进行穿透测试,如此反复多次测试是否可以打通;但这种方法也只是在某些特定NAT设备中有效。

  • 忽略数据包的payload数据
    一些老的NAT设备在做NAT转换时,由于算法过于简单陈旧,不仅会转换包头的IP地址和端口号,还会把数据包的payload数据中出现的IP地址和端口号也同时转换,这样就会影响STUN协议正常工作。

  • Hairpin转换
    如上面提到的第3个NAT穿透场景中,当两客户端位于两层(或多层)NAT设备之后,就需要NAT设备支持Hairpin转换才可以实现穿透。

全文完

参考资料

Peer-to-Peer Communication Across NATs

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,456评论 5 477
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,370评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,337评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,583评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,596评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,572评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,936评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,595评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,850评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,601评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,685评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,371评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,951评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,934评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,167评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 43,636评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,411评论 2 342

推荐阅读更多精彩内容