• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
2  * All rights reserved.
3  *
4  * This package is an SSL implementation written
5  * by Eric Young (eay@cryptsoft.com).
6  * The implementation was written so as to conform with Netscapes SSL.
7  *
8  * This library is free for commercial and non-commercial use as long as
9  * the following conditions are aheared to.  The following conditions
10  * apply to all code found in this distribution, be it the RC4, RSA,
11  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
12  * included with this distribution is covered by the same copyright terms
13  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
14  *
15  * Copyright remains Eric Young's, and as such any Copyright notices in
16  * the code are not to be removed.
17  * If this package is used in a product, Eric Young should be given attribution
18  * as the author of the parts of the library used.
19  * This can be in the form of a textual message at program startup or
20  * in documentation (online or textual) provided with the package.
21  *
22  * Redistribution and use in source and binary forms, with or without
23  * modification, are permitted provided that the following conditions
24  * are met:
25  * 1. Redistributions of source code must retain the copyright
26  *    notice, this list of conditions and the following disclaimer.
27  * 2. Redistributions in binary form must reproduce the above copyright
28  *    notice, this list of conditions and the following disclaimer in the
29  *    documentation and/or other materials provided with the distribution.
30  * 3. All advertising materials mentioning features or use of this software
31  *    must display the following acknowledgement:
32  *    "This product includes cryptographic software written by
33  *     Eric Young (eay@cryptsoft.com)"
34  *    The word 'cryptographic' can be left out if the rouines from the library
35  *    being used are not cryptographic related :-).
36  * 4. If you include any Windows specific code (or a derivative thereof) from
37  *    the apps directory (application code) you must include an acknowledgement:
38  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
39  *
40  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
41  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
42  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
43  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
44  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
45  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
46  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
47  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
48  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
49  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
50  * SUCH DAMAGE.
51  *
52  * The licence and distribution terms for any publically available version or
53  * derivative of this code cannot be changed.  i.e. this code cannot simply be
54  * copied and put under another distribution licence
55  * [including the GNU Public Licence.] */
56 
57 #include <openssl/cipher.h>
58 #include <openssl/obj.h>
59 
60 #include "internal.h"
61 
62 
63 #define c2l(c, l)                                                           \
64   (l = ((uint32_t)(*((c)++))), l |= ((uint32_t)(*((c)++))) << 8L, \
65    l |= ((uint32_t)(*((c)++))) << 16L,                                 \
66    l |= ((uint32_t)(*((c)++))) << 24L)
67 
68 #define c2ln(c, l1, l2, n)                        \
69   {                                               \
70     c += n;                                       \
71     l1 = l2 = 0;                                  \
72     switch (n) {                                  \
73       case 8:                                     \
74         l2 = ((uint32_t)(*(--(c)))) << 24L;  \
75       case 7:                                     \
76         l2 |= ((uint32_t)(*(--(c)))) << 16L; \
77       case 6:                                     \
78         l2 |= ((uint32_t)(*(--(c)))) << 8L;  \
79       case 5:                                     \
80         l2 |= ((uint32_t)(*(--(c))));        \
81       case 4:                                     \
82         l1 = ((uint32_t)(*(--(c)))) << 24L;  \
83       case 3:                                     \
84         l1 |= ((uint32_t)(*(--(c)))) << 16L; \
85       case 2:                                     \
86         l1 |= ((uint32_t)(*(--(c)))) << 8L;  \
87       case 1:                                     \
88         l1 |= ((uint32_t)(*(--(c))));        \
89     }                                             \
90   }
91 
92 #define l2c(l, c)                                   \
93   (*((c)++) = (uint8_t)(((l)) & 0xff),        \
94    *((c)++) = (uint8_t)(((l) >> 8L) & 0xff),  \
95    *((c)++) = (uint8_t)(((l) >> 16L) & 0xff), \
96    *((c)++) = (uint8_t)(((l) >> 24L) & 0xff))
97 
98 #define l2cn(l1, l2, c, n)                                \
99   {                                                       \
100     c += n;                                               \
101     switch (n) {                                          \
102       case 8:                                             \
103         *(--(c)) = (uint8_t)(((l2) >> 24L) & 0xff); \
104       case 7:                                             \
105         *(--(c)) = (uint8_t)(((l2) >> 16L) & 0xff); \
106       case 6:                                             \
107         *(--(c)) = (uint8_t)(((l2) >> 8L) & 0xff);  \
108       case 5:                                             \
109         *(--(c)) = (uint8_t)(((l2)) & 0xff);        \
110       case 4:                                             \
111         *(--(c)) = (uint8_t)(((l1) >> 24L) & 0xff); \
112       case 3:                                             \
113         *(--(c)) = (uint8_t)(((l1) >> 16L) & 0xff); \
114       case 2:                                             \
115         *(--(c)) = (uint8_t)(((l1) >> 8L) & 0xff);  \
116       case 1:                                             \
117         *(--(c)) = (uint8_t)(((l1)) & 0xff);        \
118     }                                                     \
119   }
120 
121 typedef struct rc2_key_st { uint16_t data[64]; } RC2_KEY;
122 
RC2_encrypt(uint32_t * d,RC2_KEY * key)123 static void RC2_encrypt(uint32_t *d, RC2_KEY *key) {
124   int i, n;
125   uint16_t *p0, *p1;
126   uint16_t x0, x1, x2, x3, t;
127   uint32_t l;
128 
129   l = d[0];
130   x0 = (uint16_t)l & 0xffff;
131   x1 = (uint16_t)(l >> 16L);
132   l = d[1];
133   x2 = (uint16_t)l & 0xffff;
134   x3 = (uint16_t)(l >> 16L);
135 
136   n = 3;
137   i = 5;
138 
139   p0 = p1 = &key->data[0];
140   for (;;) {
141     t = (x0 + (x1 & ~x3) + (x2 & x3) + *(p0++)) & 0xffff;
142     x0 = (t << 1) | (t >> 15);
143     t = (x1 + (x2 & ~x0) + (x3 & x0) + *(p0++)) & 0xffff;
144     x1 = (t << 2) | (t >> 14);
145     t = (x2 + (x3 & ~x1) + (x0 & x1) + *(p0++)) & 0xffff;
146     x2 = (t << 3) | (t >> 13);
147     t = (x3 + (x0 & ~x2) + (x1 & x2) + *(p0++)) & 0xffff;
148     x3 = (t << 5) | (t >> 11);
149 
150     if (--i == 0) {
151       if (--n == 0) {
152         break;
153       }
154       i = (n == 2) ? 6 : 5;
155 
156       x0 += p1[x3 & 0x3f];
157       x1 += p1[x0 & 0x3f];
158       x2 += p1[x1 & 0x3f];
159       x3 += p1[x2 & 0x3f];
160     }
161   }
162 
163   d[0] = (uint32_t)(x0 & 0xffff) | ((uint32_t)(x1 & 0xffff) << 16L);
164   d[1] = (uint32_t)(x2 & 0xffff) | ((uint32_t)(x3 & 0xffff) << 16L);
165 }
166 
RC2_decrypt(uint32_t * d,RC2_KEY * key)167 static void RC2_decrypt(uint32_t *d, RC2_KEY *key) {
168   int i, n;
169   uint16_t *p0, *p1;
170   uint16_t x0, x1, x2, x3, t;
171   uint32_t l;
172 
173   l = d[0];
174   x0 = (uint16_t)l & 0xffff;
175   x1 = (uint16_t)(l >> 16L);
176   l = d[1];
177   x2 = (uint16_t)l & 0xffff;
178   x3 = (uint16_t)(l >> 16L);
179 
180   n = 3;
181   i = 5;
182 
183   p0 = &key->data[63];
184   p1 = &key->data[0];
185   for (;;) {
186     t = ((x3 << 11) | (x3 >> 5)) & 0xffff;
187     x3 = (t - (x0 & ~x2) - (x1 & x2) - *(p0--)) & 0xffff;
188     t = ((x2 << 13) | (x2 >> 3)) & 0xffff;
189     x2 = (t - (x3 & ~x1) - (x0 & x1) - *(p0--)) & 0xffff;
190     t = ((x1 << 14) | (x1 >> 2)) & 0xffff;
191     x1 = (t - (x2 & ~x0) - (x3 & x0) - *(p0--)) & 0xffff;
192     t = ((x0 << 15) | (x0 >> 1)) & 0xffff;
193     x0 = (t - (x1 & ~x3) - (x2 & x3) - *(p0--)) & 0xffff;
194 
195     if (--i == 0) {
196       if (--n == 0) {
197         break;
198       }
199       i = (n == 2) ? 6 : 5;
200 
201       x3 = (x3 - p1[x2 & 0x3f]) & 0xffff;
202       x2 = (x2 - p1[x1 & 0x3f]) & 0xffff;
203       x1 = (x1 - p1[x0 & 0x3f]) & 0xffff;
204       x0 = (x0 - p1[x3 & 0x3f]) & 0xffff;
205     }
206   }
207 
208   d[0] = (uint32_t)(x0 & 0xffff) | ((uint32_t)(x1 & 0xffff) << 16L);
209   d[1] = (uint32_t)(x2 & 0xffff) | ((uint32_t)(x3 & 0xffff) << 16L);
210 }
211 
RC2_cbc_encrypt(const uint8_t * in,uint8_t * out,size_t length,RC2_KEY * ks,uint8_t * iv,int encrypt)212 static void RC2_cbc_encrypt(const uint8_t *in, uint8_t *out, size_t length,
213                             RC2_KEY *ks, uint8_t *iv, int encrypt) {
214   uint32_t tin0, tin1;
215   uint32_t tout0, tout1, xor0, xor1;
216   long l = length;
217   uint32_t tin[2];
218 
219   if (encrypt) {
220     c2l(iv, tout0);
221     c2l(iv, tout1);
222     iv -= 8;
223     for (l -= 8; l >= 0; l -= 8) {
224       c2l(in, tin0);
225       c2l(in, tin1);
226       tin0 ^= tout0;
227       tin1 ^= tout1;
228       tin[0] = tin0;
229       tin[1] = tin1;
230       RC2_encrypt(tin, ks);
231       tout0 = tin[0];
232       l2c(tout0, out);
233       tout1 = tin[1];
234       l2c(tout1, out);
235     }
236     if (l != -8) {
237       c2ln(in, tin0, tin1, l + 8);
238       tin0 ^= tout0;
239       tin1 ^= tout1;
240       tin[0] = tin0;
241       tin[1] = tin1;
242       RC2_encrypt(tin, ks);
243       tout0 = tin[0];
244       l2c(tout0, out);
245       tout1 = tin[1];
246       l2c(tout1, out);
247     }
248     l2c(tout0, iv);
249     l2c(tout1, iv);
250   } else {
251     c2l(iv, xor0);
252     c2l(iv, xor1);
253     iv -= 8;
254     for (l -= 8; l >= 0; l -= 8) {
255       c2l(in, tin0);
256       tin[0] = tin0;
257       c2l(in, tin1);
258       tin[1] = tin1;
259       RC2_decrypt(tin, ks);
260       tout0 = tin[0] ^ xor0;
261       tout1 = tin[1] ^ xor1;
262       l2c(tout0, out);
263       l2c(tout1, out);
264       xor0 = tin0;
265       xor1 = tin1;
266     }
267     if (l != -8) {
268       c2l(in, tin0);
269       tin[0] = tin0;
270       c2l(in, tin1);
271       tin[1] = tin1;
272       RC2_decrypt(tin, ks);
273       tout0 = tin[0] ^ xor0;
274       tout1 = tin[1] ^ xor1;
275       l2cn(tout0, tout1, out, l + 8);
276       xor0 = tin0;
277       xor1 = tin1;
278     }
279     l2c(xor0, iv);
280     l2c(xor1, iv);
281   }
282   tin[0] = tin[1] = 0;
283 }
284 
285 static const uint8_t key_table[256] = {
286     0xd9, 0x78, 0xf9, 0xc4, 0x19, 0xdd, 0xb5, 0xed, 0x28, 0xe9, 0xfd, 0x79,
287     0x4a, 0xa0, 0xd8, 0x9d, 0xc6, 0x7e, 0x37, 0x83, 0x2b, 0x76, 0x53, 0x8e,
288     0x62, 0x4c, 0x64, 0x88, 0x44, 0x8b, 0xfb, 0xa2, 0x17, 0x9a, 0x59, 0xf5,
289     0x87, 0xb3, 0x4f, 0x13, 0x61, 0x45, 0x6d, 0x8d, 0x09, 0x81, 0x7d, 0x32,
290     0xbd, 0x8f, 0x40, 0xeb, 0x86, 0xb7, 0x7b, 0x0b, 0xf0, 0x95, 0x21, 0x22,
291     0x5c, 0x6b, 0x4e, 0x82, 0x54, 0xd6, 0x65, 0x93, 0xce, 0x60, 0xb2, 0x1c,
292     0x73, 0x56, 0xc0, 0x14, 0xa7, 0x8c, 0xf1, 0xdc, 0x12, 0x75, 0xca, 0x1f,
293     0x3b, 0xbe, 0xe4, 0xd1, 0x42, 0x3d, 0xd4, 0x30, 0xa3, 0x3c, 0xb6, 0x26,
294     0x6f, 0xbf, 0x0e, 0xda, 0x46, 0x69, 0x07, 0x57, 0x27, 0xf2, 0x1d, 0x9b,
295     0xbc, 0x94, 0x43, 0x03, 0xf8, 0x11, 0xc7, 0xf6, 0x90, 0xef, 0x3e, 0xe7,
296     0x06, 0xc3, 0xd5, 0x2f, 0xc8, 0x66, 0x1e, 0xd7, 0x08, 0xe8, 0xea, 0xde,
297     0x80, 0x52, 0xee, 0xf7, 0x84, 0xaa, 0x72, 0xac, 0x35, 0x4d, 0x6a, 0x2a,
298     0x96, 0x1a, 0xd2, 0x71, 0x5a, 0x15, 0x49, 0x74, 0x4b, 0x9f, 0xd0, 0x5e,
299     0x04, 0x18, 0xa4, 0xec, 0xc2, 0xe0, 0x41, 0x6e, 0x0f, 0x51, 0xcb, 0xcc,
300     0x24, 0x91, 0xaf, 0x50, 0xa1, 0xf4, 0x70, 0x39, 0x99, 0x7c, 0x3a, 0x85,
301     0x23, 0xb8, 0xb4, 0x7a, 0xfc, 0x02, 0x36, 0x5b, 0x25, 0x55, 0x97, 0x31,
302     0x2d, 0x5d, 0xfa, 0x98, 0xe3, 0x8a, 0x92, 0xae, 0x05, 0xdf, 0x29, 0x10,
303     0x67, 0x6c, 0xba, 0xc9, 0xd3, 0x00, 0xe6, 0xcf, 0xe1, 0x9e, 0xa8, 0x2c,
304     0x63, 0x16, 0x01, 0x3f, 0x58, 0xe2, 0x89, 0xa9, 0x0d, 0x38, 0x34, 0x1b,
305     0xab, 0x33, 0xff, 0xb0, 0xbb, 0x48, 0x0c, 0x5f, 0xb9, 0xb1, 0xcd, 0x2e,
306     0xc5, 0xf3, 0xdb, 0x47, 0xe5, 0xa5, 0x9c, 0x77, 0x0a, 0xa6, 0x20, 0x68,
307     0xfe, 0x7f, 0xc1, 0xad,
308 };
309 
RC2_set_key(RC2_KEY * key,int len,const uint8_t * data,int bits)310 static void RC2_set_key(RC2_KEY *key, int len, const uint8_t *data, int bits) {
311   int i, j;
312   uint8_t *k;
313   uint16_t *ki;
314   unsigned int c, d;
315 
316   k = (uint8_t *)&key->data[0];
317   *k = 0; /* for if there is a zero length key */
318 
319   if (len > 128) {
320     len = 128;
321   }
322   if (bits <= 0) {
323     bits = 1024;
324   }
325   if (bits > 1024) {
326     bits = 1024;
327   }
328 
329   for (i = 0; i < len; i++) {
330     k[i] = data[i];
331   }
332 
333   /* expand table */
334   d = k[len - 1];
335   j = 0;
336   for (i = len; i < 128; i++, j++) {
337     d = key_table[(k[j] + d) & 0xff];
338     k[i] = d;
339   }
340 
341   /* hmm.... key reduction to 'bits' bits */
342 
343   j = (bits + 7) >> 3;
344   i = 128 - j;
345   c = (0xff >> (-bits & 0x07));
346 
347   d = key_table[k[i] & c];
348   k[i] = d;
349   while (i--) {
350     d = key_table[k[i + j] ^ d];
351     k[i] = d;
352   }
353 
354   /* copy from bytes into uint16_t's */
355   ki = &(key->data[63]);
356   for (i = 127; i >= 0; i -= 2) {
357     *(ki--) = ((k[i] << 8) | k[i - 1]) & 0xffff;
358   }
359 }
360 
361 typedef struct {
362   int key_bits; /* effective key bits */
363   RC2_KEY ks;   /* key schedule */
364 } EVP_RC2_KEY;
365 
rc2_init_key(EVP_CIPHER_CTX * ctx,const uint8_t * key,const uint8_t * iv,int enc)366 static int rc2_init_key(EVP_CIPHER_CTX *ctx, const uint8_t *key,
367                         const uint8_t *iv, int enc) {
368   EVP_RC2_KEY *rc2_key = (EVP_RC2_KEY *)ctx->cipher_data;
369   RC2_set_key(&rc2_key->ks, EVP_CIPHER_CTX_key_length(ctx), key,
370               rc2_key->key_bits);
371   return 1;
372 }
373 
rc2_cbc_cipher(EVP_CIPHER_CTX * ctx,uint8_t * out,const uint8_t * in,size_t inl)374 static int rc2_cbc_cipher(EVP_CIPHER_CTX *ctx, uint8_t *out, const uint8_t *in,
375                           size_t inl) {
376   EVP_RC2_KEY *key = (EVP_RC2_KEY *)ctx->cipher_data;
377   static const size_t kChunkSize = 0x10000;
378 
379   while (inl >= kChunkSize) {
380     RC2_cbc_encrypt(in, out, kChunkSize, &key->ks, ctx->iv, ctx->encrypt);
381     inl -= kChunkSize;
382     in += kChunkSize;
383     out += kChunkSize;
384   }
385   if (inl) {
386     RC2_cbc_encrypt(in, out, inl, &key->ks, ctx->iv, ctx->encrypt);
387   }
388   return 1;
389 }
390 
rc2_ctrl(EVP_CIPHER_CTX * ctx,int type,int arg,void * ptr)391 static int rc2_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg, void *ptr) {
392   EVP_RC2_KEY *key = (EVP_RC2_KEY *)ctx->cipher_data;
393 
394   switch (type) {
395     case EVP_CTRL_INIT:
396       key->key_bits = EVP_CIPHER_CTX_key_length(ctx) * 8;
397       return 1;
398     case EVP_CTRL_SET_RC2_KEY_BITS:
399       /* Should be overridden by later call to |EVP_CTRL_INIT|, but
400        * people call it, so it may as well work. */
401       key->key_bits = arg;
402       return 1;
403 
404     default:
405       return -1;
406   }
407 }
408 
409 static const EVP_CIPHER rc2_40_cbc = {
410     NID_rc2_40_cbc,
411     8 /* block size */,
412     5 /* 40 bit */,
413     8 /* iv len */,
414     sizeof(EVP_RC2_KEY),
415     EVP_CIPH_CBC_MODE | EVP_CIPH_VARIABLE_LENGTH | EVP_CIPH_CTRL_INIT,
416     NULL /* app_data */,
417     rc2_init_key,
418     rc2_cbc_cipher,
419     NULL,
420     rc2_ctrl,
421 };
422 
EVP_rc2_40_cbc(void)423 const EVP_CIPHER *EVP_rc2_40_cbc(void) {
424   return &rc2_40_cbc;
425 }
426 
427 static const EVP_CIPHER rc2_cbc = {
428     NID_rc2_cbc,
429     8 /* block size */,
430     16 /* 128 bit */,
431     8 /* iv len */,
432     sizeof(EVP_RC2_KEY),
433     EVP_CIPH_CBC_MODE | EVP_CIPH_VARIABLE_LENGTH | EVP_CIPH_CTRL_INIT,
434     NULL /* app_data */,
435     rc2_init_key,
436     rc2_cbc_cipher,
437     NULL,
438     rc2_ctrl,
439 };
440 
EVP_rc2_cbc(void)441 const EVP_CIPHER *EVP_rc2_cbc(void) {
442   return &rc2_cbc;
443 }
444