00001
00005 #include "system.h"
00006 #include "rpmio_internal.h"
00007 #include "debug.h"
00008
00009
00010 typedef unsigned int uint32;
00011 typedef unsigned char byte;
00012
00013
00014
00015
00019 struct DIGEST_CTX_s {
00020 rpmDigestFlags flags;
00021 uint32 digestlen;
00022 uint32 datalen;
00023 void (*transform) (DIGEST_CTX);
00024 int doByteReverse;
00025 uint32 bits[2];
00026 uint32 digest[8];
00027 byte in[64];
00028 };
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00063
00064 #define f1(x,y,z) ( z ^ ( x & ( y ^ z ) ) )
00065 #define f2(x,y,z) ( x ^ y ^ z )
00066
00067 #define f3(x,y,z) ( ( x & y ) | ( z & ( x | y ) ) )
00068 #define f4(x,y,z) ( x ^ y ^ z )
00069
00073 #define K1 0x5A827999L
00074 #define K2 0x6ED9EBA1L
00075 #define K3 0x8F1BBCDCL
00076 #define K4 0xCA62C1D6L
00077
00081 #define ROTL(n,X) ( ( (X) << (n) ) | ( (X) >> ( 32 - (n) ) ) )
00082
00100 #define expand(W,i) ( W[ i & 15 ] = \
00101 ROTL( 1, ( W[ i & 15 ] ^ W[ (i - 14) & 15 ] ^ \
00102 W[ (i - 8) & 15 ] ^ W[ (i - 3) & 15 ] ) ) )
00103
00122 #define subRound(a, b, c, d, e, f, k, data) \
00123 ( e += ROTL( 5, a ) + f( b, c, d ) + k + data, b = ROTL( 30, b ) )
00124
00140 static void
00141 SHA1Transform(DIGEST_CTX ctx)
00142 {
00143 uint32 * in = (uint32 *) ctx->in;
00144 uint32 A, B, C, D, E;
00145 #ifdef SHA_DEBUG
00146 int i;
00147 #define DPRINTF(_a) fprintf _a
00148 #else
00149 #define DPRINTF(_a)
00150 #endif
00151
00152
00153 A = ctx->digest[0];
00154 B = ctx->digest[1];
00155 C = ctx->digest[2];
00156 D = ctx->digest[3];
00157 E = ctx->digest[4];
00158
00159 #ifdef SHA_DEBUG
00160 for (i = 0; i < 16; i++)
00161 DPRINTF((stderr, "W[%2d]: %08X\n", i, in[i]));
00162 #endif
00163
00164 #ifdef SHA_DEBUG
00165 i = 0;
00166 #endif
00167 subRound( A, B, C, D, E, f1, K1, in[ 0] );
00168 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00169 subRound( E, A, B, C, D, f1, K1, in[ 1] );
00170 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00171 subRound( D, E, A, B, C, f1, K1, in[ 2] );
00172 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00173 subRound( C, D, E, A, B, f1, K1, in[ 3] );
00174 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00175 subRound( B, C, D, E, A, f1, K1, in[ 4] );
00176 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00177 subRound( A, B, C, D, E, f1, K1, in[ 5] );
00178 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00179 subRound( E, A, B, C, D, f1, K1, in[ 6] );
00180 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00181 subRound( D, E, A, B, C, f1, K1, in[ 7] );
00182 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00183 subRound( C, D, E, A, B, f1, K1, in[ 8] );
00184 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00185 subRound( B, C, D, E, A, f1, K1, in[ 9] );
00186 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00187 subRound( A, B, C, D, E, f1, K1, in[10] );
00188 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00189 subRound( E, A, B, C, D, f1, K1, in[11] );
00190 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00191 subRound( D, E, A, B, C, f1, K1, in[12] );
00192 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00193 subRound( C, D, E, A, B, f1, K1, in[13] );
00194 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00195 subRound( B, C, D, E, A, f1, K1, in[14] );
00196 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00197 subRound( A, B, C, D, E, f1, K1, in[15] );
00198 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00199 subRound( E, A, B, C, D, f1, K1, expand( in, 16 ) );
00200 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00201 subRound( D, E, A, B, C, f1, K1, expand( in, 17 ) );
00202 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00203 subRound( C, D, E, A, B, f1, K1, expand( in, 18 ) );
00204 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00205 subRound( B, C, D, E, A, f1, K1, expand( in, 19 ) );
00206
00207 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00208 subRound( A, B, C, D, E, f2, K2, expand( in, 20 ) );
00209 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00210 subRound( E, A, B, C, D, f2, K2, expand( in, 21 ) );
00211 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00212 subRound( D, E, A, B, C, f2, K2, expand( in, 22 ) );
00213 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00214 subRound( C, D, E, A, B, f2, K2, expand( in, 23 ) );
00215 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00216 subRound( B, C, D, E, A, f2, K2, expand( in, 24 ) );
00217 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00218 subRound( A, B, C, D, E, f2, K2, expand( in, 25 ) );
00219 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00220 subRound( E, A, B, C, D, f2, K2, expand( in, 26 ) );
00221 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00222 subRound( D, E, A, B, C, f2, K2, expand( in, 27 ) );
00223 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00224 subRound( C, D, E, A, B, f2, K2, expand( in, 28 ) );
00225 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00226 subRound( B, C, D, E, A, f2, K2, expand( in, 29 ) );
00227 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00228 subRound( A, B, C, D, E, f2, K2, expand( in, 30 ) );
00229 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00230 subRound( E, A, B, C, D, f2, K2, expand( in, 31 ) );
00231 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00232 subRound( D, E, A, B, C, f2, K2, expand( in, 32 ) );
00233 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00234 subRound( C, D, E, A, B, f2, K2, expand( in, 33 ) );
00235 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00236 subRound( B, C, D, E, A, f2, K2, expand( in, 34 ) );
00237 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00238 subRound( A, B, C, D, E, f2, K2, expand( in, 35 ) );
00239 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00240 subRound( E, A, B, C, D, f2, K2, expand( in, 36 ) );
00241 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00242 subRound( D, E, A, B, C, f2, K2, expand( in, 37 ) );
00243 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00244 subRound( C, D, E, A, B, f2, K2, expand( in, 38 ) );
00245 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00246 subRound( B, C, D, E, A, f2, K2, expand( in, 39 ) );
00247
00248 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00249 subRound( A, B, C, D, E, f3, K3, expand( in, 40 ) );
00250 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00251 subRound( E, A, B, C, D, f3, K3, expand( in, 41 ) );
00252 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00253 subRound( D, E, A, B, C, f3, K3, expand( in, 42 ) );
00254 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00255 subRound( C, D, E, A, B, f3, K3, expand( in, 43 ) );
00256 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00257 subRound( B, C, D, E, A, f3, K3, expand( in, 44 ) );
00258 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00259 subRound( A, B, C, D, E, f3, K3, expand( in, 45 ) );
00260 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00261 subRound( E, A, B, C, D, f3, K3, expand( in, 46 ) );
00262 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00263 subRound( D, E, A, B, C, f3, K3, expand( in, 47 ) );
00264 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00265 subRound( C, D, E, A, B, f3, K3, expand( in, 48 ) );
00266 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00267 subRound( B, C, D, E, A, f3, K3, expand( in, 49 ) );
00268 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00269 subRound( A, B, C, D, E, f3, K3, expand( in, 50 ) );
00270 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00271 subRound( E, A, B, C, D, f3, K3, expand( in, 51 ) );
00272 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00273 subRound( D, E, A, B, C, f3, K3, expand( in, 52 ) );
00274 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00275 subRound( C, D, E, A, B, f3, K3, expand( in, 53 ) );
00276 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00277 subRound( B, C, D, E, A, f3, K3, expand( in, 54 ) );
00278 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00279 subRound( A, B, C, D, E, f3, K3, expand( in, 55 ) );
00280 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00281 subRound( E, A, B, C, D, f3, K3, expand( in, 56 ) );
00282 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00283 subRound( D, E, A, B, C, f3, K3, expand( in, 57 ) );
00284 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00285 subRound( C, D, E, A, B, f3, K3, expand( in, 58 ) );
00286 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00287 subRound( B, C, D, E, A, f3, K3, expand( in, 59 ) );
00288
00289 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00290 subRound( A, B, C, D, E, f4, K4, expand( in, 60 ) );
00291 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00292 subRound( E, A, B, C, D, f4, K4, expand( in, 61 ) );
00293 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00294 subRound( D, E, A, B, C, f4, K4, expand( in, 62 ) );
00295 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00296 subRound( C, D, E, A, B, f4, K4, expand( in, 63 ) );
00297 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00298 subRound( B, C, D, E, A, f4, K4, expand( in, 64 ) );
00299 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00300 subRound( A, B, C, D, E, f4, K4, expand( in, 65 ) );
00301 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00302 subRound( E, A, B, C, D, f4, K4, expand( in, 66 ) );
00303 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00304 subRound( D, E, A, B, C, f4, K4, expand( in, 67 ) );
00305 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00306 subRound( C, D, E, A, B, f4, K4, expand( in, 68 ) );
00307 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00308 subRound( B, C, D, E, A, f4, K4, expand( in, 69 ) );
00309 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00310 subRound( A, B, C, D, E, f4, K4, expand( in, 70 ) );
00311 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00312 subRound( E, A, B, C, D, f4, K4, expand( in, 71 ) );
00313 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00314 subRound( D, E, A, B, C, f4, K4, expand( in, 72 ) );
00315 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00316 subRound( C, D, E, A, B, f4, K4, expand( in, 73 ) );
00317 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00318 subRound( B, C, D, E, A, f4, K4, expand( in, 74 ) );
00319 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, A,B,C,D,E ));
00320 subRound( A, B, C, D, E, f4, K4, expand( in, 75 ) );
00321 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, E,A,B,C,D ));
00322 subRound( E, A, B, C, D, f4, K4, expand( in, 76 ) );
00323 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, D,E,A,B,C ));
00324 subRound( D, E, A, B, C, f4, K4, expand( in, 77 ) );
00325 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, C,D,E,A,B ));
00326 subRound( C, D, E, A, B, f4, K4, expand( in, 78 ) );
00327 DPRINTF((stderr, "%5d: %08X %08X %08X %08X %08X\n", i++, B,C,D,E,A ));
00328 subRound( B, C, D, E, A, f4, K4, expand( in, 79 ) );
00329
00330
00331 ctx->digest[0] += A;
00332 ctx->digest[1] += B;
00333 ctx->digest[2] += C;
00334 ctx->digest[3] += D;
00335 ctx->digest[4] += E;
00336 }
00337
00338
00339
00340
00341
00342
00343
00344
00345
00346
00347
00348
00349
00350
00351
00352
00353
00354
00356
00357 #define F1(x, y, z) (z ^ (x & (y ^ z)))
00358 #define F2(x, y, z) F1(z, x, y)
00359 #define F3(x, y, z) (x ^ y ^ z)
00360 #define F4(x, y, z) (y ^ (x | ~z))
00361
00363 #define MD5STEP(f, w, x, y, z, data, s) \
00364 ( w += f(x, y, z) + data, w = w<<s | w>>(32-s), w += x )
00365
00371 static void
00372 MD5Transform(DIGEST_CTX ctx)
00373 {
00374 register uint32 * in = (uint32 *)ctx->in;
00375 register uint32 a = ctx->digest[0];
00376 register uint32 b = ctx->digest[1];
00377 register uint32 c = ctx->digest[2];
00378 register uint32 d = ctx->digest[3];
00379
00380 MD5STEP(F1, a, b, c, d, in[0] + 0xd76aa478, 7);
00381 MD5STEP(F1, d, a, b, c, in[1] + 0xe8c7b756, 12);
00382 MD5STEP(F1, c, d, a, b, in[2] + 0x242070db, 17);
00383 MD5STEP(F1, b, c, d, a, in[3] + 0xc1bdceee, 22);
00384 MD5STEP(F1, a, b, c, d, in[4] + 0xf57c0faf, 7);
00385 MD5STEP(F1, d, a, b, c, in[5] + 0x4787c62a, 12);
00386 MD5STEP(F1, c, d, a, b, in[6] + 0xa8304613, 17);
00387 MD5STEP(F1, b, c, d, a, in[7] + 0xfd469501, 22);
00388 MD5STEP(F1, a, b, c, d, in[8] + 0x698098d8, 7);
00389 MD5STEP(F1, d, a, b, c, in[9] + 0x8b44f7af, 12);
00390 MD5STEP(F1, c, d, a, b, in[10] + 0xffff5bb1, 17);
00391 MD5STEP(F1, b, c, d, a, in[11] + 0x895cd7be, 22);
00392 MD5STEP(F1, a, b, c, d, in[12] + 0x6b901122, 7);
00393 MD5STEP(F1, d, a, b, c, in[13] + 0xfd987193, 12);
00394 MD5STEP(F1, c, d, a, b, in[14] + 0xa679438e, 17);
00395 MD5STEP(F1, b, c, d, a, in[15] + 0x49b40821, 22);
00396
00397 MD5STEP(F2, a, b, c, d, in[1] + 0xf61e2562, 5);
00398 MD5STEP(F2, d, a, b, c, in[6] + 0xc040b340, 9);
00399 MD5STEP(F2, c, d, a, b, in[11] + 0x265e5a51, 14);
00400 MD5STEP(F2, b, c, d, a, in[0] + 0xe9b6c7aa, 20);
00401 MD5STEP(F2, a, b, c, d, in[5] + 0xd62f105d, 5);
00402 MD5STEP(F2, d, a, b, c, in[10] + 0x02441453, 9);
00403 MD5STEP(F2, c, d, a, b, in[15] + 0xd8a1e681, 14);
00404 MD5STEP(F2, b, c, d, a, in[4] + 0xe7d3fbc8, 20);
00405 MD5STEP(F2, a, b, c, d, in[9] + 0x21e1cde6, 5);
00406 MD5STEP(F2, d, a, b, c, in[14] + 0xc33707d6, 9);
00407 MD5STEP(F2, c, d, a, b, in[3] + 0xf4d50d87, 14);
00408 MD5STEP(F2, b, c, d, a, in[8] + 0x455a14ed, 20);
00409 MD5STEP(F2, a, b, c, d, in[13] + 0xa9e3e905, 5);
00410 MD5STEP(F2, d, a, b, c, in[2] + 0xfcefa3f8, 9);
00411 MD5STEP(F2, c, d, a, b, in[7] + 0x676f02d9, 14);
00412 MD5STEP(F2, b, c, d, a, in[12] + 0x8d2a4c8a, 20);
00413
00414 MD5STEP(F3, a, b, c, d, in[5] + 0xfffa3942, 4);
00415 MD5STEP(F3, d, a, b, c, in[8] + 0x8771f681, 11);
00416 MD5STEP(F3, c, d, a, b, in[11] + 0x6d9d6122, 16);
00417 MD5STEP(F3, b, c, d, a, in[14] + 0xfde5380c, 23);
00418 MD5STEP(F3, a, b, c, d, in[1] + 0xa4beea44, 4);
00419 MD5STEP(F3, d, a, b, c, in[4] + 0x4bdecfa9, 11);
00420 MD5STEP(F3, c, d, a, b, in[7] + 0xf6bb4b60, 16);
00421 MD5STEP(F3, b, c, d, a, in[10] + 0xbebfbc70, 23);
00422 MD5STEP(F3, a, b, c, d, in[13] + 0x289b7ec6, 4);
00423 MD5STEP(F3, d, a, b, c, in[0] + 0xeaa127fa, 11);
00424 MD5STEP(F3, c, d, a, b, in[3] + 0xd4ef3085, 16);
00425 MD5STEP(F3, b, c, d, a, in[6] + 0x04881d05, 23);
00426 MD5STEP(F3, a, b, c, d, in[9] + 0xd9d4d039, 4);
00427 MD5STEP(F3, d, a, b, c, in[12] + 0xe6db99e5, 11);
00428 MD5STEP(F3, c, d, a, b, in[15] + 0x1fa27cf8, 16);
00429 MD5STEP(F3, b, c, d, a, in[2] + 0xc4ac5665, 23);
00430
00431 MD5STEP(F4, a, b, c, d, in[0] + 0xf4292244, 6);
00432 MD5STEP(F4, d, a, b, c, in[7] + 0x432aff97, 10);
00433 MD5STEP(F4, c, d, a, b, in[14] + 0xab9423a7, 15);
00434 MD5STEP(F4, b, c, d, a, in[5] + 0xfc93a039, 21);
00435 MD5STEP(F4, a, b, c, d, in[12] + 0x655b59c3, 6);
00436 MD5STEP(F4, d, a, b, c, in[3] + 0x8f0ccc92, 10);
00437 MD5STEP(F4, c, d, a, b, in[10] + 0xffeff47d, 15);
00438 MD5STEP(F4, b, c, d, a, in[1] + 0x85845dd1, 21);
00439 MD5STEP(F4, a, b, c, d, in[8] + 0x6fa87e4f, 6);
00440 MD5STEP(F4, d, a, b, c, in[15] + 0xfe2ce6e0, 10);
00441 MD5STEP(F4, c, d, a, b, in[6] + 0xa3014314, 15);
00442 MD5STEP(F4, b, c, d, a, in[13] + 0x4e0811a1, 21);
00443 MD5STEP(F4, a, b, c, d, in[4] + 0xf7537e82, 6);
00444 MD5STEP(F4, d, a, b, c, in[11] + 0xbd3af235, 10);
00445 MD5STEP(F4, c, d, a, b, in[2] + 0x2ad7d2bb, 15);
00446 MD5STEP(F4, b, c, d, a, in[9] + 0xeb86d391, 21);
00447
00448 ctx->digest[0] += a;
00449 ctx->digest[1] += b;
00450 ctx->digest[2] += c;
00451 ctx->digest[3] += d;
00452 }
00453
00454 static int _ie = 0x44332211;
00455
00456 static union _mendian {
00457 int i;
00458 char b[4];
00459 } *_endian = (union _mendian *)&_ie;
00460
00461 #define IS_BIG_ENDIAN() (_endian->b[0] == '\x44')
00462 #define IS_LITTLE_ENDIAN() (_endian->b[0] == '\x11')
00463
00464
00465
00466
00467
00468
00469
00470 static void
00471 byteReverse(byte *buf, unsigned nbytes)
00472
00473 {
00474 unsigned nlongs = nbytes / sizeof(uint32);
00475 uint32 t;
00476 if (IS_BIG_ENDIAN()) {
00477 do {
00478 t = (uint32) ((unsigned) buf[3] << 8 | buf[2]) << 16 |
00479 ((unsigned) buf[1] << 8 | buf[0]);
00480 *(uint32 *) buf = t;
00481 buf += 4;
00482 } while (--nlongs);
00483 } else {
00484 do {
00485 t = (uint32) ((unsigned) buf[0] << 8 | buf[1]) << 16 |
00486 ((unsigned) buf[2] << 8 | buf[3]);
00487 *(uint32 *) buf = t;
00488 buf += 4;
00489 } while (--nlongs);
00490 }
00491 }
00492
00493
00494 DIGEST_CTX
00495 rpmDigestInit(rpmDigestFlags flags)
00496 {
00497 DIGEST_CTX ctx = xcalloc(1, sizeof(*ctx));
00498
00499 #ifdef SHA_DEBUG
00500 int i;
00501 DPRINTF((stderr, "*** Init(%x)\n", flags));
00502 #endif
00503 ctx->flags = flags;
00504
00505 if (flags & RPMDIGEST_MD5) {
00506 ctx->digestlen = 16;
00507 ctx->datalen = 64;
00508 ctx->transform = MD5Transform;
00509 ctx->digest[0] = 0x67452301;
00510 ctx->digest[1] = 0xefcdab89;
00511 ctx->digest[2] = 0x98badcfe;
00512 ctx->digest[3] = 0x10325476;
00513
00514 ctx->doByteReverse = (IS_BIG_ENDIAN()) ? 1 : 0;
00515 }
00516
00517 if (flags & RPMDIGEST_SHA1) {
00518 ctx->digestlen = 20;
00519 ctx->datalen = 64;
00520 ctx->transform = SHA1Transform;
00521 ctx->digest[ 0 ] = 0x67452301;
00522 ctx->digest[ 1 ] = 0xefcdab89;
00523 ctx->digest[ 2 ] = 0x98badcfe;
00524 ctx->digest[ 3 ] = 0x10325476;
00525 ctx->digest[ 4 ] = 0xc3d2e1f0;
00526
00527 ctx->doByteReverse = (IS_BIG_ENDIAN()) ? 0 : 1;
00528 #ifdef SHA_DEBUG
00529 for (i =0; i < 5; i++)
00530 DPRINTF((stderr, "H[%2d]: %X\n", i, ctx->digest[i]));
00531 #endif
00532 }
00533
00534 if (flags & RPMDIGEST_REVERSE)
00535 ctx->doByteReverse ^= 1;
00536
00537 ctx->bits[0] = 0;
00538 ctx->bits[1] = 0;
00539
00540 return ctx;
00541 }
00542
00543 void
00544 rpmDigestUpdate(DIGEST_CTX ctx, const void * data, size_t len)
00545 {
00546 const byte * buf = data;
00547 uint32 t;
00548
00549
00550
00551 t = ctx->bits[0];
00552 if ((ctx->bits[0] = t + ((uint32) len << 3)) < t)
00553 ctx->bits[1]++;
00554 ctx->bits[1] += len >> 29;
00555
00556 t = (t >> 3) % ctx->datalen;
00557
00558
00559 if (t) {
00560 byte *p = (byte *) ctx->in + t;
00561
00562 t = ctx->datalen - t;
00563 if (len < t) {
00564 memcpy(p, buf, len);
00565 return;
00566 }
00567 memcpy(p, buf, t);
00568 if (ctx->doByteReverse)
00569 byteReverse(ctx->in, ctx->datalen);
00570
00571 ctx->transform(ctx);
00572
00573 buf += t;
00574 len -= t;
00575 }
00576
00577
00578 for (; len >= ctx->datalen; buf += ctx->datalen, len -= ctx->datalen) {
00579 memmove(ctx->in, buf, ctx->datalen);
00580 if (ctx->doByteReverse)
00581 byteReverse(ctx->in, ctx->datalen);
00582
00583 ctx->transform(ctx);
00584
00585 }
00586
00587
00588 memmove(ctx->in, buf, len);
00589 }
00590
00591 void
00592 rpmDigestFinal( DIGEST_CTX ctx, void ** datap,
00593 size_t *lenp, int asAscii)
00594 {
00595 unsigned count = (ctx->bits[0] >> 3) % ctx->datalen;
00596 byte * p = ctx->in + count;
00597
00598
00599
00600 *p++ = 0x80;
00601
00602
00603 count = ctx->datalen - 1 - count;
00604
00605
00606 if (count < sizeof(ctx->bits)) {
00607 memset(p, 0, count);
00608 if (ctx->doByteReverse)
00609 byteReverse(ctx->in, ctx->datalen);
00610
00611 ctx->transform(ctx);
00612
00613 p = ctx->in;
00614 count = ctx->datalen;
00615 }
00616
00617
00618 memset(p, 0, count - sizeof(ctx->bits));
00619 if (ctx->doByteReverse)
00620 byteReverse(ctx->in, ctx->datalen - sizeof(ctx->bits));
00621
00622 if (ctx->flags & (RPMDIGEST_MD5|RPMDIGEST_BCSWAP)) {
00623 ((uint32 *) ctx->in)[14] = ctx->bits[0];
00624 ((uint32 *) ctx->in)[15] = ctx->bits[1];
00625 } else {
00626 ((uint32 *) ctx->in)[14] = ctx->bits[1];
00627 ((uint32 *) ctx->in)[15] = ctx->bits[0];
00628 }
00629
00630 ctx->transform(ctx);
00631
00632
00633 if (ctx->doByteReverse)
00634 byteReverse((byte *) ctx->digest, ctx->digestlen);
00635
00636
00637 if (!asAscii) {
00638 if (lenp) *lenp = ctx->digestlen;
00639 if (datap) {
00640 *datap = xmalloc(ctx->digestlen);
00641 memcpy(*datap, ctx->digest, ctx->digestlen);
00642 }
00643 } else {
00644 if (lenp) *lenp = (2*ctx->digestlen) + 1;
00645 if (datap) {
00646 const byte * s = (const byte *) ctx->digest;
00647 static const char hex[] = "0123456789abcdef";
00648 char * t;
00649 int i;
00650
00651 *datap = t = xmalloc((2*ctx->digestlen) + 1);
00652
00653 for (i = 0 ; i < ctx->digestlen; i++) {
00654 *t++ = hex[ (unsigned)((*s >> 4) & 0x0f) ];
00655 *t++ = hex[ (unsigned)((*s++ ) & 0x0f) ];
00656 }
00657 *t = '\0';
00658 }
00659 }
00660 memset(ctx, 0, sizeof(*ctx));
00661 free(ctx);
00662 }