言成言成啊 | Kit Chen's Blog

iptables实现dnat与snat

发布于2025-08-23 00:15:25,更新于2025-08-26 22:37:56,标签:devops  文章会持续修订,转载请注明来源地址:https://meethigher.top/blog

一、DNAT 与 SNAT

NAT(Network Address Translation,网络地址转换) 用于修改网络数据包中的 IP 地址或端口信息。根据修改的目标不同,NAT 分为两种常见模式:

  • DNAT(Destination Network Address Translation,目标地址转换)

    • 定义:修改数据包的目标 IP 地址或端口。当客户端发送请求时,DNAT 会将数据包的目标地址从一个 IP(或端口)替换为另一个。
    • 典型场景:负载均衡、端口转发。
  • SNAT(Source Network Address Translation,源地址转换)

    • 定义:修改数据包的源 IP 地址或端口。当数据包离开某个设备时,SNAT 会将源地址替换为另一个。
    • 典型场景
      • 内网 IP 通过公网 IP 访问互联网(保证返回数据能正确返回给源地址)。
      • 隐藏客户端真实 IP,提高安全性。

Linux 中,可以通过 iptables 配置 DNAT 和 SNAT。
Windows 中,虽然 netsh 工具支持流量转发,但功能远不及 Linux 的 iptables 强大。netsh 只能监听流入流量并转发,其核心逻辑与我实现的 meethigher/tcp-reverse-proxy 一致(基于 Vert.x 的网络库,支持 HTTP/UDP/TCP 反向代理、TCP 内网穿透、单端口多路复用等)。

二、iptables

2.1 概念

参考资料:

iptables 是 Linux 系统中用于配置和管理 Netfilter 框架 的命令行工具。
Netfilter 是内核提供的网络数据包处理框架,允许用户通过 iptables 设置规则来控制数据包的处理流程。

在新版 Linux 内核中,iptables 已逐步被 nftables 替代。但 nftablesiptables 命令进行了兼容,因此运维人员仍可直接使用 iptables

很多人习惯将 iptables 视为防火墙工具。仅从防火墙角度而言:

  • iptables:内核级防火墙规则。
  • firewalld:用户态的防火墙服务,本质上依赖于 iptables/nftables。
    • 启动时会生成对应的内核防火墙规则。
    • 停止时会清空其添加的规则。
    • 只影响通过 firewalld 管理的规则。

2.2 核心要素

iptables 有三个核心要素:

  1. 表(Tables)
    • filter:默认表,用于过滤数据包(允许或拒绝,防火墙功能基于此表)。
      • 表内包括三个链:INPUTFORWARDOUTPUT
    • nat:用于网络地址转换(DNAT、SNAT)。
      • 表内包括三个链:PREROUTINGPOSTROUTINGOUTPUT
    • mangle:用于修改报文的服务类型、TTL 等高级功能。
      • 表内包括五个链:PREROUTINGPOSTROUTINGINPUTOUTPUTFORWARD
    • raw:用于配置数据包是否绕过连接跟踪。
      • 表内包括两个链:OUTPUTPREROUTING
  2. 链(Chains)
    • INPUT:处理进入本机的数据包。
    • OUTPUT:处理本机发出的数据包。
    • FORWARD:处理需要转发(经由本机路由)的数据包。
    • PREROUTING:路由选择之前处理数据包,例如 DNAT。
    • POSTROUTING:路由选择之后处理数据包,例如 SNAT。
  3. 规则(Rules):每条链包含多条规则,每条规则定义了如何处理匹配的数据包(接受、拒绝、修改等)。

以上内容,简称为四表五链。表的处理优先级:raw>mangle>nat>filter

2.3 工作流程

下图展示了 iptables 的工作流程:

三、场景示例

先说场景:

我有一个客户端试图访问网页 A,网页 A 在其运行过程中会去请求服务 B。然而,客户端与服务 B 之间网络不通。

为了解决这个问题,我在一台网络畅通的机器上部署了一个代理服务 C,用来代理服务 B。为了让客户端的请求能够成功访问到服务 B,我通过 DNAT(目标地址转换)和 SNAT(源地址转换)技术,将原本发往服务 B 的 IP 流量拦截并转发到代理服务 C,代理服务 C 再与服务 B 通信并返回响应,从而实现客户端与服务 B 的间接通信,打通网络的效果。

假设对应的服务IP如下

  • 客户端:10.0.0.10
  • 服务 B:220.181.7.203
  • 服务 C:49.233.46.128

按如下配置,即可解决如上场景问题。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# 1. 开启 IP 转发(必须)
sysctl -w net.ipv4.ip_forward=1

# 2. 查看规则,并清理规则(可选)
# 查看nat表的规则
iptables -t nat -L
# 删除nat表的所有链的(内置链和自定义链)里面的所有规则。不会删除链本身
iptables -t nat -F
# 将nat表已经没有规则的自定义链删除
iptables -t nat -X

# 3. 配置DNAT,目标地址转换。将访问220.181.7.203:443的服务转到49.233.46.128:443
iptables -t nat -A OUTPUT -p tcp -d 220.181.7.203 --dport 443 -j DNAT --to-destination 49.233.46.128:443

# 4. 配置SNAT,源地址转换
iptables -t nat -A POSTROUTING -p tcp -d 49.233.46.128 --dport 443 -j MASQUERADE

# 5. (可选)查看 NAT 规则是否生效
iptables -t nat -L -n -v
发布:2025-08-23 00:15:25
修改:2025-08-26 22:37:56
链接:https://meethigher.top/blog/2025/linux-iptables/
标签:devops 
付款码 打赏 分享
Shift+Ctrl+1 可控制工具栏