Signed-off-by: Dmitry Eremin-Solenikov <[email protected]>
---
nettle-meta.h | 12 +++++
sha2.h | 45 ++++++++++++++++--
sha384-meta.c | 3 ++
sha512-meta.c | 3 ++
sha512.c | 129 ++++++++++++++++++++++++++++++++++++--------------
5 files changed, 152 insertions(+), 40 deletions(-)
diff --git a/nettle-meta.h b/nettle-meta.h
index a28cecf5fe62..da9591287e79 100644
--- a/nettle-meta.h
+++ b/nettle-meta.h
@@ -155,6 +155,16 @@ struct nettle_bctx_hash
(nettle_hash_block_digest_func *) name##_block_digest \
}
+#define _NETTLE_BLOCK_HASH_US(name, name_us, NAME) { \
+ #name, \
+ sizeof(struct name_us##_state), \
+ NAME##_DIGEST_SIZE, \
+ NAME##_BLOCK_SIZE, \
+ (nettle_hash_block_init_func *) name_us##_block_init, \
+ (nettle_hash_block_update_func *) name_us##_block_update, \
+ (nettle_hash_block_digest_func *) name_us##_block_digest \
+}
+
/* null-terminated list of digests implemented by this version of nettle */
const struct nettle_hash * const * _NETTLE_ATTRIBUTE_PURE
nettle_get_hashes (void);
@@ -186,6 +196,8 @@ extern const struct nettle_bctx_hash nettle_bctx_ripemd160;
extern const struct nettle_bctx_hash nettle_bctx_sha1;
extern const struct nettle_bctx_hash nettle_bctx_sha224;
extern const struct nettle_bctx_hash nettle_bctx_sha256;
+extern const struct nettle_bctx_hash nettle_bctx_sha384;
+extern const struct nettle_bctx_hash nettle_bctx_sha512;
struct nettle_aead
{
diff --git a/sha2.h b/sha2.h
index 95640b5f4b7f..4f8f5c300822 100644
--- a/sha2.h
+++ b/sha2.h
@@ -53,9 +53,14 @@ extern "C" {
#define sha256_block_digest nettle_sha256_block_digest
#define sha384_init nettle_sha384_init
#define sha384_digest nettle_sha384_digest
+#define sha384_block_init nettle_sha384_block_init
+#define sha384_block_digest nettle_sha384_block_digest
#define sha512_init nettle_sha512_init
#define sha512_update nettle_sha512_update
#define sha512_digest nettle_sha512_digest
+#define sha512_block_init nettle_sha512_block_init
+#define sha512_block_update nettle_sha512_block_update
+#define sha512_block_digest nettle_sha512_block_digest
#define sha512_224_init nettle_sha512_224_init
#define sha512_224_digest nettle_sha512_224_digest
#define sha512_256_init nettle_sha512_256_init
@@ -153,12 +158,16 @@ sha224_block_digest(struct sha256_state *state,
/* Digest is kept internally as 8 64-bit words. */
#define _SHA512_DIGEST_LENGTH 8
-struct sha512_ctx
+struct sha512_state
{
uint64_t state[_SHA512_DIGEST_LENGTH]; /* State variables */
uint64_t count_low, count_high; /* 128-bit block count */
- unsigned int index; /* index into buffer */
- uint8_t block[SHA512_BLOCK_SIZE]; /* SHA512 data buffer */
+};
+
+struct sha512_ctx
+{
+ struct sha512_state state;
+ BLOCK_CTX(SHA512_BLOCK_SIZE);
};
void
@@ -174,12 +183,28 @@ sha512_digest(struct sha512_ctx *ctx,
size_t length,
uint8_t *digest);
+void
+sha512_block_init(struct sha512_state *state,
+ struct block_ctx *bctx);
+
+void
+sha512_block_update(struct sha512_state *state,
+ struct block_ctx *bctx,
+ size_t length,
+ const uint8_t *data);
+
+void
+sha512_block_digest(struct sha512_state *state,
+ struct block_ctx *bctx,
+ size_t length,
+ uint8_t *digest);
/* SHA384, a truncated SHA512 with different initial state. */
#define SHA384_DIGEST_SIZE 48
#define SHA384_BLOCK_SIZE SHA512_BLOCK_SIZE
#define sha384_ctx sha512_ctx
+#define sha384_state sha512_state
void
sha384_init(struct sha512_ctx *ctx);
@@ -191,6 +216,18 @@ sha384_digest(struct sha512_ctx *ctx,
size_t length,
uint8_t *digest);
+void
+sha384_block_init(struct sha512_state *state,
+ struct block_ctx *bctx);
+
+#define sha384_block_update sha512_block_update
+
+void
+sha384_block_digest(struct sha512_state *state,
+ struct block_ctx *bctx,
+ size_t length,
+ uint8_t *digest);
+
/* SHA512_224 and SHA512_256, two truncated versions of SHA512
with different initial states. */
@@ -222,7 +259,7 @@ void
sha512_256_digest(struct sha512_256_ctx *ctx,
size_t length,
uint8_t *digest);
-
+
#ifdef __cplusplus
}
#endif
diff --git a/sha384-meta.c b/sha384-meta.c
index 0eb561054a73..7c842f1b1b44 100644
--- a/sha384-meta.c
+++ b/sha384-meta.c
@@ -39,3 +39,6 @@
const struct nettle_hash nettle_sha384
= _NETTLE_HASH(sha384, SHA384);
+
+const struct nettle_bctx_hash nettle_bctx_sha384
+= _NETTLE_BLOCK_HASH(sha384, SHA384);
diff --git a/sha512-meta.c b/sha512-meta.c
index d592c4bec6c7..c61812d5a8e1 100644
--- a/sha512-meta.c
+++ b/sha512-meta.c
@@ -39,3 +39,6 @@
const struct nettle_hash nettle_sha512
= _NETTLE_HASH(sha512, SHA512);
+
+const struct nettle_bctx_hash nettle_bctx_sha512
+= _NETTLE_BLOCK_HASH(sha512, SHA512);
diff --git a/sha512.c b/sha512.c
index 6936cb501142..16d79a989955 100644
--- a/sha512.c
+++ b/sha512.c
@@ -116,7 +116,7 @@ K[80] =
#define COMPRESS(ctx, data) (_nettle_sha512_compress((ctx)->state, (data), K))
void
-sha512_init(struct sha512_ctx *ctx)
+sha512_block_init(struct sha512_state *state, struct block_ctx *bctx)
{
/* Initial values, generated by the gp script
{
@@ -135,24 +135,40 @@ sha512_init(struct sha512_ctx *ctx)
0x1F83D9ABFB41BD6BULL,0x5BE0CD19137E2179ULL,
};
- memcpy(ctx->state, H0, sizeof(H0));
+ memcpy(state->state, H0, sizeof(H0));
/* Initialize bit count */
- ctx->count_low = ctx->count_high = 0;
+ state->count_low = state->count_high = 0;
/* Initialize buffer */
- ctx->index = 0;
+ bctx->index = 0;
+}
+
+void
+sha512_init(struct sha512_ctx *ctx)
+{
+ return sha512_block_init(&ctx->state, (struct block_ctx *)&ctx->block);
}
void
sha512_update(struct sha512_ctx *ctx,
size_t length, const uint8_t *data)
{
- MD_UPDATE (ctx, length, data, COMPRESS, MD_INCR(ctx));
+ MD_BLOCK_UPDATE (&ctx->state, &ctx->block, SHA512_BLOCK_SIZE, length, data,
COMPRESS, MD_INCR(&ctx->state));
+}
+
+void
+sha512_block_update(struct sha512_state *state,
+ struct block_ctx *bctx,
+ size_t length,
+ const uint8_t *data)
+{
+ MD_BLOCK_UPDATE(state, bctx, SHA512_BLOCK_SIZE, length, data, COMPRESS,
MD_INCR(state));
}
static void
-sha512_write_digest(struct sha512_ctx *ctx,
+sha512_write_digest(struct sha512_state *state,
+ struct block_ctx *bctx,
size_t length,
uint8_t *digest)
{
@@ -164,29 +180,29 @@ sha512_write_digest(struct sha512_ctx *ctx,
assert(length <= SHA512_DIGEST_SIZE);
- MD_PAD(ctx, 16, COMPRESS);
+ MD_BLOCK_PAD(state, bctx, SHA512_BLOCK_SIZE, 16, COMPRESS);
/* There are 1024 = 2^10 bits in one block */
- high = (ctx->count_high << 10) | (ctx->count_low >> 54);
- low = (ctx->count_low << 10) | (ctx->index << 3);
+ high = (state->count_high << 10) | (state->count_low >> 54);
+ low = (state->count_low << 10) | (bctx->index << 3);
/* This is slightly inefficient, as the numbers are converted to
big-endian format, and will be converted back by the compression
function. It's probably not worth the effort to fix this. */
- WRITE_UINT64(ctx->block + (SHA512_BLOCK_SIZE - 16), high);
- WRITE_UINT64(ctx->block + (SHA512_BLOCK_SIZE - 8), low);
- COMPRESS(ctx, ctx->block);
+ WRITE_UINT64(bctx->buffer + (SHA512_BLOCK_SIZE - 16), high);
+ WRITE_UINT64(bctx->buffer + (SHA512_BLOCK_SIZE - 8), low);
+ COMPRESS(state, bctx->buffer);
words = length / 8;
leftover = length % 8;
for (i = 0; i < words; i++, digest += 8)
- WRITE_UINT64(digest, ctx->state[i]);
+ WRITE_UINT64(digest, state->state[i]);
if (leftover)
{
/* Truncate to the right size */
- uint64_t word = ctx->state[i] >> (8*(8 - leftover));
+ uint64_t word = state->state[i] >> (8*(8 - leftover));
do {
digest[--leftover] = word & 0xff;
@@ -202,13 +218,23 @@ sha512_digest(struct sha512_ctx *ctx,
{
assert(length <= SHA512_DIGEST_SIZE);
- sha512_write_digest(ctx, length, digest);
+ sha512_write_digest(&ctx->state, (struct block_ctx *)&ctx->block, length,
digest);
sha512_init(ctx);
}
+void
+sha512_block_digest(struct sha512_state *state,
+ struct block_ctx *bctx,
+ size_t length,
+ uint8_t *digest)
+{
+ sha512_write_digest(state, bctx, length, digest);
+ sha512_block_init(state, bctx);
+}
+
/* sha384 variant. */
void
-sha384_init(struct sha512_ctx *ctx)
+sha384_block_init(struct sha512_state *state, struct block_ctx *bctx)
{
/* Initial values, generated by the gp script
{
@@ -227,13 +253,19 @@ sha384_init(struct sha512_ctx *ctx)
0xDB0C2E0D64F98FA7ULL, 0x47B5481DBEFA4FA4ULL,
};
- memcpy(ctx->state, H0, sizeof(H0));
+ memcpy(state->state, H0, sizeof(H0));
/* Initialize bit count */
- ctx->count_low = ctx->count_high = 0;
+ state->count_low = state->count_high = 0;
/* Initialize buffer */
- ctx->index = 0;
+ bctx->index = 0;
+}
+
+void
+sha384_init(struct sha512_ctx *ctx)
+{
+ return sha384_block_init(&ctx->state, (struct block_ctx *)&ctx->block);
}
void
@@ -243,14 +275,26 @@ sha384_digest(struct sha512_ctx *ctx,
{
assert(length <= SHA384_DIGEST_SIZE);
- sha512_write_digest(ctx, length, digest);
+ sha512_write_digest(&ctx->state, (struct block_ctx *)&ctx->block, length,
digest);
sha384_init(ctx);
}
-/* sha-512/224 variant. */
void
-sha512_224_init(struct sha512_224_ctx *ctx)
+sha384_block_digest(struct sha512_state *state,
+ struct block_ctx *bctx,
+ size_t length,
+ uint8_t *digest)
+{
+ assert(length <= SHA384_DIGEST_SIZE);
+
+ sha512_write_digest(state, bctx, length, digest);
+ sha384_block_init(state, bctx);
+}
+
+/* sha-512/224 variant. */
+static void
+sha512_224_block_init(struct sha512_state *state, struct block_ctx *bctx)
{
static const uint64_t H0[_SHA512_DIGEST_LENGTH] =
{
@@ -260,30 +304,37 @@ sha512_224_init(struct sha512_224_ctx *ctx)
0x3f9d85a86a1d36c8ULL, 0x1112e6ad91d692a1ULL,
};
- memcpy(ctx->state, H0, sizeof(H0));
+ memcpy(state->state, H0, sizeof(H0));
/* Initialize bit count */
- ctx->count_low = ctx->count_high = 0;
+ state->count_low = state->count_high = 0;
/* Initialize buffer */
- ctx->index = 0;
+ bctx->index = 0;
+}
+
+void
+sha512_224_init(struct sha512_ctx *ctx)
+{
+ return sha512_224_block_init(&ctx->state, (struct block_ctx *)&ctx->block);
}
void
sha512_224_digest(struct sha512_224_ctx *ctx,
- size_t length,
- uint8_t *digest)
+ size_t length,
+ uint8_t *digest)
{
assert(length <= SHA224_DIGEST_SIZE);
- sha512_write_digest(ctx, length, digest);
+ sha512_write_digest(&ctx->state, (struct block_ctx *)&ctx->block, length,
digest);
sha512_224_init(ctx);
}
/* sha-512/256 variant. */
-void
-sha512_256_init(struct sha512_256_ctx *ctx)
+static void
+sha512_256_block_init(struct sha512_state *state,
+ struct block_ctx *bctx)
{
static const uint64_t H0[_SHA512_DIGEST_LENGTH] =
{
@@ -293,22 +344,28 @@ sha512_256_init(struct sha512_256_ctx *ctx)
0x2b0199fc2c85b8aaULL, 0x0eb72ddc81c52ca2ULL,
};
- memcpy(ctx->state, H0, sizeof(H0));
+ memcpy(state->state, H0, sizeof(H0));
/* Initialize bit count */
- ctx->count_low = ctx->count_high = 0;
+ state->count_low = state->count_high = 0;
/* Initialize buffer */
- ctx->index = 0;
+ bctx->index = 0;
+}
+
+void
+sha512_256_init(struct sha512_256_ctx *ctx)
+{
+ sha512_256_block_init(&ctx->state, (struct block_ctx *)&ctx->block);
}
void
sha512_256_digest(struct sha512_256_ctx *ctx,
- size_t length,
- uint8_t *digest)
+ size_t length,
+ uint8_t *digest)
{
assert(length <= SHA256_DIGEST_SIZE);
- sha512_write_digest(ctx, length, digest);
+ sha512_write_digest(&ctx->state, (struct block_ctx *)&ctx->block, length,
digest);
sha512_256_init(ctx);
}
--
2.20.1
_______________________________________________
nettle-bugs mailing list
[email protected]
http://lists.lysator.liu.se/mailman/listinfo/nettle-bugs