在通过另一个本地端口离开后,维护 TCP 数据包的目的端口

在通过另一个本地端口离开后,维护 TCP 数据包的目的端口

问题:

我有一个位于主机(我们称之为host1)上的应用程序,它将 TLS 加密的 TCP 数据包发送到另一台主机的端口 5015(我们称之为host2)。由于网络限制,host1所有入站和出站流量必须通过 80 或 443 进出。我无法访问host2.

方法:

我的想法是,我可以创建一个 iptables 规则,host1将路由/重定向/转发 443 中的 5015 流量,并且必须让它到达host2:5015.我遇到的问题是创建正确的规则。这是我到目前为止所拥有的:

TCP_TRAFFIC_PORT=5015
PROXY_PORT=443

_apply_outbound_rules() {
    # Forward outgoing packets through the proxy port
    sudo iptables -t nat \
        -I OUTPUT 1 \
        -p tcp --destination-port $TCP_TRAFFIC_PORT \
        -j DNAT --to-destination :$PROXY_PORT

    # Send packets to host2:5015 port (this is likely the rule to fix)
    sudo iptables -t nat \
        -I POSTROUTING 1 \
        -p tcp --destination-port $PROXY_PORT \
        -j SNAT --to-source :$TCP_TRAFFIC_PORT
}

apply_outbound_rules

有谁知道如何做到这一点?这似乎是很常见的事情,但我却遇到了麻烦。

答案1

首先,Linux 中的 NAT 是有状态的。这意味着您不需要出站和入站规则。当流量返回经过 NAT 的出站时,Linux 将自动取消返回流量的 NAT。

尽管您将遇到的主要问题是 TCP 会话是由以下各项的组合定义的:

  • 源IP
  • 源端口
  • 目的IP
  • 目的端口

源 IP 已限制为单个值(host1 的 IP)。目标 IP 已经是单个值(主机 2 的 IP)。源端口只有 2 个可能的值(80 和 443)。并且目标端口仅限于单个值 (5015)。
这意味着您最多只能建立 2 个同时连接(如果您跨 2 个端口平衡 SNAT 负载)。即使使用顺序连接,您也可能会遇到端口重用问题,例如端口处于 TIME_WAIT 状态。

尽管如此,如果你真的想尝试这个,应该遵循的规则是:

iptables -t nat -I POSTROUTING \
  -d $HOST2_IP -p tcp --dport $TCP_TRAFFIC_PORT \
  -j SNAT --to-source :$PROXY_PORT

答案2

您是否知道应用程序在您的主机上运行的端口,如果不知道,则需要将所有源端口映射到 80 或 443

尝试下面替换 host2ip。

iptables -t nat -A POSTROUTING -p tcp -d host2ip -j SNAT -m multiport  --sports 1:65535 --to-source :443

相关内容