chiark / gitweb /
site: Generalise deletion and timeout of keys
[secnet.git] / serpent.c
1 /*
2  * This file is
3  *   Copyright (C) 1998 Ross Anderson, Eli Biham, Lars Knudsen
4  *
5  * For more information see http://www.cl.cam.ac.uk/users/rja14/serpent.html
6  *
7  *  This program is free software; you can redistribute it and/or modify
8  *  it under the terms of the GNU General Public License as published by
9  *  the Free Software Foundation; either version 2, or (at your option)
10  *  any later version.
11  *  
12  *  This program is distributed in the hope that it will be useful,
13  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  *  GNU General Public License for more details.
16  *  
17  *  You should have received a copy of the GNU General Public License
18  *  along with this program; if not, write to the Free Software Foundation,
19  *  Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 
20  *
21  */
22
23 #include "secnet.h"
24
25 #include "serpent.h"
26 #include "serpentsboxes.h"
27
28 void serpent_makekey(struct keyInstance *key, int keyLen,
29             uint8_t *keyMaterial)
30 {
31     int i;
32     uint32_t j;
33     uint32_t w[132],k[132];
34
35     for(i=0; i<keyLen/32; i++)
36         w[i]=GET_32BIT_MSB_FIRST(keyMaterial + (keyLen/8 - i*4) - 4);
37     if(keyLen<256)
38         w[i]=(GET_32BIT_MSB_FIRST(keyMaterial + (keyLen/8 - i*4) - 4)
39               & ((1L<<((keyLen&31)))-1)) | (1L<<((keyLen&31)));
40     for(i++; i<8; i++)
41         w[i]=0;
42     for(i=8; i<16; i++)
43         w[i]=ROL(w[i-8]^w[i-5]^w[i-3]^w[i-1]^PHI^(i-8),11);
44     for(i=0; i<8; i++)
45         w[i]=w[i+8];
46     for(i=8; i<132; i++)
47         w[i]=ROL(w[i-8]^w[i-5]^w[i-3]^w[i-1]^PHI^i,11);
48
49     RND03(w[  0], w[  1], w[  2], w[  3], k[  0], k[  1], k[  2], k[  3]);
50     RND02(w[  4], w[  5], w[  6], w[  7], k[  4], k[  5], k[  6], k[  7]);
51     RND01(w[  8], w[  9], w[ 10], w[ 11], k[  8], k[  9], k[ 10], k[ 11]);
52     RND00(w[ 12], w[ 13], w[ 14], w[ 15], k[ 12], k[ 13], k[ 14], k[ 15]);
53     RND31(w[ 16], w[ 17], w[ 18], w[ 19], k[ 16], k[ 17], k[ 18], k[ 19]);
54     RND30(w[ 20], w[ 21], w[ 22], w[ 23], k[ 20], k[ 21], k[ 22], k[ 23]);
55     RND29(w[ 24], w[ 25], w[ 26], w[ 27], k[ 24], k[ 25], k[ 26], k[ 27]);
56     RND28(w[ 28], w[ 29], w[ 30], w[ 31], k[ 28], k[ 29], k[ 30], k[ 31]);
57     RND27(w[ 32], w[ 33], w[ 34], w[ 35], k[ 32], k[ 33], k[ 34], k[ 35]);
58     RND26(w[ 36], w[ 37], w[ 38], w[ 39], k[ 36], k[ 37], k[ 38], k[ 39]);
59     RND25(w[ 40], w[ 41], w[ 42], w[ 43], k[ 40], k[ 41], k[ 42], k[ 43]);
60     RND24(w[ 44], w[ 45], w[ 46], w[ 47], k[ 44], k[ 45], k[ 46], k[ 47]);
61     RND23(w[ 48], w[ 49], w[ 50], w[ 51], k[ 48], k[ 49], k[ 50], k[ 51]);
62     RND22(w[ 52], w[ 53], w[ 54], w[ 55], k[ 52], k[ 53], k[ 54], k[ 55]);
63     RND21(w[ 56], w[ 57], w[ 58], w[ 59], k[ 56], k[ 57], k[ 58], k[ 59]);
64     RND20(w[ 60], w[ 61], w[ 62], w[ 63], k[ 60], k[ 61], k[ 62], k[ 63]);
65     RND19(w[ 64], w[ 65], w[ 66], w[ 67], k[ 64], k[ 65], k[ 66], k[ 67]);
66     RND18(w[ 68], w[ 69], w[ 70], w[ 71], k[ 68], k[ 69], k[ 70], k[ 71]);
67     RND17(w[ 72], w[ 73], w[ 74], w[ 75], k[ 72], k[ 73], k[ 74], k[ 75]);
68     RND16(w[ 76], w[ 77], w[ 78], w[ 79], k[ 76], k[ 77], k[ 78], k[ 79]);
69     RND15(w[ 80], w[ 81], w[ 82], w[ 83], k[ 80], k[ 81], k[ 82], k[ 83]);
70     RND14(w[ 84], w[ 85], w[ 86], w[ 87], k[ 84], k[ 85], k[ 86], k[ 87]);
71     RND13(w[ 88], w[ 89], w[ 90], w[ 91], k[ 88], k[ 89], k[ 90], k[ 91]);
72     RND12(w[ 92], w[ 93], w[ 94], w[ 95], k[ 92], k[ 93], k[ 94], k[ 95]);
73     RND11(w[ 96], w[ 97], w[ 98], w[ 99], k[ 96], k[ 97], k[ 98], k[ 99]);
74     RND10(w[100], w[101], w[102], w[103], k[100], k[101], k[102], k[103]);
75     RND09(w[104], w[105], w[106], w[107], k[104], k[105], k[106], k[107]);
76     RND08(w[108], w[109], w[110], w[111], k[108], k[109], k[110], k[111]);
77     RND07(w[112], w[113], w[114], w[115], k[112], k[113], k[114], k[115]);
78     RND06(w[116], w[117], w[118], w[119], k[116], k[117], k[118], k[119]);
79     RND05(w[120], w[121], w[122], w[123], k[120], k[121], k[122], k[123]);
80     RND04(w[124], w[125], w[126], w[127], k[124], k[125], k[126], k[127]);
81     RND03(w[128], w[129], w[130], w[131], k[128], k[129], k[130], k[131]);
82
83     for(i=0; i<=32; i++)
84         for(j=0; j<4; j++)
85             key->subkeys[i][j] = k[4*i+j];
86 }
87
88 void serpent_encrypt(struct keyInstance *key,
89                      uint8_t plaintext[16], 
90                      uint8_t ciphertext[16])
91 {
92     register uint32_t x0, x1, x2, x3;
93     register uint32_t y0, y1, y2, y3;
94
95     x0=GET_32BIT_MSB_FIRST(plaintext+12);
96     x1=GET_32BIT_MSB_FIRST(plaintext+8);
97     x2=GET_32BIT_MSB_FIRST(plaintext+4);
98     x3=GET_32BIT_MSB_FIRST(plaintext);
99
100     /* Start to encrypt the plaintext x */
101     keying(x0, x1, x2, x3, key->subkeys[ 0]);
102     RND00(x0, x1, x2, x3, y0, y1, y2, y3);
103     transform(y0, y1, y2, y3, x0, x1, x2, x3);
104     keying(x0, x1, x2, x3, key->subkeys[ 1]);
105     RND01(x0, x1, x2, x3, y0, y1, y2, y3);
106     transform(y0, y1, y2, y3, x0, x1, x2, x3);
107     keying(x0, x1, x2, x3, key->subkeys[ 2]);
108     RND02(x0, x1, x2, x3, y0, y1, y2, y3);
109     transform(y0, y1, y2, y3, x0, x1, x2, x3);
110     keying(x0, x1, x2, x3, key->subkeys[ 3]);
111     RND03(x0, x1, x2, x3, y0, y1, y2, y3);
112     transform(y0, y1, y2, y3, x0, x1, x2, x3);
113     keying(x0, x1, x2, x3, key->subkeys[ 4]);
114     RND04(x0, x1, x2, x3, y0, y1, y2, y3);
115     transform(y0, y1, y2, y3, x0, x1, x2, x3);
116     keying(x0, x1, x2, x3, key->subkeys[ 5]);
117     RND05(x0, x1, x2, x3, y0, y1, y2, y3);
118     transform(y0, y1, y2, y3, x0, x1, x2, x3);
119     keying(x0, x1, x2, x3, key->subkeys[ 6]);
120     RND06(x0, x1, x2, x3, y0, y1, y2, y3);
121     transform(y0, y1, y2, y3, x0, x1, x2, x3);
122     keying(x0, x1, x2, x3, key->subkeys[ 7]);
123     RND07(x0, x1, x2, x3, y0, y1, y2, y3);
124     transform(y0, y1, y2, y3, x0, x1, x2, x3);
125     keying(x0, x1, x2, x3, key->subkeys[ 8]);
126     RND08(x0, x1, x2, x3, y0, y1, y2, y3);
127     transform(y0, y1, y2, y3, x0, x1, x2, x3);
128     keying(x0, x1, x2, x3, key->subkeys[ 9]);
129     RND09(x0, x1, x2, x3, y0, y1, y2, y3);
130     transform(y0, y1, y2, y3, x0, x1, x2, x3);
131     keying(x0, x1, x2, x3, key->subkeys[10]);
132     RND10(x0, x1, x2, x3, y0, y1, y2, y3);
133     transform(y0, y1, y2, y3, x0, x1, x2, x3);
134     keying(x0, x1, x2, x3, key->subkeys[11]);
135     RND11(x0, x1, x2, x3, y0, y1, y2, y3);
136     transform(y0, y1, y2, y3, x0, x1, x2, x3);
137     keying(x0, x1, x2, x3, key->subkeys[12]);
138     RND12(x0, x1, x2, x3, y0, y1, y2, y3);
139     transform(y0, y1, y2, y3, x0, x1, x2, x3);
140     keying(x0, x1, x2, x3, key->subkeys[13]);
141     RND13(x0, x1, x2, x3, y0, y1, y2, y3);
142     transform(y0, y1, y2, y3, x0, x1, x2, x3);
143     keying(x0, x1, x2, x3, key->subkeys[14]);
144     RND14(x0, x1, x2, x3, y0, y1, y2, y3);
145     transform(y0, y1, y2, y3, x0, x1, x2, x3);
146     keying(x0, x1, x2, x3, key->subkeys[15]);
147     RND15(x0, x1, x2, x3, y0, y1, y2, y3);
148     transform(y0, y1, y2, y3, x0, x1, x2, x3);
149     keying(x0, x1, x2, x3, key->subkeys[16]);
150     RND16(x0, x1, x2, x3, y0, y1, y2, y3);
151     transform(y0, y1, y2, y3, x0, x1, x2, x3);
152     keying(x0, x1, x2, x3, key->subkeys[17]);
153     RND17(x0, x1, x2, x3, y0, y1, y2, y3);
154     transform(y0, y1, y2, y3, x0, x1, x2, x3);
155     keying(x0, x1, x2, x3, key->subkeys[18]);
156     RND18(x0, x1, x2, x3, y0, y1, y2, y3);
157     transform(y0, y1, y2, y3, x0, x1, x2, x3);
158     keying(x0, x1, x2, x3, key->subkeys[19]);
159     RND19(x0, x1, x2, x3, y0, y1, y2, y3);
160     transform(y0, y1, y2, y3, x0, x1, x2, x3);
161     keying(x0, x1, x2, x3, key->subkeys[20]);
162     RND20(x0, x1, x2, x3, y0, y1, y2, y3);
163     transform(y0, y1, y2, y3, x0, x1, x2, x3);
164     keying(x0, x1, x2, x3, key->subkeys[21]);
165     RND21(x0, x1, x2, x3, y0, y1, y2, y3);
166     transform(y0, y1, y2, y3, x0, x1, x2, x3);
167     keying(x0, x1, x2, x3, key->subkeys[22]);
168     RND22(x0, x1, x2, x3, y0, y1, y2, y3);
169     transform(y0, y1, y2, y3, x0, x1, x2, x3);
170     keying(x0, x1, x2, x3, key->subkeys[23]);
171     RND23(x0, x1, x2, x3, y0, y1, y2, y3);
172     transform(y0, y1, y2, y3, x0, x1, x2, x3);
173     keying(x0, x1, x2, x3, key->subkeys[24]);
174     RND24(x0, x1, x2, x3, y0, y1, y2, y3);
175     transform(y0, y1, y2, y3, x0, x1, x2, x3);
176     keying(x0, x1, x2, x3, key->subkeys[25]);
177     RND25(x0, x1, x2, x3, y0, y1, y2, y3);
178     transform(y0, y1, y2, y3, x0, x1, x2, x3);
179     keying(x0, x1, x2, x3, key->subkeys[26]);
180     RND26(x0, x1, x2, x3, y0, y1, y2, y3);
181     transform(y0, y1, y2, y3, x0, x1, x2, x3);
182     keying(x0, x1, x2, x3, key->subkeys[27]);
183     RND27(x0, x1, x2, x3, y0, y1, y2, y3);
184     transform(y0, y1, y2, y3, x0, x1, x2, x3);
185     keying(x0, x1, x2, x3, key->subkeys[28]);
186     RND28(x0, x1, x2, x3, y0, y1, y2, y3);
187     transform(y0, y1, y2, y3, x0, x1, x2, x3);
188     keying(x0, x1, x2, x3, key->subkeys[29]);
189     RND29(x0, x1, x2, x3, y0, y1, y2, y3);
190     transform(y0, y1, y2, y3, x0, x1, x2, x3);
191     keying(x0, x1, x2, x3, key->subkeys[30]);
192     RND30(x0, x1, x2, x3, y0, y1, y2, y3);
193     transform(y0, y1, y2, y3, x0, x1, x2, x3);
194     keying(x0, x1, x2, x3, key->subkeys[31]);
195     RND31(x0, x1, x2, x3, y0, y1, y2, y3);
196     x0 = y0; x1 = y1; x2 = y2; x3 = y3;
197     keying(x0, x1, x2, x3, key->subkeys[32]);
198     /* The ciphertext is now in x */
199
200     PUT_32BIT_MSB_FIRST(ciphertext+12, x0);
201     PUT_32BIT_MSB_FIRST(ciphertext+8, x1);
202     PUT_32BIT_MSB_FIRST(ciphertext+4, x2);
203     PUT_32BIT_MSB_FIRST(ciphertext, x3);
204 }
205
206 void serpent_decrypt(struct keyInstance *key,
207                      uint8_t ciphertext[16],
208                      uint8_t plaintext[16])
209 {
210     register uint32_t x0, x1, x2, x3;
211     register uint32_t y0, y1, y2, y3;
212
213     x0=GET_32BIT_MSB_FIRST(ciphertext+12);
214     x1=GET_32BIT_MSB_FIRST(ciphertext+8);
215     x2=GET_32BIT_MSB_FIRST(ciphertext+4);
216     x3=GET_32BIT_MSB_FIRST(ciphertext);
217
218     /* Start to decrypt the ciphertext x */
219     keying(x0, x1, x2, x3, key->subkeys[32]);
220     InvRND31(x0, x1, x2, x3, y0, y1, y2, y3);
221     keying(y0, y1, y2, y3, key->subkeys[31]);
222     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
223     InvRND30(x0, x1, x2, x3, y0, y1, y2, y3);
224     keying(y0, y1, y2, y3, key->subkeys[30]);
225     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
226     InvRND29(x0, x1, x2, x3, y0, y1, y2, y3);
227     keying(y0, y1, y2, y3, key->subkeys[29]);
228     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
229     InvRND28(x0, x1, x2, x3, y0, y1, y2, y3);
230     keying(y0, y1, y2, y3, key->subkeys[28]);
231     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
232     InvRND27(x0, x1, x2, x3, y0, y1, y2, y3);
233     keying(y0, y1, y2, y3, key->subkeys[27]);
234     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
235     InvRND26(x0, x1, x2, x3, y0, y1, y2, y3);
236     keying(y0, y1, y2, y3, key->subkeys[26]);
237     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
238     InvRND25(x0, x1, x2, x3, y0, y1, y2, y3);
239     keying(y0, y1, y2, y3, key->subkeys[25]);
240     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
241     InvRND24(x0, x1, x2, x3, y0, y1, y2, y3);
242     keying(y0, y1, y2, y3, key->subkeys[24]);
243     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
244     InvRND23(x0, x1, x2, x3, y0, y1, y2, y3);
245     keying(y0, y1, y2, y3, key->subkeys[23]);
246     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
247     InvRND22(x0, x1, x2, x3, y0, y1, y2, y3);
248     keying(y0, y1, y2, y3, key->subkeys[22]);
249     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
250     InvRND21(x0, x1, x2, x3, y0, y1, y2, y3);
251     keying(y0, y1, y2, y3, key->subkeys[21]);
252     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
253     InvRND20(x0, x1, x2, x3, y0, y1, y2, y3);
254     keying(y0, y1, y2, y3, key->subkeys[20]);
255     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
256     InvRND19(x0, x1, x2, x3, y0, y1, y2, y3);
257     keying(y0, y1, y2, y3, key->subkeys[19]);
258     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
259     InvRND18(x0, x1, x2, x3, y0, y1, y2, y3);
260     keying(y0, y1, y2, y3, key->subkeys[18]);
261     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
262     InvRND17(x0, x1, x2, x3, y0, y1, y2, y3);
263     keying(y0, y1, y2, y3, key->subkeys[17]);
264     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
265     InvRND16(x0, x1, x2, x3, y0, y1, y2, y3);
266     keying(y0, y1, y2, y3, key->subkeys[16]);
267     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
268     InvRND15(x0, x1, x2, x3, y0, y1, y2, y3);
269     keying(y0, y1, y2, y3, key->subkeys[15]);
270     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
271     InvRND14(x0, x1, x2, x3, y0, y1, y2, y3);
272     keying(y0, y1, y2, y3, key->subkeys[14]);
273     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
274     InvRND13(x0, x1, x2, x3, y0, y1, y2, y3);
275     keying(y0, y1, y2, y3, key->subkeys[13]);
276     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
277     InvRND12(x0, x1, x2, x3, y0, y1, y2, y3);
278     keying(y0, y1, y2, y3, key->subkeys[12]);
279     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
280     InvRND11(x0, x1, x2, x3, y0, y1, y2, y3);
281     keying(y0, y1, y2, y3, key->subkeys[11]);
282     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
283     InvRND10(x0, x1, x2, x3, y0, y1, y2, y3);
284     keying(y0, y1, y2, y3, key->subkeys[10]);
285     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
286     InvRND09(x0, x1, x2, x3, y0, y1, y2, y3);
287     keying(y0, y1, y2, y3, key->subkeys[ 9]);
288     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
289     InvRND08(x0, x1, x2, x3, y0, y1, y2, y3);
290     keying(y0, y1, y2, y3, key->subkeys[ 8]);
291     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
292     InvRND07(x0, x1, x2, x3, y0, y1, y2, y3);
293     keying(y0, y1, y2, y3, key->subkeys[ 7]);
294     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
295     InvRND06(x0, x1, x2, x3, y0, y1, y2, y3);
296     keying(y0, y1, y2, y3, key->subkeys[ 6]);
297     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
298     InvRND05(x0, x1, x2, x3, y0, y1, y2, y3);
299     keying(y0, y1, y2, y3, key->subkeys[ 5]);
300     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
301     InvRND04(x0, x1, x2, x3, y0, y1, y2, y3);
302     keying(y0, y1, y2, y3, key->subkeys[ 4]);
303     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
304     InvRND03(x0, x1, x2, x3, y0, y1, y2, y3);
305     keying(y0, y1, y2, y3, key->subkeys[ 3]);
306     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
307     InvRND02(x0, x1, x2, x3, y0, y1, y2, y3);
308     keying(y0, y1, y2, y3, key->subkeys[ 2]);
309     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
310     InvRND01(x0, x1, x2, x3, y0, y1, y2, y3);
311     keying(y0, y1, y2, y3, key->subkeys[ 1]);
312     inv_transform(y0, y1, y2, y3, x0, x1, x2, x3);
313     InvRND00(x0, x1, x2, x3, y0, y1, y2, y3);
314     x0 = y0; x1 = y1; x2 = y2; x3 = y3;
315     keying(x0, x1, x2, x3, key->subkeys[ 0]);
316     /* The plaintext is now in x */
317
318     PUT_32BIT_MSB_FIRST(plaintext+12, x0);
319     PUT_32BIT_MSB_FIRST(plaintext+8, x1);
320     PUT_32BIT_MSB_FIRST(plaintext+4, x2);
321     PUT_32BIT_MSB_FIRST(plaintext, x3);
322 }