我有一个在特定端口上运行的服务,但为了使其可以通过更容易记住的端口以及正常端口访问,我添加了一个充当端口别名的 iptables 规则:
iptables -A PREROUTING -i eth0 -p tcp -m tcp --dport 5555 -j REDIRECT --to-ports [configured port]
也许我有点天真,但我实际上是从在 POSTROUTING 中添加第二条规则开始的,该规则将 TCP 源端口重新映射到传出流量中的别名端口。然而,事实证明我根本不需要那条规则。所以,我的问题是:为什么只使用一条规则就可以工作?
客户端连接到主机:别名端口。由于 iptables 中没有规则来重新映射此服务的传出流量的源端口,因此它将收到来自主机的响应,但源端口不同。这不会导致客户端的 TCP 对话映射问题吗?我的意思是,客户端期待来自主机:别名端口的响应,但实际上(理论上)会收到来自主机:真实端口的响应。而且由于流量不会被视为“相关”,它甚至不应该通过 NAT 或其他有状态防火墙——但它却通过了。iptables 中是否有某种神奇之处,可以查看传入的预路由规则,然后自动将传出流量也调整到此规则?
答案1
REDIRECT
target 是 target 的一个特例DNAT
,用于方便使用。请参阅相关内容netfilter 文档,答案如下unix StackExchange。
目标DNAT
是改变第一个数据包,但也会改变同一连接的所有未来数据包,这就是为什么一条规则就足够了。从手动 iptables(参见目标扩展,dnat 部分):
此连接中的所有未来数据包也将被破坏
注意:目标DNAT
和仅在表、链和REDIRECT
中有效。nat
PREROUTING
OUTPUT