diff --git a/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-avoid-iterating-NM-devices-conne.patch b/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-avoid-iterating-NM-devices-conne.patch new file mode 100644 index 0000000..2cd1f74 --- /dev/null +++ b/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-avoid-iterating-NM-devices-conne.patch @@ -0,0 +1,117 @@ +From 5f41f061390876f4c43c2306911d9b3482aed396 Mon Sep 17 00:00:00 2001 +From: Lubomir Rintel +Date: Mon, 16 Jul 2018 17:42:34 +0200 +Subject: [PATCH 1/3] firewall.core.fw_nm: avoid iterating NM devices, + connections + +NetworkManager has an API to do the lookups. + +(cherry picked from commit 65f92930a5d049404dac780c15eebe2d788e6285) +--- + src/firewall/core/fw_nm.py | 70 ++++++++++++++++++---------------------------- + 1 file changed, 27 insertions(+), 43 deletions(-) + +diff --git a/src/firewall/core/fw_nm.py b/src/firewall/core/fw_nm.py +index f75733fe65f6..76901cee2adf 100644 +--- a/src/firewall/core/fw_nm.py ++++ b/src/firewall/core/fw_nm.py +@@ -73,22 +73,18 @@ def nm_get_zone_of_connection(connection): + """ + check_nm_imported() + +- active_connections = nm_get_client().get_active_connections() ++ con = nm_get_client().get_connection_by_id(connection) ++ if con is None: ++ return False + +- for active_con in active_connections: +- if active_con.get_id() == connection: +- con = active_con.get_connection() +- if con is None: +- continue +- setting_con = con.get_setting_connection() +- if setting_con is None: +- continue +- zone = setting_con.get_zone() +- if zone is None: +- zone = "" +- return zone ++ setting_con = con.get_setting_connection() ++ if setting_con is None: ++ return False + +- return None ++ zone = setting_con.get_zone() ++ if zone is None: ++ zone = "" ++ return zone + + def nm_set_zone_of_connection(zone, connection): + """Set the zone for a connection +@@ -98,24 +94,18 @@ def nm_set_zone_of_connection(zone, connection): + """ + check_nm_imported() + +- active_connections = nm_get_client().get_active_connections() +- +- for active_con in active_connections: +- con = active_con.get_connection() +- if con is None: +- continue ++ con = nm_get_client().get_connection_by_id(connection) ++ if con is None: ++ return False + +- if active_con.get_id() == connection: +- setting_con = con.get_setting_connection() +- if setting_con is None: +- continue +- if zone == "": +- zone = None +- setting_con.set_property("zone", zone) +- con.commit_changes(True, None) +- return True ++ setting_con = con.get_setting_connection() ++ if setting_con is None: ++ return False + +- return False ++ if zone == "": ++ zone = None ++ setting_con.set_property("zone", zone) ++ return con.commit_changes(True, None) + + def nm_get_connections(connections, connections_uuid): + """Get active connections from NM +@@ -150,21 +140,15 @@ def nm_get_connection_of_interface(interface): + """ + check_nm_imported() + +- active_connections = nm_get_client().get_active_connections() +- +- for active_con in active_connections: +- # ignore vpn devices for now +- if active_con.get_vpn(): +- continue +- +- devices = active_con.get_devices() +- +- for dev in devices: +- if dev.get_iface() == interface: +- return active_con.get_id() ++ device = nm_get_client().get_device_by_iface(interface) ++ if device is None: ++ return None + ++ active_con = device.get_active_connection() ++ if active_con is None: ++ return None + +- return None ++ return active_con.get_id() + + def nm_get_bus_name(): + if not _nm_imported: +-- +2.16.3 + diff --git a/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-identify-the-connections-by-uuid.patch b/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-identify-the-connections-by-uuid.patch new file mode 100644 index 0000000..1cee69c --- /dev/null +++ b/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-identify-the-connections-by-uuid.patch @@ -0,0 +1,352 @@ +From 0ce07e30014a8ee6b2a8a4909c313f207d9c9b31 Mon Sep 17 00:00:00 2001 +From: Lubomir Rintel +Date: Mon, 16 Jul 2018 17:43:04 +0200 +Subject: [PATCH 2/3] firewall.core.fw_nm: identify the connections by uuid + +...as opposed by id. Uuid is guarranteed to be uniquie, while the id is +provided merely for convenience without any guarrantees. + +(cherry picked from commit 624039964bd16e5e0e8ffb73e708d3d0c40e89d3) +--- + src/firewall-applet | 38 ++++++++++++++++++++------------------ + src/firewall-config | 45 +++++++++++++++++++++++++-------------------- + src/firewall/core/fw_nm.py | 16 ++++++++-------- + 3 files changed, 53 insertions(+), 46 deletions(-) + +diff --git a/src/firewall-applet b/src/firewall-applet +index 3dc149c32755..86aaccab9f88 100755 +--- a/src/firewall-applet ++++ b/src/firewall-applet +@@ -155,11 +155,12 @@ class ZoneInterfaceEditor(QtGui.QDialog): + # ZoneConnectionEditor ######################################################## + + class ZoneConnectionEditor(ZoneInterfaceEditor): +- def __init__(self, fw, connection, zone): ++ def __init__(self, fw, connection, connection_name, zone): + self.fw = fw + self.connection = connection ++ self.connection_name = connection_name + self.zone = None +- self.title = _("Select zone for connection '%s'") % self.connection ++ self.title = _("Select zone for connection '%s'") % self.connection_name + + QtGui.QDialog.__init__(self) + self.create_ui(zone) +@@ -168,12 +169,12 @@ class ZoneConnectionEditor(ZoneInterfaceEditor): + # apply changes + try: + nm_set_zone_of_connection(self.get_zone(), self.connection) +- except Exception as msg: +- text = _("Failed to set zone {zone} for connection {connection}") ++ except Exception: ++ text = _("Failed to set zone {zone} for connection {connection_name}") + QtGui.QMessageBox.warning(None, fromUTF8(escape(self.title)), + escape(text.format( + zone=self.get_zone(), +- connection=self.connection))) ++ connection_name=self.connection_name))) + self.hide() + + # ZoneSourceEditor ############################################################ +@@ -428,7 +429,7 @@ class TrayApplet(QtGui.QSystemTrayIcon): + + self.active_zones = { } + self.connections = { } +- self.connections_uuid = { } ++ self.connections_name = { } + self.default_zone = None + self.zone_connection_editors = { } + self.zone_interface_editors = { } +@@ -666,30 +667,31 @@ class TrayApplet(QtGui.QSystemTrayIcon): + # NM controlled connections + for interface in self.connections: + connection = self.connections[interface] +- if connection not in self.connections_uuid: +- uuid = None ++ if connection not in self.connections_name: ++ connection_name = None + else: +- uuid = self.connections_uuid[connection] ++ connection_name = self.connections_name[connection] + zone = nm_get_zone_of_connection(connection) +- connections[connection] = [ zone, uuid ] ++ connections[connection] = [ zone, connection_name ] + + binding = _("{entry} (Zone: {zone})") + + # add NM controlled bindings + for connection in sorted(connections): + zone = connections[connection][0] ++ connection_name = connections[connection][1] + if zone == "": + _binding = _("{entry} (Default Zone: {default_zone})") + action = QtGui.QAction( + fromUTF8(escape( + _binding.format(default_zone=self.default_zone, +- entry=connection))), self) ++ entry=connection_name))), self) + else: + action = QtGui.QAction( + fromUTF8(escape(binding.format(zone=zone, +- entry=connection))), self) ++ entry=connection_name))), self) + action.triggered.connect(functools.partial( +- self.zone_connection_editor, connection, zone)) ++ self.zone_connection_editor, connection, connection_name, zone)) + self.left_menu.addAction(action) + + # add interfaces entry +@@ -729,13 +731,13 @@ class TrayApplet(QtGui.QSystemTrayIcon): + editor.raise_() + editor.show() + +- def zone_connection_editor(self, connection, zone): ++ def zone_connection_editor(self, connection, connection_name, zone): + if connection in self.zone_connection_editors: + self.zone_connection_editors[connection].set_zone(zone) + self.zone_connection_editors[connection].show() + return self.zone_connection_editors[connection].raise_() + +- editor = ZoneConnectionEditor(self.fw, connection, zone) ++ editor = ZoneConnectionEditor(self.fw, connection, connection_name, zone) + self.zone_connection_editors[connection] = editor + editor.show() + editor.raise_() +@@ -755,15 +757,15 @@ class TrayApplet(QtGui.QSystemTrayIcon): + + def nm_signal_receiver(self, *args, **kwargs): + self.connections.clear() +- self.connections_uuid.clear() ++ self.connections_name.clear() + + # do not use NMClient could result in python core dump + + if nm_is_imported(): + text = _("Failed to get connections from NetworkManager") + try: +- nm_get_connections(self.connections, self.connections_uuid) +- except Exception as msg: ++ nm_get_connections(self.connections, self.connections_name) ++ except Exception: + self.notify(escape(text), urgency=Notify.Urgency.CRITICAL) + if text not in self.tooltip_messages: + self.tooltip_messages.append(text) +diff --git a/src/firewall-config b/src/firewall-config +index 02bffabf457c..223c0ff6d27d 100755 +--- a/src/firewall-config ++++ b/src/firewall-config +@@ -1368,7 +1368,7 @@ class FirewallConfig(object): + # connect + + self.connections = { } +- self.connections_uuid = { } ++ self.connections_name = { } + + if nm_is_imported(): + self.fw.bus.add_signal_receiver( +@@ -1428,11 +1428,11 @@ class FirewallConfig(object): + self.fw.changeZoneOfInterface(editor.get_zone(), interface) + del self.zone_interface_editors[interface] + +- def change_zone_connection_editor(self, item, connection, zone): ++ def change_zone_connection_editor(self, item, connection, connection_name, zone): + if connection in self.zone_connection_editors: + return self.zone_connection_editors[connection].present() + +- editor = ZoneConnectionEditor(self.fw, connection, zone) ++ editor = ZoneConnectionEditor(self.fw, connection, connection_name, zone) + editor.set_icon(self.icon) + editor.set_position(Gtk.WindowPosition.CENTER_ON_PARENT) + editor.set_transient_for(self.mainWindow) +@@ -1557,14 +1557,14 @@ class FirewallConfig(object): + self.update_active_zones() + + self.connections.clear() +- self.connections_uuid.clear() ++ self.connections_name.clear() + + # do not use NMClient could result in python core dump + + if nm_is_imported(): + try: +- nm_get_connections(self.connections, self.connections_uuid) +- except Exception as msg: ++ nm_get_connections(self.connections, self.connections_name) ++ except Exception: + text = _("Failed to get connections from NetworkManager") + self._warning(text) + +@@ -1572,12 +1572,14 @@ class FirewallConfig(object): + while iter: + interface = self.interfaceStore.get_value(iter, 0) + if interface in self.connections: +- zone = nm_get_zone_of_connection(self.connections[interface]) ++ connection = self.connections[interface] ++ connection_name = self.connections_name[connection] ++ zone = nm_get_zone_of_connection(connection) + if zone == "": + comment = self.default_zone_used_by_label % \ +- self.connections[interface] ++ connection_name + else: +- comment = self.used_by_label % self.connections[interface] ++ comment = self.used_by_label % connection_name + self.interfaceStore.set_value(iter, 1, comment) + iter = self.interfaceStore.iter_next(iter) + self.change_interface_selection_cb(self.interfaceView.get_selection()) +@@ -2427,37 +2429,38 @@ class FirewallConfig(object): + # add NM controlled entries + for connection in sorted(connections): + [ zone, _interfaces ] = connections[connection] ++ connection_name = self.connections_name[connection] + + item = Gtk.MenuItem.new() + hbox = Gtk.Box(orientation=Gtk.Orientation.HORIZONTAL, spacing=6) + label = Gtk.Label() + if zone == "": + label.set_markup("%s (%s)\n%s: %s" % \ +- (connection, ",".join(_interfaces), ++ (connection_name, ",".join(_interfaces), + escape(_("Default Zone")), self.default_zone)) + else: + label.set_markup("%s (%s)\n%s: %s" % \ +- (connection, ",".join(_interfaces), ++ (connection_name, ",".join(_interfaces), + escape(_("Zone")), zone)) + label.set_alignment(0, 0.5) + label.set_padding(12, 0) + hbox.pack_start(label, True, True, 0) + item.add(hbox) +- item.connect("activate", self.change_zone_connection_editor, connection, zone) ++ item.connect("activate", self.change_zone_connection_editor, connection, connection_name, zone) + self.left_menu.append(item) + + if zone == "": + self.bindingsStore.append( + self.connectionsIter, + [ "%s (%s)\n%s" % ( +- connection, ",".join(_interfaces), ++ connection_name, ",".join(_interfaces), + _("Default Zone: %s") % self.default_zone), + connection, zone ]) + else: + self.bindingsStore.append( + self.connectionsIter, + [ "%s (%s)\n%s" % ( +- connection, ",".join(_interfaces), ++ connection_name, ",".join(_interfaces), + _("Zone: %s") % zone), + connection, zone ]) + +@@ -2683,7 +2686,7 @@ class FirewallConfig(object): + zone = self.bindingsStore.get_value(iter, 2) + + if self.bindingsStore.get_value(parent_iter, 0) == _("Connections"): +- self.change_zone_connection_editor(None, item, zone) ++ self.change_zone_connection_editor(None, item, self.connections_name[item], zone) + elif self.bindingsStore.get_value(parent_iter, 0) == _("Interfaces"): + self.change_zone_interface_editor(None, item, zone) + elif self.bindingsStore.get_value(parent_iter, 0) == _("Sources"): +@@ -3894,9 +3897,10 @@ class FirewallConfig(object): + interface = self.interfaceStore.get_value(iter, 0) + if interface in self.connections: + connection = self.connections[interface] ++ connection_name = self.connections_name[connection] + if selected_zone == self.default_zone: + selected_zone = nm_get_zone_of_connection(connection) +- editor = ZoneConnectionEditor(self.fw, connection, selected_zone) ++ editor = ZoneConnectionEditor(self.fw, connection, connection_name, selected_zone) + editor.set_icon(self.icon) + editor.set_position(Gtk.WindowPosition.CENTER_ON_PARENT) + editor.set_transient_for(self.mainWindow) +@@ -3905,9 +3909,9 @@ class FirewallConfig(object): + result = editor.run() + except Exception: + text = _("Failed to set zone {zone} " +- "for connection {connection}") ++ "for connection {connection_name}") + self._warning(text.format(zone=editor.get_zone(), +- connection=editor.connection)) ++ connection_name=editor.connection_name)) + editor.hide() + else: + self.add_edit_interface(False) +@@ -8115,11 +8119,12 @@ class ZoneInterfaceEditor(Gtk.Dialog): + self.fw.changeZoneOfInterface(self.get_zone(), self.interface) + + class ZoneConnectionEditor(ZoneInterfaceEditor): +- def __init__(self, fw, connection, zone): ++ def __init__(self, fw, connection, connection_name, zone): + self.fw = fw + self.connection = connection ++ self.connection_name = connection_name + self.zone = None +- self.title = _("Select zone for connection '%s'") % self.connection ++ self.title = _("Select zone for connection '%s'") % self.connection_name + + Gtk.Dialog.__init__(self, self.title) + self.create_ui(zone) +diff --git a/src/firewall/core/fw_nm.py b/src/firewall/core/fw_nm.py +index 76901cee2adf..d21cc25feb8b 100644 +--- a/src/firewall/core/fw_nm.py ++++ b/src/firewall/core/fw_nm.py +@@ -73,7 +73,7 @@ def nm_get_zone_of_connection(connection): + """ + check_nm_imported() + +- con = nm_get_client().get_connection_by_id(connection) ++ con = nm_get_client().get_connection_by_uuid(connection) + if con is None: + return False + +@@ -94,7 +94,7 @@ def nm_set_zone_of_connection(zone, connection): + """ + check_nm_imported() + +- con = nm_get_client().get_connection_by_id(connection) ++ con = nm_get_client().get_connection_by_uuid(connection) + if con is None: + return False + +@@ -107,14 +107,14 @@ def nm_set_zone_of_connection(zone, connection): + setting_con.set_property("zone", zone) + return con.commit_changes(True, None) + +-def nm_get_connections(connections, connections_uuid): ++def nm_get_connections(connections, connections_name): + """Get active connections from NM + @param connections return dict +- @param connections_uuid return dict ++ @param connections_name return dict + """ + + connections.clear() +- connections_uuid.clear() ++ connections_name.clear() + + check_nm_imported() + +@@ -129,9 +129,9 @@ def nm_get_connections(connections, connections_uuid): + uuid = active_con.get_uuid() + devices = active_con.get_devices() + +- connections_uuid[name] = uuid ++ connections_name[uuid] = name + for dev in devices: +- connections[dev.get_iface()] = name ++ connections[dev.get_iface()] = uuid + + def nm_get_connection_of_interface(interface): + """Get connection from NM that is using the interface +@@ -148,7 +148,7 @@ def nm_get_connection_of_interface(interface): + if active_con is None: + return None + +- return active_con.get_id() ++ return active_con.get_uuid() + + def nm_get_bus_name(): + if not _nm_imported: +-- +2.16.3 + diff --git a/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-ignore-generated-connections.patch b/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-ignore-generated-connections.patch new file mode 100644 index 0000000..f62eb60 --- /dev/null +++ b/SOURCES/firewalld-0.6.1-firewall.core.fw_nm-ignore-generated-connections.patch @@ -0,0 +1,37 @@ +From a3e6d2c48a1535b56bc5f28094818f10f93bf352 Mon Sep 17 00:00:00 2001 +From: Lubomir Rintel +Date: Mon, 16 Jul 2018 17:43:25 +0200 +Subject: [PATCH 3/3] firewall.core.fw_nm: ignore generated connections + +If a connection is generated by NetworkManager, changing it persists it and +makes the device managed by NetworkManager. + +(cherry picked from commit a102dde5d9430d503767cbface3e3b610134bdb6) +--- + src/firewall/core/fw_nm.py | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +diff --git a/src/firewall/core/fw_nm.py b/src/firewall/core/fw_nm.py +index d21cc25feb8b..0ed19248a79f 100644 +--- a/src/firewall/core/fw_nm.py ++++ b/src/firewall/core/fw_nm.py +@@ -148,6 +148,16 @@ def nm_get_connection_of_interface(interface): + if active_con is None: + return None + ++ try: ++ con = active_con.get_connection() ++ if con.get_flags() & NM.SettingsConnectionFlags.NM_GENERATED: ++ return None ++ except AttributeError: ++ # Prior to NetworkManager 1.12, we can only guess ++ # that a connection was generated. ++ if con.get_unsaved(): ++ return None ++ + return active_con.get_uuid() + + def nm_get_bus_name(): +-- +2.16.3 + diff --git a/SPECS/firewalld.spec b/SPECS/firewalld.spec index 233b307..d9cf889 100644 --- a/SPECS/firewalld.spec +++ b/SPECS/firewalld.spec @@ -8,7 +8,7 @@ Summary: A firewall daemon with D-Bus interface providing a dynamic firewall Name: firewalld Version: 0.4.4.4 -Release: 14%{?dist} +Release: 15%{?dist} URL: http://www.firewalld.org License: GPLv2+ Source0: https://github.com/t-woerner/firewalld/archive/v%{version}.tar.gz#/%{name}-%{version}.tar.gz @@ -40,6 +40,9 @@ Patch25: firewalld-0.4.4.6-firewall-offline-cmd-Don-t-require-root-for-help-out. Patch26: firewalld-0.4.4.7-Fix-and-improve-firewalld-sysctls.conf.patch Patch27: firewalld-0.4.4.7-firewalld-also-reload-dbus-config-interface-for-glob.patch Patch28: firewalld-0.4.4.7-services-high-availability-Add-port-9929.patch +Patch29: firewalld-0.6.1-firewall.core.fw_nm-avoid-iterating-NM-devices-conne.patch +Patch30: firewalld-0.6.1-firewall.core.fw_nm-identify-the-connections-by-uuid.patch +Patch31: firewalld-0.6.1-firewall.core.fw_nm-ignore-generated-connections.patch BuildArch: noarch BuildRequires: desktop-file-utils @@ -181,6 +184,9 @@ firewalld. %patch26 -p1 -b .Fix-and-improve-firewalld-sysctls.conf %patch27 -p1 -b .firewalld-also-reload-dbus-config-interface-for-glob %patch28 -p1 +%patch29 -p1 +%patch30 -p1 +%patch31 -p1 ./autogen.sh %if 0%{?with_python3} @@ -376,6 +382,9 @@ fi %{_mandir}/man1/firewall-config*.1* %changelog +* Fri Aug 10 2018 Eric Garver - 0.4.4.4-15 +- backport patches to avoid NM for generated connections + * Tue Dec 12 2017 Eric Garver - 0.4.4.4-14 - services/high-availability: Add port 9929 (RHBZ#1486143)