1 /* md5sum.c - Compute MD5 checksum of files or strings according to the
2 * definition of MD5 in RFC 1321 from April 1992.
3 * Copyright (C) 1995-1999 Free Software Foundation, Inc.
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2, or (at your option)
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software Foundation,
17 * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
20 /* Written by Ulrich Drepper <drepper@gnu.ai.mit.edu> */
21 /* Hacked to work with BusyBox by Alfred M. Szmidt <ams@trillian.itslinux.org> */
24 * June 29, 2001 Manuel Novoa III
26 * Added MD5SUM_SIZE_VS_SPEED configuration option.
28 * Current valid values, with data from my system for comparison, are:
29 * (using uClibc and running on linux-2.4.4.tar.bz2)
30 * user times (sec) text size (386)
31 * 0 (fastest) 1.1 6144
34 * 3 (smallest) 5.1 4912
37 #define MD5SUM_SIZE_VS_SPEED 2
39 /**********************************************************************/
48 #include <sys/types.h>
49 #if defined HAVE_LIMITS_H
54 /* For some silly reason, this file uses backwards TRUE and FALSE conventions */
57 #define FALSE ((int) 1)
58 #define TRUE ((int) 0)
60 //----------------------------------------------------------------------------
62 //----------------------------------------------------------------------------
64 /* md5.c - Functions to compute MD5 message digest of files or memory blocks
65 * according to the definition of MD5 in RFC 1321 from April 1992.
66 * Copyright (C) 1995, 1996 Free Software Foundation, Inc.
68 * NOTE: The canonical source of this file is maintained with the GNU C
69 * Library. Bugs can be reported to bug-glibc@prep.ai.mit.edu.
71 * This program is free software; you can redistribute it and/or modify it
72 * under the terms of the GNU General Public License as published by the
73 * Free Software Foundation; either version 2, or (at your option) any
76 * This program is distributed in the hope that it will be useful,
77 * but WITHOUT ANY WARRANTY; without even the implied warranty of
78 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
79 * GNU General Public License for more details.
81 * You should have received a copy of the GNU General Public License
82 * along with this program; if not, write to the Free Software Foundation,
83 * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
86 /* Written by Ulrich Drepper <drepper@gnu.ai.mit.edu>, 1995. */
88 //----------------------------------------------------------------------------
90 //----------------------------------------------------------------------------
92 /* md5.h - Declaration of functions and data types used for MD5 sum
93 computing library functions.
94 Copyright (C) 1995, 1996 Free Software Foundation, Inc.
95 NOTE: The canonical source of this file is maintained with the GNU C
96 Library. Bugs can be reported to bug-glibc@prep.ai.mit.edu.
98 This program is free software; you can redistribute it and/or modify it
99 under the terms of the GNU General Public License as published by the
100 Free Software Foundation; either version 2, or (at your option) any
103 This program is distributed in the hope that it will be useful,
104 but WITHOUT ANY WARRANTY; without even the implied warranty of
105 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
106 GNU General Public License for more details.
108 You should have received a copy of the GNU General Public License
109 along with this program; if not, write to the Free Software Foundation,
110 Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
113 static const int _MD5_H = 1;
115 /* The following contortions are an attempt to use the C preprocessor
116 to determine an unsigned integral type that is 32 bits wide. An
117 alternative approach is to use autoconf's AC_CHECK_SIZEOF macro, but
118 doing that would require that the configure script compile and *run*
119 the resulting executable. Locally running cross-compiled executables
120 is usually not possible. */
122 typedef u_int32_t md5_uint32;
124 /* Structure to save state of computation between the single steps. */
138 * The following three functions are build up the low level used in
139 * the functions `md5_stream' and `md5_buffer'.
142 /* Initialize structure containing state of computation.
143 (RFC 1321, 3.3: Step 3) */
144 extern void md5_init_ctx __P ((struct md5_ctx *ctx));
146 /* Starting with the result of former calls of this function (or the
147 initialization function update the context for the next LEN bytes
149 It is necessary that LEN is a multiple of 64!!! */
150 extern void md5_process_block __P ((const void *buffer, size_t len,
151 struct md5_ctx *ctx));
153 /* Starting with the result of former calls of this function (or the
154 initialization function update the context for the next LEN bytes
156 It is NOT required that LEN is a multiple of 64. */
157 extern void md5_process_bytes __P ((const void *buffer, size_t len,
158 struct md5_ctx *ctx));
160 /* Process the remaining bytes in the buffer and put result from CTX
161 in first 16 bytes following RESBUF. The result is always in little
162 endian byte order, so that a byte-wise output yields to the wanted
163 ASCII representation of the message digest.
165 IMPORTANT: On some systems it is required that RESBUF is correctly
166 aligned for a 32 bits value. */
167 extern void *md5_finish_ctx __P ((struct md5_ctx *ctx, void *resbuf));
170 /* Put result from CTX in first 16 bytes following RESBUF. The result is
171 always in little endian byte order, so that a byte-wise output yields
172 to the wanted ASCII representation of the message digest.
174 IMPORTANT: On some systems it is required that RESBUF is correctly
175 aligned for a 32 bits value. */
176 extern void *md5_read_ctx __P ((const struct md5_ctx *ctx, void *resbuf));
179 /* Compute MD5 message digest for bytes read from STREAM. The
180 resulting message digest number will be written into the 16 bytes
181 beginning at RESBLOCK. */
182 extern int md5_stream __P ((FILE *stream, void *resblock));
184 /* Compute MD5 message digest for LEN bytes beginning at BUFFER. The
185 result is always in little endian byte order, so that a byte-wise
186 output yields to the wanted ASCII representation of the message
188 extern void *md5_buffer __P ((const char *buffer, size_t len, void *resblock));
192 //----------------------------------------------------------------------------
193 //--------end of md5.h
194 //----------------------------------------------------------------------------
196 /* Handle endian-ness */
197 #if __BYTE_ORDER == __LITTLE_ENDIAN
200 #define SWAP(n) ((n << 24) | ((n&65280)<<8) | ((n&16711680)>>8) | (n>>24))
205 #if MD5SUM_SIZE_VS_SPEED == 0
206 /* This array contains the bytes used to pad the buffer to the next
207 64-byte boundary. (RFC 1321, 3.1: Step 1) */
208 static const unsigned char fillbuf[64] = { 0x80, 0 /* , 0, 0, ... */ };
211 /* Initialize structure containing state of computation.
212 (RFC 1321, 3.3: Step 3) */
213 void md5_init_ctx(struct md5_ctx *ctx)
220 ctx->total[0] = ctx->total[1] = 0;
224 /* Put result from CTX in first 16 bytes following RESBUF. The result
225 must be in little endian byte order.
227 IMPORTANT: On some systems it is required that RESBUF is correctly
228 aligned for a 32 bits value. */
229 void *md5_read_ctx(const struct md5_ctx *ctx, void *resbuf)
231 ((md5_uint32 *) resbuf)[0] = SWAP(ctx->A);
232 ((md5_uint32 *) resbuf)[1] = SWAP(ctx->B);
233 ((md5_uint32 *) resbuf)[2] = SWAP(ctx->C);
234 ((md5_uint32 *) resbuf)[3] = SWAP(ctx->D);
239 /* Process the remaining bytes in the internal buffer and the usual
240 prolog according to the standard and write the result to RESBUF.
242 IMPORTANT: On some systems it is required that RESBUF is correctly
243 aligned for a 32 bits value. */
244 void *md5_finish_ctx(struct md5_ctx *ctx, void *resbuf)
246 /* Take yet unprocessed bytes into account. */
247 md5_uint32 bytes = ctx->buflen;
250 /* Now count remaining bytes. */
251 ctx->total[0] += bytes;
252 if (ctx->total[0] < bytes)
255 pad = bytes >= 56 ? 64 + 56 - bytes : 56 - bytes;
256 #if MD5SUM_SIZE_VS_SPEED > 0
257 memset(&ctx->buffer[bytes], 0, pad);
258 ctx->buffer[bytes] = 0x80;
260 memcpy(&ctx->buffer[bytes], fillbuf, pad);
263 /* Put the 64-bit file length in *bits* at the end of the buffer. */
264 *(md5_uint32 *) & ctx->buffer[bytes + pad] = SWAP(ctx->total[0] << 3);
265 *(md5_uint32 *) & ctx->buffer[bytes + pad + 4] =
266 SWAP( ((ctx->total[1] << 3) | (ctx->total[0] >> 29)) );
268 /* Process last bytes. */
269 md5_process_block(ctx->buffer, bytes + pad + 8, ctx);
271 return md5_read_ctx(ctx, resbuf);
274 /* Compute MD5 message digest for bytes read from STREAM. The
275 resulting message digest number will be written into the 16 bytes
276 beginning at RESBLOCK. */
277 int md5_stream(FILE *stream, void *resblock)
279 /* Important: BLOCKSIZE must be a multiple of 64. */
280 static const int BLOCKSIZE = 4096;
282 char buffer[BLOCKSIZE + 72];
285 /* Initialize the computation context. */
288 /* Iterate over full file contents. */
290 /* We read the file in blocks of BLOCKSIZE bytes. One call of the
291 computation function processes the whole buffer so that with the
292 next round of the loop another block can be read. */
296 /* Read block. Take care for partial reads. */
298 n = fread(buffer + sum, 1, BLOCKSIZE - sum, stream);
302 while (sum < BLOCKSIZE && n != 0);
303 if (n == 0 && ferror(stream))
306 /* If end of file is reached, end the loop. */
310 /* Process buffer with BLOCKSIZE bytes. Note that
313 md5_process_block(buffer, BLOCKSIZE, &ctx);
316 /* Add the last bytes if necessary. */
318 md5_process_bytes(buffer, sum, &ctx);
320 /* Construct result in desired memory. */
321 md5_finish_ctx(&ctx, resblock);
325 /* Compute MD5 message digest for LEN bytes beginning at BUFFER. The
326 result is always in little endian byte order, so that a byte-wise
327 output yields to the wanted ASCII representation of the message
329 void *md5_buffer(const char *buffer, size_t len, void *resblock)
333 /* Initialize the computation context. */
336 /* Process whole buffer but last len % 64 bytes. */
337 md5_process_bytes(buffer, len, &ctx);
339 /* Put result in desired memory area. */
340 return md5_finish_ctx(&ctx, resblock);
343 void md5_process_bytes(const void *buffer, size_t len, struct md5_ctx *ctx)
345 /* When we already have some bits in our internal buffer concatenate
346 both inputs first. */
347 if (ctx->buflen != 0) {
348 size_t left_over = ctx->buflen;
349 size_t add = 128 - left_over > len ? len : 128 - left_over;
351 memcpy(&ctx->buffer[left_over], buffer, add);
354 if (left_over + add > 64) {
355 md5_process_block(ctx->buffer, (left_over + add) & ~63, ctx);
356 /* The regions in the following copy operation cannot overlap. */
357 memcpy(ctx->buffer, &ctx->buffer[(left_over + add) & ~63],
358 (left_over + add) & 63);
359 ctx->buflen = (left_over + add) & 63;
362 buffer = (const char *) buffer + add;
366 /* Process available complete blocks. */
368 md5_process_block(buffer, len & ~63, ctx);
369 buffer = (const char *) buffer + (len & ~63);
373 /* Move remaining bytes in internal buffer. */
375 memcpy(ctx->buffer, buffer, len);
380 /* These are the four functions used in the four steps of the MD5 algorithm
381 and defined in the RFC 1321. The first function is a little bit optimized
382 (as found in Colin Plumbs public domain implementation). */
383 /* #define FF(b, c, d) ((b & c) | (~b & d)) */
384 #define FF(b, c, d) (d ^ (b & (c ^ d)))
385 #define FG(b, c, d) FF (d, b, c)
386 #define FH(b, c, d) (b ^ c ^ d)
387 #define FI(b, c, d) (c ^ (b | ~d))
389 /* Process LEN bytes of BUFFER, accumulating context into CTX.
390 It is assumed that LEN % 64 == 0. */
391 void md5_process_block(const void *buffer, size_t len, struct md5_ctx *ctx)
393 md5_uint32 correct_words[16];
394 const md5_uint32 *words = buffer;
395 size_t nwords = len / sizeof(md5_uint32);
396 const md5_uint32 *endp = words + nwords;
397 #if MD5SUM_SIZE_VS_SPEED > 0
398 static const md5_uint32 C_array[] = {
400 0xd76aa478, 0xe8c7b756, 0x242070db, 0xc1bdceee,
401 0xf57c0faf, 0x4787c62a, 0xa8304613, 0xfd469501,
402 0x698098d8, 0x8b44f7af, 0xffff5bb1, 0x895cd7be,
403 0x6b901122, 0xfd987193, 0xa679438e, 0x49b40821,
405 0xf61e2562, 0xc040b340, 0x265e5a51, 0xe9b6c7aa,
406 0xd62f105d, 0x2441453, 0xd8a1e681, 0xe7d3fbc8,
407 0x21e1cde6, 0xc33707d6, 0xf4d50d87, 0x455a14ed,
408 0xa9e3e905, 0xfcefa3f8, 0x676f02d9, 0x8d2a4c8a,
410 0xfffa3942, 0x8771f681, 0x6d9d6122, 0xfde5380c,
411 0xa4beea44, 0x4bdecfa9, 0xf6bb4b60, 0xbebfbc70,
412 0x289b7ec6, 0xeaa127fa, 0xd4ef3085, 0x4881d05,
413 0xd9d4d039, 0xe6db99e5, 0x1fa27cf8, 0xc4ac5665,
415 0xf4292244, 0x432aff97, 0xab9423a7, 0xfc93a039,
416 0x655b59c3, 0x8f0ccc92, 0xffeff47d, 0x85845dd1,
417 0x6fa87e4f, 0xfe2ce6e0, 0xa3014314, 0x4e0811a1,
418 0xf7537e82, 0xbd3af235, 0x2ad7d2bb, 0xeb86d391
421 static const char P_array[] = {
422 #if MD5SUM_SIZE_VS_SPEED > 1
423 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, /* 1 */
425 1, 6, 11, 0, 5, 10, 15, 4, 9, 14, 3, 8, 13, 2, 7, 12, /* 2 */
426 5, 8, 11, 14, 1, 4, 7, 10, 13, 0, 3, 6, 9, 12, 15, 2, /* 3 */
427 0, 7, 14, 5, 12, 3, 10, 1, 8, 15, 6, 13, 4, 11, 2, 9 /* 4 */
430 #if MD5SUM_SIZE_VS_SPEED > 1
431 static const char S_array[] = {
440 md5_uint32 A = ctx->A;
441 md5_uint32 B = ctx->B;
442 md5_uint32 C = ctx->C;
443 md5_uint32 D = ctx->D;
445 /* First increment the byte count. RFC 1321 specifies the possible
446 length of the file up to 2^64 bits. Here we only compute the
447 number of bytes. Do a double word increment. */
448 ctx->total[0] += len;
449 if (ctx->total[0] < len)
452 /* Process all bytes in the buffer with 64 bytes in each round of
454 while (words < endp) {
455 md5_uint32 *cwp = correct_words;
456 md5_uint32 A_save = A;
457 md5_uint32 B_save = B;
458 md5_uint32 C_save = C;
459 md5_uint32 D_save = D;
461 #if MD5SUM_SIZE_VS_SPEED > 1
462 #define CYCLIC(w, s) (w = (w << s) | (w >> (32 - s)))
464 const md5_uint32 *pc;
470 for ( i=0 ; i < 16 ; i++ ) {
471 cwp[i] = SWAP(words[i]);
475 #if MD5SUM_SIZE_VS_SPEED > 2
476 pc = C_array; pp = P_array; ps = S_array - 4;
478 for ( i = 0 ; i < 64 ; i++ ) {
479 if ((i&0x0f) == 0) ps += 4;
495 temp += cwp[(int)(*pp++)] + *pc++;
496 temp = CYCLIC (temp, ps[i&3]);
498 A = D; D = C; C = B; B = temp;
501 pc = C_array; pp = P_array; ps = S_array;
503 for ( i = 0 ; i < 16 ; i++ ) {
504 temp = A + FF(B,C,D) + cwp[(int)(*pp++)] + *pc++;
505 temp = CYCLIC (temp, ps[i&3]);
507 A = D; D = C; C = B; B = temp;
511 for ( i = 0 ; i < 16 ; i++ ) {
512 temp = A + FG(B,C,D) + cwp[(int)(*pp++)] + *pc++;
513 temp = CYCLIC (temp, ps[i&3]);
515 A = D; D = C; C = B; B = temp;
518 for ( i = 0 ; i < 16 ; i++ ) {
519 temp = A + FH(B,C,D) + cwp[(int)(*pp++)] + *pc++;
520 temp = CYCLIC (temp, ps[i&3]);
522 A = D; D = C; C = B; B = temp;
525 for ( i = 0 ; i < 16 ; i++ ) {
526 temp = A + FI(B,C,D) + cwp[(int)(*pp++)] + *pc++;
527 temp = CYCLIC (temp, ps[i&3]);
529 A = D; D = C; C = B; B = temp;
534 /* First round: using the given function, the context and a constant
535 the next context is computed. Because the algorithms processing
536 unit is a 32-bit word and it is determined to work on words in
537 little endian byte order we perhaps have to change the byte order
538 before the computation. To reduce the work for the next steps
539 we store the swapped words in the array CORRECT_WORDS. */
541 #define OP(a, b, c, d, s, T) \
544 a += FF (b, c, d) + (*cwp++ = SWAP (*words)) + T; \
551 /* It is unfortunate that C does not provide an operator for
552 cyclic rotation. Hope the C compiler is smart enough. */
553 #define CYCLIC(w, s) (w = (w << s) | (w >> (32 - s)))
555 /* Before we start, one word to the strange constants.
556 They are defined in RFC 1321 as
558 T[i] = (int) (4294967296.0 * fabs (sin (i))), i=1..64
561 #if MD5SUM_SIZE_VS_SPEED == 1
562 const md5_uint32 *pc;
568 #if MD5SUM_SIZE_VS_SPEED == 1
570 for ( i=0 ; i < 4 ; i++ ) {
571 OP(A, B, C, D, 7, *pc++);
572 OP(D, A, B, C, 12, *pc++);
573 OP(C, D, A, B, 17, *pc++);
574 OP(B, C, D, A, 22, *pc++);
577 OP(A, B, C, D, 7, 0xd76aa478);
578 OP(D, A, B, C, 12, 0xe8c7b756);
579 OP(C, D, A, B, 17, 0x242070db);
580 OP(B, C, D, A, 22, 0xc1bdceee);
581 OP(A, B, C, D, 7, 0xf57c0faf);
582 OP(D, A, B, C, 12, 0x4787c62a);
583 OP(C, D, A, B, 17, 0xa8304613);
584 OP(B, C, D, A, 22, 0xfd469501);
585 OP(A, B, C, D, 7, 0x698098d8);
586 OP(D, A, B, C, 12, 0x8b44f7af);
587 OP(C, D, A, B, 17, 0xffff5bb1);
588 OP(B, C, D, A, 22, 0x895cd7be);
589 OP(A, B, C, D, 7, 0x6b901122);
590 OP(D, A, B, C, 12, 0xfd987193);
591 OP(C, D, A, B, 17, 0xa679438e);
592 OP(B, C, D, A, 22, 0x49b40821);
595 /* For the second to fourth round we have the possibly swapped words
596 in CORRECT_WORDS. Redefine the macro to take an additional first
597 argument specifying the function to use. */
599 #define OP(f, a, b, c, d, k, s, T) \
602 a += f (b, c, d) + correct_words[k] + T; \
609 #if MD5SUM_SIZE_VS_SPEED == 1
611 for ( i=0 ; i < 4 ; i++ ) {
612 OP(FG, A, B, C, D, (int)(*pp++), 5, *pc++);
613 OP(FG, D, A, B, C, (int)(*pp++), 9, *pc++);
614 OP(FG, C, D, A, B, (int)(*pp++), 14, *pc++);
615 OP(FG, B, C, D, A, (int)(*pp++), 20, *pc++);
618 OP(FG, A, B, C, D, 1, 5, 0xf61e2562);
619 OP(FG, D, A, B, C, 6, 9, 0xc040b340);
620 OP(FG, C, D, A, B, 11, 14, 0x265e5a51);
621 OP(FG, B, C, D, A, 0, 20, 0xe9b6c7aa);
622 OP(FG, A, B, C, D, 5, 5, 0xd62f105d);
623 OP(FG, D, A, B, C, 10, 9, 0x02441453);
624 OP(FG, C, D, A, B, 15, 14, 0xd8a1e681);
625 OP(FG, B, C, D, A, 4, 20, 0xe7d3fbc8);
626 OP(FG, A, B, C, D, 9, 5, 0x21e1cde6);
627 OP(FG, D, A, B, C, 14, 9, 0xc33707d6);
628 OP(FG, C, D, A, B, 3, 14, 0xf4d50d87);
629 OP(FG, B, C, D, A, 8, 20, 0x455a14ed);
630 OP(FG, A, B, C, D, 13, 5, 0xa9e3e905);
631 OP(FG, D, A, B, C, 2, 9, 0xfcefa3f8);
632 OP(FG, C, D, A, B, 7, 14, 0x676f02d9);
633 OP(FG, B, C, D, A, 12, 20, 0x8d2a4c8a);
637 #if MD5SUM_SIZE_VS_SPEED == 1
638 for ( i=0 ; i < 4 ; i++ ) {
639 OP(FH, A, B, C, D, (int)(*pp++), 4, *pc++);
640 OP(FH, D, A, B, C, (int)(*pp++), 11, *pc++);
641 OP(FH, C, D, A, B, (int)(*pp++), 16, *pc++);
642 OP(FH, B, C, D, A, (int)(*pp++), 23, *pc++);
645 OP(FH, A, B, C, D, 5, 4, 0xfffa3942);
646 OP(FH, D, A, B, C, 8, 11, 0x8771f681);
647 OP(FH, C, D, A, B, 11, 16, 0x6d9d6122);
648 OP(FH, B, C, D, A, 14, 23, 0xfde5380c);
649 OP(FH, A, B, C, D, 1, 4, 0xa4beea44);
650 OP(FH, D, A, B, C, 4, 11, 0x4bdecfa9);
651 OP(FH, C, D, A, B, 7, 16, 0xf6bb4b60);
652 OP(FH, B, C, D, A, 10, 23, 0xbebfbc70);
653 OP(FH, A, B, C, D, 13, 4, 0x289b7ec6);
654 OP(FH, D, A, B, C, 0, 11, 0xeaa127fa);
655 OP(FH, C, D, A, B, 3, 16, 0xd4ef3085);
656 OP(FH, B, C, D, A, 6, 23, 0x04881d05);
657 OP(FH, A, B, C, D, 9, 4, 0xd9d4d039);
658 OP(FH, D, A, B, C, 12, 11, 0xe6db99e5);
659 OP(FH, C, D, A, B, 15, 16, 0x1fa27cf8);
660 OP(FH, B, C, D, A, 2, 23, 0xc4ac5665);
664 #if MD5SUM_SIZE_VS_SPEED == 1
665 for ( i=0 ; i < 4 ; i++ ) {
666 OP(FI, A, B, C, D, (int)(*pp++), 6, *pc++);
667 OP(FI, D, A, B, C, (int)(*pp++), 10, *pc++);
668 OP(FI, C, D, A, B, (int)(*pp++), 15, *pc++);
669 OP(FI, B, C, D, A, (int)(*pp++), 21, *pc++);
672 OP(FI, A, B, C, D, 0, 6, 0xf4292244);
673 OP(FI, D, A, B, C, 7, 10, 0x432aff97);
674 OP(FI, C, D, A, B, 14, 15, 0xab9423a7);
675 OP(FI, B, C, D, A, 5, 21, 0xfc93a039);
676 OP(FI, A, B, C, D, 12, 6, 0x655b59c3);
677 OP(FI, D, A, B, C, 3, 10, 0x8f0ccc92);
678 OP(FI, C, D, A, B, 10, 15, 0xffeff47d);
679 OP(FI, B, C, D, A, 1, 21, 0x85845dd1);
680 OP(FI, A, B, C, D, 8, 6, 0x6fa87e4f);
681 OP(FI, D, A, B, C, 15, 10, 0xfe2ce6e0);
682 OP(FI, C, D, A, B, 6, 15, 0xa3014314);
683 OP(FI, B, C, D, A, 13, 21, 0x4e0811a1);
684 OP(FI, A, B, C, D, 4, 6, 0xf7537e82);
685 OP(FI, D, A, B, C, 11, 10, 0xbd3af235);
686 OP(FI, C, D, A, B, 2, 15, 0x2ad7d2bb);
687 OP(FI, B, C, D, A, 9, 21, 0xeb86d391);
691 /* Add the starting values of the context. */
698 /* Put checksum in context given as argument. */
705 //----------------------------------------------------------------------------
706 //--------end of md5.c
707 //----------------------------------------------------------------------------
709 #define ISWHITE(c) ((c) == ' ' || (c) == '\t')
710 #define IN_CTYPE_DOMAIN(c) 1
711 #define ISXDIGIT(c) (IN_CTYPE_DOMAIN (c) && isxdigit (c))
712 #define STREQ(a, b) (strcmp ((a), (b)) == 0)
713 #define TOLOWER(Ch) tolower (Ch)
714 #define OPENOPTS(BINARY) "r"
716 /* The minimum length of a valid digest line in a file produced
717 by `md5sum FILE' and read by `md5sum -c'. This length does
718 not include any newline character at the end of a line. */
719 static const int MIN_DIGEST_LINE_LENGTH = 35; /* 32 - message digest length
720 2 - blank and binary indicator
721 1 - minimum filename length */
723 static int have_read_stdin; /* Nonzero if any of the files read were
724 the standard input. */
726 static int status_only = 0; /* With -c, don't generate any output.
727 The exit code indicates success or failure */
728 static int warn = 0; /* With -w, print a message to standard error warning
729 about each improperly formatted MD5 checksum line */
731 static int split_3(char *s,
738 int escaped_filename = 0;
740 while (ISWHITE(s[i]))
743 /* The line must have at least 35 (36 if the first is a backslash)
744 more characters to contain correct message digest information.
745 Ignore this line if it is too short. */
746 if (!(s_len - i >= MIN_DIGEST_LINE_LENGTH
747 || (s[i] == '\\' && s_len - i >= 1 + MIN_DIGEST_LINE_LENGTH)))
752 escaped_filename = 1;
754 *u = (unsigned char *) &s[i];
756 /* The first field has to be the 32-character hexadecimal
757 representation of the message digest. If it is not followed
758 immediately by a white space it's an error. */
765 if (s[i] != ' ' && s[i] != '*')
767 *binary = (s[i++] == '*');
769 /* All characters between the type indicator and end of line are
770 significant -- that includes leading and trailing white space. */
773 if (escaped_filename) {
774 /* Translate each `\n' string in the file name to a NEWLINE,
775 and each `\\' string to a backslash. */
782 if (i == s_len - 1) {
783 /* A valid line does not end with a backslash. */
795 /* Only `\' or `n' may follow a backslash. */
801 /* The file name may not contain a NUL. */
815 static int hex_digits(unsigned char const *s)
825 /* An interface to md5_stream. Operate on FILENAME (it may be "-") and
826 put the result in *MD5_RESULT. Return non-zero upon failure, zero
827 to indicate success. */
828 static int md5_file(const char *filename,
830 unsigned char *md5_result)
834 if (STREQ(filename, "-")) {
838 fp = fopen(filename, OPENOPTS(binary));
840 perror_msg("%s", filename);
845 if (md5_stream(fp, md5_result)) {
846 perror_msg("%s", filename);
853 if (fp != stdin && fclose(fp) == EOF) {
854 perror_msg("%s", filename);
861 static int md5_check(const char *checkfile_name)
863 FILE *checkfile_stream;
864 int n_properly_formated_lines = 0;
865 int n_mismatched_checksums = 0;
866 int n_open_or_read_failures = 0;
867 unsigned char md5buffer[16];
871 if (STREQ(checkfile_name, "-")) {
873 checkfile_stream = stdin;
875 checkfile_stream = fopen(checkfile_name, "r");
876 if (checkfile_stream == NULL) {
877 perror_msg("%s", checkfile_name);
887 unsigned char *md5num;
892 fgets(line, BUFSIZ-1, checkfile_stream);
893 line_length = strlen(line);
895 if (line_length <= 0 || line==NULL)
898 /* Ignore comment lines, which begin with a '#' character. */
902 /* Remove any trailing newline. */
903 if (line[line_length - 1] == '\n')
904 line[--line_length] = '\0';
906 if (split_3(line, line_length, &md5num, &binary, &filename)
907 || !hex_digits(md5num)) {
909 error_msg("%s: %lu: improperly formatted MD5 checksum line",
910 checkfile_name, (unsigned long) line_number);
913 static const char bin2hex[] = {
920 ++n_properly_formated_lines;
922 if (md5_file(filename, binary, md5buffer)) {
923 ++n_open_or_read_failures;
925 printf("%s: FAILED open or read\n", filename);
930 /* Compare generated binary number with text representation
931 in check file. Ignore case of hex digits. */
932 for (cnt = 0; cnt < 16; ++cnt) {
933 if (TOLOWER(md5num[2 * cnt])
934 != bin2hex[md5buffer[cnt] >> 4]
935 || (TOLOWER(md5num[2 * cnt + 1])
936 != (bin2hex[md5buffer[cnt] & 0xf])))
940 ++n_mismatched_checksums;
943 printf("%s: %s\n", filename,
944 (cnt != 16 ? "FAILED" : "OK"));
951 while (!feof(checkfile_stream) && !ferror(checkfile_stream));
953 if (ferror(checkfile_stream)) {
954 error_msg("%s: read error", checkfile_name);
958 if (checkfile_stream != stdin && fclose(checkfile_stream) == EOF) {
959 perror_msg("md5sum: %s", checkfile_name);
963 if (n_properly_formated_lines == 0) {
964 /* Warn if no tests are found. */
965 error_msg("%s: no properly formatted MD5 checksum lines found",
970 int n_computed_checkums = (n_properly_formated_lines
971 - n_open_or_read_failures);
973 if (n_open_or_read_failures > 0) {
974 error_msg("WARNING: %d of %d listed files could not be read",
975 n_open_or_read_failures, n_properly_formated_lines);
979 if (n_mismatched_checksums > 0) {
980 error_msg("WARNING: %d of %d computed checksums did NOT match",
981 n_mismatched_checksums, n_computed_checkums);
987 return ((n_properly_formated_lines > 0 && n_mismatched_checksums == 0
988 && n_open_or_read_failures == 0) ? 0 : 1);
991 int md5sum_main(int argc,
994 unsigned char md5buffer[16];
997 char **string = NULL;
998 size_t n_strings = 0;
1000 int file_type_specified = 0;
1003 while ((opt = getopt(argc, argv, "g:bcstw")) != -1) {
1005 case 'g': { /* read a string */
1007 string = (char **) xmalloc ((argc - 1) * sizeof (char *));
1009 string[n_strings++] = optarg;
1013 case 'b': /* read files in binary mode */
1014 file_type_specified = 1;
1018 case 'c': /* check MD5 sums against given list */
1022 case 's': /* don't output anything, status code shows success */
1027 case 't': /* read files in text mode (default) */
1028 file_type_specified = 1;
1032 case 'w': /* warn about improperly formated MD5 checksum lines */
1042 if (file_type_specified && do_check) {
1043 error_msg_and_die("the -b and -t options are meaningless when verifying checksums");
1046 if (n_strings > 0 && do_check) {
1047 error_msg_and_die("the -g and -c options are mutually exclusive");
1050 if (status_only && !do_check) {
1051 error_msg_and_die("the -s option is meaningful only when verifying checksums");
1054 if (warn && !do_check) {
1055 error_msg_and_die("the -w option is meaningful only when verifying checksums");
1058 if (n_strings > 0) {
1061 if (optind < argc) {
1062 error_msg_and_die("no files may be specified when using -g");
1064 for (i = 0; i < n_strings; ++i) {
1066 md5_buffer (string[i], strlen (string[i]), md5buffer);
1068 for (cnt = 0; cnt < 16; ++cnt)
1069 printf ("%02x", md5buffer[cnt]);
1071 printf (" \"%s\"\n", string[i]);
1073 } else if (do_check) {
1074 if (optind + 1 < argc) {
1075 error_msg("only one argument may be specified when using -c");
1078 err = md5_check ((optind == argc) ? "-" : argv[optind]);
1083 for (; optind < argc; ++optind) {
1085 char *file = argv[optind];
1087 fail = md5_file (file, binary, md5buffer);
1089 if (!fail && STREQ(file, "-")) {
1091 for (i = 0; i < 16; ++i)
1092 printf ("%02x", md5buffer[i]);
1096 /* Output a leading backslash if the file name contains
1097 a newline or backslash. */
1098 if (strchr (file, '\n') || strchr (file, '\\'))
1101 for (i = 0; i < 16; ++i)
1102 printf ("%02x", md5buffer[i]);
1110 /* Translate each NEWLINE byte to the string, "\\n",
1111 and each backslash to "\\\\". */
1112 for (i = 0; i < strlen (file); ++i) {
1115 fputs ("\\n", stdout);
1119 fputs ("\\\\", stdout);
1132 if (fclose (stdout) == EOF) {
1133 error_msg_and_die("write error");
1136 if (have_read_stdin && fclose (stdin) == EOF) {
1137 error_msg_and_die("standard input");
1141 return EXIT_SUCCESS;
1143 return EXIT_FAILURE;