Index | Thread | Search

From:
Florian Obser <florian@openbsd.org>
Subject:
dhcp6leased(8): Find interfaces with changed configuration during reload.
To:
tech <tech@openbsd.org>
Date:
Thu, 18 Sep 2025 18:43:17 +0200

Download raw body.

Thread
  • Florian Obser:

    dhcp6leased(8): Find interfaces with changed configuration during reload.

I doubt dhcp6leased(8) always does the right thing though. But at
least it detects a config change now.

OK?

diff --git frontend.c frontend.c
index fb6e51b4515..373cfa604b7 100644
--- frontend.c
+++ frontend.c
@@ -84,6 +84,8 @@ void		 iface_data_from_imsg(struct iface*, struct imsg_req_dhcp *);
 ssize_t		 build_packet(uint8_t, struct iface *, char *);
 void		 send_packet(uint8_t, struct iface *);
 int		 iface_conf_cmp(struct iface_conf *, struct iface_conf *);
+int		 ia_conf_cmp(struct iface_ia_conf *, struct iface_ia_conf *);
+int		 pd_conf_cmp(struct iface_pd_conf *, struct iface_pd_conf *);
 
 LIST_HEAD(, iface)		 interfaces;
 struct dhcp6leased_conf		*frontend_conf;
@@ -1048,7 +1050,7 @@ changed_ifaces(struct dhcp6leased_conf *oconf, struct dhcp6leased_conf *nconf)
 		if (oiface_conf == NULL) {
 			/* new interface added to config */
 			ret[i++] = if_index;
-		} else if (iface_conf_cmp(iface_conf, oiface_conf) != 0) {
+		} else if (!iface_conf_cmp(iface_conf, oiface_conf)) {
 			/* interface conf changed */
 			ret[i++] = if_index;
 		}
@@ -1068,5 +1070,73 @@ changed_ifaces(struct dhcp6leased_conf *oconf, struct dhcp6leased_conf *nconf)
 int
 iface_conf_cmp(struct iface_conf *a, struct iface_conf *b)
 {
-	return 0;
+	struct iface_ia_conf	*ia_a, *ia_b;
+
+	if (a == NULL && b == NULL)
+		return 1;
+	if (a == NULL || b == NULL)
+		return 0;
+
+	if (a->ia_count != b->ia_count)
+		return 0;
+
+	ia_a = SIMPLEQ_FIRST(&a->iface_ia_list);
+	ia_b = SIMPLEQ_FIRST(&b->iface_ia_list);
+
+	for (;;) {
+		if (!ia_conf_cmp(ia_a, ia_b))
+			return 0;
+		if (ia_a == NULL && ia_b == NULL)
+			return 1;
+		ia_a = SIMPLEQ_NEXT(ia_a, entry);
+		ia_b = SIMPLEQ_NEXT(ia_b, entry);
+
+	}
+	return 1;
+}
+
+int
+ia_conf_cmp(struct iface_ia_conf *a, struct iface_ia_conf *b)
+{
+	struct iface_pd_conf *pd_a, *pd_b;
+
+	if (a == NULL && b == NULL)
+		return 1;
+	if (a == NULL || b == NULL)
+		return 0;
+
+	if (a->id != b->id)
+		return 0;
+	if (a->prefix_len != b->prefix_len)
+		return 0;
+
+	pd_a = SIMPLEQ_FIRST(&a->iface_pd_list);
+	pd_b = SIMPLEQ_FIRST(&b->iface_pd_list);
+
+	for (;;) {
+		if (!pd_conf_cmp(pd_a, pd_b))
+			return 0;
+
+		if (pd_a == NULL && pd_b == NULL)
+			return 1;
+
+		pd_a = SIMPLEQ_NEXT(pd_a, entry);
+		pd_b = SIMPLEQ_NEXT(pd_b, entry);
+
+	}
+	return 1;
+
+}
+
+int
+pd_conf_cmp(struct iface_pd_conf *a, struct iface_pd_conf *b)
+{
+	if (a == NULL && b == NULL)
+		return 1;
+	if (a == NULL || b == NULL)
+		return 0;
+
+	return (strcmp(a->name, b->name) == 0 && memcmp(&a->prefix_mask,
+	    &b->prefix_mask, sizeof(a->prefix_mask)) == 0 && a->prefix_len ==
+	    b->prefix_len);
 }

-- 
In my defence, I have been left unsupervised.