mirror of
https://codeberg.org/libreboot/lbmk.git
synced 2026-03-25 13:29:03 +02:00
libreboot-utils: tidy up the rand code
Signed-off-by: Leah Rowe <leah@libreboot.org>
This commit is contained in:
@@ -886,53 +886,30 @@ err:
|
||||
int
|
||||
mkhtemp_fill_random(char *p, size_t xc)
|
||||
{
|
||||
size_t chx = 0;
|
||||
int rand_failures = 0;
|
||||
|
||||
size_t r;
|
||||
|
||||
int saved_rand_error = 0;
|
||||
static char ch[] =
|
||||
"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
|
||||
|
||||
size_t chx = 0;
|
||||
size_t r;
|
||||
|
||||
/* clamp rand to prevent modulo bias
|
||||
* (reduced risk of entropy leak)
|
||||
*/
|
||||
size_t limit = ((size_t)-1) - (((size_t)-1) % (sizeof(ch) - 1));
|
||||
|
||||
int saved_errno = errno;
|
||||
|
||||
if (p == NULL) {
|
||||
errno = EFAULT;
|
||||
goto err_mkhtemp_fill_random;
|
||||
}
|
||||
if (if_err(p == NULL, EFAULT))
|
||||
return -1;
|
||||
|
||||
for (chx = 0; chx < xc; chx++) {
|
||||
|
||||
do {
|
||||
saved_rand_error = errno;
|
||||
rand_failures = 0;
|
||||
retry_rand:
|
||||
errno = 0;
|
||||
|
||||
/* on bsd: uses arc4random
|
||||
on linux: uses getrandom
|
||||
on OLD linux: /dev/urandom
|
||||
on old/other unix: /dev/urandom
|
||||
*/
|
||||
r = rlong();
|
||||
|
||||
if (errno > 0) {
|
||||
if (++rand_failures <= 8)
|
||||
goto retry_rand;
|
||||
|
||||
goto err_mkhtemp_fill_random;
|
||||
}
|
||||
|
||||
rand_failures = 0;
|
||||
errno = saved_rand_error;
|
||||
|
||||
} while (r >= limit);
|
||||
/* on bsd: uses arc4random
|
||||
on linux: uses getrandom
|
||||
*never returns error*
|
||||
*/
|
||||
r = rlong(); /* always returns successful */
|
||||
if (r >= limit)
|
||||
goto retry_rand;
|
||||
|
||||
p[chx] = ch[r % (sizeof(ch) - 1)];
|
||||
}
|
||||
@@ -940,12 +917,6 @@ retry_rand:
|
||||
errno = saved_errno;
|
||||
return 0;
|
||||
|
||||
err_mkhtemp_fill_random:
|
||||
|
||||
if (errno == saved_errno)
|
||||
errno = ECANCELED;
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* WARNING: **ONCE** per file.
|
||||
|
||||
@@ -59,6 +59,7 @@ rlong(void)
|
||||
{
|
||||
size_t rval;
|
||||
int saved_errno = errno;
|
||||
errno = 0;
|
||||
|
||||
#if (defined(__OpenBSD__) && (OpenBSD) >= 201) || \
|
||||
defined(__FreeBSD__) || \
|
||||
@@ -71,30 +72,23 @@ rlong(void)
|
||||
|
||||
size_t off = 0;
|
||||
size_t len = sizeof(rval);
|
||||
|
||||
ssize_t rc;
|
||||
|
||||
if (!len)
|
||||
goto err;
|
||||
retry_rand:
|
||||
rc = (ssize_t)syscall(SYS_getrandom,
|
||||
(char *)&rval + off, len - off, 0);
|
||||
|
||||
while (off < len) {
|
||||
if (rc < 0) {
|
||||
if (errno == EINTR || errno == EAGAIN)
|
||||
goto retry_rand;
|
||||
|
||||
rc = (ssize_t)syscall(SYS_getrandom,
|
||||
(char *)&rval + off, len - off, 0);
|
||||
|
||||
if (rc < 0) {
|
||||
if (errno == EINTR || errno == EAGAIN)
|
||||
continue;
|
||||
|
||||
goto err; /* possibly unsupported by kernel */
|
||||
}
|
||||
|
||||
off += (size_t)rc;
|
||||
goto err; /* possibly unsupported by kernel */
|
||||
}
|
||||
|
||||
goto out;
|
||||
if ((off += (size_t)rc) < len)
|
||||
goto retry_rand;
|
||||
|
||||
return rval;
|
||||
goto out;
|
||||
err:
|
||||
/*
|
||||
* getrandom can return with error, butt arc4random
|
||||
@@ -103,8 +97,9 @@ err:
|
||||
* BSD. So a rand failure is to be interpreted as
|
||||
* a major systems failure, and we act accordingly.
|
||||
*/
|
||||
err_no_cleanup(1, ECANCELED, "Randomisation failure");
|
||||
exit(1);
|
||||
err_no_cleanup(1, ECANCELED,
|
||||
"Randomisation failure, possibly unsupported in your kernel.");
|
||||
exit(EXIT_FAILURE);
|
||||
|
||||
#else
|
||||
#error Unsupported operating system (possibly unsecure randomisation)
|
||||
|
||||
Reference in New Issue
Block a user