POK
des_enc.c
1 /*
2  * POK header
3  *
4  * The following file is a part of the POK project. Any modification should
5  * made according to the POK licence. You CANNOT use this file or a part of
6  * this file is this part of a file for your own project
7  *
8  * For more information on the POK licence, please see our LICENCE FILE
9  *
10  * Please follow the coding guidelines described in doc/CODING_GUIDELINES
11  *
12  * Copyright (c) 2007-2009 POK team
13  *
14  * Created by julien on Tue Dec 8 15:53:28 2009
15  */
16 
17 /* crypto/des/des_enc.c */
18 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
19  * All rights reserved.
20  *
21  * This package is an SSL implementation written
22  * by Eric Young (eay@cryptsoft.com).
23  * The implementation was written so as to conform with Netscapes SSL.
24  *
25  * This library is free for commercial and non-commercial use as long as
26  * the following conditions are aheared to. The following conditions
27  * apply to all code found in this distribution, be it the RC4, RSA,
28  * lhash, DES, etc., code; not just the SSL code. The SSL documentation
29  * included with this distribution is covered by the same copyright terms
30  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
31  *
32  * Copyright remains Eric Young's, and as such any Copyright notices in
33  * the code are not to be removed.
34  * If this package is used in a product, Eric Young should be given attribution
35  * as the author of the parts of the library used.
36  * This can be in the form of a textual message at program startup or
37  * in documentation (online or textual) provided with the package.
38  *
39  * Redistribution and use in source and binary forms, with or without
40  * modification, are permitted provided that the following conditions
41  * are met:
42  * 1. Redistributions of source code must retain the copyright
43  * notice, this list of conditions and the following disclaimer.
44  * 2. Redistributions in binary form must reproduce the above copyright
45  * notice, this list of conditions and the following disclaimer in the
46  * documentation and/or other materials provided with the distribution.
47  * 3. All advertising materials mentioning features or use of this software
48  * must display the following acknowledgement:
49  * "This product includes cryptographic software written by
50  * Eric Young (eay@cryptsoft.com)"
51  * The word 'cryptographic' can be left out if the rouines from the library
52  * being used are not cryptographic related :-).
53  * 4. If you include any Windows specific code (or a derivative thereof) from
54  * the apps directory (application code) you must include an acknowledgement:
55  * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
56  *
57  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
58  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
59  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
60  * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
61  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
62  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
63  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
64  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
65  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
66  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
67  * SUCH DAMAGE.
68  *
69  * The licence and distribution terms for any publically available version or
70  * derivative of this code cannot be changed. i.e. this code cannot simply be
71  * copied and put under another distribution licence
72  * [including the GNU Public Licence.]
73  */
74 
75 #ifdef POK_NEEDS_PROTOCOLS_DES
76 
77 #include "des_locl.h"
78 #include "spr.h"
79 
80 void DES_encrypt1(DES_LONG *data, DES_key_schedule *ks, int enc)
81  {
82  register DES_LONG l,r,t,u;
83 #ifdef DES_PTR
84  register const unsigned char *des_SP=(const unsigned char *)DES_SPtrans;
85 #endif
86 #ifndef DES_UNROLL
87  register int i;
88 #endif
89  register DES_LONG *s;
90 
91  r=data[0];
92  l=data[1];
93 
94  IP(r,l);
95  /* Things have been modified so that the initial rotate is
96  * done outside the loop. This required the
97  * DES_SPtrans values in sp.h to be rotated 1 bit to the right.
98  * One perl script later and things have a 5% speed up on a sparc2.
99  * Thanks to Richard Outerbridge <71755.204@CompuServe.COM>
100  * for pointing this out. */
101  /* clear the top bits on machines with 8byte longs */
102  /* shift left by 2 */
103  r=ROTATE(r,29)&0xffffffffL;
104  l=ROTATE(l,29)&0xffffffffL;
105 
106  s=ks->ks->deslong;
107  /* I don't know if it is worth the effort of loop unrolling the
108  * inner loop */
109  if (enc)
110  {
111 #ifdef DES_UNROLL
112  D_ENCRYPT(l,r, 0); /* 1 */
113  D_ENCRYPT(r,l, 2); /* 2 */
114  D_ENCRYPT(l,r, 4); /* 3 */
115  D_ENCRYPT(r,l, 6); /* 4 */
116  D_ENCRYPT(l,r, 8); /* 5 */
117  D_ENCRYPT(r,l,10); /* 6 */
118  D_ENCRYPT(l,r,12); /* 7 */
119  D_ENCRYPT(r,l,14); /* 8 */
120  D_ENCRYPT(l,r,16); /* 9 */
121  D_ENCRYPT(r,l,18); /* 10 */
122  D_ENCRYPT(l,r,20); /* 11 */
123  D_ENCRYPT(r,l,22); /* 12 */
124  D_ENCRYPT(l,r,24); /* 13 */
125  D_ENCRYPT(r,l,26); /* 14 */
126  D_ENCRYPT(l,r,28); /* 15 */
127  D_ENCRYPT(r,l,30); /* 16 */
128 #else
129  for (i=0; i<32; i+=8)
130  {
131  D_ENCRYPT(l,r,i+0); /* 1 */
132  D_ENCRYPT(r,l,i+2); /* 2 */
133  D_ENCRYPT(l,r,i+4); /* 3 */
134  D_ENCRYPT(r,l,i+6); /* 4 */
135  }
136 #endif
137  }
138  else
139  {
140 #ifdef DES_UNROLL
141  D_ENCRYPT(l,r,30); /* 16 */
142  D_ENCRYPT(r,l,28); /* 15 */
143  D_ENCRYPT(l,r,26); /* 14 */
144  D_ENCRYPT(r,l,24); /* 13 */
145  D_ENCRYPT(l,r,22); /* 12 */
146  D_ENCRYPT(r,l,20); /* 11 */
147  D_ENCRYPT(l,r,18); /* 10 */
148  D_ENCRYPT(r,l,16); /* 9 */
149  D_ENCRYPT(l,r,14); /* 8 */
150  D_ENCRYPT(r,l,12); /* 7 */
151  D_ENCRYPT(l,r,10); /* 6 */
152  D_ENCRYPT(r,l, 8); /* 5 */
153  D_ENCRYPT(l,r, 6); /* 4 */
154  D_ENCRYPT(r,l, 4); /* 3 */
155  D_ENCRYPT(l,r, 2); /* 2 */
156  D_ENCRYPT(r,l, 0); /* 1 */
157 #else
158  for (i=30; i>0; i-=8)
159  {
160  D_ENCRYPT(l,r,i-0); /* 16 */
161  D_ENCRYPT(r,l,i-2); /* 15 */
162  D_ENCRYPT(l,r,i-4); /* 14 */
163  D_ENCRYPT(r,l,i-6); /* 13 */
164  }
165 #endif
166  }
167 
168  /* rotate and clear the top bits on machines with 8byte longs */
169  l=ROTATE(l,3)&0xffffffffL;
170  r=ROTATE(r,3)&0xffffffffL;
171 
172  FP(r,l);
173  data[0]=l;
174  data[1]=r;
175  l=r=t=u=0;
176  }
177 
178 void DES_encrypt2(DES_LONG *data, DES_key_schedule *ks, int enc)
179  {
180  register DES_LONG l,r,t,u;
181 #ifdef DES_PTR
182  register const unsigned char *des_SP=(const unsigned char *)DES_SPtrans;
183 #endif
184 #ifndef DES_UNROLL
185  register int i;
186 #endif
187  register DES_LONG *s;
188 
189  r=data[0];
190  l=data[1];
191 
192  /* Things have been modified so that the initial rotate is
193  * done outside the loop. This required the
194  * DES_SPtrans values in sp.h to be rotated 1 bit to the right.
195  * One perl script later and things have a 5% speed up on a sparc2.
196  * Thanks to Richard Outerbridge <71755.204@CompuServe.COM>
197  * for pointing this out. */
198  /* clear the top bits on machines with 8byte longs */
199  r=ROTATE(r,29)&0xffffffffL;
200  l=ROTATE(l,29)&0xffffffffL;
201 
202  s=ks->ks->deslong;
203  /* I don't know if it is worth the effort of loop unrolling the
204  * inner loop */
205  if (enc)
206  {
207 #ifdef DES_UNROLL
208  D_ENCRYPT(l,r, 0); /* 1 */
209  D_ENCRYPT(r,l, 2); /* 2 */
210  D_ENCRYPT(l,r, 4); /* 3 */
211  D_ENCRYPT(r,l, 6); /* 4 */
212  D_ENCRYPT(l,r, 8); /* 5 */
213  D_ENCRYPT(r,l,10); /* 6 */
214  D_ENCRYPT(l,r,12); /* 7 */
215  D_ENCRYPT(r,l,14); /* 8 */
216  D_ENCRYPT(l,r,16); /* 9 */
217  D_ENCRYPT(r,l,18); /* 10 */
218  D_ENCRYPT(l,r,20); /* 11 */
219  D_ENCRYPT(r,l,22); /* 12 */
220  D_ENCRYPT(l,r,24); /* 13 */
221  D_ENCRYPT(r,l,26); /* 14 */
222  D_ENCRYPT(l,r,28); /* 15 */
223  D_ENCRYPT(r,l,30); /* 16 */
224 #else
225  for (i=0; i<32; i+=8)
226  {
227  D_ENCRYPT(l,r,i+0); /* 1 */
228  D_ENCRYPT(r,l,i+2); /* 2 */
229  D_ENCRYPT(l,r,i+4); /* 3 */
230  D_ENCRYPT(r,l,i+6); /* 4 */
231  }
232 #endif
233  }
234  else
235  {
236 #ifdef DES_UNROLL
237  D_ENCRYPT(l,r,30); /* 16 */
238  D_ENCRYPT(r,l,28); /* 15 */
239  D_ENCRYPT(l,r,26); /* 14 */
240  D_ENCRYPT(r,l,24); /* 13 */
241  D_ENCRYPT(l,r,22); /* 12 */
242  D_ENCRYPT(r,l,20); /* 11 */
243  D_ENCRYPT(l,r,18); /* 10 */
244  D_ENCRYPT(r,l,16); /* 9 */
245  D_ENCRYPT(l,r,14); /* 8 */
246  D_ENCRYPT(r,l,12); /* 7 */
247  D_ENCRYPT(l,r,10); /* 6 */
248  D_ENCRYPT(r,l, 8); /* 5 */
249  D_ENCRYPT(l,r, 6); /* 4 */
250  D_ENCRYPT(r,l, 4); /* 3 */
251  D_ENCRYPT(l,r, 2); /* 2 */
252  D_ENCRYPT(r,l, 0); /* 1 */
253 #else
254  for (i=30; i>0; i-=8)
255  {
256  D_ENCRYPT(l,r,i-0); /* 16 */
257  D_ENCRYPT(r,l,i-2); /* 15 */
258  D_ENCRYPT(l,r,i-4); /* 14 */
259  D_ENCRYPT(r,l,i-6); /* 13 */
260  }
261 #endif
262  }
263  /* rotate and clear the top bits on machines with 8byte longs */
264  data[0]=ROTATE(l,3)&0xffffffffL;
265  data[1]=ROTATE(r,3)&0xffffffffL;
266  l=r=t=u=0;
267  }
268 
269 void DES_encrypt3(DES_LONG *data, DES_key_schedule *ks1,
271  {
272  register DES_LONG l,r;
273 
274  l=data[0];
275  r=data[1];
276  IP(l,r);
277  data[0]=l;
278  data[1]=r;
279  DES_encrypt2((DES_LONG *)data,ks1,DES_ENCRYPT);
280  DES_encrypt2((DES_LONG *)data,ks2,DES_DECRYPT);
281  DES_encrypt2((DES_LONG *)data,ks3,DES_ENCRYPT);
282  l=data[0];
283  r=data[1];
284  FP(r,l);
285  data[0]=l;
286  data[1]=r;
287  }
288 
289 void DES_decrypt3(DES_LONG *data, DES_key_schedule *ks1,
291  {
292  register DES_LONG l,r;
293 
294  l=data[0];
295  r=data[1];
296  IP(l,r);
297  data[0]=l;
298  data[1]=r;
299  DES_encrypt2((DES_LONG *)data,ks3,DES_DECRYPT);
300  DES_encrypt2((DES_LONG *)data,ks2,DES_ENCRYPT);
301  DES_encrypt2((DES_LONG *)data,ks1,DES_DECRYPT);
302  l=data[0];
303  r=data[1];
304  FP(r,l);
305  data[0]=l;
306  data[1]=r;
307  }
308 
309 #ifndef DES_DEFAULT_OPTIONS
310 
311 #if !defined(OPENSSL_FIPS_DES_ASM)
312 
313 #undef CBC_ENC_C__DONT_UPDATE_IV
314 #include "ncbc_enc.c" /* DES_ncbc_encrypt */
315 
316 void DES_ede3_cbc_encrypt(const unsigned char *input, unsigned char *output,
317  long length, DES_key_schedule *ks1,
319  DES_cblock *ivec, int enc)
320  {
321  register DES_LONG tin0,tin1;
322  register DES_LONG tout0,tout1,xor0,xor1;
323  register const unsigned char *in;
324  unsigned char *out;
325  register long l=length;
326  DES_LONG tin[2];
327  unsigned char *iv;
328 
329  in=input;
330  out=output;
331  iv = &(*ivec)[0];
332 
333  if (enc)
334  {
335  c2l(iv,tout0);
336  c2l(iv,tout1);
337  for (l-=8; l>=0; l-=8)
338  {
339  c2l(in,tin0);
340  c2l(in,tin1);
341  tin0^=tout0;
342  tin1^=tout1;
343 
344  tin[0]=tin0;
345  tin[1]=tin1;
346  DES_encrypt3((DES_LONG *)tin,ks1,ks2,ks3);
347  tout0=tin[0];
348  tout1=tin[1];
349 
350  l2c(tout0,out);
351  l2c(tout1,out);
352  }
353  if (l != -8)
354  {
355  c2ln(in,tin0,tin1,l+8);
356  tin0^=tout0;
357  tin1^=tout1;
358 
359  tin[0]=tin0;
360  tin[1]=tin1;
361  DES_encrypt3((DES_LONG *)tin,ks1,ks2,ks3);
362  tout0=tin[0];
363  tout1=tin[1];
364 
365  l2c(tout0,out);
366  l2c(tout1,out);
367  }
368  iv = &(*ivec)[0];
369  l2c(tout0,iv);
370  l2c(tout1,iv);
371  }
372  else
373  {
374  register DES_LONG t0,t1;
375 
376  c2l(iv,xor0);
377  c2l(iv,xor1);
378  for (l-=8; l>=0; l-=8)
379  {
380  c2l(in,tin0);
381  c2l(in,tin1);
382 
383  t0=tin0;
384  t1=tin1;
385 
386  tin[0]=tin0;
387  tin[1]=tin1;
388  DES_decrypt3((DES_LONG *)tin,ks1,ks2,ks3);
389  tout0=tin[0];
390  tout1=tin[1];
391 
392  tout0^=xor0;
393  tout1^=xor1;
394  l2c(tout0,out);
395  l2c(tout1,out);
396  xor0=t0;
397  xor1=t1;
398  }
399  if (l != -8)
400  {
401  c2l(in,tin0);
402  c2l(in,tin1);
403 
404  t0=tin0;
405  t1=tin1;
406 
407  tin[0]=tin0;
408  tin[1]=tin1;
409  DES_decrypt3((DES_LONG *)tin,ks1,ks2,ks3);
410  tout0=tin[0];
411  tout1=tin[1];
412 
413  tout0^=xor0;
414  tout1^=xor1;
415  l2cn(tout0,tout1,out,l+8);
416  xor0=t0;
417  xor1=t1;
418  }
419 
420  iv = &(*ivec)[0];
421  l2c(xor0,iv);
422  l2c(xor1,iv);
423  }
424  tin0=tin1=tout0=tout1=xor0=xor1=0;
425  tin[0]=tin[1]=0;
426  }
427 
428 #endif
429 
430 #endif /* DES_DEFAULT_OPTIONS */
431 
432 #endif /* POK_NEEDS ... */