00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048 #include "md5.hpp"
00049
00050 #include <assert.h>
00051 #include <iostream>
00052 #include <string.h>
00053
00054
00055 #include "global.hpp"
00056
00057
00058
00059
00060
00061 MD5::MD5()
00062 : state()
00063 , count()
00064 , buffer()
00065 , digest()
00066 , finalized(0)
00067 {
00068 init();
00069 }
00070
00071
00072
00073
00074
00075 void MD5::update (uint1 *input, uint4 input_length) {
00076
00077 uint4 input_index, buffer_index;
00078 uint4 buffer_space;
00079
00080 if (finalized){
00081 std::cerr << "MD5::update: Can't update a finalized digest!" << std::endl;
00082 return;
00083 }
00084
00085
00086 buffer_index = static_cast<uint4>(((count[0] >> 3) & 0x3F));
00087
00088
00089 if ( (count[0] += (static_cast<uint4>(input_length) << 3))<(static_cast<uint4>(input_length) << 3) )
00090 count[1]++;
00091
00092 count[1] += (static_cast<uint4>(input_length) >> 29);
00093
00094
00095 buffer_space = 64 - buffer_index;
00096
00097
00098 if (input_length >= buffer_space) {
00099
00100 memcpy (buffer + buffer_index, input, buffer_space);
00101 transform (buffer);
00102
00103
00104 for (input_index = buffer_space; input_index + 63 < input_length;
00105 input_index += 64)
00106 transform (input+input_index);
00107
00108 buffer_index = 0;
00109 }
00110 else
00111 input_index=0;
00112
00113
00114
00115 memcpy(buffer+buffer_index, input+input_index, input_length-input_index);
00116 }
00117
00118
00119
00120
00121
00122 void MD5::finalize (){
00123
00124 uint1 bits[8];
00125 uint4 index, padLen;
00126 static uint1 PADDING[64]={
00127 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00128 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
00129 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
00130 };
00131
00132 if (finalized){
00133 std::cerr << "MD5::finalize: Already finalized this digest!" << std::endl;
00134 return;
00135 }
00136
00137
00138 encode (bits, count, 8);
00139
00140
00141 index = static_cast<uint4>((count[0] >> 3) & 0x3f);
00142 padLen = (index < 56) ? (56 - index) : (120 - index);
00143 update (PADDING, padLen);
00144
00145
00146 update (bits, 8);
00147
00148
00149 encode (digest, state, 16);
00150
00151
00152 memset (buffer, 0, sizeof(*buffer));
00153
00154 finalized=1;
00155
00156 }
00157
00158
00159 MD5::uint1 *MD5::raw_digest()
00160 {
00161 static uint1 s[16];
00162
00163 if (!finalized){
00164 std::cerr << "MD5::raw_digest: Can't get digest if you haven't "<<
00165 "finalized the digest!" <<std::endl;
00166 return ( const_cast<uint1*>(reinterpret_cast<const uint1*>("")));
00167 }
00168
00169 memcpy(s, digest, 16);
00170 return s;
00171 }
00172
00173
00174
00175 void MD5::init(){
00176 finalized=0;
00177
00178
00179 count[0] = 0;
00180 count[1] = 0;
00181
00182
00183 state[0] = 0x67452301;
00184 state[1] = 0xefcdab89;
00185 state[2] = 0x98badcfe;
00186 state[3] = 0x10325476;
00187 }
00188
00189
00190
00191
00192
00193
00194
00195 #define S11 7
00196 #define S12 12
00197 #define S13 17
00198 #define S14 22
00199 #define S21 5
00200 #define S22 9
00201 #define S23 14
00202 #define S24 20
00203 #define S31 4
00204 #define S32 11
00205 #define S33 16
00206 #define S34 23
00207 #define S41 6
00208 #define S42 10
00209 #define S43 15
00210 #define S44 21
00211
00212
00213
00214
00215
00216 void MD5::transform (uint1 block[64]){
00217
00218 uint4 a = state[0], b = state[1], c = state[2], d = state[3], x[16];
00219
00220 decode (x, block, 64);
00221
00222 assert(!finalized);
00223
00224
00225 FF (a, b, c, d, x[ 0], S11, 0xd76aa478);
00226 FF (d, a, b, c, x[ 1], S12, 0xe8c7b756);
00227 FF (c, d, a, b, x[ 2], S13, 0x242070db);
00228 FF (b, c, d, a, x[ 3], S14, 0xc1bdceee);
00229 FF (a, b, c, d, x[ 4], S11, 0xf57c0faf);
00230 FF (d, a, b, c, x[ 5], S12, 0x4787c62a);
00231 FF (c, d, a, b, x[ 6], S13, 0xa8304613);
00232 FF (b, c, d, a, x[ 7], S14, 0xfd469501);
00233 FF (a, b, c, d, x[ 8], S11, 0x698098d8);
00234 FF (d, a, b, c, x[ 9], S12, 0x8b44f7af);
00235 FF (c, d, a, b, x[10], S13, 0xffff5bb1);
00236 FF (b, c, d, a, x[11], S14, 0x895cd7be);
00237 FF (a, b, c, d, x[12], S11, 0x6b901122);
00238 FF (d, a, b, c, x[13], S12, 0xfd987193);
00239 FF (c, d, a, b, x[14], S13, 0xa679438e);
00240 FF (b, c, d, a, x[15], S14, 0x49b40821);
00241
00242
00243 GG (a, b, c, d, x[ 1], S21, 0xf61e2562);
00244 GG (d, a, b, c, x[ 6], S22, 0xc040b340);
00245 GG (c, d, a, b, x[11], S23, 0x265e5a51);
00246 GG (b, c, d, a, x[ 0], S24, 0xe9b6c7aa);
00247 GG (a, b, c, d, x[ 5], S21, 0xd62f105d);
00248 GG (d, a, b, c, x[10], S22, 0x2441453);
00249 GG (c, d, a, b, x[15], S23, 0xd8a1e681);
00250 GG (b, c, d, a, x[ 4], S24, 0xe7d3fbc8);
00251 GG (a, b, c, d, x[ 9], S21, 0x21e1cde6);
00252 GG (d, a, b, c, x[14], S22, 0xc33707d6);
00253 GG (c, d, a, b, x[ 3], S23, 0xf4d50d87);
00254 GG (b, c, d, a, x[ 8], S24, 0x455a14ed);
00255 GG (a, b, c, d, x[13], S21, 0xa9e3e905);
00256 GG (d, a, b, c, x[ 2], S22, 0xfcefa3f8);
00257 GG (c, d, a, b, x[ 7], S23, 0x676f02d9);
00258 GG (b, c, d, a, x[12], S24, 0x8d2a4c8a);
00259
00260
00261 HH (a, b, c, d, x[ 5], S31, 0xfffa3942);
00262 HH (d, a, b, c, x[ 8], S32, 0x8771f681);
00263 HH (c, d, a, b, x[11], S33, 0x6d9d6122);
00264 HH (b, c, d, a, x[14], S34, 0xfde5380c);
00265 HH (a, b, c, d, x[ 1], S31, 0xa4beea44);
00266 HH (d, a, b, c, x[ 4], S32, 0x4bdecfa9);
00267 HH (c, d, a, b, x[ 7], S33, 0xf6bb4b60);
00268 HH (b, c, d, a, x[10], S34, 0xbebfbc70);
00269 HH (a, b, c, d, x[13], S31, 0x289b7ec6);
00270 HH (d, a, b, c, x[ 0], S32, 0xeaa127fa);
00271 HH (c, d, a, b, x[ 3], S33, 0xd4ef3085);
00272 HH (b, c, d, a, x[ 6], S34, 0x4881d05);
00273 HH (a, b, c, d, x[ 9], S31, 0xd9d4d039);
00274 HH (d, a, b, c, x[12], S32, 0xe6db99e5);
00275 HH (c, d, a, b, x[15], S33, 0x1fa27cf8);
00276 HH (b, c, d, a, x[ 2], S34, 0xc4ac5665);
00277
00278
00279 II (a, b, c, d, x[ 0], S41, 0xf4292244);
00280 II (d, a, b, c, x[ 7], S42, 0x432aff97);
00281 II (c, d, a, b, x[14], S43, 0xab9423a7);
00282 II (b, c, d, a, x[ 5], S44, 0xfc93a039);
00283 II (a, b, c, d, x[12], S41, 0x655b59c3);
00284 II (d, a, b, c, x[ 3], S42, 0x8f0ccc92);
00285 II (c, d, a, b, x[10], S43, 0xffeff47d);
00286 II (b, c, d, a, x[ 1], S44, 0x85845dd1);
00287 II (a, b, c, d, x[ 8], S41, 0x6fa87e4f);
00288 II (d, a, b, c, x[15], S42, 0xfe2ce6e0);
00289 II (c, d, a, b, x[ 6], S43, 0xa3014314);
00290 II (b, c, d, a, x[13], S44, 0x4e0811a1);
00291 II (a, b, c, d, x[ 4], S41, 0xf7537e82);
00292 II (d, a, b, c, x[11], S42, 0xbd3af235);
00293 II (c, d, a, b, x[ 2], S43, 0x2ad7d2bb);
00294 II (b, c, d, a, x[ 9], S44, 0xeb86d391);
00295
00296 state[0] += a;
00297 state[1] += b;
00298 state[2] += c;
00299 state[3] += d;
00300
00301
00302 memset ( reinterpret_cast<uint1*>(x), 0, sizeof(x));
00303
00304 }
00305
00306
00307
00308
00309
00310 void MD5::encode (uint1 *output, uint4 *input, uint4 len) {
00311
00312 uint4 i, j;
00313
00314 for (i = 0, j = 0; j < len; i++, j += 4) {
00315 output[j] = static_cast<uint1> (input[i] & 0xff);
00316 output[j+1] = static_cast<uint1>((input[i] >> 8) & 0xff);
00317 output[j+2] = static_cast<uint1>((input[i] >> 16) & 0xff);
00318 output[j+3] = static_cast<uint1>((input[i] >> 24) & 0xff);
00319 }
00320 }
00321
00322
00323
00324
00325
00326
00327 void MD5::decode (uint4 *output, uint1 *input, uint4 len){
00328
00329 uint4 i, j;
00330
00331 for (i = 0, j = 0; j < len; i++, j += 4)
00332 output[i] = (static_cast<uint4>(input[j]))
00333 | ((static_cast<uint4>(input[j+1])) << 8)
00334 | ((static_cast<uint4>(input[j+2])) << 16)
00335 | ((static_cast<uint4>(input[j+3])) << 24);
00336 }
00337
00338
00339
00340
00341
00342
00343 inline MD5::uint4 MD5::rotate_left (uint4 x, uint4 n){
00344 return (x << n) | (x >> (32-n)) ;
00345 }
00346
00347
00348
00349
00350
00351
00352 inline MD5::uint4 MD5::F (uint4 x, uint4 y, uint4 z){
00353 return (x & y) | (~x & z);
00354 }
00355
00356 inline MD5::uint4 MD5::G (uint4 x, uint4 y, uint4 z){
00357 return (x & z) | (y & ~z);
00358 }
00359
00360 inline MD5::uint4 MD5::H (uint4 x, uint4 y, uint4 z){
00361 return x ^ y ^ z;
00362 }
00363
00364 inline MD5::uint4 MD5::I (uint4 x, uint4 y, uint4 z){
00365 return y ^ (x | ~z);
00366 }
00367
00368
00369
00370
00371
00372
00373
00374 inline void MD5::FF(uint4& a, uint4 b, uint4 c, uint4 d, uint4 x,
00375 uint4 s, uint4 ac){
00376 a += F(b, c, d) + x + ac;
00377 a = rotate_left (a, s) +b;
00378 }
00379
00380 inline void MD5::GG(uint4& a, uint4 b, uint4 c, uint4 d, uint4 x,
00381 uint4 s, uint4 ac){
00382 a += G(b, c, d) + x + ac;
00383 a = rotate_left (a, s) +b;
00384 }
00385
00386 inline void MD5::HH(uint4& a, uint4 b, uint4 c, uint4 d, uint4 x,
00387 uint4 s, uint4 ac){
00388 a += H(b, c, d) + x + ac;
00389 a = rotate_left (a, s) +b;
00390 }
00391
00392 inline void MD5::II(uint4& a, uint4 b, uint4 c, uint4 d, uint4 x,
00393 uint4 s, uint4 ac){
00394 a += I(b, c, d) + x + ac;
00395 a = rotate_left (a, s) +b;
00396 }