【问题标题】:NAT-Traversal implementation for P2P connectionP2P 连接的 NAT-Traversal 实现
【发布时间】:2013-05-02 14:51:25
【问题描述】:

我需要在 NAT 后面实现一个简单的 P2P 应用程序。它应该通过可靠和安全的连接(通过 TCP 加密数据)发送数据。从理论背景来看,我知道在几个 RFC(5389、5769 和 5780)中描述了几种 NAT 遍历技术(例如 NAT 的会话遍历实用程序)。

虽然在实践中我找不到实现这样一个系统所需的工具/库(最好是 C++ 编程语言)。我已经通过盲目的谷歌搜索找到了:ICETURN, libnice, libjingleSTUNTMAN

下图描述了它的外观。我有一个具有有效 IP 地址的 VPS、一个位于 NAT 后面的 PC 和一个位于另一个 NAT 后面的传感器。他们有私有IP。我希望我的传感器连接到服务器,找到监视器并向它发送连接请求。连接建立后,中继服务器不应用于引导数据流量。我希望我的传感器和监视器使用此路径进行通信:

Sensor <--> AP0 <--> R3 <--> {THE INTERNET} <--> R2 <--> Monitor

目前所有数据都是通过VPS传输的:

Sensor <--> AP0 <--> R3 <--> {THE INTERNET} R1 <--> 
VPS <--> R1 <--> {THE INTERNET} <--> R2 <--> Monitor

【问题讨论】:

  • 我知道我什至不应该问,但端口转发或 UPnP 支持是不可能的?
  • @AnthonyAccioly 不,我只是忘了提。我完全糊涂了。无法转过头来寻找起点……

标签: c++ linux networking nat


【解决方案1】:

基本上,如果你可以port forward,那么这更像是一个基础设施问题而不是编程问题。您只需将路由器配置为将流量从公共 IP / 端口引导到私有 IP / 端口,例如:

R2: Port 500 - TCP -> Laptop-PT - Port 500
R3: Ports 16000/16500 - TCP/UDP -> PDA-PT - Port 16000/16500

如果你想变得花哨并且你的路由器支持UPnP,只需求助于实现IGD protocol(例如MiniUPnP)的库,以便让你的应用程序控制端口映射。 This article 提供了一个很好的起点以及一些示例代码(尽管我真的会推荐一个强大的库)。

【讨论】:

  • 我需要访问路由器配置吗?
  • 是的。手动(正如@chris 指出的那样,通过其管理界面配置路由器),或者,如果路由器支持 UPnP(并且已启用),则通过 UPnP 库。看看我回答中的那篇文章,我认为它会让事情变得清晰。
  • 我读过那篇文章。现在我可以考虑使用 UPnP 进行端口转发。那么,现实世界中的路由器是怎样的呢?我应该担心数据路径的所有路由器都缺乏 UPnP 支持吗?
  • 现在大多数路由器都支持 UPnP,但您会发现反例,以及出于安全原因禁用 UPnP 的网络管理员。您应该与网络管理员交谈。
  • 谢谢。去试试吧,我想我应该学习很多 RFC 和代码。测试后会回来:P
【解决方案2】:

因为您最终希望完全移除中继服务器,并希望监视器和端点直接通信 - 您实际上是在尝试解决 NAT 后面的两个服务器之间直接通信的问题。

所以有两个问题需要解决:

1) 允许传感器获取监控系统的公网IP地址。

2) 允许 TCP 连接的 SYN 数据包通过 Router-PT R2 上的 NAT 中继到您的显示器。

中继可以帮助解决的第一个问题:您可以使用 TURN 通过服务器中继消息,将监视器的公共 IP 地址传送到传感器。

然而,第二个问题,我不知道任何通用的解决方案,因为它实际上归结为路由器上的配置。路由器需要知道将 SYN 转发到 NAT 后面的众多系统中的哪一个。它不能转发给所有人:他们都会回应。

大多数启用 NAT 的路由器都有配置设置,允许您配置要将传入数据包路由到的主机。考虑将笔记本电脑监控系统设置为 DMZ,或者将特定 TCP 端口的流量引导到您想要的系统。但是,每个路由器都会以不同的方式处理此配置;据我所知,该配置没有标准化。

希望对您有所帮助。

【讨论】:

  • 是的,但是由于 TCP 连接是点对点的,并且您不希望该数据通过中继服务器转发,因此无法帮助建立连接(正如我所说,在获取监视器的公网IP地址)
  • 换一种说法;中继可以帮助传递建立 TCP 连接的参数,但它不能帮助该实际 TCP 连接的任何数据传输;包括最难的部分——为 TCP 连接发送的第一个数据包:SYN 数据包。
猜你喜欢
  • 2012-12-31
  • 2021-01-19
  • 2017-03-25
  • 2014-07-02
  • 1970-01-01
  • 2011-04-06
  • 1970-01-01
  • 2011-07-02
  • 2013-01-16
相关资源
最近更新 更多