def test_get_devices_malformed_line(self): self.execute.return_value = '\n'.join(LINK_SAMPLE + ['gibberish']) retval = ip_lib.IPWrapper('sudo').get_devices() self.assertEquals(retval, [ip_lib.IPDevice('lo'), ip_lib.IPDevice('eth0'), ip_lib.IPDevice('br-int'), ip_lib.IPDevice('gw-ddc717df-49')]) self.execute.assert_called_once_with('o', 'link', ('list',), 'sudo', None)
def _get_driver_by_device_name(self, device_name, namespace=None): device = ip_lib.IPDevice(device_name, self.conf.root_helper, namespace) mac_address = device.link.address ports = self.quantum.list_ports(mac_address=mac_address) if not 'ports' in ports or len(ports['ports']) < 1: raise Exception('No port for this device %s' % device_name) return self._get_driver_by_network_id(ports['ports'][0]['network_id'])
def init_l3(self, device_name, ip_cidrs, namespace=None): """Set the L3 settings for the interface using data from the port. ip_cidrs: list of 'X.X.X.X/YY' strings """ device = ip_lib.IPDevice(device_name, self.root_helper, namespace=namespace) previous = {} for address in device.addr.list(scope='global', filters=['permanent']): previous[address['cidr']] = address['ip_version'] # add new addresses for ip_cidr in ip_cidrs: net = netaddr.IPNetwork(ip_cidr) if ip_cidr in previous: del previous[ip_cidr] continue device.addr.add(net.version, ip_cidr, str(net.broadcast)) # clean up any old addresses for ip_cidr, ip_version in previous.items(): device.addr.delete(ip_version, ip_cidr)
def unplug(self, device_name, bridge=None, namespace=None, prefix=None): """Unplug the interface.""" device = ip_lib.IPDevice(device_name, self.root_helper, namespace) try: device.link.delete() LOG.debug(_("Unplugged interface '%s'"), device_name) except RuntimeError: LOG.error(_("Failed unplugging interface '%s'"), device_name)
def get_local_port_mac(self): """Retrieve the mac of the bridge's local port.""" address = ip_lib.IPDevice(self.br_name, self.root_helper).link.address if address: return address else: msg = _('Unable to determine mac address for %s') % self.br_name raise Exception(msg)
def _get_device(self, network): """Return DHCP ip_lib device for this host on the network.""" device_id = self.get_device_id(network) port = self.plugin.get_dhcp_port(network.id, device_id) interface_name = self.get_interface_name(network, port) namespace = NS_PREFIX + network.id return ip_lib.IPDevice(interface_name, self.root_helper, namespace)
def setup_physical_bridges(self, bridge_mappings): '''Setup the physical network bridges. Creates physical network bridges and links them to the integration bridge using veths. :param bridge_mappings: map physical network names to bridge names. ''' self.phys_brs = {} self.int_ofports = {} self.phys_ofports = {} ip_wrapper = ip_lib.IPWrapper(self.root_helper) for physical_network, bridge in bridge_mappings.iteritems(): LOG.info( _("Mapping physical network %(physical_network)s to " "bridge %(bridge)s"), { 'physical_network': physical_network, 'bridge': bridge }) # setup physical bridge if not ip_lib.device_exists(bridge, self.root_helper): LOG.error( _("Bridge %(bridge)s for physical network " "%(physical_network)s does not exist. Agent " "terminated!"), { 'physical_network': physical_network, 'bridge': bridge }) sys.exit(1) br = ovs_lib.OVSBridge(bridge, self.root_helper) br.remove_all_flows() br.add_flow(priority=1, actions="normal") self.phys_brs[physical_network] = br # create veth to patch physical bridge with integration bridge int_veth_name = constants.VETH_INTEGRATION_PREFIX + bridge self.int_br.delete_port(int_veth_name) phys_veth_name = constants.VETH_PHYSICAL_PREFIX + bridge br.delete_port(phys_veth_name) if ip_lib.device_exists(int_veth_name, self.root_helper): ip_lib.IPDevice(int_veth_name, self.root_helper).link.delete() int_veth, phys_veth = ip_wrapper.add_veth(int_veth_name, phys_veth_name) self.int_ofports[physical_network] = self.int_br.add_port(int_veth) self.phys_ofports[physical_network] = br.add_port(phys_veth) # block all untranslated traffic over veth between bridges self.int_br.add_flow(priority=2, in_port=self.int_ofports[physical_network], actions="drop") br.add_flow(priority=2, in_port=self.phys_ofports[physical_network], actions="drop") # enable veth to pass traffic int_veth.link.set_up() phys_veth.link.set_up()
def delete_quantum_ports(ports, root_helper): """Delete non-internal ports created by Quantum Non-internal OVS ports need to be removed manually. """ for port in ports: if ip_lib.device_exists(port): device = ip_lib.IPDevice(port, root_helper) device.link.delete() LOG.info(_("Delete %s"), port)
def unplug(self, device_name, bridge=None, namespace=None, prefix=None): """Unplug the interface.""" tap_name = self._get_tap_name(device_name, prefix) try: cmd = ['ivs-ctl', 'del-port', tap_name] utils.execute(cmd, self.root_helper) device = ip_lib.IPDevice(device_name, self.root_helper, namespace) device.link.delete() LOG.debug(_("Unplugged interface '%s'"), device_name) except RuntimeError: LOG.error(_("Failed unplugging interface '%s'"), device_name)
def floating_ip_removed(self, ri, ex_gw_port, floating_ip, fixed_ip): ip_cidr = str(floating_ip) + '/32' net = netaddr.IPNetwork(ip_cidr) interface_name = self.get_external_device_name(ex_gw_port['id']) device = ip_lib.IPDevice(interface_name, self.conf.root_helper, namespace=ri.ns_name()) device.addr.delete(net.version, ip_cidr) for chain, rule in self.floating_forward_rules(floating_ip, fixed_ip): ri.iptables_manager.ipv4['nat'].remove_rule(chain, rule) ri.iptables_manager.apply()
def unplug(self, device_name, bridge=None, namespace=None): """Unplug the interface.""" device = ip_lib.IPDevice(device_name, self.conf.root_helper, namespace) try: device.link.delete() LOG.debug(_("Unplugged interface '%s'") % device_name) except RuntimeError: LOG.error(_("Failed unplugging interface '%s'") % device_name) if namespace: ip = ip_lib.IPWrapper(self.conf.root_helper, namespace) ip.garbage_collect_namespace()
def floating_ip_added(self, ri, ex_gw_port, floating_ip, fixed_ip): ip_cidr = str(floating_ip) + '/32' interface_name = self.get_external_device_name(ex_gw_port['id']) device = ip_lib.IPDevice(interface_name, self.conf.root_helper, namespace=ri.ns_name()) if not ip_cidr in [addr['cidr'] for addr in device.addr.list()]: net = netaddr.IPNetwork(ip_cidr) device.addr.add(net.version, ip_cidr, str(net.broadcast)) self._send_gratuitous_arp_packet(ri, interface_name, floating_ip) for chain, rule in self.floating_forward_rules(floating_ip, fixed_ip): ri.iptables_manager.ipv4['nat'].add_rule(chain, rule) ri.iptables_manager.apply()
def _make_subnet_interface_ip_map(self): ip_dev = ip_lib.IPDevice(self.interface_name, self.root_helper, self.namespace) subnet_lookup = dict((netaddr.IPNetwork(subnet.cidr), subnet.id) for subnet in self.network.subnets) retval = {} for addr in ip_dev.addr.list(): ip_net = netaddr.IPNetwork(addr['cidr']) if ip_net in subnet_lookup: retval[subnet_lookup[ip_net]] = addr['cidr'].split('/')[0] return retval
def unplug(self, device_name, bridge=None, namespace=None, prefix=None): """Unplug the interface.""" if not bridge: bridge = self.conf.ovs_integration_bridge tap_name = self._get_tap_name(device_name, prefix) self.check_bridge_exists(bridge) ovs = ovs_lib.OVSBridge(bridge, self.conf.root_helper) try: ovs.delete_port(tap_name) device = ip_lib.IPDevice(device_name, self.conf.root_helper, namespace) device.link.delete() LOG.debug(_("Unplugged interface '%s'") % device_name) except RuntimeError: LOG.error(_("Failed unplugging interface '%s'") % device_name)
def setup(self, network, reuse_existing=False): """Create and initialize a device for network's DHCP on this host.""" device_id = self.get_device_id(network) port = self.plugin.get_dhcp_port(network.id, device_id) interface_name = self.get_interface_name(network, port) if self.conf.use_namespaces: namespace = NS_PREFIX + network.id else: namespace = None if ip_lib.device_exists(interface_name, self.conf.root_helper, namespace): if not reuse_existing: raise exceptions.PreexistingDeviceFailure( dev_name=interface_name) LOG.debug(_('Reusing existing device: %s.') % interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=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) self.driver.init_l3(interface_name, ip_cidrs, namespace=namespace) # ensure that the dhcp interface is first in the list if namespace is None: device = ip_lib.IPDevice(interface_name, self.conf.root_helper) device.route.pullup_route(interface_name) return interface_name
def _get_device_plugin_tag(self, device_name, namespace=None): device = ip_lib.IPDevice(device_name, self.conf.root_helper, namespace) return device.link.alias
def _set_device_plugin_tag(self, network_id, device_name, namespace=None): plugin_tag = self._get_flavor_by_network_id(network_id) device = ip_lib.IPDevice(device_name, self.conf.root_helper, namespace) device.link.set_alias(plugin_tag)
def test_str(self): self.assertEqual(str(ip_lib.IPDevice('tap0')), 'tap0')
def test_eq_other_is_none(self): dev1 = ip_lib.IPDevice('tap0', 'sudo', 'ns1') self.assertNotEqual(dev1, None)
def setup(self, network, reuse_existing=False): """Create and initialize a device for network's DHCP on this host.""" device_id = self.get_device_id(network) port = self.plugin.get_dhcp_port(network.id, device_id) interface_name = self.get_interface_name(network, port) if self.conf.use_namespaces: namespace = NS_PREFIX + network.id else: namespace = None if ip_lib.device_exists(interface_name, self.root_helper, namespace): if not reuse_existing: raise exceptions.PreexistingDeviceFailure( dev_name=interface_name) LOG.debug(_('Reusing existing device: %s.'), interface_name) else: self.driver.plug(network.id, port.id, interface_name, port.mac_address, namespace=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_IP) self.driver.init_l3(interface_name, ip_cidrs, namespace=namespace) # ensure that the dhcp interface is first in the list if namespace is None: device = ip_lib.IPDevice(interface_name, self.root_helper) device.route.pullup_route(interface_name) if self.conf.enable_metadata_network: meta_cidr = netaddr.IPNetwork(METADATA_DEFAULT_IP) metadata_subnets = [s for s in network.subnets if netaddr.IPNetwork(s.cidr) in meta_cidr] if metadata_subnets: # Add a gateway so that packets can be routed back to VMs device = ip_lib.IPDevice(interface_name, self.root_helper, namespace) # Only 1 subnet on metadata access network gateway_ip = metadata_subnets[0].gateway_ip device.route.add_gateway(gateway_ip) elif self.conf.use_namespaces: self._set_default_route(network) return interface_name
def test_eq_same_namespace(self): dev1 = ip_lib.IPDevice('tap0', 'ns1') dev2 = ip_lib.IPDevice('tap0', 'ns1') self.assertEqual(dev1, dev2)
def test_eq_diff_name(self): dev1 = ip_lib.IPDevice('tap0') dev2 = ip_lib.IPDevice('tap1') self.assertNotEqual(dev1, dev2)
def test_eq_diff_namespace(self): dev1 = ip_lib.IPDevice('tap0', 'sudo', 'ns1') dev2 = ip_lib.IPDevice('tap0', 'sudo', 'ns2') self.assertNotEqual(dev1, dev2)
def setUp(self): super(TunnelTest, self).setUp() cfg.CONF.set_override('rpc_backend', 'quantum.openstack.common.rpc.impl_fake') cfg.CONF.set_override('report_interval', 0, 'AGENT') self.mox = mox.Mox() self.addCleanup(self.mox.UnsetStubs) self.INT_BRIDGE = 'integration_bridge' self.TUN_BRIDGE = 'tunnel_bridge' self.MAP_TUN_BRIDGE = 'tunnel_bridge_mapping' self.NET_MAPPING = {'net1': self.MAP_TUN_BRIDGE} self.INT_OFPORT = 11111 self.TUN_OFPORT = 22222 self.MAP_TUN_OFPORT = 33333 self.inta = self.mox.CreateMock(ip_lib.IPDevice) self.intb = self.mox.CreateMock(ip_lib.IPDevice) self.inta.link = self.mox.CreateMock(ip_lib.IpLinkCommand) self.intb.link = self.mox.CreateMock(ip_lib.IpLinkCommand) self.mox.StubOutClassWithMocks(ovs_lib, 'OVSBridge') self.mock_int_bridge = ovs_lib.OVSBridge(self.INT_BRIDGE, 'sudo') self.mock_int_bridge.delete_port('patch-tun') self.mock_int_bridge.remove_all_flows() self.mock_int_bridge.add_flow(priority=1, actions='normal') self.mock_map_tun_bridge = ovs_lib.OVSBridge(self.MAP_TUN_BRIDGE, 'sudo') self.mock_map_tun_bridge.remove_all_flows() self.mock_map_tun_bridge.add_flow(priority=1, actions='normal') self.mock_int_bridge.delete_port('int-tunnel_bridge_mapping') self.mock_map_tun_bridge.delete_port('phy-tunnel_bridge_mapping') self.mock_int_bridge.add_port(self.inta) self.mock_map_tun_bridge.add_port(self.intb) self.inta.link.set_up() self.intb.link.set_up() self.mock_int_bridge.add_flow(priority=2, in_port=None, actions='drop') self.mock_map_tun_bridge.add_flow(priority=2, in_port=None, actions='drop') self.mock_tun_bridge = ovs_lib.OVSBridge(self.TUN_BRIDGE, 'sudo') self.mock_tun_bridge.reset_bridge() self.mock_int_bridge.add_patch_port( 'patch-tun', 'patch-int').AndReturn(self.TUN_OFPORT) self.mock_tun_bridge.add_patch_port( 'patch-int', 'patch-tun').AndReturn(self.INT_OFPORT) self.mock_tun_bridge.remove_all_flows() self.mock_tun_bridge.add_flow(priority=1, actions='drop') self.mox.StubOutWithMock(ip_lib, 'device_exists') ip_lib.device_exists('tunnel_bridge_mapping', 'sudo').AndReturn(True) ip_lib.device_exists('int-tunnel_bridge_mapping', 'sudo').AndReturn(True) self.mox.StubOutWithMock(ip_lib.IpLinkCommand, 'delete') ip_lib.IPDevice('int-tunnel_bridge_mapping').link.delete() self.mox.StubOutClassWithMocks(ip_lib, 'IPWrapper') ip_lib.IPWrapper('sudo').add_veth( 'int-tunnel_bridge_mapping', 'phy-tunnel_bridge_mapping').AndReturn([self.inta, self.intb]) self.mock_int_bridge.get_local_port_mac().AndReturn('000000000001')