Back to index

avfs  1.0.1
md5.c
Go to the documentation of this file.
00001 /* md5.c - Functions to compute MD5 message digest of files or memory blocks
00002    according to the definition of MD5 in RFC 1321 from April 1992.
00003    Copyright (C) 1995, 1996, 1997 Free Software Foundation, Inc.
00004    This file is part of the GNU C Library.
00005 
00006    The GNU C Library is free software; you can redistribute it and/or
00007    modify it under the terms of the GNU Library General Public License as
00008    published by the Free Software Foundation; either version 2 of the
00009    License, or (at your option) any later version.
00010 
00011    The GNU C Library is distributed in the hope that it will be useful,
00012    but WITHOUT ANY WARRANTY; without even the implied warranty of
00013    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014    Library General Public License for more details.
00015 
00016    You should have received a copy of the GNU Library General Public
00017    License along with the GNU C Library; see the file COPYING.LIB.  If not,
00018    write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00019    Boston, MA 02111-1307, USA.  */
00020 
00021 /* Written by Ulrich Drepper <drepper@gnu.ai.mit.edu>, 1995.  */
00022 
00023 #ifdef HAVE_CONFIG_H
00024 # include "config.h"
00025 #endif
00026 
00027 #include <sys/types.h>
00028 
00029 #if STDC_HEADERS || defined _LIBC
00030 # include <stdlib.h>
00031 # include <string.h>
00032 #else
00033 #ifdef HAVE_STRING_H
00034 #include <string.h>
00035 #endif
00036 # ifndef HAVE_MEMCPY
00037 #  define memcpy(d, s, n) bcopy ((s), (d), (n))
00038 # endif
00039 #endif
00040 
00041 #include "neon_md5.h"
00042 
00043 #ifdef _LIBC
00044 # include <endian.h>
00045 # if __BYTE_ORDER == __BIG_ENDIAN
00046 #  define WORDS_BIGENDIAN 1
00047 # endif
00048 /* We need to keep the namespace clean so define the MD5 function
00049    protected using leading __ and use weak aliases.  */
00050 # define md5_init_ctx __md5_init_ctx
00051 # define md5_process_block __md5_process_block
00052 # define md5_process_bytes __md5_process_bytes
00053 # define md5_finish_ctx __md5_finish_ctx
00054 # define md5_read_ctx __md5_read_ctx
00055 # define md5_stream __md5_stream
00056 # define md5_buffer __md5_buffer
00057 #endif
00058 
00059 #ifdef WORDS_BIGENDIAN
00060 # define SWAP(n)                                               \
00061     (((n) << 24) | (((n) & 0xff00) << 8) | (((n) >> 8) & 0xff00) | ((n) >> 24))
00062 #else
00063 # define SWAP(n) (n)
00064 #endif
00065 
00066 
00067 /* This array contains the bytes used to pad the buffer to the next
00068    64-byte boundary.  (RFC 1321, 3.1: Step 1)  */
00069 static const unsigned char fillbuf[64] = { 0x80, 0 /* , 0, 0, ...  */ };
00070 
00071 
00072 /* Initialize structure containing state of computation.
00073    (RFC 1321, 3.3: Step 3)  */
00074 void
00075 md5_init_ctx (ctx)
00076      struct md5_ctx *ctx;
00077 {
00078   ctx->A = 0x67452301;
00079   ctx->B = 0xefcdab89;
00080   ctx->C = 0x98badcfe;
00081   ctx->D = 0x10325476;
00082 
00083   ctx->total[0] = ctx->total[1] = 0;
00084   ctx->buflen = 0;
00085 }
00086 
00087 /* Put result from CTX in first 16 bytes following RESBUF.  The result
00088    must be in little endian byte order.
00089 
00090    IMPORTANT: On some systems it is required that RESBUF is correctly
00091    aligned for a 32 bits value.  */
00092 void *
00093 md5_read_ctx (ctx, resbuf)
00094      const struct md5_ctx *ctx;
00095      void *resbuf;
00096 {
00097   ((md5_uint32 *) resbuf)[0] = SWAP (ctx->A);
00098   ((md5_uint32 *) resbuf)[1] = SWAP (ctx->B);
00099   ((md5_uint32 *) resbuf)[2] = SWAP (ctx->C);
00100   ((md5_uint32 *) resbuf)[3] = SWAP (ctx->D);
00101 
00102   return resbuf;
00103 }
00104 
00105 /* Process the remaining bytes in the internal buffer and the usual
00106    prolog according to the standard and write the result to RESBUF.
00107 
00108    IMPORTANT: On some systems it is required that RESBUF is correctly
00109    aligned for a 32 bits value.  */
00110 void *
00111 md5_finish_ctx (ctx, resbuf)
00112      struct md5_ctx *ctx;
00113      void *resbuf;
00114 {
00115   /* Take yet unprocessed bytes into account.  */
00116   md5_uint32 bytes = ctx->buflen;
00117   size_t pad;
00118 
00119   /* Now count remaining bytes.  */
00120   ctx->total[0] += bytes;
00121   if (ctx->total[0] < bytes)
00122     ++ctx->total[1];
00123 
00124   pad = bytes >= 56 ? 64 + 56 - bytes : 56 - bytes;
00125   memcpy (&ctx->buffer[bytes], fillbuf, pad);
00126 
00127   /* Put the 64-bit file length in *bits* at the end of the buffer.  */
00128   *(md5_uint32 *) &ctx->buffer[bytes + pad] = SWAP (ctx->total[0] << 3);
00129   *(md5_uint32 *) &ctx->buffer[bytes + pad + 4] = SWAP ((ctx->total[1] << 3) |
00130                                                  (ctx->total[0] >> 29));
00131 
00132   /* Process last bytes.  */
00133   md5_process_block (ctx->buffer, bytes + pad + 8, ctx);
00134 
00135   return md5_read_ctx (ctx, resbuf);
00136 }
00137 
00138 /* Compute MD5 message digest for bytes read from STREAM.  The
00139    resulting message digest number will be written into the 16 bytes
00140    beginning at RESBLOCK.  */
00141 int
00142 md5_stream (stream, resblock)
00143      FILE *stream;
00144      void *resblock;
00145 {
00146   /* Important: BLOCKSIZE must be a multiple of 64.  */
00147 #define BLOCKSIZE 4096
00148   struct md5_ctx ctx;
00149   char buffer[BLOCKSIZE + 72];
00150   size_t sum;
00151 
00152   /* Initialize the computation context.  */
00153   md5_init_ctx (&ctx);
00154 
00155   /* Iterate over full file contents.  */
00156   while (1)
00157     {
00158       /* We read the file in blocks of BLOCKSIZE bytes.  One call of the
00159         computation function processes the whole buffer so that with the
00160         next round of the loop another block can be read.  */
00161       size_t n;
00162       sum = 0;
00163 
00164       /* Read block.  Take care for partial reads.  */
00165       do
00166        {
00167          n = fread (buffer + sum, 1, BLOCKSIZE - sum, stream);
00168 
00169          sum += n;
00170        }
00171       while (sum < BLOCKSIZE && n != 0);
00172       if (n == 0 && ferror (stream))
00173         return 1;
00174 
00175       /* If end of file is reached, end the loop.  */
00176       if (n == 0)
00177        break;
00178 
00179       /* Process buffer with BLOCKSIZE bytes.  Note that
00180                      BLOCKSIZE % 64 == 0
00181        */
00182       md5_process_block (buffer, BLOCKSIZE, &ctx);
00183     }
00184 
00185   /* Add the last bytes if necessary.  */
00186   if (sum > 0)
00187     md5_process_bytes (buffer, sum, &ctx);
00188 
00189   /* Construct result in desired memory.  */
00190   md5_finish_ctx (&ctx, resblock);
00191   return 0;
00192 }
00193 
00194 /* Compute MD5 message digest for LEN bytes beginning at BUFFER.  The
00195    result is always in little endian byte order, so that a byte-wise
00196    output yields to the wanted ASCII representation of the message
00197    digest.  */
00198 void *
00199 md5_buffer (buffer, len, resblock)
00200      const char *buffer;
00201      size_t len;
00202      void *resblock;
00203 {
00204   struct md5_ctx ctx;
00205 
00206   /* Initialize the computation context.  */
00207   md5_init_ctx (&ctx);
00208 
00209   /* Process whole buffer but last len % 64 bytes.  */
00210   md5_process_bytes (buffer, len, &ctx);
00211 
00212   /* Put result in desired memory area.  */
00213   return md5_finish_ctx (&ctx, resblock);
00214 }
00215 
00216 
00217 void
00218 md5_process_bytes (buffer, len, ctx)
00219      const void *buffer;
00220      size_t len;
00221      struct md5_ctx *ctx;
00222 {
00223   /* When we already have some bits in our internal buffer concatenate
00224      both inputs first.  */
00225   if (ctx->buflen != 0)
00226     {
00227       size_t left_over = ctx->buflen;
00228       size_t add = 128 - left_over > len ? len : 128 - left_over;
00229 
00230       memcpy (&ctx->buffer[left_over], buffer, add);
00231       ctx->buflen += add;
00232 
00233       if (left_over + add > 64)
00234        {
00235          md5_process_block (ctx->buffer, (left_over + add) & ~63, ctx);
00236          /* The regions in the following copy operation cannot overlap.  */
00237          memcpy (ctx->buffer, &ctx->buffer[(left_over + add) & ~63],
00238                 (left_over + add) & 63);
00239          ctx->buflen = (left_over + add) & 63;
00240        }
00241 
00242       buffer = (const char *) buffer + add;
00243       len -= add;
00244     }
00245 
00246   /* Process available complete blocks.  */
00247   if (len > 64)
00248     {
00249       md5_process_block (buffer, len & ~63, ctx);
00250       buffer = (const char *) buffer + (len & ~63);
00251       len &= 63;
00252     }
00253 
00254   /* Move remaining bytes in internal buffer.  */
00255   if (len > 0)
00256     {
00257       memcpy (ctx->buffer, buffer, len);
00258       ctx->buflen = len;
00259     }
00260 }
00261 
00262 
00263 /* These are the four functions used in the four steps of the MD5 algorithm
00264    and defined in the RFC 1321.  The first function is a little bit optimized
00265    (as found in Colin Plumbs public domain implementation).  */
00266 /* #define FF(b, c, d) ((b & c) | (~b & d)) */
00267 #define FF(b, c, d) (d ^ (b & (c ^ d)))
00268 #define FG(b, c, d) FF (d, b, c)
00269 #define FH(b, c, d) (b ^ c ^ d)
00270 #define FI(b, c, d) (c ^ (b | ~d))
00271 
00272 /* Process LEN bytes of BUFFER, accumulating context into CTX.
00273    It is assumed that LEN % 64 == 0.  */
00274 
00275 void
00276 md5_process_block (buffer, len, ctx)
00277      const void *buffer;
00278      size_t len;
00279      struct md5_ctx *ctx;
00280 {
00281   md5_uint32 correct_words[16];
00282   const md5_uint32 *words = buffer;
00283   size_t nwords = len / sizeof (md5_uint32);
00284   const md5_uint32 *endp = words + nwords;
00285   md5_uint32 A = ctx->A;
00286   md5_uint32 B = ctx->B;
00287   md5_uint32 C = ctx->C;
00288   md5_uint32 D = ctx->D;
00289 
00290   /* First increment the byte count.  RFC 1321 specifies the possible
00291      length of the file up to 2^64 bits.  Here we only compute the
00292      number of bytes.  Do a double word increment.  */
00293   ctx->total[0] += len;
00294   if (ctx->total[0] < len)
00295     ++ctx->total[1];
00296 
00297   /* Process all bytes in the buffer with 64 bytes in each round of
00298      the loop.  */
00299   while (words < endp)
00300     {
00301       md5_uint32 *cwp = correct_words;
00302       md5_uint32 A_save = A;
00303       md5_uint32 B_save = B;
00304       md5_uint32 C_save = C;
00305       md5_uint32 D_save = D;
00306 
00307       /* First round: using the given function, the context and a constant
00308         the next context is computed.  Because the algorithms processing
00309         unit is a 32-bit word and it is determined to work on words in
00310         little endian byte order we perhaps have to change the byte order
00311         before the computation.  To reduce the work for the next steps
00312         we store the swapped words in the array CORRECT_WORDS.  */
00313 
00314 #define OP(a, b, c, d, s, T)                                          \
00315       do                                                       \
00316         {                                                      \
00317          a += FF (b, c, d) + (*cwp++ = SWAP (*words)) + T;            \
00318          ++words;                                              \
00319          CYCLIC (a, s);                                        \
00320          a += b;                                               \
00321         }                                                      \
00322       while (0)
00323 
00324       /* It is unfortunate that C does not provide an operator for
00325         cyclic rotation.  Hope the C compiler is smart enough.  */
00326 #define CYCLIC(w, s) (w = (w << s) | (w >> (32 - s)))
00327 
00328       /* Before we start, one word to the strange constants.
00329         They are defined in RFC 1321 as
00330 
00331         T[i] = (int) (4294967296.0 * fabs (sin (i))), i=1..64
00332        */
00333 
00334       /* Round 1.  */
00335       OP (A, B, C, D,  7, 0xd76aa478);
00336       OP (D, A, B, C, 12, 0xe8c7b756);
00337       OP (C, D, A, B, 17, 0x242070db);
00338       OP (B, C, D, A, 22, 0xc1bdceee);
00339       OP (A, B, C, D,  7, 0xf57c0faf);
00340       OP (D, A, B, C, 12, 0x4787c62a);
00341       OP (C, D, A, B, 17, 0xa8304613);
00342       OP (B, C, D, A, 22, 0xfd469501);
00343       OP (A, B, C, D,  7, 0x698098d8);
00344       OP (D, A, B, C, 12, 0x8b44f7af);
00345       OP (C, D, A, B, 17, 0xffff5bb1);
00346       OP (B, C, D, A, 22, 0x895cd7be);
00347       OP (A, B, C, D,  7, 0x6b901122);
00348       OP (D, A, B, C, 12, 0xfd987193);
00349       OP (C, D, A, B, 17, 0xa679438e);
00350       OP (B, C, D, A, 22, 0x49b40821);
00351 
00352       /* For the second to fourth round we have the possibly swapped words
00353         in CORRECT_WORDS.  Redefine the macro to take an additional first
00354         argument specifying the function to use.  */
00355 #undef OP
00356 #define OP(f, a, b, c, d, k, s, T)                             \
00357       do                                                       \
00358        {                                                       \
00359          a += f (b, c, d) + correct_words[k] + T;                     \
00360          CYCLIC (a, s);                                        \
00361          a += b;                                               \
00362        }                                                       \
00363       while (0)
00364 
00365       /* Round 2.  */
00366       OP (FG, A, B, C, D,  1,  5, 0xf61e2562);
00367       OP (FG, D, A, B, C,  6,  9, 0xc040b340);
00368       OP (FG, C, D, A, B, 11, 14, 0x265e5a51);
00369       OP (FG, B, C, D, A,  0, 20, 0xe9b6c7aa);
00370       OP (FG, A, B, C, D,  5,  5, 0xd62f105d);
00371       OP (FG, D, A, B, C, 10,  9, 0x02441453);
00372       OP (FG, C, D, A, B, 15, 14, 0xd8a1e681);
00373       OP (FG, B, C, D, A,  4, 20, 0xe7d3fbc8);
00374       OP (FG, A, B, C, D,  9,  5, 0x21e1cde6);
00375       OP (FG, D, A, B, C, 14,  9, 0xc33707d6);
00376       OP (FG, C, D, A, B,  3, 14, 0xf4d50d87);
00377       OP (FG, B, C, D, A,  8, 20, 0x455a14ed);
00378       OP (FG, A, B, C, D, 13,  5, 0xa9e3e905);
00379       OP (FG, D, A, B, C,  2,  9, 0xfcefa3f8);
00380       OP (FG, C, D, A, B,  7, 14, 0x676f02d9);
00381       OP (FG, B, C, D, A, 12, 20, 0x8d2a4c8a);
00382 
00383       /* Round 3.  */
00384       OP (FH, A, B, C, D,  5,  4, 0xfffa3942);
00385       OP (FH, D, A, B, C,  8, 11, 0x8771f681);
00386       OP (FH, C, D, A, B, 11, 16, 0x6d9d6122);
00387       OP (FH, B, C, D, A, 14, 23, 0xfde5380c);
00388       OP (FH, A, B, C, D,  1,  4, 0xa4beea44);
00389       OP (FH, D, A, B, C,  4, 11, 0x4bdecfa9);
00390       OP (FH, C, D, A, B,  7, 16, 0xf6bb4b60);
00391       OP (FH, B, C, D, A, 10, 23, 0xbebfbc70);
00392       OP (FH, A, B, C, D, 13,  4, 0x289b7ec6);
00393       OP (FH, D, A, B, C,  0, 11, 0xeaa127fa);
00394       OP (FH, C, D, A, B,  3, 16, 0xd4ef3085);
00395       OP (FH, B, C, D, A,  6, 23, 0x04881d05);
00396       OP (FH, A, B, C, D,  9,  4, 0xd9d4d039);
00397       OP (FH, D, A, B, C, 12, 11, 0xe6db99e5);
00398       OP (FH, C, D, A, B, 15, 16, 0x1fa27cf8);
00399       OP (FH, B, C, D, A,  2, 23, 0xc4ac5665);
00400 
00401       /* Round 4.  */
00402       OP (FI, A, B, C, D,  0,  6, 0xf4292244);
00403       OP (FI, D, A, B, C,  7, 10, 0x432aff97);
00404       OP (FI, C, D, A, B, 14, 15, 0xab9423a7);
00405       OP (FI, B, C, D, A,  5, 21, 0xfc93a039);
00406       OP (FI, A, B, C, D, 12,  6, 0x655b59c3);
00407       OP (FI, D, A, B, C,  3, 10, 0x8f0ccc92);
00408       OP (FI, C, D, A, B, 10, 15, 0xffeff47d);
00409       OP (FI, B, C, D, A,  1, 21, 0x85845dd1);
00410       OP (FI, A, B, C, D,  8,  6, 0x6fa87e4f);
00411       OP (FI, D, A, B, C, 15, 10, 0xfe2ce6e0);
00412       OP (FI, C, D, A, B,  6, 15, 0xa3014314);
00413       OP (FI, B, C, D, A, 13, 21, 0x4e0811a1);
00414       OP (FI, A, B, C, D,  4,  6, 0xf7537e82);
00415       OP (FI, D, A, B, C, 11, 10, 0xbd3af235);
00416       OP (FI, C, D, A, B,  2, 15, 0x2ad7d2bb);
00417       OP (FI, B, C, D, A,  9, 21, 0xeb86d391);
00418 
00419       /* Add the starting values of the context.  */
00420       A += A_save;
00421       B += B_save;
00422       C += C_save;
00423       D += D_save;
00424     }
00425 
00426   /* Put checksum in context given as argument.  */
00427   ctx->A = A;
00428   ctx->B = B;
00429   ctx->C = C;
00430   ctx->D = D;
00431 }
00432 
00433 
00434 #ifdef _LIBC
00435 /* Define weak aliases.  */
00436 # undef md5_init_ctx
00437 weak_alias (__md5_init_ctx, md5_init_ctx)
00438 # undef md5_process_block
00439 weak_alias (__md5_process_block, md5_process_block)
00440 # undef md5_process_bytes
00441 weak_alias (__md5_process_bytes, md5_process_bytes)
00442 # undef md5_finish_ctx
00443 weak_alias (__md5_finish_ctx, md5_finish_ctx)
00444 # undef md5_read_ctx
00445 weak_alias (__md5_read_ctx, md5_read_ctx)
00446 # undef md5_stream
00447 weak_alias (__md5_stream, md5_stream)
00448 # undef md5_buffer
00449 weak_alias (__md5_buffer, md5_buffer)
00450 #endif