Understanding Firewalld in Multi-Zone Configurations

A Simple Single-Zoned Example

Say you just want to lock down your firewall. Simply remove the services currently allowed by the public zone and reload:

# firewall-cmd --permanent --zone=public --remove-service=dhcpv6-client
# firewall-cmd --permanent --zone=public --remove-service=ssh
# firewall-cmd --reload

These commands result in the following firewall:

# firewall-cmd --zone=public --list-all
public (default, active)
  interfaces: eno1 eno2
  masquerade: no
  rich rules:
# firewall-cmd --permanent --zone=public --get-target

In the spirit of keeping security as tight as possible, if a situation arises where you need to open a temporary hole in your firewall (perhaps for ssh), you can add the service to just the current session (omit --permanent) and instruct firewalld to revert the modification after a specified amount of time:

# firewall-cmd --zone=public --add-service=ssh --timeout=5m

The timeout option takes time values in seconds (s), minutes (m) or hours (h).


When a zone processes a packet due to its source or interface, but there is no rule that explicitly handles the packet, the target of the zone determines the behavior:

  • ACCEPT: accept the packet.

  • %%REJECT%%: reject the packet, returning a reject reply.

  • DROP: drop the packet, returning no reply.

  • default: don't do anything. The zone washes its hands of the problem, and kicks it "upstairs".

There was a bug present in firewalld 0.3.9 (fixed in 0.3.10) for source zones with targets other than default in which the target was applied regardless of allowed services. For example, a source zone with the target DROP would drop all packets, even if they were whitelisted. Unfortunately, this version of firewalld was packaged for RHEL7 and its derivatives, causing it to be a fairly common bug. The examples in this article avoid situations that would manifest this behavior.


Active zones fulfill two different roles. Zones with associated interface(s) act as interface zones, and zones with associated source(s) act as source zones (a zone could fulfill both roles). Firewalld handles a packet in the following order:

  1. The corresponding source zone. Zero or one such zones may exist. If the source zone deals with the packet because the packet satisfies a rich rule, the service is whitelisted, or the target is not default, we end here. Otherwise, we pass the packet on.

  2. The corresponding interface zone. Exactly one such zone will always exist. If the interface zone deals with the packet, we end here. Otherwise, we pass the packet on.

  3. The firewalld default action. Accept icmp packets and reject everything else.

The take-away message is that source zones have precedence over interface zones. Therefore, the general design pattern for multi-zoned firewalld configurations is to create a privileged source zone to allow specific IP's elevated access to system services and a restrictive interface zone to limit the access of everyone else.


Nathan Vance is a computer science major at Hope College in Holland, Michigan. He installed Linux Mint 12 as a high school junior and now prefers Arch Linux.