#include <string.h>
#include <inttypes.h>
+#include "../lib/bswap.h"
#include "sha256.h"
-#if __BYTE_ORDER == __LITTLE_ENDIAN
-static int __be32_to_cpu(uint32_t val)
-{
- uint32_t c1, c2, c3, c4;
-
- c1 = (val >> 24) & 0xff;
- c2 = (val >> 16) & 0xff;
- c3 = (val >> 8) & 0xff;
- c4 = val & 0xff;
-
- return c1 | c2 << 8 | c3 << 16 | c4 << 24;
-}
-#else
-#define __be32_to_cpu(x) (x)
-#endif
-
#define SHA256_DIGEST_SIZE 32
#define SHA256_HMAC_BLOCK_SIZE 64
memset(W, 0, 64 * sizeof(uint32_t));
}
-void sha256_init(struct sha256_ctx *sctx)
+void fio_sha256_init(struct fio_sha256_ctx *sctx)
{
sctx->state[0] = H0;
sctx->state[1] = H1;
sctx->state[5] = H5;
sctx->state[6] = H6;
sctx->state[7] = H7;
- sctx->count[0] = sctx->count[1] = 0;
+ sctx->count = 0;
}
-void sha256_update(struct sha256_ctx *sctx, const uint8_t *data,
- unsigned int len)
+void fio_sha256_update(struct fio_sha256_ctx *sctx, const uint8_t *data,
+ unsigned int len)
{
- unsigned int i, index, part_len;
+ unsigned int partial, done;
+ const uint8_t *src;
+
+ partial = sctx->count & 0x3f;
+ sctx->count += len;
+ done = 0;
+ src = data;
+
+ if ((partial + len) > 63) {
+ if (partial) {
+ done = -partial;
+ memcpy(sctx->buf + partial, data, done + 64);
+ src = sctx->buf;
+ }
+
+ do {
+ sha256_transform(sctx->state, src);
+ done += 64;
+ src = data + done;
+ } while (done + 63 < len);
+
+ partial = 0;
+ }
+ memcpy(sctx->buf + partial, src, len - done);
+}
- /* Compute number of bytes mod 128 */
- index = (unsigned int)((sctx->count[0] >> 3) & 0x3f);
+void fio_sha256_final(struct fio_sha256_ctx *sctx)
+{
+ uint64_t bits;
+ unsigned int index, pad_len;
+ int i;
+ static const uint8_t padding[64] = { 0x80, };
- /* Update number of bits */
- if ((sctx->count[0] += (len << 3)) < (len << 3)) {
- sctx->count[1]++;
- sctx->count[1] += (len >> 29);
- }
+ /* Save number of bits */
+ bits = (uint64_t) sctx->count << 3;
- part_len = 64 - index;
+ /* Pad out to 56 mod 64. */
+ index = sctx->count & 0x3f;
+ pad_len = (index < 56) ? (56 - index) : ((64+56) - index);
+ fio_sha256_update(sctx, padding, pad_len);
- /* Transform as many times as possible. */
- if (len >= part_len) {
- memcpy(&sctx->buf[index], data, part_len);
- sha256_transform(sctx->state, sctx->buf);
+ /* Append length (before padding) */
+ fio_sha256_update(sctx, (const uint8_t *)&bits, sizeof(bits));
- for (i = part_len; i + 63 < len; i += 64)
- sha256_transform(sctx->state, &data[i]);
- index = 0;
- } else {
- i = 0;
- }
-
- /* Buffer remaining input */
- memcpy(&sctx->buf[index], &data[i], len-i);
+ /* Store state in digest */
+ for (i = 0; i < 8; i++)
+ sctx->buf[i] = sctx->state[i];
}