summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Härdeman2024-12-28 16:54:49 +0000
committerdedeckeh2024-12-29 11:50:42 +0000
commitc89b8b3f2ff31084d1bebbb414f396eb3c993e6a (patch)
tree569588714c51158489c15aae5c1591fca6daa48c
parent6d342cc03bf72f27d0838942d009bf1c5df4f954 (diff)
downloadodhcpd-c89b8b3f2ff31084d1bebbb414f396eb3c993e6a.tar.gz
odhcpd: make the IPv6 RA DNR lifetime configurable
Add a fake SVC parameter "_lifetime=" which allows explicit configuration of the maximum time in seconds over which a given ADN announcement is valid. In particular, this allows announcing ADNs which should no longer be used (zero lifetime, see rfc9463, §6.1). In the absence of an explicit lifetime, the previous logic is kept (i.e. the lifetime is set to 3 * MaxRtrAdvInterval, as per §6.1 of RFC9463). Signed-off-by: David Härdeman <david@hardeman.nu>
-rw-r--r--src/config.c13
-rw-r--r--src/odhcpd.h3
-rw-r--r--src/router.c5
3 files changed, 20 insertions, 1 deletions
diff --git a/src/config.c b/src/config.c
index 2eba544..42fc2fe 100644
--- a/src/config.c
+++ b/src/config.c
@@ -661,6 +661,19 @@ static int parse_dnr_str(char *str, struct interface *iface)
svc_key = strtok_r(svc_tok, "=", &saveptr2);
svc_val = strtok_r(NULL, "=", &saveptr2);
+ if (!strcmp(svc_key, "_lifetime")) {
+ uint32_t lifetime;
+
+ if (!svc_val || sscanf(svc_val, "%" SCNu32, &lifetime) != 1) {
+ syslog(LOG_ERR, "Invalid value '%s' for _lifetime", svc_val ? svc_val : "");
+ goto err;
+ }
+
+ dnr.lifetime = lifetime;
+ dnr.lifetime_set = true;
+ continue;
+ }
+
for (svc_id = 0; svc_id < DNR_SVC_MAX; svc_id++)
if (!strcmp(svc_key, svc_param_key_names[svc_id]))
break;
diff --git a/src/odhcpd.h b/src/odhcpd.h
index 473c95b..4d589f8 100644
--- a/src/odhcpd.h
+++ b/src/odhcpd.h
@@ -249,6 +249,9 @@ struct dhcp_assignment {
struct dnr_options {
uint16_t priority;
+ uint32_t lifetime;
+ bool lifetime_set;
+
uint8_t *adn;
uint16_t adn_len;
diff --git a/src/router.c b/src/router.c
index 722f2e3..b630953 100644
--- a/src/router.c
+++ b/src/router.c
@@ -824,7 +824,10 @@ pref64_out:
dnr->type = ND_OPT_DNR;
dnr->len = dnr_sz[i] / 8;
dnr->priority = htons(iface->dnr[i].priority);
- dnr->lifetime = htonl(lifetime);
+ if (iface->dnr[i].lifetime_set)
+ dnr->lifetime = htonl(iface->dnr[i].lifetime);
+ else
+ dnr->lifetime = htonl(lifetime);
dnr->adn_len = htons(iface->dnr[i].adn_len);
memcpy(tmp, iface->dnr[i].adn, iface->dnr[i].adn_len);