[PATCH, RFC 10/12] random: cap the rate which the /dev/urandom pool gets reseeded

From: Theodore Ts'o
Date: Sun Sep 22 2013 - 16:42:46 EST


In order to avoid draining the input pool of its entropy at too high
of a rate, enforce a minimum time interval between reseedings of the
urandom pool. This is set to 60 seconds by default.

Signed-off-by: "Theodore Ts'o" <tytso@xxxxxxx>
---
drivers/char/random.c | 25 +++++++++++++++++++++++++
1 file changed, 25 insertions(+)

diff --git a/drivers/char/random.c b/drivers/char/random.c
index 292e717..3439b1c 100644
--- a/drivers/char/random.c
+++ b/drivers/char/random.c
@@ -306,6 +306,13 @@ static int random_read_wakeup_thresh = 64;
static int random_write_wakeup_thresh = 128;

/*
+ * The minimum number of seconds between urandom pool resending. We
+ * do this to limit the amount of entropy that can be drained from the
+ * input pool even if there are heavy demands on /dev/urandom.
+ */
+static int random_min_urandom_seed = 60;
+
+/*
* When the input pool goes over trickle_thresh, start dropping most
* samples to avoid wasting CPU time and reduce lock contention.
*/
@@ -437,6 +444,7 @@ struct entropy_store {
struct entropy_store *pull;

/* read-write data: */
+ unsigned long last_pulled;
spinlock_t lock;
unsigned short add_ptr;
unsigned short input_rotate;
@@ -885,6 +893,15 @@ static void xfer_secondary_pool(struct entropy_store *r, size_t nbytes)
{
__u32 tmp[OUTPUT_POOL_WORDS];

+ if (r->limit == 0 && random_min_urandom_seed) {
+ unsigned long now = jiffies;
+
+ if (time_before(now,
+ r->last_pulled + random_min_urandom_seed * HZ)) {
+ return;
+ }
+ r->last_pulled = now;
+ }
if (r->pull &&
r->entropy_count < (nbytes << (ENTROPY_SHIFT + 3)) &&
r->entropy_count < r->poolinfo->poolfracbits) {
@@ -1188,6 +1205,7 @@ static void init_std_data(struct entropy_store *r)
r->entropy_count = 0;
r->entropy_total = 0;
r->last_data_init = 0;
+ r->last_pulled = jiffies;
mix_pool_bytes(r, &now, sizeof(now), NULL);
for (i = r->poolinfo->poolbytes; i > 0; i -= sizeof(rv)) {
if (!arch_get_random_long(&rv))
@@ -1539,6 +1557,13 @@ struct ctl_table random_table[] = {
.extra2 = &max_write_thresh,
},
{
+ .procname = "urandom_min_reseed_secs",
+ .data = &random_min_urandom_seed,
+ .maxlen = sizeof(int),
+ .mode = 0644,
+ .proc_handler = proc_dointvec,
+ },
+ {
.procname = "boot_id",
.data = &sysctl_bootid,
.maxlen = 16,
--
1.7.12.rc0.22.gcdd159b

--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/