From 25f8b939bb98c3cc6691e79b5f3bd3be19804fe9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Adrien=20Gallou=C3=ABt?= Date: Wed, 27 May 2020 15:01:16 +0000 Subject: [PATCH] Fix modulo bias MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Adrien Gallouët --- secret.c | 24 ++++++++++++++---------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/secret.c b/secret.c index 7dbeb3a..9e70135 100644 --- a/secret.c +++ b/secret.c @@ -358,14 +358,19 @@ s_list(int argc, char **argv, void *data) return 0; } -static void -s_normalize_and_show(unsigned char *buf, size_t size) +static size_t +s_normalize_and_show(unsigned char *buf, size_t size, size_t want) { - for (size_t i = 0; i < size; i++) - buf[i] = '!' + buf[i] % (1U + '~' - '!'); + const unsigned n = 1U + '~' - '!'; + unsigned k = 0; - s_write(1, buf, size); + for (size_t i = 0; i < size && k < want; i++) { + if (buf[i] < 2 * n) + buf[k++] = '!' + buf[i] % n; + } + s_write(1, buf, k); if (isatty(1)) s_write(1, "\n", 1); + return k; } enum s_op { @@ -401,12 +406,11 @@ s_do(int argc, char **argv, void *data) } unsigned char secret[S_ENTRYSIZE]; - size_t len = S_PWDGENLEN; + size_t len = 0; if (op & s_op_generate) { - hydro_memzero(secret, sizeof(secret)); - hydro_random_buf(secret, len); - s_normalize_and_show(secret, len); + hydro_random_buf(secret, sizeof(secret)); + len = s_normalize_and_show(secret, sizeof(secret), S_PWDGENLEN); } else { len = isatty(0) ? s_input(secret, sizeof(secret), "Secret: ") : s_read(0, secret, sizeof(secret)); @@ -469,7 +473,7 @@ s_pass(int argc, char **argv, void *data) memcpy(key, buf, sizeof(key)); if (r) s_oops(__LINE__); } - s_normalize_and_show(buf, S_PWDGENLEN); + s_normalize_and_show(buf, sizeof(buf), S_PWDGENLEN); return 0; }