Blame SOURCES/0030-feat-AllowZoneDrifting-config-option.patch

40251c
From 982024e6775c9a9c78713be82519c729107ca4e2 Mon Sep 17 00:00:00 2001
087194
From: Eric Garver <eric@garver.life>
087194
Date: Sun, 19 Jan 2020 14:13:36 -0500
40251c
Subject: [PATCH 30/37] feat: AllowZoneDrifting config option
087194
087194
Older versions of firewalld had undocumented behavior known as "zone
087194
drifting". This allowed packets to ingress multiple zones - this is a
087194
violation of zone based firewalls. However, some users rely on this
087194
behavior to have a "catch-all" zone, e.g. the default zone. You can
087194
enable this if you desire such behavior. It's disabled by default for
087194
security reasons.
087194
087194
Note: If "yes" packets will only drift from source based zones to
087194
interface based zones (including the default zone). Packets never drift
087194
from interface based zones to other interfaces based zones (including
087194
the default zone).
087194
087194
(cherry picked from commit afadd377b09dc62b340d24bcf891d31f040d1a18)
40251c
(cherry picked from commit afbd6c0e82b77ca9b687169d69bf6c2dc17a9317)
087194
---
087194
 config/firewalld.conf                  | 12 ++++++++++++
087194
 doc/xml/firewalld.conf.xml             | 19 +++++++++++++++++++
087194
 doc/xml/firewalld.dbus.xml             | 16 ++++++++++++++++
087194
 src/firewall/config/__init__.py.in     |  1 +
087194
 src/firewall/core/fw.py                | 14 ++++++++++++++
087194
 src/firewall/core/io/firewalld_conf.py | 13 +++++++++++--
087194
 src/firewall/server/config.py          | 20 +++++++++++++++++---
40251c
 src/tests/dbus/firewalld.conf.at       |  3 +++
40251c
 8 files changed, 93 insertions(+), 5 deletions(-)
087194
087194
diff --git a/config/firewalld.conf b/config/firewalld.conf
40251c
index 82ad062b8a66..532f0452212e 100644
087194
--- a/config/firewalld.conf
087194
+++ b/config/firewalld.conf
40251c
@@ -61,3 +61,15 @@ FlushAllOnReload=yes
087194
 # internet.
087194
 # Defaults to "yes".
087194
 RFC3964_IPv4=yes
087194
+
087194
+# AllowZoneDrifting
087194
+# Older versions of firewalld had undocumented behavior known as "zone
087194
+# drifting". This allowed packets to ingress multiple zones - this is a
087194
+# violation of zone based firewalls. However, some users rely on this behavior
087194
+# to have a "catch-all" zone, e.g. the default zone. You can enable this if you
087194
+# desire such behavior. It's disabled by default for security reasons.
087194
+# Note: If "yes" packets will only drift from source based zones to interface
087194
+# based zones (including the default zone). Packets never drift from interface
087194
+# based zones to other interfaces based zones (including the default zone).
087194
+# Possible values; "yes", "no". Defaults to "no".
087194
+AllowZoneDrifting=no
087194
diff --git a/doc/xml/firewalld.conf.xml b/doc/xml/firewalld.conf.xml
40251c
index 6003a6fae855..fcfbfd2b68c1 100644
087194
--- a/doc/xml/firewalld.conf.xml
087194
+++ b/doc/xml/firewalld.conf.xml
087194
@@ -183,6 +183,25 @@
087194
             </listitem>
087194
         </varlistentry>
087194
 
087194
+        <varlistentry>
087194
+            <term><option>AllowZoneDrifting</option></term>
087194
+            <listitem>
087194
+                <para>
087194
+                Older versions of firewalld had undocumented behavior known
087194
+                as "zone drifting". This allowed packets to ingress multiple
087194
+                zones - this is a violation of zone based firewalls. However,
087194
+                some users rely on this behavior to have a "catch-all" zone,
087194
+                e.g. the default zone. You can enable this if you desire such
087194
+                behavior. It's disabled by default for security reasons.
087194
+                Note: If "yes" packets will only drift from source based zones
087194
+                to interface based zones (including the default zone). Packets
087194
+                never drift from interface based zones to other interfaces
087194
+                based zones (including the default zone).
087194
+                Valid values; "yes", "no". Defaults to "no".
087194
+                </para>
087194
+            </listitem>
087194
+        </varlistentry>
087194
+
087194
     </variablelist>
087194
 
087194
   </refsect1>
087194
diff --git a/doc/xml/firewalld.dbus.xml b/doc/xml/firewalld.dbus.xml
40251c
index 66b0475ec0c8..5d77af976443 100644
087194
--- a/doc/xml/firewalld.dbus.xml
087194
+++ b/doc/xml/firewalld.dbus.xml
40251c
@@ -2578,6 +2578,22 @@
087194
       <refsect3 id="FirewallD1.config.Properties">
087194
         <title>Properties</title>
087194
         <variablelist>
087194
+          <varlistentry id="FirewallD1.config.Properties.AllowZoneDrifting">
087194
+            <term><parameter>AllowZoneDrifting</parameter> - s - (rw)</term>
087194
+            <listitem><para>
087194
+                Older versions of firewalld had undocumented behavior known
087194
+                as "zone drifting". This allowed packets to ingress multiple
087194
+                zones - this is a violation of zone based firewalls. However,
087194
+                some users rely on this behavior to have a "catch-all" zone,
087194
+                e.g. the default zone. You can enable this if you desire such
087194
+                behavior. It's disabled by default for security reasons.
087194
+                Note: If "yes" packets will only drift from source based zones
087194
+                to interface based zones (including the default zone). Packets
087194
+                never drift from interface based zones to other interfaces
087194
+                based zones (including the default zone).
087194
+                Valid values; "yes", "no". Defaults to "no".
087194
+            </para></listitem>
087194
+          </varlistentry>
087194
           <varlistentry id="FirewallD1.config.Properties.AutomaticHelpers">
087194
             <term>AutomaticHelpers - s - (rw)</term>
087194
             <listitem>
087194
diff --git a/src/firewall/config/__init__.py.in b/src/firewall/config/__init__.py.in
40251c
index 3274dd430e4e..481eb8de758d 100644
087194
--- a/src/firewall/config/__init__.py.in
087194
+++ b/src/firewall/config/__init__.py.in
40251c
@@ -130,3 +130,4 @@ FALLBACK_AUTOMATIC_HELPERS = "no"
087194
 FALLBACK_FIREWALL_BACKEND = "nftables"
087194
 FALLBACK_FLUSH_ALL_ON_RELOAD = True
087194
 FALLBACK_RFC3964_IPV4 = True
087194
+FALLBACK_ALLOW_ZONE_DRIFTING = False
087194
diff --git a/src/firewall/core/fw.py b/src/firewall/core/fw.py
40251c
index 050fb9cd976d..6206ed586988 100644
087194
--- a/src/firewall/core/fw.py
087194
+++ b/src/firewall/core/fw.py
40251c
@@ -123,6 +123,7 @@ class Firewall(object):
40251c
         self._firewall_backend = config.FALLBACK_FIREWALL_BACKEND
40251c
         self._flush_all_on_reload = config.FALLBACK_FLUSH_ALL_ON_RELOAD
40251c
         self._rfc3964_ipv4 = config.FALLBACK_RFC3964_IPV4
087194
+        self._allow_zone_drifting = config.FALLBACK_ALLOW_ZONE_DRIFTING
087194
 
087194
     def individual_calls(self):
087194
         return self._individual_calls
40251c
@@ -286,6 +287,19 @@ class Firewall(object):
087194
                 log.debug1("RFC3964_IPv4 is set to '%s'",
087194
                            self._rfc3964_ipv4)
087194
 
087194
+            if self._firewalld_conf.get("AllowZoneDrifting"):
087194
+                value = self._firewalld_conf.get("AllowZoneDrifting")
087194
+                if value.lower() in [ "no", "false" ]:
087194
+                    self._allow_zone_drifting = False
087194
+                else:
087194
+                    self._allow_zone_drifting = True
087194
+                    log.warning("AllowZoneDrifting is enabled. This is considered "
087194
+                                "an insecure configuration option. It will be "
087194
+                                "removed in a future release. Please consider "
087194
+                                "disabling it now.")
087194
+                log.debug1("AllowZoneDrifting is set to '%s'",
087194
+                           self._allow_zone_drifting)
087194
+
087194
         self.config.set_firewalld_conf(copy.deepcopy(self._firewalld_conf))
087194
 
087194
         self._select_firewall_backend(self._firewall_backend)
087194
diff --git a/src/firewall/core/io/firewalld_conf.py b/src/firewall/core/io/firewalld_conf.py
40251c
index 9e2205f93d63..7c7092120676 100644
087194
--- a/src/firewall/core/io/firewalld_conf.py
087194
+++ b/src/firewall/core/io/firewalld_conf.py
087194
@@ -28,10 +28,10 @@ from firewall import config
087194
 from firewall.core.logger import log
087194
 from firewall.functions import b2u, u2b, PY2
087194
 
087194
-valid_keys = [ "DefaultZone", "MinimalMark", "CleanupOnExit", "Lockdown", 
087194
+valid_keys = [ "DefaultZone", "MinimalMark", "CleanupOnExit", "Lockdown",
087194
                "IPv6_rpfilter", "IndividualCalls", "LogDenied",
087194
                "AutomaticHelpers", "FirewallBackend", "FlushAllOnReload",
087194
-               "RFC3964_IPv4" ]
087194
+               "RFC3964_IPv4", "AllowZoneDrifting" ]
087194
 
087194
 class firewalld_conf(object):
087194
     def __init__(self, filename):
087194
@@ -83,6 +83,7 @@ class firewalld_conf(object):
087194
             self.set("FirewallBackend", config.FALLBACK_FIREWALL_BACKEND)
087194
             self.set("FlushAllOnReload", "yes" if config.FALLBACK_FLUSH_ALL_ON_RELOAD else "no")
087194
             self.set("RFC3964_IPv4", "yes" if config.FALLBACK_RFC3964_IPV4 else "no")
087194
+            self.set("AllowZoneDrifting", "yes" if config.FALLBACK_ALLOW_ZONE_DRIFTING else "no")
087194
             raise
087194
 
087194
         for line in f:
087194
@@ -202,6 +203,14 @@ class firewalld_conf(object):
087194
                             config.FALLBACK_RFC3964_IPV4)
087194
             self.set("RFC3964_IPv4", str(config.FALLBACK_RFC3964_IPV4))
087194
 
087194
+        value = self.get("AllowZoneDrifting")
087194
+        if not value or value.lower() not in [ "yes", "true", "no", "false" ]:
087194
+            if value is not None:
087194
+                log.warning("AllowZoneDrifting '%s' is not valid, using default "
087194
+                            "value %s", value if value else '',
087194
+                            config.FALLBACK_ALLOW_ZONE_DRIFTING)
087194
+            self.set("AllowZoneDrifting", str(config.FALLBACK_ALLOW_ZONE_DRIFTING))
087194
+
087194
     # save to self.filename if there are key/value changes
087194
     def write(self):
087194
         if len(self._config) < 1:
087194
diff --git a/src/firewall/server/config.py b/src/firewall/server/config.py
40251c
index 1c35f5663d29..b3e193d7e468 100644
087194
--- a/src/firewall/server/config.py
087194
+++ b/src/firewall/server/config.py
087194
@@ -107,6 +107,7 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
                                                 "FirewallBackend": "readwrite",
087194
                                                 "FlushAllOnReload": "readwrite",
087194
                                                 "RFC3964_IPv4": "readwrite",
087194
+                                                "AllowZoneDrifting": "readwrite",
087194
                                               })
087194
 
087194
     @handle_exceptions
087194
@@ -487,7 +488,8 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
         if prop not in [ "DefaultZone", "MinimalMark", "CleanupOnExit",
087194
                          "Lockdown", "IPv6_rpfilter", "IndividualCalls",
087194
                          "LogDenied", "AutomaticHelpers", "FirewallBackend",
087194
-                         "FlushAllOnReload", "RFC3964_IPv4" ]:
087194
+                         "FlushAllOnReload", "RFC3964_IPv4",
087194
+                         "AllowZoneDrifting" ]:
087194
             raise dbus.exceptions.DBusException(
087194
                 "org.freedesktop.DBus.Error.InvalidArgs: "
087194
                 "Property '%s' does not exist" % prop)
087194
@@ -540,6 +542,10 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
             if value is None:
087194
                 value = "yes" if config.FALLBACK_RFC3964_IPV4 else "no"
087194
             return dbus.String(value)
087194
+        elif prop == "AllowZoneDrifting":
087194
+            if value is None:
087194
+                value = "yes" if config.FALLBACK_ALLOW_ZONE_DRIFTING else "no"
087194
+            return dbus.String(value)
087194
 
087194
     @dbus_handle_exceptions
087194
     def _get_dbus_property(self, prop):
087194
@@ -565,6 +571,8 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
             return dbus.String(self._get_property(prop))
087194
         elif prop == "RFC3964_IPv4":
087194
             return dbus.String(self._get_property(prop))
087194
+        elif prop == "AllowZoneDrifting":
087194
+            return dbus.String(self._get_property(prop))
087194
         else:
087194
             raise dbus.exceptions.DBusException(
087194
                 "org.freedesktop.DBus.Error.InvalidArgs: "
087194
@@ -605,7 +613,8 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
             for x in [ "DefaultZone", "MinimalMark", "CleanupOnExit",
087194
                        "Lockdown", "IPv6_rpfilter", "IndividualCalls",
087194
                        "LogDenied", "AutomaticHelpers", "FirewallBackend",
087194
-                       "FlushAllOnReload", "RFC3964_IPv4" ]:
087194
+                       "FlushAllOnReload", "RFC3964_IPv4",
087194
+                       "AllowZoneDrifting" ]:
087194
                 ret[x] = self._get_property(x)
087194
         elif interface_name in [ config.dbus.DBUS_INTERFACE_CONFIG_DIRECT,
087194
                                  config.dbus.DBUS_INTERFACE_CONFIG_POLICIES ]:
087194
@@ -633,7 +642,7 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
                                   "IPv6_rpfilter", "IndividualCalls",
087194
                                   "LogDenied", "AutomaticHelpers",
087194
                                   "FirewallBackend", "FlushAllOnReload",
087194
-                                  "RFC3964_IPv4" ]:
087194
+                                  "RFC3964_IPv4", "AllowZoneDrifting" ]:
087194
                 if property_name == "MinimalMark":
087194
                     try:
087194
                         int(new_value)
087194
@@ -677,6 +686,11 @@ class FirewallDConfig(slip.dbus.service.Object):
087194
                         raise FirewallError(errors.INVALID_VALUE,
087194
                                             "'%s' for %s" % \
087194
                                             (new_value, property_name))
087194
+                if property_name == "AllowZoneDrifting":
087194
+                    if new_value.lower() not in ["yes", "true", "no", "false"]:
087194
+                        raise FirewallError(errors.INVALID_VALUE,
087194
+                                            "'%s' for %s" % \
087194
+                                            (new_value, property_name))
087194
 
087194
                 self.config.get_firewalld_conf().set(property_name, new_value)
087194
                 self.config.get_firewalld_conf().write()
087194
diff --git a/src/tests/dbus/firewalld.conf.at b/src/tests/dbus/firewalld.conf.at
40251c
index 06f6df9bdd70..35aead759a9c 100644
087194
--- a/src/tests/dbus/firewalld.conf.at
087194
+++ b/src/tests/dbus/firewalld.conf.at
40251c
@@ -4,6 +4,7 @@ AT_KEYWORDS(dbus)
087194
 dnl Verify defaults over dbus. Should be inline with default firewalld.conf.
40251c
 IF_HOST_SUPPORTS_NFT_FIB([
40251c
 DBUS_GETALL([config], [config], 0, [dnl
40251c
+string "AllowZoneDrifting" : variant string "no"
40251c
 string "AutomaticHelpers" : variant string "no"
40251c
 string "CleanupOnExit" : variant string "no"
40251c
 string "DefaultZone" : variant string "public"
40251c
@@ -17,6 +18,7 @@ string "MinimalMark" : variant int32 100
40251c
 string "RFC3964_IPv4" : variant string "yes"
40251c
 ])], [
087194
 DBUS_GETALL([config], [config], 0, [dnl
087194
+string "AllowZoneDrifting" : variant string "no"
40251c
 string "AutomaticHelpers" : variant string "no"
087194
 string "CleanupOnExit" : variant string "no"
087194
 string "DefaultZone" : variant string "public"
40251c
@@ -49,6 +51,7 @@ _helper([FirewallBackend], [string:"iptables"], [variant string "iptables"])
087194
 _helper([FlushAllOnReload], [string:"no"], [variant string "no"])
087194
 _helper([CleanupOnExit], [string:"yes"], [variant string "yes"])
087194
 _helper([RFC3964_IPv4], [string:"no"], [variant string "no"])
087194
+_helper([AllowZoneDrifting], [string:"yes"], [variant string "yes"])
087194
 dnl Note: DefaultZone is RO
087194
 m4_undefine([_helper])
087194
 
087194
-- 
087194
2.23.0
087194