1

我目前正在使用 golang 编写 P2P 应用程序。我为此选择了Noise,因为它提供了一个易于使用的网络堆栈。

我的应用程序提供了一个 REST API,可以通过localhost. 发送到本地提供的端点的数据然后将被传输到所有连接的对等点,然后将数据分发给它们连接的对等点以保持网络同步。

到目前为止,我的实现已经成功,但这仅适用于公开暴露的节点或同一网络中的节点。

我想让我的应用程序的可用性尽可能简单,对于专用网络中的用户也是如此。因此,我想避免手动配置开销(即路由器设置中的端口转发)。如果可能的话,我还想避免使用中央服务器进行 NAT 遍历,因为我的目标是拥有一个真正去中心化的应用程序。

我知道有几种 NAT-Traversal 技术,例如STUNTURN以及其他技术,并且我知道 Noise 已经提供NAT-PMPUPnP,但不知何故我无法理解它们的工作原理。

我知道,一些 VoIP 或文件共享服务使用 NAT-PMP,它们似乎几乎可以在每个网络上工作,无需任何用户交互。这对我来说似乎有点奇怪,我被困住了。

怎么可能,我的应用程序只是神奇地更改了一些路由器配置以接受传入流量?对我来说,这似乎是一个巨大的安全风险,特别是如果我的应用程序的用户甚至不知道它。此外,我认为并非每个路由器都支持 NAT-PMP 和 UPnP。如果我的用户有其中之一怎么办?

4

2 回答 2

1

怎么可能,我的应用程序只是神奇地更改了一些路由器配置以接受传入流量?对我来说,这似乎是一个巨大的安全风险,特别是如果我的应用程序的用户甚至不知道它。

打开传入端口只会使您与侦听它的特定应用程序的网络堆栈一样不安全,并且不安全的可能性与客户端-服务器模型并没有什么不同。

以您的浏览器为例。每当您访问包含广告网络的某个随机 Internet 站点时,某些恶意实体可能会放置指向其服务器的广告。如果您的浏览器存在漏洞,那么它可能会被利用。

如果您的 P2P 应用程序没有打开端口,它仍然会与 P2P 网络中的各个节点建立传出连接,如果其中一个节点是恶意的并且您的应用程序易受攻击,那么它就可以被利用。

到目前为止,为传入连接打开一个端口只会改变等式,攻击者可以利用某些类型的漏洞(通常是网络堆栈中的低端,在连接设置的早期,例如在预授权消息解析中),而无需等待你来,他们可以拜访您。这是一个差异,但实际上是一个相当小的差异。

无论如何,必须有人打开他们的端口,否则互联网上的任何人都无法与其他人交谈。

最后,更重要的是专注于强化应该暴露在互联网上的应用程序的网络堆栈。

防火墙的好处主要在于避免意外暴露未考虑安全性的服务,无论是遗留服务还是仅仅假设只有内部用户才能访问它们。它们减少了不必要的攻击面

另一方面,NAT-PMP 和类似的存在允许您创建必要的攻击面,这仅仅是因为应用程序无法在没有使用网络的能力的情况下运行。

此外,我认为并非每个路由器都支持 NAT-PMP 和 UPnP。如果我的用户有其中之一怎么办?

UDP打洞是一种不需要路由器配合的NAT穿越策略。

此外,您可以要求用户手动调整他们的防火墙/端口转发规则。

但是,如果所有 nat 遍历策略都失败了,那么下一个问题是是否需要直接的点对点连接才能使您的协议正常工作。例如,在 bittorrent 中它们不是,在这种情况下,形成一个连通图就足够了,而不是一个完全连通的图。类似的事情也适用于群聊。

对于一对一的通信,您可以选择通知用户他们的网络正在阻止连接,或者使用提供数据中继服务的无私(或付费)节点。

于 2019-05-20T19:31:57.583 回答
0

如果没有公共中央目录服务器,这是不可能的。同行没有办法相互识别。这并不意味着服务器必须参与任何对等通信。我只允许发现进入 p2p 网络的入口点。

在 NAT-transversal 上:UPNP 是零配置的唯一方法。请注意,主要问题不是 NAT,而是防火墙配置。由于安全问题,大多数专用防火墙(不是家用路由器)不支持 UPNP。他们仍然可以建立传出连接。

于 2019-05-19T21:39:10.197 回答