【问题标题】:Programming P2P application编程 P2P 应用程序
【发布时间】:2012-01-21 08:09:51
【问题描述】:

我正在编写一个在端口 4900 上运行的自定义 p2p 程序。在某些情况下,当此人位于路由器后面时,无法从 Internet 访问此端口。

是否有一种自动方法可以从互联网启用对端口的访问。我不太确定其他 p2p 应用程序是如何工作的。

任何人都可以解释一下吗?

【问题讨论】:

  • @David 我不同意重复,尽管 UPnP 确实是“答案”。
  • @jv42:很公平,这就是为什么关闭需要 5 票。至少,它将 OP 指向有用的相关信息。我认为 StackOverflow 礼仪更喜欢以这种方式链接重复项,而不是重新发布相同的答案。但我可以看到这两者的不同之处。无论哪种方式,只要帮助了 OP,任务就完成了:)
  • @David:我明白了。作为用户,我确实更喜欢直接回答问题,即使它用非常简短的解释指出“重复”。
  • 我已经发布了我的问题,与您的问题相关,但不完全是stackoverflow.com/questions/54118006/vpn-with-webrtc-stun-ice

标签: c# .net sockets networking p2p


【解决方案1】:

我会使用 WebRTC 技术作为此类应用程序的开源框架。

Official Website

事实上,它是一个开放源代码项目,支持开箱即用的点对点技术所需的一切:

  • ICE 和 STUN(NAT 遍历)
  • DTLS 和 SRTP(安全)
  • 用于流媒体质量的 AVPF。

【讨论】:

    【解决方案2】:

    您还有另一个选择是NAT Port Mapping Protocol (NAT-PMP) NAT-PMP 被 Skype 或 BitTorrent P2P 客户端等 VoIP 应用程序广泛使用。

    【讨论】:

    【解决方案3】:

    简而言之,P2P 连接。假设我们在这里谈论的是 UDP。通过一些调整,以下步骤也可以应用于 TCP。

    1. 枚举所有本地 IP 地址(通常只有 1 个)。在给定的端口号**上为每个具有 IP 地址的适配器创建一个 UDP 套接字。

    2. 对于在第 1 步中创建的每个套接字,联系具有相同套接字的 STUN 或 TURN 服务器以发现您的外部 IP 地址并发现内部端口号映射到 NAT 外部的内容(并不总是相同的)端口值)。也就是说,你的本地地址 192.168.1.2:4900 对于外界来说可能是 128.11.12.13:8888。并且一些 NAT 在使用相同的本地端口到其他 IP 地址时并不总是使用相同的端口映射。 TURN 还会为您提供一个“中继地址”。如果路由器支持该协议,您还可以使用 UPNP 直接从路由器获取端口映射地址。

    3. 通过集合服务(SIP、XMPP、即时消息、Web 服务、电子邮件、带字符串的杯子),将您的地址候选列表发布到服务或向其他客户端发送通知,内容为“嘿,我想和你联系”。此消息包括在步骤 1 和 2 中收集的所有“候选地址”(ip 和端口对)。

    4. 远程客户端在收到连接邀请后,也会执行上述步骤 1 和 2。然后通过他收到邀请人候选人名单的同一渠道发回他的候选人名单。

    5. 打孔步骤。两个客户端都开始通过 UDP 向对方的地址候选者发送测试消息,并在他们的一端侦听相同的消息。每当收到消息时,请回复它来自的地址。最终,客户端会发现他们有一对地址,他们也可以可靠地发送数据报。通常,一个端点最终决定与哪个地址对(套接字)进行通信,并且协议有助于该端点将这个决定告诉另一个端点。

    **- 通常最好不要依赖 P2P 客户端的知名端口。因为同一 NAT 或防火墙后面的两个客户端不可能同时使用您的软件。

    这里是一些需要探索的技术的简要总结。

    STUN - 是一个简单的服务器和协议,供 NAT/路由后面的客户端发现其外部 IP 和端口映射是什么。

    TURN 是 STUN 的扩展,但支持中继用于防火墙和 NAT 阻止直接连接的 P2P 连接场景。

    ICE 是使用 STUN 和 TURN 建立 P2P 连接的一组步骤。 ICE 是上述步骤 1-5 的正式协议。 ICE 上的两组优秀幻灯片是 herehere

    WebRTC 是 ICE 标准的变体,也是使用 STUN 和 TURN 进行 P2P 会话的参考库。

    UPNP + Internet Gateway Device Protocol - 一些路由器支持主机自动获取端口映射。

    libnice 是一个用于 Linux 的开源 C 库(可能适用于 Windows),它实现了 ICE。

    libjingle 是 Google 的另一个 ICE 实现(C++)。适用于 Windows 和 Linux。

    PJNATHPJSIP 编码库套件中的一个库。它是 ICE 堆栈(C 代码)的良好实现,并已移植到许多平台。 (Windows、Linux、Mac、iOS、Symbian 以及即将推出的 Android)。

    最后,我有一个公然的插件供你使用my STUN server code base

    【讨论】:

    • 感谢您的解释。
    • @selbie ,如果其中一个或两个对等方落后于 Double NAT,STUN/TURN/ICE 实施是否可以工作?
    • @jagsgediya - 是的。很可能会通过 TURN 收敛。
    • @selbie 我仍然不清楚这些东西是如何工作的。假设 STUN 服务器返回 128.11.12.13:8888 用于 Natted ip 和端口 192.168.1.2:4900 假设我想将我的端口 3000 暴露给外界。我是否将所有到达端口 4900 的请求转发到端口 3000
    • 如果您尝试运行一个任何客户端都无法连接的专用服务器,那么这些东西都不适用。如您所述,您只需在路由器和防火墙上打开一个端口。如果您尝试在不手动配置 NAT 的情况下与另一台计算机动态建立临时短期连接,则适用上述 P2P 说明。
    【解决方案4】:

    这可能比您正在寻找的要复杂一些,但 TCP 打孔是一种应该有效的技术。 http://en.wikipedia.org/wiki/TCP_hole_punching

    另外,UPnP 非常适合支持它的路由器/防火墙。

    【讨论】:

      【解决方案5】:

      在某些情况下有解决方案,见 UPnP:https://en.wikipedia.org/wiki/Universal_Plug_and_Play#NAT_traversal

      我的家用路由器允许这样做,基本上,NAT 可以通过来自计算机的适当请求自动配置。

      我不会指望这会大大提高您的可用性,因为没有多少路由器支持并启用它。

      编辑:@David 为 UPnP 的 .NET 库建议了这个 SO 问题:Is there a UPnP Library for .NET (C# or VB.NET)?

      【讨论】:

        猜你喜欢
        • 2010-10-24
        • 2010-11-03
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2010-11-01
        • 2023-03-03
        相关资源
        最近更新 更多