From 273abcbf664adc92ef3bc1d9752a2b571623ad52 Mon Sep 17 00:00:00 2001 From: Denys Vlasenko Date: Sat, 16 Oct 2010 22:43:34 +0200 Subject: [PATCH] shaN: small code shrink function old new delta sha512_hash 134 128 -6 sha1_hash 114 106 -8 Signed-off-by: Denys Vlasenko --- libbb/md5.c | 61 +++++++++++++++++--------- libbb/sha1.c | 115 ++++++++++++++++++++++++++++++++++++------------- testsuite/md5sum.tests | 14 ++---- 3 files changed, 129 insertions(+), 61 deletions(-) diff --git a/libbb/md5.c b/libbb/md5.c index f192d0e..cf3825a 100644 --- a/libbb/md5.c +++ b/libbb/md5.c @@ -354,8 +354,8 @@ static void md5_hash_block(md5_ctx_t *ctx) ctx->D = D; } -/* The size of filled part of ctx->buffer: */ -#define BUFLEN(ctx) (((unsigned)ctx->total) & 63) +/* The first unused position in ctx->buffer: */ +#define BUFPOS(ctx) (((unsigned)ctx->total) & 63) /* Feed data through a temporary buffer to call md5_hash_aligned_block() * with chunks of data that are 4-byte aligned and a multiple of 64 bytes. @@ -363,31 +363,52 @@ static void md5_hash_block(md5_ctx_t *ctx) * bytes worth to pass on. Call md5_end() to flush this buffer. */ void FAST_FUNC md5_hash(md5_ctx_t *ctx, const void *buffer, size_t len) { - const char *buf = buffer; - unsigned buflen = BUFLEN(ctx); +#if 1 + /* Tiny bit smaller code */ + unsigned bufpos = BUFPOS(ctx); /* RFC 1321 specifies the possible length of the file up to 2^64 bits. * Here we only track the number of bytes. */ ctx->total += len; - /* Process all input. */ while (1) { - unsigned i = 64 - buflen; - if (i > len) - i = len; + unsigned remaining = 64 - bufpos; + if (remaining > len) + remaining = len; /* Copy data into aligned buffer. */ - memcpy(ctx->buffer + buflen, buf, i); - len -= i; - buf += i; - buflen += i; - /* clever way to do "if (buflen != 64) break; ... ; buflen = 0;" */ - buflen -= 64; - if (buflen != 0) + memcpy(ctx->buffer + bufpos, buffer, remaining); + len -= remaining; + buffer = (const char *)buffer + remaining; + bufpos += remaining; + /* clever way to do "if (bufpos != 64) break; ... ; bufpos = 0;" */ + bufpos -= 64; + if (bufpos != 0) break; /* Buffer is filled up, process it. */ md5_hash_block(ctx); - /*buflen = 0; - already is */ + /*bufpos = 0; - already is */ } +#else + unsigned bufpos = BUFPOS(ctx); + unsigned add = 64 - bufpos; + + /* RFC 1321 specifies the possible length of the file up to 2^64 bits. + * Here we only track the number of bytes. */ + ctx->total += len; + + /* Hash whole blocks */ + while (len >= add) { + memcpy(ctx->buffer + bufpos, buffer, add); + buffer = (const char *)buffer + add; + len -= add; + add = 64; + bufpos = 0; + md5_hash_block(ctx); + } + + /* Save last, partial blosk */ + memcpy(ctx->buffer + bufpos, buffer, len); +#endif } /* Process the remaining bytes in the buffer and put result from CTX @@ -399,13 +420,13 @@ void FAST_FUNC md5_end(md5_ctx_t *ctx, void *resbuf) { uint64_t total; unsigned i; - unsigned buflen = BUFLEN(ctx); + unsigned bufpos = BUFPOS(ctx); /* Pad data to block size. */ - ctx->buffer[buflen++] = 0x80; - memset(ctx->buffer + buflen, 0, 64 - buflen); + ctx->buffer[bufpos++] = 0x80; + memset(ctx->buffer + bufpos, 0, 64 - bufpos); - if (buflen > 56) { + if (bufpos > 56) { md5_hash_block(ctx); memset(ctx->buffer, 0, 64); } diff --git a/libbb/sha1.c b/libbb/sha1.c index fac23c0..8c67d07 100644 --- a/libbb/sha1.c +++ b/libbb/sha1.c @@ -363,62 +363,117 @@ void FAST_FUNC sha512_begin(sha512_ctx_t *ctx) /* Used also for sha256 */ void FAST_FUNC sha1_hash(sha1_ctx_t *ctx, const void *buffer, size_t len) { - unsigned in_buf = ctx->total64 & 63; - unsigned add = 64 - in_buf; +#if 0 + unsigned bufpos = ctx->total64 & 63; + unsigned add = 64 - bufpos; ctx->total64 += len; - while (len >= add) { /* transfer whole blocks while possible */ - memcpy(ctx->wbuffer + in_buf, buffer, add); + /* Hash whole blocks */ + while (len >= add) { + memcpy(ctx->wbuffer + bufpos, buffer, add); buffer = (const char *)buffer + add; len -= add; add = 64; - in_buf = 0; + bufpos = 0; ctx->process_block(ctx); } - memcpy(ctx->wbuffer + in_buf, buffer, len); + /* Save last, partial blosk */ + memcpy(ctx->wbuffer + bufpos, buffer, len); +#else + /* Tiny bit smaller code */ + unsigned bufpos = ctx->total64 & 63; + + ctx->total64 += len; + + while (1) { + unsigned remaining = 64 - bufpos; + if (remaining > len) + remaining = len; + /* Copy data into aligned buffer */ + memcpy(ctx->wbuffer + bufpos, buffer, remaining); + len -= remaining; + buffer = (const char *)buffer + remaining; + bufpos += remaining; + /* clever way to do "if (bufpos != 64) break; ... ; bufpos = 0;" */ + bufpos -= 64; + if (bufpos != 0) + break; + /* Buffer is filled up, process it */ + ctx->process_block(ctx); + /*bufpos = 0; - already is */ + } +#endif } void FAST_FUNC sha512_hash(sha512_ctx_t *ctx, const void *buffer, size_t len) { - unsigned in_buf = ctx->total64[0] & 127; - unsigned add = 128 - in_buf; +#if 0 + unsigned bufpos = ctx->total64[0] & 127; + unsigned add = 128 - bufpos; - /* First increment the byte count. FIPS 180-2 specifies the possible - length of the file up to 2^128 _bits_. - We compute the number of _bytes_ and convert to bits later. */ ctx->total64[0] += len; if (ctx->total64[0] < len) ctx->total64[1]++; - while (len >= add) { /* transfer whole blocks while possible */ - memcpy(ctx->wbuffer + in_buf, buffer, add); + /* Hash whole blocks */ + while (len >= add) { + memcpy(ctx->wbuffer + bufpos, buffer, add); buffer = (const char *)buffer + add; len -= add; add = 128; - in_buf = 0; + bufpos = 0; sha512_process_block128(ctx); } - memcpy(ctx->wbuffer + in_buf, buffer, len); + /* Save last, partial blosk */ + memcpy(ctx->wbuffer + bufpos, buffer, len); +#else + unsigned bufpos = ctx->total64[0] & 127; + + /* First increment the byte count. FIPS 180-2 specifies the possible + length of the file up to 2^128 _bits_. + We compute the number of _bytes_ and convert to bits later. */ + ctx->total64[0] += len; + if (ctx->total64[0] < len) + ctx->total64[1]++; + + while (1) { + unsigned remaining = 128 - bufpos; + if (remaining > len) + remaining = len; + /* Copy data into aligned buffer. */ + memcpy(ctx->wbuffer + bufpos, buffer, remaining); + len -= remaining; + buffer = (const char *)buffer + remaining; + bufpos += remaining; + /* clever way to do "if (bufpos != 128) break; ... ; bufpos = 0;" */ + bufpos -= 128; + if (bufpos != 0) + break; + /* Buffer is filled up, process it. */ + sha512_process_block128(ctx); + /*bufpos = 0; - already is */ + } +#endif } /* Used also for sha256 */ void FAST_FUNC sha1_end(sha1_ctx_t *ctx, void *resbuf) { - unsigned pad, in_buf; + unsigned pad, bufpos; - in_buf = ctx->total64 & 63; + bufpos = ctx->total64 & 63; /* Pad the buffer to the next 64-byte boundary with 0x80,0,0,0... */ - ctx->wbuffer[in_buf++] = 0x80; + ctx->wbuffer[bufpos++] = 0x80; /* This loop iterates either once or twice, no more, no less */ while (1) { - pad = 64 - in_buf; - memset(ctx->wbuffer + in_buf, 0, pad); - in_buf = 0; + pad = 64 - bufpos; + memset(ctx->wbuffer + bufpos, 0, pad); + bufpos = 0; /* Do we have enough space for the length count? */ if (pad >= 8) { /* Store the 64-bit counter of bits in the buffer in BE format */ @@ -432,30 +487,30 @@ void FAST_FUNC sha1_end(sha1_ctx_t *ctx, void *resbuf) break; } - in_buf = (ctx->process_block == sha1_process_block64) ? 5 : 8; + bufpos = (ctx->process_block == sha1_process_block64) ? 5 : 8; /* This way we do not impose alignment constraints on resbuf: */ if (BB_LITTLE_ENDIAN) { unsigned i; - for (i = 0; i < in_buf; ++i) + for (i = 0; i < bufpos; ++i) ctx->hash[i] = htonl(ctx->hash[i]); } - memcpy(resbuf, ctx->hash, sizeof(ctx->hash[0]) * in_buf); + memcpy(resbuf, ctx->hash, sizeof(ctx->hash[0]) * bufpos); } void FAST_FUNC sha512_end(sha512_ctx_t *ctx, void *resbuf) { - unsigned pad, in_buf; + unsigned pad, bufpos; - in_buf = ctx->total64[0] & 127; + bufpos = ctx->total64[0] & 127; /* Pad the buffer to the next 128-byte boundary with 0x80,0,0,0... * (FIPS 180-2:5.1.2) */ - ctx->wbuffer[in_buf++] = 0x80; + ctx->wbuffer[bufpos++] = 0x80; while (1) { - pad = 128 - in_buf; - memset(ctx->wbuffer + in_buf, 0, pad); - in_buf = 0; + pad = 128 - bufpos; + memset(ctx->wbuffer + bufpos, 0, pad); + bufpos = 0; if (pad >= 16) { /* Store the 128-bit counter of bits in the buffer in BE format */ uint64_t t; diff --git a/testsuite/md5sum.tests b/testsuite/md5sum.tests index 5bbdb3b..35ec67c 100755 --- a/testsuite/md5sum.tests +++ b/testsuite/md5sum.tests @@ -18,25 +18,17 @@ fi sum="$1" expected="$2" -mkdir testdir 2>/dev/null - -result=`( -cd testdir || { echo "cannot cd testdir!" >&2; exit 1; } - text="The quick brown fox jumps over the lazy dog" +text=`yes "$text" | head -c 9999` +result=`( n=0 while test $n -le 999; do - yes "$text" | head -c $n | "$sum" + echo "$text" | head -c $n | "$sum" : $((n++)) done | "$sum" - )` -rm -rf testdir - -FAILCOUNT=0 - if test x"$result" = x"$expected -"; then echo "PASS: $sum" exit 0 -- 2.7.4