1
0
mirror of https://github.com/trezor/trezor-firmware.git synced 2024-11-22 07:28:10 +00:00

crypto/hmac_drbg: Add nonce parameter to hmac_drbg_init().

This commit is contained in:
Andrew Kozlik 2019-06-07 12:14:10 +02:00
parent 7c44340c40
commit b915092a44
3 changed files with 22 additions and 19 deletions

View File

@ -25,13 +25,13 @@
#include "memzero.h"
#include "sha2.h"
static void update_k(HMAC_DRBG_CTX *ctx, uint8_t domain, const uint8_t *data,
size_t len) {
// Computes K = HMAC(K, V || domain || data).
static void update_k(HMAC_DRBG_CTX *ctx, uint8_t domain, const uint8_t *data1,
size_t len1, const uint8_t *data2, size_t len2) {
// Computes K = HMAC(K, V || domain || data1 || data 2).
// First hash operation of HMAC.
uint32_t h[SHA256_BLOCK_LENGTH / sizeof(uint32_t)] = {0};
if (data == NULL) {
if (len1 + len2 == 0) {
ctx->v[8] = 0x00800000;
ctx->v[15] = (SHA256_BLOCK_LENGTH + SHA256_DIGEST_LENGTH + 1) * 8;
sha256_Transform(ctx->idig, ctx->v, h);
@ -49,7 +49,8 @@ static void update_k(HMAC_DRBG_CTX *ctx, uint8_t domain, const uint8_t *data,
}
((uint8_t *)sha_ctx.buffer)[SHA256_DIGEST_LENGTH] = domain;
sha_ctx.bitcount = (SHA256_BLOCK_LENGTH + SHA256_DIGEST_LENGTH + 1) * 8;
sha256_Update(&sha_ctx, data, len);
sha256_Update(&sha_ctx, data1, len1);
sha256_Update(&sha_ctx, data2, len2);
sha256_Final(&sha_ctx, (uint8_t *)h);
#if BYTE_ORDER == LITTLE_ENDIAN
for (size_t i = 0; i < SHA256_DIGEST_LENGTH / sizeof(uint32_t); i++)
@ -82,7 +83,7 @@ static void update_v(HMAC_DRBG_CTX *ctx) {
sha256_Transform(ctx->odig, ctx->v, ctx->v);
}
void hmac_drbg_init(HMAC_DRBG_CTX *ctx, const uint8_t *entropy, size_t len) {
void hmac_drbg_init(HMAC_DRBG_CTX *ctx, const uint8_t *entropy, size_t entropy_len, const uint8_t *nonce, size_t nonce_len) {
uint32_t h[SHA256_BLOCK_LENGTH / sizeof(uint32_t)];
// Precompute the inner digest and outer digest of K = 0x00 ... 0x00.
@ -97,16 +98,16 @@ void hmac_drbg_init(HMAC_DRBG_CTX *ctx, const uint8_t *entropy, size_t len) {
ctx->v[8] = 0x80000000;
ctx->v[15] = (SHA256_BLOCK_LENGTH + SHA256_DIGEST_LENGTH) * 8;
hmac_drbg_reseed(ctx, entropy, len);
hmac_drbg_reseed(ctx, entropy, entropy_len, nonce, nonce_len);
memzero(h, sizeof(h));
}
void hmac_drbg_reseed(HMAC_DRBG_CTX *ctx, const uint8_t *entropy, size_t len) {
update_k(ctx, 0, entropy, len);
void hmac_drbg_reseed(HMAC_DRBG_CTX *ctx, const uint8_t *entropy, size_t len, const uint8_t *addin, size_t addin_len) {
update_k(ctx, 0, entropy, len, addin, addin_len);
update_v(ctx);
if (len == 0) return;
update_k(ctx, 1, entropy, len);
update_k(ctx, 1, entropy, len, addin, addin_len);
update_v(ctx);
}
@ -121,6 +122,6 @@ void hmac_drbg_generate(HMAC_DRBG_CTX *ctx, uint8_t *buf, size_t len) {
}
}
}
update_k(ctx, 0, NULL, 0);
update_k(ctx, 0, NULL, 0, NULL, 0);
update_v(ctx);
}

View File

@ -34,8 +34,8 @@ typedef struct _HMAC_DRBG_CTX {
uint32_t v[SHA256_BLOCK_LENGTH / sizeof(uint32_t)];
} HMAC_DRBG_CTX;
void hmac_drbg_init(HMAC_DRBG_CTX *ctx, const uint8_t *buf, size_t len);
void hmac_drbg_reseed(HMAC_DRBG_CTX *ctx, const uint8_t *buf, size_t len);
void hmac_drbg_init(HMAC_DRBG_CTX *ctx, const uint8_t *buf, size_t len, const uint8_t *nonce, size_t nonce_len);
void hmac_drbg_reseed(HMAC_DRBG_CTX *ctx, const uint8_t *buf, size_t len, const uint8_t *addin, size_t addin_len);
void hmac_drbg_generate(HMAC_DRBG_CTX *ctx, uint8_t *buf, size_t len);
#endif

View File

@ -4627,8 +4627,8 @@ END_TEST
START_TEST(test_hmac_drbg) {
char entropy[] =
"06032cd5eed33f39265f49ecb142c511da9aff2af71203bffaf34a9ca5bd9c0d0e66f71e"
"dc43e42a45ad3c6fc6cdc4df";
"06032cd5eed33f39265f49ecb142c511da9aff2af71203bffaf34a9ca5bd9c0d";
char nonce[] = "0e66f71edc43e42a45ad3c6fc6cdc4df";
char reseed[] =
"01920a4e669ed3a85ae8a33b35a74ad7fb2a6bb4cf395ce00334a9c9a5a5d552";
char expected[] =
@ -4638,15 +4638,17 @@ START_TEST(test_hmac_drbg) {
"a38cc5b6499dc43f7f2bd09e1e0f8f5885935124";
uint8_t result[128];
uint8_t nonce_bytes[16];
memcpy(nonce_bytes, fromhex(nonce), sizeof(nonce_bytes));
HMAC_DRBG_CTX ctx;
hmac_drbg_init(&ctx, fromhex(entropy), strlen(entropy) / 2);
hmac_drbg_reseed(&ctx, fromhex(reseed), strlen(reseed) / 2);
hmac_drbg_init(&ctx, fromhex(entropy), strlen(entropy) / 2, nonce_bytes, strlen(nonce) / 2);
hmac_drbg_reseed(&ctx, fromhex(reseed), strlen(reseed) / 2, NULL, 0);
hmac_drbg_generate(&ctx, result, sizeof(result));
hmac_drbg_generate(&ctx, result, sizeof(result));
ck_assert_mem_eq(result, fromhex(expected), sizeof(result));
hmac_drbg_init(&ctx, fromhex(entropy), strlen(entropy) / 2);
hmac_drbg_reseed(&ctx, fromhex(reseed), strlen(reseed) / 2);
hmac_drbg_init(&ctx, fromhex(entropy), strlen(entropy) / 2, nonce_bytes, strlen(nonce) / 2);
hmac_drbg_reseed(&ctx, fromhex(reseed), strlen(reseed) / 2, NULL, 0);
hmac_drbg_generate(&ctx, result, sizeof(result) - 13);
hmac_drbg_generate(&ctx, result, sizeof(result) - 17);
ck_assert_mem_eq(result, fromhex(expected), sizeof(result) - 17);