1 /*****************************************************************************
2 Copyright (c) 2009-2019, Intel Corporation
4 Redistribution and use in source and binary forms, with or without
5 modification, are permitted provided that the following conditions are met:
7 * Redistributions of source code must retain the above copyright notice,
8 this list of conditions and the following disclaimer.
9 * Redistributions in binary form must reproduce the above copyright
10 notice, this list of conditions and the following disclaimer in the
11 documentation and/or other materials provided with the distribution.
12 * Neither the name of Intel Corporation nor the names of its contributors
13 may be used to endorse or promote products derived from this software
14 without specific prior written permission.
16 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
20 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
23 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 *****************************************************************************/
29 /*-----------------------------------------------------------------------
31 *-----------------------------------------------------------------------
33 * A simple functional test for ZUC
35 *-----------------------------------------------------------------------*/
42 #include <intel-ipsec-mb.h>
44 #include "zuc_test_vectors.h"
45 #include "gcm_ctr_vectors_test.h"
49 #define FAIL_STATUS -1
51 int zuc_test(const enum arch_type arch
, struct MB_MGR
*mb_mgr
);
53 int validate_zuc_algorithm(struct MB_MGR
*mb_mgr
, uint8_t *pSrcData
,
54 uint8_t *pDstData
, uint8_t *pKeys
, uint8_t *pIV
);
55 int validate_zuc_EEA_1_block(struct MB_MGR
*mb_mgr
, uint8_t *pSrcData
,
56 uint8_t *pDstData
, uint8_t *pKeys
, uint8_t *pIV
);
57 int validate_zuc_EEA_4_block(struct MB_MGR
*mb_mgr
, uint8_t **pSrcData
,
58 uint8_t **pDstData
, uint8_t **pKeys
,
60 int validate_zuc_EEA_n_block(struct MB_MGR
*mb_mgr
, uint8_t **pSrcData
,
61 uint8_t **pDstData
, uint8_t **pKeys
, uint8_t **pIV
,
63 int validate_zuc_EIA_1_block(struct MB_MGR
*mb_mgr
, uint8_t *pSrcData
,
64 uint8_t *pDstData
, uint8_t *pKeys
, uint8_t *pIV
);
65 static void byte_hexdump(const char *message
, const uint8_t *ptr
, int len
);
67 /******************************************************************************
68 * @ingroup zuc_functionalTest_app
71 * This function allocates memory for buffers and set random data in each buffer
73 * pSrcData = pointers to the new source buffers
74 * numOfBuffs = number of buffers
75 * ************************************************/
76 static uint32_t createData(uint8_t *pSrcData
[MAXBUFS
],
79 uint32_t i
= 0, j
= 0;
81 for (i
= 0; i
< numOfBuffs
; i
++) {
82 pSrcData
[i
] = (uint8_t *)malloc(MAX_BUFFER_LENGTH_IN_BYTES
);
85 printf("malloc(pSrcData[i]): failed!\n");
87 for (j
= 0; j
< i
; j
++) {
98 /******************************************************************************
99 * @ingroup zuc_functionalTest_app
102 * This function creates source data and vector buffers.
104 * keyLen = key length
105 * pKeys = array of pointers to the new key buffers
106 * ivLen = vector length
107 * pIV = array of pointers to the new vector buffers
108 * numOfBuffs = number of buffers
109 ************************************************/
110 static uint32_t createKeyVecData(uint32_t keyLen
, uint8_t *pKeys
[MAXBUFS
],
111 uint32_t ivLen
, uint8_t *pIV
[MAXBUFS
],
114 uint32_t i
= 0, j
= 0;
116 for (i
= 0; i
< numOfBuffs
; i
++) {
117 pIV
[i
] = (uint8_t *)malloc(ivLen
);
120 printf("malloc(pIV[i]): failed!\n");
122 for (j
= 0; j
< i
; j
++) {
130 pKeys
[i
] = malloc(keyLen
);
133 printf("malloc(pKeys[i]): failed!\n");
135 for (j
= 0; j
<= i
; j
++) {
148 /******************************************************************************
149 * @ingroup zuc_benchmark_app
152 * This function free memory pointed to by an array of pointers
154 * arr = array of memory pointers
155 * length = length of pointer array (or number of pointers whose buffers
157 * ************************************************/
158 static void freePtrArray(uint8_t *pArr
[MAXBUFS
], uint32_t arrayLength
)
162 for (i
= 0; i
< arrayLength
; i
++)
166 static uint32_t bswap4(const uint32_t val
)
168 return ((val
>> 24) | /**< A*/
169 ((val
& 0xff0000) >> 8) | /**< B*/
170 ((val
& 0xff00) << 8) | /**< C*/
171 (val
<< 24)); /**< D*/
174 int zuc_test(const enum arch_type arch
, struct MB_MGR
*mb_mgr
)
177 uint32_t numBuffs
, a
;
178 uint32_t status
= PASS_STATUS
;
179 uint8_t *pKeys
[MAXBUFS
];
180 uint8_t *pIV
[MAXBUFS
];
181 uint8_t *pSrcData
[MAXBUFS
];
182 uint8_t *pDstData
[MAXBUFS
];
184 /* Do not run the tests for aesni emulation */
185 if (arch
== ARCH_NO_AESNI
)
188 printf("Running Functional Tests\n");
191 /*Create test data buffers + populate with random data*/
192 if (createData(pSrcData
, MAXBUFS
)) {
193 printf("createData() error\n");
196 if (createData(pDstData
, MAXBUFS
)) {
197 printf("createData() error\n");
201 /*Create random keys and vectors*/
202 if (createKeyVecData(ZUC_KEY_LEN_IN_BYTES
, pKeys
, ZUC_IV_LEN_IN_BYTES
,
204 printf("createKeyVecData() error\n");
205 freePtrArray(pSrcData
, MAXBUFS
);
206 freePtrArray(pDstData
, MAXBUFS
);
210 if (validate_zuc_algorithm(mb_mgr
, pSrcData
[0], pSrcData
[0], pKeys
[0],
214 printf("validate ZUC algorithm: PASS\n");
216 if (validate_zuc_EEA_1_block(mb_mgr
, pSrcData
[0], pSrcData
[0], pKeys
[0],
220 printf("validate ZUC 1 block: PASS\n");
222 if (validate_zuc_EEA_4_block(mb_mgr
, pSrcData
, pSrcData
, pKeys
, pIV
))
225 printf("validate ZUC 4 block: PASS\n");
227 for (a
= 0; a
< 3; a
++) {
239 if (validate_zuc_EEA_n_block(mb_mgr
, pSrcData
, pDstData
, pKeys
,
243 printf("validate ZUC n block buffers %d: PASS\n", a
);
246 if (validate_zuc_EIA_1_block(mb_mgr
, pSrcData
[0], pDstData
[0], pKeys
[0],
250 printf("validate ZUC Integrity 1 block: PASS\n");
252 freePtrArray(pKeys
, MAXBUFS
); /*Free the key buffers*/
253 freePtrArray(pIV
, MAXBUFS
); /*Free the vector buffers*/
254 freePtrArray(pSrcData
, MAXBUFS
); /*Free the source buffers*/
255 freePtrArray(pDstData
, MAXBUFS
); /*Free the destination buffers*/
259 printf("The Functional Test application completed\n");
263 int validate_zuc_EEA_1_block(struct MB_MGR
*mb_mgr
, uint8_t *pSrcData
,
264 uint8_t *pDstData
, uint8_t *pKeys
, uint8_t *pIV
)
266 uint32_t i
, byteResidue
;
271 for (i
= 0; i
< NUM_ZUC_EEA3_TESTS
; i
++) {
272 memcpy(pKeys
, testEEA3_vectors
[i
].CK
, ZUC_KEY_LEN_IN_BYTES
);
273 zuc_eea3_iv_gen(testEEA3_vectors
[i
].count
,
274 testEEA3_vectors
[i
].Bearer
,
275 testEEA3_vectors
[i
].Direction
,
277 byteLength
= (testEEA3_vectors
[i
].length_in_bits
+ 7) / 8;
278 memcpy(pSrcData
, testEEA3_vectors
[i
].plaintext
, byteLength
);
279 IMB_ZUC_EEA3_1_BUFFER(mb_mgr
, pKeys
, pIV
, pSrcData
, pDstData
,
281 retTmp
= memcmp(pDstData
, testEEA3_vectors
[i
].ciphertext
,
284 printf("Validate ZUC 1 block test %d (Enc): FAIL\n",
286 byte_hexdump("Expected", testEEA3_vectors
[i
].ciphertext
,
288 byte_hexdump("Found", pDstData
, byteLength
);
293 (testEEA3_vectors
[i
].length_in_bits
% 8)) &
296 (testEEA3_vectors
[i
].ciphertext
297 [testEEA3_vectors
[i
].length_in_bits
/ 8] ^
298 pDstData
[testEEA3_vectors
[i
].length_in_bits
/ 8]) &
301 printf("Validate ZUC 1 block test %d (Enc): "
304 printf("Expected: 0x%02X (last byte)\n",
307 .ciphertext
[testEEA3_vectors
[i
]
310 printf("Found: 0x%02X (last byte)\n",
311 0xFF & pDstData
[testEEA3_vectors
[i
]
315 printf("Validate ZUC 1 block test %d (Enc): "
323 int validate_zuc_EEA_4_block(struct MB_MGR
*mb_mgr
, uint8_t **pSrcData
,
324 uint8_t **pDstData
, uint8_t **pKeys
, uint8_t **pIV
)
326 uint32_t i
, j
, packetLen
[4], bitResidue
, byteResidue
;
329 for (i
= 0; i
< NUM_ZUC_EEA3_TESTS
; i
++) {
330 for (j
= 0; j
< 4; j
++) {
332 (testEEA3_vectors
[i
].length_in_bits
+ 7) / 8;
333 memcpy(pKeys
[j
], testEEA3_vectors
[i
].CK
,
334 ZUC_KEY_LEN_IN_BYTES
);
335 zuc_eea3_iv_gen(testEEA3_vectors
[i
].count
,
336 testEEA3_vectors
[i
].Bearer
,
337 testEEA3_vectors
[i
].Direction
,
339 memcpy(pSrcData
[j
], testEEA3_vectors
[i
].plaintext
,
342 IMB_ZUC_EEA3_4_BUFFER(mb_mgr
, (const void * const *)pKeys
,
343 (const void * const *)pIV
,
344 (const void * const *)pSrcData
,
345 (void **)pDstData
, packetLen
);
346 uint8_t *pDst8
= (uint8_t *)pDstData
[0];
348 retTmp
= memcmp(pDst8
, testEEA3_vectors
[i
].ciphertext
,
349 (testEEA3_vectors
[i
].length_in_bits
) / 8);
351 printf("Validate ZUC 4 block (Enc) test %d: FAIL\n",
353 byte_hexdump("Expected", testEEA3_vectors
[i
].ciphertext
,
354 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
356 byte_hexdump("Found", pDst8
,
357 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
363 (testEEA3_vectors
[i
].length_in_bits
% 8)) &
366 (testEEA3_vectors
[i
].ciphertext
367 [testEEA3_vectors
[i
].length_in_bits
/ 8] ^
368 pDst8
[testEEA3_vectors
[i
].length_in_bits
/ 8]) &
372 printf("Validate ZUC 4 block test %d (Enc): "
375 printf("Expected: 0x%02X (last byte)\n",
378 .ciphertext
[testEEA3_vectors
[i
]
381 printf("Found: 0x%02X (last byte)\n",
382 0xFF & pDst8
[testEEA3_vectors
[i
]
386 printf("Validate ZUC 4 block test %d (Enc): "
391 for (j
= 0; j
< 4; j
++) {
392 memcpy(pSrcData
[j
], testEEA3_vectors
[i
].ciphertext
,
393 (testEEA3_vectors
[i
].length_in_bits
+ 7) / 8);
395 IMB_ZUC_EEA3_4_BUFFER(mb_mgr
, (const void * const *)pKeys
,
396 (const void * const *)pIV
,
397 (const void * const *)pSrcData
,
398 (void **)pDstData
, packetLen
);
399 pDst8
= (uint8_t *)pDstData
[0];
400 retTmp
= memcmp(pDst8
, testEEA3_vectors
[i
].plaintext
,
401 (testEEA3_vectors
[i
].length_in_bits
) / 8);
403 printf("Validate ZUC 4 block (Dec) test %d: FAIL\n",
405 byte_hexdump("Expected", testEEA3_vectors
[i
].plaintext
,
406 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
408 byte_hexdump("Found", pDst8
,
409 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
415 (testEEA3_vectors
[i
].length_in_bits
% 8)) &
419 .plaintext
[testEEA3_vectors
[i
].length_in_bits
/
421 pDst8
[testEEA3_vectors
[i
].length_in_bits
/ 8]) &
425 printf("Validate ZUC 4 block test %d (Dec): "
428 printf("Expected: 0x%02X (last byte)\n",
431 .plaintext
[testEEA3_vectors
[i
]
434 printf("Found: 0x%02X (last byte)\n",
435 0xFF & pDst8
[testEEA3_vectors
[i
]
439 printf("Validate ZUC 4 block test %d (Dec): "
448 int validate_zuc_EEA_n_block(struct MB_MGR
*mb_mgr
, uint8_t **pSrcData
,
449 uint8_t **pDstData
, uint8_t **pKeys
, uint8_t **pIV
,
452 uint32_t i
, j
, bitResidue
, byteResidue
;
454 uint32_t packetLen
[MAXBUFS
];
456 assert(numBuffs
> 0);
457 for (i
= 0; i
< NUM_ZUC_EEA3_TESTS
; i
++) {
458 for (j
= 0; j
<= (numBuffs
- 1); j
++) {
459 memcpy(pKeys
[j
], testEEA3_vectors
[i
].CK
,
460 ZUC_KEY_LEN_IN_BYTES
);
461 zuc_eea3_iv_gen(testEEA3_vectors
[i
].count
,
462 testEEA3_vectors
[i
].Bearer
,
463 testEEA3_vectors
[i
].Direction
,
465 memcpy(pSrcData
[j
], testEEA3_vectors
[i
].plaintext
,
466 (testEEA3_vectors
[i
].length_in_bits
+ 7) / 8);
468 (testEEA3_vectors
[i
].length_in_bits
+ 7) / 8;
470 IMB_ZUC_EEA3_N_BUFFER(mb_mgr
, (const void * const *)pKeys
,
471 (const void * const *)pIV
,
472 (const void * const *)pSrcData
,
473 (void **)pDstData
, packetLen
, numBuffs
);
474 uint8_t *pDst8
= (uint8_t *)pDstData
[0];
476 retTmp
= memcmp(pDstData
[0], testEEA3_vectors
[i
].ciphertext
,
477 (testEEA3_vectors
[i
].length_in_bits
) / 8);
479 printf("Validate ZUC n block (Enc) test %d, buffers: "
482 byte_hexdump("Expected", testEEA3_vectors
[i
].ciphertext
,
483 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
485 byte_hexdump("Found", pDst8
,
486 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
492 (testEEA3_vectors
[i
].length_in_bits
% 8)) &
495 (testEEA3_vectors
[i
].ciphertext
496 [testEEA3_vectors
[i
].length_in_bits
/ 8] ^
497 pDst8
[testEEA3_vectors
[i
].length_in_bits
/ 8]) &
501 printf("Validate ZUC n block (Enc) test %d, "
502 "buffers %d: FAIL\n",
504 printf("Expected: 0x%02X (last byte)\n",
507 .ciphertext
[testEEA3_vectors
[i
]
510 printf("Found: 0x%02X (last byte)\n",
511 0xFF & pDst8
[testEEA3_vectors
[i
]
515 printf("Validate ZUC n block (Enc) test %d, "
516 "buffers %d: PASS\n",
520 for (j
= 0; j
<= (numBuffs
- 1); j
++) {
521 memcpy(pSrcData
[j
], testEEA3_vectors
[i
].ciphertext
,
522 (testEEA3_vectors
[i
].length_in_bits
+ 7) / 8);
524 IMB_ZUC_EEA3_N_BUFFER(mb_mgr
, (const void * const *)pKeys
,
525 (const void * const *)pIV
,
526 (const void * const *)pSrcData
,
527 (void **)pDstData
, packetLen
, numBuffs
);
528 retTmp
= memcmp(pDstData
[0], testEEA3_vectors
[i
].plaintext
,
529 (testEEA3_vectors
[i
].length_in_bits
) / 8);
531 printf("Validate ZUC n block (Dec) test %d, buffers "
534 byte_hexdump("Expected", testEEA3_vectors
[i
].plaintext
,
535 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
537 byte_hexdump("Found", pDstData
[0],
538 (testEEA3_vectors
[i
].length_in_bits
+ 7) /
544 (testEEA3_vectors
[i
].length_in_bits
% 8)) &
548 .plaintext
[testEEA3_vectors
[i
].length_in_bits
/
550 pDst8
[testEEA3_vectors
[i
].length_in_bits
/ 8]) &
554 printf("Validate ZUC n block (Dec) test %d, "
555 "buffers %d : FAIL\n",
557 printf("Expected: 0x%02X (last byte)\n",
560 .plaintext
[testEEA3_vectors
[i
]
563 printf("Found: 0x%02X (last byte)\n",
564 0xFF & pDst8
[testEEA3_vectors
[i
]
568 printf("Validate ZUC n block (Dec) test %d, "
569 "buffers %d: PASS\n",
577 int validate_zuc_EIA_1_block(struct MB_MGR
*mb_mgr
, uint8_t *pSrcData
,
578 uint8_t *pDstData
, uint8_t *pKeys
, uint8_t *pIV
)
584 for (i
= 0; i
< NUM_ZUC_EIA3_TESTS
; i
++) {
585 memcpy(pKeys
, testEIA3_vectors
[i
].CK
, ZUC_KEY_LEN_IN_BYTES
);
587 zuc_eia3_iv_gen(testEIA3_vectors
[i
].count
,
588 testEIA3_vectors
[i
].Bearer
,
589 testEIA3_vectors
[i
].Direction
,
591 byteLength
= (testEIA3_vectors
[i
].length_in_bits
+ 7) / 8;
592 memcpy(pSrcData
, testEIA3_vectors
[i
].message
, byteLength
);
593 IMB_ZUC_EIA3_1_BUFFER(mb_mgr
, pKeys
, pIV
, pSrcData
,
594 testEIA3_vectors
[i
].length_in_bits
,
595 (uint32_t *)pDstData
);
597 memcmp(pDstData
, &testEIA3_vectors
[i
].mac
,
598 sizeof(((struct test128EIA3_vectors_t
*)0)->mac
));
600 printf("Validate ZUC 1 block test %d (Int): FAIL\n",
602 byte_hexdump("Expected",
603 (const uint8_t *)&testEIA3_vectors
[i
].mac
,
605 byte_hexdump("Found", pDstData
, ZUC_DIGEST_LEN
);
608 printf("Validate ZUC 1 block test %d (Int): PASS\n",
615 int validate_zuc_algorithm(struct MB_MGR
*mb_mgr
, uint8_t *pSrcData
,
616 uint8_t *pDstData
, uint8_t *pKeys
, uint8_t *pIV
)
625 for (i
= 0; i
< NUM_ZUC_ALG_TESTS
; i
++) {
626 memcpy(pKeys
, testZUC_vectors
[i
].CK
, ZUC_KEY_LEN_IN_BYTES
);
627 memcpy(pIV
, testZUC_vectors
[i
].IV
, ZUC_IV_LEN_IN_BYTES
);
628 memset(pSrcData
, 0, 8);
629 IMB_ZUC_EEA3_1_BUFFER(mb_mgr
, pKeys
, pIV
, pSrcData
, pDstData
,
631 swapBytes
.sbw
[0] = bswap4(testZUC_vectors
[i
].Z
[0]);
632 swapBytes
.sbw
[1] = bswap4(testZUC_vectors
[i
].Z
[1]);
633 ret
= memcmp(pDstData
, swapBytes
.sbb
, 8);
635 printf("ZUC 1 algorithm test %d: FAIL\n", i
);
637 printf("ZUC 1 algorithm test %d: PASS\n", i
);
641 /*****************************************************************************
642 ** @description - utility function to dump test buffers$
644 ** @param message [IN] - debug message to print$
645 ** @param ptr [IN] - pointer to beginning of buffer.$
646 ** @param len [IN] - length of buffer.$
647 *****************************************************************************/
648 static void byte_hexdump(const char *message
, const uint8_t *ptr
, int len
)
652 printf("%s:\n", message
);
653 for (ctr
= 0; ctr
< len
; ctr
++) {
654 printf("0x%02X ", ptr
[ctr
] & 0xff);
655 if (!((ctr
+ 1) % 16))