|
|
1.1.1.2 root 1: // serpent.cpp - written and placed in the public domain by Wei Dai
1.1 root 2:
1.1.1.2 root 3: /* Adapted for TrueCrypt by the TrueCrypt Foundation */
1.1 root 4:
1.1.1.2 root 5: #include "Serpent.h"
1.1.1.3 ! root 6: #include "Common/Endian.h"
1.1 root 7:
1.1.1.2 root 8: #ifndef LINUX_DRIVER
9: #include <memory.h>
10: #endif
1.1 root 11:
1.1.1.2 root 12: #if defined(_WIN32) && !defined(_DEBUG)
13: #include <stdlib.h>
14: #define rotlFixed _rotl
15: #define rotrFixed _rotr
1.1 root 16: #else
1.1.1.2 root 17: #define rotlFixed(x,n) (((x) << (n)) | ((x) >> (32 - (n))))
18: #define rotrFixed(x,n) (((x) >> (n)) | ((x) << (32 - (n))))
1.1 root 19: #endif
20:
1.1.1.2 root 21: // linear transformation
22: #define LT(i,a,b,c,d,e) {\
23: a = rotlFixed(a, 13); \
24: c = rotlFixed(c, 3); \
25: d = rotlFixed(d ^ c ^ (a << 3), 7); \
26: b = rotlFixed(b ^ a ^ c, 1); \
27: a = rotlFixed(a ^ b ^ d, 5); \
28: c = rotlFixed(c ^ d ^ (b << 7), 22);}
29:
30: // inverse linear transformation
31: #define ILT(i,a,b,c,d,e) {\
32: c = rotrFixed(c, 22); \
33: a = rotrFixed(a, 5); \
34: c ^= d ^ (b << 7); \
35: a ^= b ^ d; \
36: b = rotrFixed(b, 1); \
37: d = rotrFixed(d, 7) ^ c ^ (a << 3); \
38: b ^= a ^ c; \
39: c = rotrFixed(c, 3); \
40: a = rotrFixed(a, 13);}
41:
42: // order of output from S-box functions
43: #define beforeS0(f) f(0,a,b,c,d,e)
44: #define afterS0(f) f(1,b,e,c,a,d)
45: #define afterS1(f) f(2,c,b,a,e,d)
46: #define afterS2(f) f(3,a,e,b,d,c)
47: #define afterS3(f) f(4,e,b,d,c,a)
48: #define afterS4(f) f(5,b,a,e,c,d)
49: #define afterS5(f) f(6,a,c,b,e,d)
50: #define afterS6(f) f(7,a,c,d,b,e)
51: #define afterS7(f) f(8,d,e,b,a,c)
52:
53: // order of output from inverse S-box functions
54: #define beforeI7(f) f(8,a,b,c,d,e)
55: #define afterI7(f) f(7,d,a,b,e,c)
56: #define afterI6(f) f(6,a,b,c,e,d)
57: #define afterI5(f) f(5,b,d,e,c,a)
58: #define afterI4(f) f(4,b,c,e,a,d)
59: #define afterI3(f) f(3,a,b,e,c,d)
60: #define afterI2(f) f(2,b,d,e,c,a)
61: #define afterI1(f) f(1,a,b,c,e,d)
62: #define afterI0(f) f(0,a,d,b,e,c)
63:
64: // The instruction sequences for the S-box functions
65: // come from Dag Arne Osvik's paper "Speeding up Serpent".
66:
67: #define S0(i, r0, r1, r2, r3, r4) \
68: { \
69: r3 ^= r0; \
70: r4 = r1; \
71: r1 &= r3; \
72: r4 ^= r2; \
73: r1 ^= r0; \
74: r0 |= r3; \
75: r0 ^= r4; \
76: r4 ^= r3; \
77: r3 ^= r2; \
78: r2 |= r1; \
79: r2 ^= r4; \
80: r4 = ~r4; \
81: r4 |= r1; \
82: r1 ^= r3; \
83: r1 ^= r4; \
84: r3 |= r0; \
85: r1 ^= r3; \
86: r4 ^= r3; \
87: }
88:
89: #define I0(i, r0, r1, r2, r3, r4) \
90: { \
91: r2 = ~r2; \
92: r4 = r1; \
93: r1 |= r0; \
94: r4 = ~r4; \
95: r1 ^= r2; \
96: r2 |= r4; \
97: r1 ^= r3; \
98: r0 ^= r4; \
99: r2 ^= r0; \
100: r0 &= r3; \
101: r4 ^= r0; \
102: r0 |= r1; \
103: r0 ^= r2; \
104: r3 ^= r4; \
105: r2 ^= r1; \
106: r3 ^= r0; \
107: r3 ^= r1; \
108: r2 &= r3; \
109: r4 ^= r2; \
110: }
111:
112: #define S1(i, r0, r1, r2, r3, r4) \
113: { \
114: r0 = ~r0; \
115: r2 = ~r2; \
116: r4 = r0; \
117: r0 &= r1; \
118: r2 ^= r0; \
119: r0 |= r3; \
120: r3 ^= r2; \
121: r1 ^= r0; \
122: r0 ^= r4; \
123: r4 |= r1; \
124: r1 ^= r3; \
125: r2 |= r0; \
126: r2 &= r4; \
127: r0 ^= r1; \
128: r1 &= r2; \
129: r1 ^= r0; \
130: r0 &= r2; \
131: r0 ^= r4; \
132: }
133:
134: #define I1(i, r0, r1, r2, r3, r4) \
135: { \
136: r4 = r1; \
137: r1 ^= r3; \
138: r3 &= r1; \
139: r4 ^= r2; \
140: r3 ^= r0; \
141: r0 |= r1; \
142: r2 ^= r3; \
143: r0 ^= r4; \
144: r0 |= r2; \
145: r1 ^= r3; \
146: r0 ^= r1; \
147: r1 |= r3; \
148: r1 ^= r0; \
149: r4 = ~r4; \
150: r4 ^= r1; \
151: r1 |= r0; \
152: r1 ^= r0; \
153: r1 |= r4; \
154: r3 ^= r1; \
155: }
156:
157: #define S2(i, r0, r1, r2, r3, r4) \
158: { \
159: r4 = r0; \
160: r0 &= r2; \
161: r0 ^= r3; \
162: r2 ^= r1; \
163: r2 ^= r0; \
164: r3 |= r4; \
165: r3 ^= r1; \
166: r4 ^= r2; \
167: r1 = r3; \
168: r3 |= r4; \
169: r3 ^= r0; \
170: r0 &= r1; \
171: r4 ^= r0; \
172: r1 ^= r3; \
173: r1 ^= r4; \
174: r4 = ~r4; \
175: }
176:
177: #define I2(i, r0, r1, r2, r3, r4) \
178: { \
179: r2 ^= r3; \
180: r3 ^= r0; \
181: r4 = r3; \
182: r3 &= r2; \
183: r3 ^= r1; \
184: r1 |= r2; \
185: r1 ^= r4; \
186: r4 &= r3; \
187: r2 ^= r3; \
188: r4 &= r0; \
189: r4 ^= r2; \
190: r2 &= r1; \
191: r2 |= r0; \
192: r3 = ~r3; \
193: r2 ^= r3; \
194: r0 ^= r3; \
195: r0 &= r1; \
196: r3 ^= r4; \
197: r3 ^= r0; \
198: }
199:
200: #define S3(i, r0, r1, r2, r3, r4) \
201: { \
202: r4 = r0; \
203: r0 |= r3; \
204: r3 ^= r1; \
205: r1 &= r4; \
206: r4 ^= r2; \
207: r2 ^= r3; \
208: r3 &= r0; \
209: r4 |= r1; \
210: r3 ^= r4; \
211: r0 ^= r1; \
212: r4 &= r0; \
213: r1 ^= r3; \
214: r4 ^= r2; \
215: r1 |= r0; \
216: r1 ^= r2; \
217: r0 ^= r3; \
218: r2 = r1; \
219: r1 |= r3; \
220: r1 ^= r0; \
221: }
222:
223: #define I3(i, r0, r1, r2, r3, r4) \
224: { \
225: r4 = r2; \
226: r2 ^= r1; \
227: r1 &= r2; \
228: r1 ^= r0; \
229: r0 &= r4; \
230: r4 ^= r3; \
231: r3 |= r1; \
232: r3 ^= r2; \
233: r0 ^= r4; \
234: r2 ^= r0; \
235: r0 |= r3; \
236: r0 ^= r1; \
237: r4 ^= r2; \
238: r2 &= r3; \
239: r1 |= r3; \
240: r1 ^= r2; \
241: r4 ^= r0; \
242: r2 ^= r4; \
243: }
244:
245: #define S4(i, r0, r1, r2, r3, r4) \
246: { \
247: r1 ^= r3; \
248: r3 = ~r3; \
249: r2 ^= r3; \
250: r3 ^= r0; \
251: r4 = r1; \
252: r1 &= r3; \
253: r1 ^= r2; \
254: r4 ^= r3; \
255: r0 ^= r4; \
256: r2 &= r4; \
257: r2 ^= r0; \
258: r0 &= r1; \
259: r3 ^= r0; \
260: r4 |= r1; \
261: r4 ^= r0; \
262: r0 |= r3; \
263: r0 ^= r2; \
264: r2 &= r3; \
265: r0 = ~r0; \
266: r4 ^= r2; \
267: }
268:
269: #define I4(i, r0, r1, r2, r3, r4) \
270: { \
271: r4 = r2; \
272: r2 &= r3; \
273: r2 ^= r1; \
274: r1 |= r3; \
275: r1 &= r0; \
276: r4 ^= r2; \
277: r4 ^= r1; \
278: r1 &= r2; \
279: r0 = ~r0; \
280: r3 ^= r4; \
281: r1 ^= r3; \
282: r3 &= r0; \
283: r3 ^= r2; \
284: r0 ^= r1; \
285: r2 &= r0; \
286: r3 ^= r0; \
287: r2 ^= r4; \
288: r2 |= r3; \
289: r3 ^= r0; \
290: r2 ^= r1; \
291: }
292:
293: #define S5(i, r0, r1, r2, r3, r4) \
294: { \
295: r0 ^= r1; \
296: r1 ^= r3; \
297: r3 = ~r3; \
298: r4 = r1; \
299: r1 &= r0; \
300: r2 ^= r3; \
301: r1 ^= r2; \
302: r2 |= r4; \
303: r4 ^= r3; \
304: r3 &= r1; \
305: r3 ^= r0; \
306: r4 ^= r1; \
307: r4 ^= r2; \
308: r2 ^= r0; \
309: r0 &= r3; \
310: r2 = ~r2; \
311: r0 ^= r4; \
312: r4 |= r3; \
313: r2 ^= r4; \
314: }
315:
316: #define I5(i, r0, r1, r2, r3, r4) \
317: { \
318: r1 = ~r1; \
319: r4 = r3; \
320: r2 ^= r1; \
321: r3 |= r0; \
322: r3 ^= r2; \
323: r2 |= r1; \
324: r2 &= r0; \
325: r4 ^= r3; \
326: r2 ^= r4; \
327: r4 |= r0; \
328: r4 ^= r1; \
329: r1 &= r2; \
330: r1 ^= r3; \
331: r4 ^= r2; \
332: r3 &= r4; \
333: r4 ^= r1; \
334: r3 ^= r0; \
335: r3 ^= r4; \
336: r4 = ~r4; \
337: }
338:
339: #define S6(i, r0, r1, r2, r3, r4) \
340: { \
341: r2 = ~r2; \
342: r4 = r3; \
343: r3 &= r0; \
344: r0 ^= r4; \
345: r3 ^= r2; \
346: r2 |= r4; \
347: r1 ^= r3; \
348: r2 ^= r0; \
349: r0 |= r1; \
350: r2 ^= r1; \
351: r4 ^= r0; \
352: r0 |= r3; \
353: r0 ^= r2; \
354: r4 ^= r3; \
355: r4 ^= r0; \
356: r3 = ~r3; \
357: r2 &= r4; \
358: r2 ^= r3; \
359: }
360:
361: #define I6(i, r0, r1, r2, r3, r4) \
362: { \
363: r0 ^= r2; \
364: r4 = r2; \
365: r2 &= r0; \
366: r4 ^= r3; \
367: r2 = ~r2; \
368: r3 ^= r1; \
369: r2 ^= r3; \
370: r4 |= r0; \
371: r0 ^= r2; \
372: r3 ^= r4; \
373: r4 ^= r1; \
374: r1 &= r3; \
375: r1 ^= r0; \
376: r0 ^= r3; \
377: r0 |= r2; \
378: r3 ^= r1; \
379: r4 ^= r0; \
380: }
381:
382: #define S7(i, r0, r1, r2, r3, r4) \
383: { \
384: r4 = r2; \
385: r2 &= r1; \
386: r2 ^= r3; \
387: r3 &= r1; \
388: r4 ^= r2; \
389: r2 ^= r1; \
390: r1 ^= r0; \
391: r0 |= r4; \
392: r0 ^= r2; \
393: r3 ^= r1; \
394: r2 ^= r3; \
395: r3 &= r0; \
396: r3 ^= r4; \
397: r4 ^= r2; \
398: r2 &= r0; \
399: r4 = ~r4; \
400: r2 ^= r4; \
401: r4 &= r0; \
402: r1 ^= r3; \
403: r4 ^= r1; \
404: }
405:
406: #define I7(i, r0, r1, r2, r3, r4) \
407: { \
408: r4 = r2; \
409: r2 ^= r0; \
410: r0 &= r3; \
411: r2 = ~r2; \
412: r4 |= r3; \
413: r3 ^= r1; \
414: r1 |= r0; \
415: r0 ^= r2; \
416: r2 &= r4; \
417: r1 ^= r2; \
418: r2 ^= r0; \
419: r0 |= r2; \
420: r3 &= r4; \
421: r0 ^= r3; \
422: r4 ^= r1; \
423: r3 ^= r4; \
424: r4 |= r0; \
425: r3 ^= r2; \
426: r4 ^= r2; \
427: }
428:
429: // key xor
430: #define KX(r, a, b, c, d, e) {\
431: a ^= k[4 * r + 0]; \
432: b ^= k[4 * r + 1]; \
433: c ^= k[4 * r + 2]; \
434: d ^= k[4 * r + 3];}
1.1 root 435:
436:
1.1.1.2 root 437: void serpent_set_key(const unsigned __int8 userKey[], int keylen, unsigned __int8 *ks)
1.1 root 438: {
1.1.1.2 root 439: unsigned __int32 a,b,c,d,e;
440: unsigned __int32 *k = (unsigned __int32 *)ks;
441: unsigned __int32 t;
442: int i;
443:
444: for (i = 0; i < keylen / (int)sizeof(__int32); i++)
445: k[i] = LE32(((unsigned __int32*)userKey)[i]);
446:
447: if (keylen < 32)
448: k[keylen/4] |= (unsigned __int32)1 << ((keylen%4)*8);
449:
450: k += 8;
451: t = k[-1];
452: for (i = 0; i < 132; ++i)
453: k[i] = t = rotlFixed(k[i-8] ^ k[i-5] ^ k[i-3] ^ t ^ 0x9e3779b9 ^ i, 11);
454: k -= 20;
455:
456: #define LK(r, a, b, c, d, e) {\
457: a = k[(8-r)*4 + 0]; \
458: b = k[(8-r)*4 + 1]; \
459: c = k[(8-r)*4 + 2]; \
460: d = k[(8-r)*4 + 3];}
461:
462: #define SK(r, a, b, c, d, e) {\
463: k[(8-r)*4 + 4] = a; \
464: k[(8-r)*4 + 5] = b; \
465: k[(8-r)*4 + 6] = c; \
466: k[(8-r)*4 + 7] = d;} \
467:
468: for (i=0; i<4; i++)
469: {
470: afterS2(LK); afterS2(S3); afterS3(SK);
471: afterS1(LK); afterS1(S2); afterS2(SK);
472: afterS0(LK); afterS0(S1); afterS1(SK);
473: beforeS0(LK); beforeS0(S0); afterS0(SK);
474: k += 8*4;
475: afterS6(LK); afterS6(S7); afterS7(SK);
476: afterS5(LK); afterS5(S6); afterS6(SK);
477: afterS4(LK); afterS4(S5); afterS5(SK);
478: afterS3(LK); afterS3(S4); afterS4(SK);
479: }
480: afterS2(LK); afterS2(S3); afterS3(SK);
1.1 root 481: }
482:
483:
1.1.1.2 root 484: void serpent_encrypt(const unsigned __int8 *inBlock, unsigned __int8 *outBlock, unsigned __int8 *ks)
1.1 root 485: {
1.1.1.2 root 486: unsigned __int32 a, b, c, d, e;
487: unsigned int i=1;
488: const unsigned __int32 *k = (unsigned __int32 *)ks + 8;
489: unsigned __int32 *in = (unsigned __int32 *) inBlock;
490: unsigned __int32 *out = (unsigned __int32 *) outBlock;
491:
492: a = LE32(in[0]);
493: b = LE32(in[1]);
494: c = LE32(in[2]);
495: d = LE32(in[3]);
496:
497: do
498: {
499: beforeS0(KX); beforeS0(S0); afterS0(LT);
500: afterS0(KX); afterS0(S1); afterS1(LT);
501: afterS1(KX); afterS1(S2); afterS2(LT);
502: afterS2(KX); afterS2(S3); afterS3(LT);
503: afterS3(KX); afterS3(S4); afterS4(LT);
504: afterS4(KX); afterS4(S5); afterS5(LT);
505: afterS5(KX); afterS5(S6); afterS6(LT);
506: afterS6(KX); afterS6(S7);
507:
508: if (i == 4)
509: break;
510:
511: ++i;
512: c = b;
513: b = e;
514: e = d;
515: d = a;
516: a = e;
517: k += 32;
518: beforeS0(LT);
519: }
520: while (1);
521:
522: afterS7(KX);
523:
524: out[0] = LE32(d);
525: out[1] = LE32(e);
526: out[2] = LE32(b);
527: out[3] = LE32(a);
528: }
1.1 root 529:
1.1.1.2 root 530:
531: void serpent_decrypt(const unsigned __int8 *inBlock, unsigned __int8 *outBlock, unsigned __int8 *ks)
532: {
533: unsigned __int32 a, b, c, d, e;
534: const unsigned __int32 *k = (unsigned __int32 *)ks + 104;
535: unsigned int i=4;
536: unsigned __int32 *in = (unsigned __int32 *) inBlock;
537: unsigned __int32 *out = (unsigned __int32 *) outBlock;
538:
539: a = LE32(in[0]);
540: b = LE32(in[1]);
541: c = LE32(in[2]);
542: d = LE32(in[3]);
543:
544: beforeI7(KX);
545: goto start;
546:
547: do
548: {
549: c = b;
550: b = d;
551: d = e;
552: k -= 32;
553: beforeI7(ILT);
554: start:
555: beforeI7(I7); afterI7(KX);
556: afterI7(ILT); afterI7(I6); afterI6(KX);
557: afterI6(ILT); afterI6(I5); afterI5(KX);
558: afterI5(ILT); afterI5(I4); afterI4(KX);
559: afterI4(ILT); afterI4(I3); afterI3(KX);
560: afterI3(ILT); afterI3(I2); afterI2(KX);
561: afterI2(ILT); afterI2(I1); afterI1(KX);
562: afterI1(ILT); afterI1(I0); afterI0(KX);
563: }
564: while (--i != 0);
565:
566: out[0] = LE32(a);
567: out[1] = LE32(d);
568: out[2] = LE32(b);
569: out[3] = LE32(e);
1.1 root 570: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.