diff options
| author | Christian Breunig <christian@breunig.cc> | 2026-03-04 20:30:20 +0100 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2026-03-04 20:30:20 +0100 |
| commit | 53488d0ef8ded005e75f853b6ca05342c3c8725d (patch) | |
| tree | caef839f6bb5f49ad6607a438755ca7585f6267c | |
| parent | ddaae274187916b3a7932372ee8944ddce8c5423 (diff) | |
| parent | d340acd74270728743807b1db4124b0fddcceec4 (diff) | |
| download | vyos-1x-53488d0ef8ded005e75f853b6ca05342c3c8725d.tar.gz vyos-1x-53488d0ef8ded005e75f853b6ca05342c3c8725d.zip | |
Merge pull request #5026 from natali-rs1985/T8339
vpp: T8339: Cleanup vpp interfaces and kernel-interfaces after migration
| -rw-r--r-- | data/config-mode-dependencies/vyos-vpp.json | 36 | ||||
| -rw-r--r-- | interface-definitions/include/kernel-interface-tap.xml.i | 15 | ||||
| -rw-r--r-- | interface-definitions/include/kernel-interface-tun.xml.i | 15 | ||||
| -rw-r--r-- | interface-definitions/vpp.xml.in | 25 | ||||
| -rw-r--r-- | python/vyos/vpp/config_verify.py | 70 | ||||
| -rw-r--r-- | python/vyos/vpp/interface/__init__.py | 28 | ||||
| -rw-r--r-- | python/vyos/vpp/interface/ethernet.py | 53 | ||||
| -rw-r--r-- | python/vyos/vpp/interface/geneve.py | 90 | ||||
| -rw-r--r-- | python/vyos/vpp/interface/interface.py | 49 | ||||
| -rw-r--r-- | python/vyos/vpp/interface/wireguard.py | 55 | ||||
| -rw-r--r-- | python/vyos/vpp/utils.py | 43 | ||||
| -rwxr-xr-x | smoketest/scripts/cli/test_vpp.py | 167 | ||||
| -rwxr-xr-x | src/conf_mode/vpp.py | 18 | ||||
| -rw-r--r-- | src/conf_mode/vpp_interfaces_ethernet.py | 134 | ||||
| -rw-r--r-- | src/conf_mode/vpp_interfaces_geneve.py | 193 | ||||
| -rw-r--r-- | src/conf_mode/vpp_kernel-interfaces.py | 218 | ||||
| -rwxr-xr-x | src/op_mode/show_vpp_interfaces.py | 9 |
17 files changed, 34 insertions, 1184 deletions
diff --git a/data/config-mode-dependencies/vyos-vpp.json b/data/config-mode-dependencies/vyos-vpp.json index 12dd1efad..dd664a7c7 100644 --- a/data/config-mode-dependencies/vyos-vpp.json +++ b/data/config-mode-dependencies/vyos-vpp.json @@ -3,8 +3,6 @@ "ethernet": ["interfaces_ethernet"], "vpp_interfaces_bonding": ["vpp_interfaces_bonding"], "vpp_interfaces_bridge": ["vpp_interfaces_bridge"], - "vpp_interfaces_ethernet": ["vpp_interfaces_ethernet"], - "vpp_interfaces_geneve": ["vpp_interfaces_geneve"], "vpp_interfaces_gre": ["vpp_interfaces_gre"], "vpp_interfaces_ipip": ["vpp_interfaces_ipip"], "vpp_interfaces_loopback": ["vpp_interfaces_loopback"], @@ -14,7 +12,6 @@ "vpp_ipfix": ["vpp_ipfix"], "vpp_nat_nat44": ["vpp_nat_nat44"], "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"], "vpp_sflow": ["vpp_sflow"], "pppoe_server": ["service_pppoe-server"] }, @@ -24,56 +21,33 @@ "vpp_acl": ["vpp_acl"], "vpp_nat_nat44": ["vpp_nat_nat44"], "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_ipfix": ["vpp_ipfix"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] - }, - "vpp_interfaces_ethernet": { - "vpp_interfaces_xconnect": ["vpp_interfaces_xconnect"], - "vpp_acl": ["vpp_acl"], - "vpp_nat_nat44": ["vpp_nat_nat44"], - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] - }, - "vpp_interfaces_geneve": { - "vpp_interfaces_xconnect": ["vpp_interfaces_xconnect"], - "vpp_acl": ["vpp_acl"], - "vpp_nat_nat44": ["vpp_nat_nat44"], - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] + "vpp_ipfix": ["vpp_ipfix"] }, "vpp_interfaces_gre": { "vpp_interfaces_xconnect": ["vpp_interfaces_xconnect"], "vpp_interfaces_bridge": ["vpp_interfaces_bridge"], "vpp_acl": ["vpp_acl"], "vpp_nat_nat44": ["vpp_nat_nat44"], - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] + "vpp_nat_cgnat": ["vpp_nat_cgnat"] }, "vpp_interfaces_ipip": { "vpp_interfaces_xconnect": ["vpp_interfaces_xconnect"], "vpp_acl": ["vpp_acl"], "vpp_nat_nat44": ["vpp_nat_nat44"], - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] + "vpp_nat_cgnat": ["vpp_nat_cgnat"] }, "vpp_interfaces_loopback": { "vpp_interfaces_bridge": ["vpp_interfaces_bridge"], "vpp_acl": ["vpp_acl"], "vpp_nat_nat44": ["vpp_nat_nat44"], - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] + "vpp_nat_cgnat": ["vpp_nat_cgnat"] }, "vpp_interfaces_vxlan": { "vpp_interfaces_bridge": ["vpp_interfaces_bridge"], "vpp_interfaces_xconnect": ["vpp_interfaces_xconnect"], "vpp_acl": ["vpp_acl"], "vpp_nat_nat44": ["vpp_nat_nat44"], - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_kernel_interface": ["vpp_kernel-interfaces"] - }, - "vpp_kernel_interfaces": { - "vpp_nat_cgnat": ["vpp_nat_cgnat"], - "vpp_nat_nat44": ["vpp_nat_nat44"] + "vpp_nat_cgnat": ["vpp_nat_cgnat"] } } diff --git a/interface-definitions/include/kernel-interface-tap.xml.i b/interface-definitions/include/kernel-interface-tap.xml.i deleted file mode 100644 index 83399f1f4..000000000 --- a/interface-definitions/include/kernel-interface-tap.xml.i +++ /dev/null @@ -1,15 +0,0 @@ -<!-- include start from kernel-interface-tap.xml.i --> -<leafNode name="kernel-interface"> - <properties> - <help>Kernel interface name</help> - <valueHelp> - <format>vpptapN</format> - <description>Kernel interface name</description> - </valueHelp> - <constraint> - <regex>vpptap\d+</regex> - </constraint> - <constraintErrorMessage>Kernel interface must start with vpptapN</constraintErrorMessage> - </properties> -</leafNode> -<!-- include end --> diff --git a/interface-definitions/include/kernel-interface-tun.xml.i b/interface-definitions/include/kernel-interface-tun.xml.i deleted file mode 100644 index 3cbd5ab30..000000000 --- a/interface-definitions/include/kernel-interface-tun.xml.i +++ /dev/null @@ -1,15 +0,0 @@ -<!-- include start from kernel-interface-tun.xml.i --> -<leafNode name="kernel-interface"> - <properties> - <help>Kernel interface name</help> - <valueHelp> - <format>vpptunN</format> - <description>Kernel interface name</description> - </valueHelp> - <constraint> - <regex>vpptun\d+</regex> - </constraint> - <constraintErrorMessage>Kernel interface must start with vpptunN</constraintErrorMessage> - </properties> -</leafNode> -<!-- include end --> diff --git a/interface-definitions/vpp.xml.in b/interface-definitions/vpp.xml.in index ac27d39c4..9d484dbe9 100644 --- a/interface-definitions/vpp.xml.in +++ b/interface-definitions/vpp.xml.in @@ -1244,31 +1244,6 @@ </node> </children> </node> - <tagNode name="kernel-interfaces" owner="${vyos_conf_scripts_dir}/vpp_kernel-interfaces.py"> - <properties> - <help>VPP kernel interface settings</help> - <priority>328</priority> - <valueHelp> - <format>vpptapN</format> - <description>Kernel interface name</description> - </valueHelp> - <valueHelp> - <format>vpptunN</format> - <description>Kernel interface name</description> - </valueHelp> - <constraint> - <regex>vpp(tun|tap)\d+</regex> - </constraint> - <constraintErrorMessage>Kernel interface must start with vpp and include tun or tap N</constraintErrorMessage> - </properties> - <children> - #include <include/interface/address-ipv4-ipv6.xml.i> - #include <include/generic-description.xml.i> - #include <include/interface/disable.xml.i> - #include <include/interface/mtu-68-16000.xml.i> - #include <include/vpp/vif.xml.i> - </children> - </tagNode> </children> </node> </interfaceDefinition> diff --git a/python/vyos/vpp/config_verify.py b/python/vyos/vpp/config_verify.py index d5bb70899..6f1774b2f 100644 --- a/python/vyos/vpp/config_verify.py +++ b/python/vyos/vpp/config_verify.py @@ -27,76 +27,6 @@ from vyos.vpp.config_resource_checks.resource_defaults import default_resource_m from vyos.vpp.utils import human_memory_to_bytes, bytes_to_human_memory -def verify_vpp_remove_kernel_interface(config: dict): - """Common verify for removed kernel-interfaces. - Verify that removed kernel interface are not used in 'vpp kernel-interfaces'. - - Example: - delete vpp interfaces gre|vxlan <tag>X kernel-interface vpp-tunX - set vpp kernel-interface vpp-tunX - """ - if ( - 'remove' in config - and 'kernel_interface_removed' in config - and 'vpp_kernel_interfaces' in config - ): - removed_interfaces = config['kernel_interface_removed'] - used_interfaces = config['vpp_kernel_interfaces'] - - for interface in removed_interfaces: - if interface in used_interfaces: - raise ConfigError( - f'"{interface}" is still in use within "vpp kernel-interfaces". ' - 'Please remove it before proceeding.' - ) - - -def verify_vpp_change_kernel_interface(config: dict): - """Common verify for changed kernel-interface - - Example: - set vpp interfaces gre|vxlan <tag> kernel-interface vpp-tunX' - commit - set vpp interfaces gre|vxlan <tag> kernel-interface vpp-tunY' - commit - - check if we have kernel interface config 'vpp kernel-interface vpp-tunX' - """ - kernel_interface_removed = config.get('kernel_interface_removed', []) - vpp_kernel_interfaces = config.get('vpp_kernel_interfaces', {}) - - for interface in kernel_interface_removed: - if interface in vpp_kernel_interfaces: - raise ConfigError( - f'interface "{interface}" is still in use within "vpp kernel-interfaces". ' - f'Please remove it "vpp kernel-interface {interface}" before proceeding.' - ) - - -def verify_vpp_exists_kernel_interface(config: dict): - """Verify is a kernel-interface already created by another VPP LCP pair - - Example: - set vpp interfaces vxlan vxlan10 kernel-interface vpp-tun10' - commit - set vpp interfaces vxlan vxlan20 kernel-interface vpp-tun10' - commit - """ - kernel_interface = config.get('kernel_interface', '') - vpp_interface = config.get('ifname', '') - candidate_kernel_interfaces = config.get('candidate_kernel_interfaces', []) - - for candidate_kernel_iface in candidate_kernel_interfaces: - if ( - vpp_interface != candidate_kernel_iface[0] - and kernel_interface == candidate_kernel_iface[1] - ): - raise ConfigError( - f'Kernel interface "{kernel_interface}" is already configured for {candidate_kernel_iface[0]}. ' - 'Duplicates are not allowed.' - ) - - def verify_vpp_remove_xconnect_interface(config: dict): if not 'deleted' in config: return diff --git a/python/vyos/vpp/interface/__init__.py b/python/vyos/vpp/interface/__init__.py deleted file mode 100644 index 3f8ae7954..000000000 --- a/python/vyos/vpp/interface/__init__.py +++ /dev/null @@ -1,28 +0,0 @@ -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -from .ethernet import EthernetInterface -from .geneve import GeneveInterface -from .interface import Interface -from .wireguard import WireguardInterface - -__all__ = [ - 'EthernetInterface', - 'GeneveInterface', - 'Interface', - 'WireguardInterface', -] diff --git a/python/vyos/vpp/interface/ethernet.py b/python/vyos/vpp/interface/ethernet.py deleted file mode 100644 index 523211db8..000000000 --- a/python/vyos/vpp/interface/ethernet.py +++ /dev/null @@ -1,53 +0,0 @@ -# VyOS implementation of VPP Ethernet interface -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -from vyos.vpp import VPPControl - - -class EthernetInterface: - """Interface Ethernet""" - - def __init__(self, ifname, kernel_interface: str = ''): - self.instance = int(ifname.removeprefix('eth')) - self.ifname = ifname - self.kernel_interface = kernel_interface - self.vpp = VPPControl() - - def add(self): - pass - - def delete(self): - pass - - def kernel_add(self): - """Add LCP pair - Example: - from vyos.vpp.interface import EthernetInterface - a = EthernetInterface(ifname='eth0') - a.kernel_add() - """ - self.vpp.lcp_pair_add(self.ifname, self.kernel_interface) - - def kernel_delete(self): - """Delete LCP pair - Example: - from vyos.vpp.interface import EthernetInterface - a = EthernetInterface(ifname='eth0') - a.kernel_delete() - """ - self.vpp.lcp_pair_del(self.ifname, self.kernel_interface) diff --git a/python/vyos/vpp/interface/geneve.py b/python/vyos/vpp/interface/geneve.py deleted file mode 100644 index 2d6347f12..000000000 --- a/python/vyos/vpp/interface/geneve.py +++ /dev/null @@ -1,90 +0,0 @@ -# VyOS implementation of Geneve interface -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -from vyos.vpp import VPPControl - - -def show(): - """Show Geneve interface - Example: - from vyos.vpp.interface import geneve - geneve.show() - """ - vpp = VPPControl() - return vpp.api.geneve_tunnel_dump() - - -class GeneveInterface: - def __init__(self, ifname, source_address, remote, vni, kernel_interface: str = ''): - self.instance = int(ifname.removeprefix('geneve')) - self.ifname = f'geneve_tunnel{self.instance}' - self.src_address = source_address - self.dst_address = remote - self.vni = vni - self.kernel_interface = kernel_interface - self.vpp = VPPControl() - - def add(self): - """Create Geneve interface - https://github.com/FDio/vpp/blob/stable/2306/src/plugins/geneve/geneve.api - - Example: - from vyos.vpp.interface import GeneveInterface - a = GeneveInterface(ifname='geneve25', source_address='192.0.2.1', remote='203.0.113.25', vni=25) - a.add() - """ - return self.vpp.api.geneve_add_del_tunnel2( - is_add=True, - local_address=self.src_address, - remote_address=self.dst_address, - vni=self.vni, - l3_mode=False, - ) - - def delete(self): - """Delete Geneve interface - Example: - from vyos.vpp.interface import GeneveInterface - a = GeneveInterface(ifname='vxlan25', source_address='192.0.2.1', remote='203.0.113.25', vni=25) - a.delete() - """ - return self.vpp.api.geneve_add_del_tunnel2( - is_add=False, - local_address=self.src_address, - remote_address=self.dst_address, - vni=self.vni, - l3_mode=False, - ) - - def kernel_add(self): - """Add LCP pair - Example: - from vyos.vpp.interface import GeneveInterface - a = GeneveInterface(ifname='vxlan25', source_address='192.0.2.1', remote='203.0.113.25', vni=25) - a.kernel_add() - """ - self.vpp.lcp_pair_add(self.ifname, self.kernel_interface, 'tun') - - def kernel_delete(self): - """Delete LCP pair - Example: - from vyos.vpp.interface import GeneveInterface - a = GeneveInterface(ifname='vxlan25', source_address='192.0.2.1', remote='203.0.113.25', vni=25) - a.kernel_delete() - """ - self.vpp.lcp_pair_del(self.ifname, self.kernel_interface) diff --git a/python/vyos/vpp/interface/interface.py b/python/vyos/vpp/interface/interface.py deleted file mode 100644 index 05c1d14d6..000000000 --- a/python/vyos/vpp/interface/interface.py +++ /dev/null @@ -1,49 +0,0 @@ -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -from vyos.vpp import VPPControl - - -class Interface: - def __init__(self, ifname): - self.ifname = ifname - self.vpp = VPPControl() - - def set_state(self, state: str): - """Set interface state to UP or DOWN - Args: - state (str): The state of the interface. Options are 'up' and 'down'. - Example: - from vyos.vpp.interface import Interface - a = Interface(ifname='eth0') - a.set_state(state='up') - """ - if state not in ['up', 'down']: - raise ValueError(f"Invalid state: {state}") - state_flag = 1 if state == 'up' else 0 - if_index = self.vpp.get_sw_if_index(self.ifname) - self.vpp.api.sw_interface_set_flags(sw_if_index=if_index, flags=state_flag) - - def get_state(self): - """Get interface state - Example: - from vyos.vpp.interface import Interface - a = Interface(ifname='eth0') - a.get_state() - """ - if_index = self.vpp.get_sw_if_index(self.ifname) - return self.vpp.api.sw_interface_dump(sw_if_index=if_index)[0]['flags'] diff --git a/python/vyos/vpp/interface/wireguard.py b/python/vyos/vpp/interface/wireguard.py deleted file mode 100644 index c2d36e1b0..000000000 --- a/python/vyos/vpp/interface/wireguard.py +++ /dev/null @@ -1,55 +0,0 @@ -# VyOS implementation of VPP Wireguard interface -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -from vyos.vpp import VPPControl - - -class WireguardInterface: - """Interface Wireguard""" - - def __init__(self, ifname, listen_port=51820, kernel_interface: str = ''): - self.instance = int(ifname.removeprefix('wg')) - self.ifname = ifname - self.listen_port = listen_port - self.kernel_interface = kernel_interface - self.vpp = VPPControl() - - def add(self): - """Create Wireguard interface - https://github.com/FDio/vpp/blob/stable/2306/src/plugins/wireguard/wireguard.api - Example: - from vyos.vpp.interface import WireguardInterface - a = WireguardInterface(ifname='wg5', listen_port=51820, generate_key=True) - a.add() - """ - self.vpp.api.wireguard_interface_create( - generate_key=True, - interface={'user_instance': self.instance, 'listen_port': self.listen_port}, - ) - if self.kernel_interface: - self.vpp.lcp_pair_add(self.ifname, self.kernel_interface, 'tun') - - def delete(self): - """Delete Wireguard interface - Example: - from vyos.vpp.interface import WireguardInterface - a = WireguardInterface(ifname='wg5') - a.delete() - """ - wg_if_index = self.vpp.get_sw_if_index(f'wg{self.instance}') - return self.vpp.api.wireguard_interface_delete(sw_if_index=wg_if_index) diff --git a/python/vyos/vpp/utils.py b/python/vyos/vpp/utils.py index 5976b2189..0b514fd7c 100644 --- a/python/vyos/vpp/utils.py +++ b/python/vyos/vpp/utils.py @@ -104,11 +104,6 @@ def cli_ifaces_list(config_instance, mode: str = 'candidate') -> list[str]: for iface in config.get('settings', {}).get('interface', {}).keys(): vpp_ifaces.append(iface) - # Get a list of VPP interfaces - for iface_type in config.get('interfaces', {}).keys(): - for iface in config.get('interfaces', {}).get(iface_type, {}).keys(): - vpp_ifaces.append(iface) - # Get a list of interfaces VPP for iface_type in interfaces_config.keys(): for iface in interfaces_config.get(iface_type, {}).keys(): @@ -246,44 +241,6 @@ def vpp_ifaces_stats( return ifaces_stats -def cli_ifaces_lcp_kernel_list( - config_instance, mode: str = 'candidate' -) -> list[tuple[str, str]]: - """List of all VPP kernel-interfaces (CLI names, attached VPP interfaces) - - Args: - config_instance (VyOS Config): VyOS Config instance - mode (str, optional): `candidate` or `running`. Defaults to 'candidate'. - - Returns: - list[tuple[str, str]]: list of interfaces ([(vpp_iface, kernel_iface)]) - """ - - effective_mode: bool = True if mode == 'running' else False - - # Read a config - config = config_instance.get_config_dict( - ['vpp'], - key_mangling=('-', '_'), - effective=effective_mode, - get_first_key=True, - no_tag_node_value_mangle=True, - with_recursive_defaults=True, - ) - - lcp_kernel_ifaces: list[tuple[str, str]] = [] - - # Get a list with kernel interfaces - for ifaces_list in config.get('interfaces', {}).values(): - for iface_name, iface_settings in ifaces_list.items(): - if 'kernel_interface' in iface_settings: - lcp_kernel_ifaces.append( - (iface_name, iface_settings['kernel_interface']) - ) - - return lcp_kernel_ifaces - - def get_default_hugepage_size() -> int: """ Retrieve the system's default huge page size. diff --git a/smoketest/scripts/cli/test_vpp.py b/smoketest/scripts/cli/test_vpp.py index 70ac02583..c945d8dab 100755 --- a/smoketest/scripts/cli/test_vpp.py +++ b/smoketest/scripts/cli/test_vpp.py @@ -345,128 +345,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.cli_delete(gre_path + [interface_gre]) self.cli_commit() - @unittest.skip('Skipping this test geneve index always is 0') - def test_04_vpp_geneve(self): - vni = '2' - # Must be 'geneve0' to pass smoketest - # As geneve interfaces cannot be named with "instance" suffix - interface_geneve = 'geneve0' - interface_kernel = f'vpptun{vni}' - new_interface_kernel = f'vpptun1{vni}' - source_address = '192.0.2.1' - new_source_address = '192.0.2.2' - remote_address = '203.0.113.10' - kernel_address = '10.0.0.1' - - self.cli_set( - base_path - + [ - 'interfaces', - 'geneve', - interface_geneve, - 'source-address', - source_address, - ] - ) - self.cli_set( - base_path - + ['interfaces', 'geneve', interface_geneve, 'remote', remote_address] - ) - self.cli_set(base_path + ['interfaces', 'geneve', interface_geneve, 'vni', vni]) - self.cli_set( - base_path - + [ - 'interfaces', - 'geneve', - interface_geneve, - 'kernel-interface', - interface_kernel, - ] - ) - self.cli_set( - base_path - + ['kernel-interfaces', interface_kernel, 'address', f'{kernel_address}/31'] - ) - - # commit changes - self.cli_commit() - - self.assertTrue(os.path.isdir(f'/sys/class/net/{interface_kernel}')) - current_address = get_address(interface_kernel) - self.assertEqual(kernel_address, current_address) - - # check geneve interface - _, out = rc_cmd('sudo vppctl show geneve tunnel') - required_str = f'[0] lcl {source_address} rmt {remote_address} vni {vni}' - self.assertIn(required_str, out) - - # update geneve interface - self.cli_set( - base_path - + [ - 'interfaces', - 'geneve', - interface_geneve, - 'source-address', - new_source_address, - ] - ) - self.cli_commit() - - # check geneve interface after update - _, out = rc_cmd('sudo vppctl show geneve tunnel') - required_str = f'[0] lcl {new_source_address} rmt {remote_address} vni {vni}' - self.assertIn(required_str, out) - self.assertTrue(os.path.isdir(f'/sys/class/net/{interface_kernel}')) - self.assertEqual(kernel_address, current_address) - - # delete geneve kernel-interface but do not delete 'vpp kernel-interface' - # expect raise ConfigError - self.cli_delete( - base_path - + [ - 'interfaces', - 'geneve', - interface_geneve, - 'kernel-interface', - interface_kernel, - ] - ) - with self.assertRaises(ConfigSessionError): - self.cli_commit() - - # update gemeve kernel-interface but do not change 'vpp kernel-interface' - # expect raise ConfigError - self.cli_set( - base_path - + [ - 'interfaces', - 'geneve', - interface_geneve, - 'kernel-interface', - new_interface_kernel, - ] - ) - with self.assertRaises(ConfigSessionError): - self.cli_commit() - - # delete vpp kernel-interface - self.cli_delete(base_path + ['kernel-interfaces', interface_kernel]) - self.cli_commit() - - # delete geneve kernel-interface - self.cli_delete( - base_path + ['interfaces', 'geneve', interface_geneve, 'kernel-interface'] - ) - self.cli_commit() - - self.assertFalse(os.path.isdir(f'/sys/class/net/{interface_kernel}')) - - # delete geneve interface - self.cli_set(base_path + ['interfaces', 'geneve', interface_geneve]) - self.cli_commit() - - def test_05_vpp_loopback(self): + def test_04_vpp_loopback(self): loopback_path = interfaces_path + ['loopback'] interface_loopback = 'vpplo11' address = '192.0.2.54' @@ -491,7 +370,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.cli_delete(loopback_path + [interface_loopback]) self.cli_commit() - def test_06_vpp_bonding(self): + def test_05_vpp_bonding(self): bond_path = interfaces_path + ['bonding'] interface_bond = 'vppbond23' hash = 'layer3+4' @@ -561,7 +440,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): "Interface BondEthernet23 is not in the expected state 'up'.", ) - # delete vpp kernel-interface vlan + # delete vpp interface vlan self.cli_delete(bond_path + [interface_bond, 'vif']) self.cli_commit() self.assertFalse(os.path.isdir(f'/sys/class/net/{interface_bond}.{vlan}')) @@ -574,7 +453,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): _, out = rc_cmd('sudo vppctl show interface') self.assertNotIn('BondEthernet23', out) - def test_07_vpp_bridge(self): + def test_06_vpp_bridge(self): bridge_path = interfaces_path + ['bridge'] fake_member = 'eth2' members = [interface] @@ -680,7 +559,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.assertRegex(normalized_out, r'10 1 \d+ off') self.assertRegex(out, r'\bloop23\s+\d+\s+\d+\s+\d+\s+\*\s+') - def test_08_vpp_ipip(self): + def test_07_vpp_ipip(self): ipip_path = interfaces_path + ['ipip'] interface_ipip = 'vppipip12' source_address = '192.0.2.1' @@ -729,7 +608,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.cli_delete(ipip_path + [interface_ipip]) self.cli_commit() - def test_09_vpp_xconnect(self): + def test_08_vpp_xconnect(self): xconn_path = interfaces_path + ['xconnect'] vni = '23' interface_vxlan = f'vppvxlan{vni}' @@ -782,7 +661,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): for required_string in required_str_list: self.assertNotIn(required_string, out) - def test_10_vpp_driver_options(self): + def test_09_vpp_driver_options(self): driver_options = { 'num-rx-desc': '512', 'num-tx-desc': '512', @@ -821,7 +700,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): for option, value in driver_options.items(): self.assertIn(f'{option} {value}', config) - def test_11_vpp_cpu_cores(self): + def test_10_vpp_cpu_cores(self): cpu_cores = '2' skip_cores, main_core = get_vpp_cpu_allocation() @@ -846,7 +725,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): for config_entry in config_entries: self.assertIn(config_entry, config) - def test_12_1_buffer_page_size(self): + def test_11_1_buffer_page_size(self): sizes = ['4K', '2M'] for size in sizes: self.cli_set(resource_path + ['buffers', 'page-size', size]) @@ -855,7 +734,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): conf = get_vpp_config() self.assertEqual(conf['buffers']['page-size'], size) - def test_12_2_statseg_page_size(self): + def test_11_2_statseg_page_size(self): sizes = ['4K', '2M'] for size in sizes: self.cli_set(resource_path + ['memory', 'stats', 'page-size', size]) @@ -864,7 +743,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): conf = get_vpp_config() self.assertEqual(conf['statseg']['page-size'], size) - def test_12_3_mem_page_size(self): + def test_11_3_mem_page_size(self): sizes = ['4K', '2M'] for size in sizes: self.cli_set(resource_path + ['memory', 'main-heap-page-size', size]) @@ -873,7 +752,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): conf = get_vpp_config() self.assertEqual(conf['memory']['main-heap-page-size'], size) - def test_13_vpp_ipsec_xfrm_nl(self): + def test_12_vpp_ipsec_xfrm_nl(self): rx_buffer_zise = default_resource_map.get('netlink_rx_buffer_size') self.cli_set(base_path + ['settings', 'ipsec-acceleration']) @@ -891,7 +770,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): for config_entry in config_entries: self.assertIn(config_entry, config) - def test_14_1_vpp_cgnat(self): + def test_13_1_vpp_cgnat(self): base_cgnat = base_path + ['nat', 'cgnat'] iface_out = 'eth0' iface_inside = 'eth1' @@ -930,7 +809,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.assertIn(f'tcp transitory timeout: {timeout_tcp_trans}sec', out) self.assertIn(f'icmp timeout: {timeout_icmp}sec', out) - def test_14_2_vpp_cgnat_bond_with_vifs(self): + def test_13_2_vpp_cgnat_bond_with_vifs(self): base_cgnat = base_path + ['nat', 'cgnat'] base_bond = interfaces_path + ['bonding'] iface_bond = 'vppbond0' @@ -970,7 +849,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): lines = out.split('\n') self.assertTrue(len(lines) == 3) - def test_15_vpp_nat44(self): + def test_14_vpp_nat44(self): base_nat = base_path + ['nat', 'nat44'] exclude_local_addr = '100.64.0.52' exclude_local_port = '22' @@ -1067,7 +946,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): out = vpp.api.nat44_show_running_config().forwarding_enabled self.assertTrue(out) - def test_16_vpp_sflow(self): + def test_15_vpp_sflow(self): base_sflow = ['system', 'sflow'] sampling_rate = '1500' polling_interval = '55' @@ -1128,7 +1007,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): _, out = rc_cmd('sudo vppctl show sflow') self.assertIn('interfaces enabled: 0', out) - def test_17_resource_limits(self): + def test_16_resource_limits(self): max_map_count = '100000' shmmax = '55555555555555' hr_path = ['system', 'option', 'resource-limits'] @@ -1155,7 +1034,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.assertEqual(sysctl_read('vm.max_map_count'), '65530') self.assertEqual(sysctl_read('kernel.shmmax'), '8589934592') - def test_18_vpp_pppoe_mapping(self): + def test_17_vpp_pppoe_mapping(self): config_file = '/run/accel-pppd/pppoe.conf' pool = "TEST-POOL" vni = '23' @@ -1205,7 +1084,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.cli_delete(['interfaces', 'ethernet', interface, 'vif']) self.cli_commit() - def test_19_kernel_options_hugepages(self): + def test_18_kernel_options_hugepages(self): default_hp_size = '2M' hp_size_1g = '1G' hp_size_2m = '2M' @@ -1238,7 +1117,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.assertIn(f' hugepagesz={hp_size_1g} hugepages={hp_count_1g}', tmp) self.assertIn(f' hugepagesz={hp_size_2m} hugepages={hp_count_2m}', tmp) - def test_20_static_arp(self): + def test_19_static_arp(self): host = '192.0.2.10' mac = '00:01:02:03:04:0a' path_static_arp = ['protocols', 'static', 'arp'] @@ -1262,7 +1141,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): self.cli_delete(path_static_arp) - def test_21_1_vpp_ipfix(self): + def test_20_1_vpp_ipfix(self): base_ipfix = base_path + ['ipfix'] base_collector = base_ipfix + ['collector'] collector_ip = '127.0.0.2' @@ -1349,7 +1228,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): len(non_default_exporters), 0, 'Exporters not cleaned up properly' ) - def test_21_2_vpp_ipfix_bond(self): + def test_20_2_vpp_ipfix_bond(self): base_ipfix = base_path + ['ipfix'] base_bond = interfaces_path + ['bonding'] iface_bond = 'vppbond0' @@ -1379,7 +1258,7 @@ class TestVPP(VyOSUnitTestSHIM.TestCase): _, out = rc_cmd('sudo vppctl show flowprobe feature') self.assertIn(required_str, out) - def test_22_double_enabling_vpp(self): + def test_21_double_enabling_vpp(self): # Verify double enabling of VPP # Delete already defined settings from 'setUp' method diff --git a/src/conf_mode/vpp.py b/src/conf_mode/vpp.py index 396cce548..2ae079c30 100755 --- a/src/conf_mode/vpp.py +++ b/src/conf_mode/vpp.py @@ -78,8 +78,6 @@ vpp_log = getLogger( dependency_interface_type_map = { 'vpp_interfaces_bonding': 'bonding', 'vpp_interfaces_bridge': 'bridge', - 'vpp_interfaces_ethernet': 'ethernet', - 'vpp_interfaces_geneve': 'geneve', 'vpp_interfaces_gre': 'gre', 'vpp_interfaces_ipip': 'ipip', 'vpp_interfaces_loopback': 'loopback', @@ -442,17 +440,6 @@ def get_config(config=None): # Dependencies for dependency, interface_type in dependency_interface_type_map.items(): - # if conf.exists(base + ['interfaces', interface_type]): - if effective_config.get('interfaces', {}).get(interface_type): - for iface, iface_config in ( - config.get('interfaces', {}).get(interface_type, {}).items() - ): - # filter unsupported config nodes - if interface_type == 'ethernet': - iface_filter_eth(conf, iface) - set_dependents(dependency, conf, iface) - - for dependency, interface_type in dependency_interface_type_map.items(): if conf.exists(['interfaces', 'vpp', interface_type]): for iface, iface_config in interfaces_config.get( interface_type, {} @@ -466,11 +453,6 @@ def get_config(config=None): no_tag_node_value_mangle=True, ) - # kernel-interfaces dependency - if effective_config.get('kernel_interfaces'): - for iface in config.get('kernel_interfaces', {}): - set_dependents('vpp_kernel_interface', conf, iface) - # NAT dependency if conf.exists(['vpp', 'nat', 'nat44']): set_dependents('vpp_nat_nat44', conf) diff --git a/src/conf_mode/vpp_interfaces_ethernet.py b/src/conf_mode/vpp_interfaces_ethernet.py deleted file mode 100644 index 81050444e..000000000 --- a/src/conf_mode/vpp_interfaces_ethernet.py +++ /dev/null @@ -1,134 +0,0 @@ -#!/usr/bin/env python3 -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -import os - -from vyos.config import Config -from vyos.configdep import set_dependents -from vyos import ConfigError -from vyos.vpp.config_verify import verify_vpp_remove_xconnect_interface - - -def get_config(config=None) -> dict: - """Get Ethernet interface configuration - - Args: - config (vyos.config.Config, optional): The VyOS configuration dictionary - Returns: - dict: Ethernet interface configuration - """ - if config: - conf = config - else: - conf = Config() - - base = ['vpp', 'interfaces', 'ethernet'] - base_interfaces_xconnect = ['vpp', 'interfaces', 'xconnect'] - - ifname = os.environ['VYOS_TAGNODE_VALUE'] - - # Get effective config as we need full dicitonary per interface delete - effective_config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - effective=True, - get_first_key=True, - no_tag_node_value_mangle=True, - ) - - if not conf.exists(base + [ifname]): - config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - ) - config.update({'remove': effective_config}) - else: - # Get config_dict with default values - config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - with_defaults=True, - with_recursive_defaults=True, - ) - - # Get global 'vpp interfaces xconnect' - config['vpp_interfaces_xconnect'] = conf.get_config_dict( - base_interfaces_xconnect, - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - ) - - # Dependency - for xcon_name, xcon_config in config.get('vpp_interfaces_xconnect').items(): - for member_name in xcon_config.get('member', {}).get('interface', []): - if member_name == ifname: - set_dependents('vpp_interfaces_xconnect', conf, xcon_name) - - if conf.exists(base + [ifname, 'kernel-interface']): - iface = config.get('kernel_interface') - if conf.exists(['vpp', 'kernel-interfaces', iface]): - set_dependents('vpp_kernel_interface', conf, iface) - - config['ifname'] = ifname - return config - - -def verify(config): - verify_vpp_remove_xconnect_interface(config) - if 'remove' in config: - return None - - -def generate(config): - pass - - -def apply(config): - # Delete interface - if 'remove' in config: - pass - # remove_config = config.get('remove') - # ifname = config.get('ifname') - # src_addr = remove_config.get('source_address') - # dst_addr = remove_config.get('remote') - # vni = int(remove_config.get('vni')) - # v = VXLANInterface(ifname, src_addr, dst_addr, vni) - # v.delete() - else: - pass - # ifname = config.get('ifname') - # kernel_interface = config.get('kernel_interface', '') - # v = VXLANInterface(ifname, src_addr, dst_addr, vni, kernel_interface) - # v.add() - return None - - -if __name__ == '__main__': - try: - c = get_config() - verify(c) - generate(c) - apply(c) - except ConfigError as e: - print(e) - exit(1) diff --git a/src/conf_mode/vpp_interfaces_geneve.py b/src/conf_mode/vpp_interfaces_geneve.py deleted file mode 100644 index efac4e65a..000000000 --- a/src/conf_mode/vpp_interfaces_geneve.py +++ /dev/null @@ -1,193 +0,0 @@ -#!/usr/bin/env python3 -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -import os - -from vyos import ConfigError - -from vyos.config import Config -from vyos.configdict import leaf_node_changed -from vyos.configdep import set_dependents, call_dependents -from vyos.template import is_interface - -from vyos.vpp.interface import GeneveInterface -from vyos.vpp.config_deps import deps_xconnect_dict -from vyos.vpp.config_verify import ( - verify_vpp_remove_kernel_interface, - verify_vpp_change_kernel_interface, - verify_vpp_remove_xconnect_interface, - verify_vpp_exists_kernel_interface, -) -from vyos.vpp.utils import cli_ifaces_lcp_kernel_list - - -def get_config(config=None) -> dict: - """Get Geneve interface configuration - - Args: - config (vyos.config.Config, optional): The VyOS configuration dictionary - recursive_defaults (bool, optional): Include recursive defaults - Returns: - dict: Geneve interface configuration - """ - if config: - conf = config - else: - conf = Config() - - base = ['vpp', 'interfaces', 'geneve'] - base_kernel_interfaces = ['vpp', 'kernel-interfaces'] - - ifname = os.environ['VYOS_TAGNODE_VALUE'] - - # Get config_dict with default values - config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - with_defaults=True, - with_recursive_defaults=True, - ) - - if not conf.exists(['vpp']): - config['remove_vpp'] = True - return config - - # Get effective config as we need full dicitonary per interface delete - effective_config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - effective=True, - get_first_key=True, - no_tag_node_value_mangle=True, - ) - - if effective_config: - config.update({'effective': effective_config}) - - if not conf.exists(base + [ifname]): - config['remove'] = True - - # Get global 'vpp kernel-interfaces' for verify - config['vpp_kernel_interfaces'] = conf.get_config_dict( - base_kernel_interfaces, - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - ) - - tmp = leaf_node_changed(conf, base + [ifname, 'kernel-interface']) - if tmp: - config['kernel_interface_removed'] = tmp - - # list of all kernel interfaces `vpp interface xxx kernel-interface xxx` - config['candidate_kernel_interfaces'] = cli_ifaces_lcp_kernel_list(conf) - - # Dependency - config['xconn_members'] = deps_xconnect_dict(conf) - if ifname in config['xconn_members']: - for xconn_iface in config['xconn_members'][ifname]: - set_dependents('vpp_interfaces_xconnect', conf, xconn_iface) - - if effective_config.get('kernel_interface'): - if conf.exists(base + [ifname, 'kernel-interface']): - iface = config.get('kernel_interface') - if conf.exists(['vpp', 'kernel-interfaces', iface]): - set_dependents('vpp_kernel_interface', conf, iface) - - config['ifname'] = ifname - return config - - -def verify(config): - # No need to verify anything if vpp is removed - if 'remove_vpp' in config: - return None - - # Verify that removed kernel interface is not used in 'vpp kernel-interfaces'. - # vpp interfaces geneve geneveX kernel-interface vpp-tunX - # vpp kernel-interface vpp-tunX - verify_vpp_remove_kernel_interface(config) - - verify_vpp_remove_xconnect_interface(config) - - if 'remove' in config: - return None - - required_keys = {'source_address', 'remote', 'vni'} - if not all(key in config for key in required_keys): - missing_keys = required_keys - set(config.keys()) - raise ConfigError( - f"Required options are missing: {', '.join(missing_keys).replace('_', '-')}" - ) - - # Change 'vpp interfaces geneve geneveX kernel-interface vpp-tunX' - # => 'vpp interfaces geneve geneveX kernel-interface vpp-tunY' - # check if we have kernel interface config 'vpp kernel-interface vpp-tunX' - verify_vpp_change_kernel_interface(config) - verify_vpp_exists_kernel_interface(config) - - -def generate(config): - pass - - -def apply(config): - if 'remove_vpp' in config: - return None - - ifname = config.get('ifname') - # Delete interface - if 'effective' in config: - remove_config = config.get('effective') - src_addr = remove_config.get('source_address') - dst_addr = remove_config.get('remote') - vni = int(remove_config.get('vni')) - i = GeneveInterface(ifname, src_addr, dst_addr, vni) - i.delete() - - if 'remove' in config: - return None - - # Add interface - src_addr = config.get('source_address') - dst_addr = config.get('remote') - vni = int(config.get('vni')) - kernel_interface = config.get('kernel_interface', '') - i = GeneveInterface(ifname, src_addr, dst_addr, vni, kernel_interface) - i.add() - - # Add kernel-interface (LCP) if interface is not exist - if 'kernel_interface' in config and not is_interface(kernel_interface): - i.kernel_add() - - call_dependents() - - return None - - -if __name__ == '__main__': - try: - c = get_config() - verify(c) - generate(c) - apply(c) - except ConfigError as e: - print(e) - exit(1) diff --git a/src/conf_mode/vpp_kernel-interfaces.py b/src/conf_mode/vpp_kernel-interfaces.py deleted file mode 100644 index d18a5d3e5..000000000 --- a/src/conf_mode/vpp_kernel-interfaces.py +++ /dev/null @@ -1,218 +0,0 @@ -#!/usr/bin/env python3 -# -# Copyright (C) VyOS Inc. -# -# This program is free software; you can redistribute it and/or modify -# it under the terms of the GNU General Public License as published by -# the Free Software Foundation; either version 2 of the License, or -# (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU General Public License for more details. -# -# You should have received a copy of the GNU General Public License along -# with this program; if not, write to the Free Software Foundation, Inc., -# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - -import os - -from vyos.config import Config -from vyos.configdep import set_dependents, call_dependents -from vyos.configdict import leaf_node_changed -from vyos.configdict import node_changed -from vyos import ConfigError -from vyos.ifconfig import Interface -from vyos.utils.network import interface_exists -from vyos.utils.process import call -from vyos.vpp import VPPControl - - -def get_config(config=None) -> dict: - if config: - conf = config - else: - conf = Config() - - base = ['vpp', 'kernel-interfaces'] - base_settings = ['vpp', 'settings'] - - ifname = os.environ['VYOS_TAGNODE_VALUE'] - - # Get config_dict with default values - config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - with_defaults=True, - ) - - if not conf.exists(['vpp']): - config['remove_vpp'] = True - return config - - # Get 'vpp settings' config with default values - config_settings = conf.get_config_dict( - base_settings, - key_mangling=('-', '_'), - get_first_key=True, - no_tag_node_value_mangle=True, - with_defaults=True, - ) - config['vpp_settings'] = config_settings - - # Get effective config as we need full dicitonary per interface delete - if __name__ == '__main__': - effective_config = conf.get_config_dict( - base + [ifname], - key_mangling=('-', '_'), - effective=True, - get_first_key=True, - no_tag_node_value_mangle=True, - ) - # if a file was started as dependency, we are starting from empty config - else: - effective_config = {} - - if effective_config: - config.update({'effective': effective_config}) - - address_removed = leaf_node_changed(conf, base + [ifname, 'address']) - if address_removed: - config['address_removed'] = address_removed - - description_removed = leaf_node_changed(conf, base + [ifname, 'description']) - if description_removed: - config['description_removed'] = {} - - vlans_removed = node_changed(conf, base + [ifname, 'vif']) - if vlans_removed: - config['vlans_removed'] = vlans_removed - - if conf.exists(['vpp', 'nat', 'cgnat']): - set_dependents('vpp_nat_cgnat', conf) - if conf.exists(['vpp', 'nat', 'nat44']): - set_dependents('vpp_nat_nat44', conf) - - config['ifname'] = ifname - - return config - - -def verify(config): - if 'remove' in config or 'remove_vpp' in config: - return None - - # Interface must exists before it is configured - if not interface_exists(config['ifname']): - raise ConfigError( - f'Interface {config["ifname"]} must be created before using in configuration' - ) - - -def generate(config): - pass - - -def apply(config): - if 'remove_vpp' in config: - return None - - ifname = config.get('ifname') - i = Interface(ifname) - # update/remove addresses - if 'address_removed' in config: - for address in config['address_removed']: - i.del_addr(address) - # remove description - if 'description_removed' in config: - i.set_alias('') - - # remove VLANs - if 'vlans_removed' in config: - for vlan in config['vlans_removed']: - call(f'ip link del dev {ifname}.{vlan}') - - # Delete - if 'remove' in config: - pass - else: - # Add address - if 'address' in config: - for address in config['address']: - i.add_addr(address) - # Set MTU - if 'mtu' in config: - i.set_mtu(config.get('mtu')) - # Set description - if 'description' in config: - i.set_alias(config.get('description')) - # Admin state down - if 'disable' in config: - i.set_admin_state('down') - else: - i.set_admin_state('up') - - for vlan, vlan_config in config.get('vif', {}).items(): - if vlan not in config.get('effective', {}).get('vif', {}).keys(): - call( - f'ip link add link {ifname} name {ifname}.{vlan} type vlan id {vlan}' - ) - call(f'ip link set dev {ifname}.{vlan} up') - v = Interface(f'{ifname}.{vlan}') - - # VLAN address - addresses_effective = ( - config.get('effective', {}) - .get('vif', {}) - .get(vlan, {}) - .get('address', []) - ) - addresses_candidate = vlan_config.get('address', []) - - for ipaddr in addresses_effective: - if ipaddr not in addresses_candidate: - v.del_addr(ipaddr) - for ipaddr in addresses_candidate: - if ipaddr not in addresses_effective: - v.add_addr(ipaddr) - - # VLAN description - description_effective = ( - config.get('effective', {}) - .get('vif', {}) - .get(vlan, {}) - .get('description', '') - ) - description_candidate = vlan_config.get('description', '') - - if description_candidate: - v.set_alias(description_candidate) - elif description_effective and not description_candidate: - v.set_alias('') - - v.set_admin_state('up') - - # Set rx-mode - rx_mode = config['vpp_settings'].get('interface_rx_mode') - if rx_mode: - vpp_control = VPPControl() - lcp_name = vpp_control.lcp_pair_find(kernel_name=ifname).get('vpp_name_kernel') - vpp_control.iface_rxmode(lcp_name, rx_mode) - - call_dependents() - - return None - - -if __name__ == '__main__': - try: - c = get_config() - verify(c) - generate(c) - apply(c) - except ConfigError as e: - print(e) - exit(1) diff --git a/src/op_mode/show_vpp_interfaces.py b/src/op_mode/show_vpp_interfaces.py index c159ad0aa..d5dd08247 100755 --- a/src/op_mode/show_vpp_interfaces.py +++ b/src/op_mode/show_vpp_interfaces.py @@ -248,9 +248,12 @@ if __name__ == '__main__': vpp_interfaces = [] vpp_ethernet = config.list_nodes('vpp settings interface') vpp_interfaces.extend(vpp_ethernet) - if config.exists('vpp kernel-interfaces'): - vpp_kernel_interfaces = config.list_nodes('vpp kernel-interfaces') - vpp_interfaces.extend(vpp_kernel_interfaces) + if config.exists('interfaces vpp'): + for iface_type in config.list_nodes('interfaces vpp'): + vpp_kernel_interfaces = config.list_nodes( + f'interfaces vpp {iface_type}' + ) + vpp_interfaces.extend(vpp_kernel_interfaces) print(show_interfaces(interfaces_list=vpp_interfaces)) if args.hardware: |
