You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

新旧公网/24子网1:1 NAT代理(firewall-cmd/iptables)配置求助

新旧公网/24子网1:1 NAT代理(firewall-cmd/iptables)配置求助

看起来你在做新旧公网子网的1:1 NAT迁移,这个需求其实很常见,但iptables/firewalld的规则链逻辑确实容易搞混,我来帮你梳理下问题出在哪,以及正确的配置方向。

先说说你当前配置的问题

你遇到的Invalid argument错误,核心原因是在PREROUTING链用了SNAT规则——这完全不符合iptables的规则链逻辑:

  • PREROUTING链属于nat表的"路由前"阶段,只能修改数据包的目标地址(用DNAT),用来把外部访问的旧IP导向新IP;
  • SNAT是修改数据包的源地址,必须在POSTROUTING链(路由后阶段)使用,通常用于隐藏内部源IP。
    所以你直接在PREROUTING里加SNAT,iptables肯定会报错拒绝。

另外,你当前只针对单个VIP(XXX.XXX.XXX.99)配置了规则,但你的需求是整个/24子网的1:1映射,单个IP的规则显然不高效,这里我们可以用iptables专门的NETMAP目标来实现网段级的1:1映射,比写一堆单个IP的规则方便太多。

概念先理清楚

先明确几个关键NAT类型的区别,避免再搞混:

  • DNAT:修改数据包的目标地址,用于把外部请求的旧IP映射到新IP,在PREROUTING链处理;
  • SNAT:修改数据包的源地址,用于把新子网返回的数据包的源地址改回旧IP,让外部客户端能正确接收响应,在POSTROUTING链处理;
  • NETMAP:iptables的特殊目标,专门用于同掩码网段的1:1地址映射(比如XXX.XXX.XXX.x → YYY.YYY.YYY.x,主机位完全对应),完美匹配你的需求。

正确的配置步骤

1. 永久启用IP转发

临时写/proc/sys/net/ipv4/ip_forward重启会失效,建议写到sysctl配置里:

echo "net.ipv4.ip_forward=1" >> /etc/sysctl.conf
sysctl -p  # 立即生效

2. 启用Masquerade并刷新规则

这一步你之前做的是对的,确保永久生效:

firewall-cmd --permanent --zone=public --add-masquerade
firewall-cmd --reload

3. 配置网段级1:1 NAT映射

用NETMAP实现整个旧子网到新子网的1:1映射:

第一步:配置DNAT,把旧IP的请求转发到新IP
firewall-cmd --direct --permanent --add-rule ipv4 nat PREROUTING 0 -d XXX.XXX.XXX.0/24 -j NETMAP --to YYY.YYY.YYY.0/24

这条规则的意思是:所有目标地址是旧子网XXX.XXX.XXX.0/24的数据包,自动把目标地址映射到新子网对应的IP(比如XXX.XXX.XXX.9 → YYY.YYY.YYY.9,主机位完全对应)。

第二步:配置SNAT,让新子网的返回包能正确回到客户端

新子网服务器返回的数据包源地址是新IP,需要改成对应的旧IP才能让客户端正常接收(因为客户端原本请求的是旧IP):

firewall-cmd --direct --permanent --add-rule ipv4 nat POSTROUTING 0 -s YYY.YYY.YYY.0/24 -j NETMAP --to XXX.XXX.XXX.0/24

4. 生效规则

执行reload让所有永久规则生效:

firewall-cmd --reload

关键前提提醒

你之前给代理服务器加了旧子网的VIP(XXX.XXX.XXX.99),但还要确保整个旧子网的流量都能到达这个代理服务器:

  • 要么让旧子网的上游路由器把XXX.XXX.XXX.0/24的所有路由指向代理服务器;
  • 要么在代理服务器上配置旧子网的整个段作为VIP(可以用ip addr add批量添加,比如for i in {1..254}; do ip addr add XXX.XXX.XXX.$i/24 dev eth0; done)。
    只有旧子网的流量能到代理服务器,NAT规则才能生效。

验证配置

  1. 检查IP转发是否生效:
sysctl net.ipv4.ip_forward

返回net.ipv4.ip_forward = 1就是正确的。

  1. 检查firewalld的direct规则:
firewall-cmd --direct --get-rules ipv4 nat PREROUTING
firewall-cmd --direct --get-rules ipv4 nat POSTROUTING

能看到你添加的两条NETMAP规则就说明配置成功。

  1. 抓包验证:
    在代理服务器上执行tcpdump -i any host XXX.XXX.XXX.9,然后从外部设备访问XXX.XXX.XXX.9,就能看到数据包被转发到YYY.YYY.YYY.9的流量。

备注:内容来源于stack exchange,提问作者Max Cuttins

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.21 08:38:03