1 /*
2 * Copyright (c) 2022 Rockchip Electronics Co. Ltd.
3 */
4 #include <stdbool.h>
5 #include <stdio.h>
6 #include <stdlib.h>
7 #include <string.h>
8 #include <time.h>
9 #include <unistd.h>
10 #include "rkcrypto_core.h"
11 #include "rkcrypto_mem.h"
12 #include "rkcrypto_otp_key.h"
13 #include "rkcrypto_random.h"
14 #include "test_utils.h"
15 #include "rsa_key_data.h"
16
17 #define TEST_BLOCK_SIZE 1024 * 1024 /* 1MB */
18 #define TEST_OTP_BLOCK_SIZE 500 * 1024
19 #define DURATION 1 /* 1s */
20 #define DATA_BUTT 0xFFFFFFFF
21
test_otp_key_item_tp(bool is_virt,uint32_t key_id,uint32_t key_len,uint32_t algo,uint32_t mode,uint32_t operation,rk_crypto_mem * fd,uint32_t data_len)22 static int test_otp_key_item_tp(bool is_virt, uint32_t key_id, uint32_t key_len,
23 uint32_t algo, uint32_t mode, uint32_t operation,
24 rk_crypto_mem *fd, uint32_t data_len)
25 {
26 uint32_t res = 0;
27 rk_cipher_config config;
28 uint8_t iv[16];
29 uint8_t in_out[RK_CRYPTO_MAX_DATA_LEN];
30 struct timespec start, end;
31 uint64_t total_nsec, nsec;
32 uint32_t rounds;
33
34 nsec = DURATION * 1000000000;
35
36 memset(iv, 0x00, sizeof(iv));
37 test_get_rng(iv, sizeof(iv));
38
39 if (is_virt) {
40 memset(in_out, 0x00, sizeof(in_out));
41 test_get_rng(in_out, data_len);
42 }
43
44 memcpy(config.iv, iv, sizeof(iv));
45
46 config.algo = algo;
47 config.mode = mode;
48 config.key_len = key_len;
49 config.reserved = NULL;
50 config.operation = operation;
51 total_nsec = 0;
52 rounds = 0;
53
54 while (total_nsec < nsec) {
55 clock_gettime(CLOCK_REALTIME, &start);
56
57 if (is_virt)
58 res = rk_oem_otp_key_cipher_virt(key_id, &config, in_out, in_out, data_len);
59 else
60 res = rk_oem_otp_key_cipher(key_id, &config, fd->dma_fd, fd->dma_fd, data_len);
61
62 if (res == RK_CRYPTO_ERR_NOT_SUPPORTED) {
63 if (is_virt)
64 printf("virt:\totpkey\t[%s-%u]\t%s\t%s\tN/A.\n",
65 test_algo_name(algo), key_len * 8, test_mode_name(mode),
66 test_op_name(operation));
67 else
68 printf("dma_fd:\totpkey\t[%s-%u]\t%s\t%s\tN/A.\n",
69 test_algo_name(algo), key_len * 8, test_mode_name(mode),
70 test_op_name(operation));
71
72 return RK_CRYPTO_SUCCESS;
73 } else if (res) {
74 printf("test rk_oem_otp_key_cipher failed! 0x%08x\n", res);
75 return res;
76 }
77
78 clock_gettime(CLOCK_REALTIME, &end);
79 total_nsec += (end.tv_sec - start.tv_sec) * 1000000000 +
80 (end.tv_nsec - start.tv_nsec);
81 rounds ++;
82 }
83
84 if (is_virt)
85 printf("virt:\totpkey\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
86 test_algo_name(algo), key_len * 8, test_mode_name(mode),
87 test_op_name(operation), (data_len * rounds / (1024 * 1024)));
88 else
89 printf("dma_fd:\totpkey\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
90 test_algo_name(algo), key_len * 8, test_mode_name(mode),
91 test_op_name(operation), (data_len * rounds / (1024 * 1024)));
92
93 return res;
94 }
95
test_otp_key_virt_tp(void)96 static int test_otp_key_virt_tp(void)
97 {
98 uint32_t h, j, k;
99 uint32_t algo, key_id, mode, operation, len, key_len;
100
101 const uint32_t algo_tab[] = {
102 RK_ALGO_AES,
103 RK_ALGO_SM4,
104 };
105 const uint32_t mode_tab[] = {
106 RK_CIPHER_MODE_ECB,
107 RK_CIPHER_MODE_CBC,
108 RK_CIPHER_MODE_CTR,
109 };
110 const uint32_t op_tab[] = {
111 RK_OP_CIPHER_ENC,
112 RK_OP_CIPHER_DEC,
113 };
114
115 for (h = 0; h < ARRAY_SIZE(algo_tab); h++) {
116 for (j = 0; j < ARRAY_SIZE(mode_tab); j++) {
117 for (k = 0; k < ARRAY_SIZE(op_tab); k++) {
118 algo = algo_tab[h];
119 mode = mode_tab[j];
120 operation = op_tab[k];
121 key_id = RK_OEM_OTP_KEY3;
122 len = TEST_OTP_BLOCK_SIZE;
123
124 if (algo == RK_ALGO_AES) {
125 key_len = 32;
126 } else {
127 key_len = 16;
128 }
129
130 if (test_otp_key_item_tp(true, key_id, key_len, algo,
131 mode, operation, NULL, len))
132 goto error;
133 }
134 }
135 }
136
137 printf("virt:\ttest otp_key throughput SUCCESS.\n\n");
138 return 0;
139
140 error:
141 printf("virt:\ttest otp_key throughput FAILED!!!\n\n");
142 return -1;
143 }
144
test_otp_key_fd_tp(void)145 static int test_otp_key_fd_tp(void)
146 {
147 int res = 0;
148 uint32_t h, j, k;
149 uint32_t algo, key_id, mode, operation, len, key_len;
150 rk_crypto_mem *in_out = NULL;
151
152 const uint32_t algo_tab[] = {
153 RK_ALGO_AES,
154 RK_ALGO_SM4,
155 };
156 const uint32_t mode_tab[] = {
157 RK_CIPHER_MODE_ECB,
158 RK_CIPHER_MODE_CBC,
159 RK_CIPHER_MODE_CTR,
160 };
161 const uint32_t op_tab[] = {
162 RK_OP_CIPHER_ENC,
163 RK_OP_CIPHER_DEC,
164 };
165
166 if (rk_crypto_init()) {
167 printf("rk_crypto_init error!\n");
168 return -1;
169 }
170
171 in_out = rk_crypto_mem_alloc(TEST_OTP_BLOCK_SIZE);
172 if (!in_out) {
173 printf("rk_crypto_mem_alloc %uByte error!\n", TEST_OTP_BLOCK_SIZE);
174 res = -1;
175 goto out;
176 }
177
178 for (h = 0; h < ARRAY_SIZE(algo_tab); h++) {
179 for (j = 0; j < ARRAY_SIZE(mode_tab); j++) {
180 for (k = 0; k < ARRAY_SIZE(op_tab); k++) {
181 algo = algo_tab[h];
182 mode = mode_tab[j];
183 operation = op_tab[k];
184 key_id = RK_OEM_OTP_KEY3;
185 len = TEST_OTP_BLOCK_SIZE;
186
187 if (algo == RK_ALGO_AES) {
188 key_len = 32;
189 } else {
190 key_len = 16;
191 }
192
193 if (test_otp_key_item_tp(false, key_id, key_len, algo,
194 mode, operation, in_out, len)) {
195 printf("dma_fd:\ttest otp_key throughput FAILED!!!\n");
196 res = -1;
197 goto out;
198 }
199 }
200 }
201 }
202
203 printf("dma_fd:\ttest otp_key throughput SUCCESS.\n\n");
204
205 out:
206 if (!in_out)
207 rk_crypto_mem_free(in_out);
208
209 rk_crypto_deinit();
210 return res;
211 }
212
test_otp_key_tp(void)213 static int test_otp_key_tp(void)
214 {
215 if (test_otp_key_fd_tp())
216 return -1;
217
218 if (test_otp_key_virt_tp())
219 return -1;
220
221 return 0;
222 }
223
test_cipher_item_tp(bool is_virt,uint32_t key_len,uint32_t algo,uint32_t mode,uint32_t operation,void * in_out,uint32_t data_len)224 static int test_cipher_item_tp(bool is_virt, uint32_t key_len, uint32_t algo,
225 uint32_t mode, uint32_t operation,
226 void *in_out, uint32_t data_len)
227 {
228 uint32_t res = 0;
229 rk_handle handle = 0;
230 rk_cipher_config config;
231 struct timespec start, end;
232 uint64_t total_nsec, nsec;
233 uint32_t rounds;
234
235 nsec = DURATION * 1000000000;
236
237 test_get_rng(config.iv, sizeof(config.iv));
238 test_get_rng(config.key, key_len);
239
240 if (is_virt)
241 test_get_rng(in_out, data_len);
242
243 config.algo = algo;
244 config.mode = mode;
245 config.key_len = key_len;
246 config.reserved = NULL;
247 config.operation = operation;
248 total_nsec = 0;
249 rounds = 0;
250
251 while (total_nsec < nsec) {
252 clock_gettime(CLOCK_REALTIME, &start);
253
254 res = rk_cipher_init(&config, &handle);
255 if (res) {
256 if (res != RK_CRYPTO_ERR_NOT_SUPPORTED) {
257 printf("test rk_cipher_init failed! 0x%08x\n", res);
258 goto error;
259 }
260
261 if (is_virt)
262 printf("virt:\t[%s-%u]\t%s\tN/A\n",
263 test_algo_name(algo), key_len * 8, test_mode_name(mode));
264 else
265 printf("dma_fd:\t[%s-%u]\t%s\tN/A\n",
266 test_algo_name(algo), key_len * 8, test_mode_name(mode));
267 return 0;
268 }
269
270 if (is_virt)
271 res = rk_cipher_crypt_virt(handle, in_out, in_out, data_len);
272 else
273 res = rk_cipher_crypt(handle,
274 ((rk_crypto_mem *)in_out)->dma_fd,
275 ((rk_crypto_mem *)in_out)->dma_fd,
276 data_len);
277
278 if (res) {
279 rk_cipher_final(handle);
280 printf("test rk_cipher_crypt failed! 0x%08x\n", res);
281 goto error;
282 }
283
284 rk_cipher_final(handle);
285
286 clock_gettime(CLOCK_REALTIME, &end);
287 total_nsec += (end.tv_sec - start.tv_sec) * 1000000000 +
288 (end.tv_nsec - start.tv_nsec);
289 rounds ++;
290 }
291
292 if (is_virt)
293 printf("virt:\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
294 test_algo_name(algo), key_len * 8, test_mode_name(mode),
295 test_op_name(operation), (data_len * rounds / (1024 * 1024)));
296 else
297 printf("dma_fd:\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
298 test_algo_name(algo), key_len * 8, test_mode_name(mode),
299 test_op_name(operation), (data_len * rounds / (1024 * 1024)));
300
301 return res;
302 error:
303 if (is_virt)
304 printf("virt:\t[%s-%u]\t%s\tFailed.\n",
305 test_algo_name(algo), key_len * 8, test_mode_name(mode));
306 else
307 printf("dma_fd:\t[%s-%u]\t%s\tFailed.\n",
308 test_algo_name(algo), key_len * 8, test_mode_name(mode));
309 return res;
310 }
311
test_cipher_tp(void)312 static int test_cipher_tp(void)
313 {
314 int res = 0;
315 uint32_t h, j, k;
316 uint32_t algo, mode, operation, len, key_len;
317 rk_crypto_mem *in_out_fd = NULL;
318 uint8_t *in_out_virt = NULL;
319 size_t page_size = getpagesize();
320
321 struct test_cipher_item_tp {
322 uint32_t algo;
323 uint32_t modes[RK_CIPHER_MODE_MAX];
324 uint32_t key_len;
325 uint32_t op[2];
326 };
327
328 static struct test_cipher_item_tp test_item_tbl[] = {
329 {
330 .algo = RK_ALGO_DES,
331 .modes = {
332 RK_CIPHER_MODE_ECB,
333 RK_CIPHER_MODE_CBC,
334 DATA_BUTT,
335 },
336 .key_len = 8,
337 .op = {RK_OP_CIPHER_ENC, RK_OP_CIPHER_DEC},
338 },
339
340 {
341 .algo = RK_ALGO_TDES,
342 .modes = {
343 RK_CIPHER_MODE_ECB,
344 RK_CIPHER_MODE_CBC,
345 DATA_BUTT,
346 },
347 .key_len = 24,
348 .op = {RK_OP_CIPHER_ENC, RK_OP_CIPHER_DEC},
349 },
350
351 {
352 .algo = RK_ALGO_AES,
353 .modes = {
354 RK_CIPHER_MODE_ECB,
355 RK_CIPHER_MODE_CBC,
356 RK_CIPHER_MODE_CTS,
357 RK_CIPHER_MODE_CTR,
358 DATA_BUTT,
359 },
360 .key_len = 32,
361 .op = {RK_OP_CIPHER_ENC, RK_OP_CIPHER_DEC},
362 },
363
364 {
365 .algo = RK_ALGO_SM4,
366 .modes = {
367 RK_CIPHER_MODE_ECB,
368 RK_CIPHER_MODE_CBC,
369 RK_CIPHER_MODE_CTS,
370 RK_CIPHER_MODE_CTR,
371 DATA_BUTT,
372 },
373 .key_len = 16,
374 .op = {RK_OP_CIPHER_ENC, RK_OP_CIPHER_DEC},
375 },
376
377 };
378
379 if (rk_crypto_init()) {
380 printf("rk_crypto_init error!\n");
381 return -1;
382 }
383
384 in_out_fd = rk_crypto_mem_alloc(TEST_BLOCK_SIZE);
385 if (!in_out_fd) {
386 printf("rk_crypto_mem_alloc %uByte error!\n", TEST_BLOCK_SIZE);
387 res = -1;
388 goto out;
389 }
390
391 if (posix_memalign((void *)&in_out_virt, page_size, TEST_BLOCK_SIZE) || !in_out_virt) {
392 printf("malloc %uByte error!\n", TEST_BLOCK_SIZE);
393 res = -1;
394 goto out;
395 }
396
397 /* Test dma_fd cipher */
398 for (h = 0; h < ARRAY_SIZE(test_item_tbl); h++) {
399 for (j = 0; j < ARRAY_SIZE(test_item_tbl[h].modes); j++) {
400 if (test_item_tbl[h].modes[j] == DATA_BUTT)
401 break;
402
403 for (k = 0; k < ARRAY_SIZE(test_item_tbl[h].op); k++) {
404 algo = test_item_tbl[h].algo;
405 key_len = test_item_tbl[h].key_len;
406 mode = test_item_tbl[h].modes[j];
407 operation = test_item_tbl[h].op[k];
408 len = TEST_BLOCK_SIZE;
409
410 if (test_cipher_item_tp(false, key_len, algo, mode,
411 operation, in_out_fd, len)) {
412 printf("dma_fd:\ttest cipher throughput FAILED!!!\n");
413 res = -1;
414 goto out;
415 }
416 }
417 }
418 }
419
420 printf("dma_fd:\ttest cipher throughput SUCCESS.\n\n");
421
422 /* Test virt cipher */
423 for (h = 0; h < ARRAY_SIZE(test_item_tbl); h++) {
424 for (j = 0; j < ARRAY_SIZE(test_item_tbl[h].modes); j++) {
425 if (test_item_tbl[h].modes[j] == DATA_BUTT)
426 break;
427
428 for (k = 0; k < ARRAY_SIZE(test_item_tbl[h].op); k++) {
429 algo = test_item_tbl[h].algo;
430 key_len = test_item_tbl[h].key_len;
431 mode = test_item_tbl[h].modes[j];
432 operation = test_item_tbl[h].op[k];
433 len = TEST_BLOCK_SIZE;
434
435 if (test_cipher_item_tp(true, key_len, algo, mode,
436 operation, in_out_virt, len)) {
437 printf("virt:\ttest cipher throughput FAILED!!!\n");
438 res = -1;
439 goto out;
440 }
441 }
442 }
443 }
444
445 printf("virt:\ttest cipher throughput SUCCESS.\n\n");
446
447 out:
448 if (in_out_fd)
449 rk_crypto_mem_free(in_out_fd);
450
451 if (in_out_virt)
452 free(in_out_virt);
453
454 rk_crypto_deinit();
455 return res;
456 }
457
test_ae_item_tp(bool is_virt,uint32_t key_len,uint32_t algo,uint32_t mode,void * in,void * out,uint32_t data_len,void * aad,uint32_t aad_len,void * tag)458 static int test_ae_item_tp(bool is_virt, uint32_t key_len, uint32_t algo,
459 uint32_t mode, void *in, void *out, uint32_t data_len,
460 void *aad, uint32_t aad_len, void *tag)
461 {
462 uint32_t res = 0;
463 rk_handle handle = 0;
464 rk_ae_config config;
465 struct timespec start, end;
466 uint64_t total_nsec, nsec;
467 uint32_t rounds;
468 uint8_t iv_tmp[32];
469
470 nsec = DURATION * 1000000000;
471
472 test_get_rng(config.iv, sizeof(config.iv));
473 test_get_rng(config.key, key_len);
474
475 memcpy(iv_tmp, config.iv, sizeof(config.iv));
476
477 if (is_virt) {
478 test_get_rng(in, data_len);
479 test_get_rng(aad, aad_len);
480 } else {
481 test_get_rng(((rk_crypto_mem *)in)->vaddr, data_len);
482 test_get_rng(((rk_crypto_mem *)aad)->vaddr, aad_len);
483 }
484
485 config.algo = algo;
486 config.mode = mode;
487 config.key_len = key_len;
488 config.reserved = NULL;
489 config.aad_len = aad_len;
490 config.iv_len = 12;
491 config.tag_len = 16;
492
493 /* ENC */
494 config.operation = RK_OP_CIPHER_ENC;
495 total_nsec = 0;
496 rounds = 0;
497
498 while (total_nsec < nsec) {
499 clock_gettime(CLOCK_REALTIME, &start);
500
501 res = rk_ae_init(&config, &handle);
502 if (res) {
503 if (res != RK_CRYPTO_ERR_NOT_SUPPORTED) {
504 printf("test rk_ae_init failed! 0x%08x\n", res);
505 goto error;
506 }
507
508 if (is_virt)
509 printf("virt:\t[%s-%u]\t%s\tN/A\n",
510 test_algo_name(algo), key_len * 8, test_mode_name(mode));
511 else
512 printf("dma_fd:\t[%s-%u]\t%s\tN/A\n",
513 test_algo_name(algo), key_len * 8, test_mode_name(mode));
514 return 0;
515 }
516
517 if (is_virt) {
518 res = rk_ae_set_aad_virt(handle, aad);
519 if (res) {
520 rk_ae_final(handle);
521 goto error;
522 }
523 res = rk_ae_crypt_virt(handle, in, out, data_len, tag);
524 } else {
525 res = rk_ae_set_aad(handle, ((rk_crypto_mem *)aad)->dma_fd);
526 if (res) {
527 rk_ae_final(handle);
528 goto error;
529 }
530
531 res = rk_ae_crypt(handle,
532 ((rk_crypto_mem *)in)->dma_fd,
533 ((rk_crypto_mem *)out)->dma_fd,
534 data_len,
535 tag);
536 }
537
538 if (res) {
539 rk_ae_final(handle);
540 printf("test rk_ad_crypt failed! 0x%08x\n", res);
541 goto error;
542 }
543
544 rk_ae_final(handle);
545
546 clock_gettime(CLOCK_REALTIME, &end);
547 total_nsec += (end.tv_sec - start.tv_sec) * 1000000000 +
548 (end.tv_nsec - start.tv_nsec);
549 rounds ++;
550 }
551
552 if (is_virt)
553 printf("virt:\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
554 test_algo_name(algo), key_len * 8, test_mode_name(mode),
555 test_op_name(config.operation), (data_len * rounds / (1024 * 1024)));
556 else
557 printf("dma_fd:\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
558 test_algo_name(algo), key_len * 8, test_mode_name(mode),
559 test_op_name(config.operation), (data_len * rounds / (1024 * 1024)));
560
561 /* DEC */
562 config.operation = RK_OP_CIPHER_DEC;
563 memcpy(config.iv, iv_tmp, config.iv_len);
564 total_nsec = 0;
565 rounds = 0;
566 while (total_nsec < nsec) {
567 clock_gettime(CLOCK_REALTIME, &start);
568
569 res = rk_ae_init(&config, &handle);
570 if (res) {
571 if (res != RK_CRYPTO_ERR_NOT_SUPPORTED) {
572 printf("test rk_ae_init failed! 0x%08x\n", res);
573 goto error;
574 }
575
576 if (is_virt)
577 printf("virt:\t[%s-%u]\t%s\tN/A\n",
578 test_algo_name(algo), key_len * 8, test_mode_name(mode));
579 else
580 printf("dma_fd:\t[%s-%u]\t%s\tN/A\n",
581 test_algo_name(algo), key_len * 8, test_mode_name(mode));
582 return 0;
583 }
584
585 if (is_virt) {
586 res = rk_ae_set_aad_virt(handle, aad);
587 if (res) {
588 rk_ae_final(handle);
589 goto error;
590 }
591 res = rk_ae_crypt_virt(handle, out, in, data_len, tag);
592 } else {
593 res = rk_ae_set_aad(handle, ((rk_crypto_mem *)aad)->dma_fd);
594 if (res) {
595 rk_ae_final(handle);
596 goto error;
597 }
598
599 res = rk_ae_crypt(handle,
600 ((rk_crypto_mem *)out)->dma_fd,
601 ((rk_crypto_mem *)in)->dma_fd,
602 data_len,
603 tag);
604 }
605
606 if (res) {
607 rk_ae_final(handle);
608 printf("test rk_ad_crypt failed! 0x%08x\n", res);
609 goto error;
610 }
611
612 rk_ae_final(handle);
613
614 clock_gettime(CLOCK_REALTIME, &end);
615 total_nsec += (end.tv_sec - start.tv_sec) * 1000000000 +
616 (end.tv_nsec - start.tv_nsec);
617 rounds ++;
618 }
619
620 if (is_virt)
621 printf("virt:\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
622 test_algo_name(algo), key_len * 8, test_mode_name(mode),
623 test_op_name(config.operation), (data_len * rounds / (1024 * 1024)));
624 else
625 printf("dma_fd:\t[%s-%u]\t%s\t%s\t%dMB/s.\n",
626 test_algo_name(algo), key_len * 8, test_mode_name(mode),
627 test_op_name(config.operation), (data_len * rounds / (1024 * 1024)));
628
629 return res;
630 error:
631 if (is_virt)
632 printf("virt:\t[%s-%u]\t%s\tFailed.\n",
633 test_algo_name(algo), key_len * 8, test_mode_name(mode));
634 else
635 printf("dma_fd:\t[%s-%u]\t%s\tFailed.\n",
636 test_algo_name(algo), key_len * 8, test_mode_name(mode));
637 return res;
638 }
639
test_ae_tp(void)640 static int test_ae_tp(void)
641 {
642 int res = 0;
643 uint32_t h, j;
644 uint32_t algo, mode, len, key_len, aad_len;
645 rk_crypto_mem *in_fd = NULL, *out_fd = NULL, *aad_fd = NULL;
646 uint8_t *in_virt = NULL, *out_virt = NULL, *aad_virt = NULL;
647 size_t page_size = getpagesize();
648 uint32_t aad_buff_len = 1024;
649 uint8_t tag[16];
650
651 struct test_aead_item_tp {
652 uint32_t algo;
653 uint32_t modes[RK_CIPHER_MODE_MAX];
654 uint32_t key_len;
655 uint32_t aad_len;
656 uint32_t len;
657 };
658
659 static struct test_aead_item_tp test_item_tbl[] = {
660 {
661 .algo = RK_ALGO_AES,
662 .modes = {
663 RK_CIPHER_MODE_GCM,
664 DATA_BUTT,
665 },
666 .key_len = 32,
667 .aad_len = 1024,
668 .len = TEST_BLOCK_SIZE,
669 },
670
671 {
672 .algo = RK_ALGO_SM4,
673 .modes = {
674 RK_CIPHER_MODE_GCM,
675 DATA_BUTT,
676 },
677 .key_len = 16,
678 .aad_len = 1024,
679 .len = TEST_BLOCK_SIZE,
680 },
681 };
682
683 if (rk_crypto_init()) {
684 printf("rk_crypto_init error!\n");
685 return -1;
686 }
687
688 in_fd = rk_crypto_mem_alloc(TEST_BLOCK_SIZE);
689 if (!in_fd) {
690 printf("rk_crypto_mem_alloc %uByte error!\n", TEST_BLOCK_SIZE);
691 res = -1;
692 goto out;
693 }
694
695 out_fd = rk_crypto_mem_alloc(TEST_BLOCK_SIZE);
696 if (!out_fd) {
697 printf("rk_crypto_mem_alloc %uByte error!\n", TEST_BLOCK_SIZE);
698 res = -1;
699 goto out;
700 }
701
702 aad_fd = rk_crypto_mem_alloc(aad_buff_len);
703 if (!aad_fd) {
704 printf("rk_crypto_mem_alloc %uByte error!\n", aad_buff_len);
705 res = -1;
706 goto out;
707 }
708
709 if (posix_memalign((void *)&in_virt, page_size, TEST_BLOCK_SIZE) || !in_virt) {
710 printf("malloc %uByte error!\n", TEST_BLOCK_SIZE);
711 res = -1;
712 goto out;
713 }
714
715 if (posix_memalign((void *)&out_virt, page_size, TEST_BLOCK_SIZE) || !out_virt) {
716 printf("malloc %uByte error!\n", TEST_BLOCK_SIZE);
717 res = -1;
718 goto out;
719 }
720
721 if (posix_memalign((void *)&aad_virt, page_size, aad_buff_len) || !aad_virt) {
722 printf("malloc %uByte error!\n", aad_buff_len);
723 res = -1;
724 goto out;
725 }
726
727 /* Test dma_fd cipher */
728 for (h = 0; h < ARRAY_SIZE(test_item_tbl); h++) {
729 for (j = 0; j < ARRAY_SIZE(test_item_tbl[h].modes); j++) {
730 if (test_item_tbl[h].modes[j] == DATA_BUTT)
731 break;
732
733 algo = test_item_tbl[h].algo;
734 key_len = test_item_tbl[h].key_len;
735 mode = test_item_tbl[h].modes[j];
736 aad_len = test_item_tbl[h].aad_len;
737 len = test_item_tbl[h].len;
738
739 if (test_ae_item_tp(false, key_len, algo, mode,
740 in_fd, out_fd, len,
741 aad_fd, aad_len, tag)) {
742 printf("dma_fd:\ttest aead throughput FAILED!!!\n");
743 res = -1;
744 goto out;
745 }
746 }
747 }
748
749 printf("dma_fd:\ttest aead throughput SUCCESS.\n\n");
750
751 /* Test virt cipher */
752 for (h = 0; h < ARRAY_SIZE(test_item_tbl); h++) {
753 for (j = 0; j < ARRAY_SIZE(test_item_tbl[h].modes); j++) {
754 if (test_item_tbl[h].modes[j] == DATA_BUTT)
755 break;
756
757 algo = test_item_tbl[h].algo;
758 key_len = test_item_tbl[h].key_len;
759 mode = test_item_tbl[h].modes[j];
760 aad_len = test_item_tbl[h].aad_len;
761 len = test_item_tbl[h].len;
762
763 if (test_ae_item_tp(true, key_len, algo, mode,
764 in_virt, out_virt, len,
765 aad_virt, aad_len, tag)) {
766 printf("virt:\ttest aead throughput FAILED!!!\n");
767 res = -1;
768 goto out;
769 }
770 }
771 }
772
773 printf("virt:\ttest aead throughput SUCCESS.\n\n");
774
775 out:
776 if (in_fd)
777 rk_crypto_mem_free(in_fd);
778
779 if (out_fd)
780 rk_crypto_mem_free(out_fd);
781
782 if (aad_fd)
783 rk_crypto_mem_free(aad_fd);
784
785 if (in_virt)
786 free(in_virt);
787
788 if (out_virt)
789 free(out_virt);
790
791 if (aad_virt)
792 free(aad_virt);
793
794 rk_crypto_deinit();
795 return res;
796 }
797
test_hash_item_tp(bool is_virt,bool is_hmac,uint32_t algo,uint32_t blocksize,void * input,uint32_t data_len)798 static int test_hash_item_tp(bool is_virt, bool is_hmac, uint32_t algo,
799 uint32_t blocksize, void *input, uint32_t data_len)
800 {
801 int res = 0;
802 uint32_t data_block = data_len;
803 uint32_t tmp_len;
804 uint8_t hash[64];
805 uint8_t key[MAX_HASH_BLOCK_SIZE];
806 uint8_t *tmp_data;
807 rk_handle hash_hdl = 0;
808 rk_hash_config hash_cfg;
809 uint32_t key_len;
810 struct timespec start, end;
811 uint64_t total_nsec, nsec;
812 uint32_t rounds;
813
814 nsec = DURATION * 1000000000;
815
816 if (is_virt)
817 test_get_rng(input, data_len);
818
819 memset(hash, 0x00, sizeof(hash));
820
821 memset(&hash_cfg, 0x00, sizeof(hash_cfg));
822 hash_cfg.algo = algo;
823
824 if (is_hmac) {
825 key_len = blocksize;
826 test_get_rng(key, key_len);
827 hash_cfg.key = key;
828 hash_cfg.key_len = key_len;
829 }
830
831 total_nsec = 0;
832 rounds = 0;
833
834 res = rk_hash_init(&hash_cfg, &hash_hdl);
835 if (res) {
836 if (is_virt)
837 printf("virt:\t[%12s]\tN/A\n", test_algo_name(algo));
838 else
839 printf("dma_fd:\t[%12s]\tN/A\n", test_algo_name(algo));
840 return 0;
841 }
842
843 while (total_nsec < nsec) {
844 clock_gettime(CLOCK_REALTIME, &start);
845
846 data_block = data_len;
847
848 if (is_virt) {
849 tmp_len = data_len;
850 tmp_data = input;
851
852 while (tmp_len) {
853 data_block = tmp_len > data_block ? data_block : tmp_len;
854
855 res = rk_hash_update_virt(hash_hdl, tmp_data, data_block);
856 if (res) {
857 rk_hash_final(hash_hdl, NULL);
858 printf("rk_hash_update_virt[%lu/%u] error = %d\n",
859 (unsigned long)(tmp_data - (uint8_t *)input), tmp_len, res);
860 goto error;
861 }
862
863 tmp_len -= data_block;
864 tmp_data += data_block;
865 }
866 } else {
867 res = rk_hash_update(hash_hdl, ((rk_crypto_mem *)input)->dma_fd, data_block);
868 if (res) {
869 rk_hash_final(hash_hdl, NULL);
870 printf("rk_hash_update error = %d\n", res);
871 goto error;
872 }
873 }
874
875 clock_gettime(CLOCK_REALTIME, &end);
876 total_nsec += (end.tv_sec - start.tv_sec) * 1000000000 +
877 (end.tv_nsec - start.tv_nsec);
878 rounds ++;
879 }
880
881 res = rk_hash_final(hash_hdl, hash);
882 if (res) {
883 printf("rk_hash_final error = %d\n", res);
884 return -1;
885 }
886
887 if (is_virt)
888 printf("virt:\t[%12s]\t%dMB/s.\n",
889 test_algo_name(algo), (data_len * rounds / (1024 * 1024)));
890 else
891 printf("dma_fd:\t[%12s]\t%dMB/s.\n",
892 test_algo_name(algo), (data_len * rounds / (1024 * 1024)));
893
894 return res;
895 error:
896 return res;
897 }
898
test_hash_tp(void)899 static int test_hash_tp(void)
900 {
901 int res;
902 uint32_t buffer_len = TEST_BLOCK_SIZE;;
903 rk_crypto_mem *input_fd = NULL;
904 uint8_t *input_virt = NULL;
905 uint32_t i;
906 size_t page_size = getpagesize();
907
908 struct test_hash_item {
909 uint32_t algo;
910 uint32_t blocksize;
911 };
912
913 static struct test_hash_item test_hash_tbl[] = {
914 {RK_ALGO_MD5, MD5_BLOCK_SIZE},
915 {RK_ALGO_SHA1, SHA1_BLOCK_SIZE},
916 {RK_ALGO_SHA256, SHA256_BLOCK_SIZE},
917 {RK_ALGO_SHA224, SHA224_BLOCK_SIZE},
918 {RK_ALGO_SHA512, SHA512_BLOCK_SIZE},
919 {RK_ALGO_SHA384, SHA384_BLOCK_SIZE},
920 {RK_ALGO_SHA512_224, SHA512_224_BLOCK_SIZE},
921 {RK_ALGO_SHA512_256, SHA512_256_BLOCK_SIZE},
922 {RK_ALGO_SM3, SM3_BLOCK_SIZE},
923 };
924
925 static struct test_hash_item test_hmac_tbl[] = {
926 {RK_ALGO_HMAC_MD5, MD5_BLOCK_SIZE},
927 {RK_ALGO_HMAC_SHA1, SHA1_BLOCK_SIZE},
928 {RK_ALGO_HMAC_SHA256, SHA256_BLOCK_SIZE},
929 {RK_ALGO_HMAC_SHA512, SHA512_BLOCK_SIZE},
930 {RK_ALGO_HMAC_SM3, SM3_BLOCK_SIZE},
931 };
932
933 if (rk_crypto_init()) {
934 printf("rk_crypto_init error!\n");
935 return -1;
936 }
937
938 input_fd = rk_crypto_mem_alloc(buffer_len);
939 if (!input_fd) {
940 printf("rk_crypto_mem_alloc %uByte error!\n", buffer_len);
941 res = -1;
942 goto out;
943 }
944
945 if (posix_memalign((void *)&input_virt, page_size, TEST_BLOCK_SIZE) || !input_virt) {
946 printf("malloc %uByte error!\n", TEST_BLOCK_SIZE);
947 res = -1;
948 goto out;
949 }
950
951 /* Test virt hash */
952 for (i = 0; i < ARRAY_SIZE(test_hash_tbl); i++) {
953 res = test_hash_item_tp(true, false, test_hash_tbl[i].algo,
954 test_hash_tbl[i].blocksize, input_virt, buffer_len);
955 if (res) {
956 printf("virt:\ttest hash throughput FAILED!!!\n");
957 goto out;
958 }
959 }
960
961 printf("virt:\ttest hash throughput SUCCESS.\n\n");
962
963 /* Test dma_fd hash */
964 for (i = 0; i < ARRAY_SIZE(test_hash_tbl); i++) {
965 res = test_hash_item_tp(false, false, test_hash_tbl[i].algo,
966 test_hash_tbl[i].blocksize, input_fd, buffer_len);
967 if (res) {
968 printf("dma_fd:\ttest hash throughput FAILED!!!\n");
969 goto out;
970 }
971 }
972
973 printf("dma_fd:\ttest hash throughput SUCCESS.\n\n");
974
975 /* Test virt hmac */
976 for (i = 0; i < ARRAY_SIZE(test_hmac_tbl); i++) {
977 res = test_hash_item_tp(true, true, test_hmac_tbl[i].algo,
978 test_hmac_tbl[i].blocksize, input_virt, buffer_len);
979 if (res) {
980 printf("virt:\ttest hmac throughput FAILED!!!\n");
981 goto out;
982 }
983 }
984
985 printf("virt:\ttest hmac throughput SUCCESS.\n\n");
986
987 /* Test dma_fd hmac */
988 for (i = 0; i < ARRAY_SIZE(test_hmac_tbl); i++) {
989 res = test_hash_item_tp(false, true, test_hmac_tbl[i].algo,
990 test_hmac_tbl[i].blocksize, input_fd, buffer_len);
991 if (res) {
992 printf("dma_fd:\ttest hmac throughput FAILED!!!\n");
993 goto out;
994 }
995 }
996
997 printf("dma_fd:\ttest hmac throughput SUCCESS.\n\n");
998
999 out:
1000 if (input_fd)
1001 rk_crypto_mem_free(input_fd);
1002
1003 if (input_virt)
1004 free(input_virt);
1005
1006 rk_crypto_deinit();
1007
1008 return 0;
1009 }
1010
test_rsa_item_tp(uint32_t nbits)1011 static int test_rsa_item_tp(uint32_t nbits)
1012 {
1013 uint8_t *data_plain = NULL, *data_enc = NULL, *data_dec = NULL;
1014 uint32_t nbytes = nbits / 8;
1015 rk_rsa_pub_key_pack pub_key;
1016 rk_rsa_priv_key_pack priv_key;
1017 struct timespec t1, t2, t3;
1018 uint64_t priv_cost, pub_cost;
1019 uint32_t out_len = 0;
1020 RK_RES res;
1021
1022 data_plain = malloc(nbytes);
1023 if (!data_plain) {
1024 printf("malloc data_plain %uByte error!\n", nbytes);
1025 res = RK_CRYPTO_ERR_OUT_OF_MEMORY;
1026 goto exit;
1027 }
1028
1029 data_enc = malloc(nbytes);
1030 if (!data_enc) {
1031 printf("malloc data_enc %uByte error!\n", nbytes);
1032 res = RK_CRYPTO_ERR_OUT_OF_MEMORY;
1033 goto exit;
1034 }
1035
1036 data_dec = malloc(nbytes);
1037 if (!data_dec) {
1038 printf("malloc data_dec %uByte error!\n", nbytes);
1039 res = RK_CRYPTO_ERR_OUT_OF_MEMORY;
1040 goto exit;
1041 }
1042
1043 res = rk_get_random(data_plain, nbytes);
1044 if (res) {
1045 printf("failed to get random data.");
1046 goto exit;
1047 }
1048
1049 /* make sure data_plain is less than n */
1050 data_plain[0] = 0x00;
1051
1052 memset(data_enc, 0x00, nbytes);
1053
1054 test_init_pubkey(&pub_key, nbits);
1055 test_init_privkey(&priv_key, nbits);
1056
1057 clock_gettime(CLOCK_REALTIME, &t1);
1058
1059 res = rk_rsa_priv_encrypt(&priv_key, RK_RSA_CRYPT_PADDING_NONE,
1060 data_plain, nbytes, data_enc, &out_len);
1061 if (res) {
1062 if (res != RK_CRYPTO_ERR_NOT_SUPPORTED)
1063 printf("rk_rsa_priv_encrypt failed %x\n", res);
1064 goto exit;
1065 }
1066
1067 clock_gettime(CLOCK_REALTIME, &t2);
1068
1069 res = rk_rsa_pub_decrypt(&pub_key, RK_RSA_CRYPT_PADDING_NONE,
1070 data_enc, out_len, data_dec, &out_len);
1071 if (res) {
1072 printf("rk_rsa_pub_decrypt failed %x\n", res);
1073 goto exit;
1074 }
1075
1076 clock_gettime(CLOCK_REALTIME, &t3);
1077
1078 if (nbytes != out_len || memcmp(data_dec, data_plain, nbytes)) {
1079 printf("rk_rsa_pub_decrypt compare failed\n");
1080 test_dump_hex("result", data_dec, out_len);
1081 test_dump_hex("expect", data_plain, nbytes);
1082 res = RK_CRYPTO_ERR_GENERIC;
1083 goto exit;
1084 }
1085
1086 priv_cost = (t2.tv_sec - t1.tv_sec) * 1000000000 +
1087 (t2.tv_nsec - t1.tv_nsec);
1088
1089 pub_cost = (t3.tv_sec - t2.tv_sec) * 1000000000 +
1090 (t3.tv_nsec - t2.tv_nsec);
1091
1092
1093 printf("virt:\t[RSA-%u]\tPRIV\tENCRYPT\t%lums.\n",
1094 nbits, (unsigned long)(priv_cost / 1000000));
1095
1096 printf("virt:\t[RSA-%u]\tPUB\tDECRYPT\t%lums.\n",
1097 nbits, (unsigned long)(pub_cost / 1000000));
1098
1099 exit:
1100 if (data_plain)
1101 free(data_plain);
1102
1103 if (data_enc)
1104 free(data_enc);
1105
1106 if (data_dec)
1107 free(data_dec);
1108
1109 return (res == RK_CRYPTO_SUCCESS) ? 0 : -1;
1110 }
1111
test_rsa_tp(void)1112 static int test_rsa_tp(void)
1113 {
1114 int res;
1115 uint32_t i;
1116 uint32_t rsa_bits_tbl[] = {
1117 RSA_BITS_1024,
1118 RSA_BITS_2048,
1119 RSA_BITS_3072,
1120 RSA_BITS_4096,
1121 };
1122
1123 if (rk_crypto_init()) {
1124 printf("rk_crypto_init error!\n");
1125 return -1;
1126 }
1127
1128 for (i = 0; i < ARRAY_SIZE(rsa_bits_tbl); i++) {
1129 res = test_rsa_item_tp(rsa_bits_tbl[i]);
1130 if (res) {
1131 printf("test rsa-%u throughput FAIL.\n\n", rsa_bits_tbl[i]);
1132 goto out;
1133 }
1134 }
1135
1136 printf("test rsa throughput SUCCESS.\n\n");
1137
1138 out:
1139 rk_crypto_deinit();
1140
1141 return 0;
1142 }
1143
test_throughput(void)1144 RK_RES test_throughput(void)
1145 {
1146 if (test_otp_key_tp())
1147 printf("Test otp key throughput FAILED.\n\n");
1148
1149 if (test_cipher_tp())
1150 printf("Test cipher throughput FAILED.\n\n");
1151
1152 if (test_ae_tp())
1153 printf("Test ae throughput FAILED.\n\n");
1154
1155 if (test_hash_tp())
1156 printf("Test hash throughput FAILED.\n\n");
1157
1158 if (test_rsa_tp())
1159 printf("Test rsa throughput FAILED.\n\n");
1160
1161 printf("Test throughput SUCCESS.\n");
1162
1163 return RK_CRYPTO_SUCCESS;
1164 }
1165