From 8e2112261c68189c2c78455c3e1f32d7f5447ab9 Mon Sep 17 00:00:00 2001
From: sarthurdev <965089+sarthurdev@users.noreply.github.com>
Date: Sat, 20 Jan 2024 22:25:06 +0100
Subject: dhcpv6: T3771: Allow installation of routes for delegated prefixes
---
src/etc/sudoers.d/vyos | 3 ++
src/system/on-dhcpv6-event.sh | 78 +++++++++++++++++++++++++++++++++++++++++++
2 files changed, 81 insertions(+)
create mode 100755 src/system/on-dhcpv6-event.sh
(limited to 'src')
diff --git a/src/etc/sudoers.d/vyos b/src/etc/sudoers.d/vyos
index c099446ba..63a944f41 100644
--- a/src/etc/sudoers.d/vyos
+++ b/src/etc/sudoers.d/vyos
@@ -44,6 +44,8 @@ Cmnd_Alias DIAGNOSTICS = /bin/ip vrf exec * /bin/ping *, \
/bin/ip vrf exec * /bin/traceroute *, \
/bin/ip vrf exec * /usr/bin/mtr *, \
/usr/libexec/vyos/op_mode/*
+Cmnd_Alias KEA_IP6_ROUTES = /sbin/ip -6 route replace *,\
+ /sbin/ip -6 route del *
%operator ALL=NOPASSWD: DATE, IPTABLES, ETHTOOL, IPFLUSH, HWINFO, \
PPPOE_CMDS, PCAPTURE, /usr/sbin/wanpipemon, \
DMIDECODE, DISK, CONNTRACK, IP6TABLES, \
@@ -55,3 +57,4 @@ Cmnd_Alias DIAGNOSTICS = /bin/ip vrf exec * /bin/ping *, \
# Allow members of group sudo to execute any command
%sudo ALL=NOPASSWD: ALL
+_kea ALL=NOPASSWD: KEA_IP6_ROUTES
diff --git a/src/system/on-dhcpv6-event.sh b/src/system/on-dhcpv6-event.sh
new file mode 100755
index 000000000..fcc88ae6f
--- /dev/null
+++ b/src/system/on-dhcpv6-event.sh
@@ -0,0 +1,78 @@
+#!/bin/bash
+#
+# Copyright (C) 2024 VyOS maintainers and contributors
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2 or later as
+# published by the Free Software Foundation.
+#
+# 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, see .
+#
+#
+
+if [ $# -lt 1 ]; then
+ echo Invalid args
+ logger -s -t on-dhcpv6-event "Invalid args \"$@\""
+ exit 1
+fi
+
+action=$1
+
+case "$action" in
+ lease6_renew|lease6_recover)
+ exit 0
+ ;;
+
+ lease6_release|lease6_expire|lease6_decline)
+ ifname=$QUERY6_IFACE_NAME
+ client_ip=$LEASE6_ADDRESS
+ client_prefix_len=$LEASE6_PREFIX_LEN
+
+ if [[ "$LEASE6_TYPE" != "IA_PD" ]]; then
+ exit 0
+ fi
+
+ sudo -n /sbin/ip -6 route del ${client_ip}/${client_prefix_len} \
+ dev ${ifname} \
+ proto static
+
+ exit 0
+ ;;
+
+ leases6_committed)
+ for ((i = 0; i < $LEASES6_SIZE; i++)); do
+ ifname=$QUERY6_IFACE_NAME
+ requester_link_local=$QUERY6_REMOTE_ADDR
+ client_type_var="LEASES6_AT${i}_TYPE"
+ client_ip_var="LEASES6_AT${i}_ADDRESS"
+ client_prefix_len_var="LEASES6_AT${i}_PREFIX_LEN"
+
+ client_type=${!client_type_var}
+
+ if [[ "$client_type" != "IA_PD" ]]; then
+ continue
+ fi
+
+ client_ip=${!client_ip_var}
+ client_prefix_len=${!client_prefix_len_var}
+
+ sudo -n /sbin/ip -6 route replace ${client_ip}/${client_prefix_len} \
+ via ${requester_link_local} \
+ dev ${ifname} \
+ proto static
+ done
+
+ exit 0
+ ;;
+
+ *)
+ logger -s -t on-dhcpv6-event "Invalid command \"$1\""
+ exit 1
+ ;;
+esac
--
cgit v1.2.3
From 7253c8a3d4649e2c253a4d26c8123a65aedd46e7 Mon Sep 17 00:00:00 2001
From: sarthurdev <965089+sarthurdev@users.noreply.github.com>
Date: Wed, 24 Jan 2024 00:14:52 +0100
Subject: dhcpv6: T3316: Add support for excluded-prefix in prefix delegation
---
interface-definitions/service_dhcpv6-server.xml.in | 25 ++++++++++++++++++++++
python/vyos/kea.py | 10 +++++++--
.../scripts/cli/test_service_dhcpv6-server.py | 11 +++++++++-
src/conf_mode/service_dhcpv6-server.py | 17 +++++++++++++++
4 files changed, 60 insertions(+), 3 deletions(-)
(limited to 'src')
diff --git a/interface-definitions/service_dhcpv6-server.xml.in b/interface-definitions/service_dhcpv6-server.xml.in
index 73ea69cc0..28b97a64b 100644
--- a/interface-definitions/service_dhcpv6-server.xml.in
+++ b/interface-definitions/service_dhcpv6-server.xml.in
@@ -231,6 +231,31 @@
Delegated prefix length must be between 32 and 96
+
+
+ IPv6 prefix to be excluded from prefix delegation
+
+ ipv6
+ IPv6 prefix excluded from prefix delegation
+
+
+
+
+
+
+
+
+ Length in bits of excluded prefix
+
+ u32:33-64
+ Excluded prefix length (33-128)
+
+
+
+
+ Prefix length must be between 33 and 128
+
+
diff --git a/python/vyos/kea.py b/python/vyos/kea.py
index fb5afc2ce..720bebec3 100644
--- a/python/vyos/kea.py
+++ b/python/vyos/kea.py
@@ -237,11 +237,17 @@ def kea6_parse_subnet(subnet, config):
if 'prefix' in config['prefix_delegation']:
for prefix, pd_conf in config['prefix_delegation']['prefix'].items():
- pd_pools.append({
+ pd_pool = {
'prefix': prefix,
'prefix-len': int(pd_conf['prefix_length']),
'delegated-len': int(pd_conf['delegated_length'])
- })
+ }
+
+ if 'excluded_prefix' in pd_conf:
+ pd_pool['excluded-prefix'] = pd_conf['excluded_prefix']
+ pd_pool['excluded-prefix-len'] = int(pd_conf['excluded_prefix_length'])
+
+ pd_pools.append(pd_pool)
out['pd-pools'] = pd_pools
diff --git a/smoketest/scripts/cli/test_service_dhcpv6-server.py b/smoketest/scripts/cli/test_service_dhcpv6-server.py
index dcce30f55..5a831b8a0 100755
--- a/smoketest/scripts/cli/test_service_dhcpv6-server.py
+++ b/smoketest/scripts/cli/test_service_dhcpv6-server.py
@@ -215,6 +215,7 @@ class TestServiceDHCPv6Server(VyOSUnitTestSHIM.TestCase):
delegate_start = '2001:db8:ee::'
delegate_len = '64'
prefix_len = '56'
+ exclude_len = '66'
pool = base_path + ['shared-network-name', shared_net_name, 'subnet', subnet]
self.cli_set(pool + ['subnet-id', '1'])
@@ -222,6 +223,8 @@ class TestServiceDHCPv6Server(VyOSUnitTestSHIM.TestCase):
self.cli_set(pool + ['range', '1', 'stop', range_stop])
self.cli_set(pool + ['prefix-delegation', 'prefix', delegate_start, 'delegated-length', delegate_len])
self.cli_set(pool + ['prefix-delegation', 'prefix', delegate_start, 'prefix-length', prefix_len])
+ self.cli_set(pool + ['prefix-delegation', 'prefix', delegate_start, 'excluded-prefix', delegate_start])
+ self.cli_set(pool + ['prefix-delegation', 'prefix', delegate_start, 'excluded-prefix-length', exclude_len])
# commit changes
self.cli_commit()
@@ -241,7 +244,13 @@ class TestServiceDHCPv6Server(VyOSUnitTestSHIM.TestCase):
self.verify_config_object(
obj,
['Dhcp6', 'shared-networks', 0, 'subnet6', 0, 'pd-pools'],
- {'prefix': delegate_start, 'prefix-len': int(prefix_len), 'delegated-len': int(delegate_len)})
+ {
+ 'prefix': delegate_start,
+ 'prefix-len': int(prefix_len),
+ 'delegated-len': int(delegate_len),
+ 'excluded-prefix': delegate_start,
+ 'excluded-prefix-len': int(exclude_len)
+ })
# Check for running process
self.assertTrue(process_named_running(PROCESS_NAME))
diff --git a/src/conf_mode/service_dhcpv6-server.py b/src/conf_mode/service_dhcpv6-server.py
index 214531904..add83eb0d 100755
--- a/src/conf_mode/service_dhcpv6-server.py
+++ b/src/conf_mode/service_dhcpv6-server.py
@@ -144,6 +144,23 @@ def verify(dhcpv6):
if prefix_config['prefix_length'] > prefix_config['delegated_length']:
raise ConfigError('Length of delegated IPv6 prefix must be within parent prefix')
+ if 'excluded_prefix' in prefix_config:
+ if 'excluded_prefix_length' not in prefix_config:
+ raise ConfigError('Length of excluded IPv6 prefix must be configured')
+
+ prefix_len = prefix_config['prefix_length']
+ prefix_obj = ip_network(f'{prefix}/{prefix_len}')
+
+ excluded_prefix = prefix_config['excluded_prefix']
+ excluded_len = prefix_config['excluded_prefix_length']
+ excluded_obj = ip_network(f'{excluded_prefix}/{excluded_len}')
+
+ if excluded_len <= prefix_config['delegated_length']:
+ raise ConfigError('Excluded IPv6 prefix must be smaller than delegated prefix')
+
+ if not excluded_obj.subnet_of(prefix_obj):
+ raise ConfigError(f'Excluded prefix "{excluded_prefix}" does not exist in the prefix')
+
# Static mappings don't require anything (but check if IP is in subnet if it's set)
if 'static_mapping' in subnet_config:
for mapping, mapping_config in subnet_config['static_mapping'].items():
--
cgit v1.2.3
From 9ba7093563d4c6a5d37da928298e6e7c7f0b3cd8 Mon Sep 17 00:00:00 2001
From: sarthurdev <965089+sarthurdev@users.noreply.github.com>
Date: Sat, 20 Jan 2024 21:47:23 +0100
Subject: dhcp: T3316: Fix header on script
---
src/system/on-dhcp-event.sh | 24 ++++++++++++++++--------
1 file changed, 16 insertions(+), 8 deletions(-)
(limited to 'src')
diff --git a/src/system/on-dhcp-event.sh b/src/system/on-dhcp-event.sh
index 52fadd428..47c276270 100755
--- a/src/system/on-dhcp-event.sh
+++ b/src/system/on-dhcp-event.sh
@@ -1,12 +1,20 @@
#!/bin/bash
-
-# This script came from ubnt.com forum user "bradd" in the following post
-# http://community.ubnt.com/t5/EdgeMAX/Automatic-DNS-resolution-of-DHCP-client-names/td-p/651311
-# It has been modified by Ubiquiti to update the /etc/host file
-# instead of adding to the CLI.
-# Thanks to forum user "itsmarcos" for bug fix & improvements
-# Thanks to forum user "ruudboon" for multiple domain fix
-# Thanks to forum user "chibby85" for expire patch and static-mapping
+#
+# Copyright (C) 2024 VyOS maintainers and contributors
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2 or later as
+# published by the Free Software Foundation.
+#
+# 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, see .
+#
+#
if [ $# -lt 1 ]; then
echo Invalid args
--
cgit v1.2.3
From dca220d515e6c1009b316400174382b88837df6c Mon Sep 17 00:00:00 2001
From: Chris Buechler
Date: Thu, 25 Jan 2024 16:36:33 -0600
Subject: Updates to Kea DHCPv6 PD route hook (#6)
* Fix route deletion errors when interface is missing. Clarify variable names.
---
src/system/on-dhcpv6-event.sh | 35 ++++++++++++++++++++++-------------
1 file changed, 22 insertions(+), 13 deletions(-)
(limited to 'src')
diff --git a/src/system/on-dhcpv6-event.sh b/src/system/on-dhcpv6-event.sh
index fcc88ae6f..cbb370999 100755
--- a/src/system/on-dhcpv6-event.sh
+++ b/src/system/on-dhcpv6-event.sh
@@ -31,16 +31,23 @@ case "$action" in
lease6_release|lease6_expire|lease6_decline)
ifname=$QUERY6_IFACE_NAME
- client_ip=$LEASE6_ADDRESS
- client_prefix_len=$LEASE6_PREFIX_LEN
+ lease_addr=$LEASE6_ADDRESS
+ lease_prefix_len=$LEASE6_PREFIX_LEN
if [[ "$LEASE6_TYPE" != "IA_PD" ]]; then
exit 0
fi
- sudo -n /sbin/ip -6 route del ${client_ip}/${client_prefix_len} \
- dev ${ifname} \
- proto static
+ logger -s -t on-dhcpv6-event "Processing route deletion for ${lease_addr}/${lease_prefix_len}"
+ route_cmd="sudo -n /sbin/ip -6 route del ${lease_addr}/${lease_prefix_len}"
+
+ # the ifname is not always present, like in LEASE6_VALID_LIFETIME=0 updates,
+ # but 'route del' works either way. Use interface only if there is one.
+ if [[ "$ifname" != "" ]]; then
+ route_cmd+=" dev ${ifname}"
+ fi
+ route_cmd+=" proto static"
+ eval "$route_cmd"
exit 0
;;
@@ -49,20 +56,22 @@ case "$action" in
for ((i = 0; i < $LEASES6_SIZE; i++)); do
ifname=$QUERY6_IFACE_NAME
requester_link_local=$QUERY6_REMOTE_ADDR
- client_type_var="LEASES6_AT${i}_TYPE"
- client_ip_var="LEASES6_AT${i}_ADDRESS"
- client_prefix_len_var="LEASES6_AT${i}_PREFIX_LEN"
+ lease_type_var="LEASES6_AT${i}_TYPE"
+ lease_ip_var="LEASES6_AT${i}_ADDRESS"
+ lease_prefix_len_var="LEASES6_AT${i}_PREFIX_LEN"
- client_type=${!client_type_var}
+ lease_type=${!lease_type_var}
- if [[ "$client_type" != "IA_PD" ]]; then
+ if [[ "$lease_type" != "IA_PD" ]]; then
continue
fi
- client_ip=${!client_ip_var}
- client_prefix_len=${!client_prefix_len_var}
+ lease_ip=${!lease_ip_var}
+ lease_prefix_len=${!lease_prefix_len_var}
+
+ logger -s -t on-dhcpv6-event "Processing PD route for ${lease_addr}/${lease_prefix_len}. Link local: ${requester_link_local} ifname: ${ifname}"
- sudo -n /sbin/ip -6 route replace ${client_ip}/${client_prefix_len} \
+ sudo -n /sbin/ip -6 route replace ${lease_ip}/${lease_prefix_len} \
via ${requester_link_local} \
dev ${ifname} \
proto static
--
cgit v1.2.3