本页网址二维码:
日常运维CentOS 7服务器,通过logwatch发现存在firewalld有WARNING的吐槽行为。于是查询系统日志/var/log/message,发现如下来自firewalld的COMMAND_FAILED操作失败的警告:
Nov 17 08:00:03 KDSYS firewalld[1355]: WARNING: AllowZoneDrifting is enabled. This is considered an insecure configuration option. It will be removed in a future release. Please consider disabling it now.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table mangle --delete POSTROUTING --out-interface virbr0 --protocol udp --destination-port 68 --jump CHECKSUM --checksum-fill' failed: iptables: No chain/target/match by that name.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table nat --delete POSTROUTING --source 192.168.122.0/24 --destination 224.0.0.0/24 --jump RETURN' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table nat --delete POSTROUTING --source 192.168.122.0/24 --destination 255.255.255.255/32 --jump RETURN' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table nat --delete POSTROUTING --source 192.168.122.0/24 -p tcp ! --destination 192.168.122.0/24 --jump MASQUERADE --to-ports 1024-65535' failed: iptables: No chain/target/match by that name.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table nat --delete POSTROUTING --source 192.168.122.0/24 -p udp ! --destination 192.168.122.0/24 --jump MASQUERADE --to-ports 1024-65535' failed: iptables: No chain/target/match by that name.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table nat --delete POSTROUTING --source 192.168.122.0/24 ! --destination 192.168.122.0/24 --jump MASQUERADE' failed: iptables: No chain/target/match by that name.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete FORWARD --destination 192.168.122.0/24 --out-interface virbr0 --match conntrack --ctstate ESTABLISHED,RELATED --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete FORWARD --source 192.168.122.0/24 --in-interface virbr0 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete FORWARD --in-interface virbr0 --out-interface virbr0 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete FORWARD --out-interface virbr0 --jump REJECT' failed: iptables: No chain/target/match by that name.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete FORWARD --in-interface virbr0 --jump REJECT' failed: iptables: No chain/target/match by that name.
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete INPUT --in-interface virbr0 --protocol udp --destination-port 53 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete INPUT --in-interface virbr0 --protocol tcp --destination-port 53 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete OUTPUT --out-interface virbr0 --protocol udp --destination-port 68 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete INPUT --in-interface virbr0 --protocol udp --destination-port 67 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
Nov 17 08:00:04 KDSYS firewalld[1355]: WARNING: AllowZoneDrifting is enabled. This is considered an insecure configuration option. It will be removed in a future release. Please consider disabling it now.
Nov 17 08:00:05 KDSYS firewalld[1355]: WARNING: COMMAND_FAILED: '/usr/sbin/iptables -w10 -w --table filter --delete INPUT --in-interface virbr0 --protocol tcp --destination-port 67 --jump ACCEPT' failed: iptables: Bad rule (does a matching rule exist in that chain?).
很显然是firewalld对服务器内的虚拟化桥接口virbr0,应用防火墙规则失败了。但检查virbr0接口却是存在的。
鉴于这台服务器是某个信息系统的应用服务器独占使用,不可能在其上再运行虚拟机。于是决定删除虚拟化相关软件包、禁用和取消virbr0虚拟化桥接接口,具体过程如下:
virsh net-destroy default
virsh net-undefine default
systemctl stop libvirtd
systemctl disable libvirtd
ifconfig virbr0 down
brctl delbr virbr0
yum remove qemu-guest-agent qemu-img qemu-kvm-common qemu-kvm libvirt-daemon libvirt-libs libvirt-gconfig
一些说明:
1、ifdown脚本不能操作virbr0,要用ifconfig
2、yum remove操作只给出必要的包名称,其它包会因依赖而删除。
3、有些步骤不一定需要,执行时如果显示未知命令,尤其是头两条,直接忽略即可。
另外,在日志中可以看到有:
“WARNING: AllowZoneDrifting is enabled. This is considered an insecure configuration option. It will be removed in a future release. Please consider disabling it now.”
的消息,检查了firewalld相关文档后发现,旧版本的firewalld有一个未文档化的功能,被称为区域漂移ZoneDrifting,相应的配置项目名称为AllowZoneDrifting。
AllowZoneDrifting的默认值为否。要恢复旧的、有问题的行为,用户可以将其设置为yes,但这个做法其实是不安全的。所以导致firewalld给出警告信息,建议关闭。
那么为什么这服务器上firewalld的默认配置会将其设置为开启呢?笔者本人并没有去设置过这个选项。
要搞清楚这件事,首先要理解一下什么是区域漂移ZoneDrifting。
用户可以配置一个基于源的区域,姑且称之为Foo,并通过--add-source参数添加源。如果区域Foo使用--set-target设置为default默认区域,那么数据包将被允许进入第二个基于接口的区域。这包括全覆盖的默认区域default。
这是以前版本的firewalld如何向区域调度分发数据包的结果。
每个调度分发的类型过去都有它自己的专用链,也就是:
chain filter_INPUT {
...
jump filter_INPUT_ZONES_SOURCE # 关键点
jump filter_INPUT_ZONES # 在这里
...
}
chain filter_INPUT_ZONES_SOURCE {
ip6 saddr dead:beef::/54 goto filter_IN_internal
}
chain filter_INPUT_ZONES {
iifname "dummy0" goto filter_IN_trusted
goto filter_IN_public
}
正如上面的注释部位所指出的,关键点在于有两个不同的链在执行调度分发。一个基于来源,另一个基于接口。
如果链filter_IN_internal不是终端,就如通过--set-target参数设置了目标是default(默认)时,包处理将返回到filter_INPUT链并跳转到filter_INPUT_ZONES链。
也就是一个数据包可以同时进入internal区域和trusted/public区域。
那么,为什么要默认禁用它呢?
基于区域的防火墙对流量的控制,是数据包进入且只进入某一个区域。
很明显上述的操作违反了这个原则,很可能会导致流量或服务被意外地允许通过防火墙。
社区已经就区域漂移ZoneDrifting这个特性,对firewalld给出了若干相关的错误报告。因此,AllowZoneDrifting的默认值就必须为否。
当前版本的firewalld这个选项,与以前的版本有什么不同?
即使将AllowZoneDrifting设置为是,以前版本的firewalld和当前版本之间也有轻微的行为差异。
这些行为差异发生在firewalld部分功能特性上,包括有 masquerade(地址伪装), forward-port(端口转发)和helpers(助手)等。
对于这些功能特性,区域漂移可以发生在通过--set-target设置的任何目标设置上,包括ACCEPT DROP 和EJECT,甚至对基于接口的区域也如是。
造成的典型问题如:
Forward port for external zone is reachable from internal zone and gets all port-related traffic
有鉴于此,区域漂移功能最终被认定为属于安全漏洞且没有合理的用例。所以firewalld项目的后续推进里面,AllowDroneDrifting没有被继续发展下去。
如何重新启用区域漂移?
firewalld开发团队强烈阻止启用区域漂移功能。最好的实践是将必要的服务和配置添加到基于来源的区域中。
不过如果用户还是需要启用区域漂移,可以通过修改
/etc/firewalld/firewalld.conf
配置文件,设置
AllowZoneDrifting为yes,保存然后重启firewalld服务即可。
受影响的版本有哪些?
以下firewalld版本修复了区域漂移错误,并不允许其发生:
0.6.5、0.7.0、0.8.0
在以下版本中引入了AllowZoneDrifting设置,从而允许用户重新获得之前的功能特性:
0.7.4、0.8.2、1.0.0
结论:
所以其实很明显是CentOS 7 为了保持向后兼容,而在firewalld.conf配置文件中把AllowZoneDrifiting设置为“yes”。对于不太清楚上文内容的网管员来说,直接改成“no”就没事了。
注:本期封面图通过AI生成,来自Algolet小算法: