summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorpascoe <pascoe@openbsd.org>2004-12-20 07:24:38 +0000
committerpascoe <pascoe@openbsd.org>2004-12-20 07:24:38 +0000
commitff16239745f0aafaa17c066e156856fa37040c13 (patch)
tree2ff119a2caa1927bd4318a0e0c2ac56a42dcc50b
parentsync (diff)
downloadwireguard-openbsd-ff16239745f0aafaa17c066e156856fa37040c13.tar.xz
wireguard-openbsd-ff16239745f0aafaa17c066e156856fa37040c13.zip
Enforce an ordering on ifnet such that CARP interfaces appear later in the
list than physical interfaces. This makes ifa_ifwith* prefer a physical interface over a CARP one. This addresses the problem where a CARP interface in BACKUP state is selected after a route change, resulting in a loss of communications despite there being another interface available which is perfectly usable. ok mcbride@ mpf@
-rw-r--r--sys/net/if.c21
1 files changed, 19 insertions, 2 deletions
diff --git a/sys/net/if.c b/sys/net/if.c
index c57620c5e46..58d58735e42 100644
--- a/sys/net/if.c
+++ b/sys/net/if.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: if.c,v 1.99 2004/12/08 07:02:16 mcbride Exp $ */
+/* $OpenBSD: if.c,v 1.100 2004/12/20 07:24:38 pascoe Exp $ */
/* $NetBSD: if.c,v 1.35 1996/05/07 05:26:04 thorpej Exp $ */
/*
@@ -407,6 +407,10 @@ void
if_attach(ifp)
struct ifnet *ifp;
{
+#if NCARP > 0
+ struct ifnet *before = NULL;
+#endif
+
if (if_index == 0) {
TAILQ_INIT(&ifnet);
TAILQ_INIT(&ifg_head);
@@ -417,7 +421,20 @@ if_attach(ifp)
if (ifp->if_addrhooks == NULL)
panic("if_attach: malloc");
TAILQ_INIT(ifp->if_addrhooks);
+
+#if NCARP > 0
+ if (ifp->if_type != IFT_CARP)
+ TAILQ_FOREACH(before, &ifnet, if_list)
+ if (before->if_type == IFT_CARP)
+ break;
+ if (before == NULL)
+ TAILQ_INSERT_TAIL(&ifnet, ifp, if_list);
+ else
+ TAILQ_INSERT_BEFORE(before, ifp, if_list);
+#else
TAILQ_INSERT_TAIL(&ifnet, ifp, if_list);
+#endif
+
if_attachsetup(ifp);
}
@@ -883,7 +900,7 @@ ifa_ifwithdstaddr(addr)
TAILQ_FOREACH(ifp, &ifnet, if_list) {
if (ifp->if_flags & IFF_POINTOPOINT)
- TAILQ_FOREACH(ifa, &ifp->if_addrlist, ifa_list) {
+ TAILQ_FOREACH(ifa, &ifp->if_addrlist, ifa_list) {
if (ifa->ifa_addr->sa_family != addr->sa_family ||
ifa->ifa_dstaddr == NULL)
continue;