diff options
| author | ad <ad@NetBSD.org> | 2019-12-01 14:52:13 +0000 |
|---|---|---|
| committer | ad <ad@NetBSD.org> | 2019-12-01 14:52:13 +0000 |
| commit | 127d8dcb20106ef5e787aef30c1dfea9ce9aa55c (patch) | |
| tree | eaf953452d4c79f885828831eadb5e76115b3b0f /sys/arch/usermode/dev | |
| parent | 6f2074f9e5e04514d97bc33ca10284087cc0b70e (diff) | |
Make cpu_intr_p() safe to use anywhere, i.e. outside assertions:
Don't call kpreempt_disable() / kpreempt_enable() to make sure we're not
preempted while using the value of curcpu(). Instead, observe the value of
l_ncsw before and after the check to see if we have been preempted. If
we have been preempted, then we need to retry the read.
Diffstat (limited to 'sys/arch/usermode/dev')
| -rw-r--r-- | sys/arch/usermode/dev/cpu.c | 16 |
1 files changed, 10 insertions, 6 deletions
diff --git a/sys/arch/usermode/dev/cpu.c b/sys/arch/usermode/dev/cpu.c index eb74d093f43..1cf1de2c01b 100644 --- a/sys/arch/usermode/dev/cpu.c +++ b/sys/arch/usermode/dev/cpu.c @@ -1,4 +1,4 @@ -/* $NetBSD: cpu.c,v 1.81 2019/11/23 19:40:37 ad Exp $ */ +/* $NetBSD: cpu.c,v 1.82 2019/12/01 14:52:14 ad Exp $ */ /*- * Copyright (c) 2007 Jared D. McNeill <jmcneill@invisible.ca> @@ -30,7 +30,7 @@ #include "opt_hz.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.81 2019/11/23 19:40:37 ad Exp $"); +__KERNEL_RCSID(0, "$NetBSD: cpu.c,v 1.82 2019/12/01 14:52:14 ad Exp $"); #include <sys/param.h> #include <sys/conf.h> @@ -528,11 +528,15 @@ cpu_rootconf(void) bool cpu_intr_p(void) { + uint64_t ncsw; int idepth; + lwp_t *l; - kpreempt_disable(); - idepth = curcpu()->ci_idepth; - kpreempt_enable(); + l = curlwp; + do { + ncsw = l->l_ncsw; + idepth = l->l_cpu->ci_idepth; + } while (__predict_false(ncsw != l->l_ncsw)); - return (idepth >= 0); + return idepth >= 0; } |
