aboutsummaryrefslogtreecommitdiff
path: root/sys/netinet
diff options
context:
space:
mode:
authorMark Johnston <markj@FreeBSD.org>2026-02-13 16:50:18 +0000
committerMark Johnston <markj@FreeBSD.org>2026-02-13 19:35:18 +0000
commitd19fd2f349226116f7effb281baa1eb32b8292e7 (patch)
treef68c9ceeda1b17b8fbcb8bc70d22b998a7e94949 /sys/netinet
parent284a0aa96eb63f12831a9e06514a50b2cd80957f (diff)
Diffstat (limited to 'sys/netinet')
-rw-r--r--sys/netinet/igmp.c2
-rw-r--r--sys/netinet/ip_input.c3
-rw-r--r--sys/netinet/ip_mroute.c29
-rw-r--r--sys/netinet/ip_mroute.h6
-rw-r--r--sys/netinet/ip_output.c3
-rw-r--r--sys/netinet/raw_ip.c10
6 files changed, 28 insertions, 25 deletions
diff --git a/sys/netinet/igmp.c b/sys/netinet/igmp.c
index 35128dadffe6..00288356cb1f 100644
--- a/sys/netinet/igmp.c
+++ b/sys/netinet/igmp.c
@@ -3489,7 +3489,7 @@ igmp_intr(struct mbuf *m)
imo.imo_multicast_ttl = 1;
imo.imo_multicast_vif = -1;
- imo.imo_multicast_loop = (V_ip_mrouter != NULL);
+ imo.imo_multicast_loop = V_ip_mrouting_enabled;
/*
* If the user requested that IGMP traffic be explicitly
diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c
index 4b8294c93967..7de3dc24dc53 100644
--- a/sys/netinet/ip_input.c
+++ b/sys/netinet/ip_input.c
@@ -772,7 +772,8 @@ passin:
* RFC 3927 2.7: Do not forward multicast packets from
* IN_LINKLOCAL.
*/
- if (V_ip_mrouter && !IN_LINKLOCAL(ntohl(ip->ip_src.s_addr))) {
+ if (V_ip_mrouting_enabled &&
+ !IN_LINKLOCAL(ntohl(ip->ip_src.s_addr))) {
/*
* If we are acting as a multicast router, all
* incoming multicast packets are passed to the
diff --git a/sys/netinet/ip_mroute.c b/sys/netinet/ip_mroute.c
index fb42c04548e7..7a197e20a62f 100644
--- a/sys/netinet/ip_mroute.c
+++ b/sys/netinet/ip_mroute.c
@@ -169,6 +169,9 @@ SYSCTL_VNET_PCPUSTAT(_net_inet_ip, OID_AUTO, mrtstat, struct mrtstat,
mrtstat, "IPv4 Multicast Forwarding Statistics (struct mrtstat, "
"netinet/ip_mroute.h)");
+VNET_DEFINE_STATIC(struct socket *, ip_mrouter);
+#define V_ip_mrouter VNET(ip_mrouter)
+
VNET_DEFINE_STATIC(u_long, mfchash);
#define V_mfchash VNET(mfchash)
#define MFCHASH(a, g) \
@@ -305,7 +308,7 @@ VNET_DEFINE_STATIC(struct ifnet *, multicast_register_if);
static u_long X_ip_mcast_src(int);
static int X_ip_mforward(struct ip *, struct ifnet *, struct mbuf *,
struct ip_moptions *);
-static int X_ip_mrouter_done(void);
+static void X_ip_mrouter_done(struct socket *);
static int X_ip_mrouter_get(struct socket *, struct sockopt *);
static int X_ip_mrouter_set(struct socket *, struct sockopt *);
static int X_legal_vif_num(int);
@@ -435,7 +438,7 @@ X_ip_mrouter_set(struct socket *so, struct sockopt *sopt)
error = ip_mrouter_init(so, optval);
break;
case MRT_DONE:
- error = ip_mrouter_done();
+ ip_mrouter_done(so);
break;
case MRT_ADD_VIF:
error = sooptcopyin(sopt, &vifc, sizeof vifc, sizeof vifc);
@@ -624,8 +627,7 @@ if_detached_event(void *arg __unused, struct ifnet *ifp)
struct ifnet *free_ptr, *multi_leave;
MRW_WLOCK();
-
- if (V_ip_mrouter == NULL) {
+ if (!V_ip_mrouting_enabled) {
MRW_WUNLOCK();
return;
}
@@ -740,6 +742,7 @@ ip_mrouter_init(struct socket *so, int version)
curvnet);
V_ip_mrouter = so;
+ V_ip_mrouting_enabled = true;
atomic_add_int(&ip_mrouter_cnt, 1);
/* This is a mutex required by buf_ring init, but not used internally */
@@ -756,8 +759,8 @@ ip_mrouter_init(struct socket *so, int version)
/*
* Disable multicast forwarding.
*/
-static int
-X_ip_mrouter_done(void)
+static void
+X_ip_mrouter_done(struct socket *so)
{
struct ifnet **ifps;
int nifp;
@@ -766,22 +769,22 @@ X_ip_mrouter_done(void)
struct bw_upcall *bu;
MRW_TEARDOWN_WLOCK();
-
- if (V_ip_mrouter == NULL) {
+ if (so != V_ip_mrouter) {
MRW_TEARDOWN_WUNLOCK();
- return (EINVAL);
+ return;
}
/*
* Detach/disable hooks to the reset of the system.
*/
V_ip_mrouter = NULL;
+ V_ip_mrouting_enabled = false;
atomic_subtract_int(&ip_mrouter_cnt, 1);
V_mrt_api_config = 0;
/*
- * Wait for all epoch sections to complete to ensure
- * V_ip_mrouter = NULL is visible to others.
+ * Wait for all epoch sections to complete to ensure the new value of
+ * V_ip_mrouting_enabled is visible to others.
*/
NET_EPOCH_WAIT();
@@ -856,8 +859,6 @@ X_ip_mrouter_done(void)
free(ifps, M_TEMP);
CTR1(KTR_IPMF, "%s: done", __func__);
-
- return 0;
}
/*
@@ -2872,7 +2873,7 @@ ip_mroute_modevent(module_t mod, int type, void *unused)
MRW_WLOCK();
if (ip_mrouter_cnt != 0) {
MRW_WUNLOCK();
- return (EINVAL);
+ return (EBUSY);
}
ip_mrouter_unloading = 1;
MRW_WUNLOCK();
diff --git a/sys/netinet/ip_mroute.h b/sys/netinet/ip_mroute.h
index 6f09006ec9e2..5c2527ea64e5 100644
--- a/sys/netinet/ip_mroute.h
+++ b/sys/netinet/ip_mroute.h
@@ -356,8 +356,8 @@ struct bw_meter {
};
#ifdef _KERNEL
-VNET_DECLARE(struct socket *, ip_mrouter); /* multicast routing daemon */
-#define V_ip_mrouter VNET(ip_mrouter)
+VNET_DECLARE(bool, ip_mrouting_enabled);
+#define V_ip_mrouting_enabled VNET(ip_mrouting_enabled)
struct ifnet;
struct ip;
@@ -369,7 +369,7 @@ struct sockopt;
extern u_long (*ip_mcast_src)(int);
extern int (*ip_mforward)(struct ip *, struct ifnet *, struct mbuf *,
struct ip_moptions *);
-extern int (*ip_mrouter_done)(void);
+extern void (*ip_mrouter_done)(struct socket *);
extern int (*ip_mrouter_get)(struct socket *, struct sockopt *);
extern int (*ip_mrouter_set)(struct socket *, struct sockopt *);
diff --git a/sys/netinet/ip_output.c b/sys/netinet/ip_output.c
index 1edc4906b542..8af44c6a200d 100644
--- a/sys/netinet/ip_output.c
+++ b/sys/netinet/ip_output.c
@@ -610,7 +610,8 @@ again:
* above, will be forwarded by the ip_input() routine,
* if necessary.
*/
- if (V_ip_mrouter && (flags & IP_FORWARDING) == 0) {
+ if (V_ip_mrouting_enabled &&
+ (flags & IP_FORWARDING) == 0) {
/*
* If rsvp daemon is not running, do not
* set ip_moptions. This ensures that the packet
diff --git a/sys/netinet/raw_ip.c b/sys/netinet/raw_ip.c
index bfe608be6b36..e0e7aed04cd0 100644
--- a/sys/netinet/raw_ip.c
+++ b/sys/netinet/raw_ip.c
@@ -106,16 +106,16 @@ int (*ng_ipfw_input_p)(struct mbuf **, struct ip_fw_args *, bool);
*/
/*
- * The socket used to communicate with the multicast routing daemon.
+ * A per-VNET flag indicating whether multicast routing is enabled.
*/
-VNET_DEFINE(struct socket *, ip_mrouter);
+VNET_DEFINE(bool, ip_mrouting_enabled);
/*
* The various mrouter and rsvp functions.
*/
int (*ip_mrouter_set)(struct socket *, struct sockopt *);
int (*ip_mrouter_get)(struct socket *, struct sockopt *);
-int (*ip_mrouter_done)(void);
+void (*ip_mrouter_done)(struct socket *);
int (*ip_mforward)(struct ip *, struct ifnet *, struct mbuf *,
struct ip_moptions *);
int (*mrt_ioctl)(u_long, caddr_t, int);
@@ -860,8 +860,8 @@ rip_detach(struct socket *so)
("rip_detach: not closed"));
/* Disable mrouter first */
- if (so == V_ip_mrouter && ip_mrouter_done)
- ip_mrouter_done();
+ if (ip_mrouter_done != NULL)
+ ip_mrouter_done(so);
INP_WLOCK(inp);
INP_HASH_WLOCK(&V_ripcbinfo);