def _should_add_connection(self, connection): """Should the connection be added ? :param connection: NetworkManager connection object :type connection: NMConnection :returns: tuple containing reply and message with reason :rtype: (bool, str) """ decline_reason = "" uuid = connection.get_uuid() iface = get_iface_from_connection(self.nm_client, uuid) connection_type = connection.get_connection_type() device_type = self.setting_types.get(connection_type, None) con_setting = connection.get_setting_connection() # Ignore read-only connections if con_setting and con_setting.get_read_only(): decline_reason = "read-only connection" # Ignore libvirt devices elif is_libvirt_device(iface or ""): decline_reason = "libvirt special device connection" # TODO we might want to remove the check if the devices are not renamed # to ibftX in dracut (BZ #1749331) # Ignore devices configured via iBFT elif is_ibft_configured_device(iface or ""): decline_reason = "configured from iBFT" # Ignore unsupported device types elif device_type not in supported_device_types: decline_reason = "unsupported type" # Ignore port connections elif device_type == NM.DeviceType.ETHERNET: if con_setting and con_setting.get_master(): decline_reason = "port connection" # Wireless settings are handled in scope of configuration of its device elif device_type == NM.DeviceType.WIFI: decline_reason = "wireless connection" reply = not decline_reason return reply, decline_reason
def _get_vlan_interface_name_from_connection(self, connection): """Get vlan interface name from vlan connection. If no interface name is specified in the connection settings, infer the value as <PARENT_IFACE>.<VLAN_ID> - same as NetworkManager. """ iface = connection.get_setting_connection().get_interface_name() if not iface: setting_vlan = connection.get_setting_vlan() if setting_vlan: vlanid = setting_vlan.get_id() parent = setting_vlan.get_parent() # if parent is specified by UUID if len(parent) == NM_CONNECTION_UUID_LENGTH: parent = get_iface_from_connection(self.nm_client, parent) if vlanid is not None and parent: iface = default_ks_vlan_interface_name(parent, vlanid) return iface
def get_kickstart_network_data(ifcfg, nm_client, network_data_class, root_path=""): """Get kickstart data from ifcfg object. :param ifcfg: ifcfg file object :type ifcfg: IfcfgFile :param nm_client: instance of NetworkManager client :type nm_client: NM.Client :param network_data_class: pykickstart network command data class :type: pykickstart BaseData :param root_path: optional root path for ifcfg files to be updated :type root_path: str :returns: network_data object corresponding to the ifcfg object :rtype: network_data_class object instance """ ifcfg.read() kwargs = {} # no network command for non-virtual device slaves if ifcfg.get("TYPE") not in ("Bond", "Team") and ifcfg.get("DEVICETYPE") != "Team": if ifcfg.get("MASTER") or ifcfg.get("TEAM_MASTER") or ifcfg.get( "BRIDGE"): return None # no support for wireless if ifcfg.get("TYPE") == "Wireless": return None # ipv4 and ipv6 if ifcfg.get("ONBOOT") and ifcfg.get("ONBOOT") == "no": kwargs["onboot"] = False if ifcfg.get('MTU') and ifcfg.get('MTU') != "0": kwargs["mtu"] = ifcfg.get('MTU') # ipv4 if not ifcfg.get('BOOTPROTO'): kwargs["noipv4"] = True else: if util.lowerASCII(ifcfg.get('BOOTPROTO')) == 'dhcp': kwargs["bootProto"] = "dhcp" if ifcfg.get('DHCPCLASS'): kwargs["dhcpclass"] = ifcfg.get('DHCPCLASS') elif ifcfg.get('IPADDR'): kwargs["bootProto"] = "static" kwargs["ip"] = ifcfg.get('IPADDR') netmask = ifcfg.get('NETMASK') prefix = ifcfg.get('PREFIX') if not netmask and prefix: netmask = prefix2netmask(int(prefix)) if netmask: kwargs["netmask"] = netmask # note that --gateway is common for ipv4 and ipv6 if ifcfg.get('GATEWAY'): kwargs["gateway"] = ifcfg.get('GATEWAY') elif ifcfg.get('IPADDR0'): kwargs["bootProto"] = "static" kwargs["ip"] = ifcfg.get('IPADDR0') prefix = ifcfg.get('PREFIX0') if prefix: netmask = prefix2netmask(int(prefix)) kwargs["netmask"] = netmask # note that --gateway is common for ipv4 and ipv6 if ifcfg.get('GATEWAY0'): kwargs["gateway"] = ifcfg.get('GATEWAY0') # ipv6 if not ifcfg.get('IPV6INIT') or ifcfg.get('IPV6INIT') == "no": kwargs["noipv6"] = True else: if ifcfg.get('IPV6_AUTOCONF') in ("yes", ""): kwargs["ipv6"] = "auto" else: if ifcfg.get('IPV6ADDR'): kwargs["ipv6"] = ifcfg.get('IPV6ADDR') if ifcfg.get('IPV6_DEFAULTGW') \ and ifcfg.get('IPV6_DEFAULTGW') != "::": kwargs["ipv6gateway"] = ifcfg.get('IPV6_DEFAULTGW') if ifcfg.get('DHCPV6C') == "yes": kwargs["ipv6"] = "dhcp" # ipv4 and ipv6 dnsline = '' for key in ifcfg.info.keys(): if util.upperASCII(key).startswith('DNS'): if dnsline == '': dnsline = ifcfg.get(key) else: dnsline += "," + ifcfg.get(key) if dnsline: kwargs["nameserver"] = dnsline if ifcfg.get("ETHTOOL_OPTS"): kwargs["ethtool"] = ifcfg.get("ETHTOOL_OPTS") if ifcfg.get("ESSID"): kwargs["essid"] = ifcfg.get("ESSID") # hostname if ifcfg.get("DHCP_HOSTNAME"): kwargs["hostname"] = ifcfg.get("DHCP_HOSTNAME") iface = ifcfg.get("DEVICE") if not iface: hwaddr = ifcfg.get("HWADDR") if hwaddr: iface = get_iface_from_hwaddr(nm_client, hwaddr) if iface: kwargs["device"] = iface # bonding # FIXME: dracut has only BOND_OPTS if ifcfg.get("BONDING_MASTER") == "yes" or ifcfg.get("TYPE") == "Bond": slaves = sorted( get_slaves_from_ifcfgs( nm_client, "MASTER", [ifcfg.get("DEVICE"), ifcfg.get("UUID")], root_path=root_path)) if slaves: kwargs["bondslaves"] = ",".join(iface for iface, uuid in slaves) bondopts = ifcfg.get("BONDING_OPTS") if bondopts: sep = "," if sep in bondopts: sep = ";" kwargs["bondopts"] = sep.join(bondopts.split()) # vlan if ifcfg.get("VLAN") == "yes" or ifcfg.get("TYPE") == "Vlan": physdev = ifcfg.get("PHYSDEV") if len(physdev) == NM_CONNECTION_UUID_LENGTH: physdev = get_iface_from_connection(nm_client, physdev) kwargs["device"] = physdev kwargs["vlanid"] = ifcfg.get("VLAN_ID") interface_name = ifcfg.get("DEVICE") default_name = default_ks_vlan_interface_name(kwargs["device"], kwargs["vlanid"]) if interface_name and interface_name != default_name: kwargs["interfacename"] = interface_name # bridging if ifcfg.get("TYPE") == "Bridge": slaves = sorted( get_slaves_from_ifcfgs( nm_client, "BRIDGE", [ifcfg.get("DEVICE"), ifcfg.get("UUID")], root_path=root_path)) if slaves: kwargs["bridgeslaves"] = ",".join(iface for iface, uuid in slaves) bridgeopts = ifcfg.get("BRIDGING_OPTS").replace('_', '-').split() if ifcfg.get("STP"): bridgeopts.append("%s=%s" % ("stp", ifcfg.get("STP"))) if ifcfg.get("DELAY"): bridgeopts.append("%s=%s" % ("forward-delay", ifcfg.get("DELAY"))) if bridgeopts: kwargs["bridgeopts"] = ",".join(bridgeopts) nd = network_data_class(**kwargs) # teaming if ifcfg.get("TYPE") == "Team" or ifcfg.get("DEVICETYPE") == "Team": slaves = sorted( get_slaves_from_ifcfgs( nm_client, "TEAM_MASTER", [ifcfg.get("DEVICE"), ifcfg.get("UUID")], root_path=root_path)) for iface, uuid in slaves: team_port_cfg = get_team_port_config_from_connection( nm_client, uuid) nd.teamslaves.append((iface, team_port_cfg)) teamconfig = get_team_config_from_connection(nm_client, ifcfg.get("UUID")) if teamconfig: nd.teamconfig = teamconfig return nd
def get_ifcfg_file_of_device(nm_client, device_name, device_hwaddr=None, root_path=""): """Get ifcfg file for the device specified by name. :param nm_client: instance of NetworkManager client :type nm_client: NM.Client :param device_name: name of the device :type device_name: str :param device_hwaddr: hardware address of the device :type device_hwaddr: str :param root_path: search in the filesystem specified by root path :type root_path: str :returns: ifcfg file object :rtype: IfcfgFile """ # hwaddr is supplementary (--bindto=mac) ifcfgs = [] for file_path in get_ifcfg_files_paths( os.path.normpath(root_path + IFCFG_DIR)): ifcfg = IfcfgFile(file_path) ifcfg.read() device_type = ifcfg.get("TYPE") or ifcfg.get("DEVICETYPE") if device_type == "Wireless": # TODO check ESSID against active ssid of the device pass elif device_type in ("Bond", "Team", "Bridge", "Infiniband"): if ifcfg.get("DEVICE") == device_name: ifcfgs.append(ifcfg) elif device_type == "Vlan": interface_name = ifcfg.get("DEVICE") if interface_name: if interface_name == device_name: ifcfgs.append(ifcfg) else: physdev = ifcfg.get("PHYSDEV") if len(physdev) == NM_CONNECTION_UUID_LENGTH: physdev = get_iface_from_connection(nm_client, physdev) vlanid = ifcfg.get("VLAN_ID") generated_dev_name = default_ks_vlan_interface_name( physdev, vlanid) if device_name == generated_dev_name: ifcfgs.append(ifcfg) elif device_type == "Ethernet": # Ignore slaves if ifcfg.get("MASTER") or ifcfg.get("TEAM_MASTER") or ifcfg.get( "BRIDGE"): continue device = ifcfg.get("DEVICE") hwaddr = ifcfg.get("HWADDR") if device: if device == device_name: ifcfgs.append(ifcfg) elif hwaddr: if device_hwaddr: if device_hwaddr.upper() == hwaddr.upper(): ifcfgs.append(ifcfg) else: iface = get_iface_from_hwaddr(nm_client, hwaddr) if iface == device_name: ifcfgs.append(ifcfg) elif is_s390(): # s390 setting generated in dracut with net.ifnames=0 # has neither DEVICE nor HWADDR (#1249750) if ifcfg.get("NAME") == device_name: ifcfgs.append(ifcfg) if len(ifcfgs) > 1: log.debug("Unexpected number of ifcfg files found for %s: %s", device_name, [ifcfg.path for ifcfg in ifcfgs]) if ifcfgs: return ifcfgs[0] else: log.debug("Ifcfg file for %s not found", device_name)
def add_connection(self, connection): """Add or update configuration for libnm connection object. Filters out unsupported or special devices. Only single configuration for given uuid is allowed. For devices without persistent connection it will just update the configuration. :param connection: NetworkManager conenction object :type connection: NMConnection :return: True if any configuration was added or modified, False otherwise :rtype: bool """ uuid = connection.get_uuid() existing_cfg = self.get_for_uuid(uuid) if existing_cfg: log.debug("add_connection: not adding %s: already existing: %s", uuid, existing_cfg) return False # Filter out special or unsupported devices should_add, reason = self._should_add_connection(connection) if not should_add: log.debug("add_connection: not adding %s: %s", uuid, reason) return False connection_type = connection.get_connection_type() device_type = self.setting_types.get(connection_type, None) iface = get_iface_from_connection(self.nm_client, uuid) # Require interface name for physical devices if device_type in supported_wired_device_types and not iface: log.debug( "add_connection: not adding %s: interface name is required for type %s", uuid, device_type) return False # Handle also vlan connections without interface-name specified if device_type == NM.DeviceType.VLAN: if not iface: iface = get_vlan_interface_name_from_connection( self.nm_client, connection) log.debug( "add_connection: interface name for vlan connection %s inferred: %s", uuid, iface) iface_cfg = self._find_existing_cfg_for_iface(iface) log.debug("add_connection: adding connection %s", uuid) # virtual devices if device_type in virtual_device_types: if iface_cfg: if not iface_cfg.connection_uuid: self.attach(iface_cfg, connection_uuid=uuid) return True else: # TODO check that the device shouldn't be reattached? log.debug( "add_connection: already have %s for device %s, adding another one", iface_cfg.connection_uuid, iface_cfg.device_name) self.add(connection_uuid=uuid, device_type=device_type) # physical devices else: if iface_cfg: if iface_cfg.connection_uuid: log.debug( "add_connection: already have %s for device %s, not adding %s", iface_cfg.connection_uuid, iface_cfg.device_name, uuid) return False else: self.attach(iface_cfg, connection_uuid=uuid) else: self.add(connection_uuid=uuid, device_type=device_type) return True
def get_kickstart_network_data(ifcfg, nm_client, network_data_class, root_path=""): """Get kickstart data from ifcfg object. :param ifcfg: ifcfg file object :type ifcfg: IfcfgFile :param nm_client: instance of NetworkManager client :type nm_client: NM.Client :param network_data_class: pykickstart network command data class :type: pykickstart BaseData :param root_path: optional root path for ifcfg files to be updated :type root_path: str :returns: network_data object corresponding to the ifcfg object :rtype: network_data_class object instance """ ifcfg.read() kwargs = {} # no network command for non-virtual device slaves if ifcfg.get("TYPE") not in ("Bond", "Team") and ifcfg.get("DEVICETYPE") != "Team": if ifcfg.get("MASTER") or ifcfg.get("TEAM_MASTER") or ifcfg.get("BRIDGE"): return None # no support for wireless if ifcfg.get("TYPE") == "Wireless": return None # ipv4 and ipv6 if ifcfg.get("ONBOOT") and ifcfg.get("ONBOOT") == "no": kwargs["onboot"] = False if ifcfg.get('MTU') and ifcfg.get('MTU') != "0": kwargs["mtu"] = ifcfg.get('MTU') # ipv4 if not ifcfg.get('BOOTPROTO'): kwargs["noipv4"] = True else: if util.lowerASCII(ifcfg.get('BOOTPROTO')) == 'dhcp': kwargs["bootProto"] = "dhcp" if ifcfg.get('DHCPCLASS'): kwargs["dhcpclass"] = ifcfg.get('DHCPCLASS') elif ifcfg.get('IPADDR'): kwargs["bootProto"] = "static" kwargs["ip"] = ifcfg.get('IPADDR') netmask = ifcfg.get('NETMASK') prefix = ifcfg.get('PREFIX') if not netmask and prefix: netmask = prefix2netmask(int(prefix)) if netmask: kwargs["netmask"] = netmask # note that --gateway is common for ipv4 and ipv6 if ifcfg.get('GATEWAY'): kwargs["gateway"] = ifcfg.get('GATEWAY') elif ifcfg.get('IPADDR0'): kwargs["bootProto"] = "static" kwargs["ip"] = ifcfg.get('IPADDR0') prefix = ifcfg.get('PREFIX0') if prefix: netmask = prefix2netmask(int(prefix)) kwargs["netmask"] = netmask # note that --gateway is common for ipv4 and ipv6 if ifcfg.get('GATEWAY0'): kwargs["gateway"] = ifcfg.get('GATEWAY0') # ipv6 if not ifcfg.get('IPV6INIT') or ifcfg.get('IPV6INIT') == "no": kwargs["noipv6"] = True else: if ifcfg.get('IPV6_AUTOCONF') in ("yes", ""): kwargs["ipv6"] = "auto" else: if ifcfg.get('IPV6ADDR'): kwargs["ipv6"] = ifcfg.get('IPV6ADDR') if ifcfg.get('IPV6_DEFAULTGW') \ and ifcfg.get('IPV6_DEFAULTGW') != "::": kwargs["ipv6gateway"] = ifcfg.get('IPV6_DEFAULTGW') if ifcfg.get('DHCPV6C') == "yes": kwargs["ipv6"] = "dhcp" # ipv4 and ipv6 dnsline = '' for key in ifcfg.info.keys(): if util.upperASCII(key).startswith('DNS'): if dnsline == '': dnsline = ifcfg.get(key) else: dnsline += "," + ifcfg.get(key) if dnsline: kwargs["nameserver"] = dnsline if ifcfg.get("ETHTOOL_OPTS"): kwargs["ethtool"] = ifcfg.get("ETHTOOL_OPTS") if ifcfg.get("ESSID"): kwargs["essid"] = ifcfg.get("ESSID") # hostname if ifcfg.get("DHCP_HOSTNAME"): kwargs["hostname"] = ifcfg.get("DHCP_HOSTNAME") iface = ifcfg.get("DEVICE") if not iface: hwaddr = ifcfg.get("HWADDR") if hwaddr: iface = get_iface_from_hwaddr(nm_client, hwaddr) if iface: kwargs["device"] = iface # bonding # FIXME: dracut has only BOND_OPTS if ifcfg.get("BONDING_MASTER") == "yes" or ifcfg.get("TYPE") == "Bond": slaves = sorted(get_slaves_from_ifcfgs(nm_client, "MASTER", [ifcfg.get("DEVICE"), ifcfg.get("UUID")], root_path=root_path)) if slaves: kwargs["bondslaves"] = ",".join(iface for iface, uuid in slaves) bondopts = ifcfg.get("BONDING_OPTS") if bondopts: sep = "," if sep in bondopts: sep = ";" kwargs["bondopts"] = sep.join(bondopts.split()) # vlan if ifcfg.get("VLAN") == "yes" or ifcfg.get("TYPE") == "Vlan": physdev = ifcfg.get("PHYSDEV") if len(physdev) == NM_CONNECTION_UUID_LENGTH: physdev = get_iface_from_connection(nm_client, physdev) kwargs["device"] = physdev kwargs["vlanid"] = ifcfg.get("VLAN_ID") interface_name = ifcfg.get("DEVICE") if interface_name and interface_name != default_ks_vlan_interface_name(kwargs["device"], kwargs["vlanid"]): kwargs["interfacename"] = interface_name # bridging if ifcfg.get("TYPE") == "Bridge": slaves = sorted(get_slaves_from_ifcfgs(nm_client, "BRIDGE", [ifcfg.get("DEVICE"), ifcfg.get("UUID")], root_path=root_path)) if slaves: kwargs["bridgeslaves"] = ",".join(iface for iface, uuid in slaves) bridgeopts = ifcfg.get("BRIDGING_OPTS").replace('_', '-').split() if ifcfg.get("STP"): bridgeopts.append("%s=%s" % ("stp", ifcfg.get("STP"))) if ifcfg.get("DELAY"): bridgeopts.append("%s=%s" % ("forward-delay", ifcfg.get("DELAY"))) if bridgeopts: kwargs["bridgeopts"] = ",".join(bridgeopts) nd = network_data_class(**kwargs) # teaming if ifcfg.get("TYPE") == "Team" or ifcfg.get("DEVICETYPE") == "Team": slaves = sorted(get_slaves_from_ifcfgs(nm_client, "TEAM_MASTER", [ifcfg.get("DEVICE"), ifcfg.get("UUID")], root_path=root_path)) for iface, uuid in slaves: team_port_cfg = get_team_port_config_from_connection(nm_client, uuid) nd.teamslaves.append((iface, team_port_cfg)) teamconfig = get_team_config_from_connection(nm_client, ifcfg.get("UUID")) if teamconfig: nd.teamconfig = teamconfig return nd
def get_ifcfg_file_of_device(nm_client, device_name, device_hwaddr=None, root_path=""): """Get ifcfg file for the device specified by name. :param nm_client: instance of NetworkManager client :type nm_client: NM.Client :param device_name: name of the device :type device_name: str :param hwaddr: hardware address of the device :type hwaddr: str :param root_path: search in the filesystem specified by root path :type root_path: str :returns: ifcfg file object :rtype: IfcfgFile """ # hwaddr is supplementary (--bindto=mac) ifcfgs = [] for file_path in get_ifcfg_files_paths(os.path.normpath(root_path + IFCFG_DIR)): ifcfg = IfcfgFile(file_path) ifcfg.read() device_type = ifcfg.get("TYPE") or ifcfg.get("DEVICETYPE") if device_type == "Wireless": # TODO check ESSID against active ssid of the device pass elif device_type in ("Bond", "Team", "Bridge", "Infiniband"): if ifcfg.get("DEVICE") == device_name: ifcfgs.append(ifcfg) elif device_type == "Vlan": interface_name = ifcfg.get("DEVICE") if interface_name: if interface_name == device_name: ifcfgs.append(ifcfg) else: physdev = ifcfg.get("PHYSDEV") if len(physdev) == NM_CONNECTION_UUID_LENGTH: physdev = get_iface_from_connection(nm_client, physdev) vlanid = ifcfg.get("VLAN_ID") generated_dev_name = default_ks_vlan_interface_name(physdev, vlanid) if device_name == generated_dev_name: ifcfgs.append(ifcfg) elif device_type == "Ethernet": # Ignore slaves if ifcfg.get("MASTER") or ifcfg.get("TEAM_MASTER") or ifcfg.get("BRIDGE"): continue device = ifcfg.get("DEVICE") hwaddr = ifcfg.get("HWADDR") if device: if device == device_name: ifcfgs.append(ifcfg) elif hwaddr: if device_hwaddr: if device_hwaddr.upper() == hwaddr.upper(): ifcfgs.append(ifcfg) else: iface = get_iface_from_hwaddr(nm_client, hwaddr) if iface == device_name: ifcfgs.append(ifcfg) elif is_s390(): # s390 setting generated in dracut with net.ifnames=0 # has neither DEVICE nor HWADDR (#1249750) if ifcfg.get("NAME") == device_name: ifcfgs.append(ifcfg) if len(ifcfgs) > 1: log.debug("Unexpected number of ifcfg files found for %s: %s", device_name, [ifcfg.path for ifcfg in ifcfgs]) if ifcfgs: return ifcfgs[0] else: log.debug("Ifcfg file for %s not found", device_name)