导读:全面掌握 iptables:从基础到实践
在 Linux 系统中,iptables
是一个非常强大的工具,它不仅是系统管理员用来构建和管理网络防火墙的首选工具,而且也是一个功能丰富的网络流量处理系统。无论是进行包过滤、监控网络流量、还是实现复杂的网络地址转换 (NAT),iptables
都能提供灵活的解决方案。本文将带你深入理解 iptables
的组成结构,掌握其常用命令,并通过具体的使用场景展示如何在实际中应用这些知识。
目录
iptables
是 Linux 操作系统中的一个非常强大的防火墙工具,它使用表格来组织防火墙规则,这些表格中的规则用于决定如何处理穿过防火墙的数据包。iptables
基于 Netfilter,Netfilter 是 Linux 内核的一个部分,负责处理通过网络栈的所有数据包。通过使用 iptables
,系统管理员可以定义规则,这些规则决定了如何处理进入、穿过和离开网络的数据包。
一、iptables
的主要组成
表 (Tables)
iptables
的规则分布在不同的“表”中,这些表是处理特定类型数据包的集合。每个表包含一个或多个“链”,这些链定义了数据包流经网络栈的不同点在何处应用这些规则。
filter
表- 用途: 主要用于决定数据包的基本处理,如是否允许数据包通过。
- 包含的链:
INPUT
: 处理进入本机的数据包。FORWARD
: 处理经过本机路由到其他网络的数据包。OUTPUT
: 处理由本机产生的数据包。
nat
表- 用途: 用于网络地址转换(NAT),包括源地址和目标地址的转换,主要用于路由设备。
- 包含的链:
PREROUTING
: 用于目标地址转换(DNAT),处理进入网络接口的数据包。POSTROUTING
: 用于源地址转换(SNAT),处理即将离开网络接口的数据包。OUTPUT
: 对于生成自本地进程的数据包,处理其目标地址转换。
mangle
表- 用途: 用于修改数据包的服务类型(TOS)字段或其他 IP 头信息,主要用于特殊的路由标记。
- 包含的链:
PREROUTING
: 修改进入网络接口的数据包。INPUT
: 修改到达本机的数据包。FORWARD
: 修改经过本机的数据包。OUTPUT
: 修改本机产生的数据包。POSTROUTING
: 修改即将离开本机的数据包。
raw
表- 用途: 主要用于配置免除连接跟踪的数据包,可以用来提高性能。
- 包含的链:
PREROUTING
: 设置进入网络接口前的数据包是否避开状态跟踪。OUTPUT
: 设置由本机产生的数据包是否避开状态跟踪。
security
表- 用途: 用于设置强制访问控制网络规则,通常与 SELinux 安全策略配合使用。
- 包含的链:
INPUT
: 设置进入本机的数据包的安全标记。FORWARD
: 设置经过本机的数据包的安全标记。OUTPUT
: 设置本机产生的数据包的安全标记。
链 (Chains)
表中的每个链代表数据包处理的一个阶段。预定义的链有:
PREROUTING
: 用于处理进入网络接口的数据包,主要用于nat
和mangle
表。INPUT
: 处理到达本机的数据包,用于filter
,mangle
, 和security
表。FORWARD
: 处理经过本机路由到其他网络的数据包,用于filter
,mangle
, 和security
表。OUTPUT
: 处理本机产生的数据包,用于filter
,nat
,mangle
,raw
, 和security
表。POSTROUTING
: 处理即将离开网络接口的数据包,用于nat
和mangle
表。
规则 (Rules)
规则定义了对特定条件下的数据包应该执行的操作。每条规则都关联到一个链,规则包含两个主要部分:
匹配条件: 定义了哪些数据包会被规则匹配。匹配条件可以包括多种属性:
- 源和目标 IP 地址 (
-s
,-d
) - 源和目标端口 (
--sport
,--dport
) - 协议类型 (
-p
), 如 TCP (tcp
), UDP (udp
), ICMP (icmp
) - 网络接口 (
-i
,-o
) - 更多复杂匹配,如连接状态 (
-m state --state
), 包大小 (-m length --length
), 时间段 (-m time --timestart
)
- 源和目标 IP 地址 (
目标 (Targets): 当规则匹配到一个数据包时,定义了应采取的行动。常见的内置目标有:
ACCEPT
: 允许数据包通过。DROP
: 静默丢弃数据包,不给发送方任何响应。REJECT
: 拒绝数据包,并向发送方发送一个错误响应。LOG
: 记录数据包的信息,然后继续处理该数据包。MASQUERADE
: 用于动态 NAT,隐藏数据包的源 IP。REDIRECT
: 修改数据包的目标 IP/端口为本机,用于本地端口重定向。
用户定义的链
用户可以定义自己的链来组织复杂的规则集。这允许更灵活的管理,例如创建一个专用链处理特定类型的流量,然后在预定义链中调用这个用户链。
二、常用 iptables
命令
iptables
是一个功能强大的工具,用于在 Linux 上管理网络包过滤和 NAT 规则。以下是详细解释 iptables
的常用命令和参数,帮助你更好地理解如何使用这个工具。
基本 iptables
命令格式
iptables [option] [chain] [matching criteria] [action]
- [option]: 指定命令的选项,如
-A
(添加)、-D
(删除)、-L
(列出) 等。 - [chain]: 指定规则应用于哪个链,如
INPUT
,FORWARD
,OUTPUT
等。 - [matching criteria]: 指定匹配数据包的条件,如
-p tcp
(匹配 TCP 协议的数据包)。 - [action]: 指定当匹配到数据包时执行的动作,如
-j ACCEPT
(接受数据包)。
查看规则
查看所有规则
iptables -L -n -v
-L
: 列出所有规则。-v
: 显示详细信息,包括通过每条规则的数据包和字节数。-n
: 使用数字显示 IP 地址和端口,不进行域名解析,以加快显示速度。
查看特定表的规则
iptables -t nat -L
-t nat
: 指定要查看的表,这里是nat
表。
添加规则
允许进入的 SSH 连接
iptables -A INPUT -p tcp --dport 22 -j ACCEPT
-A INPUT
: 在INPUT
链末尾添加规则。-p tcp
: 匹配 TCP 协议的数据包。--dport 22
: 匹配目的端口为 22 的数据包。-j ACCEPT
: 对匹配的数据包执行ACCEPT
动作。
允许出去的 HTTP 连接
iptables -A OUTPUT -p tcp --dport 80 -j ACCEPT
-A OUTPUT
: 在OUTPUT
链末尾添加规则。-p tcp
: 匹配 TCP 协议的数据包。--dport 80
: 匹配目的端口为 80 的数据包。
删除规则
删除特定的规则
iptables -D INPUT -p tcp --dport 22 -j ACCEPT
-D INPUT
: 从INPUT
链删除规则。- 其余参数定义了要删除的规则的匹配条件和动作。
按编号删除规则
首先,使用
-L --line-numbers
查看规则及其编号:iptables -L INPUT -n --line-numbers
然后,根据编号删除规则:
iptables -D INPUT 1
- 删除
INPUT
链中编号为 1 的规则。
- 删除
修改规则
使用编号修改规则
iptables -R INPUT 1 -p tcp --dport 22 -j DROP
-R INPUT 1
: 在INPUT
链中替换编号为 1 的规则。-p tcp --dport 22
: 匹配 TCP 协议且目的端口为 22 的数据包。-j DROP
: 新的动作是丢弃数据包。
插入规则
在链的特定位置插入规则
iptables -I INPUT 1 -p tcp --dport 80 -j ACCEPT
-I INPUT 1
: 在INPUT
链的第 1 位置插入规则。-p tcp --dport 80
: 匹配 TCP 协议且目的端口为 80 的数据包。
设置默认策略
设置链的默认策略
iptables -P INPUT DROP iptables -P FORWARD DROP iptables -P OUTPUT ACCEPT
-P INPUT DROP
: 设置INPUT
链的默认策略为DROP
。-P FORWARD DROP
: 设置FORWARD
链的默认策略为DROP
。-P OUTPUT ACCEPT
: 设置OUTPUT
链的默认策略为ACCEPT
。
保存和恢复规则
保存当前的规则
iptables-save > /etc/iptables.rules
iptables-save
: 输出当前的iptables
规则。- 重定向到
/etc/iptables.rules
文件中保存。
从文件恢复规则
iptables-restore < /etc/iptables.rules
iptables-restore
: 从输入读取规则并应用。/etc/iptables.rules
: 包含要恢复的规则。
清空规则
清空所有规则
iptables -F
-F
: 清空(Flush)所有链的所有规则。
清空特定表的规则
iptables -t nat -F
-t nat
: 指定清空nat
表的规则。
删除所有非默认链
iptables -X
-X
: 删除所有用户定义的链。
端口重定向和 NAT
将外部端口 80 重定向到本地的 8080 端口
iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-port 8080
-t nat
: 在nat
表操作。-A PREROUTING
: 在PREROUTING
链末尾添加规则。-p tcp --dport 80
: 匹配目的端口为 80 的 TCP 数据包。-j REDIRECT --to-port 8080
: 重定向这些数据包到本机的 8080 端口。
源 NAT (SNAT): 修改源 IP 地址
iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
-A POSTROUTING
: 在POSTROUTING
链末尾添加规则。-o eth0
: 匹配从eth0
网络接口发出的数据包。-j MASQUERADE
: 对这些数据包执行地址伪装,常用于动态 IP 地址。
目标 NAT (DNAT): 修改目标 IP 地址
iptables -t nat -A PREROUTING -p tcp --dport 8080 -j DNAT --to-destination 192.168.1.10:80
-A PREROUTING
: 在PREROUTING
链末尾添加规则。-p tcp --dport 8080
: 匹配目的端口为 8080 的 TCP 数据包。-j DNAT --to-destination 192.168.1.10:80
: 修改数据包的目标 IP 和端口。
高级匹配和限速
防止 SSH 爆破攻击
为了防止 SSH 爆破,我们可以使用
recent
模块来跟踪来自同一 IP 地址的连接尝试。如果在指定时间内超过了特定次数的连接尝试,则暂时拒绝来自该 IP 的连接。iptables -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --set iptables -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --update --seconds 60 --hitcount 10 -j DROP
-m state --state NEW
: 只匹配新建连接。-m recent --set
: 对匹配的每个新连接,记录其信息。-m recent --update
: 更新最近的信息,并检查条件。--seconds 60
: 指定时间窗口为 60 秒。--hitcount 10
: 如果在 60 秒内同一 IP 尝试新建连接超过 10 次,则匹配此规则。-j DROP
: 拒绝这些匹配的数据包。
日志记录
iptables
支持将匹配的数据包信息记录到系统日志中,这对于调试和安全监控非常有用。
记录被拒绝的数据包信息
iptables -A INPUT -j LOG --log-prefix "IPTables-Dropped: " --log-level 4
-j LOG
: 使用 LOG 目标记录数据包信息。--log-prefix "IPTables-Dropped: "
: 指定日志记录的前缀,便于在日志文件中搜索。--log-level 4
: 指定日志的级别(4 表示 warning 级别)。
状态检查
利用 state
模块,可以匹配数据包的连接跟踪状态,这是构建复杂防火墙规则的基础。
允许基于状态的数据包传输
iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT iptables -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
-m state --state ESTABLISHED,RELATED
: 匹配状态为ESTABLISHED
或RELATED
的数据包。ESTABLISHED
: 表示数据包是属于已经建立的连接。RELATED
: 表示数据包是与现有的连接相关的(例如,FTP 数据连接)。
时间条件匹配
使用 time
模块可以基于时间条件匹配数据包,这可以用于实现基于时间的访问控制策略。
只在工作时间允许 HTTP 访问
iptables -A INPUT -p tcp --dport 80 -m time --timestart 09:00 --timestop 17:00 --weekdays Mon,Tue,Wed,Thu,Fri -j ACCEPT
-m time
: 使用时间模块。--timestart 09:00 --timestop 17:00
: 指定允许匹配的开始和结束时间。--weekdays Mon,Tue,Wed,Thu,Fri
: 指定允许匹配的星期几。
接口匹配
可以根据数据包使用的网络接口进行匹配。
允许来自特定接口的数据包
iptables -A INPUT -i eth0 -p tcp --dport 80 -j ACCEPT
-i eth0
: 只匹配通过eth0
网络接口进入的数据包。-p tcp --dport 80
: 匹配目的端口为 80 的 TCP 数据包。
用户自定义链
用户可以定义自己的链来组织规则,这可以使规则集更加结构化和模块化。
定义和使用自定义链
iptables -N LOGGING iptables -A INPUT -j LOGGING iptables -A LOGGING -m limit --limit 2/min -j LOG --log-prefix "Input-Dropped: " iptables -A LOGGING -j DROP
-N LOGGING
: 创建一个名为LOGGING
的新链。-A LOGGING -m limit --limit 2/min -j LOG
: 在LOGGING
链中,使用limit
模块限制日志记录的速率,防止日志文件快速增长。-j DROP
: 在LOGGING
链的最后,丢弃所有数据包。
保存和加载规则
iptables
规则默认在系统重启后不会保存。你需要手动保存规则,并在系统启动时加载它们。
保存规则到文件
iptables-save > /etc/iptables.rules
iptables-save
: 输出当前的所有iptables
规则。>
: 重定向输出到文件/etc/iptables.rules
。
加载规则从文件
iptables-restore < /etc/iptables.rules
iptables-restore
: 从给定的输入加载iptables
规则。< /etc/iptables.rules
: 从文件/etc/iptables.rules
读取规则。
清空和重置
有时你可能需要清空所有规则,重置 iptables
到初始状态。
清空所有规则和自定义链
iptables -F iptables -X
-F
: 清空所有链的所有规则。-X
: 删除所有用户定义的链。
三、使用场景举例
使用 iptables
的场景非常多样,覆盖从简单的主机防火墙到复杂的网络路由和 NAT 配置。下面是一些具体的使用场景,展示如何利用 iptables
解决实际问题。
1. 基本的主机防护
在这个场景中,我们利用 iptables
设置基本的网络访问控制,以保护主机不受未授权访问。
允许特定的服务访问
假设你想在一台服务器上开放 SSH (端口 22) 和 HTTP (端口 80) 服务,同时拒绝所有其他未经授权的入站连接。
# 设置默认策略 iptables -P INPUT DROP iptables -P FORWARD DROP iptables -P OUTPUT ACCEPT # 允许本地回环接口 iptables -A INPUT -i lo -j ACCEPT iptables -A OUTPUT -o lo -j ACCEPT # 允许已建立的和相关的连接 iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT # 允许 SSH iptables -A INPUT -p tcp --dport 22 -j ACCEPT # 允许 HTTP iptables -A INPUT -p tcp --dport 80 -j ACCEPT # Optional: 允许 HTTPS iptables -A INPUT -p tcp --dport 443 -j ACCEPT
2. 防止 DDoS 攻击
使用 iptables
限制单个源 IP 的连接频率,以防止简单的 DDoS 攻击或 SSH 爆破。
限制 SSH 连接尝试
# 允许每个 IP 每分钟最多新建 3 个 SSH 连接 iptables -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --set iptables -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --update --seconds 60 --hitcount 4 -j DROP
这种设置能够有效减少暴力破解 SSH 密码的风险。
3. 端口转发
在某些情况下,你可能需要将到达某个端口的流量重定向到另一个端口上,例如将 80 端口的 HTTP 流量转发到 8080 端口。
将 80 端口转发到 8080 端口
# 在 nat 表的 PREROUTING 链上添加规则 iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-port 8080
这个操作常用于服务器上运行的 Web 应用程序,该程序绑定于非标准端口,而你希望通过标准端口访问。
4. 网络地址转换 (NAT)
在家庭或小型办公室网络中,经常需要设置 NAT 来共享访问互联网的路径。以下是一个简单的源 NAT(SNAT)配置的例子。
共享互联网访问
假设 eth1
是内部网络接口,eth0
是连接到互联网的接口。
# 启用 IP 转发 echo 1 > /proc/sys/net/ipv4/ip_forward # 设置 MASQUERADE iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE # 允许内部网络访问外部 iptables -A FORWARD -i eth1 -o eth0 -j ACCEPT # 允许已建立的连接回流 iptables -A FORWARD -i eth0 -o eth1 -m state --state ESTABLISHED,RELATED -j ACCEPT
这个配置允许内部网络通过 eth0
接口访问外部网络。
5. 日志和审计
记录某些类型的网络活动对于调试和安全监控都是非常有用的。
记录被拒绝的包
# 记录被拒绝的入站连接尝试 iptables -A INPUT -j LOG --log-prefix "IPTables-Input-Denied: " --log-level 4 # 记录被拒绘的转发连接尝试 iptables -A FORWARD -j LOG --log-prefix "IPTables-Forward-Denied: " --log-level 4
这些规则会将所有被 INPUT
和 FORWARD
链拒绝的尝试记录到系统日志中。
6. 使用时间条件控制访问
在某些环境中,你可能希望基于时间来控制网络访问。
在工作时间外允许 SSH 访问
# 工作时间外允许 SSH iptables -A INPUT -p tcp --dport 22 -m time --timestart 18:00 --timestop 09:00 -j ACCEPT
这条规则允许在晚上 6:00 到早上 9:00 之间进行 SSH 访问。
7. 防火墙绕过
在某些情况下,你可能需要临时开放或关闭防火墙的某些规则,而不是永久修改配置。
临时开放所有访问
如果需要临时允许所有流量(例如,进行某些特殊操作),可以设置:
iptables -P INPUT ACCEPT iptables -P FORWARD ACCEPT iptables -P OUTPUT ACCEPT # 清空所有规则 iptables -F
然后,在操作完成后,恢复原来的规则。
8. 防止 ICMP 泛洪攻击
ICMP 泛洪是一种常见的拒绝服务攻击方法。
限制 ICMP 回显请求
# 限制 ICMP echo-request 消息 iptables -A INPUT -p icmp --icmp-type echo-request -m limit --limit 1/s -j ACCEPT iptables -A INPUT -p icmp --icmp-type echo-request -j DROP
这些规则限制了每秒处理的 ICMP echo 请求(ping 请求)的数量,从而减轻了泛洪的影响。
9. 多网卡策略路由
在拥有多个网络接口的服务器上,你可能需要根据数据包的来源或目的地来选择不同的路由。
根据源 IP 使用特定的网络接口
# 对于从特定源 IP 发出的数据包,使用特定接口 iptables -t nat -A POSTROUTING -s 192.168.100.0/24 -o eth1 -j MASQUERADE
这个规则设置了源 NAT,允许从 192.168.100.0/24
网段出来的数据包通过 eth1
接口发送。
10. 容器和虚拟化环境
在使用 Docker 或其他容器技术时,经常需要配置 iptables
来管理和隔离网络流量。
允许特定容器访问外部网络
# 假设容器的虚拟网络接口是 veth1234 iptables -t nat -A POSTROUTING -s 172.17.0.2/32 -o eth0 -j MASQUERADE
这条规则允许 IP 地址为 172.17.0.2
的容器通过 eth0
接口访问外部网络。
通过这些场景,你可以看到 iptables
的多样性和强大功能,它能够满足从简单到复杂的多种网络需求。