diff options
author | Vsevolod Stakhov <vsevolod@highsecure.ru> | 2014-02-04 16:35:58 +0000 |
---|---|---|
committer | Vsevolod Stakhov <vsevolod@highsecure.ru> | 2014-02-04 16:37:37 +0000 |
commit | ff62d93b0ed2051a2ba5c9cd9c12dd80c2890765 (patch) | |
tree | addc18a41900c3ca04cae760b10618e78c4918f1 /contrib/libottery/ottery_entropy_egd.c | |
parent | d07102a78273a786b2d35d154173f2c4aff0cb27 (diff) | |
download | rspamd-ff62d93b0ed2051a2ba5c9cd9c12dd80c2890765.tar.gz rspamd-ff62d93b0ed2051a2ba5c9cd9c12dd80c2890765.zip |
Use libottery for secure random numbers.
Libottery itself is hosted here:
https://github.com/nmathewson/libottery
This import is a rough adoptation of libottery to use it for secure
random numbers in rspamd when needed (and in DNS resolver specifically).
This import makes the internal chacha20 code useless, hence it is
removed now.
Diffstat (limited to 'contrib/libottery/ottery_entropy_egd.c')
-rw-r--r-- | contrib/libottery/ottery_entropy_egd.c | 75 |
1 files changed, 75 insertions, 0 deletions
diff --git a/contrib/libottery/ottery_entropy_egd.c b/contrib/libottery/ottery_entropy_egd.c new file mode 100644 index 000000000..7e9cb076d --- /dev/null +++ b/contrib/libottery/ottery_entropy_egd.c @@ -0,0 +1,75 @@ +/* Libottery by Nick Mathewson. + + This software has been dedicated to the public domain under the CC0 + public domain dedication. + + To the extent possible under law, the person who associated CC0 with + libottery has waived all copyright and related or neighboring rights + to libottery. + + You should have received a copy of the CC0 legalcode along with this + work in doc/cc0.txt. If not, see + <http://creativecommons.org/publicdomain/zero/1.0/>. + */ +#ifndef _WIN32 +/* TODO: Support win32. */ +#include <sys/socket.h> + +/** Implement an entropy-source that uses the EGD protocol. The + * Entropy-Gathering Daemon is program (actually, one of several programs) + * that watches system events, periodically runs commands whose outputs have + * high variance, and so on. It communicates over a simple socket-based + * protocol, of which we use only a tiny piece. */ +static int +ottery_get_entropy_egd(const struct ottery_entropy_config *cfg, + struct ottery_entropy_state *state, + uint8_t *out, size_t outlen) +{ + int sock, n, result; + unsigned char msg[2]; + (void) state; + + if (! cfg || ! cfg->egd_sockaddr || ! cfg->egd_socklen) + return OTTERY_ERR_INIT_STRONG_RNG; + if (outlen > 255) + return OTTERY_ERR_ACCESS_STRONG_RNG; + + sock = socket(cfg->egd_sockaddr->sa_family, SOCK_STREAM, 0); + if (sock < 0) + return OTTERY_ERR_INIT_STRONG_RNG; + + if (connect(sock, cfg->egd_sockaddr, cfg->egd_socklen) < 0) { + result = OTTERY_ERR_INIT_STRONG_RNG; + goto out; + } + + msg[0] = 1; /* nonblocking request */ + msg[1] = (unsigned char) outlen; /* for outlen bytes */ + + if (write(sock, msg, 2) != 2 || + read(sock, msg, 1) != 1) { + result = OTTERY_ERR_ACCESS_STRONG_RNG; + goto out; + } + + if (msg[0] != outlen) { + /* TODO Use any bytes we get, even if they aren't as many as we wanted. */ + result = OTTERY_ERR_ACCESS_STRONG_RNG; + goto out; + } + + n = ottery_read_n_bytes_from_file_(sock, out, outlen); + if (n < 0 || (size_t)n != outlen) { + result = OTTERY_ERR_ACCESS_STRONG_RNG; + goto out; + } + result = 0; + out: + close(sock); + return result; +} + +#define ENTROPY_SOURCE_EGD \ + { ottery_get_entropy_egd, SRC(EGD)|DOM(EGD)|FL(STRONG) } + +#endif |