diff options
Diffstat (limited to '')
-rw-r--r-- | common.h | 17 | ||||
-rw-r--r-- | init.c | 16 | ||||
-rw-r--r-- | libsha2.h | 17 | ||||
-rw-r--r-- | process.c | 69 |
4 files changed, 70 insertions, 49 deletions
@@ -16,6 +16,23 @@ /** + * Truncate an unsigned integer to an unsigned 32-bit integer + * + * @param X:uint_least32_t The value to truncate + * @return :uint_least32_t The 32 lowest bits in `X` + */ +#define TRUNC32(X) ((X) & (uint_least32_t)0xFFFFFFFFUL) + +/** + * Truncate an unsigned integer to an unsigned 64-bit integer + * + * @param X:uint_least64_t The value to truncate + * @return :uint_least64_t The 64 lowest bits in `X` + */ +#define TRUNC64(X) ((X) & (uint_least64_t)0xFFFFFFFFFFFFFFFFULL) + + +/** * Process a chunk using SHA-2 * * @param state The hashing state @@ -5,7 +5,7 @@ /** * Round constants, SHA-256, should keep the 32 most significant bits of 64 first constants */ -static const uint64_t ROUND_CONSTANTS[] = { +static const uint_least64_t ROUND_CONSTANTS[] = { 0x428A2F98D728AE22ULL, 0x7137449123EF65CDULL, 0xB5C0FBCFEC4D3B2FULL, 0xE9B5DBA58189DBBCULL, 0x3956C25BF348B538ULL, 0x59F111F1B605D019ULL, 0x923F82A4AF194F9BULL, 0xAB1C5ED5DA6D8118ULL, 0xD807AA98A3030242ULL, 0x12835B0145706FBEULL, 0x243185BE4EE4B28CULL, 0x550C7DC3D5FFB4E2ULL, @@ -32,7 +32,7 @@ static const uint64_t ROUND_CONSTANTS[] = { /** * Initial state for SHA224 */ -static const uint32_t H_224[] = { +static const uint_least32_t H_224[] = { 0xC1059ED8UL, 0x367CD507UL, 0x3070DD17UL, 0xF70E5939UL, 0xFFC00B31UL, 0x68581511UL, 0x64F98FA7UL, 0xBEFA4FA4UL }; @@ -40,7 +40,7 @@ static const uint32_t H_224[] = { /** * Initial state for SHA256 */ -static const uint32_t H_256[] = { +static const uint_least32_t H_256[] = { 0x6A09E667UL, 0xBB67AE85UL, 0x3C6EF372UL, 0xA54FF53AUL, 0x510E527FUL, 0x9B05688CUL, 0x1F83D9ABUL, 0x5BE0CD19UL }; @@ -48,7 +48,7 @@ static const uint32_t H_256[] = { /** * Initial state for SHA384 */ -static const uint64_t H_384[] = { +static const uint_least64_t H_384[] = { 0xCBBB9D5DC1059ED8ULL, 0x629A292A367CD507ULL, 0x9159015A3070DD17ULL, 0x152FECD8F70E5939ULL, 0x67332667FFC00B31ULL, 0x8EB44A8768581511ULL, 0xDB0C2E0D64F98FA7ULL, 0x47B5481DBEFA4FA4ULL }; @@ -56,7 +56,7 @@ static const uint64_t H_384[] = { /** * Initial state for SHA512 */ -static const uint64_t H_512[] = { +static const uint_least64_t H_512[] = { 0x6A09E667F3BCC908ULL, 0xBB67AE8584CAA73BULL, 0x3C6EF372FE94F82BULL, 0xA54FF53A5F1D36F1ULL, 0x510E527FADE682D1ULL, 0x9B05688C2B3E6C1FULL, 0x1F83D9ABFB41BD6BULL, 0x5BE0CD19137E2179ULL }; @@ -64,7 +64,7 @@ static const uint64_t H_512[] = { /** * Initial state for SHA512/224 */ -static const uint64_t H_512_224[] = { +static const uint_least64_t H_512_224[] = { 0x8C3D37C819544DA2ULL, 0x73E1996689DCD4D6ULL, 0x1DFAB7AE32FF9C82ULL, 0x679DD514582F9FCFULL, 0x0F6D2B697BD44DA8ULL, 0x77E36F7304C48942ULL, 0x3F9D85A86A1D36C8ULL, 0x1112E6AD91D692A1ULL }; @@ -72,7 +72,7 @@ static const uint64_t H_512_224[] = { /** * Initial state for SHA512/256 */ -static const uint64_t H_512_256[] = { +static const uint_least64_t H_512_256[] = { 0x22312194FC2BF72CULL, 0x9F555FA3C84C64C2ULL, 0x2393B86B6F53B151ULL, 0x963877195940EABDULL, 0x96283EE2A88EFFE3ULL, 0xBE5E1E2553863992ULL, 0x2B0199FC2C85B8AAULL, 0x0EB72DDC81C52CA2ULL }; @@ -103,7 +103,7 @@ libsha2_init(struct libsha2_state *restrict state, enum libsha2_algorithm algori /* Set round constants, and chunk size. */ if (algorithm <= LIBSHA2_256) { for (i = 0; i < 64; i++) - state->k.b32[i] = (uint32_t)(ROUND_CONSTANTS[i] >> 32); + state->k.b32[i] = (uint_least32_t)(ROUND_CONSTANTS[i] >> 32); state->chunk_size = 64; } else { memcpy(state->k.b64, ROUND_CONSTANTS, sizeof(ROUND_CONSTANTS)); @@ -66,12 +66,12 @@ struct libsha2_state { /** * For 32-bit algorithms */ - uint32_t b32[64]; + uint_least32_t b32[64]; /** * For 64-bit algorithms */ - uint64_t b64[80]; + uint_least64_t b64[80]; } k; /** @@ -83,12 +83,12 @@ struct libsha2_state { /** * For 32-bit algorithms */ - uint32_t b32[64]; + uint_least32_t b32[64]; /** * For 64-bit algorithms */ - uint64_t b64[80]; + uint_least64_t b64[80]; } w; /** @@ -98,12 +98,12 @@ struct libsha2_state { /** * For 32-bit algorithms */ - uint32_t b32[8]; + uint_least32_t b32[8]; /** * For 64-bit algorithms */ - uint64_t b64[8]; + uint_least64_t b64[8]; } h; /** @@ -115,12 +115,12 @@ struct libsha2_state { /** * For 32-bit algorithms */ - uint32_t b32[8]; + uint_least32_t b32[8]; /** * For 64-bit algorithms */ - uint64_t b64[8]; + uint_least64_t b64[8]; } work_h; /** @@ -153,6 +153,7 @@ struct libsha2_state { * `explicit_bzero` (or `memset`) when you are done. */ struct libsha2_hmac_state { + /** * State of the underlaying hash function */ @@ -6,37 +6,40 @@ * Unified implementation (what can unified without performance impact) * of the chunk processing for all SHA-2 functions * - * @param chunk The data to process - * @param A Wordsize-dependent constant, take a look at the code - * @param B Wordsize-dependent constant, take a look at the code - * @param C Wordsize-dependent constant, take a look at the code - * @param D Wordsize-dependent constant, take a look at the code - * @param E Wordsize-dependent constant, take a look at the code - * @param F Wordsize-dependent constant, take a look at the code - * @param G Wordsize-dependent constant, take a look at the code - * @param H Wordsize-dependent constant, take a look at the code - * @param I Wordsize-dependent constant, take a look at the code - * @param J Wordsize-dependent constant, take a look at the code - * @param K Wordsize-dependent constant, take a look at the code - * @param L Wordsize-dependent constant, take a look at the code - * @param WORD_T `__typeof()` on any wordsize-dependent variable, with exact size - * @param k Round constants - * @param w Words - * @param h Hash values - * @param work_h Space for temporary hash values + * @param chunk The data to process + * @param A Wordsize-dependent constant, take a look at the code + * @param B Wordsize-dependent constant, take a look at the code + * @param C Wordsize-dependent constant, take a look at the code + * @param D Wordsize-dependent constant, take a look at the code + * @param E Wordsize-dependent constant, take a look at the code + * @param F Wordsize-dependent constant, take a look at the code + * @param G Wordsize-dependent constant, take a look at the code + * @param H Wordsize-dependent constant, take a look at the code + * @param I Wordsize-dependent constant, take a look at the code + * @param J Wordsize-dependent constant, take a look at the code + * @param K Wordsize-dependent constant, take a look at the code + * @param L Wordsize-dependent constant, take a look at the code + * @param WORD_T `__typeof()` on any wordsize-dependent variable + * @param WORD_SIZE 4 for 32-bit algorithms and 8 for 64-bit algorithms + * @param TRUNC `TRUNC32` for 32-bit algorithms and `TRUNC64` for 64-bit algorithms + * @param k Round constants + * @param w Words + * @param h Hash values + * @param work_h Space for temporary hash values */ -#define SHA2_IMPLEMENTATION(chunk, A, B, C, D, E, F, G, H, I, J, K, L, WORD_T, k, w, h, work_h)\ +#define SHA2_IMPLEMENTATION(chunk, A, B, C, D, E, F, G, H, I, J, K, L, WORD_T, WORD_SIZE, TRUNC, k, w, h, work_h) \ memcpy(work_h, h, sizeof(work_h));\ \ memset(w, 0, 16 * sizeof(*(w)));\ for (i = 0; i < 16; i++)\ - for (j = 0; j < sizeof(WORD_T); j++)\ - w[i] |= ((WORD_T)(chunk[(i + 1) * sizeof(WORD_T) - j - 1])) << (j << 3);\ + for (j = 0; j < WORD_SIZE; j++)\ + w[i] |= ((WORD_T)(chunk[(i + 1) * WORD_SIZE - j - 1])) << (j << 3);\ \ for (i = 16; i < sizeof(k) / sizeof(*(k)); i++) {\ w[i] = w[i - 16] + w[i - 7];\ w[i] += ROTR(w[i - 15], A) ^ ROTR(w[i - 15], B) ^ (w[i - 15] >> (C));\ w[i] += ROTR(w[i - 2], D) ^ ROTR(w[i - 2], E) ^ (w[i - 2] >> (F));\ + w[i] = TRUNC(w[i]);\ }\ \ for (i = 0; i < sizeof(k) / sizeof(*(k)); i++) {\ @@ -46,30 +49,30 @@ s1 += ROTR(work_h[4], G) ^ ROTR(work_h[4], H) ^ ROTR(work_h[4], I);\ s0 += ROTR(work_h[0], J) ^ ROTR(work_h[0], K) ^ ROTR(work_h[0], L);\ \ - memmove(work_h + 1, work_h, 7 * sizeof(*(work_h)));\ - work_h[4] += s1;\ - work_h[0] = s1 + s0;\ + memmove(&work_h[1], work_h, 7 * sizeof(*(work_h)));\ + work_h[4] = TRUNC(work_h[4] + s1);\ + work_h[0] = TRUNC(s1 + s0);\ }\ \ for (i = 0; i < 8; i++)\ - h[i] += work_h[i] + h[i] = TRUNC(h[i] + work_h[i]); void libsha2_process(struct libsha2_state *restrict state, const unsigned char *restrict chunk) { if (state->algorithm <= LIBSHA2_256) { - uint32_t s0, s1; + uint_least32_t s0, s1; size_t i, j; #if defined(__GNUC__) # pragma GCC diagnostic push # pragma GCC diagnostic ignored "-Wmemset-elt-size" #endif -#define ROTR(X, N) (((X) >> (N)) | ((X) << ((sizeof(uint32_t) * 8) - (N)))) +#define ROTR(X, N) TRUNC32(((X) >> (N)) | ((X) << (32 - (N)))) - SHA2_IMPLEMENTATION(chunk, 7, 18, 3, 17, 19, 10, 6, 11, 25, 2, 13, 22, uint32_t, - state->k.b32, state->w.b32, state->h.b32, state->work_h.b32); + SHA2_IMPLEMENTATION(chunk, 7, 18, 3, 17, 19, 10, 6, 11, 25, 2, 13, 22, uint_least32_t, + 4, TRUNC32, state->k.b32, state->w.b32, state->h.b32, state->work_h.b32); #undef ROTR #if defined(__GNUC__) @@ -77,13 +80,13 @@ libsha2_process(struct libsha2_state *restrict state, const unsigned char *restr #endif } else { - uint64_t s0, s1; + uint_least64_t s0, s1; size_t i, j; -#define ROTR(X, N) (((X) >> (N)) | ((X) << ((sizeof(uint64_t) * 8) - (N)))) +#define ROTR(X, N) TRUNC64(((X) >> (N)) | ((X) << (64 - (N)))) - SHA2_IMPLEMENTATION(chunk, 1, 8, 7, 19, 61, 6, 14, 18, 41, 28, 34, 39, uint64_t, - state->k.b64, state->w.b64, state->h.b64, state->work_h.b64); + SHA2_IMPLEMENTATION(chunk, 1, 8, 7, 19, 61, 6, 14, 18, 41, 28, 34, 39, uint_least64_t, + 8, TRUNC64, state->k.b64, state->w.b64, state->h.b64, state->work_h.b64); #undef ROTR } |