00001
00016 #include "includes.h"
00017
00018 #include "common.h"
00019 #include "sha1.h"
00020 #include "sha1_i.h"
00021 #include "md5.h"
00022 #include "crypto.h"
00023
00024 typedef struct SHA1Context SHA1_CTX;
00025
00026 void SHA1Transform(u32 state[5], const unsigned char buffer[64]);
00027
00028
00038 int sha1_vector(size_t num_elem, const u8 *addr[], const size_t *len, u8 *mac)
00039 {
00040 SHA1_CTX ctx;
00041 size_t i;
00042
00043 SHA1Init(&ctx);
00044 for (i = 0; i < num_elem; i++)
00045 SHA1Update(&ctx, addr[i], len[i]);
00046 SHA1Final(mac, &ctx);
00047 return 0;
00048 }
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131 #define SHA1HANDSOFF
00132
00133 #define rol(value, bits) (((value) << (bits)) | ((value) >> (32 - (bits))))
00134
00135
00136
00137 #ifndef WORDS_BIGENDIAN
00138 #define blk0(i) (block->l[i] = (rol(block->l[i], 24) & 0xFF00FF00) | \
00139 (rol(block->l[i], 8) & 0x00FF00FF))
00140 #else
00141 #define blk0(i) block->l[i]
00142 #endif
00143 #define blk(i) (block->l[i & 15] = rol(block->l[(i + 13) & 15] ^ \
00144 block->l[(i + 8) & 15] ^ block->l[(i + 2) & 15] ^ block->l[i & 15], 1))
00145
00146
00147 #define R0(v,w,x,y,z,i) \
00148 z += ((w & (x ^ y)) ^ y) + blk0(i) + 0x5A827999 + rol(v, 5); \
00149 w = rol(w, 30);
00150 #define R1(v,w,x,y,z,i) \
00151 z += ((w & (x ^ y)) ^ y) + blk(i) + 0x5A827999 + rol(v, 5); \
00152 w = rol(w, 30);
00153 #define R2(v,w,x,y,z,i) \
00154 z += (w ^ x ^ y) + blk(i) + 0x6ED9EBA1 + rol(v, 5); w = rol(w, 30);
00155 #define R3(v,w,x,y,z,i) \
00156 z += (((w | x) & y) | (w & x)) + blk(i) + 0x8F1BBCDC + rol(v, 5); \
00157 w = rol(w, 30);
00158 #define R4(v,w,x,y,z,i) \
00159 z += (w ^ x ^ y) + blk(i) + 0xCA62C1D6 + rol(v, 5); \
00160 w=rol(w, 30);
00161
00162
00163 #ifdef VERBOSE
00164 void SHAPrintContext(SHA1_CTX *context, char *msg)
00165 {
00166 printf("%s (%d,%d) %x %x %x %x %x\n",
00167 msg,
00168 context->count[0], context->count[1],
00169 context->state[0],
00170 context->state[1],
00171 context->state[2],
00172 context->state[3],
00173 context->state[4]);
00174 }
00175 #endif
00176
00177
00178
00179 void SHA1Transform(u32 state[5], const unsigned char buffer[64])
00180 {
00181 u32 a, b, c, d, e;
00182 typedef union {
00183 unsigned char c[64];
00184 u32 l[16];
00185 } CHAR64LONG16;
00186 CHAR64LONG16* block;
00187 #ifdef SHA1HANDSOFF
00188 CHAR64LONG16 workspace;
00189 block = &workspace;
00190 os_memcpy(block, buffer, 64);
00191 #else
00192 block = (CHAR64LONG16 *) buffer;
00193 #endif
00194
00195 a = state[0];
00196 b = state[1];
00197 c = state[2];
00198 d = state[3];
00199 e = state[4];
00200
00201 R0(a,b,c,d,e, 0); R0(e,a,b,c,d, 1); R0(d,e,a,b,c, 2); R0(c,d,e,a,b, 3);
00202 R0(b,c,d,e,a, 4); R0(a,b,c,d,e, 5); R0(e,a,b,c,d, 6); R0(d,e,a,b,c, 7);
00203 R0(c,d,e,a,b, 8); R0(b,c,d,e,a, 9); R0(a,b,c,d,e,10); R0(e,a,b,c,d,11);
00204 R0(d,e,a,b,c,12); R0(c,d,e,a,b,13); R0(b,c,d,e,a,14); R0(a,b,c,d,e,15);
00205 R1(e,a,b,c,d,16); R1(d,e,a,b,c,17); R1(c,d,e,a,b,18); R1(b,c,d,e,a,19);
00206 R2(a,b,c,d,e,20); R2(e,a,b,c,d,21); R2(d,e,a,b,c,22); R2(c,d,e,a,b,23);
00207 R2(b,c,d,e,a,24); R2(a,b,c,d,e,25); R2(e,a,b,c,d,26); R2(d,e,a,b,c,27);
00208 R2(c,d,e,a,b,28); R2(b,c,d,e,a,29); R2(a,b,c,d,e,30); R2(e,a,b,c,d,31);
00209 R2(d,e,a,b,c,32); R2(c,d,e,a,b,33); R2(b,c,d,e,a,34); R2(a,b,c,d,e,35);
00210 R2(e,a,b,c,d,36); R2(d,e,a,b,c,37); R2(c,d,e,a,b,38); R2(b,c,d,e,a,39);
00211 R3(a,b,c,d,e,40); R3(e,a,b,c,d,41); R3(d,e,a,b,c,42); R3(c,d,e,a,b,43);
00212 R3(b,c,d,e,a,44); R3(a,b,c,d,e,45); R3(e,a,b,c,d,46); R3(d,e,a,b,c,47);
00213 R3(c,d,e,a,b,48); R3(b,c,d,e,a,49); R3(a,b,c,d,e,50); R3(e,a,b,c,d,51);
00214 R3(d,e,a,b,c,52); R3(c,d,e,a,b,53); R3(b,c,d,e,a,54); R3(a,b,c,d,e,55);
00215 R3(e,a,b,c,d,56); R3(d,e,a,b,c,57); R3(c,d,e,a,b,58); R3(b,c,d,e,a,59);
00216 R4(a,b,c,d,e,60); R4(e,a,b,c,d,61); R4(d,e,a,b,c,62); R4(c,d,e,a,b,63);
00217 R4(b,c,d,e,a,64); R4(a,b,c,d,e,65); R4(e,a,b,c,d,66); R4(d,e,a,b,c,67);
00218 R4(c,d,e,a,b,68); R4(b,c,d,e,a,69); R4(a,b,c,d,e,70); R4(e,a,b,c,d,71);
00219 R4(d,e,a,b,c,72); R4(c,d,e,a,b,73); R4(b,c,d,e,a,74); R4(a,b,c,d,e,75);
00220 R4(e,a,b,c,d,76); R4(d,e,a,b,c,77); R4(c,d,e,a,b,78); R4(b,c,d,e,a,79);
00221
00222 state[0] += a;
00223 state[1] += b;
00224 state[2] += c;
00225 state[3] += d;
00226 state[4] += e;
00227
00228 a = b = c = d = e = 0;
00229 #ifdef SHA1HANDSOFF
00230 os_memset(block, 0, 64);
00231 #endif
00232 }
00233
00234
00235
00236
00237 void SHA1Init(SHA1_CTX* context)
00238 {
00239
00240 context->state[0] = 0x67452301;
00241 context->state[1] = 0xEFCDAB89;
00242 context->state[2] = 0x98BADCFE;
00243 context->state[3] = 0x10325476;
00244 context->state[4] = 0xC3D2E1F0;
00245 context->count[0] = context->count[1] = 0;
00246 }
00247
00248
00249
00250
00251 void SHA1Update(SHA1_CTX* context, const void *_data, u32 len)
00252 {
00253 u32 i, j;
00254 const unsigned char *data = _data;
00255
00256 #ifdef VERBOSE
00257 SHAPrintContext(context, "before");
00258 #endif
00259 j = (context->count[0] >> 3) & 63;
00260 if ((context->count[0] += len << 3) < (len << 3))
00261 context->count[1]++;
00262 context->count[1] += (len >> 29);
00263 if ((j + len) > 63) {
00264 os_memcpy(&context->buffer[j], data, (i = 64-j));
00265 SHA1Transform(context->state, context->buffer);
00266 for ( ; i + 63 < len; i += 64) {
00267 SHA1Transform(context->state, &data[i]);
00268 }
00269 j = 0;
00270 }
00271 else i = 0;
00272 os_memcpy(&context->buffer[j], &data[i], len - i);
00273 #ifdef VERBOSE
00274 SHAPrintContext(context, "after ");
00275 #endif
00276 }
00277
00278
00279
00280
00281 void SHA1Final(unsigned char digest[20], SHA1_CTX* context)
00282 {
00283 u32 i;
00284 unsigned char finalcount[8];
00285
00286 for (i = 0; i < 8; i++) {
00287 finalcount[i] = (unsigned char)
00288 ((context->count[(i >= 4 ? 0 : 1)] >>
00289 ((3-(i & 3)) * 8) ) & 255);
00290 }
00291 SHA1Update(context, (unsigned char *) "\200", 1);
00292 while ((context->count[0] & 504) != 448) {
00293 SHA1Update(context, (unsigned char *) "\0", 1);
00294 }
00295 SHA1Update(context, finalcount, 8);
00296
00297 for (i = 0; i < 20; i++) {
00298 digest[i] = (unsigned char)
00299 ((context->state[i >> 2] >> ((3 - (i & 3)) * 8)) &
00300 255);
00301 }
00302
00303 i = 0;
00304 os_memset(context->buffer, 0, 64);
00305 os_memset(context->state, 0, 20);
00306 os_memset(context->count, 0, 8);
00307 os_memset(finalcount, 0, 8);
00308 }
00309
00310
00311