Module Name: src
Committed By: riastradh
Date: Sun Mar 20 14:05:41 UTC 2022
Modified Files:
src/sys/kern: kern_entropy.c
Log Message:
Revert "entropy(9): Nix rnd_trylock_sources."
Not a premature optimization after all -- this is necessary because
entropy_request can run in softint context, where the cv_wait_sig in
rnd_lock_sources is forbidden. Need to do this another way.
To generate a diff of this commit:
cvs rdiff -u -r1.47 -r1.48 src/sys/kern/kern_entropy.c
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: src/sys/kern/kern_entropy.c
diff -u src/sys/kern/kern_entropy.c:1.47 src/sys/kern/kern_entropy.c:1.48
--- src/sys/kern/kern_entropy.c:1.47 Sun Mar 20 13:44:18 2022
+++ src/sys/kern/kern_entropy.c Sun Mar 20 14:05:41 2022
@@ -1,4 +1,4 @@
-/* $NetBSD: kern_entropy.c,v 1.47 2022/03/20 13:44:18 riastradh Exp $ */
+/* $NetBSD: kern_entropy.c,v 1.48 2022/03/20 14:05:41 riastradh Exp $ */
/*-
* Copyright (c) 2019 The NetBSD Foundation, Inc.
@@ -75,7 +75,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kern_entropy.c,v 1.47 2022/03/20 13:44:18 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kern_entropy.c,v 1.48 2022/03/20 14:05:41 riastradh Exp $");
#include <sys/param.h>
#include <sys/types.h>
@@ -1702,10 +1702,30 @@ rnd_lock_sources(void)
}
/*
+ * rnd_trylock_sources()
+ *
+ * Try to lock the list of sources, but if it's already locked,
+ * fail. Caller must hold the global entropy lock. If
+ * successful, no rndsource will go away until rnd_unlock_sources
+ * even while the caller releases the global entropy lock.
+ */
+static bool
+rnd_trylock_sources(void)
+{
+
+ KASSERT(E->stage == ENTROPY_COLD || mutex_owned(&E->lock));
+
+ if (E->sourcelock)
+ return false;
+ E->sourcelock = curlwp;
+ return true;
+}
+
+/*
* rnd_unlock_sources()
*
- * Unlock the list of sources after rnd_lock_sources. Caller must
- * hold the global entropy lock.
+ * Unlock the list of sources after rnd_lock_sources or
+ * rnd_trylock_sources. Caller must hold the global entropy lock.
*/
static void
rnd_unlock_sources(void)
@@ -1748,11 +1768,12 @@ entropy_request(size_t nbytes)
KASSERT(E->stage == ENTROPY_COLD || mutex_owned(&E->lock));
/*
- * Lock the list of entropy sources to block rnd_detach_source
- * until we're done, and to serialize calls to the entropy
- * callbacks as guaranteed to drivers.
+ * If there is a request in progress, let it proceed.
+ * Otherwise, note that a request is in progress to avoid
+ * reentry and to block rnd_detach_source until we're done.
*/
- rnd_lock_sources();
+ if (!rnd_trylock_sources())
+ return;
entropy_request_evcnt.ev_count++;
/* Clamp to the maximum reasonable request. */