Linux操作系统-防火墙
Linux 防火墙实战:iptables 与 firewalld 全面解析
引言
“我的服务器怎么访问不了了?!”
相信不少运维新手都经历过这样的时刻——应用服务正常运行,端口也监听着,但浏览器就是打不开。折腾半天,最后试探性地执行了一条命令:
systemctl stop firewalld
网页瞬间恢复访问。你顿时明白:原来是防火墙在“搞鬼”。
在 Linux 系统中,防火墙是保障网络安全的第一道防线。而说到 Linux 防火墙,绕不开两个名字:iptables 和 firewalld。它们到底是什么关系?有什么区别?日常工作中该用哪个?今天这篇文章就带你彻底搞明白。
一、Netfilter:一切防火墙的“地基”
在讲 iptables 和 firewalld 之前,有必要先认识一下 Netfilter。
Netfilter 是 Linux 内核中的一个框架,它在网络协议栈的关键路径上设置了一系列“挂载点”(钩子函数)。当数据包经过这些挂载点时,内核会依次调用挂载点上所有的钩子函数,直到数据包的处理结果被明确为接受、拒绝或丢弃。
iptables 和 firewalld 都不是真正的防火墙本身,它们只是用来定义防火墙规则的管理工具。真正执行这些规则的是内核中的 Netfilter 框架。你可以这样理解:
- Netfilter = 内核里的“执行引擎”
- iptables / firewalld = 用户用来下命令的“控制台”
明确了这一点,后面的内容就更好理解了。
二、iptables:Linux 防火墙的“元老”
2.1 核心架构:表、链、规则
iptables 采用 “表(Table)-链(Chain)-规则(Rule)” 三级结构来管理网络流量。
四表(Table) :
| 表名 | 作用 |
|---|---|
filter |
默认表,用于数据包过滤(ACCEPT / DROP / REJECT) |
nat |
网络地址转换(SNAT / DNAT / MASQUERADE),用于端口转发或共享上网 |
mangle |
修改数据包头部(如 TTL、TOS),用于 QoS 或流量标记 |
raw |
绕过 Netfilter 的连接跟踪,提升性能 |
五链(Chain):
| 链名 | 作用 |
|---|---|
PREROUTING |
数据包进入路由决策之前 |
INPUT |
过滤发往本机的流量 |
FORWARD |
过滤经过本机转发的流量(路由器场景) |
OUTPUT |
过滤本机发出的流量 |
POSTROUTING |
数据包离开网卡之前 |
💡 规则优先级:raw > mangle > nat > filter
Iptables的4表5链:
Iptables数据包转发流程:
数据包先经过PREOUTING,由该链确定数据包走向:
- 目的地址是本地,则发送到INPUT,让INPUT决定是否接收下来送到用户空间,流程为①—>②;
- 若满足PREROUTING的nat表上的转发规则,则发送给FORWARD,然后再经过POSTROUTING发送出去,流程为:①—>③—>④—>⑥;
- 主机发送数据包时,流程则是⑤—>⑥;
- 其中PREROUTING和POSTROUTING指的是数据包的流向,如上图所示POSTROUTING指的是发往服务器发出的数据包,而PREROUTING指的是来自服务器外部的数据包。

2.2 iptable命令用法
iptables的用法可以参考下图:
table:
- -t 使用的表,包括filter、nat、mangle、raw,默认不指明是filter.
command:
-A 顺序添加,添加一条新规则,添加到末尾
-I 插入,插入一条新规则 -I 后面加一数字表示插入到哪行
-R 修改, 删除一条新规则 -D 后面加一数字表示删除哪行
-D 删除,删除一条新规则 -D 后面加一数字表示删除哪行
-N 新建一个链
-X 删除一个自定义链,删除之前要保证次链是空的,而且没有被引用
-L 查看(1.iptables -L -n 以数字的方式显示 2. iptables -L -v显示详细信息 3. iptables -L -x 显示精确信息)
-E 重命名链
-F 清空链中的所有规则
-Z 清除链中使用的规则
-P 设置默认规则
match:
隐含匹配:
-p tcp udp icmp
--sport指定源端口
--dport指定目标端
-s 源地址
-d 目的地址
-i 数据包进入的网卡
-o 数据包出口的网卡
扩展匹配:
-m state --state 匹配状态的
-m mutiport --source-port 端口匹配 ,指定一组端口
-m limit --limit 3/minute 每三分种一次
-m limit --limit-burst 5 只匹配5个数据包
-m string --string --algo bm|kmp --string"xxxx" 匹配字符串
-mtime--timestart 8:00 --timestop 12:00 表示从哪个时间到哪个时间段
-mtime--days 表示那天
-m mac --mac-source xx:xx:xx:xx:xx:xx 匹配源MAC地址
-m layer7 --l7proto qq 表示匹配腾讯qq的 当然也支持很多协议,这个默认是没有的,需要我们给内核打补丁并重新编译内核及iptables才可以使用 -m layer7 这个显示扩展匹配
动作:
DROP 直接丢掉
ACCEPT 允许通过
REJECT 丢掉,但是回复信息
-j LOG --log-prefix"说明信息,自己随便定义" ,记录日志
SNAT 源地址转换
DNAT 目标地址转换
REDIRECT 重定向
MASQUERAED 地址伪装
2.3 iptables常用命令
iptables 的命令语法虽然有一定学习曲线,但掌握核心的几个命令就足够应对日常工作了。
查看规则:
# 查看所有链的规则(默认 filter 表)
iptables -L
# 查看特定链的规则,带行号
iptables -L INPUT -n --line-numbers
# 查看 nat 表的规则
iptables -t nat -L
添加规则:
# 在 INPUT 链末尾追加规则:允许 SSH(端口22)
iptables -A INPUT -p tcp --dport 22 -j ACCEPT
# 在 INPUT 链首位插入规则:禁止 ICMP(ping)
iptables -I INPUT 1 -p icmp -j DROP
# 允许来自特定 IP 的访问
iptables -A INPUT -s 192.168.1.100 -j ACCEPT
删除规则:
# 按行号删除(先查看行号)
iptables -D INPUT 1
# 按内容删除
iptables -D INPUT -p tcp --dport 80 -j ACCEPT
设置默认策略(白名单模式):
# 默认拒绝所有入站流量
iptables -P INPUT DROP
# 再逐条开放必要服务
iptables -A INPUT -p tcp --dport 80 -j ACCEPT
iptables -A INPUT -p tcp --dport 443 -j ACCEPT
保存与恢复规则:
# 保存当前规则
iptables-save > /etc/sysconfig/iptables
# 恢复规则
iptables-restore < /etc/sysconfig/iptables
2.3 高级应用:NAT 与端口转发
SNAT(源地址转换) :让内网主机通过防火墙访问外网:
iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
DNAT(目的地址转换) :将外部请求转发到内网服务器:
iptables -t nat -A PREROUTING -p tcp --dport 80 -j DNAT --to-destination 192.168.1.100:80
2.4 连接状态跟踪:提升性能的关键
利用 conntrack 模块,可以避免对已建立的连接重复匹配规则:
# 允许已建立的连接和相关连接通过
iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT
# 仅允许新的 SSH 连接
iptables -A INPUT -m conntrack --ctstate NEW -p tcp --dport 22 -j ACCEPT
这样做的好处是:一旦 SSH 连接建立成功,后续的数据包直接放行,不再逐条匹配规则,大幅提升效率。
三、firewalld:更友好的“动态管家”
3.1 设计理念:区域 + 服务
firewalld 是建立在 iptables 之上的动态防火墙管理工具,提供了更高层次的抽象。它从 RHEL/CentOS 7 开始成为默认防火墙。
firewalld 的核心优势在于 支持运行时动态修改规则,无需重启防火墙服务,不会中断现有连接。
核心概念:
| 概念 | 说明 |
|---|---|
| 区域(Zone) | 按信任级别划分的网络环境,如 public(默认)、trusted(完全信任)、block(拒绝所有)等 |
| 服务(Service) | 预定义的端口和协议组合,如 http、ssh、mysql |
| 源地址(Source) | 基于 IP 或网段绑定特定区域 |
| 富规则(Rich Rule) | 支持复杂条件(IP、端口、协议、时间等)的自定义规则 |
3.2 常用命令
firewalld 的核心管理工具是 firewall-cmd。
状态与区域管理:
# 查看防火墙状态
firewall-cmd --state
# 查看所有可用区域
firewall-cmd --get-zones
# 查看默认区域
firewall-cmd --get-default-zone
# 查看指定区域的详情
firewall-cmd --zone=public --list-all
服务与端口管理:
# 添加服务到默认区域(永久生效需加 --permanent)
firewall-cmd --add-service=http --permanent
firewall-cmd --add-service=https --permanent
# 开放端口
firewall-cmd --add-port=3306/tcp --permanent
# 重新加载配置使永久规则生效
firewall-cmd --reload
# 查看已开放的服务和端口
firewall-cmd --list-services
firewall-cmd --list-ports
💡 关键区别:不加
--permanent的修改只对当前运行生效,重启后丢失;加了--permanent需要执行--reload才能生效。
源地址控制:
# 允许特定子网访问
firewall-cmd --zone=public --add-source=192.168.1.0/24 --add-service=ssh --permanent
# 拒绝特定 IP
firewall-cmd --zone=public --add-rich-rule='rule family="ipv4" source address="10.0.0.5" reject' --permanent
3.3 自定义服务
如果应用使用非标准端口,可以创建自定义服务文件:
<!-- /etc/firewalld/services/custom_http.xml -->
<?xml version="1.0" encoding="utf-8"?>
<service>
<short>Custom HTTP</short>
<description>Custom HTTP service on port 8080</description>
<port protocol="tcp" port="8080"/>
</service>
firewall-cmd --reload
firewall-cmd --add-service=custom_http --permanent
3.4 富规则与端口转发
富规则支持更复杂的条件控制:
# 允许特定 IP 访问特定端口,仅在工作时间
firewall-cmd --add-rich-rule='rule family="ipv4" source address="192.168.1.100" port port="8080" protocol="tcp" accept' --permanent
端口转发:
# 开启伪装(端口转发的前提)
firewall-cmd --add-masquerade --permanent
# 将本机 8080 端口转发到 80 端口
firewall-cmd --add-forward-port=port=8080:proto=tcp:toport=80 --permanent
四、iptables vs firewalld:一张表看懂区别
| 对比维度 | iptables | firewalld |
|---|---|---|
| 定位 | 底层、精细控制的防火墙工具 | 高层、易用的动态管理工具 |
| 配置模型 | 基于“链+规则”的底层模型 | 基于“区域+服务”的高层抽象 |
| 规则更新 | 修改后需全部刷新,可能中断连接 | 动态更新,不中断现有连接 |
| 学习曲线 | 较陡峭,需理解表、链、匹配条件 | 更友好,通过“区域”概念简化配置 |
| 配置文件 | /etc/sysconfig/iptables |
/usr/lib/firewalld/ 和 /etc/firewalld/ |
| 默认策略 | 默认允许所有,需要拒绝的才限制 | 默认拒绝所有传入流量 |
| 图形界面 | 无 | 有 firewall-config |
| 后端支持 | 直接操作 netfilter | 可使用 iptables 或 nftables 后端 |
| 适用场景 | 精细控制、复杂规则、脚本化部署 | 快速配置、日常运维、云环境 |
一句话总结:iptables 是“乐高”——什么都能搭,但需要自己动手;firewalld 是“精装房”——拎包入住,省心省力。
五、实战:两个工具解决同一个需求
假设我们要完成一个常见任务:开放 Web 服务(80 和 443 端口),并允许 SSH 管理(22 端口),其余入站流量全部拒绝。
用 iptables 实现
# 1. 设置默认策略:拒绝所有入站
iptables -P INPUT DROP
iptables -P FORWARD DROP
# 2. 允许已建立的连接
iptables -A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT
# 3. 开放必要端口
iptables -A INPUT -p tcp --dport 22 -j ACCEPT
iptables -A INPUT -p tcp --dport 80 -j ACCEPT
iptables -A INPUT -p tcp --dport 443 -j ACCEPT
# 4. 允许本地回环
iptables -A INPUT -i lo -j ACCEPT
# 5. 保存规则
iptables-save > /etc/sysconfig/iptables
用 firewalld 实现
# 1. 确保默认区域是 public(默认拒绝入站)
firewall-cmd --get-default-zone # 应该是 public
# 2. 添加服务
firewall-cmd --add-service=ssh --permanent
firewall-cmd --add-service=http --permanent
firewall-cmd --add-service=https --permanent
# 3. 重新加载生效
firewall-cmd --reload
# 4. 验证
firewall-cmd --list-services
对比一下,firewalld 只需要 4 条命令,而 iptables 需要 6 条命令加一个保存操作。对于日常运维场景,firewalld 的简洁性显而易见。
六、常见问题与排错指南
Q1:firewalld 和 iptables 能同时用吗?
不建议同时启用。两者都操作同一套 netfilter 规则,同时启用可能导致规则冲突。如果启用了 firewalld,建议禁用 iptables 服务:
systemctl stop iptables
systemctl disable iptables
systemctl enable --now firewalld
Q2:修改了 firewalld 规则为什么不生效?
检查两个地方:
- 是否加了
--permanent但没有执行--reload - 是否修改了正确的区域(
--zone参数)
Q3:iptables 规则重启后消失了?
iptables 规则默认是临时的,需要手动保存:
# CentOS/RHEL
service iptables save
# 通用方法
iptables-save > /etc/sysconfig/iptables
Q4:服务启动失败,怎么排查?
服务启动失败可以参考如下步骤排查:
# 1. 查看防火墙状态
systemctl status firewalld
firewall-cmd --state
# 2. 查看当前规则
firewall-cmd --list-all
iptables -L -n -v
# 3. 临时关闭防火墙测试(仅用于排查)
systemctl stop firewalld
# 如果关闭后服务正常,说明是防火墙规则问题
# 4. 查看selinux状态
getenforce
Q5:找不到iptables服务,报错Unit iptables.service could not be found.
Centos 7以后默认没有安装iptables服务,需要通过yum install -y iptables-services之后就可以通过systemctl管理iptables服务了
七、iptables和firewalld到底应该选哪一个?
什么时候用 firewalld?
- 大多数现代 Linux 系统(CentOS 7+、RHEL、Fedora)
- 日常服务器运维、快速配置端口和服务
- 需要动态调整防火墙策略的场景(如云环境)
- 运维新手或不想花太多时间研究防火墙细节的人
什么时候用 iptables?
- 需要极致精细的流量控制
- 复杂的 NAT 和路由策略
- 嵌入式系统或资源受限的环境
- 维护已有的大量 iptables 脚本
📌 一句话建议:对于绝大多数新建 Linux 服务器,优先使用 firewalld;只有在 firewalld 无法满足的复杂场景下,才考虑降级到 iptables。对于一些较老的服务器iptables用得较多,一些比较资深的运维人员也比较习惯使用iptables作为linux的防火墙。
总结
从 iptables 到 firewalld,Linux 防火墙管理走过了一条从“底层精细”到“高层易用”的演进之路。两者都基于 Netfilter 框架,但设计理念截然不同:
- iptables 是“工匠型”工具——强大、灵活,但需要你亲手搭建每一块砖。
- firewalld 是“管家型”工具——开箱即用,日常运维省心省力。
记住三句话:
- Netfilter 是内核的执行引擎,iptables 和 firewalld 只是管理工具,不要搞混。
- 默认策略决定安全基调:iptables 默认允许,firewalld 默认拒绝——理解这一点,很多问题迎刃而解。
- 生产环境优先用 firewalld,复杂场景再用 iptables 补充。
防火墙是服务器的“守门人”,配置得当能挡住绝大部分恶意流量,配置失误也可能把自己挡在门外。希望这篇文章能帮你建立起清晰的防火墙管理思路,下次再遇到“服务访问不了”的问题,能快速定位是防火墙在“搞鬼”,还是真的程序出了 bug。
如果你有任何问题或经验分享,欢迎在评论区留言讨论!
openEuler 是由开放原子开源基金会孵化的全场景开源操作系统项目,面向数字基础设施四大核心场景(服务器、云计算、边缘计算、嵌入式),全面支持 ARM、x86、RISC-V、loongArch、PowerPC、SW-64 等多样性计算架构
更多推荐
所有评论(0)