38 #if defined(POLARSSL_GCM_C)
42 #if defined(POLARSSL_AESNI_C)
50 #define GET_UINT32_BE(n,b,i) \
52 (n) = ( (uint32_t) (b)[(i) ] << 24 ) \
53 | ( (uint32_t) (b)[(i) + 1] << 16 ) \
54 | ( (uint32_t) (b)[(i) + 2] << 8 ) \
55 | ( (uint32_t) (b)[(i) + 3] ); \
60 #define PUT_UINT32_BE(n,b,i) \
62 (b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
63 (b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
64 (b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
65 (b)[(i) + 3] = (unsigned char) ( (n) ); \
90 GET_UINT32_BE( hi, h, 0 );
91 GET_UINT32_BE( lo, h, 4 );
92 vh = (uint64_t) hi << 32 | lo;
94 GET_UINT32_BE( hi, h, 8 );
95 GET_UINT32_BE( lo, h, 12 );
96 vl = (uint64_t) hi << 32 | lo;
102 #if defined(POLARSSL_AESNI_C) && defined(POLARSSL_HAVE_X86_64)
112 for( i = 4; i > 0; i >>= 1 )
114 uint32_t T = ( vl & 1 ) * 0xe1000000U;
115 vl = ( vh << 63 ) | ( vl >> 1 );
116 vh = ( vh >> 1 ) ^ ( (uint64_t) T << 32);
122 for (i = 2; i < 16; i <<= 1 )
124 uint64_t *HiL = ctx->
HL + i, *HiH = ctx->
HH + i;
127 for( j = 1; j < i; j++ )
129 HiH[j] = vh ^ ctx->
HH[j];
130 HiL[j] = vl ^ ctx->
HL[j];
138 unsigned int keysize )
146 if( cipher_info == NULL )
161 if( ( ret = gcm_gen_table( ctx ) ) != 0 )
172 static const uint64_t last4[16] =
174 0x0000, 0x1c20, 0x3840, 0x2460,
175 0x7080, 0x6ca0, 0x48c0, 0x54e0,
176 0xe100, 0xfd20, 0xd940, 0xc560,
177 0x9180, 0x8da0, 0xa9c0, 0xb5e0
184 static void gcm_mult(
gcm_context *ctx,
const unsigned char x[16],
185 unsigned char output[16] )
189 unsigned char lo, hi, rem;
192 #if defined(POLARSSL_AESNI_C) && defined(POLARSSL_HAVE_X86_64)
196 PUT_UINT32_BE( ctx->
HH[8] >> 32, h, 0 );
197 PUT_UINT32_BE( ctx->
HH[8], h, 4 );
198 PUT_UINT32_BE( ctx->
HL[8] >> 32, h, 8 );
199 PUT_UINT32_BE( ctx->
HL[8], h, 12 );
201 aesni_gcm_mult( output, x, h );
206 memset( z, 0x00, 16 );
214 for( i = 15; i >= 0; i-- )
221 rem = (
unsigned char) zl & 0xf;
222 zl = ( zh << 60 ) | ( zl >> 4 );
224 zh ^= (uint64_t) last4[rem] << 48;
230 rem = (
unsigned char) zl & 0xf;
231 zl = ( zh << 60 ) | ( zl >> 4 );
233 zh ^= (uint64_t) last4[rem] << 48;
238 PUT_UINT32_BE( zh >> 32, output, 0 );
239 PUT_UINT32_BE( zh, output, 4 );
240 PUT_UINT32_BE( zl >> 32, output, 8 );
241 PUT_UINT32_BE( zl, output, 12 );
246 const unsigned char *iv,
248 const unsigned char *add,
252 unsigned char work_buf[16];
254 const unsigned char *p;
255 size_t use_len, olen = 0;
257 memset( ctx->
y, 0x00,
sizeof(ctx->
y) );
258 memset( ctx->
buf, 0x00,
sizeof(ctx->
buf) );
266 memcpy( ctx->
y, iv, iv_len );
271 memset( work_buf, 0x00, 16 );
272 PUT_UINT32_BE( iv_len * 8, work_buf, 12 );
277 use_len = ( iv_len < 16 ) ? iv_len : 16;
279 for( i = 0; i < use_len; i++ )
282 gcm_mult( ctx, ctx->
y, ctx->
y );
288 for( i = 0; i < 16; i++ )
289 ctx->
y[i] ^= work_buf[i];
291 gcm_mult( ctx, ctx->
y, ctx->
y );
304 use_len = ( add_len < 16 ) ? add_len : 16;
306 for( i = 0; i < use_len; i++ )
309 gcm_mult( ctx, ctx->
buf, ctx->
buf );
320 const unsigned char *input,
321 unsigned char *output )
324 unsigned char ectr[16];
326 const unsigned char *p;
327 unsigned char *out_p = output;
328 size_t use_len, olen = 0;
330 if( output > input && (
size_t) ( output - input ) < length )
338 use_len = ( length < 16 ) ? length : 16;
340 for( i = 16; i > 12; i-- )
341 if( ++ctx->
y[i - 1] != 0 )
350 for( i = 0; i < use_len; i++ )
354 out_p[i] = ectr[i] ^ p[i];
356 ctx->
buf[i] ^= out_p[i];
359 gcm_mult( ctx, ctx->
buf, ctx->
buf );
373 unsigned char work_buf[16];
375 uint64_t orig_len = ctx->
len * 8;
376 uint64_t orig_add_len = ctx->
add_len * 8;
384 if( orig_len || orig_add_len )
386 memset( work_buf, 0x00, 16 );
388 PUT_UINT32_BE( ( orig_add_len >> 32 ), work_buf, 0 );
389 PUT_UINT32_BE( ( orig_add_len ), work_buf, 4 );
390 PUT_UINT32_BE( ( orig_len >> 32 ), work_buf, 8 );
391 PUT_UINT32_BE( ( orig_len ), work_buf, 12 );
393 for( i = 0; i < 16; i++ )
394 ctx->
buf[i] ^= work_buf[i];
396 gcm_mult( ctx, ctx->
buf, ctx->
buf );
398 for( i = 0; i < tag_len; i++ )
399 tag[i] ^= ctx->
buf[i];
408 const unsigned char *iv,
410 const unsigned char *add,
412 const unsigned char *input,
413 unsigned char *output,
419 if( ( ret =
gcm_starts( ctx, mode, iv, iv_len, add, add_len ) ) != 0 )
422 if( ( ret =
gcm_update( ctx, length, input, output ) ) != 0 )
425 if( ( ret =
gcm_finish( ctx, tag, tag_len ) ) != 0 )
433 const unsigned char *iv,
435 const unsigned char *add,
437 const unsigned char *tag,
439 const unsigned char *input,
440 unsigned char *output )
443 unsigned char check_tag[16];
448 iv, iv_len, add, add_len,
449 input, output, tag_len, check_tag ) ) != 0 )
455 for( diff = 0, i = 0; i < tag_len; i++ )
456 diff |= tag[i] ^ check_tag[i];
460 memset( output, 0, length );
473 #if defined(POLARSSL_SELF_TEST) && defined(POLARSSL_AES_C)
484 int key_index[MAX_TESTS] =
485 { 0, 0, 1, 1, 1, 1 };
487 unsigned char key[MAX_TESTS][32] =
489 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
490 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
491 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
492 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
493 { 0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c,
494 0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08,
495 0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c,
496 0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08 },
499 size_t iv_len[MAX_TESTS] =
500 { 12, 12, 12, 12, 8, 60 };
502 int iv_index[MAX_TESTS] =
503 { 0, 0, 1, 1, 1, 2 };
505 unsigned char iv[MAX_TESTS][64] =
507 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
508 0x00, 0x00, 0x00, 0x00 },
509 { 0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce, 0xdb, 0xad,
510 0xde, 0xca, 0xf8, 0x88 },
511 { 0x93, 0x13, 0x22, 0x5d, 0xf8, 0x84, 0x06, 0xe5,
512 0x55, 0x90, 0x9c, 0x5a, 0xff, 0x52, 0x69, 0xaa,
513 0x6a, 0x7a, 0x95, 0x38, 0x53, 0x4f, 0x7d, 0xa1,
514 0xe4, 0xc3, 0x03, 0xd2, 0xa3, 0x18, 0xa7, 0x28,
515 0xc3, 0xc0, 0xc9, 0x51, 0x56, 0x80, 0x95, 0x39,
516 0xfc, 0xf0, 0xe2, 0x42, 0x9a, 0x6b, 0x52, 0x54,
517 0x16, 0xae, 0xdb, 0xf5, 0xa0, 0xde, 0x6a, 0x57,
518 0xa6, 0x37, 0xb3, 0x9b },
521 size_t add_len[MAX_TESTS] =
522 { 0, 0, 0, 20, 20, 20 };
524 int add_index[MAX_TESTS] =
525 { 0, 0, 0, 1, 1, 1 };
527 unsigned char additional[MAX_TESTS][64] =
530 { 0xfe, 0xed, 0xfa, 0xce, 0xde, 0xad, 0xbe, 0xef,
531 0xfe, 0xed, 0xfa, 0xce, 0xde, 0xad, 0xbe, 0xef,
532 0xab, 0xad, 0xda, 0xd2 },
535 size_t pt_len[MAX_TESTS] =
536 { 0, 16, 64, 60, 60, 60 };
538 int pt_index[MAX_TESTS] =
539 { 0, 0, 1, 1, 1, 1 };
541 unsigned char pt[MAX_TESTS][64] =
543 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
544 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
545 { 0xd9, 0x31, 0x32, 0x25, 0xf8, 0x84, 0x06, 0xe5,
546 0xa5, 0x59, 0x09, 0xc5, 0xaf, 0xf5, 0x26, 0x9a,
547 0x86, 0xa7, 0xa9, 0x53, 0x15, 0x34, 0xf7, 0xda,
548 0x2e, 0x4c, 0x30, 0x3d, 0x8a, 0x31, 0x8a, 0x72,
549 0x1c, 0x3c, 0x0c, 0x95, 0x95, 0x68, 0x09, 0x53,
550 0x2f, 0xcf, 0x0e, 0x24, 0x49, 0xa6, 0xb5, 0x25,
551 0xb1, 0x6a, 0xed, 0xf5, 0xaa, 0x0d, 0xe6, 0x57,
552 0xba, 0x63, 0x7b, 0x39, 0x1a, 0xaf, 0xd2, 0x55 },
555 unsigned char ct[MAX_TESTS * 3][64] =
558 { 0x03, 0x88, 0xda, 0xce, 0x60, 0xb6, 0xa3, 0x92,
559 0xf3, 0x28, 0xc2, 0xb9, 0x71, 0xb2, 0xfe, 0x78 },
560 { 0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24,
561 0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c,
562 0xe3, 0xaa, 0x21, 0x2f, 0x2c, 0x02, 0xa4, 0xe0,
563 0x35, 0xc1, 0x7e, 0x23, 0x29, 0xac, 0xa1, 0x2e,
564 0x21, 0xd5, 0x14, 0xb2, 0x54, 0x66, 0x93, 0x1c,
565 0x7d, 0x8f, 0x6a, 0x5a, 0xac, 0x84, 0xaa, 0x05,
566 0x1b, 0xa3, 0x0b, 0x39, 0x6a, 0x0a, 0xac, 0x97,
567 0x3d, 0x58, 0xe0, 0x91, 0x47, 0x3f, 0x59, 0x85 },
568 { 0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24,
569 0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c,
570 0xe3, 0xaa, 0x21, 0x2f, 0x2c, 0x02, 0xa4, 0xe0,
571 0x35, 0xc1, 0x7e, 0x23, 0x29, 0xac, 0xa1, 0x2e,
572 0x21, 0xd5, 0x14, 0xb2, 0x54, 0x66, 0x93, 0x1c,
573 0x7d, 0x8f, 0x6a, 0x5a, 0xac, 0x84, 0xaa, 0x05,
574 0x1b, 0xa3, 0x0b, 0x39, 0x6a, 0x0a, 0xac, 0x97,
575 0x3d, 0x58, 0xe0, 0x91 },
576 { 0x61, 0x35, 0x3b, 0x4c, 0x28, 0x06, 0x93, 0x4a,
577 0x77, 0x7f, 0xf5, 0x1f, 0xa2, 0x2a, 0x47, 0x55,
578 0x69, 0x9b, 0x2a, 0x71, 0x4f, 0xcd, 0xc6, 0xf8,
579 0x37, 0x66, 0xe5, 0xf9, 0x7b, 0x6c, 0x74, 0x23,
580 0x73, 0x80, 0x69, 0x00, 0xe4, 0x9f, 0x24, 0xb2,
581 0x2b, 0x09, 0x75, 0x44, 0xd4, 0x89, 0x6b, 0x42,
582 0x49, 0x89, 0xb5, 0xe1, 0xeb, 0xac, 0x0f, 0x07,
583 0xc2, 0x3f, 0x45, 0x98 },
584 { 0x8c, 0xe2, 0x49, 0x98, 0x62, 0x56, 0x15, 0xb6,
585 0x03, 0xa0, 0x33, 0xac, 0xa1, 0x3f, 0xb8, 0x94,
586 0xbe, 0x91, 0x12, 0xa5, 0xc3, 0xa2, 0x11, 0xa8,
587 0xba, 0x26, 0x2a, 0x3c, 0xca, 0x7e, 0x2c, 0xa7,
588 0x01, 0xe4, 0xa9, 0xa4, 0xfb, 0xa4, 0x3c, 0x90,
589 0xcc, 0xdc, 0xb2, 0x81, 0xd4, 0x8c, 0x7c, 0x6f,
590 0xd6, 0x28, 0x75, 0xd2, 0xac, 0xa4, 0x17, 0x03,
591 0x4c, 0x34, 0xae, 0xe5 },
593 { 0x98, 0xe7, 0x24, 0x7c, 0x07, 0xf0, 0xfe, 0x41,
594 0x1c, 0x26, 0x7e, 0x43, 0x84, 0xb0, 0xf6, 0x00 },
595 { 0x39, 0x80, 0xca, 0x0b, 0x3c, 0x00, 0xe8, 0x41,
596 0xeb, 0x06, 0xfa, 0xc4, 0x87, 0x2a, 0x27, 0x57,
597 0x85, 0x9e, 0x1c, 0xea, 0xa6, 0xef, 0xd9, 0x84,
598 0x62, 0x85, 0x93, 0xb4, 0x0c, 0xa1, 0xe1, 0x9c,
599 0x7d, 0x77, 0x3d, 0x00, 0xc1, 0x44, 0xc5, 0x25,
600 0xac, 0x61, 0x9d, 0x18, 0xc8, 0x4a, 0x3f, 0x47,
601 0x18, 0xe2, 0x44, 0x8b, 0x2f, 0xe3, 0x24, 0xd9,
602 0xcc, 0xda, 0x27, 0x10, 0xac, 0xad, 0xe2, 0x56 },
603 { 0x39, 0x80, 0xca, 0x0b, 0x3c, 0x00, 0xe8, 0x41,
604 0xeb, 0x06, 0xfa, 0xc4, 0x87, 0x2a, 0x27, 0x57,
605 0x85, 0x9e, 0x1c, 0xea, 0xa6, 0xef, 0xd9, 0x84,
606 0x62, 0x85, 0x93, 0xb4, 0x0c, 0xa1, 0xe1, 0x9c,
607 0x7d, 0x77, 0x3d, 0x00, 0xc1, 0x44, 0xc5, 0x25,
608 0xac, 0x61, 0x9d, 0x18, 0xc8, 0x4a, 0x3f, 0x47,
609 0x18, 0xe2, 0x44, 0x8b, 0x2f, 0xe3, 0x24, 0xd9,
610 0xcc, 0xda, 0x27, 0x10 },
611 { 0x0f, 0x10, 0xf5, 0x99, 0xae, 0x14, 0xa1, 0x54,
612 0xed, 0x24, 0xb3, 0x6e, 0x25, 0x32, 0x4d, 0xb8,
613 0xc5, 0x66, 0x63, 0x2e, 0xf2, 0xbb, 0xb3, 0x4f,
614 0x83, 0x47, 0x28, 0x0f, 0xc4, 0x50, 0x70, 0x57,
615 0xfd, 0xdc, 0x29, 0xdf, 0x9a, 0x47, 0x1f, 0x75,
616 0xc6, 0x65, 0x41, 0xd4, 0xd4, 0xda, 0xd1, 0xc9,
617 0xe9, 0x3a, 0x19, 0xa5, 0x8e, 0x8b, 0x47, 0x3f,
618 0xa0, 0xf0, 0x62, 0xf7 },
619 { 0xd2, 0x7e, 0x88, 0x68, 0x1c, 0xe3, 0x24, 0x3c,
620 0x48, 0x30, 0x16, 0x5a, 0x8f, 0xdc, 0xf9, 0xff,
621 0x1d, 0xe9, 0xa1, 0xd8, 0xe6, 0xb4, 0x47, 0xef,
622 0x6e, 0xf7, 0xb7, 0x98, 0x28, 0x66, 0x6e, 0x45,
623 0x81, 0xe7, 0x90, 0x12, 0xaf, 0x34, 0xdd, 0xd9,
624 0xe2, 0xf0, 0x37, 0x58, 0x9b, 0x29, 0x2d, 0xb3,
625 0xe6, 0x7c, 0x03, 0x67, 0x45, 0xfa, 0x22, 0xe7,
626 0xe9, 0xb7, 0x37, 0x3b },
628 { 0xce, 0xa7, 0x40, 0x3d, 0x4d, 0x60, 0x6b, 0x6e,
629 0x07, 0x4e, 0xc5, 0xd3, 0xba, 0xf3, 0x9d, 0x18 },
630 { 0x52, 0x2d, 0xc1, 0xf0, 0x99, 0x56, 0x7d, 0x07,
631 0xf4, 0x7f, 0x37, 0xa3, 0x2a, 0x84, 0x42, 0x7d,
632 0x64, 0x3a, 0x8c, 0xdc, 0xbf, 0xe5, 0xc0, 0xc9,
633 0x75, 0x98, 0xa2, 0xbd, 0x25, 0x55, 0xd1, 0xaa,
634 0x8c, 0xb0, 0x8e, 0x48, 0x59, 0x0d, 0xbb, 0x3d,
635 0xa7, 0xb0, 0x8b, 0x10, 0x56, 0x82, 0x88, 0x38,
636 0xc5, 0xf6, 0x1e, 0x63, 0x93, 0xba, 0x7a, 0x0a,
637 0xbc, 0xc9, 0xf6, 0x62, 0x89, 0x80, 0x15, 0xad },
638 { 0x52, 0x2d, 0xc1, 0xf0, 0x99, 0x56, 0x7d, 0x07,
639 0xf4, 0x7f, 0x37, 0xa3, 0x2a, 0x84, 0x42, 0x7d,
640 0x64, 0x3a, 0x8c, 0xdc, 0xbf, 0xe5, 0xc0, 0xc9,
641 0x75, 0x98, 0xa2, 0xbd, 0x25, 0x55, 0xd1, 0xaa,
642 0x8c, 0xb0, 0x8e, 0x48, 0x59, 0x0d, 0xbb, 0x3d,
643 0xa7, 0xb0, 0x8b, 0x10, 0x56, 0x82, 0x88, 0x38,
644 0xc5, 0xf6, 0x1e, 0x63, 0x93, 0xba, 0x7a, 0x0a,
645 0xbc, 0xc9, 0xf6, 0x62 },
646 { 0xc3, 0x76, 0x2d, 0xf1, 0xca, 0x78, 0x7d, 0x32,
647 0xae, 0x47, 0xc1, 0x3b, 0xf1, 0x98, 0x44, 0xcb,
648 0xaf, 0x1a, 0xe1, 0x4d, 0x0b, 0x97, 0x6a, 0xfa,
649 0xc5, 0x2f, 0xf7, 0xd7, 0x9b, 0xba, 0x9d, 0xe0,
650 0xfe, 0xb5, 0x82, 0xd3, 0x39, 0x34, 0xa4, 0xf0,
651 0x95, 0x4c, 0xc2, 0x36, 0x3b, 0xc7, 0x3f, 0x78,
652 0x62, 0xac, 0x43, 0x0e, 0x64, 0xab, 0xe4, 0x99,
653 0xf4, 0x7c, 0x9b, 0x1f },
654 { 0x5a, 0x8d, 0xef, 0x2f, 0x0c, 0x9e, 0x53, 0xf1,
655 0xf7, 0x5d, 0x78, 0x53, 0x65, 0x9e, 0x2a, 0x20,
656 0xee, 0xb2, 0xb2, 0x2a, 0xaf, 0xde, 0x64, 0x19,
657 0xa0, 0x58, 0xab, 0x4f, 0x6f, 0x74, 0x6b, 0xf4,
658 0x0f, 0xc0, 0xc3, 0xb7, 0x80, 0xf2, 0x44, 0x45,
659 0x2d, 0xa3, 0xeb, 0xf1, 0xc5, 0xd8, 0x2c, 0xde,
660 0xa2, 0x41, 0x89, 0x97, 0x20, 0x0e, 0xf8, 0x2e,
661 0x44, 0xae, 0x7e, 0x3f },
664 unsigned char tag[MAX_TESTS * 3][16] =
666 { 0x58, 0xe2, 0xfc, 0xce, 0xfa, 0x7e, 0x30, 0x61,
667 0x36, 0x7f, 0x1d, 0x57, 0xa4, 0xe7, 0x45, 0x5a },
668 { 0xab, 0x6e, 0x47, 0xd4, 0x2c, 0xec, 0x13, 0xbd,
669 0xf5, 0x3a, 0x67, 0xb2, 0x12, 0x57, 0xbd, 0xdf },
670 { 0x4d, 0x5c, 0x2a, 0xf3, 0x27, 0xcd, 0x64, 0xa6,
671 0x2c, 0xf3, 0x5a, 0xbd, 0x2b, 0xa6, 0xfa, 0xb4 },
672 { 0x5b, 0xc9, 0x4f, 0xbc, 0x32, 0x21, 0xa5, 0xdb,
673 0x94, 0xfa, 0xe9, 0x5a, 0xe7, 0x12, 0x1a, 0x47 },
674 { 0x36, 0x12, 0xd2, 0xe7, 0x9e, 0x3b, 0x07, 0x85,
675 0x56, 0x1b, 0xe1, 0x4a, 0xac, 0xa2, 0xfc, 0xcb },
676 { 0x61, 0x9c, 0xc5, 0xae, 0xff, 0xfe, 0x0b, 0xfa,
677 0x46, 0x2a, 0xf4, 0x3c, 0x16, 0x99, 0xd0, 0x50 },
678 { 0xcd, 0x33, 0xb2, 0x8a, 0xc7, 0x73, 0xf7, 0x4b,
679 0xa0, 0x0e, 0xd1, 0xf3, 0x12, 0x57, 0x24, 0x35 },
680 { 0x2f, 0xf5, 0x8d, 0x80, 0x03, 0x39, 0x27, 0xab,
681 0x8e, 0xf4, 0xd4, 0x58, 0x75, 0x14, 0xf0, 0xfb },
682 { 0x99, 0x24, 0xa7, 0xc8, 0x58, 0x73, 0x36, 0xbf,
683 0xb1, 0x18, 0x02, 0x4d, 0xb8, 0x67, 0x4a, 0x14 },
684 { 0x25, 0x19, 0x49, 0x8e, 0x80, 0xf1, 0x47, 0x8f,
685 0x37, 0xba, 0x55, 0xbd, 0x6d, 0x27, 0x61, 0x8c },
686 { 0x65, 0xdc, 0xc5, 0x7f, 0xcf, 0x62, 0x3a, 0x24,
687 0x09, 0x4f, 0xcc, 0xa4, 0x0d, 0x35, 0x33, 0xf8 },
688 { 0xdc, 0xf5, 0x66, 0xff, 0x29, 0x1c, 0x25, 0xbb,
689 0xb8, 0x56, 0x8f, 0xc3, 0xd3, 0x76, 0xa6, 0xd9 },
690 { 0x53, 0x0f, 0x8a, 0xfb, 0xc7, 0x45, 0x36, 0xb9,
691 0xa9, 0x63, 0xb4, 0xf1, 0xc4, 0xcb, 0x73, 0x8b },
692 { 0xd0, 0xd1, 0xc8, 0xa7, 0x99, 0x99, 0x6b, 0xf0,
693 0x26, 0x5b, 0x98, 0xb5, 0xd4, 0x8a, 0xb9, 0x19 },
694 { 0xb0, 0x94, 0xda, 0xc5, 0xd9, 0x34, 0x71, 0xbd,
695 0xec, 0x1a, 0x50, 0x22, 0x70, 0xe3, 0xcc, 0x6c },
696 { 0x76, 0xfc, 0x6e, 0xce, 0x0f, 0x4e, 0x17, 0x68,
697 0xcd, 0xdf, 0x88, 0x53, 0xbb, 0x2d, 0x55, 0x1b },
698 { 0x3a, 0x33, 0x7d, 0xbf, 0x46, 0xa7, 0x92, 0xc4,
699 0x5e, 0x45, 0x49, 0x13, 0xfe, 0x2e, 0xa8, 0xf2 },
700 { 0xa4, 0x4a, 0x82, 0x66, 0xee, 0x1c, 0x8e, 0xb0,
701 0xc8, 0xb5, 0xd4, 0xcf, 0x5a, 0xe9, 0xf1, 0x9a },
707 unsigned char buf[64];
708 unsigned char tag_buf[16];
712 for( j = 0; j < 3; j++ )
714 int key_len = 128 + 64 * j;
716 for( i = 0; i < MAX_TESTS; i++ )
719 printf(
" AES-GCM-%3d #%d (%s): ", key_len, i,
"enc" );
721 gcm_init( &ctx, cipher, key[key_index[i]], key_len );
725 iv[iv_index[i]], iv_len[i],
726 additional[add_index[i]], add_len[i],
727 pt[pt_index[i]], buf, 16, tag_buf );
730 memcmp( buf, ct[j * 6 + i], pt_len[i] ) != 0 ||
731 memcmp( tag_buf, tag[j * 6 + i], 16 ) != 0 )
734 printf(
"failed\n" );
742 printf(
"passed\n" );
745 printf(
" AES-GCM-%3d #%d (%s): ", key_len, i,
"dec" );
747 gcm_init( &ctx, cipher, key[key_index[i]], key_len );
751 iv[iv_index[i]], iv_len[i],
752 additional[add_index[i]], add_len[i],
753 ct[j * 6 + i], buf, 16, tag_buf );
756 memcmp( buf, pt[pt_index[i]], pt_len[i] ) != 0 ||
757 memcmp( tag_buf, tag[j * 6 + i], 16 ) != 0 )
760 printf(
"failed\n" );
768 printf(
"passed\n" );
771 printf(
" AES-GCM-%3d #%d split (%s): ", key_len, i,
"enc" );
773 gcm_init( &ctx, cipher, key[key_index[i]], key_len );
776 iv[iv_index[i]], iv_len[i],
777 additional[add_index[i]], add_len[i] );
781 printf(
"failed\n" );
788 size_t rest_len = pt_len[i] - 32;
789 ret =
gcm_update( &ctx, 32, pt[pt_index[i]], buf );
793 printf(
"failed\n" );
798 ret =
gcm_update( &ctx, rest_len, pt[pt_index[i]] + 32, buf + 32 );
802 printf(
"failed\n" );
809 ret =
gcm_update( &ctx, pt_len[i], pt[pt_index[i]], buf );
813 printf(
"failed\n" );
821 memcmp( buf, ct[j * 6 + i], pt_len[i] ) != 0 ||
822 memcmp( tag_buf, tag[j * 6 + i], 16 ) != 0 )
825 printf(
"failed\n" );
833 printf(
"passed\n" );
836 printf(
" AES-GCM-%3d #%d split (%s): ", key_len, i,
"dec" );
838 gcm_init( &ctx, cipher, key[key_index[i]], key_len );
841 iv[iv_index[i]], iv_len[i],
842 additional[add_index[i]], add_len[i] );
846 printf(
"failed\n" );
853 size_t rest_len = pt_len[i] - 32;
854 ret =
gcm_update( &ctx, 32, ct[j * 6 + i], buf );
858 printf(
"failed\n" );
863 ret =
gcm_update( &ctx, rest_len, ct[j * 6 + i] + 32, buf + 32 );
867 printf(
"failed\n" );
874 ret =
gcm_update( &ctx, pt_len[i], ct[j * 6 + i], buf );
878 printf(
"failed\n" );
886 memcmp( buf, pt[pt_index[i]], pt_len[i] ) != 0 ||
887 memcmp( tag_buf, tag[j * 6 + i], 16 ) != 0 )
890 printf(
"failed\n" );
898 printf(
"passed\n" );
int gcm_auth_decrypt(gcm_context *ctx, size_t length, const unsigned char *iv, size_t iv_len, const unsigned char *add, size_t add_len, const unsigned char *tag, size_t tag_len, const unsigned char *input, unsigned char *output)
GCM buffer authenticated decryption using a block cipher.
#define POLARSSL_ERR_GCM_BAD_INPUT
Bad input parameters to function.
int gcm_self_test(int verbose)
Checkup routine.
Configuration options (set of defines)
AES-NI for hardware AES acceleration on some Intel processors.
int gcm_crypt_and_tag(gcm_context *ctx, int mode, size_t length, const unsigned char *iv, size_t iv_len, const unsigned char *add, size_t add_len, const unsigned char *input, unsigned char *output, size_t tag_len, unsigned char *tag)
GCM buffer encryption/decryption using a block cipher.
#define POLARSSL_AESNI_CLMUL
int cipher_free_ctx(cipher_context_t *ctx)
Free the cipher-specific context of ctx.
int cipher_update(cipher_context_t *ctx, const unsigned char *input, size_t ilen, unsigned char *output, size_t *olen)
Generic cipher update function.
int gcm_init(gcm_context *ctx, cipher_id_t cipher, const unsigned char *key, unsigned int keysize)
GCM initialization (encryption)
#define POLARSSL_ERR_GCM_AUTH_FAILED
Authenticated decryption failed.
int cipher_init_ctx(cipher_context_t *ctx, const cipher_info_t *cipher_info)
Initialises and fills the cipher context structure with the appropriate values.
int cipher_setkey(cipher_context_t *ctx, const unsigned char *key, int key_length, const operation_t operation)
Set the key to use with the given context.
int gcm_update(gcm_context *ctx, size_t length, const unsigned char *input, unsigned char *output)
Generic GCM update function.
void gcm_free(gcm_context *ctx)
Free a GCM context and underlying cipher sub-context.
int gcm_starts(gcm_context *ctx, int mode, const unsigned char *iv, size_t iv_len, const unsigned char *add, size_t add_len)
Generic GCM stream start function.
Galois/Counter mode for 128-bit block ciphers.
int gcm_finish(gcm_context *ctx, unsigned char *tag, size_t tag_len)
Generic GCM finalisation function.
unsigned int block_size
block size, in bytes
unsigned char base_ectr[16]
cipher_context_t cipher_ctx
const cipher_info_t * cipher_info_from_values(const cipher_id_t cipher_id, int key_length, const cipher_mode_t mode)
Returns the cipher information structure associated with the given cipher id, key size and mode...