* Optional switch "--with-openssl=<PATH>" to use OpenSSL's

implementations of MD5, SHA-1 and SHA-256.  The main benefit is that
  we get assembler-optimised implementations of MD5 and SHA-1 (though
  not SHA-256 (at least on x86), unfortunately).  OpenSSL's SHA-1
  implementation on Intel is twice as fast as ours.
This commit is contained in:
Eelco Dolstra 2006-02-13 19:52:43 +00:00
parent e8475bbd5b
commit d6f586d0ea
7 changed files with 59 additions and 40 deletions

View file

@ -143,6 +143,17 @@ AC_SUBST(aterm_lib)
AC_SUBST(aterm_include) AC_SUBST(aterm_include)
AC_SUBST(aterm_bin) AC_SUBST(aterm_bin)
AC_ARG_WITH(openssl, AC_HELP_STRING([--with-openssl=PATH],
[prefix of the OpenSSL library]),
openssl=$withval, openssl=)
AM_CONDITIONAL(HAVE_OPENSSL, test -n "$openssl")
if test -n "$openssl"; then
LDFLAGS="-L$openssl/lib -lcrypto $LDFLAGS"
CFLAGS="-I$openssl/include $CFLAGS"
CXXFLAGS="-I$openssl/include $CXXFLAGS"
AC_DEFINE(HAVE_OPENSSL, 1, [whether to use OpenSSL])
fi
AC_ARG_WITH(bzip2, AC_HELP_STRING([--with-bzip2=PATH], AC_ARG_WITH(bzip2, AC_HELP_STRING([--with-bzip2=PATH],
[prefix of bzip2]), [prefix of bzip2]),
bzip2=$withval, bzip2=) bzip2=$withval, bzip2=)

View file

@ -1,7 +1,11 @@
lib_LTLIBRARIES = libutil.la lib_LTLIBRARIES = libutil.la
libutil_la_SOURCES = util.cc util.hh hash.cc hash.hh \ libutil_la_SOURCES = util.cc util.hh hash.cc hash.hh \
archive.cc archive.hh aterm.cc aterm.hh \ archive.cc archive.hh aterm.cc aterm.hh
if !HAVE_OPENSSL
libutil_la_SOURCES += \
md5.c md5.h sha1.c sha1.h sha256.c sha256.h md32_common.h md5.c md5.h sha1.c sha1.h sha256.c sha256.h md32_common.h
endif
AM_CXXFLAGS = -Wall -I.. ${aterm_include} AM_CXXFLAGS = -Wall -I.. ${aterm_include}

View file

@ -1,10 +1,17 @@
#include "config.h"
#include <iostream> #include <iostream>
#ifdef HAVE_OPENSSL
#include <openssl/md5.h>
#include <openssl/sha.h>
#else
extern "C" { extern "C" {
#include "md5.h" #include "md5.h"
#include "sha1.h" #include "sha1.h"
#include "sha256.h" #include "sha256.h"
} }
#endif
#include "hash.hh" #include "hash.hh"
#include "archive.hh" #include "archive.hh"
@ -199,16 +206,16 @@ bool isHash(const string & s)
union Ctx union Ctx
{ {
md5_ctx md5; MD5_CTX md5;
sha_ctx sha1; SHA_CTX sha1;
SHA256_CTX sha256; SHA256_CTX sha256;
}; };
static void start(HashType ht, Ctx & ctx) static void start(HashType ht, Ctx & ctx)
{ {
if (ht == htMD5) md5_init_ctx(&ctx.md5); if (ht == htMD5) MD5_Init(&ctx.md5);
else if (ht == htSHA1) sha_init(&ctx.sha1); else if (ht == htSHA1) SHA1_Init(&ctx.sha1);
else if (ht == htSHA256) SHA256_Init(&ctx.sha256); else if (ht == htSHA256) SHA256_Init(&ctx.sha256);
} }
@ -216,19 +223,16 @@ static void start(HashType ht, Ctx & ctx)
static void update(HashType ht, Ctx & ctx, static void update(HashType ht, Ctx & ctx,
const unsigned char * bytes, unsigned int len) const unsigned char * bytes, unsigned int len)
{ {
if (ht == htMD5) md5_process_bytes(bytes, len, &ctx.md5); if (ht == htMD5) MD5_Update(&ctx.md5, bytes, len);
else if (ht == htSHA1) sha_update(&ctx.sha1, bytes, len); else if (ht == htSHA1) SHA1_Update(&ctx.sha1, bytes, len);
else if (ht == htSHA256) SHA256_Update(&ctx.sha256, bytes, len); else if (ht == htSHA256) SHA256_Update(&ctx.sha256, bytes, len);
} }
static void finish(HashType ht, Ctx & ctx, unsigned char * hash) static void finish(HashType ht, Ctx & ctx, unsigned char * hash)
{ {
if (ht == htMD5) md5_finish_ctx(&ctx.md5, hash); if (ht == htMD5) MD5_Final(hash, &ctx.md5);
else if (ht == htSHA1) { else if (ht == htSHA1) SHA1_Final(hash, &ctx.sha1);
sha_final(&ctx.sha1);
sha_digest(&ctx.sha1, hash);
}
else if (ht == htSHA256) SHA256_Final(hash, &ctx.sha256); else if (ht == htSHA256) SHA256_Final(hash, &ctx.sha256);
} }

View file

@ -56,8 +56,8 @@ static const unsigned char fillbuf[64] = { 0x80, 0 /* , 0, 0, ... */ };
/* Initialize structure containing state of computation. /* Initialize structure containing state of computation.
(RFC 1321, 3.3: Step 3) */ (RFC 1321, 3.3: Step 3) */
void void
md5_init_ctx (ctx) MD5_Init (ctx)
struct md5_ctx *ctx; struct MD5_CTX *ctx;
{ {
ctx->A = 0x67452301; ctx->A = 0x67452301;
ctx->B = 0xefcdab89; ctx->B = 0xefcdab89;
@ -75,7 +75,7 @@ md5_init_ctx (ctx)
aligned for a 32 bits value. */ aligned for a 32 bits value. */
void * void *
md5_read_ctx (ctx, resbuf) md5_read_ctx (ctx, resbuf)
const struct md5_ctx *ctx; const struct MD5_CTX *ctx;
void *resbuf; void *resbuf;
{ {
((md5_uint32 *) resbuf)[0] = SWAP (ctx->A); ((md5_uint32 *) resbuf)[0] = SWAP (ctx->A);
@ -92,9 +92,9 @@ md5_read_ctx (ctx, resbuf)
IMPORTANT: On some systems it is required that RESBUF is correctly IMPORTANT: On some systems it is required that RESBUF is correctly
aligned for a 32 bits value. */ aligned for a 32 bits value. */
void * void *
md5_finish_ctx (ctx, resbuf) MD5_Final (resbuf, ctx)
struct md5_ctx *ctx;
void *resbuf; void *resbuf;
struct MD5_CTX *ctx;
{ {
/* Take yet unprocessed bytes into account. */ /* Take yet unprocessed bytes into account. */
md5_uint32 bytes = ctx->buflen; md5_uint32 bytes = ctx->buflen;
@ -120,10 +120,10 @@ md5_finish_ctx (ctx, resbuf)
} }
void void
md5_process_bytes (buffer, len, ctx) MD5_Update (ctx, buffer, len)
struct MD5_CTX *ctx;
const void *buffer; const void *buffer;
size_t len; size_t len;
struct md5_ctx *ctx;
{ {
/* When we already have some bits in our internal buffer concatenate /* When we already have some bits in our internal buffer concatenate
both inputs first. */ both inputs first. */
@ -210,7 +210,7 @@ void
md5_process_block (buffer, len, ctx) md5_process_block (buffer, len, ctx)
const void *buffer; const void *buffer;
size_t len; size_t len;
struct md5_ctx *ctx; struct MD5_CTX *ctx;
{ {
md5_uint32 correct_words[16]; md5_uint32 correct_words[16];
const md5_uint32 *words = buffer; const md5_uint32 *words = buffer;

View file

@ -26,7 +26,7 @@ typedef uint32_t md5_uint32;
typedef uintptr_t md5_uintptr; typedef uintptr_t md5_uintptr;
/* Structure to save state of computation between the single steps. */ /* Structure to save state of computation between the single steps. */
struct md5_ctx struct MD5_CTX
{ {
md5_uint32 A; md5_uint32 A;
md5_uint32 B; md5_uint32 B;
@ -45,21 +45,20 @@ struct md5_ctx
/* Initialize structure containing state of computation. /* Initialize structure containing state of computation.
(RFC 1321, 3.3: Step 3) */ (RFC 1321, 3.3: Step 3) */
extern void md5_init_ctx __P ((struct md5_ctx *ctx)); extern void MD5_Init __P ((struct MD5_CTX *ctx));
/* Starting with the result of former calls of this function (or the /* Starting with the result of former calls of this function (or the
initialization function update the context for the next LEN bytes initialization function update the context for the next LEN bytes
starting at BUFFER. starting at BUFFER.
It is necessary that LEN is a multiple of 64!!! */ It is necessary that LEN is a multiple of 64!!! */
extern void md5_process_block __P ((const void *buffer, size_t len, extern void md5_process_block __P ((const void *buffer, size_t len,
struct md5_ctx *ctx)); struct MD5_CTX *ctx));
/* Starting with the result of former calls of this function (or the /* Starting with the result of former calls of this function (or the
initialization function update the context for the next LEN bytes initialization function update the context for the next LEN bytes
starting at BUFFER. starting at BUFFER.
It is NOT required that LEN is a multiple of 64. */ It is NOT required that LEN is a multiple of 64. */
extern void md5_process_bytes __P ((const void *buffer, size_t len, extern void MD5_Update __P ((struct MD5_CTX *ctx, const void *buffer, size_t len));
struct md5_ctx *ctx));
/* Process the remaining bytes in the buffer and put result from CTX /* Process the remaining bytes in the buffer and put result from CTX
in first 16 bytes following RESBUF. The result is always in little in first 16 bytes following RESBUF. The result is always in little
@ -68,7 +67,7 @@ extern void md5_process_bytes __P ((const void *buffer, size_t len,
IMPORTANT: On some systems it is required that RESBUF is correctly IMPORTANT: On some systems it is required that RESBUF is correctly
aligned for a 32 bits value. */ aligned for a 32 bits value. */
extern void *md5_finish_ctx __P ((struct md5_ctx *ctx, void *resbuf)); extern void *MD5_Final __P ((void *resbuf, struct MD5_CTX *ctx));
/* Put result from CTX in first 16 bytes following RESBUF. The result is /* Put result from CTX in first 16 bytes following RESBUF. The result is
@ -77,7 +76,7 @@ extern void *md5_finish_ctx __P ((struct md5_ctx *ctx, void *resbuf));
IMPORTANT: On some systems it is required that RESBUF is correctly IMPORTANT: On some systems it is required that RESBUF is correctly
aligned for a 32 bits value. */ aligned for a 32 bits value. */
extern void *md5_read_ctx __P ((const struct md5_ctx *ctx, void *resbuf)); extern void *md5_read_ctx __P ((const struct MD5_CTX *ctx, void *resbuf));
#endif /* md5.h */ #endif /* md5.h */

View file

@ -37,7 +37,7 @@ effort (for example the reengineering of a great many Capstone chips).
#include <string.h> #include <string.h>
void sha_copy(struct sha_ctx *dest, struct sha_ctx *src) void sha_copy(struct SHA_CTX *dest, struct SHA_CTX *src)
{ {
unsigned int i; unsigned int i;
@ -118,7 +118,7 @@ void sha_copy(struct sha_ctx *dest, struct sha_ctx *src)
/* Initialize the SHA values */ /* Initialize the SHA values */
void sha_init(struct sha_ctx *ctx) void SHA1_Init(struct SHA_CTX *ctx)
{ {
/* Set the h-vars to their initial values */ /* Set the h-vars to their initial values */
ctx->digest[ 0 ] = h0init; ctx->digest[ 0 ] = h0init;
@ -141,7 +141,7 @@ void sha_init(struct sha_ctx *ctx)
Note that this function destroys the data area */ Note that this function destroys the data area */
static void sha_transform(struct sha_ctx *ctx, uint32_t *data ) static void sha_transform(struct SHA_CTX *ctx, uint32_t *data )
{ {
uint32_t A, B, C, D, E; /* Local vars */ uint32_t A, B, C, D, E; /* Local vars */
@ -267,7 +267,7 @@ uint32_t STRING2INT(unsigned char *s)
} }
#endif #endif
static void sha_block(struct sha_ctx *ctx, const unsigned char *block) static void sha_block(struct SHA_CTX *ctx, const unsigned char *block)
{ {
uint32_t data[SHA_DATALEN]; uint32_t data[SHA_DATALEN];
unsigned int i; unsigned int i;
@ -283,7 +283,7 @@ static void sha_block(struct sha_ctx *ctx, const unsigned char *block)
sha_transform(ctx, data); sha_transform(ctx, data);
} }
void sha_update(struct sha_ctx *ctx, const unsigned char *buffer, uint32_t len) void SHA1_Update(struct SHA_CTX *ctx, const unsigned char *buffer, uint32_t len)
{ {
if (ctx->index) if (ctx->index)
{ /* Try to fill partial block */ { /* Try to fill partial block */
@ -316,7 +316,7 @@ void sha_update(struct sha_ctx *ctx, const unsigned char *buffer, uint32_t len)
/* Final wrapup - pad to SHA_DATASIZE-byte boundary with the bit pattern /* Final wrapup - pad to SHA_DATASIZE-byte boundary with the bit pattern
1 0* (64-bit count of bits processed, MSB-first) */ 1 0* (64-bit count of bits processed, MSB-first) */
void sha_final(struct sha_ctx *ctx) void SHA1_Final(unsigned char *s, struct SHA_CTX *ctx)
{ {
uint32_t data[SHA_DATALEN]; uint32_t data[SHA_DATALEN];
unsigned int i; unsigned int i;
@ -352,9 +352,10 @@ void sha_final(struct sha_ctx *ctx)
data[SHA_DATALEN-2] = (ctx->count_h << 9) | (ctx->count_l >> 23); data[SHA_DATALEN-2] = (ctx->count_h << 9) | (ctx->count_l >> 23);
data[SHA_DATALEN-1] = (ctx->count_l << 9) | (ctx->index << 3); data[SHA_DATALEN-1] = (ctx->count_l << 9) | (ctx->index << 3);
sha_transform(ctx, data); sha_transform(ctx, data);
sha_digest(ctx, s);
} }
void sha_digest(struct sha_ctx *ctx, unsigned char *s) void sha_digest(struct SHA_CTX *ctx, unsigned char *s)
{ {
unsigned int i; unsigned int i;

View file

@ -11,18 +11,18 @@
#define SHA_DIGESTLEN 5 #define SHA_DIGESTLEN 5
/* The structure for storing SHA info */ /* The structure for storing SHA info */
struct sha_ctx { struct SHA_CTX {
uint32_t digest[SHA_DIGESTLEN]; /* Message digest */ uint32_t digest[SHA_DIGESTLEN]; /* Message digest */
uint32_t count_l, count_h; /* 64-bit block count */ uint32_t count_l, count_h; /* 64-bit block count */
uint8_t block[SHA_DATASIZE]; /* SHA data buffer */ uint8_t block[SHA_DATASIZE]; /* SHA data buffer */
unsigned int index; /* index into buffer */ unsigned int index; /* index into buffer */
}; };
void sha_init(struct sha_ctx *ctx); void SHA1_Init(struct SHA_CTX *ctx);
void sha_update(struct sha_ctx *ctx, const unsigned char *buffer, uint32_t len); void SHA1_Update(struct SHA_CTX *ctx, const unsigned char *buffer, uint32_t len);
void sha_final(struct sha_ctx *ctx); void SHA1_Final(unsigned char *s, struct SHA_CTX *ctx);
void sha_digest(struct sha_ctx *ctx, unsigned char *s); void sha_digest(struct SHA_CTX *ctx, unsigned char *s);
void sha_copy(struct sha_ctx *dest, struct sha_ctx *src); void sha_copy(struct SHA_CTX *dest, struct SHA_CTX *src);
#endif /* !_SHA_H */ #endif /* !_SHA_H */