1 /*******************************************************************************
2 Copyright (C) Marvell International Ltd. and its affiliates
4 This software file (the "File") is owned and distributed by Marvell
5 International Ltd. and/or its affiliates ("Marvell") under the following
6 alternative licensing terms. Once you have made an election to distribute the
7 File under one of the following license alternatives, please (i) delete this
8 introductory statement regarding license alternatives, (ii) delete the two
9 license alternatives that you have not elected to use and (iii) preserve the
10 Marvell copyright notice above.
13 ********************************************************************************
14 Marvell GPL License Option
16 If you received this File from Marvell, you may opt to use, redistribute and/or
17 modify this File in accordance with the terms and conditions of the General
18 Public License Version 2, June 1991 (the "GPL License"), a copy of which is
19 available along with the File in the license.txt file or by writing to the Free
20 Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 or
21 on the worldwide web at http://www.gnu.org/licenses/gpl.txt.
23 THE FILE IS DISTRIBUTED AS-IS, WITHOUT WARRANTY OF ANY KIND, AND THE IMPLIED
24 WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE ARE EXPRESSLY
25 DISCLAIMED. The GPL License provides additional details about this warranty
27 *******************************************************************************/
29 #include <linux/version.h>
30 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,38) && !defined(AUTOCONF_INCLUDED)
31 #include <linux/config.h>
33 #include <linux/module.h>
34 #include <linux/init.h>
35 #include <linux/list.h>
36 #include <linux/slab.h>
37 #include <linux/sched.h>
38 #include <linux/wait.h>
39 #include <linux/crypto.h>
41 #include <linux/skbuff.h>
42 #include <linux/random.h>
43 #include <linux/platform_device.h>
44 #include <asm/scatterlist.h>
45 #include <linux/spinlock.h>
46 #include "ctrlEnv/sys/mvSysCesa.h"
47 #include "cesa/mvCesa.h" /* moved here before cryptodev.h due to include dependencies */
48 #include <cryptodev.h>
50 #include <plat/mv_cesa.h>
51 #include <linux/mbus.h>
54 #include "cesa/mvMD5.h"
55 #include "cesa/mvSHA1.h"
57 #include "cesa/mvCesaRegs.h"
58 #include "cesa/AES/mvAes.h"
59 #include "cesa/mvLru.h"
64 module_param(debug
, int, 1);
65 MODULE_PARM_DESC(debug
, "Enable debug");
67 #define dprintk(a...) if (debug) { printk(a); } else
76 #define WINDOW_BASE(i) 0xA00 + (i << 3)
77 #define WINDOW_CTRL(i) 0xA04 + (i << 3)
79 /* interrupt handling */
80 #undef CESA_OCF_POLLING
81 #undef CESA_OCF_TASKLET
83 #if defined(CESA_OCF_POLLING) && defined(CESA_OCF_TASKLET)
84 #error "don't use both tasklet and polling mode"
87 extern int cesaReqResources
;
88 /* support for spliting action into 2 actions */
89 #define CESA_OCF_SPLIT
92 #define CESA_OCF_MAX_SES 128
93 #define CESA_Q_SIZE 64
97 struct cesa_ocf_data
{
101 #define auth_tn_decrypt encrypt_tn_auth
106 /* fragment workaround sessions */
107 short frag_wa_encrypt
;
108 short frag_wa_decrypt
;
112 /* CESA device data */
116 struct mv_cesa_platform_data
*plat_data
;
120 #define DIGEST_BUF_SIZE 32
121 struct cesa_ocf_process
{
122 MV_CESA_COMMAND cesa_cmd
;
123 MV_CESA_MBUF cesa_mbuf
;
124 MV_BUF_INFO cesa_bufs
[MV_CESA_MAX_MBUF_FRAGS
];
125 char digest
[DIGEST_BUF_SIZE
];
131 /* global variables */
132 static int32_t cesa_ocf_id
= -1;
133 static struct cesa_ocf_data
*cesa_ocf_sessions
[CESA_OCF_MAX_SES
];
134 static spinlock_t cesa_lock
;
135 static struct cesa_dev cesa_device
;
138 static int cesa_ocf_process (device_t
, struct cryptop
*, int);
139 static int cesa_ocf_newsession (device_t
, u_int32_t
*, struct cryptoini
*);
140 static int cesa_ocf_freesession (device_t
, u_int64_t
);
141 static void cesa_callback (unsigned long);
142 static irqreturn_t
cesa_interrupt_handler (int, void *);
143 #ifdef CESA_OCF_POLLING
144 static void cesa_interrupt_polling(void);
146 #ifdef CESA_OCF_TASKLET
147 static struct tasklet_struct cesa_ocf_tasklet
;
150 static struct timeval tt_start
;
151 static struct timeval tt_end
;
154 * dummy device structure
158 softc_device_decl sc_dev
;
161 static device_method_t mv_cesa_methods
= {
162 /* crypto device methods */
163 DEVMETHOD(cryptodev_newsession
, cesa_ocf_newsession
),
164 DEVMETHOD(cryptodev_freesession
,cesa_ocf_freesession
),
165 DEVMETHOD(cryptodev_process
, cesa_ocf_process
),
166 DEVMETHOD(cryptodev_kprocess
, NULL
),
171 /* Add debug Trace */
172 #undef CESA_OCF_TRACE_DEBUG
173 #ifdef CESA_OCF_TRACE_DEBUG
175 #define MV_CESA_USE_TIMER_ID 0
179 int type
; /* 0 - isrEmpty, 1 - cesaReadyGet, 2 - cesaAction */
185 MV_CESA_REQ
* pReqReady
;
186 MV_CESA_REQ
* pReqEmpty
;
187 MV_CESA_REQ
* pReqProcess
;
188 } MV_CESA_TEST_TRACE
;
190 #define MV_CESA_TEST_TRACE_SIZE 50
192 static int cesaTestTraceIdx
= 0;
193 static MV_CESA_TEST_TRACE cesaTestTrace
[MV_CESA_TEST_TRACE_SIZE
];
195 static void cesaTestTraceAdd(int type
)
197 cesaTestTrace
[cesaTestTraceIdx
].type
= type
;
198 cesaTestTrace
[cesaTestTraceIdx
].realCause
= MV_REG_READ(MV_CESA_ISR_CAUSE_REG
);
199 //cesaTestTrace[cesaTestTraceIdx].idmaCause = MV_REG_READ(IDMA_CAUSE_REG);
200 cesaTestTrace
[cesaTestTraceIdx
].resources
= cesaReqResources
;
201 cesaTestTrace
[cesaTestTraceIdx
].pReqReady
= pCesaReqReady
;
202 cesaTestTrace
[cesaTestTraceIdx
].pReqEmpty
= pCesaReqEmpty
;
203 cesaTestTrace
[cesaTestTraceIdx
].pReqProcess
= pCesaReqProcess
;
204 cesaTestTrace
[cesaTestTraceIdx
].timeStamp
= mvCntmrRead(MV_CESA_USE_TIMER_ID
);
206 if(cesaTestTraceIdx
== MV_CESA_TEST_TRACE_SIZE
)
207 cesaTestTraceIdx
= 0;
210 #else /* CESA_OCF_TRACE_DEBUG */
212 #define cesaTestTraceAdd(x)
214 #endif /* CESA_OCF_TRACE_DEBUG */
217 get_usec(unsigned int start
)
220 do_gettimeofday (&tt_start
);
224 do_gettimeofday (&tt_end
);
225 tt_end
.tv_sec
-= tt_start
.tv_sec
;
226 tt_end
.tv_usec
-= tt_start
.tv_usec
;
227 if (tt_end
.tv_usec
< 0) {
228 tt_end
.tv_usec
+= 1000 * 1000;
232 printk("time taken is %d\n", (unsigned int)(tt_end
.tv_usec
+ tt_end
.tv_sec
* 1000000));
233 return (tt_end
.tv_usec
+ tt_end
.tv_sec
* 1000000);
238 * check that the crp action match the current session
241 ocf_check_action(struct cryptop
*crp
, struct cesa_ocf_data
*cesa_ocf_cur_ses
) {
243 int encrypt
= 0, decrypt
= 0, auth
= 0;
244 struct cryptodesc
*crd
;
246 /* Go through crypto descriptors, processing as we go */
247 for (crd
= crp
->crp_desc
; crd
; crd
= crd
->crd_next
, count
++) {
249 printk("%s,%d: session mode is not supported.\n", __FILE__
, __LINE__
);
253 /* Encryption /Decryption */
254 if(crd
->crd_alg
== cesa_ocf_cur_ses
->cipher_alg
) {
255 /* check that the action is compatible with session */
256 if(encrypt
|| decrypt
) {
257 printk("%s,%d: session mode is not supported.\n", __FILE__
, __LINE__
);
261 if(crd
->crd_flags
& CRD_F_ENCRYPT
) { /* encrypt */
262 if( (count
== 2) && (cesa_ocf_cur_ses
->encrypt_tn_auth
) ) {
263 printk("%s,%d: sequence isn't supported by this session.\n", __FILE__
, __LINE__
);
269 if( (count
== 2) && !(cesa_ocf_cur_ses
->auth_tn_decrypt
) ) {
270 printk("%s,%d: sequence isn't supported by this session.\n", __FILE__
, __LINE__
);
278 else if(crd
->crd_alg
== cesa_ocf_cur_ses
->auth_alg
) {
279 /* check that the action is compatible with session */
281 printk("%s,%d: session mode is not supported.\n", __FILE__
, __LINE__
);
284 if( (count
== 2) && (decrypt
) && (cesa_ocf_cur_ses
->auth_tn_decrypt
)) {
285 printk("%s,%d: sequence isn't supported by this session.\n", __FILE__
, __LINE__
);
288 if( (count
== 2) && (encrypt
) && !(cesa_ocf_cur_ses
->encrypt_tn_auth
)) {
289 printk("%s,%d: sequence isn't supported by this session.\n", __FILE__
, __LINE__
);
295 printk("%s,%d: Alg isn't supported by this session.\n", __FILE__
, __LINE__
);
308 cesa_ocf_process(device_t dev
, struct cryptop
*crp
, int hint
)
310 struct cesa_ocf_process
*cesa_ocf_cmd
= NULL
;
311 struct cesa_ocf_process
*cesa_ocf_cmd_wa
= NULL
;
312 MV_CESA_COMMAND
*cesa_cmd
;
313 struct cryptodesc
*crd
;
314 struct cesa_ocf_data
*cesa_ocf_cur_ses
;
315 int sid
= 0, temp_len
= 0, i
;
316 int encrypt
= 0, decrypt
= 0, auth
= 0;
318 struct sk_buff
*skb
= NULL
;
319 struct uio
*uiop
= NULL
;
321 MV_BUF_INFO
*p_buf_info
;
322 MV_CESA_MBUF
*p_mbuf_info
;
325 dprintk("%s()\n", __FUNCTION__
);
327 if( cesaReqResources
<= 1 ) {
328 dprintk("%s,%d: ERESTART\n", __FILE__
, __LINE__
);
335 printk("%s,%d: EINVAL\n", __FILE__
, __LINE__
);
339 if (crp
->crp_desc
== NULL
|| crp
->crp_buf
== NULL
) {
340 printk("%s,%d: EINVAL\n", __FILE__
, __LINE__
);
341 crp
->crp_etype
= EINVAL
;
345 sid
= crp
->crp_sid
& 0xffffffff;
346 if ((sid
>= CESA_OCF_MAX_SES
) || (cesa_ocf_sessions
[sid
] == NULL
)) {
347 crp
->crp_etype
= ENOENT
;
348 printk("%s,%d: ENOENT session %d \n", __FILE__
, __LINE__
, sid
);
353 sid
= crp
->crp_sid
& 0xffffffff;
355 cesa_ocf_cur_ses
= cesa_ocf_sessions
[sid
];
358 if(ocf_check_action(crp
, cesa_ocf_cur_ses
)){
363 /* malloc a new cesa process */
364 cesa_ocf_cmd
= kmalloc(sizeof(struct cesa_ocf_process
), GFP_ATOMIC
);
366 if (cesa_ocf_cmd
== NULL
) {
367 printk("%s,%d: ENOBUFS \n", __FILE__
, __LINE__
);
370 memset(cesa_ocf_cmd
, 0, sizeof(struct cesa_ocf_process
));
372 /* init cesa_process */
373 cesa_ocf_cmd
->crp
= crp
;
374 /* always call callback */
375 cesa_ocf_cmd
->need_cb
= 1;
377 /* init cesa_cmd for usage of the HALs */
378 cesa_cmd
= &cesa_ocf_cmd
->cesa_cmd
;
379 cesa_cmd
->pReqPrv
= (void *)cesa_ocf_cmd
;
380 cesa_cmd
->sessionId
= cesa_ocf_cur_ses
->sid_encrypt
; /* defualt use encrypt */
382 /* prepare src buffer */
383 /* we send the entire buffer to the HAL, even if only part of it should be encrypt/auth. */
384 /* if not using seesions for both encrypt and auth, then it will be wiser to to copy only */
385 /* from skip to crd_len. */
386 p_buf_info
= cesa_ocf_cmd
->cesa_bufs
;
387 p_mbuf_info
= &cesa_ocf_cmd
->cesa_mbuf
;
389 p_buf_info
+= 2; /* save 2 first buffers for IV and digest -
390 we won't append them to the end since, they
391 might be places in an unaligned addresses. */
393 p_mbuf_info
->pFrags
= p_buf_info
;
397 if (crp
->crp_flags
& CRYPTO_F_SKBUF
) {
399 dprintk("%s,%d: handle SKB.\n", __FILE__
, __LINE__
);
400 skb
= (struct sk_buff
*) crp
->crp_buf
;
402 if (skb_shinfo(skb
)->nr_frags
>= (MV_CESA_MAX_MBUF_FRAGS
- 1)) {
403 printk("%s,%d: %d nr_frags > MV_CESA_MAX_MBUF_FRAGS", __FILE__
, __LINE__
, skb_shinfo(skb
)->nr_frags
);
407 p_mbuf_info
->mbufSize
= skb
->len
;
409 /* first skb fragment */
410 p_buf_info
->bufSize
= skb_headlen(skb
);
411 p_buf_info
->bufVirtPtr
= skb
->data
;
414 /* now handle all other skb fragments */
415 for ( i
= 0; i
< skb_shinfo(skb
)->nr_frags
; i
++ ) {
416 skb_frag_t
*frag
= &skb_shinfo(skb
)->frags
[i
];
417 p_buf_info
->bufSize
= frag
->size
;
418 p_buf_info
->bufVirtPtr
= page_address(frag
->page
) + frag
->page_offset
;
421 p_mbuf_info
->numFrags
= skb_shinfo(skb
)->nr_frags
+ 1;
424 else if(crp
->crp_flags
& CRYPTO_F_IOV
) {
426 dprintk("%s,%d: handle UIO.\n", __FILE__
, __LINE__
);
427 uiop
= (struct uio
*) crp
->crp_buf
;
429 if (uiop
->uio_iovcnt
> (MV_CESA_MAX_MBUF_FRAGS
- 1)) {
430 printk("%s,%d: %d uio_iovcnt > MV_CESA_MAX_MBUF_FRAGS \n", __FILE__
, __LINE__
, uiop
->uio_iovcnt
);
434 p_mbuf_info
->mbufSize
= crp
->crp_ilen
;
435 p_mbuf_info
->numFrags
= uiop
->uio_iovcnt
;
436 for(i
= 0; i
< uiop
->uio_iovcnt
; i
++) {
437 p_buf_info
->bufVirtPtr
= uiop
->uio_iov
[i
].iov_base
;
438 p_buf_info
->bufSize
= uiop
->uio_iov
[i
].iov_len
;
439 temp_len
+= p_buf_info
->bufSize
;
440 dprintk("%s,%d: buf %x-> addr %x, size %x \n"
441 , __FILE__
, __LINE__
, i
, (unsigned int)p_buf_info
->bufVirtPtr
, p_buf_info
->bufSize
);
448 dprintk("%s,%d: handle CONTIG.\n", __FILE__
, __LINE__
);
449 p_mbuf_info
->numFrags
= 1;
450 p_mbuf_info
->mbufSize
= crp
->crp_ilen
;
451 p_buf_info
->bufVirtPtr
= crp
->crp_buf
;
452 p_buf_info
->bufSize
= crp
->crp_ilen
;
453 temp_len
= crp
->crp_ilen
;
457 /* Support up to 64K why? cause! */
458 if(crp
->crp_ilen
> 64*1024) {
459 printk("%s,%d: buf too big %x \n", __FILE__
, __LINE__
, crp
->crp_ilen
);
463 if( temp_len
!= crp
->crp_ilen
) {
464 printk("%s,%d: warning size don't match.(%x %x) \n", __FILE__
, __LINE__
, temp_len
, crp
->crp_ilen
);
467 cesa_cmd
->pSrc
= p_mbuf_info
;
468 cesa_cmd
->pDst
= p_mbuf_info
;
470 /* restore p_buf_info to point to first available buf */
471 p_buf_info
= cesa_ocf_cmd
->cesa_bufs
;
475 /* Go through crypto descriptors, processing as we go */
476 for (crd
= crp
->crp_desc
; crd
; crd
= crd
->crd_next
) {
478 /* Encryption /Decryption */
479 if(crd
->crd_alg
== cesa_ocf_cur_ses
->cipher_alg
) {
481 dprintk("%s,%d: cipher", __FILE__
, __LINE__
);
483 cesa_cmd
->cryptoOffset
= crd
->crd_skip
;
484 cesa_cmd
->cryptoLength
= crd
->crd_len
;
486 if(crd
->crd_flags
& CRD_F_ENCRYPT
) { /* encrypt */
487 dprintk(" encrypt \n");
491 if (crd
->crd_flags
& CRD_F_IV_EXPLICIT
) { /* IV from USER */
492 dprintk("%s,%d: IV from USER (offset %x) \n", __FILE__
, __LINE__
, crd
->crd_inject
);
493 cesa_cmd
->ivFromUser
= 1;
497 * do we have to copy the IV back to the buffer ?
499 if ((crd
->crd_flags
& CRD_F_IV_PRESENT
) == 0) {
500 dprintk("%s,%d: copy the IV back to the buffer\n", __FILE__
, __LINE__
);
501 cesa_cmd
->ivOffset
= crd
->crd_inject
;
502 crypto_copyback(crp
->crp_flags
, crp
->crp_buf
, crd
->crd_inject
, cesa_ocf_cur_ses
->ivlen
, ivp
);
505 dprintk("%s,%d: don't copy the IV back to the buffer \n", __FILE__
, __LINE__
);
506 p_mbuf_info
->numFrags
++;
507 p_mbuf_info
->mbufSize
+= cesa_ocf_cur_ses
->ivlen
;
508 p_mbuf_info
->pFrags
= p_buf_info
;
510 p_buf_info
->bufVirtPtr
= ivp
;
511 p_buf_info
->bufSize
= cesa_ocf_cur_ses
->ivlen
;
515 cesa_cmd
->ivOffset
= 0;
516 cesa_cmd
->cryptoOffset
+= cesa_ocf_cur_ses
->ivlen
;
518 cesa_cmd
->macOffset
+= cesa_ocf_cur_ses
->ivlen
;
519 cesa_cmd
->digestOffset
+= cesa_ocf_cur_ses
->ivlen
;
523 else { /* random IV */
524 dprintk("%s,%d: random IV \n", __FILE__
, __LINE__
);
525 cesa_cmd
->ivFromUser
= 0;
528 * do we have to copy the IV back to the buffer ?
530 /* in this mode the HAL will always copy the IV */
531 /* given by the session to the ivOffset */
532 if ((crd
->crd_flags
& CRD_F_IV_PRESENT
) == 0) {
533 cesa_cmd
->ivOffset
= crd
->crd_inject
;
536 /* if IV isn't copy, then how will the user know which IV did we use??? */
537 printk("%s,%d: EINVAL\n", __FILE__
, __LINE__
);
543 dprintk(" decrypt \n");
545 cesa_cmd
->sessionId
= cesa_ocf_cur_ses
->sid_decrypt
;
548 if (crd
->crd_flags
& CRD_F_IV_EXPLICIT
) {
549 dprintk("%s,%d: IV from USER \n", __FILE__
, __LINE__
);
550 /* append the IV buf to the mbuf */
551 cesa_cmd
->ivFromUser
= 1;
552 p_mbuf_info
->numFrags
++;
553 p_mbuf_info
->mbufSize
+= cesa_ocf_cur_ses
->ivlen
;
554 p_mbuf_info
->pFrags
= p_buf_info
;
556 p_buf_info
->bufVirtPtr
= crd
->crd_iv
;
557 p_buf_info
->bufSize
= cesa_ocf_cur_ses
->ivlen
;
561 cesa_cmd
->ivOffset
= 0;
562 cesa_cmd
->cryptoOffset
+= cesa_ocf_cur_ses
->ivlen
;
564 cesa_cmd
->macOffset
+= cesa_ocf_cur_ses
->ivlen
;
565 cesa_cmd
->digestOffset
+= cesa_ocf_cur_ses
->ivlen
;
569 dprintk("%s,%d: IV inside the buffer \n", __FILE__
, __LINE__
);
570 cesa_cmd
->ivFromUser
= 0;
571 cesa_cmd
->ivOffset
= crd
->crd_inject
;
577 else if(crd
->crd_alg
== cesa_ocf_cur_ses
->auth_alg
) {
578 dprintk("%s,%d: Authentication \n", __FILE__
, __LINE__
);
580 cesa_cmd
->macOffset
= crd
->crd_skip
;
581 cesa_cmd
->macLength
= crd
->crd_len
;
584 cesa_cmd
->digestOffset
= crd
->crd_inject
;
587 printk("%s,%d: Alg isn't supported by this session.\n", __FILE__
, __LINE__
);
593 dprintk("%s,%d: Sending Action: \n", __FILE__
, __LINE__
);
594 dprintk("%s,%d: IV from user: %d. IV offset %x \n", __FILE__
, __LINE__
, cesa_cmd
->ivFromUser
, cesa_cmd
->ivOffset
);
595 dprintk("%s,%d: crypt offset %x len %x \n", __FILE__
, __LINE__
, cesa_cmd
->cryptoOffset
, cesa_cmd
->cryptoLength
);
596 dprintk("%s,%d: Auth offset %x len %x \n", __FILE__
, __LINE__
, cesa_cmd
->macOffset
, cesa_cmd
->macLength
);
597 dprintk("%s,%d: set digest in offset %x . \n", __FILE__
, __LINE__
, cesa_cmd
->digestOffset
);
599 mvCesaDebugMbuf("SRC BUFFER", cesa_cmd
->pSrc
, 0, cesa_cmd
->pSrc
->mbufSize
);
603 /* send action to HAL */
604 spin_lock_irqsave(&cesa_lock
, flags
);
605 status
= mvCesaAction(cesa_cmd
);
606 spin_unlock_irqrestore(&cesa_lock
, flags
);
608 /* action not allowed */
609 if(status
== MV_NOT_ALLOWED
) {
610 #ifdef CESA_OCF_SPLIT
611 /* if both encrypt and auth try to split */
612 if(auth
&& (encrypt
|| decrypt
)) {
613 MV_CESA_COMMAND
*cesa_cmd_wa
;
615 /* malloc a new cesa process and init it */
616 cesa_ocf_cmd_wa
= kmalloc(sizeof(struct cesa_ocf_process
), GFP_ATOMIC
);
618 if (cesa_ocf_cmd_wa
== NULL
) {
619 printk("%s,%d: ENOBUFS \n", __FILE__
, __LINE__
);
622 memcpy(cesa_ocf_cmd_wa
, cesa_ocf_cmd
, sizeof(struct cesa_ocf_process
));
623 cesa_cmd_wa
= &cesa_ocf_cmd_wa
->cesa_cmd
;
624 cesa_cmd_wa
->pReqPrv
= (void *)cesa_ocf_cmd_wa
;
625 cesa_ocf_cmd_wa
->need_cb
= 0;
627 /* break requests to two operation, first operation completion won't call callback */
628 if((decrypt
) && (cesa_ocf_cur_ses
->auth_tn_decrypt
)) {
629 cesa_cmd_wa
->sessionId
= cesa_ocf_cur_ses
->frag_wa_auth
;
630 cesa_cmd
->sessionId
= cesa_ocf_cur_ses
->frag_wa_decrypt
;
632 else if((decrypt
) && !(cesa_ocf_cur_ses
->auth_tn_decrypt
)) {
633 cesa_cmd_wa
->sessionId
= cesa_ocf_cur_ses
->frag_wa_decrypt
;
634 cesa_cmd
->sessionId
= cesa_ocf_cur_ses
->frag_wa_auth
;
636 else if((encrypt
) && (cesa_ocf_cur_ses
->encrypt_tn_auth
)) {
637 cesa_cmd_wa
->sessionId
= cesa_ocf_cur_ses
->frag_wa_encrypt
;
638 cesa_cmd
->sessionId
= cesa_ocf_cur_ses
->frag_wa_auth
;
640 else if((encrypt
) && !(cesa_ocf_cur_ses
->encrypt_tn_auth
)){
641 cesa_cmd_wa
->sessionId
= cesa_ocf_cur_ses
->frag_wa_auth
;
642 cesa_cmd
->sessionId
= cesa_ocf_cur_ses
->frag_wa_encrypt
;
645 printk("%s,%d: Unsupporterd fragment wa mode \n", __FILE__
, __LINE__
);
649 /* send the 2 actions to the HAL */
650 spin_lock_irqsave(&cesa_lock
, flags
);
651 status
= mvCesaAction(cesa_cmd_wa
);
652 spin_unlock_irqrestore(&cesa_lock
, flags
);
654 if((status
!= MV_NO_MORE
) && (status
!= MV_OK
)) {
655 printk("%s,%d: cesa action failed, status = 0x%x\n", __FILE__
, __LINE__
, status
);
658 spin_lock_irqsave(&cesa_lock
, flags
);
659 status
= mvCesaAction(cesa_cmd
);
660 spin_unlock_irqrestore(&cesa_lock
, flags
);
663 /* action not allowed and can't split */
671 /* Hal Q is full, send again. This should never happen */
672 if(status
== MV_NO_RESOURCE
) {
673 printk("%s,%d: cesa no more resources \n", __FILE__
, __LINE__
);
677 kfree(cesa_ocf_cmd_wa
);
680 else if((status
!= MV_NO_MORE
) && (status
!= MV_OK
)) {
681 printk("%s,%d: cesa action failed, status = 0x%x\n", __FILE__
, __LINE__
, status
);
686 #ifdef CESA_OCF_POLLING
687 cesa_interrupt_polling();
693 crp
->crp_etype
= EINVAL
;
697 kfree(cesa_ocf_cmd_wa
);
705 cesa_callback(unsigned long dummy
)
707 struct cesa_ocf_process
*cesa_ocf_cmd
= NULL
;
708 struct cryptop
*crp
= NULL
;
709 MV_CESA_RESULT result
[MV_CESA_MAX_CHAN
];
713 dprintk("%s()\n", __FUNCTION__
);
715 #ifdef CESA_OCF_TASKLET
716 disable_irq(cesa_device
.irq
);
720 /* Get Ready requests */
721 spin_lock(&cesa_lock
);
722 status
= mvCesaReadyGet(&result
[res_idx
]);
723 spin_unlock(&cesa_lock
);
727 if(status
!= MV_OK
) {
728 #ifdef CESA_OCF_POLLING
729 if(status
== MV_BUSY
) { /* Fragment */
730 cesa_interrupt_polling();
740 for(i
= 0; i
< res_idx
; i
++) {
742 if(!result
[i
].pReqPrv
) {
743 printk("%s,%d: warning private is NULL\n", __FILE__
, __LINE__
);
747 cesa_ocf_cmd
= result
[i
].pReqPrv
;
748 crp
= cesa_ocf_cmd
->crp
;
750 // ignore HMAC error.
751 //if(result->retCode)
752 // crp->crp_etype = EIO;
754 #if defined(CESA_OCF_POLLING)
755 if(!cesa_ocf_cmd
->need_cb
){
756 cesa_interrupt_polling();
759 if(cesa_ocf_cmd
->need_cb
) {
761 mvCesaDebugMbuf("DST BUFFER", cesa_ocf_cmd
->cesa_cmd
.pDst
, 0, cesa_ocf_cmd
->cesa_cmd
.pDst
->mbufSize
);
767 #ifdef CESA_OCF_TASKLET
768 enable_irq(cesa_device
.irq
);
776 #ifdef CESA_OCF_POLLING
778 cesa_interrupt_polling(void)
782 dprintk("%s()\n", __FUNCTION__
);
784 /* Read cause register */
786 cause
= MV_REG_READ(MV_CESA_ISR_CAUSE_REG
);
787 cause
&= MV_CESA_CAUSE_ACC_DMA_ALL_MASK
;
789 } while (cause
== 0);
791 /* clear interrupts */
792 MV_REG_WRITE(MV_CESA_ISR_CAUSE_REG
, 0);
802 * cesa Interrupt polling routine.
805 cesa_interrupt_handler(int irq
, void *arg
)
809 dprintk("%s()\n", __FUNCTION__
);
813 /* Read cause register */
814 cause
= MV_REG_READ(MV_CESA_ISR_CAUSE_REG
);
816 if( (cause
& MV_CESA_CAUSE_ACC_DMA_ALL_MASK
) == 0)
818 /* Empty interrupt */
819 dprintk("%s,%d: cesaTestReadyIsr: cause=0x%x\n", __FILE__
, __LINE__
, cause
);
823 /* clear interrupts */
824 MV_REG_WRITE(MV_CESA_ISR_CAUSE_REG
, 0);
827 #ifdef CESA_OCF_TASKLET
828 tasklet_hi_schedule(&cesa_ocf_tasklet
);
839 /*cesa_ocf_newsession(void *arg, u_int32_t *sid, struct cryptoini *cri)*/
840 cesa_ocf_newsession(device_t dev
, u_int32_t
*sid
, struct cryptoini
*cri
)
843 u32 count
= 0, auth
= 0, encrypt
=0;
844 struct cesa_ocf_data
*cesa_ocf_cur_ses
;
845 MV_CESA_OPEN_SESSION cesa_session
;
846 MV_CESA_OPEN_SESSION
*cesa_ses
= &cesa_session
;
849 dprintk("%s()\n", __FUNCTION__
);
850 if (sid
== NULL
|| cri
== NULL
) {
851 printk("%s,%d: EINVAL\n", __FILE__
, __LINE__
);
855 /* leave first empty like in other implementations */
856 for (i
= 1; i
< CESA_OCF_MAX_SES
; i
++) {
857 if (cesa_ocf_sessions
[i
] == NULL
)
861 if(i
>= CESA_OCF_MAX_SES
) {
862 printk("%s,%d: no more sessions \n", __FILE__
, __LINE__
);
866 cesa_ocf_sessions
[i
] = (struct cesa_ocf_data
*) kmalloc(sizeof(struct cesa_ocf_data
), GFP_ATOMIC
);
867 if (cesa_ocf_sessions
[i
] == NULL
) {
868 cesa_ocf_freesession(NULL
, i
);
869 printk("%s,%d: ENOBUFS \n", __FILE__
, __LINE__
);
872 dprintk("%s,%d: new session %d \n", __FILE__
, __LINE__
, i
);
875 cesa_ocf_cur_ses
= cesa_ocf_sessions
[i
];
876 memset(cesa_ocf_cur_ses
, 0, sizeof(struct cesa_ocf_data
));
877 cesa_ocf_cur_ses
->sid_encrypt
= -1;
878 cesa_ocf_cur_ses
->sid_decrypt
= -1;
879 cesa_ocf_cur_ses
->frag_wa_encrypt
= -1;
880 cesa_ocf_cur_ses
->frag_wa_decrypt
= -1;
881 cesa_ocf_cur_ses
->frag_wa_auth
= -1;
883 /* init the session */
884 memset(cesa_ses
, 0, sizeof(MV_CESA_OPEN_SESSION
));
888 printk("%s,%d: don't support more then 2 operations\n", __FILE__
, __LINE__
);
891 switch (cri
->cri_alg
) {
893 dprintk("%s,%d: (%d) AES CBC \n", __FILE__
, __LINE__
, count
);
894 cesa_ocf_cur_ses
->cipher_alg
= cri
->cri_alg
;
895 cesa_ocf_cur_ses
->ivlen
= MV_CESA_AES_BLOCK_SIZE
;
896 cesa_ses
->cryptoAlgorithm
= MV_CESA_CRYPTO_AES
;
897 cesa_ses
->cryptoMode
= MV_CESA_CRYPTO_CBC
;
898 if(cri
->cri_klen
/8 > MV_CESA_MAX_CRYPTO_KEY_LENGTH
) {
899 printk("%s,%d: CRYPTO key too long.\n", __FILE__
, __LINE__
);
902 memcpy(cesa_ses
->cryptoKey
, cri
->cri_key
, cri
->cri_klen
/8);
903 dprintk("%s,%d: key length %d \n", __FILE__
, __LINE__
, cri
->cri_klen
/8);
904 cesa_ses
->cryptoKeyLength
= cri
->cri_klen
/8;
907 case CRYPTO_3DES_CBC
:
908 dprintk("%s,%d: (%d) 3DES CBC \n", __FILE__
, __LINE__
, count
);
909 cesa_ocf_cur_ses
->cipher_alg
= cri
->cri_alg
;
910 cesa_ocf_cur_ses
->ivlen
= MV_CESA_3DES_BLOCK_SIZE
;
911 cesa_ses
->cryptoAlgorithm
= MV_CESA_CRYPTO_3DES
;
912 cesa_ses
->cryptoMode
= MV_CESA_CRYPTO_CBC
;
913 if(cri
->cri_klen
/8 > MV_CESA_MAX_CRYPTO_KEY_LENGTH
) {
914 printk("%s,%d: CRYPTO key too long.\n", __FILE__
, __LINE__
);
917 memcpy(cesa_ses
->cryptoKey
, cri
->cri_key
, cri
->cri_klen
/8);
918 cesa_ses
->cryptoKeyLength
= cri
->cri_klen
/8;
922 dprintk("%s,%d: (%d) DES CBC \n", __FILE__
, __LINE__
, count
);
923 cesa_ocf_cur_ses
->cipher_alg
= cri
->cri_alg
;
924 cesa_ocf_cur_ses
->ivlen
= MV_CESA_DES_BLOCK_SIZE
;
925 cesa_ses
->cryptoAlgorithm
= MV_CESA_CRYPTO_DES
;
926 cesa_ses
->cryptoMode
= MV_CESA_CRYPTO_CBC
;
927 if(cri
->cri_klen
/8 > MV_CESA_MAX_CRYPTO_KEY_LENGTH
) {
928 printk("%s,%d: CRYPTO key too long.\n", __FILE__
, __LINE__
);
931 memcpy(cesa_ses
->cryptoKey
, cri
->cri_key
, cri
->cri_klen
/8);
932 cesa_ses
->cryptoKeyLength
= cri
->cri_klen
/8;
936 case CRYPTO_MD5_HMAC
:
937 dprintk("%s,%d: (%d) %sMD5 CBC \n", __FILE__
, __LINE__
, count
, (cri
->cri_alg
!= CRYPTO_MD5
)? "H-":" ");
938 cesa_ocf_cur_ses
->auth_alg
= cri
->cri_alg
;
939 cesa_ocf_cur_ses
->digestlen
= (cri
->cri_alg
== CRYPTO_MD5
)? MV_CESA_MD5_DIGEST_SIZE
: 12;
940 cesa_ses
->macMode
= (cri
->cri_alg
== CRYPTO_MD5
)? MV_CESA_MAC_MD5
: MV_CESA_MAC_HMAC_MD5
;
941 if(cri
->cri_klen
/8 > MV_CESA_MAX_CRYPTO_KEY_LENGTH
) {
942 printk("%s,%d: MAC key too long. \n", __FILE__
, __LINE__
);
945 cesa_ses
->macKeyLength
= cri
->cri_klen
/8;
946 memcpy(cesa_ses
->macKey
, cri
->cri_key
, cri
->cri_klen
/8);
947 cesa_ses
->digestSize
= cesa_ocf_cur_ses
->digestlen
;
951 case CRYPTO_SHA1_HMAC
:
952 dprintk("%s,%d: (%d) %sSHA1 CBC \n", __FILE__
, __LINE__
, count
, (cri
->cri_alg
!= CRYPTO_SHA1
)? "H-":" ");
953 cesa_ocf_cur_ses
->auth_alg
= cri
->cri_alg
;
954 cesa_ocf_cur_ses
->digestlen
= (cri
->cri_alg
== CRYPTO_SHA1
)? MV_CESA_SHA1_DIGEST_SIZE
: 12;
955 cesa_ses
->macMode
= (cri
->cri_alg
== CRYPTO_SHA1
)? MV_CESA_MAC_SHA1
: MV_CESA_MAC_HMAC_SHA1
;
956 if(cri
->cri_klen
/8 > MV_CESA_MAX_CRYPTO_KEY_LENGTH
) {
957 printk("%s,%d: MAC key too long. \n", __FILE__
, __LINE__
);
960 cesa_ses
->macKeyLength
= cri
->cri_klen
/8;
961 memcpy(cesa_ses
->macKey
, cri
->cri_key
, cri
->cri_klen
/8);
962 cesa_ses
->digestSize
= cesa_ocf_cur_ses
->digestlen
;
966 printk("%s,%d: unknown algo 0x%x\n", __FILE__
, __LINE__
, cri
->cri_alg
);
973 if((encrypt
> 2) || (auth
> 2)) {
974 printk("%s,%d: session mode is not supported.\n", __FILE__
, __LINE__
);
977 /* create new sessions in HAL */
979 cesa_ses
->operation
= MV_CESA_CRYPTO_ONLY
;
980 /* encrypt session */
982 cesa_ses
->operation
= MV_CESA_MAC_THEN_CRYPTO
;
985 cesa_ses
->operation
= MV_CESA_CRYPTO_THEN_MAC
;
986 cesa_ocf_cur_ses
->encrypt_tn_auth
= 1;
989 cesa_ses
->operation
= MV_CESA_CRYPTO_ONLY
;
991 cesa_ses
->direction
= MV_CESA_DIR_ENCODE
;
992 status
= mvCesaSessionOpen(cesa_ses
, &cesa_ocf_cur_ses
->sid_encrypt
);
993 if(status
!= MV_OK
) {
994 printk("%s,%d: Can't open new session - status = 0x%x\n", __FILE__
, __LINE__
, status
);
997 /* decrypt session */
998 if( cesa_ses
->operation
== MV_CESA_MAC_THEN_CRYPTO
) {
999 cesa_ses
->operation
= MV_CESA_CRYPTO_THEN_MAC
;
1001 else if( cesa_ses
->operation
== MV_CESA_CRYPTO_THEN_MAC
) {
1002 cesa_ses
->operation
= MV_CESA_MAC_THEN_CRYPTO
;
1004 cesa_ses
->direction
= MV_CESA_DIR_DECODE
;
1005 status
= mvCesaSessionOpen(cesa_ses
, &cesa_ocf_cur_ses
->sid_decrypt
);
1006 if(status
!= MV_OK
) {
1007 printk("%s,%d: Can't open new session - status = 0x%x\n", __FILE__
, __LINE__
, status
);
1011 /* preapre one action sessions for case we will need to split an action */
1012 #ifdef CESA_OCF_SPLIT
1013 if(( cesa_ses
->operation
== MV_CESA_MAC_THEN_CRYPTO
) ||
1014 ( cesa_ses
->operation
== MV_CESA_CRYPTO_THEN_MAC
)) {
1015 /* open one session for encode and one for decode */
1016 cesa_ses
->operation
= MV_CESA_CRYPTO_ONLY
;
1017 cesa_ses
->direction
= MV_CESA_DIR_ENCODE
;
1018 status
= mvCesaSessionOpen(cesa_ses
, &cesa_ocf_cur_ses
->frag_wa_encrypt
);
1019 if(status
!= MV_OK
) {
1020 printk("%s,%d: Can't open new session - status = 0x%x\n", __FILE__
, __LINE__
, status
);
1024 cesa_ses
->direction
= MV_CESA_DIR_DECODE
;
1025 status
= mvCesaSessionOpen(cesa_ses
, &cesa_ocf_cur_ses
->frag_wa_decrypt
);
1026 if(status
!= MV_OK
) {
1027 printk("%s,%d: Can't open new session - status = 0x%x\n", __FILE__
, __LINE__
, status
);
1030 /* open one session for auth */
1031 cesa_ses
->operation
= MV_CESA_MAC_ONLY
;
1032 cesa_ses
->direction
= MV_CESA_DIR_ENCODE
;
1033 status
= mvCesaSessionOpen(cesa_ses
, &cesa_ocf_cur_ses
->frag_wa_auth
);
1034 if(status
!= MV_OK
) {
1035 printk("%s,%d: Can't open new session - status = 0x%x\n", __FILE__
, __LINE__
, status
);
1041 else { /* only auth */
1042 cesa_ses
->operation
= MV_CESA_MAC_ONLY
;
1043 cesa_ses
->direction
= MV_CESA_DIR_ENCODE
;
1044 status
= mvCesaSessionOpen(cesa_ses
, &cesa_ocf_cur_ses
->sid_encrypt
);
1045 if(status
!= MV_OK
) {
1046 printk("%s,%d: Can't open new session - status = 0x%x\n", __FILE__
, __LINE__
, status
);
1053 cesa_ocf_freesession(NULL
, *sid
);
1063 cesa_ocf_freesession(device_t dev
, u_int64_t tid
)
1065 struct cesa_ocf_data
*cesa_ocf_cur_ses
;
1066 u_int32_t sid
= CRYPTO_SESID2LID(tid
);
1067 //unsigned long flags;
1069 dprintk("%s() %d \n", __FUNCTION__
, sid
);
1070 if ( (sid
>= CESA_OCF_MAX_SES
) || (cesa_ocf_sessions
[sid
] == NULL
) ) {
1071 printk("%s,%d: EINVAL can't free session %d \n", __FILE__
, __LINE__
, sid
);
1075 /* Silently accept and return */
1079 /* release session from HAL */
1080 cesa_ocf_cur_ses
= cesa_ocf_sessions
[sid
];
1081 if (cesa_ocf_cur_ses
->sid_encrypt
!= -1) {
1082 mvCesaSessionClose(cesa_ocf_cur_ses
->sid_encrypt
);
1084 if (cesa_ocf_cur_ses
->sid_decrypt
!= -1) {
1085 mvCesaSessionClose(cesa_ocf_cur_ses
->sid_decrypt
);
1087 if (cesa_ocf_cur_ses
->frag_wa_encrypt
!= -1) {
1088 mvCesaSessionClose(cesa_ocf_cur_ses
->frag_wa_encrypt
);
1090 if (cesa_ocf_cur_ses
->frag_wa_decrypt
!= -1) {
1091 mvCesaSessionClose(cesa_ocf_cur_ses
->frag_wa_decrypt
);
1093 if (cesa_ocf_cur_ses
->frag_wa_auth
!= -1) {
1094 mvCesaSessionClose(cesa_ocf_cur_ses
->frag_wa_auth
);
1097 kfree(cesa_ocf_cur_ses
);
1098 cesa_ocf_sessions
[sid
] = NULL
;
1104 /* TDMA Window setup */
1107 setup_tdma_mbus_windows(struct cesa_dev
*dev
)
1111 for (i
= 0; i
< 4; i
++) {
1112 writel(0, dev
->reg
+ WINDOW_BASE(i
));
1113 writel(0, dev
->reg
+ WINDOW_CTRL(i
));
1116 for (i
= 0; i
< dev
->plat_data
->dram
->num_cs
; i
++) {
1117 struct mbus_dram_window
*cs
= dev
->plat_data
->dram
->cs
+ i
;
1119 ((cs
->size
- 1) & 0xffff0000) |
1120 (cs
->mbus_attr
<< 8) |
1121 (dev
->plat_data
->dram
->mbus_dram_target_id
<< 4) | 1,
1122 dev
->reg
+ WINDOW_CTRL(i
)
1124 writel(cs
->base
, dev
->reg
+ WINDOW_BASE(i
));
1129 * our driver startup and shutdown routines
1132 mv_cesa_ocf_init(struct platform_device
*pdev
)
1134 #if defined(CONFIG_MV78200) || defined(CONFIG_MV632X)
1135 if (MV_FALSE
== mvSocUnitIsMappedToThisCpu(CESA
))
1137 dprintk("CESA is not mapped to this CPU\n");
1142 dprintk("%s\n", __FUNCTION__
);
1143 memset(&mv_cesa_dev
, 0, sizeof(mv_cesa_dev
));
1144 softc_device_init(&mv_cesa_dev
, "MV CESA", 0, mv_cesa_methods
);
1145 cesa_ocf_id
= crypto_get_driverid(softc_get_device(&mv_cesa_dev
),CRYPTOCAP_F_HARDWARE
);
1147 if (cesa_ocf_id
< 0)
1148 panic("MV CESA crypto device cannot initialize!");
1150 dprintk("%s,%d: cesa ocf device id is %d \n", __FILE__
, __LINE__
, cesa_ocf_id
);
1152 /* CESA unit is auto power on off */
1154 if (MV_FALSE
== mvCtrlPwrClckGet(CESA_UNIT_ID
,0))
1156 printk("\nWarning CESA %d is Powered Off\n",0);
1161 memset(&cesa_device
, 0, sizeof(struct cesa_dev
));
1162 /* Get the IRQ, and crypto memory regions */
1164 struct resource
*res
;
1165 res
= platform_get_resource_byname(pdev
, IORESOURCE_MEM
, "sram");
1170 cesa_device
.sram
= ioremap(res
->start
, res
->end
- res
->start
+ 1);
1171 res
= platform_get_resource_byname(pdev
, IORESOURCE_MEM
, "regs");
1174 iounmap(cesa_device
.sram
);
1177 cesa_device
.reg
= ioremap(res
->start
, res
->end
- res
->start
+ 1);
1178 cesa_device
.irq
= platform_get_irq(pdev
, 0);
1179 cesa_device
.plat_data
= pdev
->dev
.platform_data
;
1180 setup_tdma_mbus_windows(&cesa_device
);
1185 if( MV_OK
!= mvCesaInit(CESA_OCF_MAX_SES
*5, CESA_Q_SIZE
, cesa_device
.reg
,
1187 printk("%s,%d: mvCesaInit Failed. \n", __FILE__
, __LINE__
);
1191 /* clear and unmask Int */
1192 MV_REG_WRITE( MV_CESA_ISR_CAUSE_REG
, 0);
1193 #ifndef CESA_OCF_POLLING
1194 MV_REG_WRITE( MV_CESA_ISR_MASK_REG
, MV_CESA_CAUSE_ACC_DMA_MASK
);
1196 #ifdef CESA_OCF_TASKLET
1197 tasklet_init(&cesa_ocf_tasklet
, cesa_callback
, (unsigned int) 0);
1199 /* register interrupt */
1200 if( request_irq( cesa_device
.irq
, cesa_interrupt_handler
,
1201 (IRQF_DISABLED
) , "cesa", &cesa_ocf_id
) < 0) {
1202 printk("%s,%d: cannot assign irq %x\n", __FILE__
, __LINE__
, cesa_device
.reg
);
1207 memset(cesa_ocf_sessions
, 0, sizeof(struct cesa_ocf_data
*) * CESA_OCF_MAX_SES
);
1209 #define REGISTER(alg) \
1210 crypto_register(cesa_ocf_id, alg, 0,0)
1211 REGISTER(CRYPTO_AES_CBC
);
1212 REGISTER(CRYPTO_DES_CBC
);
1213 REGISTER(CRYPTO_3DES_CBC
);
1214 REGISTER(CRYPTO_MD5
);
1215 REGISTER(CRYPTO_MD5_HMAC
);
1216 REGISTER(CRYPTO_SHA1
);
1217 REGISTER(CRYPTO_SHA1_HMAC
);
1224 mv_cesa_ocf_exit(struct platform_device
*pdev
)
1226 dprintk("%s()\n", __FUNCTION__
);
1228 crypto_unregister_all(cesa_ocf_id
);
1230 iounmap(cesa_device
.reg
);
1231 iounmap(cesa_device
.sram
);
1232 free_irq(cesa_device
.irq
, NULL
);
1234 /* mask and clear Int */
1235 MV_REG_WRITE( MV_CESA_ISR_MASK_REG
, 0);
1236 MV_REG_WRITE( MV_CESA_ISR_CAUSE_REG
, 0);
1239 if( MV_OK
!= mvCesaFinish() ) {
1240 printk("%s,%d: mvCesaFinish Failed. \n", __FILE__
, __LINE__
);
1246 void cesa_ocf_debug(void)
1249 #ifdef CESA_OCF_TRACE_DEBUG
1252 j
= cesaTestTraceIdx
;
1253 mvOsPrintf("No Type rCause iCause Proc Isr Res Time pReady pProc pEmpty\n");
1254 for(i
=0; i
<MV_CESA_TEST_TRACE_SIZE
; i
++)
1256 mvOsPrintf("%02d. %d 0x%04x 0x%04x 0x%02x 0x%02x %02d 0x%06x %p %p %p\n",
1257 j
, cesaTestTrace
[j
].type
, cesaTestTrace
[j
].realCause
,
1258 cesaTestTrace
[j
].idmaCause
,
1259 cesaTestTrace
[j
].resources
, cesaTestTrace
[j
].timeStamp
,
1260 cesaTestTrace
[j
].pReqReady
, cesaTestTrace
[j
].pReqProcess
, cesaTestTrace
[j
].pReqEmpty
);
1262 if(j
== MV_CESA_TEST_TRACE_SIZE
)
1270 static struct platform_driver marvell_cesa
= {
1271 .probe
= mv_cesa_ocf_init
,
1272 .remove
= mv_cesa_ocf_exit
,
1274 .owner
= THIS_MODULE
,
1275 .name
= "mv_crypto",
1279 MODULE_ALIAS("platform:mv_crypto");
1281 static int __init
mv_cesa_init(void)
1283 return platform_driver_register(&marvell_cesa
);
1286 module_init(mv_cesa_init
);
1288 static void __exit
mv_cesa_exit(void)
1290 platform_driver_unregister(&marvell_cesa
);
1293 module_exit(mv_cesa_exit
);
1295 MODULE_LICENSE("GPL");
1296 MODULE_AUTHOR("Ronen Shitrit");
1297 MODULE_DESCRIPTION("OCF module for Orion CESA crypto");