diff options
author | wtc%google.com <devnull@localhost> | 2009-03-29 16:51:58 +0000 |
---|---|---|
committer | wtc%google.com <devnull@localhost> | 2009-03-29 16:51:58 +0000 |
commit | 030d974fdacfd1ef0247f4b4c9a21edfc9f0e78a (patch) | |
tree | 476400bf6f18fcb7b51e2fc760d4b9baff9a05c0 | |
parent | 5b884abf0d63de6f5d59ef99b720ae8e83aa667e (diff) | |
download | nss-hg-030d974fdacfd1ef0247f4b4c9a21edfc9f0e78a.tar.gz |
Bug 457045: moved the remaining FIPS 186-2 RNG code from drbg.c to dsa.c.
The comments and code could use more work in the future. r=nelson.
Modified Files:
mozilla/security/nss/lib/freebl/drbg.c
mozilla/security/nss/lib/freebl/dsa.c
-rw-r--r-- | security/nss/lib/freebl/drbg.c | 109 | ||||
-rw-r--r-- | security/nss/lib/freebl/dsa.c | 109 |
2 files changed, 105 insertions, 113 deletions
diff --git a/security/nss/lib/freebl/drbg.c b/security/nss/lib/freebl/drbg.c index 587d458e3..a0e008624 100644 --- a/security/nss/lib/freebl/drbg.c +++ b/security/nss/lib/freebl/drbg.c @@ -43,7 +43,7 @@ #include "stubs.h" #endif -#include "prerr.h" +#include "prerror.h" #include "secerr.h" #include "prtypes.h" @@ -646,113 +646,6 @@ RNG_RNGShutdown(void) } /* - * Specialized RNG for DSA - * - * As per Algorithm 1 of FIPS 186-2 Change Notice 1, in step 3.3 the value - * Xj should be reduced mod q, a 160-bit prime number. Since this parameter - * is only meaningful in the context of DSA, the above RNG functions - * were implemented without it. They are re-implemented below for use - * with DSA. - * - * Is this code needed now that we have the Hash_DRBG function? - * - */ -#define FIPS_DSA_Q 160 -#define QSIZE (FIPS_DSA_Q / PR_BITS_PER_BYTE) - -/* - * FIPS 186 requires result from random output to be reduced mod q when - * generating random numbers for DSA. - * - * Input: w, 2*QSIZE bytes - * q, DSA_SUBPRIME_LEN bytes - * Output: xj, DSA_SUBPRIME_LEN bytes - */ -SECStatus -FIPS186Change_ReduceModQForDSA(const PRUint8 *w, - const PRUint8 *q, - PRUint8 *xj) -{ - mp_int W, Q, Xj; - mp_err err; - SECStatus rv = SECSuccess; - - /* Initialize MPI integers. */ - MP_DIGITS(&W) = 0; - MP_DIGITS(&Q) = 0; - MP_DIGITS(&Xj) = 0; - CHECK_MPI_OK( mp_init(&W) ); - CHECK_MPI_OK( mp_init(&Q) ); - CHECK_MPI_OK( mp_init(&Xj) ); - /* - * Convert input arguments into MPI integers. - */ - CHECK_MPI_OK( mp_read_unsigned_octets(&W, w, 2*QSIZE) ); - CHECK_MPI_OK( mp_read_unsigned_octets(&Q, q, DSA_SUBPRIME_LEN) ); - /* - * Algorithm 1 of FIPS 186-2 Change Notice 1, Step 3.3 - * - * xj = (w0 || w1) mod q - */ - CHECK_MPI_OK( mp_mod(&W, &Q, &Xj) ); - CHECK_MPI_OK( mp_to_fixlen_octets(&Xj, xj, DSA_SUBPRIME_LEN) ); -cleanup: - mp_clear(&W); - mp_clear(&Q); - mp_clear(&Xj); - if (err) { - MP_TO_SEC_ERROR(err); - rv = SECFailure; - } - return rv; -} - -/* -** Generate some random bytes, using the global random number generator -** object. In DSA mode, so there is a q. -*/ -SECStatus -DSA_GenerateGlobalRandomBytes(void *dest, size_t len, const PRUint8 *q) -{ - SECStatus rv; - PRUint8 w[2*QSIZE]; - - /* is this still necessary for the Hash_DRBG prng? */ - - PORT_Assert(q && len == DSA_SUBPRIME_LEN); - if (len != DSA_SUBPRIME_LEN) { - PORT_SetError(SEC_ERROR_OUTPUT_LEN); - return SECFailure; - } - if (*q == 0) { - ++q; - } - rv = prng_GenerateGlobalRandomBytes(globalrng, w, 2*QSIZE); - if (rv != SECSuccess) { - return rv; - } - FIPS186Change_ReduceModQForDSA(w, q, (PRUint8 *)dest); - return rv; -} - -/* - * The core of Algorithm 1 of FIPS 186-2 Change Notice 1, - * we no longer support FIPS 186-2. This function was exported - * for power-on self tests and FIPS tests. Keep this stub, which fails, - * to prevent crashes, but also to signal to test code that - * FIPS-186 is no longer supported. - */ -SECStatus -FIPS186Change_GenerateX(PRUint8 *XKEY, const PRUint8 *XSEEDj, - PRUint8 *x_j) -{ - PORT_SetError(PR_NOT_IMPLEMENTED_ERROR); - return SECFailure; -} - - - -/* * Test case interface. used by fips testing and power on self test */ /* make sure the test context is separate from the global context, This diff --git a/security/nss/lib/freebl/dsa.c b/security/nss/lib/freebl/dsa.c index bfb50afd5..019e76b0f 100644 --- a/security/nss/lib/freebl/dsa.c +++ b/security/nss/lib/freebl/dsa.c @@ -41,6 +41,7 @@ #include "stubs.h" #endif +#include "prerror.h" #include "secerr.h" #include "prtypes.h" @@ -55,9 +56,107 @@ /* XXX to be replaced by define in blapit.h */ #define NSS_FREEBL_DSA_DEFAULT_CHUNKSIZE 2048 -/* DSA-specific random number function defined in prng_fips1861.c. */ -extern SECStatus -DSA_GenerateGlobalRandomBytes(void *dest, size_t len, const unsigned char *q); +#define FIPS_DSA_Q 160 +#define QSIZE (FIPS_DSA_Q / PR_BITS_PER_BYTE) + +/* + * FIPS 186-2 requires result from random output to be reduced mod q when + * generating random numbers for DSA. + * + * Input: w, 2*QSIZE bytes + * q, DSA_SUBPRIME_LEN bytes + * Output: xj, DSA_SUBPRIME_LEN bytes + */ +SECStatus +FIPS186Change_ReduceModQForDSA(const PRUint8 *w, + const PRUint8 *q, + PRUint8 *xj) +{ + mp_int W, Q, Xj; + mp_err err; + SECStatus rv = SECSuccess; + + /* Initialize MPI integers. */ + MP_DIGITS(&W) = 0; + MP_DIGITS(&Q) = 0; + MP_DIGITS(&Xj) = 0; + CHECK_MPI_OK( mp_init(&W) ); + CHECK_MPI_OK( mp_init(&Q) ); + CHECK_MPI_OK( mp_init(&Xj) ); + /* + * Convert input arguments into MPI integers. + */ + CHECK_MPI_OK( mp_read_unsigned_octets(&W, w, 2*QSIZE) ); + CHECK_MPI_OK( mp_read_unsigned_octets(&Q, q, DSA_SUBPRIME_LEN) ); + /* + * Algorithm 1 of FIPS 186-2 Change Notice 1, Step 3.3 + * + * xj = (w0 || w1) mod q + */ + CHECK_MPI_OK( mp_mod(&W, &Q, &Xj) ); + CHECK_MPI_OK( mp_to_fixlen_octets(&Xj, xj, DSA_SUBPRIME_LEN) ); +cleanup: + mp_clear(&W); + mp_clear(&Q); + mp_clear(&Xj); + if (err) { + MP_TO_SEC_ERROR(err); + rv = SECFailure; + } + return rv; +} + +/* + * The core of Algorithm 1 of FIPS 186-2 Change Notice 1. + * + * We no longer support FIPS 186-2 RNG. This function was exported + * for power-up self tests and FIPS tests. Keep this stub, which fails, + * to prevent crashes, but also to signal to test code that FIPS 186-2 + * RNG is no longer supported. + */ +SECStatus +FIPS186Change_GenerateX(PRUint8 *XKEY, const PRUint8 *XSEEDj, + PRUint8 *x_j) +{ + PORT_SetError(PR_NOT_IMPLEMENTED_ERROR); + return SECFailure; +} + +/* + * Specialized RNG for DSA + * + * As per Algorithm 1 of FIPS 186-2 Change Notice 1, in step 3.3 the value + * Xj should be reduced mod q, a 160-bit prime number. Since this parameter + * is only meaningful in the context of DSA, the above RNG functions + * were implemented without it. They are re-implemented below for use + * with DSA. + */ + +/* +** Generate some random bytes, using the global random number generator +** object. In DSA mode, so there is a q. +*/ +static SECStatus +dsa_GenerateGlobalRandomBytes(void *dest, size_t len, const PRUint8 *q) +{ + SECStatus rv; + PRUint8 w[2*QSIZE]; + + PORT_Assert(q && len == DSA_SUBPRIME_LEN); + if (len != DSA_SUBPRIME_LEN) { + PORT_SetError(SEC_ERROR_OUTPUT_LEN); + return SECFailure; + } + if (*q == 0) { + ++q; + } + rv = RNG_GenerateGlobalRandomBytes(w, 2*QSIZE); + if (rv != SECSuccess) { + return rv; + } + FIPS186Change_ReduceModQForDSA(w, q, (PRUint8 *)dest); + return rv; +} static void translate_mpi_error(mp_err err) { @@ -150,7 +249,7 @@ DSA_NewKey(const PQGParams *params, DSAPrivateKey **privKey) do { /* Generate seed bytes for x according to FIPS 186-1 appendix 3 */ - if (DSA_GenerateGlobalRandomBytes(seed, DSA_SUBPRIME_LEN, + if (dsa_GenerateGlobalRandomBytes(seed, DSA_SUBPRIME_LEN, params->subPrime.data)) return SECFailure; /* Disallow values of 0 and 1 for x. */ @@ -299,7 +398,7 @@ DSA_SignDigest(DSAPrivateKey *key, SECItem *signature, const SECItem *digest) PORT_SetError(0); do { - rv = DSA_GenerateGlobalRandomBytes(kSeed, DSA_SUBPRIME_LEN, + rv = dsa_GenerateGlobalRandomBytes(kSeed, DSA_SUBPRIME_LEN, key->params.subPrime.data); if (rv != SECSuccess) break; |