def test_ensure_device_is_ready(self): ip_lib_mock = mock.Mock() with mock.patch.object(ip_lib, 'IPDevice', return_value=ip_lib_mock): self.assertTrue(ip_lib.ensure_device_is_ready("eth0")) self.assertTrue(ip_lib_mock.link.set_up.called) ip_lib_mock.reset_mock() # device doesn't exists ip_lib_mock.link.set_up.side_effect = RuntimeError self.assertFalse(ip_lib.ensure_device_is_ready("eth0"))
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) self._update_dhcp_port(network, port) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, namespace=network.namespace): LOG.debug("Reusing existing device: %s.", interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=network.namespace) self.fill_dhcp_udp_checksums(namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet if not ipv6_utils.is_auto_address_subnet(subnet): net = netaddr.IPNetwork(subnet.cidr) ip_cidr = "%s/%s" % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) if self.conf.enable_isolated_metadata and self.conf.use_namespaces: ip_cidrs.append(METADATA_DEFAULT_CIDR) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) # ensure that the dhcp interface is first in the list if network.namespace is None: device = ip_lib.IPDevice(interface_name) device.route.pullup_route(interface_name, ip_version=constants.IP_VERSION_4) if self.conf.use_namespaces: self._set_default_route(network, interface_name) return interface_name
def ensure_bridge(self, bridge_name, interface=None, update_interface=True): """Create a bridge unless it already exists.""" # ensure_device_is_ready instead of device_exists is used here # because there are cases where the bridge exists but it's not UP, # for example: # 1) A greenthread was executing this function and had not yet executed # "ip link set bridge_name up" before eventlet switched to this # thread running the same function # 2) The Nova VIF driver was running concurrently and had just created # the bridge, but had not yet put it UP if not ip_lib.ensure_device_is_ready(bridge_name): LOG.debug( "Starting bridge %(bridge_name)s for subinterface " "%(interface)s", { 'bridge_name': bridge_name, 'interface': interface }) bridge_device = bridge_lib.BridgeDevice.addbr(bridge_name) if not bridge_device.setfd(0): return if not bridge_device.disable_stp(): return if bridge_device.link.set_up(): return LOG.debug( "Done starting bridge %(bridge_name)s for " "subinterface %(interface)s", { 'bridge_name': bridge_name, 'interface': interface }) else: bridge_device = bridge_lib.BridgeDevice(bridge_name) if not interface: return bridge_name # Update IP info if necessary if update_interface: self.update_interface_ip_details(bridge_name, interface) # Check if the interface is part of the bridge if not bridge_device.owns_interface(interface): # Check if the interface is attached to another bridge bridge = bridge_lib.BridgeDevice.get_interface_bridge(interface) if bridge: bridge.delif(interface) if not bridge_device.addif(interface): LOG.error("Unable to add %(interface)s to %(bridge_name)s", { 'interface': interface, 'bridge_name': bridge_name }) return return bridge_name
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) self._update_dhcp_port(network, port) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, namespace=network.namespace): LOG.debug("Reusing existing device: %s.", interface_name) else: try: self.driver.plug( network.id, port.id, interface_name, port.mac_address, namespace=network.namespace, mtu=network.get("mtu"), ) except Exception: with excutils.save_and_reraise_exception(): LOG.exception(_LE("Unable to plug DHCP port for " "network %s. Releasing port."), network.id) self.plugin.release_dhcp_port(network.id, port.device_id) self.fill_dhcp_udp_checksums(namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet if not ipv6_utils.is_auto_address_subnet(subnet): net = netaddr.IPNetwork(subnet.cidr) ip_cidr = "%s/%s" % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) if self.driver.use_gateway_ips: # For each DHCP-enabled subnet, add that subnet's gateway # IP address to the Linux device for the DHCP port. for subnet in network.subnets: if not subnet.enable_dhcp: continue gateway = subnet.gateway_ip if gateway: net = netaddr.IPNetwork(subnet.cidr) ip_cidrs.append("%s/%s" % (gateway, net.prefixlen)) if self.conf.enable_isolated_metadata: ip_cidrs.append(METADATA_DEFAULT_CIDR) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) self._set_default_route(network, interface_name) try: self._cleanup_stale_devices(network, port) except Exception: # catch everything as we don't want to fail because of # cleanup step LOG.error(_LE("Exception during stale dhcp device cleanup")) return interface_name
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, namespace=network.namespace): LOG.debug('Reusing existing device: %s.', interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=network.namespace) self.fill_dhcp_udp_checksums(namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet if not ipv6_utils.is_auto_address_subnet(subnet): net = netaddr.IPNetwork(subnet.cidr) ip_cidr = '%s/%s' % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) LOG.debug("ip_cidrs = %s" % ip_cidrs) if self.driver.subnet_ip_usage is constants.USE_GATEWAY_IPS: # For each DHCP-enabled subnet, add that subnet's gateway # IP address to the Linux device for the DHCP port.. for subnet in network.subnets: if not subnet.enable_dhcp: continue gateway = subnet.gateway_ip if gateway: net = netaddr.IPNetwork(subnet.cidr) ip_cidrs.append('%s/%s' % (gateway, net.prefixlen)) LOG.debug("ip_cidrs = %s" % ip_cidrs) if (self.conf.enable_isolated_metadata and self.conf.use_namespaces): ip_cidrs.append(METADATA_DEFAULT_CIDR) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) # ensure that the dhcp interface is first in the list if network.namespace is None: device = ip_lib.IPDevice(interface_name) device.route.pullup_route(interface_name, ip_version=constants.IP_VERSION_4) if self.conf.use_namespaces: self._set_default_route(network, interface_name) return interface_name
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) self._update_dhcp_port(network, port) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, namespace=network.namespace): LOG.debug('Reusing existing device: %s.', interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=network.namespace) self.fill_dhcp_udp_checksums(namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet if not ipv6_utils.is_auto_address_subnet(subnet): net = netaddr.IPNetwork(subnet.cidr) ip_cidr = '%s/%s' % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) if self.driver.use_gateway_ips: # For each DHCP-enabled subnet, add that subnet's gateway # IP address to the Linux device for the DHCP port. for subnet in network.subnets: if not subnet.enable_dhcp: continue gateway = subnet.gateway_ip if gateway: net = netaddr.IPNetwork(subnet.cidr) ip_cidrs.append('%s/%s' % (gateway, net.prefixlen)) if (self.conf.enable_isolated_metadata and self.conf.use_namespaces): ip_cidrs.append(METADATA_DEFAULT_CIDR) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) # ensure that the dhcp interface is first in the list if network.namespace is None: device = ip_lib.IPDevice(interface_name) device.route.pullup_route(interface_name, ip_version=constants.IP_VERSION_4) if self.conf.use_namespaces: self._set_default_route(network, interface_name) return interface_name
def ensure_bridge(self, bridge_name, interface=None, update_interface=True): """Create a bridge unless it already exists.""" # ensure_device_is_ready instead of device_exists is used here # because there are cases where the bridge exists but it's not UP, # for example: # 1) A greenthread was executing this function and had not yet executed # "ip link set bridge_name up" before eventlet switched to this # thread running the same function # 2) The Nova VIF driver was running concurrently and had just created # the bridge, but had not yet put it UP if not ip_lib.ensure_device_is_ready(bridge_name): LOG.debug("Starting bridge %(bridge_name)s for subinterface " "%(interface)s", {'bridge_name': bridge_name, 'interface': interface}) bridge_device = bridge_lib.BridgeDevice.addbr(bridge_name) if bridge_device.setfd(0): return if bridge_device.disable_stp(): return if bridge_device.link.set_up(): return LOG.debug("Done starting bridge %(bridge_name)s for " "subinterface %(interface)s", {'bridge_name': bridge_name, 'interface': interface}) else: bridge_device = bridge_lib.BridgeDevice(bridge_name) if not interface: return bridge_name # Update IP info if necessary if update_interface: self.update_interface_ip_details(bridge_name, interface) # Check if the interface is part of the bridge if not bridge_device.owns_interface(interface): try: # Check if the interface is not enslaved in another bridge bridge = bridge_lib.BridgeDevice.get_interface_bridge( interface) if bridge: bridge.delif(interface) bridge_device.addif(interface) except Exception as e: LOG.error("Unable to add %(interface)s to %(bridge_name)s" "! Exception: %(e)s", {'interface': interface, 'bridge_name': bridge_name, 'e': e}) return return bridge_name
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, self.root_helper, network.namespace): LOG.debug(_('Reusing existing device: %s.'), interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet net = netaddr.IPNetwork(subnet.cidr) ip_cidr = '%s/%s' % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) if (self.conf.enable_isolated_metadata and self.conf.use_namespaces): ip_cidrs.append(METADATA_DEFAULT_CIDR) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) # ensure that the dhcp interface is first in the list if network.namespace is None: device = ip_lib.IPDevice(interface_name, self.root_helper) device.route.pullup_route(interface_name) if self.conf.use_namespaces: self._set_default_route(network, interface_name) return interface_name
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, self.root_helper, network.namespace): LOG.debug('Reusing existing device: %s.', interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet net = netaddr.IPNetwork(subnet.cidr) ip_cidr = '%s/%s' % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) if (self.conf.enable_isolated_metadata and self.conf.use_namespaces): ip_cidrs.append(METADATA_DEFAULT_CIDR) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) # ensure that the dhcp interface is first in the list if network.namespace is None: device = ip_lib.IPDevice(interface_name, self.root_helper) device.route.pullup_route(interface_name) if self.conf.use_namespaces: self._set_default_route(network, interface_name) return interface_name
def setup(self, network): """Create and initialize a device for network's DHCP on this host.""" port = self.setup_dhcp_port(network) interface_name = self.get_interface_name(network, port) if ip_lib.ensure_device_is_ready(interface_name, self.root_helper, network.namespace): LOG.debug(_('Reusing existing device: %s.'), interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=network.namespace) ip_cidrs = [] for fixed_ip in port.fixed_ips: subnet = fixed_ip.subnet net = netaddr.IPNetwork(subnet.cidr) ip_cidr = '%s/%s' % (fixed_ip.ip_address, net.prefixlen) ip_cidrs.append(ip_cidr) if not self.driver.bridged(): # When the DHCP port and VM TAP interfaces are not # bridged, assign the subnet's gateway IP address to the # DHCP port. LOG.debug("ip_cidrs = %s" % ip_cidrs) for i, subnet in enumerate(network.subnets): if not subnet.enable_dhcp: continue gateway = subnet.gateway_ip for hr in subnet.host_routes: if hr.destination == "0.0.0.0/0": gateway = hr.nexthop if gateway: net = netaddr.IPNetwork(subnet.cidr) ip_cidrs.append('%s/%s' % (gateway, net.prefixlen)) if (self.driver.bridged() and self.conf.enable_isolated_metadata and self.conf.use_namespaces): ip_cidrs.append(METADATA_DEFAULT_CIDR) LOG.debug("ip_cidrs = %s" % ip_cidrs) self.driver.init_l3(interface_name, ip_cidrs, namespace=network.namespace) # ensure that the dhcp interface is first in the list if self.driver.bridged() and network.namespace is None: device = ip_lib.IPDevice(interface_name, self.root_helper) device.route.pullup_route(interface_name) if (self.driver.bridged() and self.conf.use_namespaces): self._set_default_route(network, port) return interface_name