|
|
873a72 |
From c25a14ab6ce15d18338a7499e5849225aea03a7d Mon Sep 17 00:00:00 2001
|
|
|
873a72 |
From: Nikos Mavrogiannopoulos <nmav@redhat.com>
|
|
|
873a72 |
Date: Tue, 14 Oct 2014 13:57:33 +0200
|
|
|
873a72 |
Subject: [PATCH] FIPS140-2 RSA key generation changes to account for seed
|
|
|
873a72 |
starting with null byte
|
|
|
873a72 |
|
|
|
873a72 |
---
|
|
|
873a72 |
lib/nettle/int/dsa-fips.h | 2 ++
|
|
|
873a72 |
lib/nettle/int/provable-prime.c | 25 ++++++++++++++++++-------
|
|
|
873a72 |
lib/nettle/int/rsa-keygen-fips186.c | 33 ++++++++++++++++++++-------------
|
|
|
873a72 |
3 files changed, 40 insertions(+), 20 deletions(-)
|
|
|
873a72 |
|
|
|
873a72 |
diff --git a/lib/nettle/int/dsa-fips.h b/lib/nettle/int/dsa-fips.h
|
|
|
873a72 |
index 571bc0a..08fac25 100644
|
|
|
873a72 |
--- a/lib/nettle/int/dsa-fips.h
|
|
|
873a72 |
+++ b/lib/nettle/int/dsa-fips.h
|
|
|
873a72 |
@@ -115,4 +115,6 @@ hash (uint8_t digest[DIGEST_SIZE], unsigned length, void *data)
|
|
|
873a72 |
return;
|
|
|
873a72 |
}
|
|
|
873a72 |
|
|
|
873a72 |
+unsigned mpz_seed_sizeinbase_256_u(mpz_t s, unsigned nominal);
|
|
|
873a72 |
+
|
|
|
873a72 |
#endif /* DSA_FIPS_H_INCLUDED */
|
|
|
873a72 |
diff --git a/lib/nettle/int/provable-prime.c b/lib/nettle/int/provable-prime.c
|
|
|
873a72 |
index 3bb46aa..e4a4325 100644
|
|
|
873a72 |
--- a/lib/nettle/int/provable-prime.c
|
|
|
873a72 |
+++ b/lib/nettle/int/provable-prime.c
|
|
|
873a72 |
@@ -992,6 +992,18 @@ static unsigned small_prime_check(unsigned x)
|
|
|
873a72 |
return 1;
|
|
|
873a72 |
}
|
|
|
873a72 |
|
|
|
873a72 |
+/* The seed in FIPS186-3 is used either as an integer or blob,
|
|
|
873a72 |
+ * but when used as an integer it must not be trunacated below
|
|
|
873a72 |
+ * the "nominal" seed size. This function returns the size
|
|
|
873a72 |
+ * that way. */
|
|
|
873a72 |
+unsigned mpz_seed_sizeinbase_256_u(mpz_t s, unsigned nominal)
|
|
|
873a72 |
+{
|
|
|
873a72 |
+ unsigned ret = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ if (ret < nominal)
|
|
|
873a72 |
+ return nominal;
|
|
|
873a72 |
+ return ret;
|
|
|
873a72 |
+}
|
|
|
873a72 |
+
|
|
|
873a72 |
static int st_provable_prime_small(mpz_t p,
|
|
|
873a72 |
unsigned *prime_seed_length,
|
|
|
873a72 |
void *prime_seed,
|
|
|
873a72 |
@@ -1018,7 +1030,7 @@ static int st_provable_prime_small(mpz_t p,
|
|
|
873a72 |
nettle_mpz_set_str_256_u(s, seed_length, seed);
|
|
|
873a72 |
|
|
|
873a72 |
retry:
|
|
|
873a72 |
- tseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, seed_length);
|
|
|
873a72 |
if (tseed_length > sizeof(tseed)) {
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
}
|
|
|
873a72 |
@@ -1030,7 +1042,7 @@ static int st_provable_prime_small(mpz_t p,
|
|
|
873a72 |
|
|
|
873a72 |
mpz_add_ui(s, s, 1);
|
|
|
873a72 |
|
|
|
873a72 |
- tseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, seed_length);
|
|
|
873a72 |
if (tseed_length > sizeof(tseed))
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
|
|
|
873a72 |
@@ -1071,7 +1083,7 @@ static int st_provable_prime_small(mpz_t p,
|
|
|
873a72 |
mpz_set_ui(p, c);
|
|
|
873a72 |
|
|
|
873a72 |
if (prime_seed != NULL) {
|
|
|
873a72 |
- tseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, tseed_length);
|
|
|
873a72 |
if (*prime_seed_length < tseed_length)
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
|
|
|
873a72 |
@@ -1161,7 +1173,7 @@ st_provable_prime(mpz_t p,
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
|
|
|
873a72 |
for (i = 0; i < iterations; i++) {
|
|
|
873a72 |
- tseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, pseed_length);
|
|
|
873a72 |
if (tseed_length > sizeof(tseed))
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
nettle_mpz_get_str_256(tseed_length, tseed, s);
|
|
|
873a72 |
@@ -1212,9 +1224,8 @@ st_provable_prime(mpz_t p,
|
|
|
873a72 |
|
|
|
873a72 |
mpz_set_ui(r, 0); /* a = 0 */
|
|
|
873a72 |
if (iterations > 0) {
|
|
|
873a72 |
-
|
|
|
873a72 |
for (i = 0; i < iterations; i++) {
|
|
|
873a72 |
- tseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, pseed_length);
|
|
|
873a72 |
if (tseed_length > sizeof(tseed))
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
|
|
|
873a72 |
@@ -1249,7 +1260,7 @@ st_provable_prime(mpz_t p,
|
|
|
873a72 |
mpz_set(p, c);
|
|
|
873a72 |
|
|
|
873a72 |
if (prime_seed != NULL) {
|
|
|
873a72 |
- tseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, pseed_length);
|
|
|
873a72 |
if (*prime_seed_length < tseed_length)
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
|
|
|
873a72 |
diff --git a/lib/nettle/int/rsa-keygen-fips186.c b/lib/nettle/int/rsa-keygen-fips186.c
|
|
|
873a72 |
index 754842a..624aa36 100644
|
|
|
873a72 |
--- a/lib/nettle/int/rsa-keygen-fips186.c
|
|
|
873a72 |
+++ b/lib/nettle/int/rsa-keygen-fips186.c
|
|
|
873a72 |
@@ -53,7 +53,7 @@ unsigned iterations;
|
|
|
873a72 |
unsigned storage_length = 0, i;
|
|
|
873a72 |
uint8_t *storage = NULL;
|
|
|
873a72 |
uint8_t pseed[MAX_PVP_SEED_SIZE+1];
|
|
|
873a72 |
-unsigned pseed_length = sizeof(pseed);
|
|
|
873a72 |
+unsigned pseed_length = sizeof(pseed), tseed_length;
|
|
|
873a72 |
unsigned max = bits*5;
|
|
|
873a72 |
|
|
|
873a72 |
mpz_init(p0);
|
|
|
873a72 |
@@ -85,11 +85,13 @@ unsigned max = bits*5;
|
|
|
873a72 |
|
|
|
873a72 |
nettle_mpz_set_str_256_u(s, pseed_length, pseed);
|
|
|
873a72 |
for (i = 0; i < iterations; i++) {
|
|
|
873a72 |
- pseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
- nettle_mpz_get_str_256(pseed_length, pseed, s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, pseed_length);
|
|
|
873a72 |
+ if (tseed_length > sizeof(pseed))
|
|
|
873a72 |
+ goto fail;
|
|
|
873a72 |
+ nettle_mpz_get_str_256(tseed_length, pseed, s);
|
|
|
873a72 |
|
|
|
873a72 |
hash(&storage[(iterations - i - 1) * DIGEST_SIZE],
|
|
|
873a72 |
- pseed_length, pseed);
|
|
|
873a72 |
+ tseed_length, pseed);
|
|
|
873a72 |
mpz_add_ui(s, s, 1);
|
|
|
873a72 |
}
|
|
|
873a72 |
|
|
|
873a72 |
@@ -170,11 +172,13 @@ unsigned max = bits*5;
|
|
|
873a72 |
mpz_set_ui(x, 0); /* a = 0 */
|
|
|
873a72 |
if (iterations > 0) {
|
|
|
873a72 |
for (i = 0; i < iterations; i++) {
|
|
|
873a72 |
- pseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
- nettle_mpz_get_str_256(pseed_length, pseed, s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, pseed_length);
|
|
|
873a72 |
+ if (tseed_length > sizeof(pseed))
|
|
|
873a72 |
+ goto fail;
|
|
|
873a72 |
+ nettle_mpz_get_str_256(tseed_length, pseed, s);
|
|
|
873a72 |
|
|
|
873a72 |
hash(&storage[(iterations - i - 1) * DIGEST_SIZE],
|
|
|
873a72 |
- pseed_length, pseed);
|
|
|
873a72 |
+ tseed_length, pseed);
|
|
|
873a72 |
mpz_add_ui(s, s, 1);
|
|
|
873a72 |
}
|
|
|
873a72 |
|
|
|
873a72 |
@@ -203,16 +207,19 @@ unsigned max = bits*5;
|
|
|
873a72 |
mpz_powm(r1, r2, p0, p);
|
|
|
873a72 |
if (mpz_cmp_ui(r1, 1) == 0) {
|
|
|
873a72 |
if (prime_seed_length != NULL) {
|
|
|
873a72 |
- pseed_length = nettle_mpz_sizeinbase_256_u(s);
|
|
|
873a72 |
- nettle_mpz_get_str_256(pseed_length, pseed, s);
|
|
|
873a72 |
+ tseed_length = mpz_seed_sizeinbase_256_u(s, pseed_length);
|
|
|
873a72 |
+ if (tseed_length > sizeof(pseed))
|
|
|
873a72 |
+ goto fail;
|
|
|
873a72 |
+
|
|
|
873a72 |
+ nettle_mpz_get_str_256(tseed_length, pseed, s);
|
|
|
873a72 |
|
|
|
873a72 |
- if (*prime_seed_length < pseed_length) {
|
|
|
873a72 |
- *prime_seed_length = pseed_length;
|
|
|
873a72 |
+ if (*prime_seed_length < tseed_length) {
|
|
|
873a72 |
+ *prime_seed_length = tseed_length;
|
|
|
873a72 |
goto fail;
|
|
|
873a72 |
}
|
|
|
873a72 |
- *prime_seed_length = pseed_length;
|
|
|
873a72 |
+ *prime_seed_length = tseed_length;
|
|
|
873a72 |
if (prime_seed != NULL)
|
|
|
873a72 |
- memcpy(prime_seed, pseed, pseed_length);
|
|
|
873a72 |
+ memcpy(prime_seed, pseed, tseed_length);
|
|
|
873a72 |
}
|
|
|
873a72 |
ret = 1;
|
|
|
873a72 |
goto cleanup;
|
|
|
873a72 |
--
|
|
|
873a72 |
1.9.3
|
|
|
873a72 |
|