summaryrefslogtreecommitdiff
path: root/python/vyos/ifconfig/interface.py
diff options
context:
space:
mode:
Diffstat (limited to 'python/vyos/ifconfig/interface.py')
-rwxr-xr-x[-rw-r--r--]python/vyos/ifconfig/interface.py74
1 files changed, 69 insertions, 5 deletions
diff --git a/python/vyos/ifconfig/interface.py b/python/vyos/ifconfig/interface.py
index 048a2cd19..a1928ba51 100644..100755
--- a/python/vyos/ifconfig/interface.py
+++ b/python/vyos/ifconfig/interface.py
@@ -311,6 +311,28 @@ class Interface(Control):
cmd = 'ip link del dev {ifname}'.format(**self.config)
return self._cmd(cmd)
+ def _set_vrf_ct_zone(self, vrf):
+ """
+ Add/Remove rules in nftables to associate traffic in VRF to an
+ individual conntack zone
+ """
+ if vrf:
+ # Get routing table ID for VRF
+ vrf_table_id = get_interface_config(vrf).get('linkinfo', {}).get(
+ 'info_data', {}).get('table')
+ # Add map element with interface and zone ID
+ if vrf_table_id:
+ self._cmd(
+ f'nft add element inet vrf_zones ct_iface_map {{ "{self.ifname}" : {vrf_table_id} }}'
+ )
+ else:
+ nft_del_element = f'delete element inet vrf_zones ct_iface_map {{ "{self.ifname}" }}'
+ # Check if deleting is possible first to avoid raising errors
+ _, err = self._popen(f'nft -c {nft_del_element}')
+ if not err:
+ # Remove map element
+ self._cmd(f'nft {nft_del_element}')
+
def get_min_mtu(self):
"""
Get hardware minimum supported MTU
@@ -401,6 +423,7 @@ class Interface(Control):
>>> Interface('eth0').set_vrf()
"""
self.set_interface('vrf', vrf)
+ self._set_vrf_ct_zone(vrf)
def set_arp_cache_tmo(self, tmo):
"""
@@ -779,9 +802,7 @@ class Interface(Control):
# Note that currently expanded netmasks are not supported. That means
# 2001:db00::0/24 is a valid argument while 2001:db00::0/ffff:ff00:: not.
# see https://docs.python.org/3/library/ipaddress.html
- bits = bin(
- int(v6_addr['netmask'].replace(':', ''), 16)).count('1')
- prefix = '/' + str(bits)
+ prefix = '/' + v6_addr['netmask'].split('/')[-1]
# we alsoneed to remove the interface suffix on link local
# addresses
@@ -1345,12 +1366,55 @@ class Interface(Control):
# create/update 802.1q VLAN interfaces
for vif_id, vif_config in config.get('vif', {}).items():
+
+ vif_ifname = f'{ifname}.{vif_id}'
+ vif_config['ifname'] = vif_ifname
+
tmp = deepcopy(VLANIf.get_config())
tmp['source_interface'] = ifname
tmp['vlan_id'] = vif_id
- vif_ifname = f'{ifname}.{vif_id}'
- vif_config['ifname'] = vif_ifname
+ # We need to ensure that the string format is consistent, and we need to exclude redundant spaces.
+ sep = ' '
+ if 'egress_qos' in vif_config:
+ # Unwrap strings into arrays
+ egress_qos_array = vif_config['egress_qos'].split()
+ # The split array is spliced according to the fixed format
+ tmp['egress_qos'] = sep.join(egress_qos_array)
+
+ if 'ingress_qos' in vif_config:
+ # Unwrap strings into arrays
+ ingress_qos_array = vif_config['ingress_qos'].split()
+ # The split array is spliced according to the fixed format
+ tmp['ingress_qos'] = sep.join(ingress_qos_array)
+
+ # Since setting the QoS control parameters in the later stage will
+ # not completely delete the old settings,
+ # we still need to delete the VLAN encapsulation interface in order to
+ # ensure that the changed settings are effective.
+ cur_cfg = get_interface_config(vif_ifname)
+ qos_str = ''
+ tmp2 = dict_search('linkinfo.info_data.ingress_qos', cur_cfg)
+ if 'ingress_qos' in tmp and tmp2:
+ for item in tmp2:
+ from_key = item['from']
+ to_key = item['to']
+ qos_str += f'{from_key}:{to_key} '
+ if qos_str != tmp['ingress_qos']:
+ if self.exists(vif_ifname):
+ VLANIf(vif_ifname).remove()
+
+ qos_str = ''
+ tmp2 = dict_search('linkinfo.info_data.egress_qos', cur_cfg)
+ if 'egress_qos' in tmp and tmp2:
+ for item in tmp2:
+ from_key = item['from']
+ to_key = item['to']
+ qos_str += f'{from_key}:{to_key} '
+ if qos_str != tmp['egress_qos']:
+ if self.exists(vif_ifname):
+ VLANIf(vif_ifname).remove()
+
vlan = VLANIf(vif_ifname, **tmp)
vlan.update(vif_config)