rijndael-alg-fst.c revision 78358
1/*	$FreeBSD: head/sys/crypto/rijndael/rijndael-alg-fst.c 78358 2001-06-16 19:32:37Z ume $	*/
2/*	$KAME: rijndael-alg-fst.c,v 1.7 2001/05/27 00:23:23 itojun Exp $	*/
3
4/*
5 * rijndael-alg-fst.c   v2.3   April '2000
6 *
7 * Optimised ANSI C code
8 *
9 * authors: v1.0: Antoon Bosselaers
10 *          v2.0: Vincent Rijmen
11 *          v2.3: Paulo Barreto
12 *
13 * This code is placed in the public domain.
14 */
15
16#include <sys/cdefs.h>
17#include <sys/types.h>
18#ifdef _KERNEL
19#include <sys/systm.h>
20#else
21#include <string.h>
22#endif
23#include <crypto/rijndael/rijndael-alg-fst.h>
24#include <crypto/rijndael/rijndael_local.h>
25
26#include <crypto/rijndael/boxes-fst.dat>
27
28int rijndaelKeySched(word8 k[MAXKC][4], word8 W[MAXROUNDS+1][4][4], int ROUNDS) {
29	/* Calculate the necessary round keys
30	 * The number of calculations depends on keyBits and blockBits
31	 */
32	int j, r, t, rconpointer = 0;
33	union {
34		word8	x8[MAXKC][4];
35		word32	x32[MAXKC];
36	} xtk;
37#define	tk	xtk.x8
38	int KC = ROUNDS - 6;
39
40	for (j = KC-1; j >= 0; j--) {
41		*((word32*)tk[j]) = *((word32*)k[j]);
42	}
43	r = 0;
44	t = 0;
45	/* copy values into round key array */
46	for (j = 0; (j < KC) && (r < ROUNDS + 1); ) {
47		for (; (j < KC) && (t < 4); j++, t++) {
48			*((word32*)W[r][t]) = *((word32*)tk[j]);
49		}
50		if (t == 4) {
51			r++;
52			t = 0;
53		}
54	}
55
56	while (r < ROUNDS + 1) { /* while not enough round key material calculated */
57		/* calculate new values */
58		tk[0][0] ^= S[tk[KC-1][1]];
59		tk[0][1] ^= S[tk[KC-1][2]];
60		tk[0][2] ^= S[tk[KC-1][3]];
61		tk[0][3] ^= S[tk[KC-1][0]];
62		tk[0][0] ^= rcon[rconpointer++];
63
64		if (KC != 8) {
65			for (j = 1; j < KC; j++) {
66				*((word32*)tk[j]) ^= *((word32*)tk[j-1]);
67			}
68		} else {
69			for (j = 1; j < KC/2; j++) {
70				*((word32*)tk[j]) ^= *((word32*)tk[j-1]);
71			}
72			tk[KC/2][0] ^= S[tk[KC/2 - 1][0]];
73			tk[KC/2][1] ^= S[tk[KC/2 - 1][1]];
74			tk[KC/2][2] ^= S[tk[KC/2 - 1][2]];
75			tk[KC/2][3] ^= S[tk[KC/2 - 1][3]];
76			for (j = KC/2 + 1; j < KC; j++) {
77				*((word32*)tk[j]) ^= *((word32*)tk[j-1]);
78			}
79		}
80		/* copy values into round key array */
81		for (j = 0; (j < KC) && (r < ROUNDS + 1); ) {
82			for (; (j < KC) && (t < 4); j++, t++) {
83				*((word32*)W[r][t]) = *((word32*)tk[j]);
84			}
85			if (t == 4) {
86				r++;
87				t = 0;
88			}
89		}
90	}
91	return 0;
92#undef tk
93}
94
95int rijndaelKeyEncToDec(word8 W[MAXROUNDS+1][4][4], int ROUNDS) {
96	int r;
97	word8 *w;
98
99	for (r = 1; r < ROUNDS; r++) {
100		w = W[r][0];
101		*((word32*)w) =
102			  *((const word32*)U1[w[0]])
103			^ *((const word32*)U2[w[1]])
104			^ *((const word32*)U3[w[2]])
105			^ *((const word32*)U4[w[3]]);
106
107		w = W[r][1];
108		*((word32*)w) =
109			  *((const word32*)U1[w[0]])
110			^ *((const word32*)U2[w[1]])
111			^ *((const word32*)U3[w[2]])
112			^ *((const word32*)U4[w[3]]);
113
114		w = W[r][2];
115		*((word32*)w) =
116			  *((const word32*)U1[w[0]])
117			^ *((const word32*)U2[w[1]])
118			^ *((const word32*)U3[w[2]])
119			^ *((const word32*)U4[w[3]]);
120
121		w = W[r][3];
122		*((word32*)w) =
123			  *((const word32*)U1[w[0]])
124			^ *((const word32*)U2[w[1]])
125			^ *((const word32*)U3[w[2]])
126			^ *((const word32*)U4[w[3]]);
127	}
128	return 0;
129}
130
131/**
132 * Encrypt a single block.
133 */
134int rijndaelEncrypt(word8 in[16], word8 out[16], word8 rk[MAXROUNDS+1][4][4], int ROUNDS) {
135	int r;
136	union {
137		word8	x8[16];
138		word32	x32[4];
139	} xa, xb;
140#define	a	xa.x8
141#define	b	xb.x8
142	union {
143		word8	x8[4][4];
144		word32	x32[4];
145	} xtemp;
146#define	temp	xtemp.x8
147
148    memcpy(a, in, sizeof a);
149
150    *((word32*)temp[0]) = *((word32*)(a   )) ^ *((word32*)rk[0][0]);
151    *((word32*)temp[1]) = *((word32*)(a+ 4)) ^ *((word32*)rk[0][1]);
152    *((word32*)temp[2]) = *((word32*)(a+ 8)) ^ *((word32*)rk[0][2]);
153    *((word32*)temp[3]) = *((word32*)(a+12)) ^ *((word32*)rk[0][3]);
154    *((word32*)(b    )) = *((const word32*)T1[temp[0][0]])
155					^ *((const word32*)T2[temp[1][1]])
156					^ *((const word32*)T3[temp[2][2]])
157					^ *((const word32*)T4[temp[3][3]]);
158    *((word32*)(b + 4)) = *((const word32*)T1[temp[1][0]])
159					^ *((const word32*)T2[temp[2][1]])
160					^ *((const word32*)T3[temp[3][2]])
161					^ *((const word32*)T4[temp[0][3]]);
162    *((word32*)(b + 8)) = *((const word32*)T1[temp[2][0]])
163					^ *((const word32*)T2[temp[3][1]])
164					^ *((const word32*)T3[temp[0][2]])
165					^ *((const word32*)T4[temp[1][3]]);
166    *((word32*)(b +12)) = *((const word32*)T1[temp[3][0]])
167					^ *((const word32*)T2[temp[0][1]])
168					^ *((const word32*)T3[temp[1][2]])
169					^ *((const word32*)T4[temp[2][3]]);
170	for (r = 1; r < ROUNDS-1; r++) {
171		*((word32*)temp[0]) = *((word32*)(b   )) ^ *((word32*)rk[r][0]);
172		*((word32*)temp[1]) = *((word32*)(b+ 4)) ^ *((word32*)rk[r][1]);
173		*((word32*)temp[2]) = *((word32*)(b+ 8)) ^ *((word32*)rk[r][2]);
174		*((word32*)temp[3]) = *((word32*)(b+12)) ^ *((word32*)rk[r][3]);
175
176		*((word32*)(b    )) = *((const word32*)T1[temp[0][0]])
177					^ *((const word32*)T2[temp[1][1]])
178					^ *((const word32*)T3[temp[2][2]])
179					^ *((const word32*)T4[temp[3][3]]);
180		*((word32*)(b + 4)) = *((const word32*)T1[temp[1][0]])
181					^ *((const word32*)T2[temp[2][1]])
182					^ *((const word32*)T3[temp[3][2]])
183					^ *((const word32*)T4[temp[0][3]]);
184		*((word32*)(b + 8)) = *((const word32*)T1[temp[2][0]])
185					^ *((const word32*)T2[temp[3][1]])
186					^ *((const word32*)T3[temp[0][2]])
187					^ *((const word32*)T4[temp[1][3]]);
188		*((word32*)(b +12)) = *((const word32*)T1[temp[3][0]])
189					^ *((const word32*)T2[temp[0][1]])
190					^ *((const word32*)T3[temp[1][2]])
191					^ *((const word32*)T4[temp[2][3]]);
192	}
193	/* last round is special */
194	*((word32*)temp[0]) = *((word32*)(b   )) ^ *((word32*)rk[ROUNDS-1][0]);
195	*((word32*)temp[1]) = *((word32*)(b+ 4)) ^ *((word32*)rk[ROUNDS-1][1]);
196	*((word32*)temp[2]) = *((word32*)(b+ 8)) ^ *((word32*)rk[ROUNDS-1][2]);
197	*((word32*)temp[3]) = *((word32*)(b+12)) ^ *((word32*)rk[ROUNDS-1][3]);
198	b[ 0] = T1[temp[0][0]][1];
199	b[ 1] = T1[temp[1][1]][1];
200	b[ 2] = T1[temp[2][2]][1];
201	b[ 3] = T1[temp[3][3]][1];
202	b[ 4] = T1[temp[1][0]][1];
203	b[ 5] = T1[temp[2][1]][1];
204	b[ 6] = T1[temp[3][2]][1];
205	b[ 7] = T1[temp[0][3]][1];
206	b[ 8] = T1[temp[2][0]][1];
207	b[ 9] = T1[temp[3][1]][1];
208	b[10] = T1[temp[0][2]][1];
209	b[11] = T1[temp[1][3]][1];
210	b[12] = T1[temp[3][0]][1];
211	b[13] = T1[temp[0][1]][1];
212	b[14] = T1[temp[1][2]][1];
213	b[15] = T1[temp[2][3]][1];
214	*((word32*)(b   )) ^= *((word32*)rk[ROUNDS][0]);
215	*((word32*)(b+ 4)) ^= *((word32*)rk[ROUNDS][1]);
216	*((word32*)(b+ 8)) ^= *((word32*)rk[ROUNDS][2]);
217	*((word32*)(b+12)) ^= *((word32*)rk[ROUNDS][3]);
218
219	memcpy(out, b, sizeof b /* XXX out */);
220
221	return 0;
222#undef a
223#undef b
224#undef temp
225}
226
227#ifdef INTERMEDIATE_VALUE_KAT
228/**
229 * Encrypt only a certain number of rounds.
230 * Only used in the Intermediate Value Known Answer Test.
231 */
232int rijndaelEncryptRound(word8 a[4][4], word8 rk[MAXROUNDS+1][4][4], int ROUNDS, int rounds) {
233	int r;
234	word8 temp[4][4];
235
236	/* make number of rounds sane */
237	if (rounds > ROUNDS) {
238		rounds = ROUNDS;
239	}
240
241	*((word32*)a[0]) = *((word32*)a[0]) ^ *((word32*)rk[0][0]);
242	*((word32*)a[1]) = *((word32*)a[1]) ^ *((word32*)rk[0][1]);
243	*((word32*)a[2]) = *((word32*)a[2]) ^ *((word32*)rk[0][2]);
244	*((word32*)a[3]) = *((word32*)a[3]) ^ *((word32*)rk[0][3]);
245
246	for (r = 1; (r <= rounds) && (r < ROUNDS); r++) {
247		*((word32*)temp[0]) = *((word32*)T1[a[0][0]])
248           ^ *((word32*)T2[a[1][1]])
249           ^ *((word32*)T3[a[2][2]])
250           ^ *((word32*)T4[a[3][3]]);
251		*((word32*)temp[1]) = *((word32*)T1[a[1][0]])
252           ^ *((word32*)T2[a[2][1]])
253           ^ *((word32*)T3[a[3][2]])
254           ^ *((word32*)T4[a[0][3]]);
255		*((word32*)temp[2]) = *((word32*)T1[a[2][0]])
256           ^ *((word32*)T2[a[3][1]])
257           ^ *((word32*)T3[a[0][2]])
258           ^ *((word32*)T4[a[1][3]]);
259		*((word32*)temp[3]) = *((word32*)T1[a[3][0]])
260           ^ *((word32*)T2[a[0][1]])
261           ^ *((word32*)T3[a[1][2]])
262           ^ *((word32*)T4[a[2][3]]);
263		*((word32*)a[0]) = *((word32*)temp[0]) ^ *((word32*)rk[r][0]);
264		*((word32*)a[1]) = *((word32*)temp[1]) ^ *((word32*)rk[r][1]);
265		*((word32*)a[2]) = *((word32*)temp[2]) ^ *((word32*)rk[r][2]);
266		*((word32*)a[3]) = *((word32*)temp[3]) ^ *((word32*)rk[r][3]);
267	}
268	if (rounds == ROUNDS) {
269	   	/* last round is special */
270	   	temp[0][0] = T1[a[0][0]][1];
271	   	temp[0][1] = T1[a[1][1]][1];
272	   	temp[0][2] = T1[a[2][2]][1];
273	   	temp[0][3] = T1[a[3][3]][1];
274	   	temp[1][0] = T1[a[1][0]][1];
275	   	temp[1][1] = T1[a[2][1]][1];
276	   	temp[1][2] = T1[a[3][2]][1];
277	   	temp[1][3] = T1[a[0][3]][1];
278	   	temp[2][0] = T1[a[2][0]][1];
279	   	temp[2][1] = T1[a[3][1]][1];
280	   	temp[2][2] = T1[a[0][2]][1];
281	   	temp[2][3] = T1[a[1][3]][1];
282	   	temp[3][0] = T1[a[3][0]][1];
283	   	temp[3][1] = T1[a[0][1]][1];
284	   	temp[3][2] = T1[a[1][2]][1];
285	   	temp[3][3] = T1[a[2][3]][1];
286		*((word32*)a[0]) = *((word32*)temp[0]) ^ *((word32*)rk[ROUNDS][0]);
287		*((word32*)a[1]) = *((word32*)temp[1]) ^ *((word32*)rk[ROUNDS][1]);
288		*((word32*)a[2]) = *((word32*)temp[2]) ^ *((word32*)rk[ROUNDS][2]);
289		*((word32*)a[3]) = *((word32*)temp[3]) ^ *((word32*)rk[ROUNDS][3]);
290	}
291
292	return 0;
293}
294#endif /* INTERMEDIATE_VALUE_KAT */
295
296/**
297 * Decrypt a single block.
298 */
299int rijndaelDecrypt(word8 in[16], word8 out[16], word8 rk[MAXROUNDS+1][4][4], int ROUNDS) {
300	int r;
301	union {
302		word8	x8[16];
303		word32	x32[4];
304	} xa, xb;
305#define	a	xa.x8
306#define	b	xb.x8
307	union {
308		word8	x8[4][4];
309		word32	x32[4];
310	} xtemp;
311#define	temp	xtemp.x8
312
313    memcpy(a, in, sizeof a);
314
315    *((word32*)temp[0]) = *((word32*)(a   )) ^ *((word32*)rk[ROUNDS][0]);
316    *((word32*)temp[1]) = *((word32*)(a+ 4)) ^ *((word32*)rk[ROUNDS][1]);
317    *((word32*)temp[2]) = *((word32*)(a+ 8)) ^ *((word32*)rk[ROUNDS][2]);
318    *((word32*)temp[3]) = *((word32*)(a+12)) ^ *((word32*)rk[ROUNDS][3]);
319
320    *((word32*)(b   )) = *((const word32*)T5[temp[0][0]])
321           ^ *((const word32*)T6[temp[3][1]])
322           ^ *((const word32*)T7[temp[2][2]])
323           ^ *((const word32*)T8[temp[1][3]]);
324	*((word32*)(b+ 4)) = *((const word32*)T5[temp[1][0]])
325           ^ *((const word32*)T6[temp[0][1]])
326           ^ *((const word32*)T7[temp[3][2]])
327           ^ *((const word32*)T8[temp[2][3]]);
328	*((word32*)(b+ 8)) = *((const word32*)T5[temp[2][0]])
329           ^ *((const word32*)T6[temp[1][1]])
330           ^ *((const word32*)T7[temp[0][2]])
331           ^ *((const word32*)T8[temp[3][3]]);
332	*((word32*)(b+12)) = *((const word32*)T5[temp[3][0]])
333           ^ *((const word32*)T6[temp[2][1]])
334           ^ *((const word32*)T7[temp[1][2]])
335           ^ *((const word32*)T8[temp[0][3]]);
336	for (r = ROUNDS-1; r > 1; r--) {
337		*((word32*)temp[0]) = *((word32*)(b   )) ^ *((word32*)rk[r][0]);
338		*((word32*)temp[1]) = *((word32*)(b+ 4)) ^ *((word32*)rk[r][1]);
339		*((word32*)temp[2]) = *((word32*)(b+ 8)) ^ *((word32*)rk[r][2]);
340		*((word32*)temp[3]) = *((word32*)(b+12)) ^ *((word32*)rk[r][3]);
341		*((word32*)(b   )) = *((const word32*)T5[temp[0][0]])
342           ^ *((const word32*)T6[temp[3][1]])
343           ^ *((const word32*)T7[temp[2][2]])
344           ^ *((const word32*)T8[temp[1][3]]);
345		*((word32*)(b+ 4)) = *((const word32*)T5[temp[1][0]])
346           ^ *((const word32*)T6[temp[0][1]])
347           ^ *((const word32*)T7[temp[3][2]])
348           ^ *((const word32*)T8[temp[2][3]]);
349		*((word32*)(b+ 8)) = *((const word32*)T5[temp[2][0]])
350           ^ *((const word32*)T6[temp[1][1]])
351           ^ *((const word32*)T7[temp[0][2]])
352           ^ *((const word32*)T8[temp[3][3]]);
353		*((word32*)(b+12)) = *((const word32*)T5[temp[3][0]])
354           ^ *((const word32*)T6[temp[2][1]])
355           ^ *((const word32*)T7[temp[1][2]])
356           ^ *((const word32*)T8[temp[0][3]]);
357	}
358	/* last round is special */
359	*((word32*)temp[0]) = *((word32*)(b   )) ^ *((word32*)rk[1][0]);
360	*((word32*)temp[1]) = *((word32*)(b+ 4)) ^ *((word32*)rk[1][1]);
361	*((word32*)temp[2]) = *((word32*)(b+ 8)) ^ *((word32*)rk[1][2]);
362	*((word32*)temp[3]) = *((word32*)(b+12)) ^ *((word32*)rk[1][3]);
363	b[ 0] = S5[temp[0][0]];
364	b[ 1] = S5[temp[3][1]];
365	b[ 2] = S5[temp[2][2]];
366	b[ 3] = S5[temp[1][3]];
367	b[ 4] = S5[temp[1][0]];
368	b[ 5] = S5[temp[0][1]];
369	b[ 6] = S5[temp[3][2]];
370	b[ 7] = S5[temp[2][3]];
371	b[ 8] = S5[temp[2][0]];
372	b[ 9] = S5[temp[1][1]];
373	b[10] = S5[temp[0][2]];
374	b[11] = S5[temp[3][3]];
375	b[12] = S5[temp[3][0]];
376	b[13] = S5[temp[2][1]];
377	b[14] = S5[temp[1][2]];
378	b[15] = S5[temp[0][3]];
379	*((word32*)(b   )) ^= *((word32*)rk[0][0]);
380	*((word32*)(b+ 4)) ^= *((word32*)rk[0][1]);
381	*((word32*)(b+ 8)) ^= *((word32*)rk[0][2]);
382	*((word32*)(b+12)) ^= *((word32*)rk[0][3]);
383
384	memcpy(out, b, sizeof b /* XXX out */);
385
386	return 0;
387#undef a
388#undef b
389#undef temp
390}
391
392
393#ifdef INTERMEDIATE_VALUE_KAT
394/**
395 * Decrypt only a certain number of rounds.
396 * Only used in the Intermediate Value Known Answer Test.
397 * Operations rearranged such that the intermediate values
398 * of decryption correspond with the intermediate values
399 * of encryption.
400 */
401int rijndaelDecryptRound(word8 a[4][4], word8 rk[MAXROUNDS+1][4][4], int ROUNDS, int rounds) {
402	int r, i;
403	word8 temp[4], shift;
404
405	/* make number of rounds sane */
406	if (rounds > ROUNDS) {
407		rounds = ROUNDS;
408	}
409    /* first round is special: */
410	*(word32 *)a[0] ^= *(word32 *)rk[ROUNDS][0];
411	*(word32 *)a[1] ^= *(word32 *)rk[ROUNDS][1];
412	*(word32 *)a[2] ^= *(word32 *)rk[ROUNDS][2];
413	*(word32 *)a[3] ^= *(word32 *)rk[ROUNDS][3];
414	for (i = 0; i < 4; i++) {
415		a[i][0] = Si[a[i][0]];
416		a[i][1] = Si[a[i][1]];
417		a[i][2] = Si[a[i][2]];
418		a[i][3] = Si[a[i][3]];
419	}
420	for (i = 1; i < 4; i++) {
421		shift = (4 - i) & 3;
422		temp[0] = a[(0 + shift) & 3][i];
423		temp[1] = a[(1 + shift) & 3][i];
424		temp[2] = a[(2 + shift) & 3][i];
425		temp[3] = a[(3 + shift) & 3][i];
426		a[0][i] = temp[0];
427		a[1][i] = temp[1];
428		a[2][i] = temp[2];
429		a[3][i] = temp[3];
430	}
431	/* ROUNDS-1 ordinary rounds */
432	for (r = ROUNDS-1; r > rounds; r--) {
433		*(word32 *)a[0] ^= *(word32 *)rk[r][0];
434		*(word32 *)a[1] ^= *(word32 *)rk[r][1];
435		*(word32 *)a[2] ^= *(word32 *)rk[r][2];
436		*(word32 *)a[3] ^= *(word32 *)rk[r][3];
437
438		*((word32*)a[0]) =
439			  *((word32*)U1[a[0][0]])
440			^ *((word32*)U2[a[0][1]])
441			^ *((word32*)U3[a[0][2]])
442			^ *((word32*)U4[a[0][3]]);
443
444		*((word32*)a[1]) =
445			  *((word32*)U1[a[1][0]])
446			^ *((word32*)U2[a[1][1]])
447			^ *((word32*)U3[a[1][2]])
448			^ *((word32*)U4[a[1][3]]);
449
450		*((word32*)a[2]) =
451			  *((word32*)U1[a[2][0]])
452			^ *((word32*)U2[a[2][1]])
453			^ *((word32*)U3[a[2][2]])
454			^ *((word32*)U4[a[2][3]]);
455
456		*((word32*)a[3]) =
457			  *((word32*)U1[a[3][0]])
458			^ *((word32*)U2[a[3][1]])
459			^ *((word32*)U3[a[3][2]])
460			^ *((word32*)U4[a[3][3]]);
461		for (i = 0; i < 4; i++) {
462			a[i][0] = Si[a[i][0]];
463			a[i][1] = Si[a[i][1]];
464			a[i][2] = Si[a[i][2]];
465			a[i][3] = Si[a[i][3]];
466		}
467		for (i = 1; i < 4; i++) {
468			shift = (4 - i) & 3;
469			temp[0] = a[(0 + shift) & 3][i];
470			temp[1] = a[(1 + shift) & 3][i];
471			temp[2] = a[(2 + shift) & 3][i];
472			temp[3] = a[(3 + shift) & 3][i];
473			a[0][i] = temp[0];
474			a[1][i] = temp[1];
475			a[2][i] = temp[2];
476			a[3][i] = temp[3];
477		}
478	}
479	if (rounds == 0) {
480		/* End with the extra key addition */
481		*(word32 *)a[0] ^= *(word32 *)rk[0][0];
482		*(word32 *)a[1] ^= *(word32 *)rk[0][1];
483		*(word32 *)a[2] ^= *(word32 *)rk[0][2];
484		*(word32 *)a[3] ^= *(word32 *)rk[0][3];
485	}
486	return 0;
487}
488#endif /* INTERMEDIATE_VALUE_KAT */
489