From e57190c312c513fbcb277569264e63ddb0f6ff47 Mon Sep 17 00:00:00 2001 From: Andreas Steffen Date: Mon, 27 Jul 2015 14:50:14 +0200 Subject: [PATCH] Use MGF1 with SHA-512 as BLISS random oracle --- NEWS | 5 ++ .../plugins/bliss/bliss_private_key.c | 18 ++-- .../plugins/bliss/bliss_public_key.c | 19 ++-- src/libstrongswan/plugins/bliss/bliss_utils.c | 87 +++++++++---------- src/libstrongswan/plugins/bliss/bliss_utils.h | 10 +-- 5 files changed, 65 insertions(+), 74 deletions(-) diff --git a/NEWS b/NEWS index e0540240e..938487926 100644 --- a/NEWS +++ b/NEWS @@ -11,6 +11,11 @@ strongswan-5.3.3 - The vici interface now supports the configuration of auxiliary certification authority information as CRL and OCSP URIs +- In the bliss plugin the c_indices derivation using a SHA-512 based random oracle + has been fixed, generalized and standardized by employing the MGF1 mask generation + function with SHA-512. As a consequence BLISS signatures unsing the improved oracle + are not compatible with the earlier implementation. + strongswan-5.3.2 ---------------- diff --git a/src/libstrongswan/plugins/bliss/bliss_private_key.c b/src/libstrongswan/plugins/bliss/bliss_private_key.c index e1064d2f2..1386eeb2d 100644 --- a/src/libstrongswan/plugins/bliss/bliss_private_key.c +++ b/src/libstrongswan/plugins/bliss/bliss_private_key.c @@ -168,7 +168,7 @@ static bool sign_bliss(private_bliss_private_key_t *this, hash_algorithm_t alg, bliss_sampler_t *sampler = NULL; rng_t *rng; hasher_t *hasher; - hash_algorithm_t mgf1_alg; + hash_algorithm_t mgf1_alg, oracle_alg; size_t mgf1_seed_len; uint8_t mgf1_seed_buf[HASH_SIZE_SHA512], data_hash_buf[HASH_SIZE_SHA512]; chunk_t mgf1_seed, data_hash; @@ -185,7 +185,7 @@ static bool sign_bliss(private_bliss_private_key_t *this, hash_algorithm_t alg, /* Initialize signature */ *signature = chunk_empty; - /* Create data hash */ + /* Create data hash using configurable hash algorithm */ hasher = lib->crypto->create_hasher(lib->crypto, alg); if (!hasher) { @@ -200,13 +200,6 @@ static bool sign_bliss(private_bliss_private_key_t *this, hash_algorithm_t alg, } hasher->destroy(hasher); - /* Create SHA512 hasher for c_indices oracle */ - hasher = lib->crypto->create_hasher(lib->crypto, HASH_SHA512); - if (!hasher) - { - return FALSE; - } - /* Set MGF1 hash algorithm and seed length based on security strength */ if (this->set->strength > 160) { @@ -223,10 +216,12 @@ static bool sign_bliss(private_bliss_private_key_t *this, hash_algorithm_t alg, rng = lib->crypto->create_rng(lib->crypto, RNG_STRONG); if (!rng) { - hasher->destroy(hasher); return FALSE; } + /* MGF1 hash algorithm to be used for random oracle */ + oracle_alg = HASH_SHA512; + /* Initialize a couple of needed variables */ n = this->set->n; q = this->set->q; @@ -360,7 +355,7 @@ static bool sign_bliss(private_bliss_private_key_t *this, hash_algorithm_t alg, DBG3(DBG_LIB, "%3d %6d %4d", i, u[i], ud[i]); } - if (!bliss_utils_generate_c(hasher, data_hash, ud, n, this->set->kappa, + if (!bliss_utils_generate_c(oracle_alg, data_hash, ud, this->set, c_indices)) { goto end; @@ -495,7 +490,6 @@ static bool sign_bliss(private_bliss_private_key_t *this, hash_algorithm_t alg, end: /* cleanup */ DESTROY_IF(sampler); - hasher->destroy(hasher); sig->destroy(sig); fft->destroy(fft); rng->destroy(rng); diff --git a/src/libstrongswan/plugins/bliss/bliss_public_key.c b/src/libstrongswan/plugins/bliss/bliss_public_key.c index 0175b0f8e..2b305f6c2 100644 --- a/src/libstrongswan/plugins/bliss/bliss_public_key.c +++ b/src/libstrongswan/plugins/bliss/bliss_public_key.c @@ -70,11 +70,12 @@ static bool verify_bliss(private_bliss_public_key_t *this, hash_algorithm_t alg, uint8_t data_hash_buf[HASH_SIZE_SHA512]; chunk_t data_hash; hasher_t *hasher; + hash_algorithm_t oracle_alg; bliss_fft_t *fft; bliss_signature_t *sig; bool success = FALSE; - /* Create data hash */ + /* Create data hash using configurable hash algorithm */ hasher = lib->crypto->create_hasher(lib->crypto, alg); if (!hasher ) { @@ -89,28 +90,22 @@ static bool verify_bliss(private_bliss_public_key_t *this, hash_algorithm_t alg, } hasher->destroy(hasher); - /* Create SHA512 hasher for c_indices oracle */ - hasher = lib->crypto->create_hasher(lib->crypto, HASH_SHA512); - if (!hasher) - { - return FALSE; - } - sig = bliss_signature_create_from_data(this->set, signature); if (!sig) { - hasher->destroy(hasher); return FALSE; } sig->get_parameters(sig, &z1, &z2d, &c_indices); if (!bliss_utils_check_norms(this->set, z1, z2d)) { - hasher->destroy(hasher); sig->destroy(sig); return FALSE; } + /* MGF1 hash algorithm to be used for random oracle */ + oracle_alg = HASH_SHA512; + /* Initialize a couple of needed variables */ n = this->set->n; q = this->set->q; @@ -165,8 +160,7 @@ static bool verify_bliss(private_bliss_public_key_t *this, hash_algorithm_t alg, DBG3(DBG_LIB, "%3d %6d %4d %4d", i, u[i], ud[i], z2d[i]); } - if (!bliss_utils_generate_c(hasher, data_hash, ud, n, this->set->kappa, - indices)) + if (!bliss_utils_generate_c(oracle_alg, data_hash, ud, this->set, indices)) { goto end; } @@ -183,7 +177,6 @@ static bool verify_bliss(private_bliss_public_key_t *this, hash_algorithm_t alg, end: /* cleanup */ - hasher->destroy(hasher); sig->destroy(sig); fft->destroy(fft); free(az); diff --git a/src/libstrongswan/plugins/bliss/bliss_utils.c b/src/libstrongswan/plugins/bliss/bliss_utils.c index 85bd7dfd4..5e313ff26 100644 --- a/src/libstrongswan/plugins/bliss/bliss_utils.c +++ b/src/libstrongswan/plugins/bliss/bliss_utils.c @@ -17,6 +17,7 @@ #include #include +#include #include /** @@ -54,64 +55,62 @@ void bliss_utils_round_and_drop(bliss_param_set_t *set, int32_t *x, int16_t *xd) /** * See header. */ -bool bliss_utils_generate_c(hasher_t *hasher, chunk_t data_hash, uint16_t *ud, - int n, uint16_t kappa, uint16_t *c_indices) +bool bliss_utils_generate_c(hash_algorithm_t alg, chunk_t data_hash, + uint16_t *ud, bliss_param_set_t *set, + uint16_t *c_indices) { - int i, index_found, rounds; - uint16_t index; - uint8_t hash[HASH_SIZE_SHA512], un16_buf[2]; - chunk_t un16 = { un16_buf, 2 }; - bool index_taken[n]; + int i, index_trials = 0, index_found = 0; + bool index_taken[set->n]; + uint32_t index; + uint8_t *seed_pos; + chunk_t seed; + mgf1_bitspender_t *bitspender; - for (i = 0; i < n; i++) + seed = chunk_alloca(data_hash.len + set->n * sizeof(uint16_t)); + + /* the data hash makes up the first part of the oracle seed */ + memcpy(seed.ptr, data_hash.ptr, data_hash.len); + seed_pos = seed.ptr + data_hash.len; + + /* followed by the n elements of the ud vector in network order */ + for (i = 0; i < set->n; i++) + { + htoun16(seed_pos, ud[i]); + seed_pos += sizeof(uint16_t); + } + + bitspender = mgf1_bitspender_create(alg, seed, FALSE); + if (!bitspender) + { + return NULL; + } + + for (i = 0; i < set->n; i++) { index_taken[i] = FALSE; } - index_found = 0; - for (rounds = 0; rounds < 0x10000; rounds++) + DBG3(DBG_LIB, " i c_index[i]"); + while (bitspender->get_bits(bitspender, set->n_bits, &index)) { - /* hash data */ - if (!hasher->get_hash(hasher, data_hash, NULL)) - { - return FALSE; - } + index_trials++; - /* followed by the ud vector */ - for (i = 0; i < n; i++) + if (!index_taken[index]) { - htoun16(un16_buf, ud[i]); - if (!hasher->get_hash(hasher, un16, NULL)) + DBG3(DBG_LIB, "%2u %8u", index_found, index); + c_indices[index_found++] = index; + index_taken[index] = TRUE; + + if (index_found == set->kappa) { - return FALSE; - } - } - - /* hash the round iteration */ - htoun16(un16_buf, rounds); - if (!hasher->get_hash(hasher, un16, hash)) - { - return FALSE; - } - - for (i = 0; i < HASH_SIZE_SHA512; i += 2) - { - index = untoh16(&hash[i]) % n; - - if (!index_taken[index]) - { - c_indices[index_found++] = index; - index_taken[index] = TRUE; - - if (index_found == kappa) - { - return TRUE; - } + DBG3(DBG_LIB, "%2d index trials", index_trials); + bitspender->destroy(bitspender); + return TRUE; } } } - DBG1(DBG_LIB, "aborted c_indices generation after 2^16 rounds"); + bitspender->destroy(bitspender); return FALSE; } diff --git a/src/libstrongswan/plugins/bliss/bliss_utils.h b/src/libstrongswan/plugins/bliss/bliss_utils.h index 063fd91c8..156968dd7 100644 --- a/src/libstrongswan/plugins/bliss/bliss_utils.h +++ b/src/libstrongswan/plugins/bliss/bliss_utils.h @@ -47,15 +47,15 @@ void bliss_utils_round_and_drop(bliss_param_set_t *set, int32_t *x, int16_t *xd) /** * Generate the binary challenge vector c as an array of kappa indices * - * @param hasher hasher used as an oracle + * @param alg hash algorithm to be used for the internal oracle * @param data_hash hash of the data to be signed * @param ud input vector ud of size n - * @param n size of input vector ud - * @param kappa parameter kappa + * @param set BLISS parameter set to be used (n, n_bits, kappa) * @param c_indices indexes of non-zero challenge coefficients */ -bool bliss_utils_generate_c(hasher_t *hasher, chunk_t data_hash, uint16_t *ud, - int n, uint16_t kappa, uint16_t *c_indices); +bool bliss_utils_generate_c(hash_algorithm_t alg, chunk_t data_hash, + uint16_t *ud, bliss_param_set_t *set, + uint16_t *c_indices); /** * Check the infinity and l2 norms of the vectors z1 and z2d << d