network: allow incoming connections to guests on routed networks w/firewalld

Prior to firewalld version 1.0.0, the default action of ACCEPT in the
"libvirt" zone (subsequently overridden with a lower priority "REJECT"
action) would result in an implicit rule that allowed incoming sessions
through the zone; libvirt relied on this implicit rule to permit
incoming connections to guests that were connected via a libvirt
"routed" network.

Starting in firewalld 1.0.0, the rules generated for this same
zonefile changed such that incoming sessions through the libvirt zone
were no longer allowed, breaking the longstanding convention that they
should be allowed (only for routed networks).

However, beginning with firewalld 0.9.0, a zone can explicitly
allow/block forwarded traffic (by adding a "policy" to the zone that
specifies what happens to packets that are going in one zone and out
another zone).

This patch changes the zone for routed networks from "libvirt" to the
newly-added "libvirt-routed" zone that uses the new policy
functionality to once again allow incoming sessions to guests on
routed networks.

(If firewalld is < 0.9.0, then the policy file won't be read at all,
so firewalld won't log any error, and libvirt will just use the old
setup that takes advantage of the implicit forwarding rules).

Resolves: https://bugzilla.redhat.com/2055706
Signed-off-by: Eric Garver <eric@garver.life>
Reviewed-by: Laine Stump <laine@redhat.com>
This commit is contained in:
Eric Garver 2022-09-22 11:13:24 -04:00 committed by Laine Stump
parent 2a461957b1
commit 7f7a09a2d2

View File

@ -857,8 +857,17 @@ int networkAddFirewallRules(virNetworkDef *def)
* nftables + default zone means that traffic cannot be
* forwarded (and even DHCP and DNS from guest to host
* will probably no be permitted by the default zone
*
* Routed networks use a different zone and policy which we also
* need to verify exist. Probing for the policy guarantees the
* running firewalld has support for policies (firewalld >= 0.9.0).
*/
if (virFirewallDZoneExists("libvirt")) {
if (def->forward.type == VIR_NETWORK_FORWARD_ROUTE &&
virFirewallDPolicyExists("libvirt-routed-out") &&
virFirewallDZoneExists("libvirt-routed")) {
if (virFirewallDInterfaceSetZone(def->bridge, "libvirt-routed") < 0)
return -1;
} else if (virFirewallDZoneExists("libvirt")) {
if (virFirewallDInterfaceSetZone(def->bridge, "libvirt") < 0)
return -1;
} else {