summaryrefslogtreecommitdiff
path: root/drivers
diff options
context:
space:
mode:
authorJason A. Donenfeld <Jason@zx2c4.com>2022-03-08 10:12:16 -0700
committerJason A. Donenfeld <Jason@zx2c4.com>2022-03-12 20:51:39 -0700
commit3e504d2026eb6c8762cd6040ae57db166516824a (patch)
tree7cd0e241000615b841b9be8837032dd1f45bac6c /drivers
parent7a7ff644aeaf071d433caffb3b8ea57354b55bd3 (diff)
random: check for signal and try earlier when generating entropy
Rather than waiting a full second in an interruptable waiter before trying to generate entropy, try to generate entropy first and wait second. While waiting one second might give an extra second for getting entropy from elsewhere, we're already pretty late in the init process here, and whatever else is generating entropy will still continue to contribute. This has implications on signal handling: we call try_to_generate_entropy() from wait_for_random_bytes(), and wait_for_random_bytes() always uses wait_event_interruptible_timeout() when waiting, since it's called by userspace code in restartable contexts, where signals can pend. Since try_to_generate_entropy() now runs first, if a signal is pending, it's necessary for try_to_generate_entropy() to check for signals, since it won't hit the wait until after try_to_generate_entropy() has returned. And even before this change, when entering a busy loop in try_to_generate_entropy(), we should have been checking to see if any signals are pending, so that a process doesn't get stuck in that loop longer than expected. Cc: Theodore Ts'o <tytso@mit.edu> Reviewed-by: Dominik Brodowski <linux@dominikbrodowski.net> Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/char/random.c5
1 files changed, 3 insertions, 2 deletions
diff --git a/drivers/char/random.c b/drivers/char/random.c
index defdba110d1d..0bdefada7453 100644
--- a/drivers/char/random.c
+++ b/drivers/char/random.c
@@ -124,10 +124,11 @@ int wait_for_random_bytes(void)
{
while (!crng_ready()) {
int ret;
+
+ try_to_generate_entropy();
ret = wait_event_interruptible_timeout(crng_init_wait, crng_ready(), HZ);
if (ret)
return ret > 0 ? 0 : ret;
- try_to_generate_entropy();
}
return 0;
}
@@ -1398,7 +1399,7 @@ static void try_to_generate_entropy(void)
return;
timer_setup_on_stack(&stack.timer, entropy_timer, 0);
- while (!crng_ready()) {
+ while (!crng_ready() && !signal_pending(current)) {
if (!timer_pending(&stack.timer))
mod_timer(&stack.timer, jiffies + 1);
mix_pool_bytes(&stack.cycles, sizeof(stack.cycles));