NetBSD-Bugs archive

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

lib/56905: getentropy() may return predictable data



>Number:         56905
>Category:       lib
>Synopsis:       getentropy() may return predictable data
>Confidential:   no
>Severity:       serious
>Priority:       high
>Responsible:    lib-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Wed Jun 29 16:00:00 +0000 2022
>Originator:     Andreas Gustafsson
>Release:        NetBSD-current, source date >= 2022.05.31.13.42.59
>Organization:
  
>Environment:
System: NetBSD
Architecture: any
Machine: any
>Description:

On 2022-05-31, riastradh@ committed a change to re-enable the
getentropy(3) library call which nia@ had added on 2020-05-06 and
then disabled on 2020-09-23.

When the system lacks entropy, this implementation of getentropy()
will succeed and therefore return data known by the system to be
predictable, rather than failing or blocking until entropy becomes
available.  I consider this to be a security vulnerability, similar to
the one in ssh-keygen I reported in PR 55659 but this time affecting
any third-party application that use getentropy() for cryptographic
purposes.

I understand that not everyone agrees with this assessment, and as
the commit message says, "Discussion of details of the semantics, as
interpreted by NetBSD, is ongoing".  Nonetheless, when I see what
I believe is a security vulnerability, I feel it is my duty to report
it, and if possible, fix it.  And because I believe the discussion
about this issue should be public, I'm filing this in category lib
rather than category security, as PRs in category security and their
follow-up messages don't get publicly posted to netbsd-bugs even if
you explicitly set "Confidential: no".

>How-To-Repeat:

Boot a -current system with no entropy source.  Call getentropy().
Find that it succeeds.

>Fix:

The following patch fixes the issue by making getentropy() block
until entropy is available.  It passes all the tests in
/usr/src/tests/lib/libc/gen/t_getentropy.c.

Index: getentropy.c
===================================================================
RCS file: /cvsroot/src/lib/libc/gen/getentropy.c,v
retrieving revision 1.3
diff -u -r1.3 getentropy.c
--- getentropy.c	31 May 2022 13:42:59 -0000	1.3
+++ getentropy.c	28 Jun 2022 08:33:27 -0000
@@ -35,8 +35,9 @@
 #include "namespace.h"
 
 #include <sys/param.h>
-#include <sys/sysctl.h>
+#include <sys/random.h>
 
+#include <assert.h>
 #include <errno.h>
 #include <limits.h>
 #include <unistd.h>
@@ -50,8 +51,7 @@
 int
 getentropy(void *buf, size_t buflen)
 {
-	size_t len = buflen;
-	int name[2] = { CTL_KERN, KERN_ARND };
+	ssize_t r;
 
 	if (buf == NULL && buflen > 0) {
 		errno = EFAULT;
@@ -63,5 +63,11 @@
 		return -1;
 	}
 
-	return sysctl(name, 2, buf, &len, NULL, 0);
+	do {
+		r = getrandom(buf, buflen, 0);
+	} while (r == -1 && errno == EINTR);
+
+	assert(r == -1 || r == (ssize_t)buflen);
+
+	return (int)r;
 }



Home | Main Index | Thread Index | Old Index