dcf6c18a98748768f69bc1b7905e23e708429441
[openwrt/openwrt.git] / package / kernel / lantiq / ltq-deu / src / ifxmips_des.c
1 /******************************************************************************
2 **
3 ** FILE NAME : ifxmips_des.c
4 ** PROJECT : IFX UEIP
5 ** MODULES : DEU Module
6 **
7 ** DATE : September 8, 2009
8 ** AUTHOR : Mohammad Firdaus
9 ** DESCRIPTION : Data Encryption Unit Driver for DES Algorithm
10 ** COPYRIGHT : Copyright (c) 2009
11 ** Infineon Technologies AG
12 ** Am Campeon 1-12, 85579 Neubiberg, Germany
13 **
14 ** This program is free software; you can redistribute it and/or modify
15 ** it under the terms of the GNU General Public License as published by
16 ** the Free Software Foundation; either version 2 of the License, or
17 ** (at your option) any later version.
18 **
19 ** HISTORY
20 ** $Date $Author $Comment
21 ** 08 Sept 2009 Mohammad Firdaus Initial UEIP release
22 *******************************************************************************/
23
24 /*!
25 \defgroup IFX_DEU IFX_DEU_DRIVERS
26 \ingroup API
27 \brief ifx deu driver
28 */
29
30 /*!
31 \file ifxmips_des.c
32 \ingroup IFX_DEU
33 \brief DES encryption DEU driver file
34 */
35
36 /*!
37 \defgroup IFX_DES_FUNCTIONS IFX_DES_FUNCTIONS
38 \ingroup IFX_DEU
39 \brief IFX DES Encryption functions
40 */
41
42 /* Project Header Files */
43 #include <linux/version.h>
44 #include <linux/module.h>
45 #include <linux/init.h>
46 #include <linux/types.h>
47 #include <linux/errno.h>
48 #include <linux/crypto.h>
49 #include <linux/interrupt.h>
50 #include <linux/delay.h>
51 #include <asm/byteorder.h>
52 #include <crypto/algapi.h>
53 #include "ifxmips_deu.h"
54
55 #if defined(CONFIG_DANUBE)
56 #include "ifxmips_deu_danube.h"
57 extern int ifx_danube_pre_1_4;
58 #elif defined(CONFIG_AR9)
59 #include "ifxmips_deu_ar9.h"
60 #elif defined(CONFIG_VR9) || defined(CONFIG_AR10)
61 #include "ifxmips_deu_vr9.h"
62 #else
63 #error "Unkown platform"
64 #endif
65
66 /* DMA specific header and variables */
67
68 #if 0
69 #define CRTCL_SECT_INIT
70 #define CRTCL_SECT_START
71 #define CRTCL_SECT_END
72 #else
73 spinlock_t des_lock;
74 #define CRTCL_SECT_INIT spin_lock_init(&des_lock)
75 #define CRTCL_SECT_START spin_lock_irqsave(&des_lock, flag)
76 #define CRTCL_SECT_END spin_unlock_irqrestore(&des_lock, flag)
77 #endif
78
79 /* Preprocessor declerations */
80 #ifdef CRYPTO_DEBUG
81 extern char debug_level;
82 #define DPRINTF(level, format, args...) if (level < debug_level) printk(KERN_INFO "[%s %s %d]: " format, __FILE__, __func__, __LINE__, ##args);
83 #else
84 #define DPRINTF(level, format, args...)
85 #endif
86 #define DES_3DES_START IFX_DES_CON
87 #define DES_KEY_SIZE 8
88 #define DES_EXPKEY_WORDS 32
89 #define DES_BLOCK_SIZE 8
90 #define DES3_EDE_KEY_SIZE (3 * DES_KEY_SIZE)
91 #define DES3_EDE_EXPKEY_WORDS (3 * DES_EXPKEY_WORDS)
92 #define DES3_EDE_BLOCK_SIZE DES_BLOCK_SIZE
93
94 /* Function Declaration to prevent warning messages */
95 void des_chip_init (void);
96 u32 endian_swap(u32 input);
97 u32 input_swap(u32 input);
98 int aes_memory_allocate(int value);
99 int des_memory_allocate(int value);
100 void memory_release(u32 *buffer);
101 u32* memory_alignment(const u8 *arg, u32 *buff_alloc, int in_out, int nbytes);
102 void aes_dma_memory_copy(u32 *outcopy, u32 *out_dma, u8 *out_arg, int nbytes);
103 void des_dma_memory_copy(u32 *outcopy, u32 *out_dma, u8 *out_arg, int nbytes);
104
105 void ifx_deu_des (void *ctx_arg, u8 *out_arg, const u8 *in_arg,
106 u8 *iv_arg, u32 nbytes, int encdec, int mode);
107
108 struct des_ctx {
109 int controlr_M;
110 int key_length;
111 u8 iv[DES_BLOCK_SIZE];
112 u32 expkey[DES3_EDE_EXPKEY_WORDS];
113 };
114
115 extern int disable_multiblock;
116 extern int disable_deudma;
117
118
119 /*! \fn int des_setkey(struct crypto_tfm *tfm, const u8 *key, unsigned int keylen)
120 * \ingroup IFX_DES_FUNCTIONS
121 * \brief sets DES key
122 * \param tfm linux crypto algo transform
123 * \param key input key
124 * \param keylen key length
125 */
126 int des_setkey(struct crypto_tfm *tfm, const u8 *key,
127 unsigned int keylen)
128 {
129 struct des_ctx *dctx = crypto_tfm_ctx(tfm);
130
131 //printk("setkey in %s\n", __FILE__);
132
133 dctx->controlr_M = 0; // des
134 dctx->key_length = keylen;
135
136 memcpy ((u8 *) (dctx->expkey), key, keylen);
137
138 return 0;
139 }
140
141
142 /*! \fn void ifx_deu_des(void *ctx_arg, u8 *out_arg, const u8 *in_arg, u8 *iv_arg, u32 nbytes, int encdec, int mode)
143 * \ingroup IFX_DES_FUNCTIONS
144 * \brief main interface to DES hardware
145 * \param ctx_arg crypto algo context
146 * \param out_arg output bytestream
147 * \param in_arg input bytestream
148 * \param iv_arg initialization vector
149 * \param nbytes length of bytestream
150 * \param encdec 1 for encrypt; 0 for decrypt
151 * \param mode operation mode such as ebc, cbc
152 */
153
154 void ifx_deu_des (void *ctx_arg, u8 *out_arg, const u8 *in_arg,
155 u8 *iv_arg, u32 nbytes, int encdec, int mode)
156 {
157 volatile struct des_t *des = (struct des_t *) DES_3DES_START;
158 struct des_ctx *dctx = ctx_arg;
159 u32 *key = dctx->expkey;
160 unsigned long flag;
161
162 int i = 0;
163 int nblocks = 0;
164
165 CRTCL_SECT_START;
166
167 des->controlr.M = dctx->controlr_M;
168 if (dctx->controlr_M == 0) // des
169 {
170 des->K1HR = DEU_ENDIAN_SWAP(*((u32 *) key + 0));
171 des->K1LR = DEU_ENDIAN_SWAP(*((u32 *) key + 1));
172
173 }
174 else {
175 /* Hardware Section */
176 switch (dctx->key_length) {
177 case 24:
178 des->K3HR = DEU_ENDIAN_SWAP(*((u32 *) key + 4));
179 des->K3LR = DEU_ENDIAN_SWAP(*((u32 *) key + 5));
180 /* no break; */
181
182 case 16:
183 des->K2HR = DEU_ENDIAN_SWAP(*((u32 *) key + 2));
184 des->K2LR = DEU_ENDIAN_SWAP(*((u32 *) key + 3));
185
186 /* no break; */
187 case 8:
188 des->K1HR = DEU_ENDIAN_SWAP(*((u32 *) key + 0));
189 des->K1LR = DEU_ENDIAN_SWAP(*((u32 *) key + 1));
190 break;
191
192 default:
193 CRTCL_SECT_END;
194 return;
195 }
196 }
197
198 des->controlr.E_D = !encdec; //encryption
199 des->controlr.O = mode; //0 ECB 1 CBC 2 OFB 3 CFB 4 CTR hexdump(prin,sizeof(*des));
200
201 if (mode > 0) {
202 des->IVHR = DEU_ENDIAN_SWAP(*(u32 *) iv_arg);
203 des->IVLR = DEU_ENDIAN_SWAP(*((u32 *) iv_arg + 1));
204 };
205
206 nblocks = nbytes / 4;
207
208 for (i = 0; i < nblocks; i += 2) {
209 /* wait for busy bit to clear */
210
211 /*--- Workaround ----------------------------------------------------
212 do a dummy read to the busy flag because it is not raised early
213 enough in CFB/OFB 3DES modes */
214 #ifdef CRYPTO_DEBUG
215 printk ("ihr: %x\n", (*((u32 *) in_arg + i)));
216 printk ("ilr: %x\n", (*((u32 *) in_arg + 1 + i)));
217 #endif
218 des->IHR = INPUT_ENDIAN_SWAP(*((u32 *) in_arg + i));
219 des->ILR = INPUT_ENDIAN_SWAP(*((u32 *) in_arg + 1 + i)); /* start crypto */
220
221 while (des->controlr.BUS) {
222 // this will not take long
223 }
224
225 *((u32 *) out_arg + 0 + i) = des->OHR;
226 *((u32 *) out_arg + 1 + i) = des->OLR;
227
228 }
229
230
231
232 if (mode > 0) {
233 *(u32 *) iv_arg = DEU_ENDIAN_SWAP(des->IVHR);
234 *((u32 *) iv_arg + 1) = DEU_ENDIAN_SWAP(des->IVLR);
235 };
236
237 CRTCL_SECT_END;
238 }
239
240 //definitions from linux/include/crypto.h:
241 //#define CRYPTO_TFM_MODE_ECB 0x00000001
242 //#define CRYPTO_TFM_MODE_CBC 0x00000002
243 //#define CRYPTO_TFM_MODE_CFB 0x00000004
244 //#define CRYPTO_TFM_MODE_CTR 0x00000008
245 //#define CRYPTO_TFM_MODE_OFB 0x00000010 // not even defined
246 //but hardware definition: 0 ECB 1 CBC 2 OFB 3 CFB 4 CTR
247
248 /*! \fn void ifx_deu_des(void *ctx_arg, u8 *out_arg, const u8 *in_arg, u8 *iv_arg, u32 nbytes, int encdec, int mode)
249 * \ingroup IFX_DES_FUNCTIONS
250 * \brief main interface to DES hardware
251 * \param ctx_arg crypto algo context
252 * \param out_arg output bytestream
253 * \param in_arg input bytestream
254 * \param iv_arg initialization vector
255 * \param nbytes length of bytestream
256 * \param encdec 1 for encrypt; 0 for decrypt
257 * \param mode operation mode such as ebc, cbc
258 */
259
260
261
262 /*! \fn void ifx_deu_des_ecb (void *ctx, uint8_t *dst, const uint8_t *src, uint8_t *iv, size_t nbytes, int encdec, int inplace)
263 * \ingroup IFX_DES_FUNCTIONS
264 * \brief sets DES hardware to ECB mode
265 * \param ctx crypto algo context
266 * \param dst output bytestream
267 * \param src input bytestream
268 * \param iv initialization vector
269 * \param nbytes length of bytestream
270 * \param encdec 1 for encrypt; 0 for decrypt
271 * \param inplace not used
272 */
273
274 void ifx_deu_des_ecb (void *ctx, uint8_t *dst, const uint8_t *src,
275 uint8_t *iv, size_t nbytes, int encdec, int inplace)
276 {
277 ifx_deu_des (ctx, dst, src, NULL, nbytes, encdec, 0);
278 }
279
280 /*! \fn void ifx_deu_des_cbc (void *ctx, uint8_t *dst, const uint8_t *src, uint8_t *iv, size_t nbytes, int encdec, int inplace)
281 * \ingroup IFX_DES_FUNCTIONS
282 * \brief sets DES hardware to CBC mode
283 * \param ctx crypto algo context
284 * \param dst output bytestream
285 * \param src input bytestream
286 * \param iv initialization vector
287 * \param nbytes length of bytestream
288 * \param encdec 1 for encrypt; 0 for decrypt
289 * \param inplace not used
290 */
291 void ifx_deu_des_cbc (void *ctx, uint8_t *dst, const uint8_t *src,
292 uint8_t *iv, size_t nbytes, int encdec, int inplace)
293 {
294 ifx_deu_des (ctx, dst, src, iv, nbytes, encdec, 1);
295 }
296
297 /*! \fn void ifx_deu_des_ofb (void *ctx, uint8_t *dst, const uint8_t *src, uint8_t *iv, size_t nbytes, int encdec, int inplace)
298 * \ingroup IFX_DES_FUNCTIONS
299 * \brief sets DES hardware to OFB mode
300 * \param ctx crypto algo context
301 * \param dst output bytestream
302 * \param src input bytestream
303 * \param iv initialization vector
304 * \param nbytes length of bytestream
305 * \param encdec 1 for encrypt; 0 for decrypt
306 * \param inplace not used
307 */
308 void ifx_deu_des_ofb (void *ctx, uint8_t *dst, const uint8_t *src,
309 uint8_t *iv, size_t nbytes, int encdec, int inplace)
310 {
311 ifx_deu_des (ctx, dst, src, iv, nbytes, encdec, 2);
312 }
313
314 /*! \fn void ifx_deu_des_cfb (void *ctx, uint8_t *dst, const uint8_t *src, uint8_t *iv, size_t nbytes, int encdec, int inplace)
315 \ingroup IFX_DES_FUNCTIONS
316 \brief sets DES hardware to CFB mode
317 \param ctx crypto algo context
318 \param dst output bytestream
319 \param src input bytestream
320 \param iv initialization vector
321 \param nbytes length of bytestream
322 \param encdec 1 for encrypt; 0 for decrypt
323 \param inplace not used
324 */
325 void ifx_deu_des_cfb (void *ctx, uint8_t *dst, const uint8_t *src,
326 uint8_t *iv, size_t nbytes, int encdec, int inplace)
327 {
328 ifx_deu_des (ctx, dst, src, iv, nbytes, encdec, 3);
329 }
330
331 /*! \fn void ifx_deu_des_ctr (void *ctx, uint8_t *dst, const uint8_t *src, uint8_t *iv, size_t nbytes, int encdec, int inplace)
332 * \ingroup IFX_DES_FUNCTIONS
333 * \brief sets DES hardware to CTR mode
334 * \param ctx crypto algo context
335 * \param dst output bytestream
336 * \param src input bytestream
337 * \param iv initialization vector
338 * \param nbytes length of bytestream
339 * \param encdec 1 for encrypt; 0 for decrypt
340 * \param inplace not used
341 */
342 void ifx_deu_des_ctr (void *ctx, uint8_t *dst, const uint8_t *src,
343 uint8_t *iv, size_t nbytes, int encdec, int inplace)
344 {
345 ifx_deu_des (ctx, dst, src, iv, nbytes, encdec, 4);
346 }
347
348 /*! \fn void des_encrypt (struct crypto_tfm *tfm, uint8_t *out, const uint8_t *in)
349 * \ingroup IFX_DES_FUNCTIONS
350 * \brief encrypt DES_BLOCK_SIZE of data
351 * \param tfm linux crypto algo transform
352 * \param out output bytestream
353 * \param in input bytestream
354 */
355 void des_encrypt (struct crypto_tfm *tfm, uint8_t * out, const uint8_t * in)
356 {
357 struct des_ctx *ctx = crypto_tfm_ctx(tfm);
358 ifx_deu_des (ctx, out, in, NULL, DES_BLOCK_SIZE,
359 CRYPTO_DIR_ENCRYPT, 0);
360
361 }
362
363 /*! \fn void des_decrypt (struct crypto_tfm *tfm, uint8_t *out, const uint8_t *in)
364 * \ingroup IFX_DES_FUNCTIONS
365 * \brief encrypt DES_BLOCK_SIZE of data
366 * \param tfm linux crypto algo transform
367 * \param out output bytestream
368 * \param in input bytestream
369 */
370 void des_decrypt (struct crypto_tfm *tfm, uint8_t * out, const uint8_t * in)
371 {
372 struct des_ctx *ctx = crypto_tfm_ctx(tfm);
373 ifx_deu_des (ctx, out, in, NULL, DES_BLOCK_SIZE,
374 CRYPTO_DIR_DECRYPT, 0);
375 }
376
377 /*
378 * \brief RFC2451:
379 *
380 * For DES-EDE3, there is no known need to reject weak or
381 * complementation keys. Any weakness is obviated by the use of
382 * multiple keys.
383 *
384 * However, if the first two or last two independent 64-bit keys are
385 * equal (k1 == k2 or k2 == k3), then the DES3 operation is simply the
386 * same as DES. Implementers MUST reject keys that exhibit this
387 * property.
388 *
389 */
390
391 /*! \fn int des3_ede_setkey(struct crypto_tfm *tfm, const u8 *key, unsigned int keylen)
392 * \ingroup IFX_DES_FUNCTIONS
393 * \brief sets 3DES key
394 * \param tfm linux crypto algo transform
395 * \param key input key
396 * \param keylen key length
397 */
398 int des3_ede_setkey(struct crypto_tfm *tfm, const u8 *key,
399 unsigned int keylen)
400 {
401 struct des_ctx *dctx = crypto_tfm_ctx(tfm);
402
403 //printk("setkey in %s\n", __FILE__);
404
405 dctx->controlr_M = keylen / 8 + 1; // 3DES EDE1 / EDE2 / EDE3 Mode
406 dctx->key_length = keylen;
407
408 memcpy ((u8 *) (dctx->expkey), key, keylen);
409
410 return 0;
411 }
412
413 /*
414 * \brief DES function mappings
415 */
416 struct crypto_alg ifxdeu_des_alg = {
417 .cra_name = "des",
418 .cra_driver_name = "ifxdeu-des",
419 .cra_flags = CRYPTO_ALG_TYPE_CIPHER,
420 .cra_blocksize = DES_BLOCK_SIZE,
421 .cra_ctxsize = sizeof(struct des_ctx),
422 .cra_module = THIS_MODULE,
423 .cra_alignmask = 3,
424 .cra_list = LIST_HEAD_INIT(ifxdeu_des_alg.cra_list),
425 .cra_u = { .cipher = {
426 .cia_min_keysize = DES_KEY_SIZE,
427 .cia_max_keysize = DES_KEY_SIZE,
428 .cia_setkey = des_setkey,
429 .cia_encrypt = des_encrypt,
430 .cia_decrypt = des_decrypt } }
431 };
432
433 /*
434 * \brief DES function mappings
435 */
436 struct crypto_alg ifxdeu_des3_ede_alg = {
437 .cra_name = "des3_ede",
438 .cra_driver_name = "ifxdeu-des3_ede",
439 .cra_flags = CRYPTO_ALG_TYPE_CIPHER,
440 .cra_blocksize = DES_BLOCK_SIZE,
441 .cra_ctxsize = sizeof(struct des_ctx),
442 .cra_module = THIS_MODULE,
443 .cra_alignmask = 3,
444 .cra_list = LIST_HEAD_INIT(ifxdeu_des3_ede_alg.cra_list),
445 .cra_u = { .cipher = {
446 .cia_min_keysize = DES_KEY_SIZE,
447 .cia_max_keysize = DES_KEY_SIZE,
448 .cia_setkey = des3_ede_setkey,
449 .cia_encrypt = des_encrypt,
450 .cia_decrypt = des_decrypt } }
451 };
452
453 /*! \fn int ecb_des_encrypt(struct blkcipher_desc *desc, struct scatterlist *dst, struct scatterlist *src, unsigned int nbytes)
454 * \ingroup IFX_DES_FUNCTIONS
455 * \brief ECB DES encrypt using linux crypto blkcipher
456 * \param desc blkcipher descriptor
457 * \param dst output scatterlist
458 * \param src input scatterlist
459 * \param nbytes data size in bytes
460 */
461 int ecb_des_encrypt(struct blkcipher_desc *desc,
462 struct scatterlist *dst, struct scatterlist *src,
463 unsigned int nbytes)
464 {
465 struct des_ctx *ctx = crypto_blkcipher_ctx(desc->tfm);
466 struct blkcipher_walk walk;
467 int err;
468
469 blkcipher_walk_init(&walk, dst, src, nbytes);
470 err = blkcipher_walk_virt(desc, &walk);
471
472 while ((nbytes = walk.nbytes)) {
473 nbytes -= (nbytes % DES_BLOCK_SIZE);
474 ifx_deu_des_ecb(ctx, walk.dst.virt.addr, walk.src.virt.addr,
475 NULL, nbytes, CRYPTO_DIR_ENCRYPT, 0);
476 nbytes &= DES_BLOCK_SIZE - 1;
477 err = blkcipher_walk_done(desc, &walk, nbytes);
478 }
479
480 return err;
481 }
482
483 /*! \fn int ecb_des_decrypt(struct blkcipher_desc *desc, struct scatterlist *dst, struct scatterlist *src, unsigned int nbytes)
484 * \ingroup IFX_DES_FUNCTIONS
485 * \brief ECB DES decrypt using linux crypto blkcipher
486 * \param desc blkcipher descriptor
487 * \param dst output scatterlist
488 * \param src input scatterlist
489 * \param nbytes data size in bytes
490 * \return err
491 */
492 int ecb_des_decrypt(struct blkcipher_desc *desc,
493 struct scatterlist *dst, struct scatterlist *src,
494 unsigned int nbytes)
495 {
496 struct des_ctx *ctx = crypto_blkcipher_ctx(desc->tfm);
497 struct blkcipher_walk walk;
498 int err;
499
500 DPRINTF(1, "\n");
501 blkcipher_walk_init(&walk, dst, src, nbytes);
502 err = blkcipher_walk_virt(desc, &walk);
503
504 while ((nbytes = walk.nbytes)) {
505 nbytes -= (nbytes % DES_BLOCK_SIZE);
506 ifx_deu_des_ecb(ctx, walk.dst.virt.addr, walk.src.virt.addr,
507 NULL, nbytes, CRYPTO_DIR_DECRYPT, 0);
508 nbytes &= DES_BLOCK_SIZE - 1;
509 err = blkcipher_walk_done(desc, &walk, nbytes);
510 }
511
512 return err;
513 }
514
515 /*
516 * \brief DES function mappings
517 */
518 struct crypto_alg ifxdeu_ecb_des_alg = {
519 .cra_name = "ecb(des)",
520 .cra_driver_name = "ifxdeu-ecb(des)",
521 .cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER,
522 .cra_blocksize = DES_BLOCK_SIZE,
523 .cra_ctxsize = sizeof(struct des_ctx),
524 .cra_type = &crypto_blkcipher_type,
525 .cra_module = THIS_MODULE,
526 .cra_list = LIST_HEAD_INIT(ifxdeu_ecb_des_alg.cra_list),
527 .cra_u = {
528 .blkcipher = {
529 .min_keysize = DES_KEY_SIZE,
530 .max_keysize = DES_KEY_SIZE,
531 .setkey = des_setkey,
532 .encrypt = ecb_des_encrypt,
533 .decrypt = ecb_des_decrypt,
534 }
535 }
536 };
537
538 /*
539 * \brief DES function mappings
540 */
541 struct crypto_alg ifxdeu_ecb_des3_ede_alg = {
542 .cra_name = "ecb(des3_ede)",
543 .cra_driver_name = "ifxdeu-ecb(des3_ede)",
544 .cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER,
545 .cra_blocksize = DES3_EDE_BLOCK_SIZE,
546 .cra_ctxsize = sizeof(struct des_ctx),
547 .cra_type = &crypto_blkcipher_type,
548 .cra_module = THIS_MODULE,
549 .cra_list = LIST_HEAD_INIT(ifxdeu_ecb_des3_ede_alg.cra_list),
550 .cra_u = {
551 .blkcipher = {
552 .min_keysize = DES3_EDE_KEY_SIZE,
553 .max_keysize = DES3_EDE_KEY_SIZE,
554 .setkey = des3_ede_setkey,
555 .encrypt = ecb_des_encrypt,
556 .decrypt = ecb_des_decrypt,
557 }
558 }
559 };
560
561 /*! \fn int cbc_des_encrypt(struct blkcipher_desc *desc, struct scatterlist *dst, struct scatterlist *src, unsigned int nbytes)
562 * \ingroup IFX_DES_FUNCTIONS
563 * \brief CBC DES encrypt using linux crypto blkcipher
564 * \param desc blkcipher descriptor
565 * \param dst output scatterlist
566 * \param src input scatterlist
567 * \param nbytes data size in bytes
568 * \return err
569 */
570 int cbc_des_encrypt(struct blkcipher_desc *desc,
571 struct scatterlist *dst, struct scatterlist *src,
572 unsigned int nbytes)
573 {
574 struct des_ctx *ctx = crypto_blkcipher_ctx(desc->tfm);
575 struct blkcipher_walk walk;
576 int err;
577
578 DPRINTF(1, "\n");
579 blkcipher_walk_init(&walk, dst, src, nbytes);
580 err = blkcipher_walk_virt(desc, &walk);
581
582 while ((nbytes = walk.nbytes)) {
583 u8 *iv = walk.iv;
584 nbytes -= (nbytes % DES_BLOCK_SIZE);
585 ifx_deu_des_cbc(ctx, walk.dst.virt.addr, walk.src.virt.addr,
586 iv, nbytes, CRYPTO_DIR_ENCRYPT, 0);
587 nbytes &= DES_BLOCK_SIZE - 1;
588 err = blkcipher_walk_done(desc, &walk, nbytes);
589 }
590
591 return err;
592 }
593
594 /*! \fn int cbc_des_decrypt(struct blkcipher_desc *desc, struct scatterlist *dst, struct scatterlist *src, unsigned int nbytes)
595 * \ingroup IFX_DES_FUNCTIONS
596 * \brief CBC DES decrypt using linux crypto blkcipher
597 * \param desc blkcipher descriptor
598 * \param dst output scatterlist
599 * \param src input scatterlist
600 * \param nbytes data size in bytes
601 * \return err
602 */
603 int cbc_des_decrypt(struct blkcipher_desc *desc,
604 struct scatterlist *dst, struct scatterlist *src,
605 unsigned int nbytes)
606 {
607 struct des_ctx *ctx = crypto_blkcipher_ctx(desc->tfm);
608 struct blkcipher_walk walk;
609 int err;
610
611 DPRINTF(1, "\n");
612 blkcipher_walk_init(&walk, dst, src, nbytes);
613 err = blkcipher_walk_virt(desc, &walk);
614
615 while ((nbytes = walk.nbytes)) {
616 u8 *iv = walk.iv;
617 nbytes -= (nbytes % DES_BLOCK_SIZE);
618 ifx_deu_des_cbc(ctx, walk.dst.virt.addr, walk.src.virt.addr,
619 iv, nbytes, CRYPTO_DIR_DECRYPT, 0);
620 nbytes &= DES_BLOCK_SIZE - 1;
621 err = blkcipher_walk_done(desc, &walk, nbytes);
622 }
623
624 return err;
625 }
626
627 /*
628 * \brief DES function mappings
629 */
630 struct crypto_alg ifxdeu_cbc_des_alg = {
631 .cra_name = "cbc(des)",
632 .cra_driver_name = "ifxdeu-cbc(des)",
633 .cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER,
634 .cra_blocksize = DES_BLOCK_SIZE,
635 .cra_ctxsize = sizeof(struct des_ctx),
636 .cra_type = &crypto_blkcipher_type,
637 .cra_module = THIS_MODULE,
638 .cra_list = LIST_HEAD_INIT(ifxdeu_cbc_des_alg.cra_list),
639 .cra_u = {
640 .blkcipher = {
641 .min_keysize = DES_KEY_SIZE,
642 .max_keysize = DES_KEY_SIZE,
643 .ivsize = DES_BLOCK_SIZE,
644 .setkey = des_setkey,
645 .encrypt = cbc_des_encrypt,
646 .decrypt = cbc_des_decrypt,
647 }
648 }
649 };
650
651 /*
652 * \brief DES function mappings
653 */
654 struct crypto_alg ifxdeu_cbc_des3_ede_alg = {
655 .cra_name = "cbc(des3_ede)",
656 .cra_driver_name = "ifxdeu-cbc(des3_ede)",
657 .cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER,
658 .cra_blocksize = DES3_EDE_BLOCK_SIZE,
659 .cra_ctxsize = sizeof(struct des_ctx),
660 .cra_type = &crypto_blkcipher_type,
661 .cra_module = THIS_MODULE,
662 .cra_list = LIST_HEAD_INIT(ifxdeu_cbc_des3_ede_alg.cra_list),
663 .cra_u = {
664 .blkcipher = {
665 .min_keysize = DES3_EDE_KEY_SIZE,
666 .max_keysize = DES3_EDE_KEY_SIZE,
667 .ivsize = DES_BLOCK_SIZE,
668 .setkey = des3_ede_setkey,
669 .encrypt = cbc_des_encrypt,
670 .decrypt = cbc_des_decrypt,
671 }
672 }
673 };
674
675 /*! \fn int __init ifxdeu_init_des (void)
676 * \ingroup IFX_DES_FUNCTIONS
677 * \brief initialize des driver
678 */
679 int __init ifxdeu_init_des (void)
680 {
681 int ret = -ENOSYS;
682
683
684 #if (LINUX_VERSION_CODE < KERNEL_VERSION(2,6,20))
685 if (!disable_multiblock) {
686 ifxdeu_des_alg.cra_u.cipher.cia_max_nbytes = DES_BLOCK_SIZE; //(size_t)-1;
687 ifxdeu_des_alg.cra_u.cipher.cia_req_align = 16;
688 ifxdeu_des_alg.cra_u.cipher.cia_ecb = ifx_deu_des_ecb;
689 ifxdeu_des_alg.cra_u.cipher.cia_cbc = ifx_deu_des_cbc;
690 ifxdeu_des_alg.cra_u.cipher.cia_cfb = ifx_deu_des_cfb;
691 ifxdeu_des_alg.cra_u.cipher.cia_ofb = ifx_deu_des_ofb;
692 }
693 #endif
694
695 ret = crypto_register_alg(&ifxdeu_des_alg);
696 if (ret < 0)
697 goto des_err;
698
699 ret = crypto_register_alg(&ifxdeu_ecb_des_alg);
700 if (ret < 0)
701 goto ecb_des_err;
702
703 ret = crypto_register_alg(&ifxdeu_cbc_des_alg);
704 if (ret < 0)
705 goto cbc_des_err;
706
707 ret = crypto_register_alg(&ifxdeu_des3_ede_alg);
708 if (ret < 0)
709 goto des3_ede_err;
710
711 ret = crypto_register_alg(&ifxdeu_ecb_des3_ede_alg);
712 if (ret < 0)
713 goto ecb_des3_ede_err;
714
715 ret = crypto_register_alg(&ifxdeu_cbc_des3_ede_alg);
716 if (ret < 0)
717 goto cbc_des3_ede_err;
718
719 des_chip_init();
720 CRTCL_SECT_INIT;
721
722
723
724 printk (KERN_NOTICE "IFX DEU DES initialized%s%s.\n", disable_multiblock ? "" : " (multiblock)", disable_deudma ? "" : " (DMA)");
725 return ret;
726
727 des_err:
728 crypto_unregister_alg(&ifxdeu_des_alg);
729 printk(KERN_ERR "IFX des initialization failed!\n");
730 return ret;
731 ecb_des_err:
732 crypto_unregister_alg(&ifxdeu_ecb_des_alg);
733 printk (KERN_ERR "IFX ecb_des initialization failed!\n");
734 return ret;
735 cbc_des_err:
736 crypto_unregister_alg(&ifxdeu_cbc_des_alg);
737 printk (KERN_ERR "IFX cbc_des initialization failed!\n");
738 return ret;
739 des3_ede_err:
740 crypto_unregister_alg(&ifxdeu_des3_ede_alg);
741 printk(KERN_ERR "IFX des3_ede initialization failed!\n");
742 return ret;
743 ecb_des3_ede_err:
744 crypto_unregister_alg(&ifxdeu_ecb_des3_ede_alg);
745 printk (KERN_ERR "IFX ecb_des3_ede initialization failed!\n");
746 return ret;
747 cbc_des3_ede_err:
748 crypto_unregister_alg(&ifxdeu_cbc_des3_ede_alg);
749 printk (KERN_ERR "IFX cbc_des3_ede initialization failed!\n");
750 return ret;
751
752 }
753
754 /*! \fn void __exit ifxdeu_fini_des (void)
755 * \ingroup IFX_DES_FUNCTIONS
756 * \brief unregister des driver
757 */
758 void __exit ifxdeu_fini_des (void)
759 {
760 crypto_unregister_alg (&ifxdeu_des_alg);
761 crypto_unregister_alg (&ifxdeu_ecb_des_alg);
762 crypto_unregister_alg (&ifxdeu_cbc_des_alg);
763 crypto_unregister_alg (&ifxdeu_des3_ede_alg);
764 crypto_unregister_alg (&ifxdeu_ecb_des3_ede_alg);
765 crypto_unregister_alg (&ifxdeu_cbc_des3_ede_alg);
766
767 }
768