From 7545646709ce414ab9655df0e566c27f424aed2c Mon Sep 17 00:00:00 2001 From: claudio Date: Thu, 14 Apr 2022 14:10:22 +0000 Subject: [PATCH] Relax address availability check for multicast binds. While it makes sense to limit bind(2) of unicast addresses that overlap each other to be all from the same UID (like 0.0.0.0:53 and 127.0.0.1:53) it makes little sense for multicast. Multicast is delivered to all sockets that match so there is no risk of someone stealing traffic from someone else. This should hopefully help with mDNS as reported by robert@ OK deraadt@ bluhm@ --- sys/netinet/in_pcb.c | 4 ++-- sys/netinet6/in6_pcb.c | 10 ++++------ 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/sys/netinet/in_pcb.c b/sys/netinet/in_pcb.c index 4b00dbfc3d2..9d4749f50e0 100644 --- a/sys/netinet/in_pcb.c +++ b/sys/netinet/in_pcb.c @@ -1,4 +1,4 @@ -/* $OpenBSD: in_pcb.c,v 1.264 2022/03/22 18:02:54 bluhm Exp $ */ +/* $OpenBSD: in_pcb.c,v 1.265 2022/04/14 14:10:22 claudio Exp $ */ /* $NetBSD: in_pcb.c,v 1.25 1996/02/13 23:41:53 christos Exp $ */ /* @@ -404,7 +404,7 @@ in_pcbaddrisavail(struct inpcb *inp, struct sockaddr_in *sin, int wild, if (lport) { struct inpcb *t; - if (so->so_euid) { + if (so->so_euid && !IN_MULTICAST(sin->sin_addr.s_addr)) { t = in_pcblookup_local(table, &sin->sin_addr, lport, INPLOOKUP_WILDCARD, inp->inp_rtableid); if (t && (so->so_euid != t->inp_socket->so_euid)) diff --git a/sys/netinet6/in6_pcb.c b/sys/netinet6/in6_pcb.c index 75fc61ef9d4..115c8167cdf 100644 --- a/sys/netinet6/in6_pcb.c +++ b/sys/netinet6/in6_pcb.c @@ -1,4 +1,4 @@ -/* $OpenBSD: in6_pcb.c,v 1.116 2022/03/21 09:12:34 bluhm Exp $ */ +/* $OpenBSD: in6_pcb.c,v 1.117 2022/04/14 14:10:22 claudio Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -209,16 +209,14 @@ in6_pcbaddrisavail(struct inpcb *inp, struct sockaddr_in6 *sin6, int wild, if (lport) { struct inpcb *t; - if (so->so_euid) { - t = in_pcblookup_local(table, - (struct in_addr *)&sin6->sin6_addr, lport, + if (so->so_euid && !IN6_IS_ADDR_MULTICAST(&sin6->sin6_addr)) { + t = in_pcblookup_local(table, &sin6->sin6_addr, lport, INPLOOKUP_WILDCARD | INPLOOKUP_IPV6, inp->inp_rtableid); if (t && (so->so_euid != t->inp_socket->so_euid)) return (EADDRINUSE); } - t = in_pcblookup_local(table, - (struct in_addr *)&sin6->sin6_addr, lport, + t = in_pcblookup_local(table, &sin6->sin6_addr, lport, wild, inp->inp_rtableid); if (t && (reuseport & t->inp_socket->so_options) == 0) return (EADDRINUSE); -- 2.20.1