Use domain name for socket lock.
authorbluhm <bluhm@openbsd.org>
Thu, 11 Jan 2024 14:15:11 +0000 (14:15 +0000)
committerbluhm <bluhm@openbsd.org>
Thu, 11 Jan 2024 14:15:11 +0000 (14:15 +0000)
Syzkaller with witness complains about lock ordering of pf lock
with socket lock.  Socket lock for inet is taken before pf lock.
Pf lock is taken before socket lock for route.  This is a false
positive as route and inet socket locks are distinct.  Witness does
not know this.  Name the socket lock like the domain of the socket,
then rwlock name is used in witness lo_name subtype.  Make domain
names more consistent for locking, they were not used anyway.
Regardless of witness problem, unique lock name for each socket
type make sense.

Reported-by: syzbot+34d22dcbf20d76629c5a@syzkaller.appspotmail.com
Reported-by: syzbot+fde8d07ba74b69d0adfe@syzkaller.appspotmail.com
OK mvs@

sys/kern/uipc_domain.c
sys/kern/uipc_socket.c
sys/kern/uipc_socket2.c
sys/net/pfkeyv2.c
sys/netinet/in_proto.c
sys/netinet6/in6_proto.c
sys/sys/domain.h
sys/sys/protosw.h
sys/sys/socketvar.h

index 78ae090..da73a54 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: uipc_domain.c,v 1.64 2023/05/18 10:23:19 mvs Exp $    */
+/*     $OpenBSD: uipc_domain.c,v 1.65 2024/01/11 14:15:11 bluhm Exp $  */
 /*     $NetBSD: uipc_domain.c,v 1.14 1996/02/09 19:00:44 christos Exp $        */
 
 /*
@@ -62,7 +62,6 @@ const struct domain *const domains[] = {
 
 void           pffasttimo(void *);
 void           pfslowtimo(void *);
-const struct domain *  pffinddomain(int);
 
 void
 domaininit(void)
index 5005fef..913649f 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: uipc_socket.c,v 1.312 2023/12/19 21:34:22 bluhm Exp $ */
+/*     $OpenBSD: uipc_socket.c,v 1.313 2024/01/11 14:15:11 bluhm Exp $ */
 /*     $NetBSD: uipc_socket.c,v 1.21 1996/02/04 02:17:52 christos Exp $        */
 
 /*
@@ -148,7 +148,7 @@ soinit(void)
 }
 
 struct socket *
-soalloc(int wait)
+soalloc(const struct domain *dp, int wait)
 {
        struct socket *so;
 
@@ -156,7 +156,7 @@ soalloc(int wait)
            PR_ZERO);
        if (so == NULL)
                return (NULL);
-       rw_init_flags(&so->so_lock, "solock", RWL_DUPOK);
+       rw_init_flags(&so->so_lock, dp->dom_name, RWL_DUPOK);
        refcnt_init(&so->so_refcnt);
        klist_init(&so->so_rcv.sb_klist, &socket_klistops, so);
        klist_init(&so->so_snd.sb_klist, &socket_klistops, so);
@@ -190,7 +190,7 @@ socreate(int dom, struct socket **aso, int type, int proto)
                return (EPROTONOSUPPORT);
        if (prp->pr_type != type)
                return (EPROTOTYPE);
-       so = soalloc(M_WAIT);
+       so = soalloc(pffinddomain(dom), M_WAIT);
        so->so_type = type;
        if (suser(p) == 0)
                so->so_state = SS_PRIV;
index 18f7746..5b55090 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: uipc_socket2.c,v 1.139 2023/12/18 13:11:20 bluhm Exp $        */
+/*     $OpenBSD: uipc_socket2.c,v 1.140 2024/01/11 14:15:11 bluhm Exp $        */
 /*     $NetBSD: uipc_socket2.c,v 1.11 1996/02/04 02:17:55 christos Exp $       */
 
 /*
@@ -188,7 +188,7 @@ sonewconn(struct socket *head, int connstatus, int wait)
                return (NULL);
        if (head->so_qlen + head->so_q0len > head->so_qlimit * 3)
                return (NULL);
-       so = soalloc(wait);
+       so = soalloc(head->so_proto->pr_domain, wait);
        if (so == NULL)
                return (NULL);
        so->so_type = head->so_type;
index 6916810..a6a1648 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: pfkeyv2.c,v 1.259 2023/10/11 22:13:16 tobhe Exp $ */
+/* $OpenBSD: pfkeyv2.c,v 1.260 2024/01/11 14:15:11 bluhm Exp $ */
 
 /*
  *     @(#)COPYRIGHT   1.1 (NRL) 17 January 1995
@@ -225,7 +225,7 @@ const struct protosw pfkeysw[] = {
 
 const struct domain pfkeydomain = {
   .dom_family = PF_KEY,
-  .dom_name = "PF_KEY",
+  .dom_name = "pfkey",
   .dom_init = pfkey_init,
   .dom_protosw = pfkeysw,
   .dom_protoswNPROTOSW = &pfkeysw[nitems(pfkeysw)],
index d2e67c6..9748baf 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: in_proto.c,v 1.102 2023/07/06 04:55:05 dlg Exp $      */
+/*     $OpenBSD: in_proto.c,v 1.103 2024/01/11 14:15:12 bluhm Exp $    */
 /*     $NetBSD: in_proto.c,v 1.14 1996/02/18 18:58:32 christos Exp $   */
 
 /*
@@ -387,7 +387,7 @@ const struct protosw inetsw[] = {
 
 const struct domain inetdomain = {
   .dom_family = AF_INET,
-  .dom_name = "internet",
+  .dom_name = "inet",
   .dom_init = in_init,
   .dom_protosw = inetsw,
   .dom_protoswNPROTOSW = &inetsw[nitems(inetsw)],
index 4e48a1e..db218af 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: in6_proto.c,v 1.112 2022/11/23 14:48:28 kn Exp $      */
+/*     $OpenBSD: in6_proto.c,v 1.113 2024/01/11 14:15:12 bluhm Exp $   */
 /*     $KAME: in6_proto.c,v 1.66 2000/10/10 15:35:47 itojun Exp $      */
 
 /*
@@ -332,7 +332,7 @@ const struct protosw inet6sw[] = {
 
 const struct domain inet6domain = {
   .dom_family = AF_INET6,
-  .dom_name = "internet6",
+  .dom_name = "inet6",
   .dom_protosw = inet6sw,
   .dom_protoswNPROTOSW = &inet6sw[nitems(inet6sw)],
   .dom_sasize = sizeof(struct sockaddr_in6),
index 478bc19..87d662a 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: domain.h,v 1.23 2022/11/23 14:50:59 kn Exp $  */
+/*     $OpenBSD: domain.h,v 1.24 2024/01/11 14:15:12 bluhm Exp $       */
 /*     $NetBSD: domain.h,v 1.10 1996/02/09 18:25:07 christos Exp $     */
 
 /*
@@ -49,7 +49,7 @@ struct        ifnet;
 
 struct domain {
        int     dom_family;             /* AF_xxx */
-       char    *dom_name;
+       const   char *dom_name;
        void    (*dom_init)(void);      /* initialize domain data structures */
                                        /* externalize access rights */
        int     (*dom_externalize)(struct mbuf *, socklen_t, int);
index 78b439b..03ade94 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: protosw.h,v 1.63 2023/12/18 13:11:20 bluhm Exp $      */
+/*     $OpenBSD: protosw.h,v 1.64 2024/01/11 14:15:12 bluhm Exp $      */
 /*     $NetBSD: protosw.h,v 1.10 1996/04/09 20:55:32 cgd Exp $ */
 
 /*-
@@ -259,6 +259,7 @@ struct ifnet;
 struct sockaddr;
 const struct protosw *pffindproto(int, int, int);
 const struct protosw *pffindtype(int, int);
+const struct domain *pffinddomain(int);
 void pfctlinput(int, struct sockaddr *);
 
 extern u_char ip_protox[];
index 0290d64..41403c0 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: socketvar.h,v 1.120 2023/07/04 22:28:24 mvs Exp $     */
+/*     $OpenBSD: socketvar.h,v 1.121 2024/01/11 14:15:12 bluhm Exp $   */
 /*     $NetBSD: socketvar.h,v 1.18 1996/02/09 18:25:38 christos Exp $  */
 
 /*-
@@ -346,7 +346,7 @@ int soconnect(struct socket *, struct mbuf *);
 int    soconnect2(struct socket *, struct socket *);
 int    socreate(int, struct socket **, int, int);
 int    sodisconnect(struct socket *);
-struct socket *soalloc(int);
+struct socket *soalloc(const struct domain *, int);
 void   sofree(struct socket *, int);
 int    sogetopt(struct socket *, int, int, struct mbuf *);
 void   sohasoutofband(struct socket *);