/home/dko/projects/mobilec/trunk/src/security/xyssl-0.7/library/sha4.c

Go to the documentation of this file.
00001 /* SVN FILE INFO
00002  * $Revision: 174 $ : Last Committed Revision
00003  * $Date: 2008-06-24 10:50:29 -0700 (Tue, 24 Jun 2008) $ : Last Committed Date */
00004 /*
00005  *  FIPS-180-2 compliant SHA-384/512 implementation
00006  *
00007  *  Copyright (C) 2006-2007  Christophe Devine
00008  *
00009  *  This library is free software; you can redistribute it and/or
00010  *  modify it under the terms of the GNU Lesser General Public
00011  *  License, version 2.1 as published by the Free Software Foundation.
00012  *
00013  *  This library is distributed in the hope that it will be usefu),
00014  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00015  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00016  *  Lesser General Public License for more details.
00017  *
00018  *  You should have received a copy of the GNU Lesser General Public
00019  *  License along with this library; if not, write to the Free Software
00020  *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
00021  *  MA  02110-1301  USA
00022  */
00023 /*
00024  *  The SHA-512 Secure Hash Standard was published by NIST in 2002.
00025  *
00026  *  http://csrc.nist.gov/publications/fips/fips180-2/fips180-2.pdf
00027  */
00028 
00029 #ifndef _CRT_SECURE_NO_DEPRECATE
00030 #define _CRT_SECURE_NO_DEPRECATE 1
00031 #endif
00032 
00033 #include <string.h>
00034 #include <stdio.h>
00035 
00036 #include "xyssl/sha4.h"
00037 
00038 /*
00039  * 64-bit integer manipulation macros (big endian)
00040  */
00041 #ifndef GET_UINT64_BE
00042 #define GET_UINT64_BE(n,b,i)                            \
00043 {                                                       \
00044     (n) = ( (uint64) (b)[(i)    ] << 56 )               \
00045         | ( (uint64) (b)[(i) + 1] << 48 )               \
00046         | ( (uint64) (b)[(i) + 2] << 40 )               \
00047         | ( (uint64) (b)[(i) + 3] << 32 )               \
00048         | ( (uint64) (b)[(i) + 4] << 24 )               \
00049         | ( (uint64) (b)[(i) + 5] << 16 )               \
00050         | ( (uint64) (b)[(i) + 6] <<  8 )               \
00051         | ( (uint64) (b)[(i) + 7]       );              \
00052 }
00053 #endif
00054 
00055 #ifndef PUT_UINT64_BE
00056 #define PUT_UINT64_BE(n,b,i)                            \
00057 {                                                       \
00058     (b)[(i)    ] = (unsigned char) ( (n) >> 56 );       \
00059     (b)[(i) + 1] = (unsigned char) ( (n) >> 48 );       \
00060     (b)[(i) + 2] = (unsigned char) ( (n) >> 40 );       \
00061     (b)[(i) + 3] = (unsigned char) ( (n) >> 32 );       \
00062     (b)[(i) + 4] = (unsigned char) ( (n) >> 24 );       \
00063     (b)[(i) + 5] = (unsigned char) ( (n) >> 16 );       \
00064     (b)[(i) + 6] = (unsigned char) ( (n) >>  8 );       \
00065     (b)[(i) + 7] = (unsigned char) ( (n)       );       \
00066 }
00067 #endif
00068 
00069 /*
00070  * Round constants
00071  */
00072 static const uint64 K[80] =
00073 {
00074     UL64(0x428A2F98D728AE22),  UL64(0x7137449123EF65CD),
00075     UL64(0xB5C0FBCFEC4D3B2F),  UL64(0xE9B5DBA58189DBBC),
00076     UL64(0x3956C25BF348B538),  UL64(0x59F111F1B605D019),
00077     UL64(0x923F82A4AF194F9B),  UL64(0xAB1C5ED5DA6D8118),
00078     UL64(0xD807AA98A3030242),  UL64(0x12835B0145706FBE),
00079     UL64(0x243185BE4EE4B28C),  UL64(0x550C7DC3D5FFB4E2),
00080     UL64(0x72BE5D74F27B896F),  UL64(0x80DEB1FE3B1696B1),
00081     UL64(0x9BDC06A725C71235),  UL64(0xC19BF174CF692694),
00082     UL64(0xE49B69C19EF14AD2),  UL64(0xEFBE4786384F25E3),
00083     UL64(0x0FC19DC68B8CD5B5),  UL64(0x240CA1CC77AC9C65),
00084     UL64(0x2DE92C6F592B0275),  UL64(0x4A7484AA6EA6E483),
00085     UL64(0x5CB0A9DCBD41FBD4),  UL64(0x76F988DA831153B5),
00086     UL64(0x983E5152EE66DFAB),  UL64(0xA831C66D2DB43210),
00087     UL64(0xB00327C898FB213F),  UL64(0xBF597FC7BEEF0EE4),
00088     UL64(0xC6E00BF33DA88FC2),  UL64(0xD5A79147930AA725),
00089     UL64(0x06CA6351E003826F),  UL64(0x142929670A0E6E70),
00090     UL64(0x27B70A8546D22FFC),  UL64(0x2E1B21385C26C926),
00091     UL64(0x4D2C6DFC5AC42AED),  UL64(0x53380D139D95B3DF),
00092     UL64(0x650A73548BAF63DE),  UL64(0x766A0ABB3C77B2A8),
00093     UL64(0x81C2C92E47EDAEE6),  UL64(0x92722C851482353B),
00094     UL64(0xA2BFE8A14CF10364),  UL64(0xA81A664BBC423001),
00095     UL64(0xC24B8B70D0F89791),  UL64(0xC76C51A30654BE30),
00096     UL64(0xD192E819D6EF5218),  UL64(0xD69906245565A910),
00097     UL64(0xF40E35855771202A),  UL64(0x106AA07032BBD1B8),
00098     UL64(0x19A4C116B8D2D0C8),  UL64(0x1E376C085141AB53),
00099     UL64(0x2748774CDF8EEB99),  UL64(0x34B0BCB5E19B48A8),
00100     UL64(0x391C0CB3C5C95A63),  UL64(0x4ED8AA4AE3418ACB),
00101     UL64(0x5B9CCA4F7763E373),  UL64(0x682E6FF3D6B2B8A3),
00102     UL64(0x748F82EE5DEFB2FC),  UL64(0x78A5636F43172F60),
00103     UL64(0x84C87814A1F0AB72),  UL64(0x8CC702081A6439EC),
00104     UL64(0x90BEFFFA23631E28),  UL64(0xA4506CEBDE82BDE9),
00105     UL64(0xBEF9A3F7B2C67915),  UL64(0xC67178F2E372532B),
00106     UL64(0xCA273ECEEA26619C),  UL64(0xD186B8C721C0C207),
00107     UL64(0xEADA7DD6CDE0EB1E),  UL64(0xF57D4F7FEE6ED178),
00108     UL64(0x06F067AA72176FBA),  UL64(0x0A637DC5A2C898A6),
00109     UL64(0x113F9804BEF90DAE),  UL64(0x1B710B35131C471B),
00110     UL64(0x28DB77F523047D84),  UL64(0x32CAAB7B40C72493),
00111     UL64(0x3C9EBE0A15C9BEBC),  UL64(0x431D67C49C100D4C),
00112     UL64(0x4CC5D4BECB3E42B6),  UL64(0x597F299CFC657E2A),
00113     UL64(0x5FCB6FAB3AD6FAEC),  UL64(0x6C44198C4A475817)
00114 };
00115 
00116 /*
00117  * SHA-512 context setup
00118  */
00119 void sha4_starts( sha4_context *ctx, int is384 )
00120 {
00121     ctx->total[0] = 0;
00122     ctx->total[1] = 0;
00123 
00124     if( is384 == 0 )
00125     {
00126         /* SHA-512 */
00127         ctx->state[0] = UL64(0x6A09E667F3BCC908);
00128         ctx->state[1] = UL64(0xBB67AE8584CAA73B);
00129         ctx->state[2] = UL64(0x3C6EF372FE94F82B);
00130         ctx->state[3] = UL64(0xA54FF53A5F1D36F1);
00131         ctx->state[4] = UL64(0x510E527FADE682D1);
00132         ctx->state[5] = UL64(0x9B05688C2B3E6C1F);
00133         ctx->state[6] = UL64(0x1F83D9ABFB41BD6B);
00134         ctx->state[7] = UL64(0x5BE0CD19137E2179);
00135     }
00136     else
00137     {
00138         /* SHA-384 */
00139         ctx->state[0] = UL64(0xCBBB9D5DC1059ED8);
00140         ctx->state[1] = UL64(0x629A292A367CD507);
00141         ctx->state[2] = UL64(0x9159015A3070DD17);
00142         ctx->state[3] = UL64(0x152FECD8F70E5939);
00143         ctx->state[4] = UL64(0x67332667FFC00B31);
00144         ctx->state[5] = UL64(0x8EB44A8768581511);
00145         ctx->state[6] = UL64(0xDB0C2E0D64F98FA7);
00146         ctx->state[7] = UL64(0x47B5481DBEFA4FA4);
00147     }
00148 
00149     ctx->is384 = is384;
00150 }
00151 
00152 static void sha4_process( sha4_context *ctx, unsigned char data[128] )
00153 {
00154     int i;
00155     uint64 temp1, temp2, W[80];
00156     uint64 A, B, C, D, E, F, G, H;
00157 
00158 #define  SHR(x,n) (x >> n)
00159 #define ROTR(x,n) (SHR(x,n) | (x << (64 - n)))
00160 
00161 #define S0(x) (ROTR(x, 1) ^ ROTR(x, 8) ^  SHR(x, 7))
00162 #define S1(x) (ROTR(x,19) ^ ROTR(x,61) ^  SHR(x, 6))
00163 
00164 #define S2(x) (ROTR(x,28) ^ ROTR(x,34) ^ ROTR(x,39))
00165 #define S3(x) (ROTR(x,14) ^ ROTR(x,18) ^ ROTR(x,41))
00166 
00167 #define F0(x,y,z) ((x & y) | (z & (x | y)))
00168 #define F1(x,y,z) (z ^ (x & (y ^ z)))
00169 
00170 #define P(a,b,c,d,e,f,g,h,x,K)                  \
00171 {                                               \
00172     temp1 = h + S3(e) + F1(e,f,g) + K + x;      \
00173     temp2 = S2(a) + F0(a,b,c);                  \
00174     d += temp1; h = temp1 + temp2;              \
00175 }
00176 
00177     for( i = 0; i < 16; i++ )
00178     {
00179         GET_UINT64_BE( W[i], data, i << 3 );
00180     }
00181 
00182     for( ; i < 80; i++ )
00183     {
00184         W[i] = S1(W[i -  2]) + W[i -  7] +
00185                S0(W[i - 15]) + W[i - 16];
00186     }
00187 
00188     A = ctx->state[0];
00189     B = ctx->state[1];
00190     C = ctx->state[2];
00191     D = ctx->state[3];
00192     E = ctx->state[4];
00193     F = ctx->state[5];
00194     G = ctx->state[6];
00195     H = ctx->state[7];
00196     i = 0;
00197 
00198     do
00199     {
00200         P( A, B, C, D, E, F, G, H, W[i], K[i] ); i++;
00201         P( H, A, B, C, D, E, F, G, W[i], K[i] ); i++;
00202         P( G, H, A, B, C, D, E, F, W[i], K[i] ); i++;
00203         P( F, G, H, A, B, C, D, E, W[i], K[i] ); i++;
00204         P( E, F, G, H, A, B, C, D, W[i], K[i] ); i++;
00205         P( D, E, F, G, H, A, B, C, W[i], K[i] ); i++;
00206         P( C, D, E, F, G, H, A, B, W[i], K[i] ); i++;
00207         P( B, C, D, E, F, G, H, A, W[i], K[i] ); i++;
00208     }
00209     while( i < 80 );
00210 
00211     ctx->state[0] += A;
00212     ctx->state[1] += B;
00213     ctx->state[2] += C;
00214     ctx->state[3] += D;
00215     ctx->state[4] += E;
00216     ctx->state[5] += F;
00217     ctx->state[6] += G;
00218     ctx->state[7] += H;
00219 }
00220 
00221 /*
00222  * SHA-512 process buffer
00223  */
00224 void sha4_update( sha4_context *ctx, unsigned char *input, int ilen )
00225 {
00226     int fill;
00227     uint64 left;
00228 
00229     if( ilen <= 0 )
00230         return;
00231 
00232     left = ctx->total[0] & 0x7F;
00233     fill = (int)( 128 - left );
00234 
00235     ctx->total[0] += ilen;
00236 
00237     if( ctx->total[0] < (uint64) ilen )
00238         ctx->total[1]++;
00239 
00240     if( left && ilen >= fill )
00241     {
00242         memcpy( (void *) (ctx->buffer + left),
00243                 (void *) input, fill );
00244         sha4_process( ctx, ctx->buffer );
00245         input += fill;
00246         ilen  -= fill;
00247         left = 0;
00248     }
00249 
00250     while( ilen >= 128 )
00251     {
00252         sha4_process( ctx, input );
00253         input += 128;
00254         ilen  -= 128;
00255     }
00256 
00257     if( ilen > 0 )
00258     {
00259         memcpy( (void *) (ctx->buffer + left),
00260                 (void *) input, ilen );
00261     }
00262 }
00263 
00264 static const unsigned char sha4_padding[128] =
00265 {
00266  0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00267     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00268     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00269     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00270     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00271     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00272     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00273     0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
00274 };
00275 
00276 /*
00277  * SHA-512 final digest
00278  */
00279 void sha4_finish( sha4_context *ctx, unsigned char *output )
00280 {
00281         int last, padn;
00282     uint64 high, low;
00283     unsigned char msglen[16];
00284 
00285     high = ( ctx->total[0] >> 61 )
00286          | ( ctx->total[1] <<  3 );
00287     low  = ( ctx->total[0] <<  3 );
00288 
00289     PUT_UINT64_BE( high, msglen, 0 );
00290     PUT_UINT64_BE( low,  msglen, 8 );
00291 
00292     last = (int)( ctx->total[0] & 0x7F );
00293     padn = ( last < 112 ) ? ( 112 - last ) : ( 240 - last );
00294 
00295     sha4_update( ctx, (unsigned char *) sha4_padding, padn );
00296     sha4_update( ctx, msglen, 16 );
00297 
00298     PUT_UINT64_BE( ctx->state[0], output,  0 );
00299     PUT_UINT64_BE( ctx->state[1], output,  8 );
00300     PUT_UINT64_BE( ctx->state[2], output, 16 );
00301     PUT_UINT64_BE( ctx->state[3], output, 24 );
00302     PUT_UINT64_BE( ctx->state[4], output, 32 );
00303     PUT_UINT64_BE( ctx->state[5], output, 40 );
00304 
00305     if( ctx->is384 == 0 )
00306     {
00307         PUT_UINT64_BE( ctx->state[6], output, 48 );
00308         PUT_UINT64_BE( ctx->state[7], output, 56 );
00309     }
00310 }
00311 
00312 /*
00313  * Output = SHA-512( input buffer )
00314  */
00315 void sha4( unsigned char *input,  int ilen,
00316            unsigned char *output, int is384 )
00317 {
00318     sha4_context ctx;
00319 
00320     sha4_starts( &ctx, is384 );
00321     sha4_update( &ctx, input, ilen );
00322     sha4_finish( &ctx, output );
00323 
00324     memset( &ctx, 0, sizeof( sha4_context ) );
00325 }
00326 
00327 /*
00328  * Output = SHA-512( file contents )
00329  */
00330 int sha4_file( char *path, unsigned char *output, int is384 )
00331 {
00332     FILE *f;
00333     size_t n;
00334     sha4_context ctx;
00335     unsigned char buf[1024];
00336 
00337     if( ( f = fopen( path, "rb" ) ) == NULL )
00338         return( 1 );
00339 
00340     sha4_starts( &ctx, is384 );
00341 
00342     while( ( n = fread( buf, 1, sizeof( buf ), f ) ) > 0 )
00343         sha4_update( &ctx, buf, (int) n );
00344 
00345     sha4_finish( &ctx, output );
00346 
00347     memset( &ctx, 0, sizeof( sha4_context ) );
00348 
00349     if( ferror( f ) != 0 )
00350     {
00351         fclose( f );
00352         return( 2 );
00353     }
00354 
00355     fclose( f );
00356     return( 0 );
00357 }
00358 
00359 /*
00360  * SHA-512 HMAC context setup
00361  */
00362 void sha4_hmac_starts( sha4_context *ctx,  int is384,
00363                        unsigned char *key, int keylen )
00364 {
00365     int i;
00366 
00367     memset( ctx->ipad, 0x36, 64 );
00368     memset( ctx->opad, 0x5C, 64 );
00369 
00370     for( i = 0; i < keylen; i++ )
00371     {
00372         if( i >= 64 ) break;
00373 
00374         ctx->ipad[i] ^= key[i];
00375         ctx->opad[i] ^= key[i];
00376     }
00377 
00378     sha4_starts( ctx, is384 );
00379     sha4_update( ctx, ctx->ipad, 64 );
00380 }
00381 
00382 /*
00383  * SHA-512 HMAC process buffer
00384  */
00385 void sha4_hmac_update( sha4_context *ctx,
00386                        unsigned char *input, int ilen )
00387 {
00388     sha4_update( ctx, input, ilen );
00389 }
00390 
00391 /*
00392  * SHA-512 HMAC final digest
00393  */
00394 void sha4_hmac_finish( sha4_context *ctx, unsigned char *output )
00395 {
00396     int is384, hlen;
00397     unsigned char tmpbuf[64];
00398 
00399     is384 = ctx->is384;
00400     hlen = ( is384 == 0 ) ? 64 : 48;
00401 
00402     sha4_finish( ctx, tmpbuf );
00403     sha4_starts( ctx, is384 );
00404     sha4_update( ctx, ctx->opad, 64 );
00405     sha4_update( ctx, tmpbuf, hlen );
00406     sha4_finish( ctx, output );
00407 
00408     memset( tmpbuf, 0, sizeof( tmpbuf ) );
00409 }
00410 
00411 /*
00412  * Output = HMAC-SHA-512( hmac key, input buffer )
00413  */
00414 void sha4_hmac( unsigned char *key,  int keylen,
00415                 unsigned char *input,  int ilen,
00416                 unsigned char *output, int is384 )
00417 {
00418     sha4_context ctx;
00419 
00420     sha4_hmac_starts( &ctx, is384, key, keylen );
00421     sha4_hmac_update( &ctx, input, ilen );
00422     sha4_hmac_finish( &ctx, output );
00423 
00424     memset( &ctx, 0, sizeof( sha4_context ) );
00425 }
00426 
00427 static const char _sha4_src[] = "_sha4_src";
00428 
00429 #if defined(SELF_TEST)
00430 /*
00431  * FIPS-180-2 test vectors
00432  */
00433 static const char sha4_test_str[3][112] = 
00434 {
00435     { "abc" },
00436     { "abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmn"
00437       "hijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu" },
00438     { "" }
00439 };
00440 
00441 static const unsigned char sha4_test_sum[6][64] =
00442 {
00443     /*
00444      * SHA-384 test vectors
00445      */
00446     { 0xCB, 0x00, 0x75, 0x3F, 0x45, 0xA3, 0x5E, 0x8B,
00447       0xB5, 0xA0, 0x3D, 0x69, 0x9A, 0xC6, 0x50, 0x07,
00448       0x27, 0x2C, 0x32, 0xAB, 0x0E, 0xDE, 0xD1, 0x63,
00449       0x1A, 0x8B, 0x60, 0x5A, 0x43, 0xFF, 0x5B, 0xED,
00450       0x80, 0x86, 0x07, 0x2B, 0xA1, 0xE7, 0xCC, 0x23,
00451       0x58, 0xBA, 0xEC, 0xA1, 0x34, 0xC8, 0x25, 0xA7 },
00452     { 0x09, 0x33, 0x0C, 0x33, 0xF7, 0x11, 0x47, 0xE8,
00453       0x3D, 0x19, 0x2F, 0xC7, 0x82, 0xCD, 0x1B, 0x47,
00454       0x53, 0x11, 0x1B, 0x17, 0x3B, 0x3B, 0x05, 0xD2,
00455       0x2F, 0xA0, 0x80, 0x86, 0xE3, 0xB0, 0xF7, 0x12,
00456       0xFC, 0xC7, 0xC7, 0x1A, 0x55, 0x7E, 0x2D, 0xB9,
00457       0x66, 0xC3, 0xE9, 0xFA, 0x91, 0x74, 0x60, 0x39 },
00458     { 0x9D, 0x0E, 0x18, 0x09, 0x71, 0x64, 0x74, 0xCB,
00459       0x08, 0x6E, 0x83, 0x4E, 0x31, 0x0A, 0x4A, 0x1C,
00460       0xED, 0x14, 0x9E, 0x9C, 0x00, 0xF2, 0x48, 0x52,
00461       0x79, 0x72, 0xCE, 0xC5, 0x70, 0x4C, 0x2A, 0x5B,
00462       0x07, 0xB8, 0xB3, 0xDC, 0x38, 0xEC, 0xC4, 0xEB,
00463       0xAE, 0x97, 0xDD, 0xD8, 0x7F, 0x3D, 0x89, 0x85 },
00464 
00465     /*
00466      * SHA-512 test vectors
00467      */
00468     { 0xDD, 0xAF, 0x35, 0xA1, 0x93, 0x61, 0x7A, 0xBA,
00469       0xCC, 0x41, 0x73, 0x49, 0xAE, 0x20, 0x41, 0x31,
00470       0x12, 0xE6, 0xFA, 0x4E, 0x89, 0xA9, 0x7E, 0xA2,
00471       0x0A, 0x9E, 0xEE, 0xE6, 0x4B, 0x55, 0xD3, 0x9A,
00472       0x21, 0x92, 0x99, 0x2A, 0x27, 0x4F, 0xC1, 0xA8,
00473       0x36, 0xBA, 0x3C, 0x23, 0xA3, 0xFE, 0xEB, 0xBD,
00474       0x45, 0x4D, 0x44, 0x23, 0x64, 0x3C, 0xE8, 0x0E,
00475       0x2A, 0x9A, 0xC9, 0x4F, 0xA5, 0x4C, 0xA4, 0x9F },
00476     { 0x8E, 0x95, 0x9B, 0x75, 0xDA, 0xE3, 0x13, 0xDA,
00477       0x8C, 0xF4, 0xF7, 0x28, 0x14, 0xFC, 0x14, 0x3F,
00478       0x8F, 0x77, 0x79, 0xC6, 0xEB, 0x9F, 0x7F, 0xA1,
00479       0x72, 0x99, 0xAE, 0xAD, 0xB6, 0x88, 0x90, 0x18,
00480       0x50, 0x1D, 0x28, 0x9E, 0x49, 0x00, 0xF7, 0xE4,
00481       0x33, 0x1B, 0x99, 0xDE, 0xC4, 0xB5, 0x43, 0x3A,
00482       0xC7, 0xD3, 0x29, 0xEE, 0xB6, 0xDD, 0x26, 0x54,
00483       0x5E, 0x96, 0xE5, 0x5B, 0x87, 0x4B, 0xE9, 0x09 },
00484     { 0xE7, 0x18, 0x48, 0x3D, 0x0C, 0xE7, 0x69, 0x64,
00485       0x4E, 0x2E, 0x42, 0xC7, 0xBC, 0x15, 0xB4, 0x63,
00486       0x8E, 0x1F, 0x98, 0xB1, 0x3B, 0x20, 0x44, 0x28,
00487       0x56, 0x32, 0xA8, 0x03, 0xAF, 0xA9, 0x73, 0xEB,
00488       0xDE, 0x0F, 0xF2, 0x44, 0x87, 0x7E, 0xA6, 0x0A,
00489       0x4C, 0xB0, 0x43, 0x2C, 0xE5, 0x77, 0xC3, 0x1B,
00490       0xEB, 0x00, 0x9C, 0x5C, 0x2C, 0x49, 0xAA, 0x2E,
00491       0x4E, 0xAD, 0xB2, 0x17, 0xAD, 0x8C, 0xC0, 0x9B }
00492 };
00493 
00494 /*
00495  * Checkup routine
00496  */
00497 int sha4_self_test( int verbose )
00498 {
00499     int i, j, k;
00500     unsigned char buf[1000];
00501     unsigned char sha4sum[64];
00502     sha4_context ctx;
00503 
00504     memset( buf, 'a', 1000 );
00505 
00506     for( i = 0; i < 6; i++ )
00507     {
00508         j = i % 3;
00509         k = i < 3;
00510 
00511         if( verbose != 0 )
00512             printf( "  SHA-%d test #%d: ", 512 - k * 128, j + 1 );
00513 
00514         sha4_starts( &ctx, k );
00515 
00516         if( j < 2 )
00517             sha4_update( &ctx,
00518                          (unsigned char *) sha4_test_str[j],
00519                          strlen( sha4_test_str[j] ) );
00520         else
00521         {
00522             for( j = 0; j < 1000; j++ )
00523                 sha4_update( &ctx, buf, 1000 );
00524         }
00525 
00526         sha4_finish( &ctx, sha4sum );
00527 
00528         if( memcmp( sha4sum, sha4_test_sum[i], 64 - k * 16 ) != 0 )
00529         {
00530             if( verbose != 0 )
00531                 printf( "failed\n" );
00532 
00533             return( 1 );
00534         }
00535 
00536         if( verbose != 0 )
00537             printf( "passed\n" );
00538     }
00539 
00540     if( verbose != 0 )
00541         printf( "\n" );
00542 
00543     return( 0 );
00544 }
00545 #else
00546 int sha4_self_test( int verbose )
00547 {
00548     return( 0 );
00549 }
00550 #endif

Generated on Tue Jul 1 15:29:59 2008 for Mobile-C by  doxygen 1.5.4