文章

iptables 指令详情

学习 iptables 指令并做的笔记

iptables 指令详情

Linux 内核 Netfilter 框架的用户态配置工具, 用于定义数据包在内核网络协议栈中的处理规则, 本质上是一个包过滤与控制系统. 并不直接“转发”或“阻止”流量, 而是通过规则告诉内核: 某一类数据包在某个阶段应该如何处理

1. 核心架构: 四表五链

要掌握 iptables, 首先要理解数据包在内核中流经的逻辑路径.

1.1. 五个链 (Chains)

链 (Chains) 代表了数据包在 Linux 内核网络栈中传递的 不同阶段或时机. 每一个链都像是一个 “关卡”, 当数据包经过这个位置时, 内核会检查该链上定义的规则, 并决定如何处理该数据包.

链是数据包处理的 “检查站”:

  • PREROUTING (prerouting): 数据包进入路由表之前. 常用于 DNAT (目的地址转换).
  • INPUT: 数据包目的地为本机时触发.
  • FORWARD (forward): 数据包只是经过本机转发到其他目的地时触发.
  • OUTPUT: 本机产生的数据包向外发送时触发.
  • POSTROUTING (postrouting): 数据包离开路由表之后. 常用于 SNAT (源地址转换).

1.1.1. PREROUTING (路有前)

这是数据包进入网络接口 (网卡) 后遇到的 第一个关卡.

  • 触发时机: 硬件接收到数据包, 准备交给内核处理, 但还 没有 进行路由决策 (即还不知道该包是发给本机的, 还是需要转发的).
  • 主要作用: 主要用于 DNAT (目的地址转换). 比如你有一台公网服务器, 想把访问 80 端口的流量转发到内网的另一台机器, 就在这里修改目的 IP.

1.1.2. INPUT (入站)

当内核完成路由决策, 确定数据包的 目的地是本机 时, 数据包会进入此链.

  • 触发时机: 路由决策后, 确定是发往本地进程 (如 Apache, SSHD).
  • 主要作用: 防火墙的核心防御地带. 用于 过滤 (Filter) 进来的流量, 决定哪些 IP 或端口可以访问本机的服务.
  • 典型操作: iptables -A INPUT -p tcp --dport 22 -j ACCEPT.

1.1.3. FORWARD (转发)

当内核完成路由决策, 发现数据包的 目的地不是本机, 需要通过本机中转到另一个网段时, 数据包会进入此链.

  • 触发时机: 路由决策后, 确定本机只是一个 “路由器” 角色.
  • 主要作用: 控制内网机器通过本机上网的权限, 或者在两个不同网段间建立访问控制.
  • 注意: 必须开启 Linux 内核的转发功能 (ip_forward) 此链才会生效.

1.1.4. OUTPUT (出站)

处理由 本机进程产生 并准备发往外部的数据包.

  • 触发时机: 本地应用程序 (如 curl, ping) 发起网络请求并产生数据包时.
  • 主要作用: 限制本机对外的访问. 比如为了安全, 禁止本机访问某些特定的恶意 IP 或屏蔽特定的传出端口.

1.1.5. POSTROUTING (路由后)

这是数据包离开本机网卡之前遇到的 最后一个关卡.

  • 触发时机: 路由决策已完成, 且数据包即将发往物理介质 (网卡).
  • 主要作用: 主要用于 SNAT (源地址转换)Masquerade (伪装). 比如局域网多台机器共享一个公网 IP 上网时, 在这里将内网 IP 替换为公网 IP.

1.1.6 数据包的流向路径

数据包通常会走以下三条路之一:

  • 发往本机: PREROUTING $\to$ INPUT $\to$ (本地进程)
  • 由本机发出: (本地进程) $\to$ OUTPUT $\to$ POSTROUTING
  • 经本机转发: PREROUTING $\to$ FORWARD $\to$ POSTROUTING

1.1.7 链与表的对应关系

链名称 常用表 核心用途
PREROUTING nat, mangle 端口映射 (DNAT), 修改包头
INPUT filter, mangle 允许/拒绝入站流量
FORWARD filter, mangle 控制中转流量
OUTPUT filter, nat, mangle 控制本机出站流量
**POSTROUTING ** nat, mangle 网络地址转换 (SNAT/网关)

1.2. 四个表 (Tables)

表 (Tables) 决定了你对数据包进行的 操作类型. 如果说 “链” 是关卡的位置, 那么 “表” 就是关卡内提供的 功能手册.

表是规则的 “分类容器”:

  • filter: 默认表, 负责过滤 (ACCEPT/DROP).
  • nat: 负责网络地址转换 (SNAT/DNAT).
  • mangle: 修改数据包头部信息 (如 TTL, TOS).
  • raw: 用于配置不被连接追踪 (Connection Tracking) 机制处理的数据包.

1.2.1. Filter 表 (过滤表)

最常用、也是默认的表. 如果你在指令中没有使用 -t 指定表名, iptables 就会默认操作 filter 表.

  • 核心功能: 数据包过滤. 决定一个包是该放行 (ACCEPT), 还是该丢弃 (DROP/REJECT).
  • 支持的链: INPUT, FORWARD, OUTPUT.
  • 典型场景:
    • 关闭不需要的端口 (如禁止外网访问 3306 数据库端口).
    • 屏蔽来自特定恶意 IP 的攻击.
    • 限制内网用户只能访问特定的网站.

1.2.2. NAT 表 (地址转换表)

NAT 代表 Network Address Translation. 它不用于过滤数据包, 而是用于修改数据包的 源地址 (Source IP)目的地址 (Destination IP).

  • 核心功能: 网络地址转换和端口转发.
  • 支持的链: PREROUTING, POSTROUTING, OUTPUT
  • 典型场景:
    • SNAT (源地址转换): 局域网服务器通过一台有公网 IP 的网关上网.
    • DNAT (目的地址转换): 把公网 80 端口的请求映射到内网服务器的 8080 端口.

1.2.3. Mangle 表 (修改表)

这个表比较高级, 用于对数据包的头部信息进行特定修改.

  • 核心功能: 修改报文内容 (如 TTL, TOS, Mark).
  • 支持的链: PREROUTING, INPUT, FORWARD, OUTPUT, POSTROUTING.
  • 典型场景:
    • QoS (服务质量): 通过修改 TOS (Type of Service) 字段, 为视频流或语音流提供更高的优先级.
    • 策略路由: 给特定的数据包打上标记 (Mark), 配合 ip route 指令让这些包走特定的网卡或线路.
    • 修改 TTL: 隐藏路径信息或防止多跳路由.

1.2.4. Raw 表 (原始表)

这是优先级最高的表, 数据包进入内核后最先被 raw 表处理.

  • 核心功能: 决定数据包是否跳过 连接追踪 (Connection Tracking) 机制.
  • 支持的链: PREROUTING, OUTPUT.
  • 为什么要用它?: Linux 内核会跟踪每一个连接 (stateful inspection), 这需要消耗 CPU 和内存. 在高并发场景下 (比如大规模 DDoS 攻击), 连接追踪表可能会溢出导致宕机.
  • 典型场景:
    • 在高流量的 Web 服务器上, 对大量的不需要状态跟踪的数据包设置 NOTRACK, 从而极大地提高处理性能.

1.2.5. 表的执行优先级

当一个数据包到达某个链 (比如 PREROUTING) 时, 多个表可能会同时存在规则. 它们的执行顺序如下:

  1. Raw (最高优先级)
  2. Mangle
  3. Nat
  4. Filter (最低优先级)

表链对照表:

表名 主要功能 常用动作 (Targets) 包含的链
filter 过滤、安全控制 ACCEPT, DROP, REJECT INPUT, FORWARD, OUTPUT
nat 地址/端口转换 SNAT, DNAT, MASQUERADE PREROUTING, POSTROUTING, OUTPUT
mangle 修改包头、标记 MARK, TOS, TTL 全部五条链
raw 性能优化、脱离追踪 NOTRACK PREROUTING, OUTPUT

2. 常用指令参数

2.1. 管理规则 (Options)

  • -A <chain>: 在指定链的末尾追加规则 (Append).
  • -I <chain> [number]: 在指定链的开头或指定位置插入规则 (Insert).
  • -D <chain> <number>: 删除指定行号的规则 (Delete).
  • -R <chain> <number>: 替换指定位置的规则 (Replace).
  • -L: 列出所有规则 (List).
  • -F: 清空所有规则 (Flush).
  • -P: 设置链的默认策略 (Policy), 如 iptables -P INPUT DROP.

2.2. 查看技巧

  • -n: 以数字形式显示 IP 和端口, 避免 DNS 解析带来的延迟.
  • -v: 显示详细信息 (数据包计数器, 流量统计).
  • --line-numbers: 显示规则行号, 方便删除或修改.

3. 匹配条件 (Matches)

参数 含义 示例
-p 协议类型 -p tcp, -p udp, -p icmp
-s 源 IP 地址 -s 192.168.1.10
-d 目的 IP 地址 -d 8.8.8.8
–sport 源端口 --sport 443
–dport 目的端口 --dport 22
-i 进站网卡接口 -i eth0
-o 出站网卡接口 -o eth0
-m state 状态匹配 --state ESTABLISHED,RELATED

4. 动作处理 (Targets)

  • ACCEPT: 允许数据包通过.
  • DROP: 直接丢弃数据包, 不发送任何回应.
  • REJECT: 拒绝数据包, 并向源头发送一个错误消息 (如 ICMP Port Unreachable).
  • LOG: 在系统日志中记录匹配的数据包信息.
  • SNAT: 源地址转换, 用于内网访问外网.
  • DNAT: 目的地址转换, 用于外网访问内网服务器 (端口映射).
  • MASQUERADE: 动态 SNAT, 适用于拨号上网等动态 IP 场景.

5. 常见实战案例

标准命令构成公式: \(iptables + [-t\ 表名] + [管理选项] + [匹配条件] + [-j\ 动作]\)

5.1. 添加与插入实例 (Append & Insert)

通过 -A-I 来定义防火墙的基本准入规则.

  • 案例 1: 允许 SSH 远程管理 (常用端口)
    • 组合: -A (追加) + -p tcp --dport (匹配协议与目的端口) + -j ACCEPT (接收)
    • 指令: iptables -A INPUT -p tcp --dport 22 -j ACCEPT
  • 案例 2: 在首行插入紧急屏蔽规则 (优先级最高)
    • 组合: -I (插入第一行) + -s (匹配源 IP) + -j DROP (丢弃)
    • 指令: iptables -I INPUT 1 -s 192.168.1.100 -j DROP
  • 案例 3: 允许已建立的连接通行 (保证回程流量)
    • 组合: -A (追加) + -m state --state (匹配连接状态) + -j ACCEPT (接收)
    • 指令: iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT

5.2. 网络地址转换实例 (NAT 表)

涉及 -t nat 参数, 结合路由前后链进行地址转换.

  • 案例 4: 局域网共享上网 (源地址转换)
    • 组合: -t nat -A (操作 NAT 表) + -o (匹配出站网卡) + -j MASQUERADE (地址伪装)
    • 指令: iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
  • 案例 5: 外部访问映射到内网服务器 (目的地址转换)
    • 组合: -t nat -A (路由前) + -p tcp --dport (匹配外网访问端口) + -j DNAT --to-destination (重定向目的 IP)
    • 指令: iptables -t nat -A PREROUTING -p tcp --dport 80 -j DNAT --to-destination 192.168.1.50:80

5.3. 删除与修改实例 (Delete & Replace)

用于清理或更正现有的规则.

  • 案例 6: 按行号删除指定规则
    • 组合: -D (删除) + [链名] + [行号]
    • 指令: iptables -D INPUT 2
  • 案例 7: 修改现有的规则内容
    • 组合: -R (替换) + [行号] + [新匹配条件] + -j REJECT (改为拒绝并回应)
    • 指令: iptables -R INPUT 3 -s 10.0.0.1 -j REJECT

5.4. 查看技巧与策略管理 (List & Policy)

在配置完成后, 用于检查和设置全局防御基调.

  • 案例 8: 数字化详细列出所有规则 (排查首选)
    • 组合: -L (列出) + -n (数字显示) + -v (详细统计) + --line-numbers (显示行号)
    • 指令: iptables -L -n -v --line-numbers
  • 案例 9: 设置默认拒绝策略 (白名单模式)
    • 组合: -P (设置默认策略) + [链名] + DROP (默认丢弃)
    • 指令: iptables -P INPUT DROP
  • 案例 10: 清空特定表的所有规则
    • 组合: -t nat (指定表) + -F (清空)
    • 指令: iptables -t nat -F

6. 注意事项

  1. 即时生效: 所有的 iptables 指令都是立即生效的.
  2. 顺序敏感: 匹配规则是从上往下执行的, 一旦命中则不再执行后续规则 (LOG 除外). 所以 -I (插入到首行) 和 -A (追加到末尾) 效果完全不同.
  3. 持久化: 重启系统后规则会丢失. 在 Ubuntu 上推荐使用 iptables-persistent, 在 CentOS 上可以使用 iptables-save > /etc/sysconfig/iptables.
本文由作者按照 CC BY 4.0 进行授权