1 /*
2  *  NIST SP800-38D compliant GCM implementation
3  *
4  *  Copyright The Mbed TLS Contributors
5  *  SPDX-License-Identifier: Apache-2.0
6  *
7  *  Licensed under the Apache License, Version 2.0 (the "License"); you may
8  *  not use this file except in compliance with the License.
9  *  You may obtain a copy of the License at
10  *
11  *  http://www.apache.org/licenses/LICENSE-2.0
12  *
13  *  Unless required by applicable law or agreed to in writing, software
14  *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
15  *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  *  See the License for the specific language governing permissions and
17  *  limitations under the License.
18  */
19 
20 /*
21  * http://csrc.nist.gov/publications/nistpubs/800-38D/SP-800-38D.pdf
22  *
23  * See also:
24  * [MGV] http://csrc.nist.gov/groups/ST/toolkit/BCM/documents/proposedmodes/gcm/gcm-revised-spec.pdf
25  *
26  * We use the algorithm described as Shoup's method with 4-bit tables in
27  * [MGV] 4.1, pp. 12-13, to enhance speed without using too much memory.
28  */
29 
30 #include "common.h"
31 
32 #if defined(MBEDTLS_GCM_C)
33 
34 #include "mbedtls/gcm.h"
35 #include "mbedtls/platform_util.h"
36 #include "mbedtls/error.h"
37 
38 #include <string.h>
39 
40 #if defined(MBEDTLS_AESNI_C)
41 #include "mbedtls/aesni.h"
42 #endif
43 
44 #if defined(MBEDTLS_SELF_TEST) && defined(MBEDTLS_AES_C)
45 #include "mbedtls/aes.h"
46 #include "mbedtls/platform.h"
47 #if !defined(MBEDTLS_PLATFORM_C)
48 #include <stdio.h>
49 #define mbedtls_printf printf
50 #endif /* MBEDTLS_PLATFORM_C */
51 #endif /* MBEDTLS_SELF_TEST && MBEDTLS_AES_C */
52 
53 #if !defined(MBEDTLS_GCM_ALT)
54 
55 /* Parameter validation macros */
56 #define GCM_VALIDATE_RET( cond ) \
57     MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_GCM_BAD_INPUT )
58 #define GCM_VALIDATE( cond ) \
59     MBEDTLS_INTERNAL_VALIDATE( cond )
60 
61 /*
62  * 32-bit integer manipulation macros (big endian)
63  */
64 #ifndef GET_UINT32_BE
65 #define GET_UINT32_BE(n,b,i)                            \
66 {                                                       \
67     (n) = ( (uint32_t) (b)[(i)    ] << 24 )             \
68         | ( (uint32_t) (b)[(i) + 1] << 16 )             \
69         | ( (uint32_t) (b)[(i) + 2] <<  8 )             \
70         | ( (uint32_t) (b)[(i) + 3]       );            \
71 }
72 #endif
73 
74 #ifndef PUT_UINT32_BE
75 #define PUT_UINT32_BE(n,b,i)                            \
76 {                                                       \
77     (b)[(i)    ] = (unsigned char) ( (n) >> 24 );       \
78     (b)[(i) + 1] = (unsigned char) ( (n) >> 16 );       \
79     (b)[(i) + 2] = (unsigned char) ( (n) >>  8 );       \
80     (b)[(i) + 3] = (unsigned char) ( (n)       );       \
81 }
82 #endif
83 
84 /*
85  * Initialize a context
86  */
mbedtls_gcm_init(mbedtls_gcm_context * ctx)87 void mbedtls_gcm_init( mbedtls_gcm_context *ctx )
88 {
89     GCM_VALIDATE( ctx != NULL );
90     memset( ctx, 0, sizeof( mbedtls_gcm_context ) );
91 }
92 
93 /*
94  * Precompute small multiples of H, that is set
95  *      HH[i] || HL[i] = H times i,
96  * where i is seen as a field element as in [MGV], ie high-order bits
97  * correspond to low powers of P. The result is stored in the same way, that
98  * is the high-order bit of HH corresponds to P^0 and the low-order bit of HL
99  * corresponds to P^127.
100  */
gcm_gen_table(mbedtls_gcm_context * ctx)101 static int gcm_gen_table( mbedtls_gcm_context *ctx )
102 {
103     int ret, i, j;
104     uint64_t hi, lo;
105     uint64_t vl, vh;
106     unsigned char h[16];
107     size_t olen = 0;
108 
109     memset( h, 0, 16 );
110     if( ( ret = mbedtls_cipher_update( &ctx->cipher_ctx, h, 16, h, &olen ) ) != 0 )
111         return( ret );
112 
113     /* pack h as two 64-bits ints, big-endian */
114     GET_UINT32_BE( hi, h,  0  );
115     GET_UINT32_BE( lo, h,  4  );
116     vh = (uint64_t) hi << 32 | lo;
117 
118     GET_UINT32_BE( hi, h,  8  );
119     GET_UINT32_BE( lo, h,  12 );
120     vl = (uint64_t) hi << 32 | lo;
121 
122     /* 8 = 1000 corresponds to 1 in GF(2^128) */
123     ctx->HL[8] = vl;
124     ctx->HH[8] = vh;
125 
126 #if defined(MBEDTLS_AESNI_C) && defined(MBEDTLS_HAVE_X86_64)
127     /* With CLMUL support, we need only h, not the rest of the table */
128     if( mbedtls_aesni_has_support( MBEDTLS_AESNI_CLMUL ) )
129         return( 0 );
130 #endif
131 
132     /* 0 corresponds to 0 in GF(2^128) */
133     ctx->HH[0] = 0;
134     ctx->HL[0] = 0;
135 
136     for( i = 4; i > 0; i >>= 1 )
137     {
138         uint32_t T = ( vl & 1 ) * 0xe1000000U;
139         vl  = ( vh << 63 ) | ( vl >> 1 );
140         vh  = ( vh >> 1 ) ^ ( (uint64_t) T << 32);
141 
142         ctx->HL[i] = vl;
143         ctx->HH[i] = vh;
144     }
145 
146     for( i = 2; i <= 8; i *= 2 )
147     {
148         uint64_t *HiL = ctx->HL + i, *HiH = ctx->HH + i;
149         vh = *HiH;
150         vl = *HiL;
151         for( j = 1; j < i; j++ )
152         {
153             HiH[j] = vh ^ ctx->HH[j];
154             HiL[j] = vl ^ ctx->HL[j];
155         }
156     }
157 
158     return( 0 );
159 }
160 
mbedtls_gcm_setkey(mbedtls_gcm_context * ctx,mbedtls_cipher_id_t cipher,const unsigned char * key,unsigned int keybits)161 int mbedtls_gcm_setkey( mbedtls_gcm_context *ctx,
162                         mbedtls_cipher_id_t cipher,
163                         const unsigned char *key,
164                         unsigned int keybits )
165 {
166     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
167     const mbedtls_cipher_info_t *cipher_info;
168 
169     GCM_VALIDATE_RET( ctx != NULL );
170     GCM_VALIDATE_RET( key != NULL );
171     GCM_VALIDATE_RET( keybits == 128 || keybits == 192 || keybits == 256 );
172 
173     cipher_info = mbedtls_cipher_info_from_values( cipher, keybits,
174                                                    MBEDTLS_MODE_ECB );
175     if( cipher_info == NULL )
176         return( MBEDTLS_ERR_GCM_BAD_INPUT );
177 
178     if( cipher_info->block_size != 16 )
179         return( MBEDTLS_ERR_GCM_BAD_INPUT );
180 
181     mbedtls_cipher_free( &ctx->cipher_ctx );
182 
183     if( ( ret = mbedtls_cipher_setup( &ctx->cipher_ctx, cipher_info ) ) != 0 )
184         return( ret );
185 
186     if( ( ret = mbedtls_cipher_setkey( &ctx->cipher_ctx, key, keybits,
187                                MBEDTLS_ENCRYPT ) ) != 0 )
188     {
189         return( ret );
190     }
191 
192     if( ( ret = gcm_gen_table( ctx ) ) != 0 )
193         return( ret );
194 
195     return( 0 );
196 }
197 
198 /*
199  * Shoup's method for multiplication use this table with
200  *      last4[x] = x times P^128
201  * where x and last4[x] are seen as elements of GF(2^128) as in [MGV]
202  */
203 static const uint64_t last4[16] =
204 {
205     0x0000, 0x1c20, 0x3840, 0x2460,
206     0x7080, 0x6ca0, 0x48c0, 0x54e0,
207     0xe100, 0xfd20, 0xd940, 0xc560,
208     0x9180, 0x8da0, 0xa9c0, 0xb5e0
209 };
210 
211 /*
212  * Sets output to x times H using the precomputed tables.
213  * x and output are seen as elements of GF(2^128) as in [MGV].
214  */
gcm_mult(mbedtls_gcm_context * ctx,const unsigned char x[16],unsigned char output[16])215 static void gcm_mult( mbedtls_gcm_context *ctx, const unsigned char x[16],
216                       unsigned char output[16] )
217 {
218     int i = 0;
219     unsigned char lo, hi, rem;
220     uint64_t zh, zl;
221 
222 #if defined(MBEDTLS_AESNI_C) && defined(MBEDTLS_HAVE_X86_64)
223     if( mbedtls_aesni_has_support( MBEDTLS_AESNI_CLMUL ) ) {
224         unsigned char h[16];
225 
226         PUT_UINT32_BE( ctx->HH[8] >> 32, h,  0 );
227         PUT_UINT32_BE( ctx->HH[8],       h,  4 );
228         PUT_UINT32_BE( ctx->HL[8] >> 32, h,  8 );
229         PUT_UINT32_BE( ctx->HL[8],       h, 12 );
230 
231         mbedtls_aesni_gcm_mult( output, x, h );
232         return;
233     }
234 #endif /* MBEDTLS_AESNI_C && MBEDTLS_HAVE_X86_64 */
235 
236     lo = x[15] & 0xf;
237 
238     zh = ctx->HH[lo];
239     zl = ctx->HL[lo];
240 
241     for( i = 15; i >= 0; i-- )
242     {
243         lo = x[i] & 0xf;
244         hi = ( x[i] >> 4 ) & 0xf;
245 
246         if( i != 15 )
247         {
248             rem = (unsigned char) zl & 0xf;
249             zl = ( zh << 60 ) | ( zl >> 4 );
250             zh = ( zh >> 4 );
251             zh ^= (uint64_t) last4[rem] << 48;
252             zh ^= ctx->HH[lo];
253             zl ^= ctx->HL[lo];
254 
255         }
256 
257         rem = (unsigned char) zl & 0xf;
258         zl = ( zh << 60 ) | ( zl >> 4 );
259         zh = ( zh >> 4 );
260         zh ^= (uint64_t) last4[rem] << 48;
261         zh ^= ctx->HH[hi];
262         zl ^= ctx->HL[hi];
263     }
264 
265     PUT_UINT32_BE( zh >> 32, output, 0 );
266     PUT_UINT32_BE( zh, output, 4 );
267     PUT_UINT32_BE( zl >> 32, output, 8 );
268     PUT_UINT32_BE( zl, output, 12 );
269 }
270 
mbedtls_gcm_starts(mbedtls_gcm_context * ctx,int mode,const unsigned char * iv,size_t iv_len,const unsigned char * add,size_t add_len)271 int mbedtls_gcm_starts( mbedtls_gcm_context *ctx,
272                 int mode,
273                 const unsigned char *iv,
274                 size_t iv_len,
275                 const unsigned char *add,
276                 size_t add_len )
277 {
278     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
279     unsigned char work_buf[16];
280     size_t i;
281     const unsigned char *p;
282     size_t use_len, olen = 0;
283 
284     GCM_VALIDATE_RET( ctx != NULL );
285     GCM_VALIDATE_RET( iv != NULL );
286     GCM_VALIDATE_RET( add_len == 0 || add != NULL );
287 
288     /* IV and AD are limited to 2^64 bits, so 2^61 bytes */
289     /* IV is not allowed to be zero length */
290     if( iv_len == 0 ||
291       ( (uint64_t) iv_len  ) >> 61 != 0 ||
292       ( (uint64_t) add_len ) >> 61 != 0 )
293     {
294         return( MBEDTLS_ERR_GCM_BAD_INPUT );
295     }
296 
297     memset( ctx->y, 0x00, sizeof(ctx->y) );
298     memset( ctx->buf, 0x00, sizeof(ctx->buf) );
299 
300     ctx->mode = mode;
301     ctx->len = 0;
302     ctx->add_len = 0;
303 
304     if( iv_len == 12 )
305     {
306         memcpy( ctx->y, iv, iv_len );
307         ctx->y[15] = 1;
308     }
309     else
310     {
311         memset( work_buf, 0x00, 16 );
312         PUT_UINT32_BE( iv_len * 8, work_buf, 12 );
313 
314         p = iv;
315         while( iv_len > 0 )
316         {
317             use_len = ( iv_len < 16 ) ? iv_len : 16;
318 
319             for( i = 0; i < use_len; i++ )
320                 ctx->y[i] ^= p[i];
321 
322             gcm_mult( ctx, ctx->y, ctx->y );
323 
324             iv_len -= use_len;
325             p += use_len;
326         }
327 
328         for( i = 0; i < 16; i++ )
329             ctx->y[i] ^= work_buf[i];
330 
331         gcm_mult( ctx, ctx->y, ctx->y );
332     }
333 
334     if( ( ret = mbedtls_cipher_update( &ctx->cipher_ctx, ctx->y, 16,
335                                        ctx->base_ectr, &olen ) ) != 0 )
336     {
337         return( ret );
338     }
339 
340     ctx->add_len = add_len;
341     p = add;
342     while( add_len > 0 )
343     {
344         use_len = ( add_len < 16 ) ? add_len : 16;
345 
346         for( i = 0; i < use_len; i++ )
347             ctx->buf[i] ^= p[i];
348 
349         gcm_mult( ctx, ctx->buf, ctx->buf );
350 
351         add_len -= use_len;
352         p += use_len;
353     }
354 
355     return( 0 );
356 }
357 
mbedtls_gcm_update(mbedtls_gcm_context * ctx,size_t length,const unsigned char * input,unsigned char * output)358 int mbedtls_gcm_update( mbedtls_gcm_context *ctx,
359                 size_t length,
360                 const unsigned char *input,
361                 unsigned char *output )
362 {
363     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
364     unsigned char ectr[16];
365     size_t i;
366     const unsigned char *p;
367     unsigned char *out_p = output;
368     size_t use_len, olen = 0;
369 
370     GCM_VALIDATE_RET( ctx != NULL );
371     GCM_VALIDATE_RET( length == 0 || input != NULL );
372     GCM_VALIDATE_RET( length == 0 || output != NULL );
373 
374     if( output > input && (size_t) ( output - input ) < length )
375         return( MBEDTLS_ERR_GCM_BAD_INPUT );
376 
377     /* Total length is restricted to 2^39 - 256 bits, ie 2^36 - 2^5 bytes
378      * Also check for possible overflow */
379     if( ctx->len + length < ctx->len ||
380         (uint64_t) ctx->len + length > 0xFFFFFFFE0ull )
381     {
382         return( MBEDTLS_ERR_GCM_BAD_INPUT );
383     }
384 
385     ctx->len += length;
386 
387     p = input;
388     while( length > 0 )
389     {
390         use_len = ( length < 16 ) ? length : 16;
391 
392         for( i = 16; i > 12; i-- )
393             if( ++ctx->y[i - 1] != 0 )
394                 break;
395 
396         if( ( ret = mbedtls_cipher_update( &ctx->cipher_ctx, ctx->y, 16, ectr,
397                                    &olen ) ) != 0 )
398         {
399             return( ret );
400         }
401 
402         for( i = 0; i < use_len; i++ )
403         {
404             if( ctx->mode == MBEDTLS_GCM_DECRYPT )
405                 ctx->buf[i] ^= p[i];
406             out_p[i] = ectr[i] ^ p[i];
407             if( ctx->mode == MBEDTLS_GCM_ENCRYPT )
408                 ctx->buf[i] ^= out_p[i];
409         }
410 
411         gcm_mult( ctx, ctx->buf, ctx->buf );
412 
413         length -= use_len;
414         p += use_len;
415         out_p += use_len;
416     }
417 
418     return( 0 );
419 }
420 
mbedtls_gcm_finish(mbedtls_gcm_context * ctx,unsigned char * tag,size_t tag_len)421 int mbedtls_gcm_finish( mbedtls_gcm_context *ctx,
422                 unsigned char *tag,
423                 size_t tag_len )
424 {
425     unsigned char work_buf[16];
426     size_t i;
427     uint64_t orig_len;
428     uint64_t orig_add_len;
429 
430     GCM_VALIDATE_RET( ctx != NULL );
431     GCM_VALIDATE_RET( tag != NULL );
432 
433     orig_len = ctx->len * 8;
434     orig_add_len = ctx->add_len * 8;
435 
436     if( tag_len > 16 || tag_len < 4 )
437         return( MBEDTLS_ERR_GCM_BAD_INPUT );
438 
439     memcpy( tag, ctx->base_ectr, tag_len );
440 
441     if( orig_len || orig_add_len )
442     {
443         memset( work_buf, 0x00, 16 );
444 
445         PUT_UINT32_BE( ( orig_add_len >> 32 ), work_buf, 0  );
446         PUT_UINT32_BE( ( orig_add_len       ), work_buf, 4  );
447         PUT_UINT32_BE( ( orig_len     >> 32 ), work_buf, 8  );
448         PUT_UINT32_BE( ( orig_len           ), work_buf, 12 );
449 
450         for( i = 0; i < 16; i++ )
451             ctx->buf[i] ^= work_buf[i];
452 
453         gcm_mult( ctx, ctx->buf, ctx->buf );
454 
455         for( i = 0; i < tag_len; i++ )
456             tag[i] ^= ctx->buf[i];
457     }
458 
459     return( 0 );
460 }
461 
mbedtls_gcm_crypt_and_tag(mbedtls_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)462 int mbedtls_gcm_crypt_and_tag( mbedtls_gcm_context *ctx,
463                        int mode,
464                        size_t length,
465                        const unsigned char *iv,
466                        size_t iv_len,
467                        const unsigned char *add,
468                        size_t add_len,
469                        const unsigned char *input,
470                        unsigned char *output,
471                        size_t tag_len,
472                        unsigned char *tag )
473 {
474     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
475 
476     GCM_VALIDATE_RET( ctx != NULL );
477     GCM_VALIDATE_RET( iv != NULL );
478     GCM_VALIDATE_RET( add_len == 0 || add != NULL );
479     GCM_VALIDATE_RET( length == 0 || input != NULL );
480     GCM_VALIDATE_RET( length == 0 || output != NULL );
481     GCM_VALIDATE_RET( tag != NULL );
482 
483     if( ( ret = mbedtls_gcm_starts( ctx, mode, iv, iv_len, add, add_len ) ) != 0 )
484         return( ret );
485 
486     if( ( ret = mbedtls_gcm_update( ctx, length, input, output ) ) != 0 )
487         return( ret );
488 
489     if( ( ret = mbedtls_gcm_finish( ctx, tag, tag_len ) ) != 0 )
490         return( ret );
491 
492     return( 0 );
493 }
494 
mbedtls_gcm_auth_decrypt(mbedtls_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)495 int mbedtls_gcm_auth_decrypt( mbedtls_gcm_context *ctx,
496                       size_t length,
497                       const unsigned char *iv,
498                       size_t iv_len,
499                       const unsigned char *add,
500                       size_t add_len,
501                       const unsigned char *tag,
502                       size_t tag_len,
503                       const unsigned char *input,
504                       unsigned char *output )
505 {
506     int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
507     unsigned char check_tag[16];
508     size_t i;
509     int diff;
510 
511     GCM_VALIDATE_RET( ctx != NULL );
512     GCM_VALIDATE_RET( iv != NULL );
513     GCM_VALIDATE_RET( add_len == 0 || add != NULL );
514     GCM_VALIDATE_RET( tag != NULL );
515     GCM_VALIDATE_RET( length == 0 || input != NULL );
516     GCM_VALIDATE_RET( length == 0 || output != NULL );
517 
518     if( ( ret = mbedtls_gcm_crypt_and_tag( ctx, MBEDTLS_GCM_DECRYPT, length,
519                                    iv, iv_len, add, add_len,
520                                    input, output, tag_len, check_tag ) ) != 0 )
521     {
522         return( ret );
523     }
524 
525     /* Check tag in "constant-time" */
526     for( diff = 0, i = 0; i < tag_len; i++ )
527         diff |= tag[i] ^ check_tag[i];
528 
529     if( diff != 0 )
530     {
531         mbedtls_platform_zeroize( output, length );
532         return( MBEDTLS_ERR_GCM_AUTH_FAILED );
533     }
534 
535     return( 0 );
536 }
537 
mbedtls_gcm_free(mbedtls_gcm_context * ctx)538 void mbedtls_gcm_free( mbedtls_gcm_context *ctx )
539 {
540     if( ctx == NULL )
541         return;
542     mbedtls_cipher_free( &ctx->cipher_ctx );
543     mbedtls_platform_zeroize( ctx, sizeof( mbedtls_gcm_context ) );
544 }
545 
546 #endif /* !MBEDTLS_GCM_ALT */
547 
548 #if defined(MBEDTLS_SELF_TEST) && defined(MBEDTLS_AES_C)
549 /*
550  * AES-GCM test vectors from:
551  *
552  * http://csrc.nist.gov/groups/STM/cavp/documents/mac/gcmtestvectors.zip
553  */
554 #define MAX_TESTS   6
555 
556 static const int key_index_test_data[MAX_TESTS] =
557     { 0, 0, 1, 1, 1, 1 };
558 
559 static const unsigned char key_test_data[MAX_TESTS][32] =
560 {
561     { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
562       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
563       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
564       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
565     { 0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c,
566       0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08,
567       0xfe, 0xff, 0xe9, 0x92, 0x86, 0x65, 0x73, 0x1c,
568       0x6d, 0x6a, 0x8f, 0x94, 0x67, 0x30, 0x83, 0x08 },
569 };
570 
571 static const size_t iv_len_test_data[MAX_TESTS] =
572     { 12, 12, 12, 12, 8, 60 };
573 
574 static const int iv_index_test_data[MAX_TESTS] =
575     { 0, 0, 1, 1, 1, 2 };
576 
577 static const unsigned char iv_test_data[MAX_TESTS][64] =
578 {
579     { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
580       0x00, 0x00, 0x00, 0x00 },
581     { 0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce, 0xdb, 0xad,
582       0xde, 0xca, 0xf8, 0x88 },
583     { 0x93, 0x13, 0x22, 0x5d, 0xf8, 0x84, 0x06, 0xe5,
584       0x55, 0x90, 0x9c, 0x5a, 0xff, 0x52, 0x69, 0xaa,
585       0x6a, 0x7a, 0x95, 0x38, 0x53, 0x4f, 0x7d, 0xa1,
586       0xe4, 0xc3, 0x03, 0xd2, 0xa3, 0x18, 0xa7, 0x28,
587       0xc3, 0xc0, 0xc9, 0x51, 0x56, 0x80, 0x95, 0x39,
588       0xfc, 0xf0, 0xe2, 0x42, 0x9a, 0x6b, 0x52, 0x54,
589       0x16, 0xae, 0xdb, 0xf5, 0xa0, 0xde, 0x6a, 0x57,
590       0xa6, 0x37, 0xb3, 0x9b },
591 };
592 
593 static const size_t add_len_test_data[MAX_TESTS] =
594     { 0, 0, 0, 20, 20, 20 };
595 
596 static const int add_index_test_data[MAX_TESTS] =
597     { 0, 0, 0, 1, 1, 1 };
598 
599 static const unsigned char additional_test_data[MAX_TESTS][64] =
600 {
601     { 0x00 },
602     { 0xfe, 0xed, 0xfa, 0xce, 0xde, 0xad, 0xbe, 0xef,
603       0xfe, 0xed, 0xfa, 0xce, 0xde, 0xad, 0xbe, 0xef,
604       0xab, 0xad, 0xda, 0xd2 },
605 };
606 
607 static const size_t pt_len_test_data[MAX_TESTS] =
608     { 0, 16, 64, 60, 60, 60 };
609 
610 static const int pt_index_test_data[MAX_TESTS] =
611     { 0, 0, 1, 1, 1, 1 };
612 
613 static const unsigned char pt_test_data[MAX_TESTS][64] =
614 {
615     { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
616       0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
617     { 0xd9, 0x31, 0x32, 0x25, 0xf8, 0x84, 0x06, 0xe5,
618       0xa5, 0x59, 0x09, 0xc5, 0xaf, 0xf5, 0x26, 0x9a,
619       0x86, 0xa7, 0xa9, 0x53, 0x15, 0x34, 0xf7, 0xda,
620       0x2e, 0x4c, 0x30, 0x3d, 0x8a, 0x31, 0x8a, 0x72,
621       0x1c, 0x3c, 0x0c, 0x95, 0x95, 0x68, 0x09, 0x53,
622       0x2f, 0xcf, 0x0e, 0x24, 0x49, 0xa6, 0xb5, 0x25,
623       0xb1, 0x6a, 0xed, 0xf5, 0xaa, 0x0d, 0xe6, 0x57,
624       0xba, 0x63, 0x7b, 0x39, 0x1a, 0xaf, 0xd2, 0x55 },
625 };
626 
627 static const unsigned char ct_test_data[MAX_TESTS * 3][64] =
628 {
629     { 0x00 },
630     { 0x03, 0x88, 0xda, 0xce, 0x60, 0xb6, 0xa3, 0x92,
631       0xf3, 0x28, 0xc2, 0xb9, 0x71, 0xb2, 0xfe, 0x78 },
632     { 0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24,
633       0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c,
634       0xe3, 0xaa, 0x21, 0x2f, 0x2c, 0x02, 0xa4, 0xe0,
635       0x35, 0xc1, 0x7e, 0x23, 0x29, 0xac, 0xa1, 0x2e,
636       0x21, 0xd5, 0x14, 0xb2, 0x54, 0x66, 0x93, 0x1c,
637       0x7d, 0x8f, 0x6a, 0x5a, 0xac, 0x84, 0xaa, 0x05,
638       0x1b, 0xa3, 0x0b, 0x39, 0x6a, 0x0a, 0xac, 0x97,
639       0x3d, 0x58, 0xe0, 0x91, 0x47, 0x3f, 0x59, 0x85 },
640     { 0x42, 0x83, 0x1e, 0xc2, 0x21, 0x77, 0x74, 0x24,
641       0x4b, 0x72, 0x21, 0xb7, 0x84, 0xd0, 0xd4, 0x9c,
642       0xe3, 0xaa, 0x21, 0x2f, 0x2c, 0x02, 0xa4, 0xe0,
643       0x35, 0xc1, 0x7e, 0x23, 0x29, 0xac, 0xa1, 0x2e,
644       0x21, 0xd5, 0x14, 0xb2, 0x54, 0x66, 0x93, 0x1c,
645       0x7d, 0x8f, 0x6a, 0x5a, 0xac, 0x84, 0xaa, 0x05,
646       0x1b, 0xa3, 0x0b, 0x39, 0x6a, 0x0a, 0xac, 0x97,
647       0x3d, 0x58, 0xe0, 0x91 },
648     { 0x61, 0x35, 0x3b, 0x4c, 0x28, 0x06, 0x93, 0x4a,
649       0x77, 0x7f, 0xf5, 0x1f, 0xa2, 0x2a, 0x47, 0x55,
650       0x69, 0x9b, 0x2a, 0x71, 0x4f, 0xcd, 0xc6, 0xf8,
651       0x37, 0x66, 0xe5, 0xf9, 0x7b, 0x6c, 0x74, 0x23,
652       0x73, 0x80, 0x69, 0x00, 0xe4, 0x9f, 0x24, 0xb2,
653       0x2b, 0x09, 0x75, 0x44, 0xd4, 0x89, 0x6b, 0x42,
654       0x49, 0x89, 0xb5, 0xe1, 0xeb, 0xac, 0x0f, 0x07,
655       0xc2, 0x3f, 0x45, 0x98 },
656     { 0x8c, 0xe2, 0x49, 0x98, 0x62, 0x56, 0x15, 0xb6,
657       0x03, 0xa0, 0x33, 0xac, 0xa1, 0x3f, 0xb8, 0x94,
658       0xbe, 0x91, 0x12, 0xa5, 0xc3, 0xa2, 0x11, 0xa8,
659       0xba, 0x26, 0x2a, 0x3c, 0xca, 0x7e, 0x2c, 0xa7,
660       0x01, 0xe4, 0xa9, 0xa4, 0xfb, 0xa4, 0x3c, 0x90,
661       0xcc, 0xdc, 0xb2, 0x81, 0xd4, 0x8c, 0x7c, 0x6f,
662       0xd6, 0x28, 0x75, 0xd2, 0xac, 0xa4, 0x17, 0x03,
663       0x4c, 0x34, 0xae, 0xe5 },
664     { 0x00 },
665     { 0x98, 0xe7, 0x24, 0x7c, 0x07, 0xf0, 0xfe, 0x41,
666       0x1c, 0x26, 0x7e, 0x43, 0x84, 0xb0, 0xf6, 0x00 },
667     { 0x39, 0x80, 0xca, 0x0b, 0x3c, 0x00, 0xe8, 0x41,
668       0xeb, 0x06, 0xfa, 0xc4, 0x87, 0x2a, 0x27, 0x57,
669       0x85, 0x9e, 0x1c, 0xea, 0xa6, 0xef, 0xd9, 0x84,
670       0x62, 0x85, 0x93, 0xb4, 0x0c, 0xa1, 0xe1, 0x9c,
671       0x7d, 0x77, 0x3d, 0x00, 0xc1, 0x44, 0xc5, 0x25,
672       0xac, 0x61, 0x9d, 0x18, 0xc8, 0x4a, 0x3f, 0x47,
673       0x18, 0xe2, 0x44, 0x8b, 0x2f, 0xe3, 0x24, 0xd9,
674       0xcc, 0xda, 0x27, 0x10, 0xac, 0xad, 0xe2, 0x56 },
675     { 0x39, 0x80, 0xca, 0x0b, 0x3c, 0x00, 0xe8, 0x41,
676       0xeb, 0x06, 0xfa, 0xc4, 0x87, 0x2a, 0x27, 0x57,
677       0x85, 0x9e, 0x1c, 0xea, 0xa6, 0xef, 0xd9, 0x84,
678       0x62, 0x85, 0x93, 0xb4, 0x0c, 0xa1, 0xe1, 0x9c,
679       0x7d, 0x77, 0x3d, 0x00, 0xc1, 0x44, 0xc5, 0x25,
680       0xac, 0x61, 0x9d, 0x18, 0xc8, 0x4a, 0x3f, 0x47,
681       0x18, 0xe2, 0x44, 0x8b, 0x2f, 0xe3, 0x24, 0xd9,
682       0xcc, 0xda, 0x27, 0x10 },
683     { 0x0f, 0x10, 0xf5, 0x99, 0xae, 0x14, 0xa1, 0x54,
684       0xed, 0x24, 0xb3, 0x6e, 0x25, 0x32, 0x4d, 0xb8,
685       0xc5, 0x66, 0x63, 0x2e, 0xf2, 0xbb, 0xb3, 0x4f,
686       0x83, 0x47, 0x28, 0x0f, 0xc4, 0x50, 0x70, 0x57,
687       0xfd, 0xdc, 0x29, 0xdf, 0x9a, 0x47, 0x1f, 0x75,
688       0xc6, 0x65, 0x41, 0xd4, 0xd4, 0xda, 0xd1, 0xc9,
689       0xe9, 0x3a, 0x19, 0xa5, 0x8e, 0x8b, 0x47, 0x3f,
690       0xa0, 0xf0, 0x62, 0xf7 },
691     { 0xd2, 0x7e, 0x88, 0x68, 0x1c, 0xe3, 0x24, 0x3c,
692       0x48, 0x30, 0x16, 0x5a, 0x8f, 0xdc, 0xf9, 0xff,
693       0x1d, 0xe9, 0xa1, 0xd8, 0xe6, 0xb4, 0x47, 0xef,
694       0x6e, 0xf7, 0xb7, 0x98, 0x28, 0x66, 0x6e, 0x45,
695       0x81, 0xe7, 0x90, 0x12, 0xaf, 0x34, 0xdd, 0xd9,
696       0xe2, 0xf0, 0x37, 0x58, 0x9b, 0x29, 0x2d, 0xb3,
697       0xe6, 0x7c, 0x03, 0x67, 0x45, 0xfa, 0x22, 0xe7,
698       0xe9, 0xb7, 0x37, 0x3b },
699     { 0x00 },
700     { 0xce, 0xa7, 0x40, 0x3d, 0x4d, 0x60, 0x6b, 0x6e,
701       0x07, 0x4e, 0xc5, 0xd3, 0xba, 0xf3, 0x9d, 0x18 },
702     { 0x52, 0x2d, 0xc1, 0xf0, 0x99, 0x56, 0x7d, 0x07,
703       0xf4, 0x7f, 0x37, 0xa3, 0x2a, 0x84, 0x42, 0x7d,
704       0x64, 0x3a, 0x8c, 0xdc, 0xbf, 0xe5, 0xc0, 0xc9,
705       0x75, 0x98, 0xa2, 0xbd, 0x25, 0x55, 0xd1, 0xaa,
706       0x8c, 0xb0, 0x8e, 0x48, 0x59, 0x0d, 0xbb, 0x3d,
707       0xa7, 0xb0, 0x8b, 0x10, 0x56, 0x82, 0x88, 0x38,
708       0xc5, 0xf6, 0x1e, 0x63, 0x93, 0xba, 0x7a, 0x0a,
709       0xbc, 0xc9, 0xf6, 0x62, 0x89, 0x80, 0x15, 0xad },
710     { 0x52, 0x2d, 0xc1, 0xf0, 0x99, 0x56, 0x7d, 0x07,
711       0xf4, 0x7f, 0x37, 0xa3, 0x2a, 0x84, 0x42, 0x7d,
712       0x64, 0x3a, 0x8c, 0xdc, 0xbf, 0xe5, 0xc0, 0xc9,
713       0x75, 0x98, 0xa2, 0xbd, 0x25, 0x55, 0xd1, 0xaa,
714       0x8c, 0xb0, 0x8e, 0x48, 0x59, 0x0d, 0xbb, 0x3d,
715       0xa7, 0xb0, 0x8b, 0x10, 0x56, 0x82, 0x88, 0x38,
716       0xc5, 0xf6, 0x1e, 0x63, 0x93, 0xba, 0x7a, 0x0a,
717       0xbc, 0xc9, 0xf6, 0x62 },
718     { 0xc3, 0x76, 0x2d, 0xf1, 0xca, 0x78, 0x7d, 0x32,
719       0xae, 0x47, 0xc1, 0x3b, 0xf1, 0x98, 0x44, 0xcb,
720       0xaf, 0x1a, 0xe1, 0x4d, 0x0b, 0x97, 0x6a, 0xfa,
721       0xc5, 0x2f, 0xf7, 0xd7, 0x9b, 0xba, 0x9d, 0xe0,
722       0xfe, 0xb5, 0x82, 0xd3, 0x39, 0x34, 0xa4, 0xf0,
723       0x95, 0x4c, 0xc2, 0x36, 0x3b, 0xc7, 0x3f, 0x78,
724       0x62, 0xac, 0x43, 0x0e, 0x64, 0xab, 0xe4, 0x99,
725       0xf4, 0x7c, 0x9b, 0x1f },
726     { 0x5a, 0x8d, 0xef, 0x2f, 0x0c, 0x9e, 0x53, 0xf1,
727       0xf7, 0x5d, 0x78, 0x53, 0x65, 0x9e, 0x2a, 0x20,
728       0xee, 0xb2, 0xb2, 0x2a, 0xaf, 0xde, 0x64, 0x19,
729       0xa0, 0x58, 0xab, 0x4f, 0x6f, 0x74, 0x6b, 0xf4,
730       0x0f, 0xc0, 0xc3, 0xb7, 0x80, 0xf2, 0x44, 0x45,
731       0x2d, 0xa3, 0xeb, 0xf1, 0xc5, 0xd8, 0x2c, 0xde,
732       0xa2, 0x41, 0x89, 0x97, 0x20, 0x0e, 0xf8, 0x2e,
733       0x44, 0xae, 0x7e, 0x3f },
734 };
735 
736 static const unsigned char tag_test_data[MAX_TESTS * 3][16] =
737 {
738     { 0x58, 0xe2, 0xfc, 0xce, 0xfa, 0x7e, 0x30, 0x61,
739       0x36, 0x7f, 0x1d, 0x57, 0xa4, 0xe7, 0x45, 0x5a },
740     { 0xab, 0x6e, 0x47, 0xd4, 0x2c, 0xec, 0x13, 0xbd,
741       0xf5, 0x3a, 0x67, 0xb2, 0x12, 0x57, 0xbd, 0xdf },
742     { 0x4d, 0x5c, 0x2a, 0xf3, 0x27, 0xcd, 0x64, 0xa6,
743       0x2c, 0xf3, 0x5a, 0xbd, 0x2b, 0xa6, 0xfa, 0xb4 },
744     { 0x5b, 0xc9, 0x4f, 0xbc, 0x32, 0x21, 0xa5, 0xdb,
745       0x94, 0xfa, 0xe9, 0x5a, 0xe7, 0x12, 0x1a, 0x47 },
746     { 0x36, 0x12, 0xd2, 0xe7, 0x9e, 0x3b, 0x07, 0x85,
747       0x56, 0x1b, 0xe1, 0x4a, 0xac, 0xa2, 0xfc, 0xcb },
748     { 0x61, 0x9c, 0xc5, 0xae, 0xff, 0xfe, 0x0b, 0xfa,
749       0x46, 0x2a, 0xf4, 0x3c, 0x16, 0x99, 0xd0, 0x50 },
750     { 0xcd, 0x33, 0xb2, 0x8a, 0xc7, 0x73, 0xf7, 0x4b,
751       0xa0, 0x0e, 0xd1, 0xf3, 0x12, 0x57, 0x24, 0x35 },
752     { 0x2f, 0xf5, 0x8d, 0x80, 0x03, 0x39, 0x27, 0xab,
753       0x8e, 0xf4, 0xd4, 0x58, 0x75, 0x14, 0xf0, 0xfb },
754     { 0x99, 0x24, 0xa7, 0xc8, 0x58, 0x73, 0x36, 0xbf,
755       0xb1, 0x18, 0x02, 0x4d, 0xb8, 0x67, 0x4a, 0x14 },
756     { 0x25, 0x19, 0x49, 0x8e, 0x80, 0xf1, 0x47, 0x8f,
757       0x37, 0xba, 0x55, 0xbd, 0x6d, 0x27, 0x61, 0x8c },
758     { 0x65, 0xdc, 0xc5, 0x7f, 0xcf, 0x62, 0x3a, 0x24,
759       0x09, 0x4f, 0xcc, 0xa4, 0x0d, 0x35, 0x33, 0xf8 },
760     { 0xdc, 0xf5, 0x66, 0xff, 0x29, 0x1c, 0x25, 0xbb,
761       0xb8, 0x56, 0x8f, 0xc3, 0xd3, 0x76, 0xa6, 0xd9 },
762     { 0x53, 0x0f, 0x8a, 0xfb, 0xc7, 0x45, 0x36, 0xb9,
763       0xa9, 0x63, 0xb4, 0xf1, 0xc4, 0xcb, 0x73, 0x8b },
764     { 0xd0, 0xd1, 0xc8, 0xa7, 0x99, 0x99, 0x6b, 0xf0,
765       0x26, 0x5b, 0x98, 0xb5, 0xd4, 0x8a, 0xb9, 0x19 },
766     { 0xb0, 0x94, 0xda, 0xc5, 0xd9, 0x34, 0x71, 0xbd,
767       0xec, 0x1a, 0x50, 0x22, 0x70, 0xe3, 0xcc, 0x6c },
768     { 0x76, 0xfc, 0x6e, 0xce, 0x0f, 0x4e, 0x17, 0x68,
769       0xcd, 0xdf, 0x88, 0x53, 0xbb, 0x2d, 0x55, 0x1b },
770     { 0x3a, 0x33, 0x7d, 0xbf, 0x46, 0xa7, 0x92, 0xc4,
771       0x5e, 0x45, 0x49, 0x13, 0xfe, 0x2e, 0xa8, 0xf2 },
772     { 0xa4, 0x4a, 0x82, 0x66, 0xee, 0x1c, 0x8e, 0xb0,
773       0xc8, 0xb5, 0xd4, 0xcf, 0x5a, 0xe9, 0xf1, 0x9a },
774 };
775 
mbedtls_gcm_self_test(int verbose)776 int mbedtls_gcm_self_test( int verbose )
777 {
778     mbedtls_gcm_context ctx;
779     unsigned char buf[64];
780     unsigned char tag_buf[16];
781     int i, j, ret;
782     mbedtls_cipher_id_t cipher = MBEDTLS_CIPHER_ID_AES;
783 
784     for( j = 0; j < 3; j++ )
785     {
786         int key_len = 128 + 64 * j;
787 
788         for( i = 0; i < MAX_TESTS; i++ )
789         {
790             mbedtls_gcm_init( &ctx );
791 
792             if( verbose != 0 )
793                 mbedtls_printf( "  AES-GCM-%3d #%d (%s): ",
794                                 key_len, i, "enc" );
795 
796             ret = mbedtls_gcm_setkey( &ctx, cipher,
797                                       key_test_data[key_index_test_data[i]],
798                                       key_len );
799             /*
800              * AES-192 is an optional feature that may be unavailable when
801              * there is an alternative underlying implementation i.e. when
802              * MBEDTLS_AES_ALT is defined.
803              */
804             if( ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && key_len == 192 )
805             {
806                 mbedtls_printf( "skipped\n" );
807                 break;
808             }
809             else if( ret != 0 )
810             {
811                 goto exit;
812             }
813 
814             ret = mbedtls_gcm_crypt_and_tag( &ctx, MBEDTLS_GCM_ENCRYPT,
815                                 pt_len_test_data[i],
816                                 iv_test_data[iv_index_test_data[i]],
817                                 iv_len_test_data[i],
818                                 additional_test_data[add_index_test_data[i]],
819                                 add_len_test_data[i],
820                                 pt_test_data[pt_index_test_data[i]],
821                                 buf, 16, tag_buf );
822 #if defined(MBEDTLS_GCM_ALT)
823             /* Allow alternative implementations to only support 12-byte nonces. */
824             if( ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED &&
825                 iv_len_test_data[i] != 12 )
826             {
827                 mbedtls_printf( "skipped\n" );
828                 break;
829             }
830 #endif /* defined(MBEDTLS_GCM_ALT) */
831             if( ret != 0 )
832                 goto exit;
833 
834             if ( memcmp( buf, ct_test_data[j * 6 + i],
835                          pt_len_test_data[i] ) != 0 ||
836                  memcmp( tag_buf, tag_test_data[j * 6 + i], 16 ) != 0 )
837             {
838                 ret = 1;
839                 goto exit;
840             }
841 
842             mbedtls_gcm_free( &ctx );
843 
844             if( verbose != 0 )
845                 mbedtls_printf( "passed\n" );
846 
847             mbedtls_gcm_init( &ctx );
848 
849             if( verbose != 0 )
850                 mbedtls_printf( "  AES-GCM-%3d #%d (%s): ",
851                                 key_len, i, "dec" );
852 
853             ret = mbedtls_gcm_setkey( &ctx, cipher,
854                                       key_test_data[key_index_test_data[i]],
855                                       key_len );
856             if( ret != 0 )
857                 goto exit;
858 
859             ret = mbedtls_gcm_crypt_and_tag( &ctx, MBEDTLS_GCM_DECRYPT,
860                                 pt_len_test_data[i],
861                                 iv_test_data[iv_index_test_data[i]],
862                                 iv_len_test_data[i],
863                                 additional_test_data[add_index_test_data[i]],
864                                 add_len_test_data[i],
865                                 ct_test_data[j * 6 + i], buf, 16, tag_buf );
866 
867             if( ret != 0 )
868                 goto exit;
869 
870             if( memcmp( buf, pt_test_data[pt_index_test_data[i]],
871                         pt_len_test_data[i] ) != 0 ||
872                 memcmp( tag_buf, tag_test_data[j * 6 + i], 16 ) != 0 )
873             {
874                 ret = 1;
875                 goto exit;
876             }
877 
878             mbedtls_gcm_free( &ctx );
879 
880             if( verbose != 0 )
881                 mbedtls_printf( "passed\n" );
882 
883             mbedtls_gcm_init( &ctx );
884 
885             if( verbose != 0 )
886                 mbedtls_printf( "  AES-GCM-%3d #%d split (%s): ",
887                                 key_len, i, "enc" );
888 
889             ret = mbedtls_gcm_setkey( &ctx, cipher,
890                                       key_test_data[key_index_test_data[i]],
891                                       key_len );
892             if( ret != 0 )
893                 goto exit;
894 
895             ret = mbedtls_gcm_starts( &ctx, MBEDTLS_GCM_ENCRYPT,
896                                   iv_test_data[iv_index_test_data[i]],
897                                   iv_len_test_data[i],
898                                   additional_test_data[add_index_test_data[i]],
899                                   add_len_test_data[i] );
900             if( ret != 0 )
901                 goto exit;
902 
903             if( pt_len_test_data[i] > 32 )
904             {
905                 size_t rest_len = pt_len_test_data[i] - 32;
906                 ret = mbedtls_gcm_update( &ctx, 32,
907                                           pt_test_data[pt_index_test_data[i]],
908                                           buf );
909                 if( ret != 0 )
910                     goto exit;
911 
912                 ret = mbedtls_gcm_update( &ctx, rest_len,
913                                       pt_test_data[pt_index_test_data[i]] + 32,
914                                       buf + 32 );
915                 if( ret != 0 )
916                     goto exit;
917             }
918             else
919             {
920                 ret = mbedtls_gcm_update( &ctx, pt_len_test_data[i],
921                                           pt_test_data[pt_index_test_data[i]],
922                                           buf );
923                 if( ret != 0 )
924                     goto exit;
925             }
926 
927             ret = mbedtls_gcm_finish( &ctx, tag_buf, 16 );
928             if( ret != 0 )
929                 goto exit;
930 
931             if( memcmp( buf, ct_test_data[j * 6 + i],
932                         pt_len_test_data[i] ) != 0 ||
933                 memcmp( tag_buf, tag_test_data[j * 6 + i], 16 ) != 0 )
934             {
935                 ret = 1;
936                 goto exit;
937             }
938 
939             mbedtls_gcm_free( &ctx );
940 
941             if( verbose != 0 )
942                 mbedtls_printf( "passed\n" );
943 
944             mbedtls_gcm_init( &ctx );
945 
946             if( verbose != 0 )
947                 mbedtls_printf( "  AES-GCM-%3d #%d split (%s): ",
948                                 key_len, i, "dec" );
949 
950             ret = mbedtls_gcm_setkey( &ctx, cipher,
951                                       key_test_data[key_index_test_data[i]],
952                                       key_len );
953             if( ret != 0 )
954                 goto exit;
955 
956             ret = mbedtls_gcm_starts( &ctx, MBEDTLS_GCM_DECRYPT,
957                               iv_test_data[iv_index_test_data[i]],
958                               iv_len_test_data[i],
959                               additional_test_data[add_index_test_data[i]],
960                               add_len_test_data[i] );
961             if( ret != 0 )
962                 goto exit;
963 
964             if( pt_len_test_data[i] > 32 )
965             {
966                 size_t rest_len = pt_len_test_data[i] - 32;
967                 ret = mbedtls_gcm_update( &ctx, 32, ct_test_data[j * 6 + i],
968                                           buf );
969                 if( ret != 0 )
970                     goto exit;
971 
972                 ret = mbedtls_gcm_update( &ctx, rest_len,
973                                           ct_test_data[j * 6 + i] + 32,
974                                           buf + 32 );
975                 if( ret != 0 )
976                     goto exit;
977             }
978             else
979             {
980                 ret = mbedtls_gcm_update( &ctx, pt_len_test_data[i],
981                                           ct_test_data[j * 6 + i],
982                                           buf );
983                 if( ret != 0 )
984                     goto exit;
985             }
986 
987             ret = mbedtls_gcm_finish( &ctx, tag_buf, 16 );
988             if( ret != 0 )
989                 goto exit;
990 
991             if( memcmp( buf, pt_test_data[pt_index_test_data[i]],
992                         pt_len_test_data[i] ) != 0 ||
993                 memcmp( tag_buf, tag_test_data[j * 6 + i], 16 ) != 0 )
994             {
995                 ret = 1;
996                 goto exit;
997             }
998 
999             mbedtls_gcm_free( &ctx );
1000 
1001             if( verbose != 0 )
1002                 mbedtls_printf( "passed\n" );
1003         }
1004     }
1005 
1006     if( verbose != 0 )
1007         mbedtls_printf( "\n" );
1008 
1009     ret = 0;
1010 
1011 exit:
1012     if( ret != 0 )
1013     {
1014         if( verbose != 0 )
1015             mbedtls_printf( "failed\n" );
1016         mbedtls_gcm_free( &ctx );
1017     }
1018 
1019     return( ret );
1020 }
1021 
1022 #endif /* MBEDTLS_SELF_TEST && MBEDTLS_AES_C */
1023 
1024 #endif /* MBEDTLS_GCM_C */
1025