Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/netbsd-8]: src/sys Pull up following revision(s) (requested by ozaki-r i...



details:   https://anonhg.NetBSD.org/src/rev/7e63524d7e55
branches:  netbsd-8
changeset: 434455:7e63524d7e55
user:      martin <martin%NetBSD.org@localhost>
date:      Thu Nov 30 14:40:46 2017 +0000

description:
Pull up following revision(s) (requested by ozaki-r in ticket #405):
        sys/sys/pserialize.h: revision 1.2
        sys/kern/kern_lock.c: revision 1.160
        sys/kern/subr_pserialize.c: revision 1.9
        sys/rump/librump/rumpkern/emul.c: revision 1.184
        sys/rump/librump/rumpkern/emul.c: revision 1.185
        sys/rump/librump/rumpkern/rump.c: revision 1.330
Implement debugging feature for pserialize(9)
The debugging feature detects violations of pserialize constraints.
It causes a panic:
- if a context switch happens in a read section, or
- if a sleepable function is called in a read section.
The feature is enabled only if LOCKDEBUG is on.
Discussed on tech-kern@
Add missing inclusion of pserialize.h (fix build)

diffstat:

 sys/kern/kern_lock.c             |   8 ++-
 sys/kern/subr_pserialize.c       |  98 ++++++++++++++++++++++++++++++++++++++-
 sys/rump/librump/rumpkern/emul.c |  17 ++++++-
 sys/rump/librump/rumpkern/rump.c |   6 +-
 sys/sys/pserialize.h             |   4 +-
 5 files changed, 122 insertions(+), 11 deletions(-)

diffs (290 lines):

diff -r cb8777dc89c8 -r 7e63524d7e55 sys/kern/kern_lock.c
--- a/sys/kern/kern_lock.c      Thu Nov 30 14:31:04 2017 +0000
+++ b/sys/kern/kern_lock.c      Thu Nov 30 14:40:46 2017 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: kern_lock.c,v 1.158 2017/01/26 04:11:56 christos Exp $ */
+/*     $NetBSD: kern_lock.c,v 1.158.6.1 2017/11/30 14:40:46 martin Exp $       */
 
 /*-
  * Copyright (c) 2002, 2006, 2007, 2008, 2009 The NetBSD Foundation, Inc.
@@ -31,7 +31,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kern_lock.c,v 1.158 2017/01/26 04:11:56 christos Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kern_lock.c,v 1.158.6.1 2017/11/30 14:40:46 martin Exp $");
 
 #include <sys/param.h>
 #include <sys/proc.h>
@@ -43,6 +43,7 @@
 #include <sys/syslog.h>
 #include <sys/atomic.h>
 #include <sys/lwp.h>
+#include <sys/pserialize.h>
 
 #include <machine/lock.h>
 
@@ -88,6 +89,9 @@
        if (cpu_softintr_p()) {
                reason = "softint";
        }
+       if (!pserialize_not_in_read_section()) {
+               reason = "pserialize";
+       }
 
        if (reason) {
                panic("%s: %s caller=%p", __func__, reason,
diff -r cb8777dc89c8 -r 7e63524d7e55 sys/kern/subr_pserialize.c
--- a/sys/kern/subr_pserialize.c        Thu Nov 30 14:31:04 2017 +0000
+++ b/sys/kern/subr_pserialize.c        Thu Nov 30 14:40:46 2017 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: subr_pserialize.c,v 1.8 2015/06/12 19:18:30 dholland Exp $     */
+/*     $NetBSD: subr_pserialize.c,v 1.8.10.1 2017/11/30 14:40:46 martin Exp $  */
 
 /*-
  * Copyright (c) 2010, 2011 The NetBSD Foundation, Inc.
@@ -38,7 +38,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: subr_pserialize.c,v 1.8 2015/06/12 19:18:30 dholland Exp $");
+__KERNEL_RCSID(0, "$NetBSD: subr_pserialize.c,v 1.8.10.1 2017/11/30 14:40:46 martin Exp $");
 
 #include <sys/param.h>
 
@@ -73,6 +73,12 @@
 static TAILQ_HEAD(, pserialize)        psz_queue1      __cacheline_aligned;
 static TAILQ_HEAD(, pserialize)        psz_queue2      __cacheline_aligned;
 
+#ifdef LOCKDEBUG
+#include <sys/percpu.h>
+
+static percpu_t                *psz_debug_nreads       __cacheline_aligned;
+#endif
+
 /*
  * pserialize_init:
  *
@@ -89,6 +95,9 @@
        mutex_init(&psz_lock, MUTEX_DEFAULT, IPL_SCHED);
        evcnt_attach_dynamic(&psz_ev_excl, EVCNT_TYPE_MISC, NULL,
            "pserialize", "exclusive access");
+#ifdef LOCKDEBUG
+       psz_debug_nreads = percpu_alloc(sizeof(uint32_t));
+#endif
 }
 
 /*
@@ -185,15 +194,37 @@
 int
 pserialize_read_enter(void)
 {
+       int s;
 
        KASSERT(!cpu_intr_p());
-       return splsoftserial();
+       s = splsoftserial();
+#ifdef LOCKDEBUG
+       {
+               uint32_t *nreads;
+               nreads = percpu_getref(psz_debug_nreads);
+               (*nreads)++;
+               if (*nreads == 0)
+                       panic("nreads overflow");
+               percpu_putref(psz_debug_nreads);
+       }
+#endif
+       return s;
 }
 
 void
 pserialize_read_exit(int s)
 {
 
+#ifdef LOCKDEBUG
+       {
+               uint32_t *nreads;
+               nreads = percpu_getref(psz_debug_nreads);
+               (*nreads)--;
+               if (*nreads == UINT_MAX)
+                       panic("nreads underflow");
+               percpu_putref(psz_debug_nreads);
+       }
+#endif
        splx(s);
 }
 
@@ -209,6 +240,9 @@
        pserialize_t psz, next;
        cpuid_t cid;
 
+       /* We must to ensure not to come here from inside a read section. */
+       KASSERT(pserialize_not_in_read_section());
+
        /*
         * If no updates pending, bail out.  No need to lock in order to
         * test psz_work_todo; the only ill effect of missing an update
@@ -261,3 +295,61 @@
        }
        mutex_spin_exit(&psz_lock);
 }
+
+/*
+ * pserialize_in_read_section:
+ *
+ *   True if the caller is in a pserialize read section.  To be used only
+ *   for diagnostic assertions where we want to guarantee the condition like:
+ *
+ *     KASSERT(pserialize_in_read_section());
+ */
+bool
+pserialize_in_read_section(void)
+{
+#ifdef LOCKDEBUG
+       uint32_t *nreads;
+       bool in;
+
+       /* Not initialized yet */
+       if (__predict_false(psz_debug_nreads == NULL))
+               return true;
+
+       nreads = percpu_getref(psz_debug_nreads);
+       in = *nreads != 0;
+       percpu_putref(psz_debug_nreads);
+
+       return in;
+#else
+       return true;
+#endif
+}
+
+/*
+ * pserialize_not_in_read_section:
+ *
+ *   True if the caller is not in a pserialize read section.  To be used only
+ *   for diagnostic assertions where we want to guarantee the condition like:
+ *
+ *     KASSERT(pserialize_not_in_read_section());
+ */
+bool
+pserialize_not_in_read_section(void)
+{
+#ifdef LOCKDEBUG
+       uint32_t *nreads;
+       bool notin;
+
+       /* Not initialized yet */
+       if (__predict_false(psz_debug_nreads == NULL))
+               return true;
+
+       nreads = percpu_getref(psz_debug_nreads);
+       notin = *nreads == 0;
+       percpu_putref(psz_debug_nreads);
+
+       return notin;
+#else
+       return true;
+#endif
+}
diff -r cb8777dc89c8 -r 7e63524d7e55 sys/rump/librump/rumpkern/emul.c
--- a/sys/rump/librump/rumpkern/emul.c  Thu Nov 30 14:31:04 2017 +0000
+++ b/sys/rump/librump/rumpkern/emul.c  Thu Nov 30 14:40:46 2017 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: emul.c,v 1.181.6.1 2017/06/04 20:35:01 bouyer Exp $    */
+/*     $NetBSD: emul.c,v 1.181.6.2 2017/11/30 14:40:46 martin Exp $    */
 
 /*
  * Copyright (c) 2007-2011 Antti Kantee.  All Rights Reserved.
@@ -26,7 +26,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: emul.c,v 1.181.6.1 2017/06/04 20:35:01 bouyer Exp $");
+__KERNEL_RCSID(0, "$NetBSD: emul.c,v 1.181.6.2 2017/11/30 14:40:46 martin Exp $");
 
 #include <sys/param.h>
 #include <sys/cprng.h>
@@ -36,6 +36,7 @@
 #include <sys/module.h>
 #include <sys/reboot.h>
 #include <sys/syscall.h>
+#include <sys/pserialize.h>
 #ifdef LOCKDEBUG
 #include <sys/sleepq.h>
 #endif
@@ -165,11 +166,23 @@
        return t;
 }
 
+#define        RETURN_ADDRESS  (uintptr_t)__builtin_return_address(0)
+
 void
 assert_sleepable(void)
 {
+       const char *reason = NULL;
 
        /* always sleepable, although we should improve this */
+
+       if (!pserialize_not_in_read_section()) {
+               reason = "pserialize";
+       }
+
+       if (reason) {
+               panic("%s: %s caller=%p", __func__, reason,
+                   (void *)RETURN_ADDRESS);
+       }
 }
 
 void
diff -r cb8777dc89c8 -r 7e63524d7e55 sys/rump/librump/rumpkern/rump.c
--- a/sys/rump/librump/rumpkern/rump.c  Thu Nov 30 14:31:04 2017 +0000
+++ b/sys/rump/librump/rumpkern/rump.c  Thu Nov 30 14:40:46 2017 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: rump.c,v 1.329 2016/03/08 14:30:48 joerg Exp $ */
+/*     $NetBSD: rump.c,v 1.329.10.1 2017/11/30 14:40:46 martin Exp $   */
 
 /*
  * Copyright (c) 2007-2011 Antti Kantee.  All Rights Reserved.
@@ -26,7 +26,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: rump.c,v 1.329 2016/03/08 14:30:48 joerg Exp $");
+__KERNEL_RCSID(0, "$NetBSD: rump.c,v 1.329.10.1 2017/11/30 14:40:46 martin Exp $");
 
 #include <sys/systm.h>
 #define ELFSIZE ARCH_ELFSIZE
@@ -301,6 +301,7 @@
        callout_startup();
 
        kprintf_init();
+       percpu_init();
        pserialize_init();
 
        kauth_init();
@@ -351,7 +352,6 @@
        rump_schedule();
        bootlwp = curlwp;
 
-       percpu_init();
        inittimecounter();
        ntp_init();
 
diff -r cb8777dc89c8 -r 7e63524d7e55 sys/sys/pserialize.h
--- a/sys/sys/pserialize.h      Thu Nov 30 14:31:04 2017 +0000
+++ b/sys/sys/pserialize.h      Thu Nov 30 14:40:46 2017 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: pserialize.h,v 1.1 2011/07/30 17:01:04 christos Exp $  */
+/*     $NetBSD: pserialize.h,v 1.1.46.1 2017/11/30 14:40:46 martin Exp $       */
 
 /*-
  * Copyright (c) 2010, 2011 The NetBSD Foundation, Inc.
@@ -44,6 +44,8 @@
 int            pserialize_read_enter(void);
 void           pserialize_read_exit(int);
 
+bool           pserialize_in_read_section(void);
+bool           pserialize_not_in_read_section(void);
 #endif /* _KERNEL */
 
 #endif /* _SYS_PSERIALIZE_H_ */



Home | Main Index | Thread Index | Old Index