2013-08-29 130 views
2

是否有可能在两个不同NAT的客户端之间建立一个直接连接? 当然,我认识到在某种程度上,具有公有IP的服务器将是必不可少的,但我不希望它成为代理。看看下面的场景:如何创建一个P2P连接,当两个客户端都在NAT之后

  • 我不想与配置网络设备有任何关系。我只是想在代码中做到这一点。
  • 我不希望服务器参与文件传输过程中(由于性能原因)
  • 我们有:客户A,客户B和服务器S和它看起来有点像这样:

A - [路由器1] - S - [路由器2] - 乙

  • A连接S和授权
  • B连接到S和授权
  • A想发送一个文件给B
  • 一个要求S代表一连接到B
  • S [做它的魔力在这里]和A现在已经到B
  • A开始发送一个文件的连接
  • S端变为向下(或至少所述文件传输绕过是)
  • 仍有
  • A继续发送文件到B
A和B之间的连接个

我的问题:

  1. 这可能吗?
  2. 如何做到这一点?
  3. 是否遇到过可以做到这一点的示例项目?

我发现WCF/WPF Chat Application,但它原来是一个代理。

我还发现一些帖子提示使用UPnP和NAT Traversal,但没有直接回答我的第一个问题,所以我没有深入研究它。

回答

5

您正在寻找“魔术部分”的术语叫做NAT Hole Punching。不幸的是,这个话题有点太广泛,无法在这里完整解释如何实现它,但现在知道正确的术语应该至少能够让你开始寻找正确的教程。

下面是UDP Hole Punching页面的算法摘要。

让A和B成为两个主机,每个主机都在自己的专用网络中; N1和 N2分别是具有全球可达IP地址P1和 P2的两个NAT设备; S是一个公共服务器,具有全球知名的IP地址 。

  1. A和B各自开始与S的UDP会话; NAT设备N1和N2创建UDP转换状态并分配临时的外部 端口号X和Y
  2. 小号检查UDP数据包获得通过N1和N2(外部NAT端口X和Y)所使用的源端口
  3. S通过P1:X到B和P2:Y到A
  4. A向P2发送数据包:Y和B使用与S对话相同的源端口向P1:X发送数据包,从而“冲孔” 朝向其他主机的NAT
  5. 如果任一主机接收到一个数据包,则打孔成功并且两台主机都可以通信。

如果两个主机具有Restricted cone NATsSymmetric NATs,外部NAT端口将来自那些使用S.在某些 路由器,外部端口依次拾取使得能够 通过猜测附近端口建立对话不同。

无论它的工作是否高度依赖于两个端点的NAT路由器如何工作,很可能您的大部分使用都将配对,并且两个路由器都不是“打孔友好” 。

在你的情况下,我会让我的软件按顺序尝试这些步骤。

  1. 检查,看看我们是否可以只连接(用户做手工端口转发)
  2. 使用UPnP,并打开一个端口
  3. 用途使用的是公共服务器作为
  4. 之间的旅途中某种形式的打孔的
  5. 使用确实已将端口打开的另一端作为数据的代理(一个Supernode)。
  6. 使用我托管的服务器作为代理来转发数据。
相关问题