ReactOS 0.4.15-dev-7953-g1f49173
nist_kw.c
Go to the documentation of this file.
1/*
2 * Implementation of NIST SP 800-38F key wrapping, supporting KW and KWP modes
3 * only
4 *
5 * Copyright The Mbed TLS Contributors
6 * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
7 *
8 * This file is provided under the Apache License 2.0, or the
9 * GNU General Public License v2.0 or later.
10 *
11 * **********
12 * Apache License 2.0:
13 *
14 * Licensed under the Apache License, Version 2.0 (the "License"); you may
15 * not use this file except in compliance with the License.
16 * You may obtain a copy of the License at
17 *
18 * http://www.apache.org/licenses/LICENSE-2.0
19 *
20 * Unless required by applicable law or agreed to in writing, software
21 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
22 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
23 * See the License for the specific language governing permissions and
24 * limitations under the License.
25 *
26 * **********
27 *
28 * **********
29 * GNU General Public License v2.0 or later:
30 *
31 * This program is free software; you can redistribute it and/or modify
32 * it under the terms of the GNU General Public License as published by
33 * the Free Software Foundation; either version 2 of the License, or
34 * (at your option) any later version.
35 *
36 * This program is distributed in the hope that it will be useful,
37 * but WITHOUT ANY WARRANTY; without even the implied warranty of
38 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
39 * GNU General Public License for more details.
40 *
41 * You should have received a copy of the GNU General Public License along
42 * with this program; if not, write to the Free Software Foundation, Inc.,
43 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
44 *
45 * **********
46 */
47/*
48 * Definition of Key Wrapping:
49 * https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-38F.pdf
50 * RFC 3394 "Advanced Encryption Standard (AES) Key Wrap Algorithm"
51 * RFC 5649 "Advanced Encryption Standard (AES) Key Wrap with Padding Algorithm"
52 *
53 * Note: RFC 3394 defines different methodology for intermediate operations for
54 * the wrapping and unwrapping operation than the definition in NIST SP 800-38F.
55 */
56
57#if !defined(MBEDTLS_CONFIG_FILE)
58#include "mbedtls/config.h"
59#else
60#include MBEDTLS_CONFIG_FILE
61#endif
62
63#if defined(MBEDTLS_NIST_KW_C)
64
65#include "mbedtls/nist_kw.h"
67
68#include <stdint.h>
69#include <string.h>
70
71#if defined(MBEDTLS_SELF_TEST) && defined(MBEDTLS_AES_C)
72#if defined(MBEDTLS_PLATFORM_C)
73#include "mbedtls/platform.h"
74#else
75#include <stdio.h>
76#define mbedtls_printf printf
77#endif /* MBEDTLS_PLATFORM_C */
78#endif /* MBEDTLS_SELF_TEST && MBEDTLS_AES_C */
79
80#if !defined(MBEDTLS_NIST_KW_ALT)
81
82#define KW_SEMIBLOCK_LENGTH 8
83#define MIN_SEMIBLOCKS_COUNT 3
84
85/* constant-time buffer comparison */
86static inline unsigned char mbedtls_nist_kw_safer_memcmp( const void *a, const void *b, size_t n )
87{
88 size_t i;
89 volatile const unsigned char *A = (volatile const unsigned char *) a;
90 volatile const unsigned char *B = (volatile const unsigned char *) b;
91 volatile unsigned char diff = 0;
92
93 for( i = 0; i < n; i++ )
94 {
95 /* Read volatile data in order before computing diff.
96 * This avoids IAR compiler warning:
97 * 'the order of volatile accesses is undefined ..' */
98 unsigned char x = A[i], y = B[i];
99 diff |= x ^ y;
100 }
101
102 return( diff );
103}
104
106static const unsigned char NIST_KW_ICV1[] = {0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xA6};
108static const unsigned char NIST_KW_ICV2[] = {0xA6, 0x59, 0x59, 0xA6};
109
110#ifndef GET_UINT32_BE
111#define GET_UINT32_BE(n,b,i) \
112do { \
113 (n) = ( (uint32_t) (b)[(i) ] << 24 ) \
114 | ( (uint32_t) (b)[(i) + 1] << 16 ) \
115 | ( (uint32_t) (b)[(i) + 2] << 8 ) \
116 | ( (uint32_t) (b)[(i) + 3] ); \
117} while( 0 )
118#endif
119
120#ifndef PUT_UINT32_BE
121#define PUT_UINT32_BE(n,b,i) \
122do { \
123 (b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
124 (b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
125 (b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
126 (b)[(i) + 3] = (unsigned char) ( (n) ); \
127} while( 0 )
128#endif
129
130/*
131 * Initialize context
132 */
134{
135 memset( ctx, 0, sizeof( mbedtls_nist_kw_context ) );
136}
137
140 const unsigned char *key,
141 unsigned int keybits,
142 const int is_wrap )
143{
144 int ret;
145 const mbedtls_cipher_info_t *cipher_info;
146
148 keybits,
150 if( cipher_info == NULL )
152
153 if( cipher_info->block_size != 16 )
155
156 /*
157 * SP 800-38F currently defines AES cipher as the only block cipher allowed:
158 * "For KW and KWP, the underlying block cipher shall be approved, and the
159 * block size shall be 128 bits. Currently, the AES block cipher, with key
160 * lengths of 128, 192, or 256 bits, is the only block cipher that fits
161 * this profile."
162 * Currently we don't support other 128 bit block ciphers for key wrapping,
163 * such as Camellia and Aria.
164 */
167
168 mbedtls_cipher_free( &ctx->cipher_ctx );
169
170 if( ( ret = mbedtls_cipher_setup( &ctx->cipher_ctx, cipher_info ) ) != 0 )
171 return( ret );
172
173 if( ( ret = mbedtls_cipher_setkey( &ctx->cipher_ctx, key, keybits,
174 is_wrap ? MBEDTLS_ENCRYPT :
176 ) != 0 )
177 {
178 return( ret );
179 }
180
181 return( 0 );
182}
183
184/*
185 * Free context
186 */
188{
189 mbedtls_cipher_free( &ctx->cipher_ctx );
191}
192
193/*
194 * Helper function for Xoring the uint64_t "t" with the encrypted A.
195 * Defined in NIST SP 800-38F section 6.1
196 */
197static void calc_a_xor_t( unsigned char A[KW_SEMIBLOCK_LENGTH], uint64_t t )
198{
199 size_t i = 0;
200 for( i = 0; i < sizeof( t ); i++ )
201 {
202 A[i] ^= ( t >> ( ( sizeof( t ) - 1 - i ) * 8 ) ) & 0xff;
203 }
204}
205
206/*
207 * KW-AE as defined in SP 800-38F section 6.2
208 * KWP-AE as defined in SP 800-38F section 6.3
209 */
212 const unsigned char *input, size_t in_len,
213 unsigned char *output, size_t *out_len, size_t out_size )
214{
215 int ret = 0;
216 size_t semiblocks = 0;
217 size_t s;
218 size_t olen, padlen = 0;
219 uint64_t t = 0;
220 unsigned char outbuff[KW_SEMIBLOCK_LENGTH * 2];
221 unsigned char inbuff[KW_SEMIBLOCK_LENGTH * 2];
222
223 *out_len = 0;
224 /*
225 * Generate the String to work on
226 */
227 if( mode == MBEDTLS_KW_MODE_KW )
228 {
229 if( out_size < in_len + KW_SEMIBLOCK_LENGTH )
230 {
232 }
233
234 /*
235 * According to SP 800-38F Table 1, the plaintext length for KW
236 * must be between 2 to 2^54-1 semiblocks inclusive.
237 */
238 if( in_len < 16 ||
239#if SIZE_MAX > 0x1FFFFFFFFFFFFF8
240 in_len > 0x1FFFFFFFFFFFFF8 ||
241#endif
242 in_len % KW_SEMIBLOCK_LENGTH != 0 )
243 {
245 }
246
247 memcpy( output, NIST_KW_ICV1, KW_SEMIBLOCK_LENGTH );
248 memmove( output + KW_SEMIBLOCK_LENGTH, input, in_len );
249 }
250 else
251 {
252 if( in_len % 8 != 0 )
253 {
254 padlen = ( 8 - ( in_len % 8 ) );
255 }
256
257 if( out_size < in_len + KW_SEMIBLOCK_LENGTH + padlen )
258 {
260 }
261
262 /*
263 * According to SP 800-38F Table 1, the plaintext length for KWP
264 * must be between 1 and 2^32-1 octets inclusive.
265 */
266 if( in_len < 1
267#if SIZE_MAX > 0xFFFFFFFF
268 || in_len > 0xFFFFFFFF
269#endif
270 )
271 {
273 }
274
275 memcpy( output, NIST_KW_ICV2, KW_SEMIBLOCK_LENGTH / 2 );
276 PUT_UINT32_BE( ( in_len & 0xffffffff ), output,
277 KW_SEMIBLOCK_LENGTH / 2 );
278
279 memcpy( output + KW_SEMIBLOCK_LENGTH, input, in_len );
280 memset( output + KW_SEMIBLOCK_LENGTH + in_len, 0, padlen );
281 }
282 semiblocks = ( ( in_len + padlen ) / KW_SEMIBLOCK_LENGTH ) + 1;
283
284 s = 6 * ( semiblocks - 1 );
285
287 && in_len <= KW_SEMIBLOCK_LENGTH )
288 {
289 memcpy( inbuff, output, 16 );
290 ret = mbedtls_cipher_update( &ctx->cipher_ctx,
291 inbuff, 16, output, &olen );
292 if( ret != 0 )
293 goto cleanup;
294 }
295 else
296 {
297 unsigned char *R2 = output + KW_SEMIBLOCK_LENGTH;
298 unsigned char *A = output;
299
300 /*
301 * Do the wrapping function W, as defined in RFC 3394 section 2.2.1
302 */
303 if( semiblocks < MIN_SEMIBLOCKS_COUNT )
304 {
306 goto cleanup;
307 }
308
309 /* Calculate intermediate values */
310 for( t = 1; t <= s; t++ )
311 {
312 memcpy( inbuff, A, KW_SEMIBLOCK_LENGTH );
313 memcpy( inbuff + KW_SEMIBLOCK_LENGTH, R2, KW_SEMIBLOCK_LENGTH );
314
315 ret = mbedtls_cipher_update( &ctx->cipher_ctx,
316 inbuff, 16, outbuff, &olen );
317 if( ret != 0 )
318 goto cleanup;
319
320 memcpy( A, outbuff, KW_SEMIBLOCK_LENGTH );
321 calc_a_xor_t( A, t );
322
323 memcpy( R2, outbuff + KW_SEMIBLOCK_LENGTH, KW_SEMIBLOCK_LENGTH );
324 R2 += KW_SEMIBLOCK_LENGTH;
325 if( R2 >= output + ( semiblocks * KW_SEMIBLOCK_LENGTH ) )
326 R2 = output + KW_SEMIBLOCK_LENGTH;
327 }
328 }
329
330 *out_len = semiblocks * KW_SEMIBLOCK_LENGTH;
331
332cleanup:
333
334 if( ret != 0)
335 {
336 memset( output, 0, semiblocks * KW_SEMIBLOCK_LENGTH );
337 }
338 mbedtls_platform_zeroize( inbuff, KW_SEMIBLOCK_LENGTH * 2 );
339 mbedtls_platform_zeroize( outbuff, KW_SEMIBLOCK_LENGTH * 2 );
340
341 return( ret );
342}
343
344/*
345 * W-1 function as defined in RFC 3394 section 2.2.2
346 * This function assumes the following:
347 * 1. Output buffer is at least of size ( semiblocks - 1 ) * KW_SEMIBLOCK_LENGTH.
348 * 2. The input buffer is of size semiblocks * KW_SEMIBLOCK_LENGTH.
349 * 3. Minimal number of semiblocks is 3.
350 * 4. A is a buffer to hold the first semiblock of the input buffer.
351 */
353 const unsigned char *input, size_t semiblocks,
354 unsigned char A[KW_SEMIBLOCK_LENGTH],
355 unsigned char *output, size_t* out_len )
356{
357 int ret = 0;
358 const size_t s = 6 * ( semiblocks - 1 );
359 size_t olen;
360 uint64_t t = 0;
361 unsigned char outbuff[KW_SEMIBLOCK_LENGTH * 2];
362 unsigned char inbuff[KW_SEMIBLOCK_LENGTH * 2];
363 unsigned char *R = NULL;
364 *out_len = 0;
365
366 if( semiblocks < MIN_SEMIBLOCKS_COUNT )
367 {
369 }
370
371 memcpy( A, input, KW_SEMIBLOCK_LENGTH );
372 memmove( output, input + KW_SEMIBLOCK_LENGTH, ( semiblocks - 1 ) * KW_SEMIBLOCK_LENGTH );
373 R = output + ( semiblocks - 2 ) * KW_SEMIBLOCK_LENGTH;
374
375 /* Calculate intermediate values */
376 for( t = s; t >= 1; t-- )
377 {
378 calc_a_xor_t( A, t );
379
380 memcpy( inbuff, A, KW_SEMIBLOCK_LENGTH );
381 memcpy( inbuff + KW_SEMIBLOCK_LENGTH, R, KW_SEMIBLOCK_LENGTH );
382
383 ret = mbedtls_cipher_update( &ctx->cipher_ctx,
384 inbuff, 16, outbuff, &olen );
385 if( ret != 0 )
386 goto cleanup;
387
388 memcpy( A, outbuff, KW_SEMIBLOCK_LENGTH );
389
390 /* Set R as LSB64 of outbuff */
391 memcpy( R, outbuff + KW_SEMIBLOCK_LENGTH, KW_SEMIBLOCK_LENGTH );
392
393 if( R == output )
394 R = output + ( semiblocks - 2 ) * KW_SEMIBLOCK_LENGTH;
395 else
396 R -= KW_SEMIBLOCK_LENGTH;
397 }
398
399 *out_len = ( semiblocks - 1 ) * KW_SEMIBLOCK_LENGTH;
400
401cleanup:
402 if( ret != 0)
403 memset( output, 0, ( semiblocks - 1 ) * KW_SEMIBLOCK_LENGTH );
404 mbedtls_platform_zeroize( inbuff, sizeof( inbuff ) );
405 mbedtls_platform_zeroize( outbuff, sizeof( outbuff ) );
406
407 return( ret );
408}
409
410/*
411 * KW-AD as defined in SP 800-38F section 6.2
412 * KWP-AD as defined in SP 800-38F section 6.3
413 */
416 const unsigned char *input, size_t in_len,
417 unsigned char *output, size_t *out_len, size_t out_size )
418{
419 int ret = 0;
420 size_t i, olen;
421 unsigned char A[KW_SEMIBLOCK_LENGTH];
422 unsigned char diff, bad_padding = 0;
423
424 *out_len = 0;
425 if( out_size < in_len - KW_SEMIBLOCK_LENGTH )
426 {
428 }
429
430 if( mode == MBEDTLS_KW_MODE_KW )
431 {
432 /*
433 * According to SP 800-38F Table 1, the ciphertext length for KW
434 * must be between 3 to 2^54 semiblocks inclusive.
435 */
436 if( in_len < 24 ||
437#if SIZE_MAX > 0x200000000000000
438 in_len > 0x200000000000000 ||
439#endif
440 in_len % KW_SEMIBLOCK_LENGTH != 0 )
441 {
443 }
444
445 ret = unwrap( ctx, input, in_len / KW_SEMIBLOCK_LENGTH,
446 A, output, out_len );
447 if( ret != 0 )
448 goto cleanup;
449
450 /* Check ICV in "constant-time" */
451 diff = mbedtls_nist_kw_safer_memcmp( NIST_KW_ICV1, A, KW_SEMIBLOCK_LENGTH );
452
453 if( diff != 0 )
454 {
456 goto cleanup;
457 }
458
459 }
460 else if( mode == MBEDTLS_KW_MODE_KWP )
461 {
462 size_t padlen = 0;
463 uint32_t Plen;
464 /*
465 * According to SP 800-38F Table 1, the ciphertext length for KWP
466 * must be between 2 to 2^29 semiblocks inclusive.
467 */
468 if( in_len < KW_SEMIBLOCK_LENGTH * 2 ||
469#if SIZE_MAX > 0x100000000
470 in_len > 0x100000000 ||
471#endif
472 in_len % KW_SEMIBLOCK_LENGTH != 0 )
473 {
475 }
476
477 if( in_len == KW_SEMIBLOCK_LENGTH * 2 )
478 {
479 unsigned char outbuff[KW_SEMIBLOCK_LENGTH * 2];
480 ret = mbedtls_cipher_update( &ctx->cipher_ctx,
481 input, 16, outbuff, &olen );
482 if( ret != 0 )
483 goto cleanup;
484
485 memcpy( A, outbuff, KW_SEMIBLOCK_LENGTH );
486 memcpy( output, outbuff + KW_SEMIBLOCK_LENGTH, KW_SEMIBLOCK_LENGTH );
487 mbedtls_platform_zeroize( outbuff, sizeof( outbuff ) );
488 *out_len = KW_SEMIBLOCK_LENGTH;
489 }
490 else
491 {
492 /* in_len >= KW_SEMIBLOCK_LENGTH * 3 */
493 ret = unwrap( ctx, input, in_len / KW_SEMIBLOCK_LENGTH,
494 A, output, out_len );
495 if( ret != 0 )
496 goto cleanup;
497 }
498
499 /* Check ICV in "constant-time" */
500 diff = mbedtls_nist_kw_safer_memcmp( NIST_KW_ICV2, A, KW_SEMIBLOCK_LENGTH / 2 );
501
502 if( diff != 0 )
503 {
505 }
506
507 GET_UINT32_BE( Plen, A, KW_SEMIBLOCK_LENGTH / 2 );
508
509 /*
510 * Plen is the length of the plaintext, when the input is valid.
511 * If Plen is larger than the plaintext and padding, padlen will be
512 * larger than 8, because of the type wrap around.
513 */
514 padlen = in_len - KW_SEMIBLOCK_LENGTH - Plen;
515 if ( padlen > 7 )
516 {
517 padlen &= 7;
519 }
520
521 /* Check padding in "constant-time" */
522 for( diff = 0, i = 0; i < KW_SEMIBLOCK_LENGTH; i++ )
523 {
524 if( i >= KW_SEMIBLOCK_LENGTH - padlen )
525 diff |= output[*out_len - KW_SEMIBLOCK_LENGTH + i];
526 else
527 bad_padding |= output[*out_len - KW_SEMIBLOCK_LENGTH + i];
528 }
529
530 if( diff != 0 )
531 {
533 }
534
535 if( ret != 0 )
536 {
537 goto cleanup;
538 }
539 memset( output + Plen, 0, padlen );
540 *out_len = Plen;
541 }
542 else
543 {
545 goto cleanup;
546 }
547
548cleanup:
549 if( ret != 0 )
550 {
551 memset( output, 0, *out_len );
552 *out_len = 0;
553 }
554
555 mbedtls_platform_zeroize( &bad_padding, sizeof( bad_padding) );
556 mbedtls_platform_zeroize( &diff, sizeof( diff ) );
557 mbedtls_platform_zeroize( A, sizeof( A ) );
558
559 return( ret );
560}
561
562#endif /* !MBEDTLS_NIST_KW_ALT */
563
564#if defined(MBEDTLS_SELF_TEST) && defined(MBEDTLS_AES_C)
565
566#define KW_TESTS 3
567
568/*
569 * Test vectors taken from NIST
570 * https://csrc.nist.gov/Projects/Cryptographic-Algorithm-Validation-Program/CAVP-TESTING-BLOCK-CIPHER-MODES#KW
571 */
572static const unsigned int key_len[KW_TESTS] = { 16, 24, 32 };
573
574static const unsigned char kw_key[KW_TESTS][32] = {
575 { 0x75, 0x75, 0xda, 0x3a, 0x93, 0x60, 0x7c, 0xc2,
576 0xbf, 0xd8, 0xce, 0xc7, 0xaa, 0xdf, 0xd9, 0xa6 },
577 { 0x2d, 0x85, 0x26, 0x08, 0x1d, 0x02, 0xfb, 0x5b,
578 0x85, 0xf6, 0x9a, 0xc2, 0x86, 0xec, 0xd5, 0x7d,
579 0x40, 0xdf, 0x5d, 0xf3, 0x49, 0x47, 0x44, 0xd3 },
580 { 0x11, 0x2a, 0xd4, 0x1b, 0x48, 0x56, 0xc7, 0x25,
581 0x4a, 0x98, 0x48, 0xd3, 0x0f, 0xdd, 0x78, 0x33,
582 0x5b, 0x03, 0x9a, 0x48, 0xa8, 0x96, 0x2c, 0x4d,
583 0x1c, 0xb7, 0x8e, 0xab, 0xd5, 0xda, 0xd7, 0x88 }
584};
585
586static const unsigned char kw_msg[KW_TESTS][40] = {
587 { 0x42, 0x13, 0x6d, 0x3c, 0x38, 0x4a, 0x3e, 0xea,
588 0xc9, 0x5a, 0x06, 0x6f, 0xd2, 0x8f, 0xed, 0x3f },
589 { 0x95, 0xc1, 0x1b, 0xf5, 0x35, 0x3a, 0xfe, 0xdb,
590 0x98, 0xfd, 0xd6, 0xc8, 0xca, 0x6f, 0xdb, 0x6d,
591 0xa5, 0x4b, 0x74, 0xb4, 0x99, 0x0f, 0xdc, 0x45,
592 0xc0, 0x9d, 0x15, 0x8f, 0x51, 0xce, 0x62, 0x9d,
593 0xe2, 0xaf, 0x26, 0xe3, 0x25, 0x0e, 0x6b, 0x4c },
594 { 0x1b, 0x20, 0xbf, 0x19, 0x90, 0xb0, 0x65, 0xd7,
595 0x98, 0xe1, 0xb3, 0x22, 0x64, 0xad, 0x50, 0xa8,
596 0x74, 0x74, 0x92, 0xba, 0x09, 0xa0, 0x4d, 0xd1 }
597};
598
599static const size_t kw_msg_len[KW_TESTS] = { 16, 40, 24 };
600static const size_t kw_out_len[KW_TESTS] = { 24, 48, 32 };
601static const unsigned char kw_res[KW_TESTS][48] = {
602 { 0x03, 0x1f, 0x6b, 0xd7, 0xe6, 0x1e, 0x64, 0x3d,
603 0xf6, 0x85, 0x94, 0x81, 0x6f, 0x64, 0xca, 0xa3,
604 0xf5, 0x6f, 0xab, 0xea, 0x25, 0x48, 0xf5, 0xfb },
605 { 0x44, 0x3c, 0x6f, 0x15, 0x09, 0x83, 0x71, 0x91,
606 0x3e, 0x5c, 0x81, 0x4c, 0xa1, 0xa0, 0x42, 0xec,
607 0x68, 0x2f, 0x7b, 0x13, 0x6d, 0x24, 0x3a, 0x4d,
608 0x6c, 0x42, 0x6f, 0xc6, 0x97, 0x15, 0x63, 0xe8,
609 0xa1, 0x4a, 0x55, 0x8e, 0x09, 0x64, 0x16, 0x19,
610 0xbf, 0x03, 0xfc, 0xaf, 0x90, 0xb1, 0xfc, 0x2d },
611 { 0xba, 0x8a, 0x25, 0x9a, 0x47, 0x1b, 0x78, 0x7d,
612 0xd5, 0xd5, 0x40, 0xec, 0x25, 0xd4, 0x3d, 0x87,
613 0x20, 0x0f, 0xda, 0xdc, 0x6d, 0x1f, 0x05, 0xd9,
614 0x16, 0x58, 0x4f, 0xa9, 0xf6, 0xcb, 0xf5, 0x12 }
615};
616
617static const unsigned char kwp_key[KW_TESTS][32] = {
618 { 0x78, 0x65, 0xe2, 0x0f, 0x3c, 0x21, 0x65, 0x9a,
619 0xb4, 0x69, 0x0b, 0x62, 0x9c, 0xdf, 0x3c, 0xc4 },
620 { 0xf5, 0xf8, 0x96, 0xa3, 0xbd, 0x2f, 0x4a, 0x98,
621 0x23, 0xef, 0x16, 0x2b, 0x00, 0xb8, 0x05, 0xd7,
622 0xde, 0x1e, 0xa4, 0x66, 0x26, 0x96, 0xa2, 0x58 },
623 { 0x95, 0xda, 0x27, 0x00, 0xca, 0x6f, 0xd9, 0xa5,
624 0x25, 0x54, 0xee, 0x2a, 0x8d, 0xf1, 0x38, 0x6f,
625 0x5b, 0x94, 0xa1, 0xa6, 0x0e, 0xd8, 0xa4, 0xae,
626 0xf6, 0x0a, 0x8d, 0x61, 0xab, 0x5f, 0x22, 0x5a }
627};
628
629static const unsigned char kwp_msg[KW_TESTS][31] = {
630 { 0xbd, 0x68, 0x43, 0xd4, 0x20, 0x37, 0x8d, 0xc8,
631 0x96 },
632 { 0x6c, 0xcd, 0xd5, 0x85, 0x18, 0x40, 0x97, 0xeb,
633 0xd5, 0xc3, 0xaf, 0x3e, 0x47, 0xd0, 0x2c, 0x19,
634 0x14, 0x7b, 0x4d, 0x99, 0x5f, 0x96, 0x43, 0x66,
635 0x91, 0x56, 0x75, 0x8c, 0x13, 0x16, 0x8f },
636 { 0xd1 }
637};
638static const size_t kwp_msg_len[KW_TESTS] = { 9, 31, 1 };
639
640static const unsigned char kwp_res[KW_TESTS][48] = {
641 { 0x41, 0xec, 0xa9, 0x56, 0xd4, 0xaa, 0x04, 0x7e,
642 0xb5, 0xcf, 0x4e, 0xfe, 0x65, 0x96, 0x61, 0xe7,
643 0x4d, 0xb6, 0xf8, 0xc5, 0x64, 0xe2, 0x35, 0x00 },
644 { 0x4e, 0x9b, 0xc2, 0xbc, 0xbc, 0x6c, 0x1e, 0x13,
645 0xd3, 0x35, 0xbc, 0xc0, 0xf7, 0x73, 0x6a, 0x88,
646 0xfa, 0x87, 0x53, 0x66, 0x15, 0xbb, 0x8e, 0x63,
647 0x8b, 0xcc, 0x81, 0x66, 0x84, 0x68, 0x17, 0x90,
648 0x67, 0xcf, 0xa9, 0x8a, 0x9d, 0x0e, 0x33, 0x26 },
649 { 0x06, 0xba, 0x7a, 0xe6, 0xf3, 0x24, 0x8c, 0xfd,
650 0xcf, 0x26, 0x75, 0x07, 0xfa, 0x00, 0x1b, 0xc4 }
651};
652static const size_t kwp_out_len[KW_TESTS] = { 24, 40, 16 };
653
654int mbedtls_nist_kw_self_test( int verbose )
655{
657 unsigned char out[48];
658 size_t olen;
659 int i;
660 int ret = 0;
662
663 for( i = 0; i < KW_TESTS; i++ )
664 {
665 if( verbose != 0 )
666 mbedtls_printf( " KW-AES-%u ", (unsigned int) key_len[i] * 8 );
667
669 kw_key[i], key_len[i] * 8, 1 );
670 if( ret != 0 )
671 {
672 if( verbose != 0 )
673 mbedtls_printf( " KW: setup failed " );
674
675 goto end;
676 }
677
679 kw_msg_len[i], out, &olen, sizeof( out ) );
680 if( ret != 0 || kw_out_len[i] != olen ||
681 memcmp( out, kw_res[i], kw_out_len[i] ) != 0 )
682 {
683 if( verbose != 0 )
684 mbedtls_printf( "failed. ");
685
686 ret = 1;
687 goto end;
688 }
689
691 kw_key[i], key_len[i] * 8, 0 ) )
692 != 0 )
693 {
694 if( verbose != 0 )
695 mbedtls_printf( " KW: setup failed ");
696
697 goto end;
698 }
699
701 out, olen, out, &olen, sizeof( out ) );
702
703 if( ret != 0 || olen != kw_msg_len[i] ||
704 memcmp( out, kw_msg[i], kw_msg_len[i] ) != 0 )
705 {
706 if( verbose != 0 )
707 mbedtls_printf( "failed\n" );
708
709 ret = 1;
710 goto end;
711 }
712
713 if( verbose != 0 )
714 mbedtls_printf( " passed\n" );
715 }
716
717 for( i = 0; i < KW_TESTS; i++ )
718 {
719 olen = sizeof( out );
720 if( verbose != 0 )
721 mbedtls_printf( " KWP-AES-%u ", (unsigned int) key_len[i] * 8 );
722
724 key_len[i] * 8, 1 );
725 if( ret != 0 )
726 {
727 if( verbose != 0 )
728 mbedtls_printf( " KWP: setup failed " );
729
730 goto end;
731 }
733 kwp_msg_len[i], out, &olen, sizeof( out ) );
734
735 if( ret != 0 || kwp_out_len[i] != olen ||
736 memcmp( out, kwp_res[i], kwp_out_len[i] ) != 0 )
737 {
738 if( verbose != 0 )
739 mbedtls_printf( "failed. ");
740
741 ret = 1;
742 goto end;
743 }
744
746 kwp_key[i], key_len[i] * 8, 0 ) )
747 != 0 )
748 {
749 if( verbose != 0 )
750 mbedtls_printf( " KWP: setup failed ");
751
752 goto end;
753 }
754
756 olen, out, &olen, sizeof( out ) );
757
758 if( ret != 0 || olen != kwp_msg_len[i] ||
759 memcmp( out, kwp_msg[i], kwp_msg_len[i] ) != 0 )
760 {
761 if( verbose != 0 )
762 mbedtls_printf( "failed. ");
763
764 ret = 1;
765 goto end;
766 }
767
768 if( verbose != 0 )
769 mbedtls_printf( " passed\n" );
770 }
771end:
773
774 if( verbose != 0 )
775 mbedtls_printf( "\n" );
776
777 return( ret );
778}
779
780#endif /* MBEDTLS_SELF_TEST && MBEDTLS_AES_C */
781
782#endif /* MBEDTLS_NIST_KW_C */
int memcmp(void *Buffer1, void *Buffer2, ACPI_SIZE Count)
Definition: utclib.c:112
int mbedtls_cipher_setup(mbedtls_cipher_context_t *ctx, const mbedtls_cipher_info_t *cipher_info)
This function initializes and fills the cipher-context structure with the appropriate values....
int mbedtls_cipher_setkey(mbedtls_cipher_context_t *ctx, const unsigned char *key, int key_bitlen, const mbedtls_operation_t operation)
This function sets the key to use with the given context.
#define MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
Definition: cipher.h:84
#define MBEDTLS_ERR_CIPHER_AUTH_FAILED
Definition: cipher.h:89
#define MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
Definition: cipher.h:85
const mbedtls_cipher_info_t * mbedtls_cipher_info_from_values(const mbedtls_cipher_id_t cipher_id, int key_bitlen, const mbedtls_cipher_mode_t mode)
This function retrieves the cipher-information structure associated with the given cipher ID,...
void mbedtls_cipher_free(mbedtls_cipher_context_t *ctx)
This function frees and clears the cipher-specific context of ctx. Freeing ctx itself remains the res...
int mbedtls_cipher_update(mbedtls_cipher_context_t *ctx, const unsigned char *input, size_t ilen, unsigned char *output, size_t *olen)
The generic cipher update function. It encrypts or decrypts using the given cipher context....
@ MBEDTLS_DECRYPT
Definition: cipher.h:233
@ MBEDTLS_ENCRYPT
Definition: cipher.h:234
@ MBEDTLS_MODE_ECB
Definition: cipher.h:209
mbedtls_cipher_id_t
Supported cipher types.
Definition: cipher.h:109
@ MBEDTLS_CIPHER_ID_AES
Definition: cipher.h:112
Definition: ehthrow.cxx:93
Definition: ehthrow.cxx:54
#define NULL
Definition: types.h:112
UINT32 uint32_t
Definition: types.h:75
UINT64 uint64_t
Definition: types.h:77
static void unwrap(TOOLBAR_INFO *info)
Definition: toolbar.c:5249
static void cleanup(void)
Definition: main.c:1335
GLint GLint GLint GLint GLint x
Definition: gl.h:1548
GLdouble s
Definition: gl.h:2039
GLint GLint GLint GLint GLint GLint y
Definition: gl.h:1548
GLuint GLuint end
Definition: gl.h:1545
GLdouble GLdouble t
Definition: gl.h:2047
GLdouble n
Definition: glext.h:7729
GLboolean GLboolean GLboolean b
Definition: glext.h:6204
GLenum mode
Definition: glext.h:6217
GLboolean GLboolean GLboolean GLboolean a
Definition: glext.h:6204
GLenum GLenum GLenum input
Definition: glext.h:9031
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define SIZE_MAX
Definition: limits.h:75
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
#define memmove(s1, s2, n)
Definition: mkisofs.h:881
static DATA_BLOB cipher
Definition: protectdata.c:38
static HANDLE PIO_APC_ROUTINE PVOID PIO_STATUS_BLOCK ULONG PVOID ULONG PVOID ULONG out_size
Definition: file.c:100
This file provides an API for key wrapping (KW) and key wrapping with padding (KWP) as defined in NIS...
int mbedtls_nist_kw_setkey(mbedtls_nist_kw_context *ctx, mbedtls_cipher_id_t cipher, const unsigned char *key, unsigned int keybits, const int is_wrap)
This function initializes the key wrapping context set in the ctx parameter and sets the encryption k...
int mbedtls_nist_kw_wrap(mbedtls_nist_kw_context *ctx, mbedtls_nist_kw_mode_t mode, const unsigned char *input, size_t in_len, unsigned char *output, size_t *out_len, size_t out_size)
This function encrypts a buffer using key wrapping.
int mbedtls_nist_kw_unwrap(mbedtls_nist_kw_context *ctx, mbedtls_nist_kw_mode_t mode, const unsigned char *input, size_t in_len, unsigned char *output, size_t *out_len, size_t out_size)
This function decrypts a buffer using key wrapping.
mbedtls_nist_kw_mode_t
Definition: nist_kw.h:78
@ MBEDTLS_KW_MODE_KW
Definition: nist_kw.h:79
@ MBEDTLS_KW_MODE_KWP
Definition: nist_kw.h:80
void mbedtls_nist_kw_free(mbedtls_nist_kw_context *ctx)
This function releases and clears the specified key wrapping context and underlying cipher sub-contex...
void mbedtls_nist_kw_init(mbedtls_nist_kw_context *ctx)
This function initializes the specified key wrapping context to make references valid and prepare the...
void mbedtls_platform_zeroize(void *buf, size_t len)
Securely zeroize a buffer.
Definition: platform_util.c:98
Common and shared functions used by multiple modules in the Mbed TLS library.
static FILE * out
Definition: regtests2xml.c:44
#define verbose
Definition: rosglue.h:36
Configuration options (set of defines)
This file contains the definitions and functions of the Mbed TLS platform abstraction layer.
#define R2(v, w, x, y, z, i)
Definition: sha1.c:37
#define memset(x, y, z)
Definition: compat.h:39
#define R(b, x)
Definition: sha2.c:134
Definition: copy.c:22
unsigned int block_size
Definition: cipher.h:299
The key wrapping context-type definition. The key wrapping context is passed to the APIs called.
Definition: nist_kw.h:94
#define mbedtls_printf
Definition: timing.c:57
int ret