Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/dev Fix spurious kassert on interrupted blocking read fr...
details: https://anonhg.NetBSD.org/src/rev/45af7694ae2f
branches: trunk
changeset: 790192:45af7694ae2f
user: riastradh <riastradh%NetBSD.org@localhost>
date: Wed Sep 25 03:14:55 2013 +0000
description:
Fix spurious kassert on interrupted blocking read from /dev/random.
Return EINTR in this case instead. While here, clarify comment.
Fixes PR kern/48119, simpler than the patch attached there, per
discussion with tls@, who had this right in the earlier version
of rndpseudo.c before I broke it (oops!).
diffstat:
sys/dev/rndpseudo.c | 36 +++++++++++++++++++++++++-----------
1 files changed, 25 insertions(+), 11 deletions(-)
diffs (60 lines):
diff -r 4b1c4f48fe98 -r 45af7694ae2f sys/dev/rndpseudo.c
--- a/sys/dev/rndpseudo.c Tue Sep 24 23:45:16 2013 +0000
+++ b/sys/dev/rndpseudo.c Wed Sep 25 03:14:55 2013 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: rndpseudo.c,v 1.16 2013/07/21 22:30:19 riastradh Exp $ */
+/* $NetBSD: rndpseudo.c,v 1.17 2013/09/25 03:14:55 riastradh Exp $ */
/*-
* Copyright (c) 1997-2013 The NetBSD Foundation, Inc.
@@ -31,7 +31,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: rndpseudo.c,v 1.16 2013/07/21 22:30:19 riastradh Exp $");
+__KERNEL_RCSID(0, "$NetBSD: rndpseudo.c,v 1.17 2013/09/25 03:14:55 riastradh Exp $");
#if defined(_KERNEL_OPT)
#include "opt_compat_netbsd.h"
@@ -389,18 +389,32 @@
goto out;
/*
- * Do at most one iteration for /dev/random and return
- * a short read without hanging further. Hanging
- * breaks applications worse than short reads. Reads
- * can't be zero unless nonblocking from /dev/random;
- * in that case, ask caller to retry, instead of just
- * returning zero bytes, which means EOF.
+ * For /dev/urandom: Reads always succeed in full, no
+ * matter how many iterations that takes. (XXX But
+ * this means the computation can't be interrupted,
+ * wihch seems suboptimal.)
+ *
+ * For /dev/random, nonblocking: Reads succeed with as
+ * many bytes as a single request can return without
+ * blocking, or fail with EAGAIN if a request would
+ * block. (There is no sense in trying multiple
+ * requests because if the first one didn't fill the
+ * buffer, the second one would almost certainly
+ * block.)
+ *
+ * For /dev/random, blocking: Reads succeed with as
+ * many bytes as a single request -- which may block --
+ * can return if uninterrupted, or fail with EINTR if
+ * the request is interrupted.
*/
- KASSERT((0 < n_read) || (ctx->rc_hard &&
- ISSET(fp->f_flag, FNONBLOCK)));
+ KASSERT((0 < n_read) || ctx->rc_hard);
if (ctx->rc_hard) {
- if (n_read == 0)
+ if (0 < n_read)
+ error = 0;
+ else if (ISSET(fp->f_flag, FNONBLOCK))
error = EAGAIN;
+ else
+ error = EINTR;
goto out;
}
}
Home |
Main Index |
Thread Index |
Old Index