Beispiel #1
0
def port_unbind(endpoint_id, neutron_port):
    """Unbinds the Neutron port from the network interface on the host.

    :param endpoint_id: the ID of the Docker container as string
    :param neutron_port: a port dictionary returned from python-neutronclient
    :returns: the tuple of stdout and stderr returned by processutils.execute
              invoked with the executable script for unbinding
    :raises: processutils.ProcessExecutionError, pyroute2.NetlinkError
    """

    vif_type = neutron_port.get(constants.VIF_TYPE_KEY,
                                constants.FALLBACK_VIF_TYPE)
    vif_details = lib_utils.string_mappings(neutron_port.get(
                                            constants.VIF_DETAILS_KEY))
    unbinding_exec_path = os.path.join(cfg.CONF.bindir, vif_type)

    port_id = neutron_port['id']
    ifname, _ = utils.get_veth_pair_names(port_id)

    mac_address = neutron_port['mac_address']
    network_id = neutron_port['network_id']
    stdout, stderr = processutils.execute(
        unbinding_exec_path, constants.UNBINDING_SUBCOMMAND, port_id, ifname,
        endpoint_id, mac_address, vif_details, network_id, run_as_root=True)
    try:
        utils.remove_device(ifname)
    except pyroute2.NetlinkError:
        raise exceptions.VethDeletionFailure(
            'Deleting the veth pair failed.')
    return (stdout, stderr)
Beispiel #2
0
def port_bind(endpoint_id, port, subnets, network=None,
              vm_port=None, segmentation_id=None):
    """Binds the Neutron port to the network interface on the host.

    :param endpoint_id:   the ID of the endpoint as string
    :param port:         the container Neutron port dictionary as returned by
                         python-neutronclient
    :param subnets:      an iterable of all the Neutron subnets which the
                         endpoint is trying to join
    :param network:      the Neutron network which the endpoint is trying to
                         join
    :param vm_port:      the Nova instance port dictionary, as returned by
                         python-neutronclient. Container is running inside this
                         instance (either ipvlan/macvlan or a subport)
    :param segmentation_id: ID of the segment for container traffic isolation)
    :returns: the tuple of the names of the veth pair and the tuple of stdout
              and stderr returned by processutils.execute invoked with the
              executable script for binding
    :raises: kuryr.common.exceptions.VethCreationFailure,
             processutils.ProcessExecutionError
    """
    ip = utils.get_ipdb()
    port_id = port['id']
    _, devname = utils.get_veth_pair_names(port_id)
    link_iface = nested.get_link_iface(vm_port)
    with ip.create(ifname=devname, kind=KIND,
                   link=ip.interfaces[link_iface],
                   address=port.get(utils.MAC_ADDRESS_KEY),
                   vlan_id=segmentation_id) as container_iface:
        utils._configure_container_iface(
            container_iface, subnets,
            fixed_ips=port.get(utils.FIXED_IP_KEY))

    return None, devname, ('', None)
Beispiel #3
0
def port_unbind(endpoint_id, neutron_port, **kwargs):
    """Unbinds the Neutron port from the network interface on the host.

    :param endpoint_id: the ID of the Docker container as string
    :param neutron_port: a port dictionary returned from python-neutronclient
    :param kwargs:       Additional driver-specific arguments
    :returns: the tuple of stdout and stderr returned by processutils.execute
              invoked with the executable script for unbinding
    :raises: processutils.ProcessExecutionError, pyroute2.NetlinkError
    """

    vif_type = neutron_port.get(constants.VIF_TYPE_KEY,
                                constants.FALLBACK_VIF_TYPE)
    vif_details = lib_utils.string_mappings(neutron_port.get(
                                            constants.VIF_DETAILS_KEY))
    unbinding_exec_path = os.path.join(cfg.CONF.bindir, vif_type)

    port_id = neutron_port['id']
    ifname, _ = utils.get_veth_pair_names(port_id)

    mac_address = neutron_port['mac_address']
    network_id = neutron_port['network_id']
    stdout, stderr = processutils.execute(
        unbinding_exec_path, constants.UNBINDING_SUBCOMMAND, port_id, ifname,
        endpoint_id, mac_address, vif_details, network_id, run_as_root=True)
    try:
        utils.remove_device(ifname)
    except pyroute2.NetlinkError:
        raise exceptions.VethDeletionFailure(
            'Deleting the veth pair failed.')
    return (stdout, stderr)
Beispiel #4
0
    def get_container_iface_name(self, neutron_port_id):
        """Returns interface name of a container in the default namespace.

        :param neutron_port_id: The ID of a neutron port as string
        :returns: interface name as string.
        """
        _, container_iface_name = utils.get_veth_pair_names(neutron_port_id)
        return container_iface_name
Beispiel #5
0
    def get_container_iface_name(self, neutron_port):
        """Returns interface name of a container in the default namespace.

        :param neutron_port_id: The neutron port
        :returns: interface name as string
        """
        _, container_iface_name = utils.get_veth_pair_names(neutron_port['id'])
        return container_iface_name
Beispiel #6
0
def _get_vif_name(neutron_port):
    """Gets a VIF device name for port.

    :param neutron_port: dict containing port information as returned by
                         neutron client's 'show_port'
    """

    vif_name, _ = kl_utils.get_veth_pair_names(neutron_port['id'])
    return vif_name
Beispiel #7
0
def port_bind(endpoint_id, port, subnets, network=None, vm_port=None,
              segmentation_id=None, **kwargs):
    """Binds the Neutron port to the network interface on the host.

    :param endpoint_id:   the ID of the endpoint as string
    :param port:         the container Neutron port dictionary as returned by
                         python-neutronclient
    :param subnets:      an iterable of all the Neutron subnets which the
                         endpoint is trying to join
    :param network:      the Neutron network which the endpoint is trying to
                         join
    :param vm_port:      the Nova instance port dictionary, as returned by
                         python-neutronclient. Container port under binding is
                         running inside this instance (either ipvlan/macvlan or
                         a subport)
    :param segmentation_id: ID of the segment for container traffic isolation)
    :param kwargs:       Additional driver-specific arguments
    :returns: the tuple of the names of the veth pair and the tuple of stdout
              and stderr returned by processutils.execute invoked with the
              executable script for binding
    :raises: kuryr.common.exceptions.VethCreationFailure,
             processutils.ProcessExecutionError
    """
    ip = utils.get_ipdb()
    port_id = port['id']
    host_ifname, container_ifname = utils.get_veth_pair_names(port_id)
    mtu = utils.get_mtu_from_network(network)

    try:
        with ip.create(ifname=host_ifname, kind=KIND,
                       reuse=True, peer=container_ifname) as host_veth:
            if not utils.is_up(host_veth):
                host_veth.up()
        with ip.interfaces[container_ifname] as container_veth:
            utils._configure_container_iface(
                container_veth, subnets,
                fixed_ips=port.get(utils.FIXED_IP_KEY),
                mtu=mtu, hwaddr=port[utils.MAC_ADDRESS_KEY].lower())
    except pyroute2.CreateException:
        raise exceptions.VethCreationFailure(
            'Virtual device creation failed.')
    except pyroute2.CommitException:
        raise exceptions.VethCreationFailure(
            'Could not configure the container virtual device networking.')

    try:
        stdout, stderr = _configure_host_iface(
            host_ifname, endpoint_id, port_id,
            port['network_id'], port.get('project_id') or port['tenant_id'],
            port[utils.MAC_ADDRESS_KEY],
            kind=port.get(constants.VIF_TYPE_KEY),
            details=port.get(constants.VIF_DETAILS_KEY))
    except Exception:
        with excutils.save_and_reraise_exception():
            utils.remove_device(host_ifname)

    return host_ifname, container_ifname, (stdout, stderr)
Beispiel #8
0
def port_bind(endpoint_id, port, subnets, network=None, vm_port=None,
              segmentation_id=None):
    """Binds the Neutron port to the network interface on the host.

    :param endpoint_id:   the ID of the endpoint as string
    :param port:         the container Neutron port dictionary as returned by
                         python-neutronclient
    :param subnets:      an iterable of all the Neutron subnets which the
                         endpoint is trying to join
    :param network:      the Neutron network which the endpoint is trying to
                         join
    :param vm_port:      the Nova instance dictionary, as returned by
                         python-neutronclient. Container port under binding is
                         running inside this instance (either ipvlan/macvlan or
                         a subport)
    :param segmentation_id: ID of the segment for container traffic isolation)
    :returns: the tuple of the names of the veth pair and the tuple of stdout
              and stderr returned by processutils.execute invoked with the
              executable script for binding
    :raises: kuryr.common.exceptions.VethCreationFailure,
             processutils.ProcessExecutionError
    """
    ip = utils.get_ipdb()
    port_id = port['id']
    host_ifname, container_ifname = utils.get_veth_pair_names(port_id)
    mtu = utils.get_mtu_from_network(network)

    try:
        with ip.create(ifname=host_ifname, kind=KIND,
                       reuse=True, peer=container_ifname) as host_veth:
            if not utils.is_up(host_veth):
                host_veth.up()
        with ip.interfaces[container_ifname] as container_veth:
            utils._configure_container_iface(
                container_veth, subnets,
                fixed_ips=port.get(utils.FIXED_IP_KEY),
                mtu=mtu, hwaddr=port[utils.MAC_ADDRESS_KEY].lower())
    except pyroute2.CreateException:
        raise exceptions.VethCreationFailure(
            'Virtual device creation failed.')
    except pyroute2.CommitException:
        raise exceptions.VethCreationFailure(
            'Could not configure the container virtual device networking.')

    try:
        stdout, stderr = _configure_host_iface(
            host_ifname, endpoint_id, port_id,
            port['network_id'], port.get('project_id') or port['tenant_id'],
            port[utils.MAC_ADDRESS_KEY],
            kind=port.get(constants.VIF_TYPE_KEY),
            details=port.get(constants.VIF_DETAILS_KEY))
    except Exception:
        with excutils.save_and_reraise_exception():
            utils.remove_device(host_ifname)

    return host_ifname, container_ifname, (stdout, stderr)
Beispiel #9
0
    def test_get_veth_pair_names(self):
        fake_neutron_port_id = uuidutils.generate_uuid()
        generated_ifname, generated_peer = utils.get_veth_pair_names(
            fake_neutron_port_id)

        namelen = constants.NIC_NAME_LEN
        ifname_postlen = namelen - len(constants.VETH_PREFIX)
        peer_postlen = namelen - len(constants.CONTAINER_VETH_PREFIX)

        self.assertEqual(namelen, len(generated_ifname))
        self.assertEqual(namelen, len(generated_peer))
        self.assertIn(constants.VETH_PREFIX, generated_ifname)
        self.assertIn(constants.CONTAINER_VETH_PREFIX, generated_peer)
        self.assertIn(fake_neutron_port_id[:ifname_postlen], generated_ifname)
        self.assertIn(fake_neutron_port_id[:peer_postlen], generated_peer)
Beispiel #10
0
def _get_vif_name(neutron_port):
    """Gets a VIF device name for port.

    :param neutron_port: dict containing port information as returned by
                         neutron client's 'show_port', or an port object
                         returned by openstack client.
    """

    try:
        port_id = neutron_port['id']
    except TypeError:
        port_id = neutron_port.id

    vif_name, _ = kl_utils.get_veth_pair_names(port_id)
    return vif_name
Beispiel #11
0
    def test_get_veth_pair_names(self):
        fake_neutron_port_id = uuidutils.generate_uuid()
        generated_ifname, generated_peer = utils.get_veth_pair_names(
            fake_neutron_port_id)

        namelen = constants.NIC_NAME_LEN
        ifname_postlen = namelen - len(constants.VETH_PREFIX)
        peer_postlen = namelen - len(constants.CONTAINER_VETH_PREFIX)

        self.assertEqual(namelen, len(generated_ifname))
        self.assertEqual(namelen, len(generated_peer))
        self.assertIn(constants.VETH_PREFIX, generated_ifname)
        self.assertIn(constants.CONTAINER_VETH_PREFIX, generated_peer)
        self.assertIn(fake_neutron_port_id[:ifname_postlen], generated_ifname)
        self.assertIn(fake_neutron_port_id[:peer_postlen], generated_peer)
Beispiel #12
0
def port_unbind(endpoint_id, neutron_port):
    """Unbinds the Neutron port from the network interface on the host.

    :param endpoint_id: the ID of the Docker container as string
    :param neutron_port: a port dictionary returned from python-neutronclient
    :returns: the tuple of stdout and stderr returned by processutils.execute
              invoked with the executable script for unbinding
    :raises: processutils.ProcessExecutionError, pyroute2.NetlinkError
    """
    port_id = neutron_port['id']
    _, devname = utils.get_veth_pair_names(port_id)

    try:
        utils.remove_device(devname)
    except pyroute2.NetlinkError:
        raise exceptions.VethDeletionFailure(
            'Failed to delete the container device.')

    return '', None
Beispiel #13
0
def port_bind(endpoint_id, port, subnets, network=None, nested_port=None):
    """Binds the Neutron port to the network interface on the host.

    :param endpoint_id:   the ID of the endpoint as string
    :param port:         the instance Neutron port dictionary as returned by
                         python-neutronclient
    :param subnets:      an iterable of all the Neutron subnets which the
                         endpoint is trying to join
    :param network:      the Neutron network which the endpoint is trying to
                         join
    :param nested_port:  the dictionary, as returned by python-neutronclient,
                         of the port that that is used when running inside
                         another instance (either ipvlan/macvlan or a subport)
    :returns: the tuple of the names of the veth pair and the tuple of stdout
              and stderr returned by processutils.execute invoked with the
              executable script for binding
    :raises: kuryr.common.exceptions.VethCreationFailure,
             processutils.ProcessExecutionError
    """
    ip = utils.get_ipdb()
    port_id = port['id']
    host_ifname, container_ifname = utils.get_veth_pair_names(port_id)
    if network is None:
        mtu = DEFAULT_NETWORK_MTU
    else:
        mtu = network.get('mtu', DEFAULT_NETWORK_MTU)

    try:
        with ip.create(ifname=host_ifname,
                       kind=KIND,
                       reuse=True,
                       peer=container_ifname) as host_veth:
            if not utils.is_up(host_veth):
                host_veth.up()
        with ip.interfaces[container_ifname] as container_veth:
            utils._configure_container_iface(
                container_veth,
                subnets,
                fixed_ips=port.get(utils.FIXED_IP_KEY),
                mtu=mtu,
                hwaddr=port[utils.MAC_ADDRESS_KEY].lower())
    except pyroute2.CreateException:
        raise exceptions.VethCreationFailure('Virtual device creation failed.')
    except pyroute2.CommitException:
        raise exceptions.VethCreationFailure(
            'Could not configure the container virtual device networking.')

    try:
        stdout, stderr = _configure_host_iface(
            host_ifname,
            endpoint_id,
            port_id,
            port['network_id'],
            port['tenant_id'],
            port[utils.MAC_ADDRESS_KEY],
            kind=port.get(VIF_TYPE_KEY),
            details=port.get(VIF_DETAILS_KEY))
    except Exception:
        with excutils.save_and_reraise_exception():
            utils.remove_device(host_ifname)

    return host_ifname, container_ifname, (stdout, stderr)