zynq_lvgl/sw/swss/zynq_fsbl/md5.c

485 lines
14 KiB
C
Raw Normal View History

2024-10-20 23:34:36 +08:00
/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
* All rights reserved.
*
* This package is an SSL implementation written
* by Eric Young (eay@cryptsoft.com).
* The implementation was written so as to conform with Netscapes SSL.
*
* This library is free for commercial and non-commercial use as long as
* the following conditions are adhered to. The following conditions
* apply to all code found in this distribution, be it the RC4, RSA,
* lhash, DES, etc., code; not just the SSL code. The SSL documentation
* included with this distribution is covered by the same copyright terms
* except that the holder is Tim Hudson (tjh@cryptsoft.com).
*
* Copyright remains Eric Young's, and as such any Copyright notices in
* the code are not to be removed.
* If this package is used in a product, Eric Young should be given attribution
* as the author of the parts of the library used.
* This can be in the form of a textual message at program startup or
* in documentation (online or textual) provided with the package.
*
* 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 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 acknowledgement:
* "This product includes cryptographic software written by
* Eric Young (eay@cryptsoft.com)"
* The word 'cryptographic' can be left out if the routines from the library
* being used are not cryptographic related :-).
* 4. If you include any Windows specific code (or a derivative thereof) from
* the apps directory (application code) you must include an acknowledgement:
* "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
*
* THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
* ANY EXPRESS 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 AUTHOR OR 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.
*
* The licence and distribution terms for any publicly available version or
* derivative of this code cannot be changed. i.e. this code cannot simply be
* copied and put under another distribution licence
* [including the GNU Public Licence.]
*/
/*****************************************************************************/
/**
*
* @file md5.c
*
* Contains code to calculate checksum using md5 algorithm
*
* <pre>
* MODIFICATION HISTORY:
*
* Ver Who Date Changes
* ----- ---- -------- -------------------------------------------------------
* 5.00a sgd 05/17/13 Initial release
*
*
* </pre>
*
* @note
*
******************************************************************************/
/****************************** Include Files *********************************/
#include "md5.h"
/******************************************************************************/
/**
*
* This function sets the memory
*
* @param dest
*
* @param ch
*
* @param count
*
* @return None
*
* @note None
*
****************************************************************************/
inline void * MD5Memset( void *dest, int ch, u32 count )
{
register char *dst8 = (char*)dest;
while( count-- )
*dst8++ = ch;
return dest;
}
/******************************************************************************/
/**
*
* This function copy the memory
*
* @param dest
*
* @param ch
*
* @param count
*
* @return None
*
* @note None
*
****************************************************************************/
inline void * MD5Memcpy( void *dest, const void *src,
u32 count, boolean doByteSwap )
{
register char * dst8 = (char*)dest;
register char * src8 = (char*)src;
if( doByteSwap == FALSE ) {
while( count-- )
*dst8++ = *src8++;
} else {
count /= sizeof( u32 );
while( count-- ) {
dst8[ 0 ] = src8[ 3 ];
dst8[ 1 ] = src8[ 2 ];
dst8[ 2 ] = src8[ 1 ];
dst8[ 3 ] = src8[ 0 ];
dst8 += 4;
src8 += 4;
}
}
return dest;
}
/******************************************************************************/
/**
*
* This function is the core of the MD5 algorithm,
* this alters an existing MD5 hash to
* reflect the addition of 16 longwords of new data. MD5Update blocks
* the data and converts bytes into longwords for this routine.
*
* Use binary integer part of the sine of integers (Radians) as constants.
* Calculated as:
*
* for( i = 0; i < 63; i++ )
* k[ i ] := floor( abs( sin( i + 1 ) ) × pow( 2, 32 ) )
*
* Following number is the per-round shift amount.
*
* @param dest
*
* @param ch
*
* @param count
*
* @return None
*
* @note None
*
****************************************************************************/
void MD5Transform( u32 *buffer, u32 *intermediate )
{
register u32 a, b, c, d;
a = buffer[ 0 ];
b = buffer[ 1 ];
c = buffer[ 2 ];
d = buffer[ 3 ];
MD5_STEP( F1, a, b, c, d, intermediate[ 0 ] + 0xd76aa478, 7 );
MD5_STEP( F1, d, a, b, c, intermediate[ 1 ] + 0xe8c7b756, 12 );
MD5_STEP( F1, c, d, a, b, intermediate[ 2 ] + 0x242070db, 17 );
MD5_STEP( F1, b, c, d, a, intermediate[ 3 ] + 0xc1bdceee, 22 );
MD5_STEP( F1, a, b, c, d, intermediate[ 4 ] + 0xf57c0faf, 7 );
MD5_STEP( F1, d, a, b, c, intermediate[ 5 ] + 0x4787c62a, 12 );
MD5_STEP( F1, c, d, a, b, intermediate[ 6 ] + 0xa8304613, 17 );
MD5_STEP( F1, b, c, d, a, intermediate[ 7 ] + 0xfd469501, 22 );
MD5_STEP( F1, a, b, c, d, intermediate[ 8 ] + 0x698098d8, 7 );
MD5_STEP( F1, d, a, b, c, intermediate[ 9 ] + 0x8b44f7af, 12 );
MD5_STEP( F1, c, d, a, b, intermediate[ 10 ] + 0xffff5bb1, 17 );
MD5_STEP( F1, b, c, d, a, intermediate[ 11 ] + 0x895cd7be, 22 );
MD5_STEP( F1, a, b, c, d, intermediate[ 12 ] + 0x6b901122, 7 );
MD5_STEP( F1, d, a, b, c, intermediate[ 13 ] + 0xfd987193, 12 );
MD5_STEP( F1, c, d, a, b, intermediate[ 14 ] + 0xa679438e, 17 );
MD5_STEP( F1, b, c, d, a, intermediate[ 15 ] + 0x49b40821, 22 );
MD5_STEP( F2, a, b, c, d, intermediate[ 1 ] + 0xf61e2562, 5 );
MD5_STEP( F2, d, a, b, c, intermediate[ 6 ] + 0xc040b340, 9 );
MD5_STEP( F2, c, d, a, b, intermediate[ 11 ] + 0x265e5a51, 14 );
MD5_STEP( F2, b, c, d, a, intermediate[ 0 ] + 0xe9b6c7aa, 20 );
MD5_STEP( F2, a, b, c, d, intermediate[ 5 ] + 0xd62f105d, 5 );
MD5_STEP( F2, d, a, b, c, intermediate[ 10 ] + 0x02441453, 9 );
MD5_STEP( F2, c, d, a, b, intermediate[ 15 ] + 0xd8a1e681, 14 );
MD5_STEP( F2, b, c, d, a, intermediate[ 4 ] + 0xe7d3fbc8, 20 );
MD5_STEP( F2, a, b, c, d, intermediate[ 9 ] + 0x21e1cde6, 5 );
MD5_STEP( F2, d, a, b, c, intermediate[ 14 ] + 0xc33707d6, 9 );
MD5_STEP( F2, c, d, a, b, intermediate[ 3 ] + 0xf4d50d87, 14 );
MD5_STEP( F2, b, c, d, a, intermediate[ 8 ] + 0x455a14ed, 20 );
MD5_STEP( F2, a, b, c, d, intermediate[ 13 ] + 0xa9e3e905, 5 );
MD5_STEP( F2, d, a, b, c, intermediate[ 2 ] + 0xfcefa3f8, 9 );
MD5_STEP( F2, c, d, a, b, intermediate[ 7 ] + 0x676f02d9, 14 );
MD5_STEP( F2, b, c, d, a, intermediate[ 12 ] + 0x8d2a4c8a, 20 );
MD5_STEP( F3, a, b, c, d, intermediate[ 5 ] + 0xfffa3942, 4 );
MD5_STEP( F3, d, a, b, c, intermediate[ 8 ] + 0x8771f681, 11 );
MD5_STEP( F3, c, d, a, b, intermediate[ 11 ] + 0x6d9d6122, 16 );
MD5_STEP( F3, b, c, d, a, intermediate[ 14 ] + 0xfde5380c, 23 );
MD5_STEP( F3, a, b, c, d, intermediate[ 1 ] + 0xa4beea44, 4 );
MD5_STEP( F3, d, a, b, c, intermediate[ 4 ] + 0x4bdecfa9, 11 );
MD5_STEP( F3, c, d, a, b, intermediate[ 7 ] + 0xf6bb4b60, 16 );
MD5_STEP( F3, b, c, d, a, intermediate[ 10 ] + 0xbebfbc70, 23 );
MD5_STEP( F3, a, b, c, d, intermediate[ 13 ] + 0x289b7ec6, 4 );
MD5_STEP( F3, d, a, b, c, intermediate[ 0 ] + 0xeaa127fa, 11 );
MD5_STEP( F3, c, d, a, b, intermediate[ 3 ] + 0xd4ef3085, 16 );
MD5_STEP( F3, b, c, d, a, intermediate[ 6 ] + 0x04881d05, 23 );
MD5_STEP( F3, a, b, c, d, intermediate[ 9 ] + 0xd9d4d039, 4 );
MD5_STEP( F3, d, a, b, c, intermediate[ 12 ] + 0xe6db99e5, 11 );
MD5_STEP( F3, c, d, a, b, intermediate[ 15 ] + 0x1fa27cf8, 16 );
MD5_STEP( F3, b, c, d, a, intermediate[ 2 ] + 0xc4ac5665, 23 );
MD5_STEP( F4, a, b, c, d, intermediate[ 0 ] + 0xf4292244, 6 );
MD5_STEP( F4, d, a, b, c, intermediate[ 7 ] + 0x432aff97, 10 );
MD5_STEP( F4, c, d, a, b, intermediate[ 14 ] + 0xab9423a7, 15 );
MD5_STEP( F4, b, c, d, a, intermediate[ 5 ] + 0xfc93a039, 21 );
MD5_STEP( F4, a, b, c, d, intermediate[ 12 ] + 0x655b59c3, 6 );
MD5_STEP( F4, d, a, b, c, intermediate[ 3 ] + 0x8f0ccc92, 10 );
MD5_STEP( F4, c, d, a, b, intermediate[ 10 ] + 0xffeff47d, 15 );
MD5_STEP( F4, b, c, d, a, intermediate[ 1 ] + 0x85845dd1, 21 );
MD5_STEP( F4, a, b, c, d, intermediate[ 8 ] + 0x6fa87e4f, 6 );
MD5_STEP( F4, d, a, b, c, intermediate[ 15 ] + 0xfe2ce6e0, 10 );
MD5_STEP( F4, c, d, a, b, intermediate[ 6 ] + 0xa3014314, 15 );
MD5_STEP( F4, b, c, d, a, intermediate[ 13 ] + 0x4e0811a1, 21 );
MD5_STEP( F4, a, b, c, d, intermediate[ 4 ] + 0xf7537e82, 6 );
MD5_STEP( F4, d, a, b, c, intermediate[ 11 ] + 0xbd3af235, 10 );
MD5_STEP( F4, c, d, a, b, intermediate[ 2 ] + 0x2ad7d2bb, 15 );
MD5_STEP( F4, b, c, d, a, intermediate[ 9 ] + 0xeb86d391, 21 );
buffer[ 0 ] += a;
buffer[ 1 ] += b;
buffer[ 2 ] += c;
buffer[ 3 ] += d;
}
/******************************************************************************/
/**
*
* This function Start MD5 accumulation
* Set bit count to 0 and buffer to mysterious initialization constants
*
* @param
*
* @return None
*
* @note None
*
****************************************************************************/
inline void MD5Init( MD5Context *context )
{
context->buffer[ 0 ] = 0x67452301;
context->buffer[ 1 ] = 0xefcdab89;
context->buffer[ 2 ] = 0x98badcfe;
context->buffer[ 3 ] = 0x10325476;
context->bits[ 0 ] = 0;
context->bits[ 1 ] = 0;
}
/******************************************************************************/
/**
*
* This function updates context to reflect the concatenation of another
* buffer full of bytes
*
* @param
*
* @param
*
* @param
*
* @param
*
* @return None
*
* @note None
*
****************************************************************************/
inline void MD5Update( MD5Context *context, u8 *buffer,
u32 len, boolean doByteSwap )
{
register u32 temp;
register u8 * p;
/*
* Update bitcount
*/
temp = context->bits[ 0 ];
if( ( context->bits[ 0 ] = temp + ( (u32)len << 3 ) ) < temp ) {
/*
* Carry from low to high
*/
context->bits[ 1 ]++;
}
context->bits[ 1 ] += len >> 29;
/*
* Bytes already in shsInfo->data
*/
temp = ( temp >> 3 ) & 0x3f;
/*
* Handle any leading odd-sized chunks
*/
if( temp ) {
p = (u8 *)context->intermediate + temp;
temp = MD5_SIGNATURE_BYTE_SIZE - temp;
if( len < temp ) {
MD5Memcpy( p, buffer, len, doByteSwap );
return;
}
MD5Memcpy( p, buffer, temp, doByteSwap );
MD5Transform( context->buffer, (u32 *)context->intermediate );
buffer += temp;
len -= temp;
}
/*
* Process data in 64-byte, 512 bit, chunks
*/
while( len >= MD5_SIGNATURE_BYTE_SIZE ) {
MD5Memcpy( context->intermediate, buffer, MD5_SIGNATURE_BYTE_SIZE,
doByteSwap );
MD5Transform( context->buffer, (u32 *)context->intermediate );
buffer += MD5_SIGNATURE_BYTE_SIZE;
len -= MD5_SIGNATURE_BYTE_SIZE;
}
/*
* Handle any remaining bytes of data
*/
MD5Memcpy( context->intermediate, buffer, len, doByteSwap );
}
/******************************************************************************/
/**
*
* This function final wrap-up - pad to 64-byte boundary with the bit pattern
* 1 0* (64-bit count of bits processed, MSB-first
*
* @param
*
* @param
*
* @param
*
* @param
*
* @return None
*
* @note None
*
****************************************************************************/
inline void MD5Final( MD5Context *context, u8 *digest,
boolean doByteSwap )
{
u32 count;
u8 * p;
/*
* Compute number of bytes mod 64
*/
count = ( context->bits[ 0 ] >> 3 ) & 0x3F;
/*
* Set the first char of padding to 0x80. This is safe since there is
* always at least one byte free
*/
p = context->intermediate + count;
*p++ = 0x80;
/*
* Bytes of padding needed to make 64 bytes
*/
count = MD5_SIGNATURE_BYTE_SIZE - 1 - count;
/*
* Pad out to 56 mod 64
*/
if( count < 8 ) {
/*
* Two lots of padding: Pad the first block to 64 bytes
*/
MD5Memset( p, 0, count );
MD5Transform( context->buffer, (u32 *)context->intermediate );
/*
* Now fill the next block with 56 bytes
*/
MD5Memset( context->intermediate, 0, 56 );
} else {
/*
* Pad block to 56 bytes
*/
MD5Memset( p, 0, count - 8 );
}
/*
* Append length in bits and transform
*/
( (u32 *)context->intermediate )[ 14 ] = context->bits[ 0 ];
( (u32 *)context->intermediate )[ 15 ] = context->bits[ 1 ];
MD5Transform( context->buffer, (u32 *)context->intermediate );
/*
* Now return the digest
*/
MD5Memcpy( digest, context->buffer, 16, doByteSwap );
}
/******************************************************************************/
/**
*
* This function calculate and store in 'digest' the MD5 digest of 'len' bytes at
* 'input'. 'digest' must have enough space to hold 16 bytes
*
* @param
*
* @param
*
* @param
*
* @param
*
* @return None
*
* @note None
*
****************************************************************************/
void md5( u8 *input, u32 len, u8 *digest, boolean doByteSwap )
{
MD5Context context;
MD5Init( &context );
MD5Update( &context, input, len, doByteSwap );
MD5Final( &context, digest, doByteSwap );
}