svn commit: r284029 - head/sys/kern
John Baldwin
jhb at freebsd.org
Fri Jun 5 17:45:30 UTC 2015
On Friday, June 05, 2015 04:21:44 PM Sean Bruno wrote:
> Author: sbruno
> Date: Fri Jun 5 16:21:43 2015
> New Revision: 284029
> URL: https://svnweb.freebsd.org/changeset/base/284029
>
> Log:
> This change uses a reader count instead of holding the mutex for the
> interpreter list to avoid the problem of holding a non-sleep lock during
> a page fault as reported by witness. In addition, it consistently uses
> memset()/memcpy() instead of bzero()/bcopy() except in the case where
> bcopy() is required (i.e. overlapping copy).
>
> Differential Revision: https://reviews.freebsd.org/D2123
> Submitted by: sson
> MFC after: 2 weeks
> Relnotes: Yes
>
> Modified:
> head/sys/kern/imgact_binmisc.c
>
> Modified: head/sys/kern/imgact_binmisc.c
> ==============================================================================
> --- head/sys/kern/imgact_binmisc.c Fri Jun 5 16:02:24 2015 (r284028)
> +++ head/sys/kern/imgact_binmisc.c Fri Jun 5 16:21:43 2015 (r284029)
> @@ -1,5 +1,5 @@
> /*-
> - * Copyright (c) 2013, Stacey D. Son
> + * Copyright (c) 2013-15, Stacey D. Son
> * All rights reserved.
> *
> * Redistribution and use in source and binary forms, with or without
> @@ -41,6 +41,9 @@ __FBSDID("$FreeBSD$");
> #include <sys/malloc.h>
> #include <sys/mutex.h>
> #include <sys/sysctl.h>
> +#include <sys/sx.h>
> +
> +#include <machine/atomic.h>
>
> /**
> * Miscellaneous binary interpreter image activator.
> @@ -95,11 +98,68 @@ static SLIST_HEAD(, imgact_binmisc_entry
> SLIST_HEAD_INITIALIZER(interpreter_list);
>
> static int interp_list_entry_count = 0;
> -
> +static int interp_list_rcount = 0;
This should probably be volatile?
> static struct mtx interp_list_mtx;
>
> int imgact_binmisc_exec(struct image_params *imgp);
>
> +static inline void
> +interp_list_rlock()
> +{
> +
> + /* Don't use atomic_add() here. We must block if the mutex is held. */
> + mtx_lock(&interp_list_mtx);
> + interp_list_rcount++;
> + mtx_unlock(&interp_list_mtx);
It's not really safe to not use an atomic here but use one in runlock.
What happens if the compiler uses separate load - add - store here and
another thread does the atomic subtract after the load but before the
store?
> +}
> +
> +static inline void
> +interp_list_runlock()
> +{
> +
> + /* Decrement the reader count and wake up one writer, if any. */
> + atomic_subtract_int(&interp_list_rcount, 1);
> + if (interp_list_rcount == 0)
> + wakeup_one(&interp_list_rcount);
Reading the variable after subtract is also racey. You can use
atomic_fetchadd() instead (which is what refcount_release does).
--
John Baldwin
More information about the svn-src-all
mailing list