先说结论:
iptables, firewalld, 和 nftables 都是用于在 Linux 系统中实施网络防火墙的工具,但是它们在架构、功能和使用方式上有明显的差异。
iptables 适用于需要对防火墙规则有精细控制和理解的场景。
firewalld 提供了一个更现代、易于管理和维护的防火墙配置方案,尤其适用于服务和端口动态变化的环境。
nftables 是面向未来的网络过滤框架,提供更高的效率和灵活性,以及更简单的配置语法。
目标一致:所有三个工具都旨在控制进出 Linux 系统的网络流量,提供安全防护。
依赖内核:它们都依赖于 Linux 内核的网络过滤框架,如 netfilter 或 nftables。
规则执行:最终,所有这些工具都会影响内核如何处理网络数据包,决定数据包的接受或拒绝。
历史最悠久:iptables 是最古老的防火墙工具之一,用于配置基于 netfilter 框架的包过滤规则。
静态规则集:一旦配置好规则,就需要重新加载规则链来应用任何更改。
复杂性:使用 iptables 需要对网络协议和防火墙概念有深入的理解。
规则管理:规则直接写入内核,没有独立的守护进程来管理规则。
现代替代:firewalld 是为了克服 iptables 的一些限制而设计的,它是一个运行在用户空间的守护进程。
动态管理:firewalld 提供了一个基于服务的配置方式,而不是仅仅基于端口。这意味着你可以通过服务名称来开启或关闭服务,而不是记忆特定的端口号。
简化配置:使用区域(zones)、服务(services)和接口(interfaces)的概念简化了配置过程。
基于 iptables/nftables:虽然 firewalld 使用自己的配置文件和命令行工具,但它实际上使用 iptables 或 nftables 作为后端来实现规则。
最新框架:nftables 是一个较新的内核框架,旨在取代 iptables 和其他旧的过滤表。
统一 API:它提供了一个统一的 API 来处理 IPv4, IPv6, ARP 和桥接流量。
性能改进:nftables 设计为更高效,具有更好的性能和更低的内存使用。
更高级的功能:包括正则表达式匹配、类型检查和更细粒度的权限控制。
iptables,作为 Linux 系统中防火墙功能的核心组件,扮演着数据包过滤和网络防护的关键角色。它是 netfilter 框架的一部分,直接与 Linux 内核交互,负责定义和执行 IP 数据包过滤规则,为网络通信设立了一道坚固的屏障。
强大而灵活:iptables 凭借其内置的 filter、nat 及 mangle 三张表,实现了从基础过滤到复杂网络地址转换(NAT)和数据包修改的全方位网络管理。
即时生效:任何对 iptables 规则的更改都会立即生效,无需重启服务或等待系统响应,确保了网络策略的实时性和有效性。
iptables 的架构围绕着 “表”、“链” 和 “规则” 这三个核心概念展开:
表(Tables):作为规则的分类器,不同的表承载着特定功能的规则集,如 filter 表用于数据包过滤,nat 表用于地址转换,mangle 表则用于数据包的修改。
链(Chains):是规则的集合体,每个表包含多个链,如 INPUT、OUTPUT、FORWARD 等,分别对应着数据包的不同处理路径。
规则(Rules):是最小的控制单元,它们定义了如何处理特定的数据包,包括匹配条件和动作指令。

注意:raw 表:用于处理异常,包括的规则链有:prerouting,output;一般使用不到。
总体来说,iptables 是由"三表五链"组成
filter:这是 iptables 的默认表,用于网络封包过滤。filter 表主要用于实现基本的防火墙功能,决定数据包是否应该被丢弃(DROP)或继续传递(ACCEPT)。它包含以下三个链:input,output 和 forward
nat:nat 表主要用于网络地址转换(Network Address Translation,NAT),这包括源地址转换(Source NAT,SNAT)和目的地址转换(Destination NAT,DNAT)。它允许你改变数据包中的源或目的 IP 地址,通常用于私有网络连接到公共网络(如互联网)的情况。nat表包含以下链:prerouting,postrouting 和 output
mangle:mangle 表用于数据包的修改,它可以在数据包的生命周期中修改数据包的某些部分,如 TOS(Type of Service)字段、TTL(Time to Live)值或其他数据包头部信息。这通常用于高级的网络操作,比如策略路由(Policy Routing)或 QoS(Quality of Service)配置。可以理解主要用于修改数据包、流量整形、给数据包打标识。mangle表包含以下链:INPUT,OUTPUT, FORWARD,POSTROUTING,PREROUTING
优先级:mangle > nat > filter
input:处理所有到达本地系统的数据包。
output:处理所有从本地系统产生的数据包。
forward:处理所有从一个网络接口传送到另一个网络接口的数据包(即网络转发)。
prerouting:在数据包被路由之前处理数据包,常用于 DNAT。如:把内网中的 80 端口映射到互联网端口
postrouting:在数据包被路由之后处理数据包,常用于 SNAT。如:局域网共享一个公网 IP 接入 Internet。
当一个数据包进入网卡时,它首先进入 PREROUTING 链,内核根据数据包目的 IP 判断是否需要转送出去。
如果数据包就是进入本机的,它就会沿着图向下移动,到达 INPUT 链。数据包到了 INPUT 链后,任何进程都会收到它。
本机上运行的程序可以发送数据包,这些数据包会经过 OUTPUT 链,然后到达 POSTROUTING 链输出。
如果数据包是要转发出去的,且内核允许转发,数据包就会如图所示向右移动,经过 FORWARD 链,然后到达 POSTROUTING 链输出。

总结:整体数据包分两类:1、发给防火墙本身的数据包 ;2、需要经过防火墙的数据包
// 关闭 firewalld 服务
systemctl stop firewalld
// 禁止 firewalld 开机自启动
systemctl disable firewalldyum install iptables iptables-services// 启动 iptables
systemctl start iptables
// 设置 iptables 开机自启动
systemctl start iptables/etc/sysconfig/iptablesiptables [-t table] command [链名] [条件匹配] [-j 目标动作]

-t table:用来指明使用的表,有三种选项: filter,nat,mangle。若未指定,则默认使用 filter 表。
指定 iptables 对我们提交的规则要做什么样的操作,以下是 command 常用参数:
-A:Append,追加一条规则(放到最后)
#拒绝所有人访问服务器(作为最后一条规则)
iptables -A INPUT -j DROP
// 若未 -t 指定表,默认使用filter表-I:Insert,在指定的位置插入规则
#允许 10.10.10.1 主机访问本机
iptables -I INPUT 2 -s 10.10.10.1 -j ACCEPT
// 在 filter 表的 INPUT 链插入成第2条规则-L:List,查看规则列表
具体参数:
n:只显示 IP 地址和端口号码,不显示域名和服务名称
v:显示详细信息,包括每条规则的匹配包数量和匹配字节数
x:在 v 的基础上,禁止自动单位换算(K、M)
--line-number:可以查看到规则号
# 常用的命令就能看到
iptables -nvL-D:Delete,从规则列表中删除规则
// 删除 filter 表 INPUT 链中的第 2 条规则
iptables -D INPUT 2-P:Policy,设置某个链的默认规则(当数据包没有被任何规则匹配时,则按默认规则处理。)
// 设置 filter 表 INPUT 链的默认规则是 DROP
iptables -P INPUT DROP-F:Flush,清空规则
# 清空filter 表中INPUT链上的规则
iptables -F INPUT
# 清空filter 表中所有链上的规则
iptables -F
# 清空 NAT 表中 PREROUTING 链上的规则
iptables -t nat -F PREROUTING
# 清空NAT表中所有链上的规则
iptables -t nat -F注意:-F 是清空链中规则,但并不影响 -P 设置的默认规则。
因此在生产环境中,若指定默认规则为 DROP,一旦执行 iptables -F,很容易导致自己也无法连接服务器(-F 会把配置的明细 ACCEPT 规则删除,只留下默认规则拒接所有)。
-Z:zero,将指定链的所有计数器归零。(如未指定,则认为是所有链)
# 清除filter表INPUT链上的计数器
iptables -Z INPUT-i:匹配数据进入的网络接口,此参数主要应用 nat 表,例如目标地址转换。
-o:匹配数据流出的网络接口
这俩说实话不推荐使用,因为我也没搞懂这俩具体生效的作用,但 iptables 开发者是把这两个参数作为危险标记的
[!] --in-interface -i input name[+]
network interface name ([+] for wildcard)
[!] --out-interface -o output name[+]
network interface name ([+] for wildcard)以下来自 AI 的教学:
实际上,iptables -i 和 iptables -o 不是单独的命令,它们是 iptables 命令的一部分,用于指定数据包过滤规则中的输入接口(-i)和输出接口(-o)。iptables 是一个用于设置 Linux 内核 IP 信息包过滤规则的工具。
-i:指定数据包进入系统时所通过的网络接口。例如,如果你有一个网络接口名为 eth0,你可以使用 -i eth0 来仅对通过 eth0 接口的数据包进行过滤。
-o:指定数据包离开系统时所通过的网络接口。同样地,如果你有一个网络接口名为 eth1,你可以使用 -o eth1 来仅对通过 eth1 接口的数据包进行过滤。
sudo iptables -A INPUT -i eth0 -j DROP这条命令会在 INPUT 链中添加一条规则,拒绝所有通过 eth0 接口进入的数据包。
sudo iptables -A OUTPUT -o eth1 -j ACCEPT这条命令会在 OUTPUT 链中添加一条规则,允许所有通过 eth1 接口发出的数据包。
sudo iptables -A INPUT -i eth0 -s 192.168.1.100 -j DROP这条命令会拒绝 IP 地址为 192.168.1.100 的主机通过 eth0 接口向你的系统发送的数据包。
sudo iptables -A OUTPUT -o eth1 -d 192.168.1.100 -j ACCEPT这条命令会允许你的系统通过 eth1 接口向 IP 地址为 192.168.1.100 的主机发送数据包。
请记得在执行 iptables 命令前加上 sudo,因为这通常需要 root 权限。同时,不要忘记在对 iptables 规则进行更改后保存规则,以确保重启后规则仍然有效。这可以通过运行 service iptables save 或者使用 iptables-persistent 等工具来实现,具体取决于你的 Linux 发行版。
-s:匹配源地址,可以是 IP、网段、域名,也可空(代表任何地址)
-d:匹配目标地址
# -s 参数举例:
# 拒绝 10.10.10.10 主机访问本机
iptables -A INPUT -s 10.10.10.10 -j DROP
# -d 参数举例:
# 禁止本机访问百度
iptables -A OUTPUT -d www.baidu.com -j DROP-p:匹配协议类型,可以是 TCP、UDP、ICMP 等
# 禁止 10.10.10.10 主机 ping 通本机
iptables -A INPUT -s 10.10.10.10 -p icmp -j DROP--sport:匹配源端口;可以是单个端口,也可以是端口范围
--dport:匹配目的端口
# 匹配源端口是23的数据包
--sport 23
# 匹配源端口是 2000-3000 的数据包
--sport 2000:3000
# 匹配 2000 以下的数据包(包含2000)
--sport :2000
# 匹配 1000 以上的数据包(包含1000)
--sport 1000:
# 允许外部数据访问本地服务器 80 端口
iptables -A INPUT -p tcp --dport 80 -j ACCEPT注意:--sport 和 --dport 必须配合 -p 参数使用
-j ACCEPT:允许数据包通过本链而不拦截它
-j DROP:丢弃数据包;阻止数据包通过本链
-j SNAT:源地址转换,支持转换为单 IP,也支持转换到 IP 地址池
# 将内网 192.168.1.0/24 转换为公网 18.18.18.18 地址;SNAT,用于访问互联网
iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -j SNAT --to-source 18.18.18.18
# 将内网 192.168.1.0/24 转换为公网 18.18.18.18 地址池;SNAT,用于访问互联网
iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -j SNAT ---to-source 18.18.18.18-18.18.18.28
# 来个复杂点的:将所有内部主机使用公共 IP 地址 1.1.1.1 访问互联网
sudo iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -j SNAT --to-source 1.1.1.1-j DNAT:目标地址转换,支持转换为单 IP
# DNAT 示例
# 将目标地址由 192.168.1.11:8020 转换为 47.100.100.100:8020
sudo iptables -t nat -A OUTPUT -p tcp -m tcp -d 192.168.1.11 --dport 8020 -j DNAT --to-destination 47.100.100.100:8020-j MASQUERADE:动态 SNAT 转换(适用于动态 IP 场景 )
# MASQUERADE 示例:将源地址是 192.168.1.0/24 的数据包进行地址伪装,转换成 eth0 上的 IP 地址
iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -o eth0 -j MASQUERADE按包状态匹配 (state)
# 用法:-m state --state 状态
# 示例:将目前已运行的服务端口全部放行
iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT按来源 MAC 匹配(mac)
# 用法:-m mac --mac-source MAC
# 示例:拒绝来自某 MAC 地址的数据包进入本机
iptables -A INPUT -m mac --mac-source xx:xx:xx:xx:xx:xx -j DROP按包速率匹配 (limit)
# 用法:-m limit --limit 匹配速率
# 示例:
iptables -A FORWARD -d 192.168.1.1 -m limit --limit 50/s -j ACCEPT
iptables -A FORWARD -d 192.168.1.1 -j DROP
# 注意:limit 英语上看是限制的意思,但实际上只是按一定速率去匹配而已,50/s 表示 1 秒中转发 50 个数据包,要想限制的话后面要再跟一条 DROP 规则多端口匹配 (multiport)
# 用法:-m multiport <--sports|--dports|--ports> 端口 1[,端口 2,..,端口 n]
# 端口范围使用 : 隔开,例如 21000:25000
# 示例:允许访问本机 TCP / 22,53,80,443, 21000 - 25000 端口
iptables -A INPUT -p tcp -m multiport --dports 22,53,80,443,21000:25000 -j ACCEPT