1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27#include "../crypt_md5.h"
28
29#ifdef MD5_SUPPORT
30
31
32
33#define F(x, y, z) (((x) & (y)) | ((~x) & (z)))
34#define G(x, y, z) (((x) & (z)) | ((y) & (~z)))
35#define H(x, y, z) ((x) ^ (y) ^ (z))
36#define I(x, y, z) ((y) ^ ((x) | (~z)))
37
38#define ROTL(x,n,w) ((x << n) | (x >> (w - n)))
39#define ROTL32(x,n) ROTL(x,n,32)
40
41#define ROUND1(a, b, c, d, x, s, ac) { \
42 (a) += F((b),(c),(d)) + (x) + (u32)(ac); \
43 (a) = ROTL32((a),(s)); \
44 (a) += (b); \
45}
46#define ROUND2(a, b, c, d, x, s, ac) { \
47 (a) += G((b),(c),(d)) + (x) + (u32)(ac); \
48 (a) = ROTL32((a),(s)); \
49 (a) += (b); \
50}
51#define ROUND3(a, b, c, d, x, s, ac) { \
52 (a) += H((b),(c),(d)) + (x) + (u32)(ac); \
53 (a) = ROTL32((a),(s)); \
54 (a) += (b); \
55}
56#define ROUND4(a, b, c, d, x, s, ac) { \
57 (a) += I((b),(c),(d)) + (x) + (u32)(ac); \
58 (a) = ROTL32((a),(s)); \
59 (a) += (b); \
60}
61static const u32 MD5_DefaultHashValue[4] = {
62 0x67452301UL, 0xefcdab89UL, 0x98badcfeUL, 0x10325476UL
63};
64#endif
65
66#ifdef MD5_SUPPORT
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82void MD5_Init(struct rt_md5_ctx_struc *pMD5_CTX)
83{
84 NdisMoveMemory(pMD5_CTX->HashValue, MD5_DefaultHashValue,
85 sizeof(MD5_DefaultHashValue));
86 NdisZeroMemory(pMD5_CTX->Block, MD5_BLOCK_SIZE);
87 pMD5_CTX->BlockLen = 0;
88 pMD5_CTX->MessageLen = 0;
89}
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106void MD5_Hash(struct rt_md5_ctx_struc *pMD5_CTX)
107{
108 u32 X_i;
109 u32 X[16];
110 u32 a, b, c, d;
111
112
113 NdisMoveMemory(X, pMD5_CTX->Block, MD5_BLOCK_SIZE);
114 for (X_i = 0; X_i < 16; X_i++)
115 X[X_i] = cpu2le32(X[X_i]);
116
117
118
119
120 a = pMD5_CTX->HashValue[0];
121 b = pMD5_CTX->HashValue[1];
122 c = pMD5_CTX->HashValue[2];
123 d = pMD5_CTX->HashValue[3];
124
125
126
127
128
129
130 ROUND1(a, b, c, d, X[0], 7, 0xd76aa478);
131 ROUND1(d, a, b, c, X[1], 12, 0xe8c7b756);
132 ROUND1(c, d, a, b, X[2], 17, 0x242070db);
133 ROUND1(b, c, d, a, X[3], 22, 0xc1bdceee);
134 ROUND1(a, b, c, d, X[4], 7, 0xf57c0faf);
135 ROUND1(d, a, b, c, X[5], 12, 0x4787c62a);
136 ROUND1(c, d, a, b, X[6], 17, 0xa8304613);
137 ROUND1(b, c, d, a, X[7], 22, 0xfd469501);
138 ROUND1(a, b, c, d, X[8], 7, 0x698098d8);
139 ROUND1(d, a, b, c, X[9], 12, 0x8b44f7af);
140 ROUND1(c, d, a, b, X[10], 17, 0xffff5bb1);
141 ROUND1(b, c, d, a, X[11], 22, 0x895cd7be);
142 ROUND1(a, b, c, d, X[12], 7, 0x6b901122);
143 ROUND1(d, a, b, c, X[13], 12, 0xfd987193);
144 ROUND1(c, d, a, b, X[14], 17, 0xa679438e);
145 ROUND1(b, c, d, a, X[15], 22, 0x49b40821);
146
147
148
149
150
151
152 ROUND2(a, b, c, d, X[1], 5, 0xf61e2562);
153 ROUND2(d, a, b, c, X[6], 9, 0xc040b340);
154 ROUND2(c, d, a, b, X[11], 14, 0x265e5a51);
155 ROUND2(b, c, d, a, X[0], 20, 0xe9b6c7aa);
156 ROUND2(a, b, c, d, X[5], 5, 0xd62f105d);
157 ROUND2(d, a, b, c, X[10], 9, 0x2441453);
158 ROUND2(c, d, a, b, X[15], 14, 0xd8a1e681);
159 ROUND2(b, c, d, a, X[4], 20, 0xe7d3fbc8);
160 ROUND2(a, b, c, d, X[9], 5, 0x21e1cde6);
161 ROUND2(d, a, b, c, X[14], 9, 0xc33707d6);
162 ROUND2(c, d, a, b, X[3], 14, 0xf4d50d87);
163 ROUND2(b, c, d, a, X[8], 20, 0x455a14ed);
164 ROUND2(a, b, c, d, X[13], 5, 0xa9e3e905);
165 ROUND2(d, a, b, c, X[2], 9, 0xfcefa3f8);
166 ROUND2(c, d, a, b, X[7], 14, 0x676f02d9);
167 ROUND2(b, c, d, a, X[12], 20, 0x8d2a4c8a);
168
169
170
171
172
173
174 ROUND3(a, b, c, d, X[5], 4, 0xfffa3942);
175 ROUND3(d, a, b, c, X[8], 11, 0x8771f681);
176 ROUND3(c, d, a, b, X[11], 16, 0x6d9d6122);
177 ROUND3(b, c, d, a, X[14], 23, 0xfde5380c);
178 ROUND3(a, b, c, d, X[1], 4, 0xa4beea44);
179 ROUND3(d, a, b, c, X[4], 11, 0x4bdecfa9);
180 ROUND3(c, d, a, b, X[7], 16, 0xf6bb4b60);
181 ROUND3(b, c, d, a, X[10], 23, 0xbebfbc70);
182 ROUND3(a, b, c, d, X[13], 4, 0x289b7ec6);
183 ROUND3(d, a, b, c, X[0], 11, 0xeaa127fa);
184 ROUND3(c, d, a, b, X[3], 16, 0xd4ef3085);
185 ROUND3(b, c, d, a, X[6], 23, 0x4881d05);
186 ROUND3(a, b, c, d, X[9], 4, 0xd9d4d039);
187 ROUND3(d, a, b, c, X[12], 11, 0xe6db99e5);
188 ROUND3(c, d, a, b, X[15], 16, 0x1fa27cf8);
189 ROUND3(b, c, d, a, X[2], 23, 0xc4ac5665);
190
191
192
193
194
195
196 ROUND4(a, b, c, d, X[0], 6, 0xf4292244);
197 ROUND4(d, a, b, c, X[7], 10, 0x432aff97);
198 ROUND4(c, d, a, b, X[14], 15, 0xab9423a7);
199 ROUND4(b, c, d, a, X[5], 21, 0xfc93a039);
200 ROUND4(a, b, c, d, X[12], 6, 0x655b59c3);
201 ROUND4(d, a, b, c, X[3], 10, 0x8f0ccc92);
202 ROUND4(c, d, a, b, X[10], 15, 0xffeff47d);
203 ROUND4(b, c, d, a, X[1], 21, 0x85845dd1);
204 ROUND4(a, b, c, d, X[8], 6, 0x6fa87e4f);
205 ROUND4(d, a, b, c, X[15], 10, 0xfe2ce6e0);
206 ROUND4(c, d, a, b, X[6], 15, 0xa3014314);
207 ROUND4(b, c, d, a, X[13], 21, 0x4e0811a1);
208 ROUND4(a, b, c, d, X[4], 6, 0xf7537e82);
209 ROUND4(d, a, b, c, X[11], 10, 0xbd3af235);
210 ROUND4(c, d, a, b, X[2], 15, 0x2ad7d2bb);
211 ROUND4(b, c, d, a, X[9], 21, 0xeb86d391);
212
213
214 pMD5_CTX->HashValue[0] += a;
215 pMD5_CTX->HashValue[1] += b;
216 pMD5_CTX->HashValue[2] += c;
217 pMD5_CTX->HashValue[3] += d;
218
219 NdisZeroMemory(pMD5_CTX->Block, MD5_BLOCK_SIZE);
220 pMD5_CTX->BlockLen = 0;
221}
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241void MD5_Append(struct rt_md5_ctx_struc *pMD5_CTX,
242 IN const u8 Message[], u32 MessageLen)
243{
244 u32 appendLen = 0;
245 u32 diffLen = 0;
246
247 while (appendLen != MessageLen) {
248 diffLen = MessageLen - appendLen;
249 if ((pMD5_CTX->BlockLen + diffLen) < MD5_BLOCK_SIZE) {
250 NdisMoveMemory(pMD5_CTX->Block + pMD5_CTX->BlockLen,
251 Message + appendLen, diffLen);
252 pMD5_CTX->BlockLen += diffLen;
253 appendLen += diffLen;
254 } else {
255 NdisMoveMemory(pMD5_CTX->Block + pMD5_CTX->BlockLen,
256 Message + appendLen,
257 MD5_BLOCK_SIZE - pMD5_CTX->BlockLen);
258 appendLen += (MD5_BLOCK_SIZE - pMD5_CTX->BlockLen);
259 pMD5_CTX->BlockLen = MD5_BLOCK_SIZE;
260 MD5_Hash(pMD5_CTX);
261 }
262 }
263 pMD5_CTX->MessageLen += MessageLen;
264}
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283void MD5_End(struct rt_md5_ctx_struc *pMD5_CTX, u8 DigestMessage[])
284{
285 u32 index;
286 u64 message_length_bits;
287
288
289 NdisFillMemory(pMD5_CTX->Block + pMD5_CTX->BlockLen, 1, 0x80);
290
291
292 if (pMD5_CTX->BlockLen > 55)
293 MD5_Hash(pMD5_CTX);
294
295
296
297 message_length_bits = pMD5_CTX->MessageLen * 8;
298 message_length_bits = cpu2le64(message_length_bits);
299 NdisMoveMemory(&pMD5_CTX->Block[56], &message_length_bits, 8);
300 MD5_Hash(pMD5_CTX);
301
302
303 for (index = 0; index < 4; index++)
304 pMD5_CTX->HashValue[index] =
305 cpu2le32(pMD5_CTX->HashValue[index]);
306
307 NdisMoveMemory(DigestMessage, pMD5_CTX->HashValue, MD5_DIGEST_SIZE);
308}
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326void RT_MD5(IN const u8 Message[],
327 u32 MessageLen, u8 DigestMessage[])
328{
329 struct rt_md5_ctx_struc md5_ctx;
330
331 NdisZeroMemory(&md5_ctx, sizeof(struct rt_md5_ctx_struc));
332 MD5_Init(&md5_ctx);
333 MD5_Append(&md5_ctx, Message, MessageLen);
334 MD5_End(&md5_ctx, DigestMessage);
335}
336
337#endif
338
339
340