Require OpenSSL
This commit is contained in:
		
							parent
							
								
									85aeedb9bc
								
							
						
					
					
						commit
						a6ca68a70c
					
				
					 11 changed files with 3 additions and 1759 deletions
				
			
		|  | @ -3,7 +3,6 @@ CC = @CC@ | ||||||
| CFLAGS = @CFLAGS@ | CFLAGS = @CFLAGS@ | ||||||
| CXX = @CXX@ | CXX = @CXX@ | ||||||
| CXXFLAGS = @CXXFLAGS@ | CXXFLAGS = @CXXFLAGS@ | ||||||
| HAVE_OPENSSL = @HAVE_OPENSSL@ |  | ||||||
| HAVE_SODIUM = @HAVE_SODIUM@ | HAVE_SODIUM = @HAVE_SODIUM@ | ||||||
| OPENSSL_LIBS = @OPENSSL_LIBS@ | OPENSSL_LIBS = @OPENSSL_LIBS@ | ||||||
| PACKAGE_NAME = @PACKAGE_NAME@ | PACKAGE_NAME = @PACKAGE_NAME@ | ||||||
|  |  | ||||||
|  | @ -183,16 +183,12 @@ AC_ARG_WITH(store-dir, AC_HELP_STRING([--with-store-dir=PATH], | ||||||
| AC_SUBST(storedir) | AC_SUBST(storedir) | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| # Look for OpenSSL, an optional dependency. | # Look for OpenSSL, a required dependency. | ||||||
| AC_PATH_PROG(openssl, openssl, openssl) # if not found, call openssl in $PATH | AC_PATH_PROG(openssl, openssl, openssl) # if not found, call openssl in $PATH | ||||||
| AC_SUBST(openssl) | AC_SUBST(openssl) | ||||||
| AC_DEFINE_UNQUOTED(OPENSSL_PATH, ["$openssl"], [Path of the OpenSSL binary]) | AC_DEFINE_UNQUOTED(OPENSSL_PATH, ["$openssl"], [Path of the OpenSSL binary]) | ||||||
| 
 | 
 | ||||||
| PKG_CHECK_MODULES([OPENSSL], [libcrypto], | PKG_CHECK_MODULES([OPENSSL], [libcrypto], [CXXFLAGS="$OPENSSL_CFLAGS $CXXFLAGS"]) | ||||||
|   [AC_DEFINE([HAVE_OPENSSL], [1], [Whether to use OpenSSL.]) |  | ||||||
|    CXXFLAGS="$OPENSSL_CFLAGS $CXXFLAGS" |  | ||||||
|    have_openssl=1], [have_openssl=]) |  | ||||||
| AC_SUBST(HAVE_OPENSSL, [$have_openssl]) |  | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| # Look for libbz2, a required dependency. | # Look for libbz2, a required dependency. | ||||||
|  |  | ||||||
|  | @ -3,16 +3,8 @@ | ||||||
| #include <iostream> | #include <iostream> | ||||||
| #include <cstring> | #include <cstring> | ||||||
| 
 | 
 | ||||||
| #ifdef HAVE_OPENSSL |  | ||||||
| #include <openssl/md5.h> | #include <openssl/md5.h> | ||||||
| #include <openssl/sha.h> | #include <openssl/sha.h> | ||||||
| #else |  | ||||||
| extern "C" { |  | ||||||
| #include "md5.h" |  | ||||||
| #include "sha1.h" |  | ||||||
| #include "sha256.h" |  | ||||||
| } |  | ||||||
| #endif |  | ||||||
| 
 | 
 | ||||||
| #include "hash.hh" | #include "hash.hh" | ||||||
| #include "archive.hh" | #include "archive.hh" | ||||||
|  |  | ||||||
|  | @ -6,12 +6,6 @@ libutil_DIR := $(d) | ||||||
| 
 | 
 | ||||||
| libutil_SOURCES := $(wildcard $(d)/*.cc) | libutil_SOURCES := $(wildcard $(d)/*.cc) | ||||||
| 
 | 
 | ||||||
| libutil_LDFLAGS = -llzma | libutil_LDFLAGS = -llzma $(OPENSSL_LIBS) | ||||||
| 
 |  | ||||||
| ifeq ($(HAVE_OPENSSL), 1) |  | ||||||
|   libutil_LDFLAGS += $(OPENSSL_LIBS) |  | ||||||
| else |  | ||||||
|   libutil_SOURCES += $(d)/md5.c $(d)/sha1.c $(d)/sha256.c |  | ||||||
| endif |  | ||||||
| 
 | 
 | ||||||
| libutil_LIBS = libformat | libutil_LIBS = libformat | ||||||
|  |  | ||||||
|  | @ -1,620 +0,0 @@ | ||||||
| /* crypto/md32_common.h */ |  | ||||||
| /* ====================================================================
 |  | ||||||
|  * Copyright (c) 1999-2002 The OpenSSL Project.  All rights reserved. |  | ||||||
|  * |  | ||||||
|  * Redistribution and use in source and binary forms, with or without |  | ||||||
|  * modification, are permitted provided that the following conditions |  | ||||||
|  * are met: |  | ||||||
|  * |  | ||||||
|  * 1. Redistributions of source code must retain the above copyright |  | ||||||
|  *    notice, this list of conditions and the following disclaimer.  |  | ||||||
|  * |  | ||||||
|  * 2. Redistributions in binary form must reproduce the above copyright |  | ||||||
|  *    notice, this list of conditions and the following disclaimer in |  | ||||||
|  *    the documentation and/or other materials provided with the |  | ||||||
|  *    distribution. |  | ||||||
|  * |  | ||||||
|  * 3. All advertising materials mentioning features or use of this |  | ||||||
|  *    software must display the following acknowledgment: |  | ||||||
|  *    "This product includes software developed by the OpenSSL Project |  | ||||||
|  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 |  | ||||||
|  * |  | ||||||
|  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to |  | ||||||
|  *    endorse or promote products derived from this software without |  | ||||||
|  *    prior written permission. For written permission, please contact |  | ||||||
|  *    licensing@OpenSSL.org. |  | ||||||
|  * |  | ||||||
|  * 5. Products derived from this software may not be called "OpenSSL" |  | ||||||
|  *    nor may "OpenSSL" appear in their names without prior written |  | ||||||
|  *    permission of the OpenSSL Project. |  | ||||||
|  * |  | ||||||
|  * 6. Redistributions of any form whatsoever must retain the following |  | ||||||
|  *    acknowledgment: |  | ||||||
|  *    "This product includes software developed by the OpenSSL Project |  | ||||||
|  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 |  | ||||||
|  * |  | ||||||
|  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY |  | ||||||
|  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |  | ||||||
|  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR |  | ||||||
|  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR |  | ||||||
|  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |  | ||||||
|  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT |  | ||||||
|  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |  | ||||||
|  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) |  | ||||||
|  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, |  | ||||||
|  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |  | ||||||
|  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED |  | ||||||
|  * OF THE POSSIBILITY OF SUCH DAMAGE. |  | ||||||
|  * ==================================================================== |  | ||||||
|  * |  | ||||||
|  * This product includes cryptographic software written by Eric Young |  | ||||||
|  * (eay@cryptsoft.com).  This product includes software written by Tim |  | ||||||
|  * Hudson (tjh@cryptsoft.com). |  | ||||||
|  * |  | ||||||
|  */ |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * This is a generic 32 bit "collector" for message digest algorithms. |  | ||||||
|  * Whenever needed it collects input character stream into chunks of |  | ||||||
|  * 32 bit values and invokes a block function that performs actual hash |  | ||||||
|  * calculations. |  | ||||||
|  * |  | ||||||
|  * Porting guide. |  | ||||||
|  * |  | ||||||
|  * Obligatory macros: |  | ||||||
|  * |  | ||||||
|  * DATA_ORDER_IS_BIG_ENDIAN or DATA_ORDER_IS_LITTLE_ENDIAN |  | ||||||
|  *	this macro defines byte order of input stream. |  | ||||||
|  * HASH_CBLOCK |  | ||||||
|  *	size of a unit chunk HASH_BLOCK operates on. |  | ||||||
|  * HASH_LONG |  | ||||||
|  *	has to be at lest 32 bit wide, if it's wider, then |  | ||||||
|  *	HASH_LONG_LOG2 *has to* be defined along |  | ||||||
|  * HASH_CTX |  | ||||||
|  *	context structure that at least contains following |  | ||||||
|  *	members: |  | ||||||
|  *		typedef struct { |  | ||||||
|  *			... |  | ||||||
|  *			HASH_LONG	Nl,Nh; |  | ||||||
|  *			HASH_LONG	data[HASH_LBLOCK]; |  | ||||||
|  *			unsigned int	num; |  | ||||||
|  *			... |  | ||||||
|  *			} HASH_CTX; |  | ||||||
|  * HASH_UPDATE |  | ||||||
|  *	name of "Update" function, implemented here. |  | ||||||
|  * HASH_TRANSFORM |  | ||||||
|  *	name of "Transform" function, implemented here. |  | ||||||
|  * HASH_FINAL |  | ||||||
|  *	name of "Final" function, implemented here. |  | ||||||
|  * HASH_BLOCK_HOST_ORDER |  | ||||||
|  *	name of "block" function treating *aligned* input message |  | ||||||
|  *	in host byte order, implemented externally. |  | ||||||
|  * HASH_BLOCK_DATA_ORDER |  | ||||||
|  *	name of "block" function treating *unaligned* input message |  | ||||||
|  *	in original (data) byte order, implemented externally (it |  | ||||||
|  *	actually is optional if data and host are of the same |  | ||||||
|  *	"endianess"). |  | ||||||
|  * HASH_MAKE_STRING |  | ||||||
|  *	macro convering context variables to an ASCII hash string. |  | ||||||
|  * |  | ||||||
|  * Optional macros: |  | ||||||
|  * |  | ||||||
|  * B_ENDIAN or L_ENDIAN |  | ||||||
|  *	defines host byte-order. |  | ||||||
|  * HASH_LONG_LOG2 |  | ||||||
|  *	defaults to 2 if not states otherwise. |  | ||||||
|  * HASH_LBLOCK |  | ||||||
|  *	assumed to be HASH_CBLOCK/4 if not stated otherwise. |  | ||||||
|  * HASH_BLOCK_DATA_ORDER_ALIGNED |  | ||||||
|  *	alternative "block" function capable of treating |  | ||||||
|  *	aligned input message in original (data) order, |  | ||||||
|  *	implemented externally. |  | ||||||
|  * |  | ||||||
|  * MD5 example: |  | ||||||
|  * |  | ||||||
|  *	#define DATA_ORDER_IS_LITTLE_ENDIAN |  | ||||||
|  * |  | ||||||
|  *	#define HASH_LONG		MD5_LONG |  | ||||||
|  *	#define HASH_LONG_LOG2		MD5_LONG_LOG2 |  | ||||||
|  *	#define HASH_CTX		MD5_CTX |  | ||||||
|  *	#define HASH_CBLOCK		MD5_CBLOCK |  | ||||||
|  *	#define HASH_LBLOCK		MD5_LBLOCK |  | ||||||
|  *	#define HASH_UPDATE		MD5_Update |  | ||||||
|  *	#define HASH_TRANSFORM		MD5_Transform |  | ||||||
|  *	#define HASH_FINAL		MD5_Final |  | ||||||
|  *	#define HASH_BLOCK_HOST_ORDER	md5_block_host_order |  | ||||||
|  *	#define HASH_BLOCK_DATA_ORDER	md5_block_data_order |  | ||||||
|  * |  | ||||||
|  *					<appro@fy.chalmers.se> |  | ||||||
|  */ |  | ||||||
| 
 |  | ||||||
| #if !defined(DATA_ORDER_IS_BIG_ENDIAN) && !defined(DATA_ORDER_IS_LITTLE_ENDIAN) |  | ||||||
| #error "DATA_ORDER must be defined!" |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HASH_CBLOCK |  | ||||||
| #error "HASH_CBLOCK must be defined!" |  | ||||||
| #endif |  | ||||||
| #ifndef HASH_LONG |  | ||||||
| #error "HASH_LONG must be defined!" |  | ||||||
| #endif |  | ||||||
| #ifndef HASH_CTX |  | ||||||
| #error "HASH_CTX must be defined!" |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HASH_UPDATE |  | ||||||
| #error "HASH_UPDATE must be defined!" |  | ||||||
| #endif |  | ||||||
| #ifndef HASH_TRANSFORM |  | ||||||
| #error "HASH_TRANSFORM must be defined!" |  | ||||||
| #endif |  | ||||||
| #ifndef HASH_FINAL |  | ||||||
| #error "HASH_FINAL must be defined!" |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HASH_BLOCK_HOST_ORDER |  | ||||||
| #error "HASH_BLOCK_HOST_ORDER must be defined!" |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #if 0 |  | ||||||
| /*
 |  | ||||||
|  * Moved below as it's required only if HASH_BLOCK_DATA_ORDER_ALIGNED |  | ||||||
|  * isn't defined. |  | ||||||
|  */ |  | ||||||
| #ifndef HASH_BLOCK_DATA_ORDER |  | ||||||
| #error "HASH_BLOCK_DATA_ORDER must be defined!" |  | ||||||
| #endif |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HASH_LBLOCK |  | ||||||
| #define HASH_LBLOCK	(HASH_CBLOCK/4) |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HASH_LONG_LOG2 |  | ||||||
| #define HASH_LONG_LOG2	2 |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * Engage compiler specific rotate intrinsic function if available. |  | ||||||
|  */ |  | ||||||
| #undef ROTATE |  | ||||||
| #ifndef PEDANTIC |  | ||||||
| # if defined(_MSC_VER) || defined(__ICC) |  | ||||||
| #  define ROTATE(a,n)	_lrotl(a,n) |  | ||||||
| # elif defined(__MWERKS__) |  | ||||||
| #  if defined(__POWERPC__) |  | ||||||
| #   define ROTATE(a,n)	__rlwinm(a,n,0,31) |  | ||||||
| #  elif defined(__MC68K__) |  | ||||||
|     /* Motorola specific tweak. <appro@fy.chalmers.se> */ |  | ||||||
| #   define ROTATE(a,n)	( n<24 ? __rol(a,n) : __ror(a,32-n) ) |  | ||||||
| #  else |  | ||||||
| #   define ROTATE(a,n)	__rol(a,n) |  | ||||||
| #  endif |  | ||||||
| # elif defined(__GNUC__) && __GNUC__>=2 && !defined(OPENSSL_NO_ASM) && !defined(OPENSSL_NO_INLINE_ASM) |  | ||||||
|   /*
 |  | ||||||
|    * Some GNU C inline assembler templates. Note that these are |  | ||||||
|    * rotates by *constant* number of bits! But that's exactly |  | ||||||
|    * what we need here... |  | ||||||
|    * 					<appro@fy.chalmers.se> |  | ||||||
|    */ |  | ||||||
| #  if defined(__i386) || defined(__i386__) || defined(__x86_64) || defined(__x86_64__) |  | ||||||
| #   define ROTATE(a,n)	({ register unsigned int ret;	\ |  | ||||||
| 				asm (			\ |  | ||||||
| 				"roll %1,%0"		\ |  | ||||||
| 				: "=r"(ret)		\ |  | ||||||
| 				: "I"(n), "0"(a)	\ |  | ||||||
| 				: "cc");		\ |  | ||||||
| 			   ret;				\ |  | ||||||
| 			}) |  | ||||||
| #  elif defined(__powerpc) || defined(__ppc__) || defined(__powerpc64__) |  | ||||||
| #   define ROTATE(a,n)	({ register unsigned int ret;	\ |  | ||||||
| 				asm (			\ |  | ||||||
| 				"rlwinm %0,%1,%2,0,31"	\ |  | ||||||
| 				: "=r"(ret)		\ |  | ||||||
| 				: "r"(a), "I"(n));	\ |  | ||||||
| 			   ret;				\ |  | ||||||
| 			}) |  | ||||||
| #  endif |  | ||||||
| # endif |  | ||||||
| #endif /* PEDANTIC */ |  | ||||||
| 
 |  | ||||||
| #if HASH_LONG_LOG2==2	/* Engage only if sizeof(HASH_LONG)== 4 */ |  | ||||||
| /* A nice byte order reversal from Wei Dai <weidai@eskimo.com> */ |  | ||||||
| #ifdef ROTATE |  | ||||||
| /* 5 instructions with rotate instruction, else 9 */ |  | ||||||
| #define REVERSE_FETCH32(a,l)	(					\ |  | ||||||
| 		l=*(const HASH_LONG *)(a),				\ |  | ||||||
| 		((ROTATE(l,8)&0x00FF00FF)|(ROTATE((l&0x00FF00FF),24)))	\ |  | ||||||
| 				) |  | ||||||
| #else |  | ||||||
| /* 6 instructions with rotate instruction, else 8 */ |  | ||||||
| #define REVERSE_FETCH32(a,l)	(				\ |  | ||||||
| 		l=*(const HASH_LONG *)(a),			\ |  | ||||||
| 		l=(((l>>8)&0x00FF00FF)|((l&0x00FF00FF)<<8)),	\ |  | ||||||
| 		ROTATE(l,16)					\ |  | ||||||
| 				) |  | ||||||
| /*
 |  | ||||||
|  * Originally the middle line started with l=(((l&0xFF00FF00)>>8)|... |  | ||||||
|  * It's rewritten as above for two reasons: |  | ||||||
|  *	- RISCs aren't good at long constants and have to explicitely |  | ||||||
|  *	  compose 'em with several (well, usually 2) instructions in a |  | ||||||
|  *	  register before performing the actual operation and (as you |  | ||||||
|  *	  already realized:-) having same constant should inspire the |  | ||||||
|  *	  compiler to permanently allocate the only register for it; |  | ||||||
|  *	- most modern CPUs have two ALUs, but usually only one has |  | ||||||
|  *	  circuitry for shifts:-( this minor tweak inspires compiler |  | ||||||
|  *	  to schedule shift instructions in a better way... |  | ||||||
|  * |  | ||||||
|  *				<appro@fy.chalmers.se> |  | ||||||
|  */ |  | ||||||
| #endif |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef ROTATE |  | ||||||
| #define ROTATE(a,n)     (((a)<<(n))|(((a)&0xffffffff)>>(32-(n)))) |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * Make some obvious choices. E.g., HASH_BLOCK_DATA_ORDER_ALIGNED |  | ||||||
|  * and HASH_BLOCK_HOST_ORDER ought to be the same if input data |  | ||||||
|  * and host are of the same "endianess". It's possible to mask |  | ||||||
|  * this with blank #define HASH_BLOCK_DATA_ORDER though... |  | ||||||
|  * |  | ||||||
|  *				<appro@fy.chalmers.se> |  | ||||||
|  */ |  | ||||||
| #if defined(B_ENDIAN) |  | ||||||
| #  if defined(DATA_ORDER_IS_BIG_ENDIAN) |  | ||||||
| #    if !defined(HASH_BLOCK_DATA_ORDER_ALIGNED) && HASH_LONG_LOG2==2 |  | ||||||
| #      define HASH_BLOCK_DATA_ORDER_ALIGNED	HASH_BLOCK_HOST_ORDER |  | ||||||
| #    endif |  | ||||||
| #  endif |  | ||||||
| #elif defined(L_ENDIAN) |  | ||||||
| #  if defined(DATA_ORDER_IS_LITTLE_ENDIAN) |  | ||||||
| #    if !defined(HASH_BLOCK_DATA_ORDER_ALIGNED) && HASH_LONG_LOG2==2 |  | ||||||
| #      define HASH_BLOCK_DATA_ORDER_ALIGNED	HASH_BLOCK_HOST_ORDER |  | ||||||
| #    endif |  | ||||||
| #  endif |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #if !defined(HASH_BLOCK_DATA_ORDER_ALIGNED) |  | ||||||
| #ifndef HASH_BLOCK_DATA_ORDER |  | ||||||
| #error "HASH_BLOCK_DATA_ORDER must be defined!" |  | ||||||
| #endif |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #if defined(DATA_ORDER_IS_BIG_ENDIAN) |  | ||||||
| 
 |  | ||||||
| #ifndef PEDANTIC |  | ||||||
| # if defined(__GNUC__) && __GNUC__>=2 && !defined(OPENSSL_NO_ASM) && !defined(OPENSSL_NO_INLINE_ASM) |  | ||||||
| #  if defined(__i386) || defined(__i386__) || defined(__x86_64) || defined(__x86_64__) |  | ||||||
|     /*
 |  | ||||||
|      * This gives ~30-40% performance improvement in SHA-256 compiled |  | ||||||
|      * with gcc [on P4]. Well, first macro to be frank. We can pull |  | ||||||
|      * this trick on x86* platforms only, because these CPUs can fetch |  | ||||||
|      * unaligned data without raising an exception. |  | ||||||
|      */ |  | ||||||
| #   define HOST_c2l(c,l)	({ unsigned int r=*((const unsigned int *)(c));	\ |  | ||||||
| 				   asm ("bswapl %0":"=r"(r):"0"(r));	\ |  | ||||||
| 				   (c)+=4; (l)=r;			}) |  | ||||||
| #   define HOST_l2c(l,c)	({ unsigned int r=(l);			\ |  | ||||||
| 				   asm ("bswapl %0":"=r"(r):"0"(r));	\ |  | ||||||
| 				   *((unsigned int *)(c))=r; (c)+=4; r;	}) |  | ||||||
| #  endif |  | ||||||
| # endif |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HOST_c2l |  | ||||||
| #define HOST_c2l(c,l)	(l =(((unsigned long)(*((c)++)))<<24),		\ |  | ||||||
| 			 l|=(((unsigned long)(*((c)++)))<<16),		\ |  | ||||||
| 			 l|=(((unsigned long)(*((c)++)))<< 8),		\ |  | ||||||
| 			 l|=(((unsigned long)(*((c)++)))    ),		\ |  | ||||||
| 			 l) |  | ||||||
| #endif |  | ||||||
| #define HOST_p_c2l(c,l,n)	{					\ |  | ||||||
| 			switch (n) {					\ |  | ||||||
| 			case 0: l =((unsigned long)(*((c)++)))<<24;	\ |  | ||||||
| 			case 1: l|=((unsigned long)(*((c)++)))<<16;	\ |  | ||||||
| 			case 2: l|=((unsigned long)(*((c)++)))<< 8;	\ |  | ||||||
| 			case 3: l|=((unsigned long)(*((c)++)));		\ |  | ||||||
| 				} } |  | ||||||
| #define HOST_p_c2l_p(c,l,sc,len) {					\ |  | ||||||
| 			switch (sc) {					\ |  | ||||||
| 			case 0: l =((unsigned long)(*((c)++)))<<24;	\ |  | ||||||
| 				if (--len == 0) break;			\ |  | ||||||
| 			case 1: l|=((unsigned long)(*((c)++)))<<16;	\ |  | ||||||
| 				if (--len == 0) break;			\ |  | ||||||
| 			case 2: l|=((unsigned long)(*((c)++)))<< 8;	\ |  | ||||||
| 				} } |  | ||||||
| /* NOTE the pointer is not incremented at the end of this */ |  | ||||||
| #define HOST_c2l_p(c,l,n)	{					\ |  | ||||||
| 			l=0; (c)+=n;					\ |  | ||||||
| 			switch (n) {					\ |  | ||||||
| 			case 3: l =((unsigned long)(*(--(c))))<< 8;	\ |  | ||||||
| 			case 2: l|=((unsigned long)(*(--(c))))<<16;	\ |  | ||||||
| 			case 1: l|=((unsigned long)(*(--(c))))<<24;	\ |  | ||||||
| 				} } |  | ||||||
| #ifndef HOST_l2c |  | ||||||
| #define HOST_l2c(l,c)	(*((c)++)=(unsigned char)(((l)>>24)&0xff),	\ |  | ||||||
| 			 *((c)++)=(unsigned char)(((l)>>16)&0xff),	\ |  | ||||||
| 			 *((c)++)=(unsigned char)(((l)>> 8)&0xff),	\ |  | ||||||
| 			 *((c)++)=(unsigned char)(((l)    )&0xff),	\ |  | ||||||
| 			 l) |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #elif defined(DATA_ORDER_IS_LITTLE_ENDIAN) |  | ||||||
| 
 |  | ||||||
| #if defined(__i386) || defined(__i386__) || defined(__x86_64) || defined(__x86_64__) |  | ||||||
|   /* See comment in DATA_ORDER_IS_BIG_ENDIAN section. */ |  | ||||||
| # define HOST_c2l(c,l)	((l)=*((const unsigned int *)(c)), (c)+=4, l) |  | ||||||
| # define HOST_l2c(l,c)	(*((unsigned int *)(c))=(l), (c)+=4, l) |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #ifndef HOST_c2l |  | ||||||
| #define HOST_c2l(c,l)	(l =(((unsigned long)(*((c)++)))    ),		\ |  | ||||||
| 			 l|=(((unsigned long)(*((c)++)))<< 8),		\ |  | ||||||
| 			 l|=(((unsigned long)(*((c)++)))<<16),		\ |  | ||||||
| 			 l|=(((unsigned long)(*((c)++)))<<24),		\ |  | ||||||
| 			 l) |  | ||||||
| #endif |  | ||||||
| #define HOST_p_c2l(c,l,n)	{					\ |  | ||||||
| 			switch (n) {					\ |  | ||||||
| 			case 0: l =((unsigned long)(*((c)++)));		\ |  | ||||||
| 			case 1: l|=((unsigned long)(*((c)++)))<< 8;	\ |  | ||||||
| 			case 2: l|=((unsigned long)(*((c)++)))<<16;	\ |  | ||||||
| 			case 3: l|=((unsigned long)(*((c)++)))<<24;	\ |  | ||||||
| 				} } |  | ||||||
| #define HOST_p_c2l_p(c,l,sc,len) {					\ |  | ||||||
| 			switch (sc) {					\ |  | ||||||
| 			case 0: l =((unsigned long)(*((c)++)));		\ |  | ||||||
| 				if (--len == 0) break;			\ |  | ||||||
| 			case 1: l|=((unsigned long)(*((c)++)))<< 8;	\ |  | ||||||
| 				if (--len == 0) break;			\ |  | ||||||
| 			case 2: l|=((unsigned long)(*((c)++)))<<16;	\ |  | ||||||
| 				} } |  | ||||||
| /* NOTE the pointer is not incremented at the end of this */ |  | ||||||
| #define HOST_c2l_p(c,l,n)	{					\ |  | ||||||
| 			l=0; (c)+=n;					\ |  | ||||||
| 			switch (n) {					\ |  | ||||||
| 			case 3: l =((unsigned long)(*(--(c))))<<16;	\ |  | ||||||
| 			case 2: l|=((unsigned long)(*(--(c))))<< 8;	\ |  | ||||||
| 			case 1: l|=((unsigned long)(*(--(c))));		\ |  | ||||||
| 				} } |  | ||||||
| #ifndef HOST_l2c |  | ||||||
| #define HOST_l2c(l,c)	(*((c)++)=(unsigned char)(((l)    )&0xff),	\ |  | ||||||
| 			 *((c)++)=(unsigned char)(((l)>> 8)&0xff),	\ |  | ||||||
| 			 *((c)++)=(unsigned char)(((l)>>16)&0xff),	\ |  | ||||||
| 			 *((c)++)=(unsigned char)(((l)>>24)&0xff),	\ |  | ||||||
| 			 l) |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * Time for some action:-) |  | ||||||
|  */ |  | ||||||
| 
 |  | ||||||
| int HASH_UPDATE (HASH_CTX *c, const void *data_, size_t len) |  | ||||||
| 	{ |  | ||||||
| 	const unsigned char *data=data_; |  | ||||||
| 	register HASH_LONG * p; |  | ||||||
| 	register HASH_LONG l; |  | ||||||
| 	size_t sw,sc,ew,ec; |  | ||||||
| 
 |  | ||||||
| 	if (len==0) return 1; |  | ||||||
| 
 |  | ||||||
| 	l=(c->Nl+(((HASH_LONG)len)<<3))&0xffffffffUL; |  | ||||||
| 	/* 95-05-24 eay Fixed a bug with the overflow handling, thanks to
 |  | ||||||
| 	 * Wei Dai <weidai@eskimo.com> for pointing it out. */ |  | ||||||
| 	if (l < c->Nl) /* overflow */ |  | ||||||
| 		c->Nh++; |  | ||||||
| 	c->Nh+=(len>>29);	/* might cause compiler warning on 16-bit */ |  | ||||||
| 	c->Nl=l; |  | ||||||
| 
 |  | ||||||
| 	if (c->num != 0) |  | ||||||
| 		{ |  | ||||||
| 		p=c->data; |  | ||||||
| 		sw=c->num>>2; |  | ||||||
| 		sc=c->num&0x03; |  | ||||||
| 
 |  | ||||||
| 		if ((c->num+len) >= HASH_CBLOCK) |  | ||||||
| 			{ |  | ||||||
| 			l=p[sw]; HOST_p_c2l(data,l,sc); p[sw++]=l; |  | ||||||
| 			for (; sw<HASH_LBLOCK; sw++) |  | ||||||
| 				{ |  | ||||||
| 				HOST_c2l(data,l); p[sw]=l; |  | ||||||
| 				} |  | ||||||
| 			HASH_BLOCK_HOST_ORDER (c,p,1); |  | ||||||
| 			len-=(HASH_CBLOCK-c->num); |  | ||||||
| 			c->num=0; |  | ||||||
| 			/* drop through and do the rest */ |  | ||||||
| 			} |  | ||||||
| 		else |  | ||||||
| 			{ |  | ||||||
| 			c->num+=(unsigned int)len; |  | ||||||
| 			if ((sc+len) < 4) /* ugly, add char's to a word */ |  | ||||||
| 				{ |  | ||||||
| 				l=p[sw]; HOST_p_c2l_p(data,l,sc,len); p[sw]=l; |  | ||||||
| 				} |  | ||||||
| 			else |  | ||||||
| 				{ |  | ||||||
| 				ew=(c->num>>2); |  | ||||||
| 				ec=(c->num&0x03); |  | ||||||
| 				if (sc) |  | ||||||
| 					l=p[sw]; |  | ||||||
| 				HOST_p_c2l(data,l,sc); |  | ||||||
| 				p[sw++]=l; |  | ||||||
| 				for (; sw < ew; sw++) |  | ||||||
| 					{ |  | ||||||
| 					HOST_c2l(data,l); p[sw]=l; |  | ||||||
| 					} |  | ||||||
| 				if (ec) |  | ||||||
| 					{ |  | ||||||
| 					HOST_c2l_p(data,l,ec); p[sw]=l; |  | ||||||
| 					} |  | ||||||
| 				} |  | ||||||
| 			return 1; |  | ||||||
| 			} |  | ||||||
| 		} |  | ||||||
| 
 |  | ||||||
| 	sw=len/HASH_CBLOCK; |  | ||||||
| 	if (sw > 0) |  | ||||||
| 		{ |  | ||||||
| #if defined(HASH_BLOCK_DATA_ORDER_ALIGNED) |  | ||||||
| 		/*
 |  | ||||||
| 		 * Note that HASH_BLOCK_DATA_ORDER_ALIGNED gets defined |  | ||||||
| 		 * only if sizeof(HASH_LONG)==4. |  | ||||||
| 		 */ |  | ||||||
| 		if ((((size_t)data)%4) == 0) |  | ||||||
| 			{ |  | ||||||
| 			/* data is properly aligned so that we can cast it: */ |  | ||||||
| 			HASH_BLOCK_DATA_ORDER_ALIGNED (c,(const HASH_LONG *)data,sw); |  | ||||||
| 			sw*=HASH_CBLOCK; |  | ||||||
| 			data+=sw; |  | ||||||
| 			len-=sw; |  | ||||||
| 			} |  | ||||||
| 		else |  | ||||||
| #if !defined(HASH_BLOCK_DATA_ORDER) |  | ||||||
| 			while (sw--) |  | ||||||
| 				{ |  | ||||||
| 				memcpy (p=c->data,data,HASH_CBLOCK); |  | ||||||
| 				HASH_BLOCK_DATA_ORDER_ALIGNED(c,p,1); |  | ||||||
| 				data+=HASH_CBLOCK; |  | ||||||
| 				len-=HASH_CBLOCK; |  | ||||||
| 				} |  | ||||||
| #endif |  | ||||||
| #endif |  | ||||||
| #if defined(HASH_BLOCK_DATA_ORDER) |  | ||||||
| 			{ |  | ||||||
| 			HASH_BLOCK_DATA_ORDER(c,data,sw); |  | ||||||
| 			sw*=HASH_CBLOCK; |  | ||||||
| 			data+=sw; |  | ||||||
| 			len-=sw; |  | ||||||
| 			} |  | ||||||
| #endif |  | ||||||
| 		} |  | ||||||
| 
 |  | ||||||
| 	if (len!=0) |  | ||||||
| 		{ |  | ||||||
| 		p = c->data; |  | ||||||
| 		c->num = len; |  | ||||||
| 		ew=len>>2;	/* words to copy */ |  | ||||||
| 		ec=len&0x03; |  | ||||||
| 		for (; ew; ew--,p++) |  | ||||||
| 			{ |  | ||||||
| 			HOST_c2l(data,l); *p=l; |  | ||||||
| 			} |  | ||||||
| 		HOST_c2l_p(data,l,ec); |  | ||||||
| 		*p=l; |  | ||||||
| 		} |  | ||||||
| 	return 1; |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| void HASH_TRANSFORM (HASH_CTX *c, const unsigned char *data) |  | ||||||
| 	{ |  | ||||||
| #if defined(HASH_BLOCK_DATA_ORDER_ALIGNED) |  | ||||||
| 	if ((((size_t)data)%4) == 0) |  | ||||||
| 		/* data is properly aligned so that we can cast it: */ |  | ||||||
| 		HASH_BLOCK_DATA_ORDER_ALIGNED (c,(const HASH_LONG *)data,1); |  | ||||||
| 	else |  | ||||||
| #if !defined(HASH_BLOCK_DATA_ORDER) |  | ||||||
| 		{ |  | ||||||
| 		memcpy (c->data,data,HASH_CBLOCK); |  | ||||||
| 		HASH_BLOCK_DATA_ORDER_ALIGNED (c,c->data,1); |  | ||||||
| 		} |  | ||||||
| #endif |  | ||||||
| #endif |  | ||||||
| #if defined(HASH_BLOCK_DATA_ORDER) |  | ||||||
| 	HASH_BLOCK_DATA_ORDER (c,data,1); |  | ||||||
| #endif |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| int HASH_FINAL (unsigned char *md, HASH_CTX *c) |  | ||||||
| 	{ |  | ||||||
| 	register HASH_LONG *p; |  | ||||||
| 	register unsigned long l; |  | ||||||
| 	register int i,j; |  | ||||||
| 	static const unsigned char end[4]={0x80,0x00,0x00,0x00}; |  | ||||||
| 	const unsigned char *cp=end; |  | ||||||
| 
 |  | ||||||
| 	/* c->num should definitly have room for at least one more byte. */ |  | ||||||
| 	p=c->data; |  | ||||||
| 	i=c->num>>2; |  | ||||||
| 	j=c->num&0x03; |  | ||||||
| 
 |  | ||||||
| #if 0 |  | ||||||
| 	/* purify often complains about the following line as an
 |  | ||||||
| 	 * Uninitialized Memory Read.  While this can be true, the |  | ||||||
| 	 * following p_c2l macro will reset l when that case is true. |  | ||||||
| 	 * This is because j&0x03 contains the number of 'valid' bytes |  | ||||||
| 	 * already in p[i].  If and only if j&0x03 == 0, the UMR will |  | ||||||
| 	 * occur but this is also the only time p_c2l will do |  | ||||||
| 	 * l= *(cp++) instead of l|= *(cp++) |  | ||||||
| 	 * Many thanks to Alex Tang <altitude@cic.net> for pickup this |  | ||||||
| 	 * 'potential bug' */ |  | ||||||
| #ifdef PURIFY |  | ||||||
| 	if (j==0) p[i]=0; /* Yeah, but that's not the way to fix it:-) */ |  | ||||||
| #endif |  | ||||||
| 	l=p[i]; |  | ||||||
| #else |  | ||||||
| 	l = (j==0) ? 0 : p[i]; |  | ||||||
| #endif |  | ||||||
| 	HOST_p_c2l(cp,l,j); p[i++]=l; /* i is the next 'undefined word' */ |  | ||||||
| 
 |  | ||||||
| 	if (i>(HASH_LBLOCK-2)) /* save room for Nl and Nh */ |  | ||||||
| 		{ |  | ||||||
| 		if (i<HASH_LBLOCK) p[i]=0; |  | ||||||
| 		HASH_BLOCK_HOST_ORDER (c,p,1); |  | ||||||
| 		i=0; |  | ||||||
| 		} |  | ||||||
| 	for (; i<(HASH_LBLOCK-2); i++) |  | ||||||
| 		p[i]=0; |  | ||||||
| 
 |  | ||||||
| #if   defined(DATA_ORDER_IS_BIG_ENDIAN) |  | ||||||
| 	p[HASH_LBLOCK-2]=c->Nh; |  | ||||||
| 	p[HASH_LBLOCK-1]=c->Nl; |  | ||||||
| #elif defined(DATA_ORDER_IS_LITTLE_ENDIAN) |  | ||||||
| 	p[HASH_LBLOCK-2]=c->Nl; |  | ||||||
| 	p[HASH_LBLOCK-1]=c->Nh; |  | ||||||
| #endif |  | ||||||
| 	HASH_BLOCK_HOST_ORDER (c,p,1); |  | ||||||
| 
 |  | ||||||
| #ifndef HASH_MAKE_STRING |  | ||||||
| #error "HASH_MAKE_STRING must be defined!" |  | ||||||
| #else |  | ||||||
| 	HASH_MAKE_STRING(c,md); |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| 	c->num=0; |  | ||||||
| 	/* clear stuff, HASH_BLOCK may be leaving some stuff on the stack
 |  | ||||||
| 	 * but I'm not worried :-) |  | ||||||
| 	OPENSSL_cleanse((void *)c,sizeof(HASH_CTX)); |  | ||||||
| 	 */ |  | ||||||
| 	return 1; |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| #ifndef MD32_REG_T |  | ||||||
| #define MD32_REG_T long |  | ||||||
| /*
 |  | ||||||
|  * This comment was originaly written for MD5, which is why it |  | ||||||
|  * discusses A-D. But it basically applies to all 32-bit digests, |  | ||||||
|  * which is why it was moved to common header file. |  | ||||||
|  * |  | ||||||
|  * In case you wonder why A-D are declared as long and not |  | ||||||
|  * as MD5_LONG. Doing so results in slight performance |  | ||||||
|  * boost on LP64 architectures. The catch is we don't |  | ||||||
|  * really care if 32 MSBs of a 64-bit register get polluted |  | ||||||
|  * with eventual overflows as we *save* only 32 LSBs in |  | ||||||
|  * *either* case. Now declaring 'em long excuses the compiler |  | ||||||
|  * from keeping 32 MSBs zeroed resulting in 13% performance |  | ||||||
|  * improvement under SPARC Solaris7/64 and 5% under AlphaLinux. |  | ||||||
|  * Well, to be honest it should say that this *prevents*  |  | ||||||
|  * performance degradation. |  | ||||||
|  *				<appro@fy.chalmers.se> |  | ||||||
|  * Apparently there're LP64 compilers that generate better |  | ||||||
|  * code if A-D are declared int. Most notably GCC-x86_64 |  | ||||||
|  * generates better code. |  | ||||||
|  *				<appro@fy.chalmers.se> |  | ||||||
|  */ |  | ||||||
| #endif |  | ||||||
|  | @ -1,365 +0,0 @@ | ||||||
| /* Functions to compute MD5 message digest of files or memory blocks.
 |  | ||||||
|    according to the definition of MD5 in RFC 1321 from April 1992. |  | ||||||
|    Copyright (C) 1995,1996,1997,1999,2000,2001 Free Software Foundation, Inc. |  | ||||||
|    This file is part of the GNU C Library. |  | ||||||
| 
 |  | ||||||
|    The GNU C Library is free software; you can redistribute it and/or |  | ||||||
|    modify it under the terms of the GNU Lesser General Public |  | ||||||
|    License as published by the Free Software Foundation; either |  | ||||||
|    version 2.1 of the License, or (at your option) any later version. |  | ||||||
| 
 |  | ||||||
|    The GNU C Library is distributed in the hope that it will be useful, |  | ||||||
|    but WITHOUT ANY WARRANTY; without even the implied warranty of |  | ||||||
|    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU |  | ||||||
|    Lesser General Public License for more details. |  | ||||||
| 
 |  | ||||||
|    You should have received a copy of the GNU Lesser General Public |  | ||||||
|    License along with the GNU C Library; if not, write to the Free |  | ||||||
|    Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA |  | ||||||
|    02111-1307 USA.  */ |  | ||||||
| 
 |  | ||||||
| /* Written by Ulrich Drepper <drepper@gnu.ai.mit.edu>, 1995.  */ |  | ||||||
| 
 |  | ||||||
| #include <sys/types.h> |  | ||||||
| 
 |  | ||||||
| #include <stdlib.h> |  | ||||||
| #include <string.h> |  | ||||||
| 
 |  | ||||||
| #include "md5.h" |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| static md5_uint32 SWAP(md5_uint32 n) |  | ||||||
| { |  | ||||||
|   static int checked = 0; |  | ||||||
|   static int bigendian = 0; |  | ||||||
|   static md5_uint32 test; |  | ||||||
| 
 |  | ||||||
|   if (!checked) { |  | ||||||
|     test = 1; |  | ||||||
|     if (* (char *) &test == 0) |  | ||||||
|       bigendian = 1; |  | ||||||
|     checked = 1; |  | ||||||
|   } |  | ||||||
| 
 |  | ||||||
|   if (bigendian) |  | ||||||
|     return (((n) << 24) | (((n) & 0xff00) << 8) | (((n) >> 8) & 0xff00) | ((n) >> 24)); |  | ||||||
|   else |  | ||||||
|     return n; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| /* This array contains the bytes used to pad the buffer to the next
 |  | ||||||
|    64-byte boundary.  (RFC 1321, 3.1: Step 1)  */ |  | ||||||
| static const unsigned char fillbuf[64] = { 0x80, 0 /* , 0, 0, ...  */ }; |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| /* Initialize structure containing state of computation.
 |  | ||||||
|    (RFC 1321, 3.3: Step 3)  */ |  | ||||||
| void |  | ||||||
| MD5_Init (ctx) |  | ||||||
|      struct MD5_CTX *ctx; |  | ||||||
| { |  | ||||||
|   ctx->A = 0x67452301; |  | ||||||
|   ctx->B = 0xefcdab89; |  | ||||||
|   ctx->C = 0x98badcfe; |  | ||||||
|   ctx->D = 0x10325476; |  | ||||||
| 
 |  | ||||||
|   ctx->total[0] = ctx->total[1] = 0; |  | ||||||
|   ctx->buflen = 0; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| /* Put result from CTX in first 16 bytes following RESBUF.  The result
 |  | ||||||
|    must be in little endian byte order. |  | ||||||
| 
 |  | ||||||
|    IMPORTANT: On some systems it is required that RESBUF is correctly |  | ||||||
|    aligned for a 32 bits value.  */ |  | ||||||
| void * |  | ||||||
| md5_read_ctx (ctx, resbuf) |  | ||||||
|      const struct MD5_CTX *ctx; |  | ||||||
|      void *resbuf; |  | ||||||
| { |  | ||||||
|   ((md5_uint32 *) resbuf)[0] = SWAP (ctx->A); |  | ||||||
|   ((md5_uint32 *) resbuf)[1] = SWAP (ctx->B); |  | ||||||
|   ((md5_uint32 *) resbuf)[2] = SWAP (ctx->C); |  | ||||||
|   ((md5_uint32 *) resbuf)[3] = SWAP (ctx->D); |  | ||||||
| 
 |  | ||||||
|   return resbuf; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| /* Process the remaining bytes in the internal buffer and the usual
 |  | ||||||
|    prolog according to the standard and write the result to RESBUF. |  | ||||||
| 
 |  | ||||||
|    IMPORTANT: On some systems it is required that RESBUF is correctly |  | ||||||
|    aligned for a 32 bits value.  */ |  | ||||||
| void * |  | ||||||
| MD5_Final (resbuf, ctx) |  | ||||||
|      void *resbuf; |  | ||||||
|      struct MD5_CTX *ctx; |  | ||||||
| { |  | ||||||
|   /* Take yet unprocessed bytes into account.  */ |  | ||||||
|   md5_uint32 bytes = ctx->buflen; |  | ||||||
|   size_t pad; |  | ||||||
| 
 |  | ||||||
|   /* Now count remaining bytes.  */ |  | ||||||
|   ctx->total[0] += bytes; |  | ||||||
|   if (ctx->total[0] < bytes) |  | ||||||
|     ++ctx->total[1]; |  | ||||||
| 
 |  | ||||||
|   pad = bytes >= 56 ? 64 + 56 - bytes : 56 - bytes; |  | ||||||
|   memcpy (&ctx->buffer[bytes], fillbuf, pad); |  | ||||||
| 
 |  | ||||||
|   /* Put the 64-bit file length in *bits* at the end of the buffer.  */ |  | ||||||
|   *(md5_uint32 *) &ctx->buffer[bytes + pad] = SWAP (ctx->total[0] << 3); |  | ||||||
|   *(md5_uint32 *) &ctx->buffer[bytes + pad + 4] = SWAP ((ctx->total[1] << 3) | |  | ||||||
| 							(ctx->total[0] >> 29)); |  | ||||||
| 
 |  | ||||||
|   /* Process last bytes.  */ |  | ||||||
|   md5_process_block (ctx->buffer, bytes + pad + 8, ctx); |  | ||||||
| 
 |  | ||||||
|   return md5_read_ctx (ctx, resbuf); |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| void |  | ||||||
| MD5_Update (ctx, buffer, len) |  | ||||||
|      struct MD5_CTX *ctx; |  | ||||||
|      const void *buffer; |  | ||||||
|      size_t len; |  | ||||||
| { |  | ||||||
|   /* When we already have some bits in our internal buffer concatenate
 |  | ||||||
|      both inputs first.  */ |  | ||||||
|   if (ctx->buflen != 0) |  | ||||||
|     { |  | ||||||
|       size_t left_over = ctx->buflen; |  | ||||||
|       size_t add = 128 - left_over > len ? len : 128 - left_over; |  | ||||||
| 
 |  | ||||||
|       memcpy (&ctx->buffer[left_over], buffer, add); |  | ||||||
|       ctx->buflen += add; |  | ||||||
| 
 |  | ||||||
|       if (ctx->buflen > 64) |  | ||||||
| 	{ |  | ||||||
| 	  md5_process_block (ctx->buffer, ctx->buflen & ~63, ctx); |  | ||||||
| 
 |  | ||||||
| 	  ctx->buflen &= 63; |  | ||||||
| 	  /* The regions in the following copy operation cannot overlap.  */ |  | ||||||
| 	  memcpy (ctx->buffer, &ctx->buffer[(left_over + add) & ~63], |  | ||||||
| 		  ctx->buflen); |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
|       buffer = (const char *) buffer + add; |  | ||||||
|       len -= add; |  | ||||||
|     } |  | ||||||
| 
 |  | ||||||
|   /* Process available complete blocks.  */ |  | ||||||
|   if (len >= 64) |  | ||||||
|     { |  | ||||||
| #if !_STRING_ARCH_unaligned |  | ||||||
| /* To check alignment gcc has an appropriate operator.  Other
 |  | ||||||
|    compilers don't.  */ |  | ||||||
| # if __GNUC__ >= 2 |  | ||||||
| #  define UNALIGNED_P(p) (((md5_uintptr) p) % __alignof__ (md5_uint32) != 0) |  | ||||||
| # else |  | ||||||
| #  define UNALIGNED_P(p) (((md5_uintptr) p) % sizeof (md5_uint32) != 0) |  | ||||||
| # endif |  | ||||||
|       if (UNALIGNED_P (buffer)) |  | ||||||
| 	while (len > 64) |  | ||||||
| 	  { |  | ||||||
| 	    md5_process_block (memcpy (ctx->buffer, buffer, 64), 64, ctx); |  | ||||||
| 	    buffer = (const char *) buffer + 64; |  | ||||||
| 	    len -= 64; |  | ||||||
| 	  } |  | ||||||
|       else |  | ||||||
| #endif |  | ||||||
| 	{ |  | ||||||
| 	  md5_process_block (buffer, len & ~63, ctx); |  | ||||||
| 	  buffer = (const char *) buffer + (len & ~63); |  | ||||||
| 	  len &= 63; |  | ||||||
| 	} |  | ||||||
|     } |  | ||||||
| 
 |  | ||||||
|   /* Move remaining bytes in internal buffer.  */ |  | ||||||
|   if (len > 0) |  | ||||||
|     { |  | ||||||
|       size_t left_over = ctx->buflen; |  | ||||||
| 
 |  | ||||||
|       memcpy (&ctx->buffer[left_over], buffer, len); |  | ||||||
|       left_over += len; |  | ||||||
|       if (left_over >= 64) |  | ||||||
| 	{ |  | ||||||
| 	  md5_process_block (ctx->buffer, 64, ctx); |  | ||||||
| 	  left_over -= 64; |  | ||||||
| 	  memcpy (ctx->buffer, &ctx->buffer[64], left_over); |  | ||||||
| 	} |  | ||||||
|       ctx->buflen = left_over; |  | ||||||
|     } |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| /* These are the four functions used in the four steps of the MD5 algorithm
 |  | ||||||
|    and defined in the RFC 1321.  The first function is a little bit optimized |  | ||||||
|    (as found in Colin Plumbs public domain implementation).  */ |  | ||||||
| /* #define FF(b, c, d) ((b & c) | (~b & d)) */ |  | ||||||
| #define FF(b, c, d) (d ^ (b & (c ^ d))) |  | ||||||
| #define FG(b, c, d) FF (d, b, c) |  | ||||||
| #define FH(b, c, d) (b ^ c ^ d) |  | ||||||
| #define FI(b, c, d) (c ^ (b | ~d)) |  | ||||||
| 
 |  | ||||||
| /* Process LEN bytes of BUFFER, accumulating context into CTX.
 |  | ||||||
|    It is assumed that LEN % 64 == 0.  */ |  | ||||||
| 
 |  | ||||||
| void |  | ||||||
| md5_process_block (buffer, len, ctx) |  | ||||||
|      const void *buffer; |  | ||||||
|      size_t len; |  | ||||||
|      struct MD5_CTX *ctx; |  | ||||||
| { |  | ||||||
|   md5_uint32 correct_words[16]; |  | ||||||
|   const md5_uint32 *words = buffer; |  | ||||||
|   size_t nwords = len / sizeof (md5_uint32); |  | ||||||
|   const md5_uint32 *endp = words + nwords; |  | ||||||
|   md5_uint32 A = ctx->A; |  | ||||||
|   md5_uint32 B = ctx->B; |  | ||||||
|   md5_uint32 C = ctx->C; |  | ||||||
|   md5_uint32 D = ctx->D; |  | ||||||
| 
 |  | ||||||
|   /* First increment the byte count.  RFC 1321 specifies the possible
 |  | ||||||
|      length of the file up to 2^64 bits.  Here we only compute the |  | ||||||
|      number of bytes.  Do a double word increment.  */ |  | ||||||
|   ctx->total[0] += len; |  | ||||||
|   if (ctx->total[0] < len) |  | ||||||
|     ++ctx->total[1]; |  | ||||||
| 
 |  | ||||||
|   /* Process all bytes in the buffer with 64 bytes in each round of
 |  | ||||||
|      the loop.  */ |  | ||||||
|   while (words < endp) |  | ||||||
|     { |  | ||||||
|       md5_uint32 *cwp = correct_words; |  | ||||||
|       md5_uint32 A_save = A; |  | ||||||
|       md5_uint32 B_save = B; |  | ||||||
|       md5_uint32 C_save = C; |  | ||||||
|       md5_uint32 D_save = D; |  | ||||||
| 
 |  | ||||||
|       /* First round: using the given function, the context and a constant
 |  | ||||||
| 	 the next context is computed.  Because the algorithms processing |  | ||||||
| 	 unit is a 32-bit word and it is determined to work on words in |  | ||||||
| 	 little endian byte order we perhaps have to change the byte order |  | ||||||
| 	 before the computation.  To reduce the work for the next steps |  | ||||||
| 	 we store the swapped words in the array CORRECT_WORDS.  */ |  | ||||||
| 
 |  | ||||||
| #define OP(a, b, c, d, s, T)						\ |  | ||||||
|       do								\ |  | ||||||
|         {								\ |  | ||||||
| 	  a += FF (b, c, d) + (*cwp++ = SWAP (*words)) + T;		\ |  | ||||||
| 	  ++words;							\ |  | ||||||
| 	  CYCLIC (a, s);						\ |  | ||||||
| 	  a += b;							\ |  | ||||||
|         }								\ |  | ||||||
|       while (0) |  | ||||||
| 
 |  | ||||||
|       /* It is unfortunate that C does not provide an operator for
 |  | ||||||
| 	 cyclic rotation.  Hope the C compiler is smart enough.  */ |  | ||||||
| #define CYCLIC(w, s) (w = (w << s) | (w >> (32 - s))) |  | ||||||
| 
 |  | ||||||
|       /* Before we start, one word to the strange constants.
 |  | ||||||
| 	 They are defined in RFC 1321 as |  | ||||||
| 
 |  | ||||||
| 	 T[i] = (int) (4294967296.0 * fabs (sin (i))), i=1..64 |  | ||||||
|        */ |  | ||||||
| 
 |  | ||||||
|       /* Round 1.  */ |  | ||||||
|       OP (A, B, C, D,  7, 0xd76aa478); |  | ||||||
|       OP (D, A, B, C, 12, 0xe8c7b756); |  | ||||||
|       OP (C, D, A, B, 17, 0x242070db); |  | ||||||
|       OP (B, C, D, A, 22, 0xc1bdceee); |  | ||||||
|       OP (A, B, C, D,  7, 0xf57c0faf); |  | ||||||
|       OP (D, A, B, C, 12, 0x4787c62a); |  | ||||||
|       OP (C, D, A, B, 17, 0xa8304613); |  | ||||||
|       OP (B, C, D, A, 22, 0xfd469501); |  | ||||||
|       OP (A, B, C, D,  7, 0x698098d8); |  | ||||||
|       OP (D, A, B, C, 12, 0x8b44f7af); |  | ||||||
|       OP (C, D, A, B, 17, 0xffff5bb1); |  | ||||||
|       OP (B, C, D, A, 22, 0x895cd7be); |  | ||||||
|       OP (A, B, C, D,  7, 0x6b901122); |  | ||||||
|       OP (D, A, B, C, 12, 0xfd987193); |  | ||||||
|       OP (C, D, A, B, 17, 0xa679438e); |  | ||||||
|       OP (B, C, D, A, 22, 0x49b40821); |  | ||||||
| 
 |  | ||||||
|       /* For the second to fourth round we have the possibly swapped words
 |  | ||||||
| 	 in CORRECT_WORDS.  Redefine the macro to take an additional first |  | ||||||
| 	 argument specifying the function to use.  */ |  | ||||||
| #undef OP |  | ||||||
| #define OP(f, a, b, c, d, k, s, T)					\ |  | ||||||
|       do 								\ |  | ||||||
| 	{								\ |  | ||||||
| 	  a += f (b, c, d) + correct_words[k] + T;			\ |  | ||||||
| 	  CYCLIC (a, s);						\ |  | ||||||
| 	  a += b;							\ |  | ||||||
| 	}								\ |  | ||||||
|       while (0) |  | ||||||
| 
 |  | ||||||
|       /* Round 2.  */ |  | ||||||
|       OP (FG, A, B, C, D,  1,  5, 0xf61e2562); |  | ||||||
|       OP (FG, D, A, B, C,  6,  9, 0xc040b340); |  | ||||||
|       OP (FG, C, D, A, B, 11, 14, 0x265e5a51); |  | ||||||
|       OP (FG, B, C, D, A,  0, 20, 0xe9b6c7aa); |  | ||||||
|       OP (FG, A, B, C, D,  5,  5, 0xd62f105d); |  | ||||||
|       OP (FG, D, A, B, C, 10,  9, 0x02441453); |  | ||||||
|       OP (FG, C, D, A, B, 15, 14, 0xd8a1e681); |  | ||||||
|       OP (FG, B, C, D, A,  4, 20, 0xe7d3fbc8); |  | ||||||
|       OP (FG, A, B, C, D,  9,  5, 0x21e1cde6); |  | ||||||
|       OP (FG, D, A, B, C, 14,  9, 0xc33707d6); |  | ||||||
|       OP (FG, C, D, A, B,  3, 14, 0xf4d50d87); |  | ||||||
|       OP (FG, B, C, D, A,  8, 20, 0x455a14ed); |  | ||||||
|       OP (FG, A, B, C, D, 13,  5, 0xa9e3e905); |  | ||||||
|       OP (FG, D, A, B, C,  2,  9, 0xfcefa3f8); |  | ||||||
|       OP (FG, C, D, A, B,  7, 14, 0x676f02d9); |  | ||||||
|       OP (FG, B, C, D, A, 12, 20, 0x8d2a4c8a); |  | ||||||
| 
 |  | ||||||
|       /* Round 3.  */ |  | ||||||
|       OP (FH, A, B, C, D,  5,  4, 0xfffa3942); |  | ||||||
|       OP (FH, D, A, B, C,  8, 11, 0x8771f681); |  | ||||||
|       OP (FH, C, D, A, B, 11, 16, 0x6d9d6122); |  | ||||||
|       OP (FH, B, C, D, A, 14, 23, 0xfde5380c); |  | ||||||
|       OP (FH, A, B, C, D,  1,  4, 0xa4beea44); |  | ||||||
|       OP (FH, D, A, B, C,  4, 11, 0x4bdecfa9); |  | ||||||
|       OP (FH, C, D, A, B,  7, 16, 0xf6bb4b60); |  | ||||||
|       OP (FH, B, C, D, A, 10, 23, 0xbebfbc70); |  | ||||||
|       OP (FH, A, B, C, D, 13,  4, 0x289b7ec6); |  | ||||||
|       OP (FH, D, A, B, C,  0, 11, 0xeaa127fa); |  | ||||||
|       OP (FH, C, D, A, B,  3, 16, 0xd4ef3085); |  | ||||||
|       OP (FH, B, C, D, A,  6, 23, 0x04881d05); |  | ||||||
|       OP (FH, A, B, C, D,  9,  4, 0xd9d4d039); |  | ||||||
|       OP (FH, D, A, B, C, 12, 11, 0xe6db99e5); |  | ||||||
|       OP (FH, C, D, A, B, 15, 16, 0x1fa27cf8); |  | ||||||
|       OP (FH, B, C, D, A,  2, 23, 0xc4ac5665); |  | ||||||
| 
 |  | ||||||
|       /* Round 4.  */ |  | ||||||
|       OP (FI, A, B, C, D,  0,  6, 0xf4292244); |  | ||||||
|       OP (FI, D, A, B, C,  7, 10, 0x432aff97); |  | ||||||
|       OP (FI, C, D, A, B, 14, 15, 0xab9423a7); |  | ||||||
|       OP (FI, B, C, D, A,  5, 21, 0xfc93a039); |  | ||||||
|       OP (FI, A, B, C, D, 12,  6, 0x655b59c3); |  | ||||||
|       OP (FI, D, A, B, C,  3, 10, 0x8f0ccc92); |  | ||||||
|       OP (FI, C, D, A, B, 10, 15, 0xffeff47d); |  | ||||||
|       OP (FI, B, C, D, A,  1, 21, 0x85845dd1); |  | ||||||
|       OP (FI, A, B, C, D,  8,  6, 0x6fa87e4f); |  | ||||||
|       OP (FI, D, A, B, C, 15, 10, 0xfe2ce6e0); |  | ||||||
|       OP (FI, C, D, A, B,  6, 15, 0xa3014314); |  | ||||||
|       OP (FI, B, C, D, A, 13, 21, 0x4e0811a1); |  | ||||||
|       OP (FI, A, B, C, D,  4,  6, 0xf7537e82); |  | ||||||
|       OP (FI, D, A, B, C, 11, 10, 0xbd3af235); |  | ||||||
|       OP (FI, C, D, A, B,  2, 15, 0x2ad7d2bb); |  | ||||||
|       OP (FI, B, C, D, A,  9, 21, 0xeb86d391); |  | ||||||
| 
 |  | ||||||
|       /* Add the starting values of the context.  */ |  | ||||||
|       A += A_save; |  | ||||||
|       B += B_save; |  | ||||||
|       C += C_save; |  | ||||||
|       D += D_save; |  | ||||||
|     } |  | ||||||
| 
 |  | ||||||
|   /* Put checksum in context given as argument.  */ |  | ||||||
|   ctx->A = A; |  | ||||||
|   ctx->B = B; |  | ||||||
|   ctx->C = C; |  | ||||||
|   ctx->D = D; |  | ||||||
| } |  | ||||||
|  | @ -1,82 +0,0 @@ | ||||||
| /* Declaration of functions and data types used for MD5 sum computing
 |  | ||||||
|    library functions. |  | ||||||
|    Copyright (C) 1995,1996,1997,1999,2000,2001 Free Software Foundation, Inc. |  | ||||||
|    This file is part of the GNU C Library. |  | ||||||
| 
 |  | ||||||
|    The GNU C Library is free software; you can redistribute it and/or |  | ||||||
|    modify it under the terms of the GNU Lesser General Public |  | ||||||
|    License as published by the Free Software Foundation; either |  | ||||||
|    version 2.1 of the License, or (at your option) any later version. |  | ||||||
| 
 |  | ||||||
|    The GNU C Library is distributed in the hope that it will be useful, |  | ||||||
|    but WITHOUT ANY WARRANTY; without even the implied warranty of |  | ||||||
|    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU |  | ||||||
|    Lesser General Public License for more details. |  | ||||||
| 
 |  | ||||||
|    You should have received a copy of the GNU Lesser General Public |  | ||||||
|    License along with the GNU C Library; if not, write to the Free |  | ||||||
|    Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA |  | ||||||
|    02111-1307 USA.  */ |  | ||||||
| 
 |  | ||||||
| #ifndef _MD5_H |  | ||||||
| #define _MD5_H 1 |  | ||||||
| 
 |  | ||||||
| #include <inttypes.h> |  | ||||||
| typedef uint32_t md5_uint32; |  | ||||||
| typedef uintptr_t md5_uintptr; |  | ||||||
| 
 |  | ||||||
| /* Structure to save state of computation between the single steps.  */ |  | ||||||
| struct MD5_CTX |  | ||||||
| { |  | ||||||
|   md5_uint32 A; |  | ||||||
|   md5_uint32 B; |  | ||||||
|   md5_uint32 C; |  | ||||||
|   md5_uint32 D; |  | ||||||
| 
 |  | ||||||
|   md5_uint32 total[2]; |  | ||||||
|   md5_uint32 buflen; |  | ||||||
|   char buffer[128] __attribute__ ((__aligned__ (__alignof__ (md5_uint32)))); |  | ||||||
| }; |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * The following three functions are build up the low level used in |  | ||||||
|  * the functions `md5_stream' and `md5_buffer'. |  | ||||||
|  */ |  | ||||||
| 
 |  | ||||||
| /* Initialize structure containing state of computation.
 |  | ||||||
|    (RFC 1321, 3.3: Step 3)  */ |  | ||||||
| extern void MD5_Init (struct MD5_CTX *ctx); |  | ||||||
| 
 |  | ||||||
| /* Starting with the result of former calls of this function (or the
 |  | ||||||
|    initialization function update the context for the next LEN bytes |  | ||||||
|    starting at BUFFER. |  | ||||||
|    It is necessary that LEN is a multiple of 64!!! */ |  | ||||||
| extern void md5_process_block (const void *buffer, size_t len, |  | ||||||
| 				      struct MD5_CTX *ctx); |  | ||||||
| 
 |  | ||||||
| /* Starting with the result of former calls of this function (or the
 |  | ||||||
|    initialization function update the context for the next LEN bytes |  | ||||||
|    starting at BUFFER. |  | ||||||
|    It is NOT required that LEN is a multiple of 64.  */ |  | ||||||
| extern void MD5_Update (struct MD5_CTX *ctx, const void *buffer, size_t len); |  | ||||||
| 
 |  | ||||||
| /* Process the remaining bytes in the buffer and put result from CTX
 |  | ||||||
|    in first 16 bytes following RESBUF.  The result is always in little |  | ||||||
|    endian byte order, so that a byte-wise output yields to the wanted |  | ||||||
|    ASCII representation of the message digest. |  | ||||||
| 
 |  | ||||||
|    IMPORTANT: On some systems it is required that RESBUF is correctly |  | ||||||
|    aligned for a 32 bits value.  */ |  | ||||||
| extern void *MD5_Final (void *resbuf, struct MD5_CTX *ctx); |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| /* Put result from CTX in first 16 bytes following RESBUF.  The result is
 |  | ||||||
|    always in little endian byte order, so that a byte-wise output yields |  | ||||||
|    to the wanted ASCII representation of the message digest. |  | ||||||
| 
 |  | ||||||
|    IMPORTANT: On some systems it is required that RESBUF is correctly |  | ||||||
|    aligned for a 32 bits value.  */ |  | ||||||
| extern void *md5_read_ctx (const struct MD5_CTX *ctx, void *resbuf); |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| #endif /* md5.h */ |  | ||||||
|  | @ -1,369 +0,0 @@ | ||||||
| /* $Id$ */ |  | ||||||
| 
 |  | ||||||
| /* sha.c - Implementation of the Secure Hash Algorithm
 |  | ||||||
|  * |  | ||||||
|  * Copyright (C) 1995, A.M. Kuchling |  | ||||||
|  * |  | ||||||
|  * Distribute and use freely; there are no restrictions on further  |  | ||||||
|  * dissemination and usage except those imposed by the laws of your  |  | ||||||
|  * country of residence. |  | ||||||
|  * |  | ||||||
|  * Adapted to pike and some cleanup by Niels Möller. |  | ||||||
|  */ |  | ||||||
| 
 |  | ||||||
| /* $Id$ */ |  | ||||||
| 
 |  | ||||||
| /* SHA: NIST's Secure Hash Algorithm */ |  | ||||||
| 
 |  | ||||||
| /* Based on SHA code originally posted to sci.crypt by Peter Gutmann
 |  | ||||||
|    in message <30ajo5$oe8@ccu2.auckland.ac.nz>. |  | ||||||
|    Modified to test for endianness on creation of SHA objects by AMK. |  | ||||||
|    Also, the original specification of SHA was found to have a weakness |  | ||||||
|    by NSA/NIST.  This code implements the fixed version of SHA. |  | ||||||
| */ |  | ||||||
| 
 |  | ||||||
| /* Here's the first paragraph of Peter Gutmann's posting:
 |  | ||||||
|     |  | ||||||
| The following is my SHA (FIPS 180) code updated to allow use of the "fixed" |  | ||||||
| SHA, thanks to Jim Gillogly and an anonymous contributor for the information on |  | ||||||
| what's changed in the new version.  The fix is a simple change which involves |  | ||||||
| adding a single rotate in the initial expansion function.  It is unknown |  | ||||||
| whether this is an optimal solution to the problem which was discovered in the |  | ||||||
| SHA or whether it's simply a bandaid which fixes the problem with a minimum of |  | ||||||
| effort (for example the reengineering of a great many Capstone chips). |  | ||||||
| */ |  | ||||||
| 
 |  | ||||||
| #include "sha1.h" |  | ||||||
| 
 |  | ||||||
| #include <string.h> |  | ||||||
| 
 |  | ||||||
| void sha_copy(struct SHA_CTX *dest, struct SHA_CTX *src) |  | ||||||
| { |  | ||||||
|   unsigned int i; |  | ||||||
| 
 |  | ||||||
|   dest->count_l=src->count_l; |  | ||||||
|   dest->count_h=src->count_h; |  | ||||||
|   for(i=0; i<SHA_DIGESTLEN; i++) |  | ||||||
|     dest->digest[i]=src->digest[i]; |  | ||||||
|   for(i=0; i < src->index; i++) |  | ||||||
|     dest->block[i] = src->block[i]; |  | ||||||
|   dest->index = src->index; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| /* The SHA f()-functions.  The f1 and f3 functions can be optimized to
 |  | ||||||
|    save one boolean operation each - thanks to Rich Schroeppel, |  | ||||||
|    rcs@cs.arizona.edu for discovering this */ |  | ||||||
| 
 |  | ||||||
| /*#define f1(x,y,z) ( ( x & y ) | ( ~x & z ) )          // Rounds  0-19 */ |  | ||||||
| #define f1(x,y,z)   ( z ^ ( x & ( y ^ z ) ) )           /* Rounds  0-19 */ |  | ||||||
| #define f2(x,y,z)   ( x ^ y ^ z )                       /* Rounds 20-39 */ |  | ||||||
| /*#define f3(x,y,z) ( ( x & y ) | ( x & z ) | ( y & z ) )   // Rounds 40-59 */ |  | ||||||
| #define f3(x,y,z)   ( ( x & y ) | ( z & ( x | y ) ) )   /* Rounds 40-59 */ |  | ||||||
| #define f4(x,y,z)   ( x ^ y ^ z )                       /* Rounds 60-79 */ |  | ||||||
| 
 |  | ||||||
| /* The SHA Mysterious Constants */ |  | ||||||
| 
 |  | ||||||
| #define K1  0x5A827999L                                 /* Rounds  0-19 */ |  | ||||||
| #define K2  0x6ED9EBA1L                                 /* Rounds 20-39 */ |  | ||||||
| #define K3  0x8F1BBCDCL                                 /* Rounds 40-59 */ |  | ||||||
| #define K4  0xCA62C1D6L                                 /* Rounds 60-79 */ |  | ||||||
| 
 |  | ||||||
| /* SHA initial values */ |  | ||||||
| 
 |  | ||||||
| #define h0init  0x67452301L |  | ||||||
| #define h1init  0xEFCDAB89L |  | ||||||
| #define h2init  0x98BADCFEL |  | ||||||
| #define h3init  0x10325476L |  | ||||||
| #define h4init  0xC3D2E1F0L |  | ||||||
| 
 |  | ||||||
| /* 32-bit rotate left - kludged with shifts */ |  | ||||||
| 
 |  | ||||||
| #define ROTL(n,X)  ( ( (X) << (n) ) | ( (X) >> ( 32 - (n) ) ) ) |  | ||||||
| 
 |  | ||||||
| /* The initial expanding function.  The hash function is defined over an
 |  | ||||||
|    80-word expanded input array W, where the first 16 are copies of the input |  | ||||||
|    data, and the remaining 64 are defined by |  | ||||||
| 
 |  | ||||||
|         W[ i ] = W[ i - 16 ] ^ W[ i - 14 ] ^ W[ i - 8 ] ^ W[ i - 3 ] |  | ||||||
| 
 |  | ||||||
|    This implementation generates these values on the fly in a circular |  | ||||||
|    buffer - thanks to Colin Plumb, colin@nyx10.cs.du.edu for this |  | ||||||
|    optimization. |  | ||||||
| 
 |  | ||||||
|    The updated SHA changes the expanding function by adding a rotate of 1 |  | ||||||
|    bit.  Thanks to Jim Gillogly, jim@rand.org, and an anonymous contributor |  | ||||||
|    for this information */ |  | ||||||
| 
 |  | ||||||
| #define expand(W,i) ( W[ i & 15 ] = \ |  | ||||||
| 		      ROTL( 1, ( W[ i & 15 ] ^ W[ (i - 14) & 15 ] ^ \ |  | ||||||
| 				 W[ (i - 8) & 15 ] ^ W[ (i - 3) & 15 ] ) ) ) |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| /* The prototype SHA sub-round.  The fundamental sub-round is:
 |  | ||||||
| 
 |  | ||||||
|         a' = e + ROTL( 5, a ) + f( b, c, d ) + k + data; |  | ||||||
|         b' = a; |  | ||||||
|         c' = ROTL( 30, b ); |  | ||||||
|         d' = c; |  | ||||||
|         e' = d; |  | ||||||
| 
 |  | ||||||
|    but this is implemented by unrolling the loop 5 times and renaming the |  | ||||||
|    variables ( e, a, b, c, d ) = ( a', b', c', d', e' ) each iteration. |  | ||||||
|    This code is then replicated 20 times for each of the 4 functions, using |  | ||||||
|    the next 20 values from the W[] array each time */ |  | ||||||
| 
 |  | ||||||
| #define subRound(a, b, c, d, e, f, k, data) \ |  | ||||||
|     ( e += ROTL( 5, a ) + f( b, c, d ) + k + data, b = ROTL( 30, b ) ) |  | ||||||
| 
 |  | ||||||
| /* Initialize the SHA values */ |  | ||||||
| 
 |  | ||||||
| void SHA1_Init(struct SHA_CTX *ctx) |  | ||||||
| { |  | ||||||
|   /* Set the h-vars to their initial values */ |  | ||||||
|   ctx->digest[ 0 ] = h0init; |  | ||||||
|   ctx->digest[ 1 ] = h1init; |  | ||||||
|   ctx->digest[ 2 ] = h2init; |  | ||||||
|   ctx->digest[ 3 ] = h3init; |  | ||||||
|   ctx->digest[ 4 ] = h4init; |  | ||||||
| 
 |  | ||||||
|   /* Initialize bit count */ |  | ||||||
|   ctx->count_l = ctx->count_h = 0; |  | ||||||
|    |  | ||||||
|   /* Initialize buffer */ |  | ||||||
|   ctx->index = 0; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| /* Perform the SHA transformation.  Note that this code, like MD5, seems to
 |  | ||||||
|    break some optimizing compilers due to the complexity of the expressions |  | ||||||
|    and the size of the basic block.  It may be necessary to split it into |  | ||||||
|    sections, e.g. based on the four subrounds |  | ||||||
| 
 |  | ||||||
|    Note that this function destroys the data area */ |  | ||||||
| 
 |  | ||||||
| static void sha_transform(struct SHA_CTX *ctx, uint32_t *data ) |  | ||||||
| { |  | ||||||
|   uint32_t A, B, C, D, E;     /* Local vars */ |  | ||||||
| 
 |  | ||||||
|   /* Set up first buffer and local data buffer */ |  | ||||||
|   A = ctx->digest[0]; |  | ||||||
|   B = ctx->digest[1]; |  | ||||||
|   C = ctx->digest[2]; |  | ||||||
|   D = ctx->digest[3]; |  | ||||||
|   E = ctx->digest[4]; |  | ||||||
| 
 |  | ||||||
|   /* Heavy mangling, in 4 sub-rounds of 20 interations each. */ |  | ||||||
|   subRound( A, B, C, D, E, f1, K1, data[ 0] ); |  | ||||||
|   subRound( E, A, B, C, D, f1, K1, data[ 1] ); |  | ||||||
|   subRound( D, E, A, B, C, f1, K1, data[ 2] ); |  | ||||||
|   subRound( C, D, E, A, B, f1, K1, data[ 3] ); |  | ||||||
|   subRound( B, C, D, E, A, f1, K1, data[ 4] ); |  | ||||||
|   subRound( A, B, C, D, E, f1, K1, data[ 5] ); |  | ||||||
|   subRound( E, A, B, C, D, f1, K1, data[ 6] ); |  | ||||||
|   subRound( D, E, A, B, C, f1, K1, data[ 7] ); |  | ||||||
|   subRound( C, D, E, A, B, f1, K1, data[ 8] ); |  | ||||||
|   subRound( B, C, D, E, A, f1, K1, data[ 9] ); |  | ||||||
|   subRound( A, B, C, D, E, f1, K1, data[10] ); |  | ||||||
|   subRound( E, A, B, C, D, f1, K1, data[11] ); |  | ||||||
|   subRound( D, E, A, B, C, f1, K1, data[12] ); |  | ||||||
|   subRound( C, D, E, A, B, f1, K1, data[13] ); |  | ||||||
|   subRound( B, C, D, E, A, f1, K1, data[14] ); |  | ||||||
|   subRound( A, B, C, D, E, f1, K1, data[15] ); |  | ||||||
|   subRound( E, A, B, C, D, f1, K1, expand( data, 16 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f1, K1, expand( data, 17 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f1, K1, expand( data, 18 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f1, K1, expand( data, 19 ) ); |  | ||||||
| 
 |  | ||||||
|   subRound( A, B, C, D, E, f2, K2, expand( data, 20 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f2, K2, expand( data, 21 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f2, K2, expand( data, 22 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f2, K2, expand( data, 23 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f2, K2, expand( data, 24 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f2, K2, expand( data, 25 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f2, K2, expand( data, 26 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f2, K2, expand( data, 27 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f2, K2, expand( data, 28 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f2, K2, expand( data, 29 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f2, K2, expand( data, 30 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f2, K2, expand( data, 31 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f2, K2, expand( data, 32 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f2, K2, expand( data, 33 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f2, K2, expand( data, 34 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f2, K2, expand( data, 35 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f2, K2, expand( data, 36 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f2, K2, expand( data, 37 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f2, K2, expand( data, 38 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f2, K2, expand( data, 39 ) ); |  | ||||||
| 
 |  | ||||||
|   subRound( A, B, C, D, E, f3, K3, expand( data, 40 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f3, K3, expand( data, 41 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f3, K3, expand( data, 42 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f3, K3, expand( data, 43 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f3, K3, expand( data, 44 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f3, K3, expand( data, 45 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f3, K3, expand( data, 46 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f3, K3, expand( data, 47 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f3, K3, expand( data, 48 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f3, K3, expand( data, 49 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f3, K3, expand( data, 50 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f3, K3, expand( data, 51 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f3, K3, expand( data, 52 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f3, K3, expand( data, 53 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f3, K3, expand( data, 54 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f3, K3, expand( data, 55 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f3, K3, expand( data, 56 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f3, K3, expand( data, 57 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f3, K3, expand( data, 58 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f3, K3, expand( data, 59 ) ); |  | ||||||
| 
 |  | ||||||
|   subRound( A, B, C, D, E, f4, K4, expand( data, 60 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f4, K4, expand( data, 61 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f4, K4, expand( data, 62 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f4, K4, expand( data, 63 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f4, K4, expand( data, 64 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f4, K4, expand( data, 65 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f4, K4, expand( data, 66 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f4, K4, expand( data, 67 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f4, K4, expand( data, 68 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f4, K4, expand( data, 69 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f4, K4, expand( data, 70 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f4, K4, expand( data, 71 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f4, K4, expand( data, 72 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f4, K4, expand( data, 73 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f4, K4, expand( data, 74 ) ); |  | ||||||
|   subRound( A, B, C, D, E, f4, K4, expand( data, 75 ) ); |  | ||||||
|   subRound( E, A, B, C, D, f4, K4, expand( data, 76 ) ); |  | ||||||
|   subRound( D, E, A, B, C, f4, K4, expand( data, 77 ) ); |  | ||||||
|   subRound( C, D, E, A, B, f4, K4, expand( data, 78 ) ); |  | ||||||
|   subRound( B, C, D, E, A, f4, K4, expand( data, 79 ) ); |  | ||||||
| 
 |  | ||||||
|   /* Build message digest */ |  | ||||||
|   ctx->digest[0] += A; |  | ||||||
|   ctx->digest[1] += B; |  | ||||||
|   ctx->digest[2] += C; |  | ||||||
|   ctx->digest[3] += D; |  | ||||||
|   ctx->digest[4] += E; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| #if 1 |  | ||||||
| 
 |  | ||||||
| #ifndef EXTRACT_UCHAR |  | ||||||
| #define EXTRACT_UCHAR(p)  (*(unsigned char *)(p)) |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| #define STRING2INT(s) ((((((EXTRACT_UCHAR(s) << 8)    \ |  | ||||||
| 			 | EXTRACT_UCHAR(s+1)) << 8)  \ |  | ||||||
| 			 | EXTRACT_UCHAR(s+2)) << 8)  \ |  | ||||||
| 			 | EXTRACT_UCHAR(s+3)) |  | ||||||
| #else |  | ||||||
| uint32_t STRING2INT(unsigned char *s) |  | ||||||
| { |  | ||||||
|   uint32_t r; |  | ||||||
|   unsigned int i; |  | ||||||
|    |  | ||||||
|   for (i = 0, r = 0; i < 4; i++, s++) |  | ||||||
|     r = (r << 8) | *s; |  | ||||||
|   return r; |  | ||||||
| } |  | ||||||
| #endif |  | ||||||
| 
 |  | ||||||
| static void sha_block(struct SHA_CTX *ctx, const unsigned char *block) |  | ||||||
| { |  | ||||||
|   uint32_t data[SHA_DATALEN]; |  | ||||||
|   unsigned int i; |  | ||||||
|    |  | ||||||
|   /* Update block count */ |  | ||||||
|   if (!++ctx->count_l) |  | ||||||
|     ++ctx->count_h; |  | ||||||
| 
 |  | ||||||
|   /* Endian independent conversion */ |  | ||||||
|   for (i = 0; i<SHA_DATALEN; i++, block += 4) |  | ||||||
|     data[i] = STRING2INT(block); |  | ||||||
| 
 |  | ||||||
|   sha_transform(ctx, data); |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| void SHA1_Update(struct SHA_CTX *ctx, const unsigned char *buffer, uint32_t len) |  | ||||||
| { |  | ||||||
|   if (ctx->index) |  | ||||||
|     { /* Try to fill partial block */ |  | ||||||
|       unsigned left = SHA_DATASIZE - ctx->index; |  | ||||||
|       if (len < left) |  | ||||||
| 	{ |  | ||||||
| 	  memcpy(ctx->block + ctx->index, buffer, len); |  | ||||||
| 	  ctx->index += len; |  | ||||||
| 	  return; /* Finished */ |  | ||||||
| 	} |  | ||||||
|       else |  | ||||||
| 	{ |  | ||||||
| 	  memcpy(ctx->block + ctx->index, buffer, left); |  | ||||||
| 	  sha_block(ctx, ctx->block); |  | ||||||
| 	  buffer += left; |  | ||||||
| 	  len -= left; |  | ||||||
| 	} |  | ||||||
|     } |  | ||||||
|   while (len >= SHA_DATASIZE) |  | ||||||
|     { |  | ||||||
|       sha_block(ctx, buffer); |  | ||||||
|       buffer += SHA_DATASIZE; |  | ||||||
|       len -= SHA_DATASIZE; |  | ||||||
|     } |  | ||||||
|   if ((ctx->index = len))     /* This assignment is intended */ |  | ||||||
|     /* Buffer leftovers */ |  | ||||||
|     memcpy(ctx->block, buffer, len); |  | ||||||
| } |  | ||||||
| 	   |  | ||||||
| /* Final wrapup - pad to SHA_DATASIZE-byte boundary with the bit pattern
 |  | ||||||
|    1 0* (64-bit count of bits processed, MSB-first) */ |  | ||||||
| 
 |  | ||||||
| void SHA1_Final(unsigned char *s, struct SHA_CTX *ctx) |  | ||||||
| { |  | ||||||
|   uint32_t data[SHA_DATALEN]; |  | ||||||
|   unsigned int i; |  | ||||||
|   unsigned int words; |  | ||||||
|    |  | ||||||
|   i = ctx->index; |  | ||||||
|   /* Set the first char of padding to 0x80.  This is safe since there is
 |  | ||||||
|      always at least one byte free */ |  | ||||||
|   ctx->block[i++] = 0x80; |  | ||||||
| 
 |  | ||||||
|   /* Fill rest of word */ |  | ||||||
|   for( ; i & 3; i++) |  | ||||||
|     ctx->block[i] = 0; |  | ||||||
| 
 |  | ||||||
|   /* i is now a multiple of the word size 4 */ |  | ||||||
|   words = i >> 2; |  | ||||||
|   for (i = 0; i < words; i++) |  | ||||||
|     data[i] = STRING2INT(ctx->block + 4*i); |  | ||||||
|    |  | ||||||
|   if (words > (SHA_DATALEN-2)) |  | ||||||
|     { /* No room for length in this block. Process it and
 |  | ||||||
|        * pad with another one */ |  | ||||||
|       for (i = words ; i < SHA_DATALEN; i++) |  | ||||||
| 	data[i] = 0; |  | ||||||
|       sha_transform(ctx, data); |  | ||||||
|       for (i = 0; i < (SHA_DATALEN-2); i++) |  | ||||||
| 	data[i] = 0; |  | ||||||
|     } |  | ||||||
|   else |  | ||||||
|     for (i = words ; i < SHA_DATALEN - 2; i++) |  | ||||||
|       data[i] = 0; |  | ||||||
|   /* Theres 512 = 2^9 bits in one block */ |  | ||||||
|   data[SHA_DATALEN-2] = (ctx->count_h << 9) | (ctx->count_l >> 23); |  | ||||||
|   data[SHA_DATALEN-1] = (ctx->count_l << 9) | (ctx->index << 3); |  | ||||||
|   sha_transform(ctx, data); |  | ||||||
|   sha_digest(ctx, s); |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| void sha_digest(struct SHA_CTX *ctx, unsigned char *s) |  | ||||||
| { |  | ||||||
|   unsigned int i; |  | ||||||
| 
 |  | ||||||
|   for (i = 0; i < SHA_DIGESTLEN; i++) |  | ||||||
|     { |  | ||||||
|       *s++ =         ctx->digest[i] >> 24; |  | ||||||
|       *s++ = 0xff & (ctx->digest[i] >> 16); |  | ||||||
|       *s++ = 0xff & (ctx->digest[i] >> 8); |  | ||||||
|       *s++ = 0xff &  ctx->digest[i]; |  | ||||||
|     } |  | ||||||
| } |  | ||||||
|  | @ -1,28 +0,0 @@ | ||||||
| #ifndef _SHA_H |  | ||||||
| #define _SHA_H |  | ||||||
| 
 |  | ||||||
| #include <inttypes.h> |  | ||||||
| 
 |  | ||||||
| /* The SHA block size and message digest sizes, in bytes */ |  | ||||||
| 
 |  | ||||||
| #define SHA_DATASIZE    64 |  | ||||||
| #define SHA_DATALEN     16 |  | ||||||
| #define SHA_DIGESTSIZE  20 |  | ||||||
| #define SHA_DIGESTLEN    5 |  | ||||||
| /* The structure for storing SHA info */ |  | ||||||
| 
 |  | ||||||
| struct SHA_CTX { |  | ||||||
|   uint32_t digest[SHA_DIGESTLEN];  /* Message digest */ |  | ||||||
|   uint32_t count_l, count_h;       /* 64-bit block count */ |  | ||||||
|   uint8_t block[SHA_DATASIZE];     /* SHA data buffer */ |  | ||||||
|   unsigned int index;            /* index into buffer */ |  | ||||||
| }; |  | ||||||
| 
 |  | ||||||
| void SHA1_Init(struct SHA_CTX *ctx); |  | ||||||
| void SHA1_Update(struct SHA_CTX *ctx, const unsigned char *buffer, uint32_t len); |  | ||||||
| void SHA1_Final(unsigned char *s, struct SHA_CTX *ctx); |  | ||||||
| void sha_digest(struct SHA_CTX *ctx, unsigned char *s); |  | ||||||
| void sha_copy(struct SHA_CTX *dest, struct SHA_CTX *src); |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| #endif /* !_SHA_H */ |  | ||||||
|  | @ -1,238 +0,0 @@ | ||||||
| /* crypto/sha/sha256.c */ |  | ||||||
| /* ====================================================================
 |  | ||||||
|  * Copyright (c) 2004 The OpenSSL Project.  All rights reserved |  | ||||||
|  * according to the OpenSSL license [found in ./md32_common.h]. |  | ||||||
|  * ==================================================================== |  | ||||||
|  */ |  | ||||||
| 
 |  | ||||||
| #include <stdlib.h> |  | ||||||
| #include <string.h> |  | ||||||
| 
 |  | ||||||
| #include "sha256.h" |  | ||||||
| 
 |  | ||||||
| int SHA224_Init (SHA256_CTX *c) |  | ||||||
| 	{ |  | ||||||
| 	c->h[0]=0xc1059ed8UL;	c->h[1]=0x367cd507UL; |  | ||||||
| 	c->h[2]=0x3070dd17UL;	c->h[3]=0xf70e5939UL; |  | ||||||
| 	c->h[4]=0xffc00b31UL;	c->h[5]=0x68581511UL; |  | ||||||
| 	c->h[6]=0x64f98fa7UL;	c->h[7]=0xbefa4fa4UL; |  | ||||||
| 	c->Nl=0;	c->Nh=0; |  | ||||||
| 	c->num=0;	c->md_len=SHA224_DIGEST_LENGTH; |  | ||||||
| 	return 1; |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| int SHA256_Init (SHA256_CTX *c) |  | ||||||
| 	{ |  | ||||||
| 	c->h[0]=0x6a09e667UL;	c->h[1]=0xbb67ae85UL; |  | ||||||
| 	c->h[2]=0x3c6ef372UL;	c->h[3]=0xa54ff53aUL; |  | ||||||
| 	c->h[4]=0x510e527fUL;	c->h[5]=0x9b05688cUL; |  | ||||||
| 	c->h[6]=0x1f83d9abUL;	c->h[7]=0x5be0cd19UL; |  | ||||||
| 	c->Nl=0;	c->Nh=0; |  | ||||||
| 	c->num=0;	c->md_len=SHA256_DIGEST_LENGTH; |  | ||||||
| 	return 1; |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| unsigned char *SHA224(const unsigned char *d, size_t n, unsigned char *md) |  | ||||||
| 	{ |  | ||||||
| 	SHA256_CTX c; |  | ||||||
| 	static unsigned char m[SHA224_DIGEST_LENGTH]; |  | ||||||
| 
 |  | ||||||
| 	if (md == NULL) md=m; |  | ||||||
| 	SHA224_Init(&c); |  | ||||||
| 	SHA256_Update(&c,d,n); |  | ||||||
| 	SHA256_Final(md,&c); |  | ||||||
| 	return(md); |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| unsigned char *SHA256(const unsigned char *d, size_t n, unsigned char *md) |  | ||||||
| 	{ |  | ||||||
| 	SHA256_CTX c; |  | ||||||
| 	static unsigned char m[SHA256_DIGEST_LENGTH]; |  | ||||||
| 
 |  | ||||||
| 	if (md == NULL) md=m; |  | ||||||
| 	SHA256_Init(&c); |  | ||||||
| 	SHA256_Update(&c,d,n); |  | ||||||
| 	SHA256_Final(md,&c); |  | ||||||
| 	return(md); |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| int SHA224_Update(SHA256_CTX *c, const void *data, size_t len) |  | ||||||
| {   return SHA256_Update (c,data,len);   } |  | ||||||
| int SHA224_Final (unsigned char *md, SHA256_CTX *c) |  | ||||||
| {   return SHA256_Final (md,c);   } |  | ||||||
| 
 |  | ||||||
| #define	DATA_ORDER_IS_BIG_ENDIAN |  | ||||||
| 
 |  | ||||||
| #define	HASH_LONG		uint32_t |  | ||||||
| #define	HASH_LONG_LOG2		2 |  | ||||||
| #define	HASH_CTX		SHA256_CTX |  | ||||||
| #define	HASH_CBLOCK		SHA_CBLOCK |  | ||||||
| #define	HASH_LBLOCK		SHA_LBLOCK |  | ||||||
| /*
 |  | ||||||
|  * Note that FIPS180-2 discusses "Truncation of the Hash Function Output." |  | ||||||
|  * default: case below covers for it. It's not clear however if it's |  | ||||||
|  * permitted to truncate to amount of bytes not divisible by 4. I bet not, |  | ||||||
|  * but if it is, then default: case shall be extended. For reference. |  | ||||||
|  * Idea behind separate cases for pre-defined lenghts is to let the |  | ||||||
|  * compiler decide if it's appropriate to unroll small loops. |  | ||||||
|  */ |  | ||||||
| #define	HASH_MAKE_STRING(c,s)	do {	\ |  | ||||||
| 	unsigned long ll;		\ |  | ||||||
| 	unsigned int  n;		\ |  | ||||||
| 	switch ((c)->md_len)		\ |  | ||||||
| 	{   case SHA224_DIGEST_LENGTH:	\ |  | ||||||
| 		for (n=0;n<SHA224_DIGEST_LENGTH/4;n++)	\ |  | ||||||
| 		{   ll=(c)->h[n]; HOST_l2c(ll,(s));   }	\ |  | ||||||
| 		break;			\ |  | ||||||
| 	    case SHA256_DIGEST_LENGTH:	\ |  | ||||||
| 		for (n=0;n<SHA256_DIGEST_LENGTH/4;n++)	\ |  | ||||||
| 		{   ll=(c)->h[n]; HOST_l2c(ll,(s));   }	\ |  | ||||||
| 		break;			\ |  | ||||||
| 	    default:			\ |  | ||||||
| 		if ((c)->md_len > SHA256_DIGEST_LENGTH)	\ |  | ||||||
| 		    return 0;				\ |  | ||||||
| 		for (n=0;n<(c)->md_len/4;n++)		\ |  | ||||||
| 		{   ll=(c)->h[n]; HOST_l2c(ll,(s));   }	\ |  | ||||||
| 		break;			\ |  | ||||||
| 	}				\ |  | ||||||
| 	} while (0) |  | ||||||
| 
 |  | ||||||
| #define	HASH_UPDATE		SHA256_Update |  | ||||||
| #define	HASH_TRANSFORM		SHA256_Transform |  | ||||||
| #define	HASH_FINAL		SHA256_Final |  | ||||||
| #define	HASH_BLOCK_HOST_ORDER	sha256_block_host_order |  | ||||||
| #define	HASH_BLOCK_DATA_ORDER	sha256_block_data_order |  | ||||||
| void sha256_block_host_order (SHA256_CTX *ctx, const void *in, size_t num); |  | ||||||
| void sha256_block_data_order (SHA256_CTX *ctx, const void *in, size_t num); |  | ||||||
| 
 |  | ||||||
| #include "md32_common.h" |  | ||||||
| 
 |  | ||||||
| static const uint32_t K256[64] = { |  | ||||||
| 	0x428a2f98UL,0x71374491UL,0xb5c0fbcfUL,0xe9b5dba5UL, |  | ||||||
| 	0x3956c25bUL,0x59f111f1UL,0x923f82a4UL,0xab1c5ed5UL, |  | ||||||
| 	0xd807aa98UL,0x12835b01UL,0x243185beUL,0x550c7dc3UL, |  | ||||||
| 	0x72be5d74UL,0x80deb1feUL,0x9bdc06a7UL,0xc19bf174UL, |  | ||||||
| 	0xe49b69c1UL,0xefbe4786UL,0x0fc19dc6UL,0x240ca1ccUL, |  | ||||||
| 	0x2de92c6fUL,0x4a7484aaUL,0x5cb0a9dcUL,0x76f988daUL, |  | ||||||
| 	0x983e5152UL,0xa831c66dUL,0xb00327c8UL,0xbf597fc7UL, |  | ||||||
| 	0xc6e00bf3UL,0xd5a79147UL,0x06ca6351UL,0x14292967UL, |  | ||||||
| 	0x27b70a85UL,0x2e1b2138UL,0x4d2c6dfcUL,0x53380d13UL, |  | ||||||
| 	0x650a7354UL,0x766a0abbUL,0x81c2c92eUL,0x92722c85UL, |  | ||||||
| 	0xa2bfe8a1UL,0xa81a664bUL,0xc24b8b70UL,0xc76c51a3UL, |  | ||||||
| 	0xd192e819UL,0xd6990624UL,0xf40e3585UL,0x106aa070UL, |  | ||||||
| 	0x19a4c116UL,0x1e376c08UL,0x2748774cUL,0x34b0bcb5UL, |  | ||||||
| 	0x391c0cb3UL,0x4ed8aa4aUL,0x5b9cca4fUL,0x682e6ff3UL, |  | ||||||
| 	0x748f82eeUL,0x78a5636fUL,0x84c87814UL,0x8cc70208UL, |  | ||||||
| 	0x90befffaUL,0xa4506cebUL,0xbef9a3f7UL,0xc67178f2UL }; |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * FIPS specification refers to right rotations, while our ROTATE macro |  | ||||||
|  * is left one. This is why you might notice that rotation coefficients |  | ||||||
|  * differ from those observed in FIPS document by 32-N... |  | ||||||
|  */ |  | ||||||
| #define Sigma0(x)	(ROTATE((x),30) ^ ROTATE((x),19) ^ ROTATE((x),10)) |  | ||||||
| #define Sigma1(x)	(ROTATE((x),26) ^ ROTATE((x),21) ^ ROTATE((x),7)) |  | ||||||
| #define sigma0(x)	(ROTATE((x),25) ^ ROTATE((x),14) ^ ((x)>>3)) |  | ||||||
| #define sigma1(x)	(ROTATE((x),15) ^ ROTATE((x),13) ^ ((x)>>10)) |  | ||||||
| 
 |  | ||||||
| #define Ch(x,y,z)	(((x) & (y)) ^ ((~(x)) & (z))) |  | ||||||
| #define Maj(x,y,z)	(((x) & (y)) ^ ((x) & (z)) ^ ((y) & (z))) |  | ||||||
| 
 |  | ||||||
| #define	ROUND_00_15(i,a,b,c,d,e,f,g,h)		do {	\ |  | ||||||
| 	T1 += h + Sigma1(e) + Ch(e,f,g) + K256[i];	\ |  | ||||||
| 	h = Sigma0(a) + Maj(a,b,c);			\ |  | ||||||
| 	d += T1;	h += T1;		} while (0) |  | ||||||
| 
 |  | ||||||
| #define	ROUND_16_63(i,a,b,c,d,e,f,g,h,X)	do {	\ |  | ||||||
| 	s0 = X[(i+1)&0x0f];	s0 = sigma0(s0);	\ |  | ||||||
| 	s1 = X[(i+14)&0x0f];	s1 = sigma1(s1);	\ |  | ||||||
| 	T1 = X[(i)&0x0f] += s0 + s1 + X[(i+9)&0x0f];	\ |  | ||||||
| 	ROUND_00_15(i,a,b,c,d,e,f,g,h);		} while (0) |  | ||||||
| 
 |  | ||||||
| static void sha256_block (SHA256_CTX *ctx, const void *in, size_t num, int host) |  | ||||||
| 	{ |  | ||||||
| 	uint32_t a,b,c,d,e,f,g,h,s0,s1,T1; |  | ||||||
| 	uint32_t	X[16]; |  | ||||||
| 	int i; |  | ||||||
| 	const unsigned char *data=in; |  | ||||||
| 
 |  | ||||||
| 			while (num--) { |  | ||||||
| 
 |  | ||||||
| 	a = ctx->h[0];	b = ctx->h[1];	c = ctx->h[2];	d = ctx->h[3]; |  | ||||||
| 	e = ctx->h[4];	f = ctx->h[5];	g = ctx->h[6];	h = ctx->h[7]; |  | ||||||
| 
 |  | ||||||
| 	if (host) |  | ||||||
| 		{ |  | ||||||
| 		const uint32_t *W=(const uint32_t *)data; |  | ||||||
| 
 |  | ||||||
| 		T1 = X[0] = W[0];	ROUND_00_15(0,a,b,c,d,e,f,g,h); |  | ||||||
| 		T1 = X[1] = W[1];	ROUND_00_15(1,h,a,b,c,d,e,f,g); |  | ||||||
| 		T1 = X[2] = W[2];	ROUND_00_15(2,g,h,a,b,c,d,e,f); |  | ||||||
| 		T1 = X[3] = W[3];	ROUND_00_15(3,f,g,h,a,b,c,d,e); |  | ||||||
| 		T1 = X[4] = W[4];	ROUND_00_15(4,e,f,g,h,a,b,c,d); |  | ||||||
| 		T1 = X[5] = W[5];	ROUND_00_15(5,d,e,f,g,h,a,b,c); |  | ||||||
| 		T1 = X[6] = W[6];	ROUND_00_15(6,c,d,e,f,g,h,a,b); |  | ||||||
| 		T1 = X[7] = W[7];	ROUND_00_15(7,b,c,d,e,f,g,h,a); |  | ||||||
| 		T1 = X[8] = W[8];	ROUND_00_15(8,a,b,c,d,e,f,g,h); |  | ||||||
| 		T1 = X[9] = W[9];	ROUND_00_15(9,h,a,b,c,d,e,f,g); |  | ||||||
| 		T1 = X[10] = W[10];	ROUND_00_15(10,g,h,a,b,c,d,e,f); |  | ||||||
| 		T1 = X[11] = W[11];	ROUND_00_15(11,f,g,h,a,b,c,d,e); |  | ||||||
| 		T1 = X[12] = W[12];	ROUND_00_15(12,e,f,g,h,a,b,c,d); |  | ||||||
| 		T1 = X[13] = W[13];	ROUND_00_15(13,d,e,f,g,h,a,b,c); |  | ||||||
| 		T1 = X[14] = W[14];	ROUND_00_15(14,c,d,e,f,g,h,a,b); |  | ||||||
| 		T1 = X[15] = W[15];	ROUND_00_15(15,b,c,d,e,f,g,h,a); |  | ||||||
| 
 |  | ||||||
| 		data += SHA256_CBLOCK; |  | ||||||
| 		} |  | ||||||
| 	else |  | ||||||
| 		{ |  | ||||||
| 		uint32_t l; |  | ||||||
| 
 |  | ||||||
| 		HOST_c2l(data,l); T1 = X[0] = l;  ROUND_00_15(0,a,b,c,d,e,f,g,h); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[1] = l;  ROUND_00_15(1,h,a,b,c,d,e,f,g); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[2] = l;  ROUND_00_15(2,g,h,a,b,c,d,e,f); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[3] = l;  ROUND_00_15(3,f,g,h,a,b,c,d,e); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[4] = l;  ROUND_00_15(4,e,f,g,h,a,b,c,d); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[5] = l;  ROUND_00_15(5,d,e,f,g,h,a,b,c); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[6] = l;  ROUND_00_15(6,c,d,e,f,g,h,a,b); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[7] = l;  ROUND_00_15(7,b,c,d,e,f,g,h,a); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[8] = l;  ROUND_00_15(8,a,b,c,d,e,f,g,h); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[9] = l;  ROUND_00_15(9,h,a,b,c,d,e,f,g); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[10] = l; ROUND_00_15(10,g,h,a,b,c,d,e,f); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[11] = l; ROUND_00_15(11,f,g,h,a,b,c,d,e); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[12] = l; ROUND_00_15(12,e,f,g,h,a,b,c,d); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[13] = l; ROUND_00_15(13,d,e,f,g,h,a,b,c); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[14] = l; ROUND_00_15(14,c,d,e,f,g,h,a,b); |  | ||||||
| 		HOST_c2l(data,l); T1 = X[15] = l; ROUND_00_15(15,b,c,d,e,f,g,h,a); |  | ||||||
| 		} |  | ||||||
| 
 |  | ||||||
| 	for (i=16;i<64;i+=8) |  | ||||||
| 		{ |  | ||||||
| 		ROUND_16_63(i+0,a,b,c,d,e,f,g,h,X); |  | ||||||
| 		ROUND_16_63(i+1,h,a,b,c,d,e,f,g,X); |  | ||||||
| 		ROUND_16_63(i+2,g,h,a,b,c,d,e,f,X); |  | ||||||
| 		ROUND_16_63(i+3,f,g,h,a,b,c,d,e,X); |  | ||||||
| 		ROUND_16_63(i+4,e,f,g,h,a,b,c,d,X); |  | ||||||
| 		ROUND_16_63(i+5,d,e,f,g,h,a,b,c,X); |  | ||||||
| 		ROUND_16_63(i+6,c,d,e,f,g,h,a,b,X); |  | ||||||
| 		ROUND_16_63(i+7,b,c,d,e,f,g,h,a,X); |  | ||||||
| 		} |  | ||||||
| 
 |  | ||||||
| 	ctx->h[0] += a;	ctx->h[1] += b;	ctx->h[2] += c;	ctx->h[3] += d; |  | ||||||
| 	ctx->h[4] += e;	ctx->h[5] += f;	ctx->h[6] += g;	ctx->h[7] += h; |  | ||||||
| 
 |  | ||||||
| 			} |  | ||||||
| 	} |  | ||||||
| 
 |  | ||||||
| /*
 |  | ||||||
|  * Idea is to trade couple of cycles for some space. On IA-32 we save |  | ||||||
|  * about 4K in "big footprint" case. In "small footprint" case any gain |  | ||||||
|  * is appreciated:-) |  | ||||||
|  */ |  | ||||||
| void HASH_BLOCK_HOST_ORDER (SHA256_CTX *ctx, const void *in, size_t num) |  | ||||||
| {   sha256_block (ctx,in,num,1);   } |  | ||||||
| 
 |  | ||||||
| void HASH_BLOCK_DATA_ORDER (SHA256_CTX *ctx, const void *in, size_t num) |  | ||||||
| {   sha256_block (ctx,in,num,0);   } |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
|  | @ -1,35 +0,0 @@ | ||||||
| #ifndef _SHA256_H |  | ||||||
| #define _SHA256_H 1 |  | ||||||
| 
 |  | ||||||
| #include <inttypes.h> |  | ||||||
| 
 |  | ||||||
| #define SHA_LBLOCK	16 |  | ||||||
| #define SHA_CBLOCK	(SHA_LBLOCK*4)	/* SHA treats input data as a |  | ||||||
| 					 * contiguous array of 32 bit |  | ||||||
| 					 * wide big-endian values. */ |  | ||||||
| 
 |  | ||||||
| #define SHA256_CBLOCK	(SHA_LBLOCK*4)	/* SHA-256 treats input data as a |  | ||||||
| 					 * contiguous array of 32 bit |  | ||||||
| 					 * wide big-endian values. */ |  | ||||||
| #define SHA224_DIGEST_LENGTH	28 |  | ||||||
| #define SHA256_DIGEST_LENGTH	32 |  | ||||||
| 
 |  | ||||||
| typedef struct SHA256state_st |  | ||||||
| 	{ |  | ||||||
| 	uint32_t h[8]; |  | ||||||
| 	uint32_t Nl,Nh; |  | ||||||
| 	uint32_t data[SHA_LBLOCK]; |  | ||||||
| 	unsigned int num,md_len; |  | ||||||
| 	} SHA256_CTX; |  | ||||||
| 
 |  | ||||||
| int SHA224_Init(SHA256_CTX *c); |  | ||||||
| int SHA224_Update(SHA256_CTX *c, const void *data, size_t len); |  | ||||||
| int SHA224_Final(unsigned char *md, SHA256_CTX *c); |  | ||||||
| unsigned char *SHA224(const unsigned char *d, size_t n,unsigned char *md); |  | ||||||
| int SHA256_Init(SHA256_CTX *c); |  | ||||||
| int SHA256_Update(SHA256_CTX *c, const void *data, size_t len); |  | ||||||
| int SHA256_Final(unsigned char *md, SHA256_CTX *c); |  | ||||||
| unsigned char *SHA256(const unsigned char *d, size_t n,unsigned char *md); |  | ||||||
| void SHA256_Transform(SHA256_CTX *c, const unsigned char *data); |  | ||||||
| 
 |  | ||||||
| #endif |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue