diff options
author | H. Peter Anvin <hpa@linux.intel.com> | 2012-07-30 14:42:36 -0700 |
---|---|---|
committer | Jeff Garzik <jgarzik@redhat.com> | 2012-07-31 15:32:58 -0400 |
commit | 870f0d5d2f06d778a49e35d3a5f55183e5c9b9c0 (patch) | |
tree | ef64fe562cb09af6f91b3478329645d6f707ac04 | |
parent | 593a93021566a41546b433bbb5d4eb66302c5eb3 (diff) | |
download | rng-tools-870f0d5d2f06d778a49e35d3a5f55183e5c9b9c0.tar.gz |
rngd_linux: Modify write_wakeup_threshold to the fill threshold
The kernel.random.write_wakeup_threshold sysctl needs to be set to the
point where we want poll() on the random device to wake up. This
replaces the level check in ioctl() used during polling.
Set it by default to 3/4 to the value of kernel.random.poolsize.
Signed-off-by: H. Peter Anvin <hpa@linux.intel.com>
Signed-off-by: Jeff Garzik <jgarzik@redhat.com>
-rw-r--r-- | rngd.c | 4 | ||||
-rw-r--r-- | rngd_linux.c | 39 | ||||
-rw-r--r-- | rngd_linux.h | 3 |
3 files changed, 45 insertions, 1 deletions
@@ -112,7 +112,6 @@ static struct arguments default_arguments = { .random_name = "/dev/random", .pid_file = "/var/run/rngd.pid", .random_step = 64, - .fill_watermark = 2048, .daemon = true, .enable_drng = true, .enable_tpm = true, @@ -292,6 +291,9 @@ int main(int argc, char **argv) openlog("rngd", 0, LOG_DAEMON); + /* Get the default watermark level for this platform */ + arguments->fill_watermark = default_watermark(); + /* Parsing of commandline parameters */ argp_parse(&argp, argc, argv, 0, 0, arguments); diff --git a/rngd_linux.c b/rngd_linux.c index 6400adf..3556fd0 100644 --- a/rngd_linux.c +++ b/rngd_linux.c @@ -53,6 +53,37 @@ extern struct rng *rng_list; /* Kernel output device */ static int random_fd; +/* + * Get the default watermark + */ +int default_watermark(void) +{ + char psbuf[64], *p; + unsigned long ps; + FILE *f; + size_t l; + unsigned int wm = 2048; /* Default guess */ + + f = fopen("/proc/sys/kernel/random/poolsize", "r"); + if (!f) + goto err; + l = fread(psbuf, 1, sizeof psbuf, f); + if (ferror(f) || !feof(f) || l == 0) + goto err; + if (psbuf[l-1] != '\n') + goto err; + psbuf[l-1] = '\0'; + ps = strtoul(psbuf, &p, 0); + if (*p) + goto err; + + wm = ps*3/4; + +err: + if (f) + fclose(f); + return wm; +} /* * Initialize the interface to the Linux Kernel @@ -62,12 +93,20 @@ static int random_fd; */ void init_kernel_rng(const char* randomdev) { + FILE *f; + random_fd = open(randomdev, O_RDWR); if (random_fd == -1) { message(LOG_DAEMON|LOG_ERR, "can't open %s: %s", randomdev, strerror(errno)); exit(EXIT_USAGE); } + + f = fopen("/proc/sys/kernel/random/write_wakeup_threshold", "w"); + if (f) { + fprintf(f, "%u\n", arguments->fill_watermark); + fclose(f); + } } void random_add_entropy(void *buf, size_t size) diff --git a/rngd_linux.h b/rngd_linux.h index 187e17c..029584b 100644 --- a/rngd_linux.h +++ b/rngd_linux.h @@ -26,6 +26,9 @@ #include <unistd.h> #include <stdint.h> +/* The default watermark level for this platform */ +extern int default_watermark(void); + /* * Initialize the interface to the Linux Kernel * entropy pool (through /dev/random) |