4 * \brief Generic cipher wrapper for mbed TLS
6 * \author Adriaan de Jong <dejong@fox-it.com>
8 * Copyright (C) 2006-2015, ARM Limited, All Rights Reserved
9 * SPDX-License-Identifier: GPL-2.0
11 * This program is free software; you can redistribute it and/or modify
12 * it under the terms of the GNU General Public License as published by
13 * the Free Software Foundation; either version 2 of the License, or
14 * (at your option) any later version.
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License along
22 * with this program; if not, write to the Free Software Foundation, Inc.,
23 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
25 * This file is part of mbed TLS (https://tls.mbed.org)
28 #if !defined(MBEDTLS_CONFIG_FILE)
29 #include "mbedtls/config.h"
31 #include MBEDTLS_CONFIG_FILE
34 #if defined(MBEDTLS_CIPHER_C)
36 #include "mbedtls/cipher.h"
37 #include "mbedtls/cipher_internal.h"
42 #if defined(MBEDTLS_GCM_C)
43 #include "mbedtls/gcm.h"
46 #if defined(MBEDTLS_CCM_C)
47 #include "mbedtls/ccm.h"
50 #if defined(MBEDTLS_CMAC_C)
51 #include "mbedtls/cmac.h"
54 #if defined(MBEDTLS_PLATFORM_C)
55 #include "mbedtls/platform.h"
57 #define mbedtls_calloc calloc
58 #define mbedtls_free free
61 /* Implementation that should never be optimized out by the compiler */
62 static void mbedtls_zeroize( void *v
, size_t n
) {
63 volatile unsigned char *p
= (unsigned char*)v
; while( n
-- ) *p
++ = 0;
66 static int supported_init
= 0;
68 const int *mbedtls_cipher_list( void )
70 const mbedtls_cipher_definition_t
*def
;
73 if( ! supported_init
)
75 def
= mbedtls_cipher_definitions
;
76 type
= mbedtls_cipher_supported
;
78 while( def
->type
!= 0 )
79 *type
++ = (*def
++).type
;
86 return( mbedtls_cipher_supported
);
89 const mbedtls_cipher_info_t
*mbedtls_cipher_info_from_type( const mbedtls_cipher_type_t cipher_type
)
91 const mbedtls_cipher_definition_t
*def
;
93 for( def
= mbedtls_cipher_definitions
; def
->info
!= NULL
; def
++ )
94 if( def
->type
== cipher_type
)
100 const mbedtls_cipher_info_t
*mbedtls_cipher_info_from_string( const char *cipher_name
)
102 const mbedtls_cipher_definition_t
*def
;
104 if( NULL
== cipher_name
)
107 for( def
= mbedtls_cipher_definitions
; def
->info
!= NULL
; def
++ )
108 if( ! strcmp( def
->info
->name
, cipher_name
) )
114 const mbedtls_cipher_info_t
*mbedtls_cipher_info_from_values( const mbedtls_cipher_id_t cipher_id
,
116 const mbedtls_cipher_mode_t mode
)
118 const mbedtls_cipher_definition_t
*def
;
120 for( def
= mbedtls_cipher_definitions
; def
->info
!= NULL
; def
++ )
121 if( def
->info
->base
->cipher
== cipher_id
&&
122 def
->info
->key_bitlen
== (unsigned) key_bitlen
&&
123 def
->info
->mode
== mode
)
129 void mbedtls_cipher_init( mbedtls_cipher_context_t
*ctx
)
131 memset( ctx
, 0, sizeof( mbedtls_cipher_context_t
) );
134 void mbedtls_cipher_free( mbedtls_cipher_context_t
*ctx
)
139 #if defined(MBEDTLS_CMAC_C)
142 mbedtls_zeroize( ctx
->cmac_ctx
, sizeof( mbedtls_cmac_context_t
) );
143 mbedtls_free( ctx
->cmac_ctx
);
147 if( ctx
->cipher_ctx
)
148 ctx
->cipher_info
->base
->ctx_free_func( ctx
->cipher_ctx
);
150 mbedtls_zeroize( ctx
, sizeof(mbedtls_cipher_context_t
) );
153 int mbedtls_cipher_setup( mbedtls_cipher_context_t
*ctx
, const mbedtls_cipher_info_t
*cipher_info
)
155 if( NULL
== cipher_info
|| NULL
== ctx
)
156 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
158 memset( ctx
, 0, sizeof( mbedtls_cipher_context_t
) );
160 if( NULL
== ( ctx
->cipher_ctx
= cipher_info
->base
->ctx_alloc_func() ) )
161 return( MBEDTLS_ERR_CIPHER_ALLOC_FAILED
);
163 ctx
->cipher_info
= cipher_info
;
165 #if defined(MBEDTLS_CIPHER_MODE_WITH_PADDING)
167 * Ignore possible errors caused by a cipher mode that doesn't use padding
169 #if defined(MBEDTLS_CIPHER_PADDING_PKCS7)
170 (void) mbedtls_cipher_set_padding_mode( ctx
, MBEDTLS_PADDING_PKCS7
);
172 (void) mbedtls_cipher_set_padding_mode( ctx
, MBEDTLS_PADDING_NONE
);
174 #endif /* MBEDTLS_CIPHER_MODE_WITH_PADDING */
179 int mbedtls_cipher_setkey( mbedtls_cipher_context_t
*ctx
, const unsigned char *key
,
180 int key_bitlen
, const mbedtls_operation_t operation
)
182 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
)
183 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
185 if( ( ctx
->cipher_info
->flags
& MBEDTLS_CIPHER_VARIABLE_KEY_LEN
) == 0 &&
186 (int) ctx
->cipher_info
->key_bitlen
!= key_bitlen
)
188 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
191 ctx
->key_bitlen
= key_bitlen
;
192 ctx
->operation
= operation
;
195 * For CFB and CTR mode always use the encryption key schedule
197 if( MBEDTLS_ENCRYPT
== operation
||
198 MBEDTLS_MODE_CFB
== ctx
->cipher_info
->mode
||
199 MBEDTLS_MODE_CTR
== ctx
->cipher_info
->mode
)
201 return ctx
->cipher_info
->base
->setkey_enc_func( ctx
->cipher_ctx
, key
,
205 if( MBEDTLS_DECRYPT
== operation
)
206 return ctx
->cipher_info
->base
->setkey_dec_func( ctx
->cipher_ctx
, key
,
209 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
212 int mbedtls_cipher_set_iv( mbedtls_cipher_context_t
*ctx
,
213 const unsigned char *iv
, size_t iv_len
)
215 size_t actual_iv_size
;
216 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
)
217 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
218 else if( NULL
== iv
&& iv_len
!= 0 )
219 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
221 if( NULL
== iv
&& iv_len
== 0 )
224 /* avoid buffer overflow in ctx->iv */
225 if( iv_len
> MBEDTLS_MAX_IV_LENGTH
)
226 return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
);
228 if( ( ctx
->cipher_info
->flags
& MBEDTLS_CIPHER_VARIABLE_IV_LEN
) != 0 )
229 actual_iv_size
= iv_len
;
232 actual_iv_size
= ctx
->cipher_info
->iv_size
;
234 /* avoid reading past the end of input buffer */
235 if( actual_iv_size
> iv_len
)
236 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
238 if ( actual_iv_size
!= 0 )
240 memcpy( ctx
->iv
, iv
, actual_iv_size
);
241 ctx
->iv_size
= actual_iv_size
;
247 int mbedtls_cipher_reset( mbedtls_cipher_context_t
*ctx
)
249 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
)
250 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
252 ctx
->unprocessed_len
= 0;
257 #if defined(MBEDTLS_GCM_C)
258 int mbedtls_cipher_update_ad( mbedtls_cipher_context_t
*ctx
,
259 const unsigned char *ad
, size_t ad_len
)
261 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
)
262 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
264 if( MBEDTLS_MODE_GCM
== ctx
->cipher_info
->mode
)
266 return mbedtls_gcm_starts( (mbedtls_gcm_context
*) ctx
->cipher_ctx
, ctx
->operation
,
267 ctx
->iv
, ctx
->iv_size
, ad
, ad_len
);
272 #endif /* MBEDTLS_GCM_C */
274 int mbedtls_cipher_update( mbedtls_cipher_context_t
*ctx
, const unsigned char *input
,
275 size_t ilen
, unsigned char *output
, size_t *olen
)
278 size_t block_size
= 0;
280 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
|| NULL
== olen
)
282 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
286 block_size
= mbedtls_cipher_get_block_size( ctx
);
288 if( ctx
->cipher_info
->mode
== MBEDTLS_MODE_ECB
)
290 if( ilen
!= block_size
)
291 return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED
);
295 if( 0 != ( ret
= ctx
->cipher_info
->base
->ecb_func( ctx
->cipher_ctx
,
296 ctx
->operation
, input
, output
) ) )
304 #if defined(MBEDTLS_GCM_C)
305 if( ctx
->cipher_info
->mode
== MBEDTLS_MODE_GCM
)
308 return mbedtls_gcm_update( (mbedtls_gcm_context
*) ctx
->cipher_ctx
, ilen
, input
,
313 if ( 0 == block_size
)
315 return MBEDTLS_ERR_CIPHER_INVALID_CONTEXT
;
318 if( input
== output
&&
319 ( ctx
->unprocessed_len
!= 0 || ilen
% block_size
) )
321 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
324 #if defined(MBEDTLS_CIPHER_MODE_CBC)
325 if( ctx
->cipher_info
->mode
== MBEDTLS_MODE_CBC
)
330 * If there is not enough data for a full block, cache it.
332 if( ( ctx
->operation
== MBEDTLS_DECRYPT
&& NULL
!= ctx
->add_padding
&&
333 ilen
<= block_size
- ctx
->unprocessed_len
) ||
334 ( ctx
->operation
== MBEDTLS_DECRYPT
&& NULL
== ctx
->add_padding
&&
335 ilen
< block_size
- ctx
->unprocessed_len
) ||
336 ( ctx
->operation
== MBEDTLS_ENCRYPT
&&
337 ilen
< block_size
- ctx
->unprocessed_len
) )
339 memcpy( &( ctx
->unprocessed_data
[ctx
->unprocessed_len
] ), input
,
342 ctx
->unprocessed_len
+= ilen
;
347 * Process cached data first
349 if( 0 != ctx
->unprocessed_len
)
351 copy_len
= block_size
- ctx
->unprocessed_len
;
353 memcpy( &( ctx
->unprocessed_data
[ctx
->unprocessed_len
] ), input
,
356 if( 0 != ( ret
= ctx
->cipher_info
->base
->cbc_func( ctx
->cipher_ctx
,
357 ctx
->operation
, block_size
, ctx
->iv
,
358 ctx
->unprocessed_data
, output
) ) )
364 output
+= block_size
;
365 ctx
->unprocessed_len
= 0;
372 * Cache final, incomplete block
376 if( 0 == block_size
)
378 return MBEDTLS_ERR_CIPHER_INVALID_CONTEXT
;
381 /* Encryption: only cache partial blocks
382 * Decryption w/ padding: always keep at least one whole block
383 * Decryption w/o padding: only cache partial blocks
385 copy_len
= ilen
% block_size
;
387 ctx
->operation
== MBEDTLS_DECRYPT
&&
388 NULL
!= ctx
->add_padding
)
390 copy_len
= block_size
;
393 memcpy( ctx
->unprocessed_data
, &( input
[ilen
- copy_len
] ),
396 ctx
->unprocessed_len
+= copy_len
;
401 * Process remaining full blocks
405 if( 0 != ( ret
= ctx
->cipher_info
->base
->cbc_func( ctx
->cipher_ctx
,
406 ctx
->operation
, ilen
, ctx
->iv
, input
, output
) ) )
416 #endif /* MBEDTLS_CIPHER_MODE_CBC */
418 #if defined(MBEDTLS_CIPHER_MODE_CFB)
419 if( ctx
->cipher_info
->mode
== MBEDTLS_MODE_CFB
)
421 if( 0 != ( ret
= ctx
->cipher_info
->base
->cfb_func( ctx
->cipher_ctx
,
422 ctx
->operation
, ilen
, &ctx
->unprocessed_len
, ctx
->iv
,
432 #endif /* MBEDTLS_CIPHER_MODE_CFB */
434 #if defined(MBEDTLS_CIPHER_MODE_CTR)
435 if( ctx
->cipher_info
->mode
== MBEDTLS_MODE_CTR
)
437 if( 0 != ( ret
= ctx
->cipher_info
->base
->ctr_func( ctx
->cipher_ctx
,
438 ilen
, &ctx
->unprocessed_len
, ctx
->iv
,
439 ctx
->unprocessed_data
, input
, output
) ) )
448 #endif /* MBEDTLS_CIPHER_MODE_CTR */
450 #if defined(MBEDTLS_CIPHER_MODE_STREAM)
451 if( ctx
->cipher_info
->mode
== MBEDTLS_MODE_STREAM
)
453 if( 0 != ( ret
= ctx
->cipher_info
->base
->stream_func( ctx
->cipher_ctx
,
454 ilen
, input
, output
) ) )
463 #endif /* MBEDTLS_CIPHER_MODE_STREAM */
465 return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
);
468 #if defined(MBEDTLS_CIPHER_MODE_WITH_PADDING)
469 #if defined(MBEDTLS_CIPHER_PADDING_PKCS7)
471 * PKCS7 (and PKCS5) padding: fill with ll bytes, with ll = padding_len
473 static void add_pkcs_padding( unsigned char *output
, size_t output_len
,
476 size_t padding_len
= output_len
- data_len
;
479 for( i
= 0; i
< padding_len
; i
++ )
480 output
[data_len
+ i
] = (unsigned char) padding_len
;
483 static int get_pkcs_padding( unsigned char *input
, size_t input_len
,
487 unsigned char padding_len
, bad
= 0;
489 if( NULL
== input
|| NULL
== data_len
)
490 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
492 padding_len
= input
[input_len
- 1];
493 *data_len
= input_len
- padding_len
;
495 /* Avoid logical || since it results in a branch */
496 bad
|= padding_len
> input_len
;
497 bad
|= padding_len
== 0;
499 /* The number of bytes checked must be independent of padding_len,
500 * so pick input_len, which is usually 8 or 16 (one block) */
501 pad_idx
= input_len
- padding_len
;
502 for( i
= 0; i
< input_len
; i
++ )
503 bad
|= ( input
[i
] ^ padding_len
) * ( i
>= pad_idx
);
505 return( MBEDTLS_ERR_CIPHER_INVALID_PADDING
* ( bad
!= 0 ) );
507 #endif /* MBEDTLS_CIPHER_PADDING_PKCS7 */
509 #if defined(MBEDTLS_CIPHER_PADDING_ONE_AND_ZEROS)
511 * One and zeros padding: fill with 80 00 ... 00
513 static void add_one_and_zeros_padding( unsigned char *output
,
514 size_t output_len
, size_t data_len
)
516 size_t padding_len
= output_len
- data_len
;
519 output
[data_len
] = 0x80;
520 for( i
= 1; i
< padding_len
; i
++ )
521 output
[data_len
+ i
] = 0x00;
524 static int get_one_and_zeros_padding( unsigned char *input
, size_t input_len
,
528 unsigned char done
= 0, prev_done
, bad
;
530 if( NULL
== input
|| NULL
== data_len
)
531 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
535 for( i
= input_len
; i
> 0; i
-- )
538 done
|= ( input
[i
- 1] != 0 );
539 *data_len
|= ( i
- 1 ) * ( done
!= prev_done
);
540 bad
^= input
[i
- 1] * ( done
!= prev_done
);
543 return( MBEDTLS_ERR_CIPHER_INVALID_PADDING
* ( bad
!= 0 ) );
546 #endif /* MBEDTLS_CIPHER_PADDING_ONE_AND_ZEROS */
548 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS_AND_LEN)
550 * Zeros and len padding: fill with 00 ... 00 ll, where ll is padding length
552 static void add_zeros_and_len_padding( unsigned char *output
,
553 size_t output_len
, size_t data_len
)
555 size_t padding_len
= output_len
- data_len
;
558 for( i
= 1; i
< padding_len
; i
++ )
559 output
[data_len
+ i
- 1] = 0x00;
560 output
[output_len
- 1] = (unsigned char) padding_len
;
563 static int get_zeros_and_len_padding( unsigned char *input
, size_t input_len
,
567 unsigned char padding_len
, bad
= 0;
569 if( NULL
== input
|| NULL
== data_len
)
570 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
572 padding_len
= input
[input_len
- 1];
573 *data_len
= input_len
- padding_len
;
575 /* Avoid logical || since it results in a branch */
576 bad
|= padding_len
> input_len
;
577 bad
|= padding_len
== 0;
579 /* The number of bytes checked must be independent of padding_len */
580 pad_idx
= input_len
- padding_len
;
581 for( i
= 0; i
< input_len
- 1; i
++ )
582 bad
|= input
[i
] * ( i
>= pad_idx
);
584 return( MBEDTLS_ERR_CIPHER_INVALID_PADDING
* ( bad
!= 0 ) );
586 #endif /* MBEDTLS_CIPHER_PADDING_ZEROS_AND_LEN */
588 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS)
590 * Zero padding: fill with 00 ... 00
592 static void add_zeros_padding( unsigned char *output
,
593 size_t output_len
, size_t data_len
)
597 for( i
= data_len
; i
< output_len
; i
++ )
601 static int get_zeros_padding( unsigned char *input
, size_t input_len
,
605 unsigned char done
= 0, prev_done
;
607 if( NULL
== input
|| NULL
== data_len
)
608 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
611 for( i
= input_len
; i
> 0; i
-- )
614 done
|= ( input
[i
-1] != 0 );
615 *data_len
|= i
* ( done
!= prev_done
);
620 #endif /* MBEDTLS_CIPHER_PADDING_ZEROS */
623 * No padding: don't pad :)
625 * There is no add_padding function (check for NULL in mbedtls_cipher_finish)
626 * but a trivial get_padding function
628 static int get_no_padding( unsigned char *input
, size_t input_len
,
631 if( NULL
== input
|| NULL
== data_len
)
632 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
634 *data_len
= input_len
;
638 #endif /* MBEDTLS_CIPHER_MODE_WITH_PADDING */
640 int mbedtls_cipher_finish( mbedtls_cipher_context_t
*ctx
,
641 unsigned char *output
, size_t *olen
)
643 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
|| NULL
== olen
)
644 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
648 if( MBEDTLS_MODE_CFB
== ctx
->cipher_info
->mode
||
649 MBEDTLS_MODE_CTR
== ctx
->cipher_info
->mode
||
650 MBEDTLS_MODE_GCM
== ctx
->cipher_info
->mode
||
651 MBEDTLS_MODE_STREAM
== ctx
->cipher_info
->mode
)
656 if( MBEDTLS_MODE_ECB
== ctx
->cipher_info
->mode
)
658 if( ctx
->unprocessed_len
!= 0 )
659 return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED
);
664 #if defined(MBEDTLS_CIPHER_MODE_CBC)
665 if( MBEDTLS_MODE_CBC
== ctx
->cipher_info
->mode
)
669 if( MBEDTLS_ENCRYPT
== ctx
->operation
)
671 /* check for 'no padding' mode */
672 if( NULL
== ctx
->add_padding
)
674 if( 0 != ctx
->unprocessed_len
)
675 return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED
);
680 ctx
->add_padding( ctx
->unprocessed_data
, mbedtls_cipher_get_iv_size( ctx
),
681 ctx
->unprocessed_len
);
683 else if( mbedtls_cipher_get_block_size( ctx
) != ctx
->unprocessed_len
)
686 * For decrypt operations, expect a full block,
687 * or an empty block if no padding
689 if( NULL
== ctx
->add_padding
&& 0 == ctx
->unprocessed_len
)
692 return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED
);
696 if( 0 != ( ret
= ctx
->cipher_info
->base
->cbc_func( ctx
->cipher_ctx
,
697 ctx
->operation
, mbedtls_cipher_get_block_size( ctx
), ctx
->iv
,
698 ctx
->unprocessed_data
, output
) ) )
703 /* Set output size for decryption */
704 if( MBEDTLS_DECRYPT
== ctx
->operation
)
705 return ctx
->get_padding( output
, mbedtls_cipher_get_block_size( ctx
),
708 /* Set output size for encryption */
709 *olen
= mbedtls_cipher_get_block_size( ctx
);
714 #endif /* MBEDTLS_CIPHER_MODE_CBC */
716 return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
);
719 #if defined(MBEDTLS_CIPHER_MODE_WITH_PADDING)
720 int mbedtls_cipher_set_padding_mode( mbedtls_cipher_context_t
*ctx
, mbedtls_cipher_padding_t mode
)
723 MBEDTLS_MODE_CBC
!= ctx
->cipher_info
->mode
)
725 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
730 #if defined(MBEDTLS_CIPHER_PADDING_PKCS7)
731 case MBEDTLS_PADDING_PKCS7
:
732 ctx
->add_padding
= add_pkcs_padding
;
733 ctx
->get_padding
= get_pkcs_padding
;
736 #if defined(MBEDTLS_CIPHER_PADDING_ONE_AND_ZEROS)
737 case MBEDTLS_PADDING_ONE_AND_ZEROS
:
738 ctx
->add_padding
= add_one_and_zeros_padding
;
739 ctx
->get_padding
= get_one_and_zeros_padding
;
742 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS_AND_LEN)
743 case MBEDTLS_PADDING_ZEROS_AND_LEN
:
744 ctx
->add_padding
= add_zeros_and_len_padding
;
745 ctx
->get_padding
= get_zeros_and_len_padding
;
748 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS)
749 case MBEDTLS_PADDING_ZEROS
:
750 ctx
->add_padding
= add_zeros_padding
;
751 ctx
->get_padding
= get_zeros_padding
;
754 case MBEDTLS_PADDING_NONE
:
755 ctx
->add_padding
= NULL
;
756 ctx
->get_padding
= get_no_padding
;
760 return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
);
765 #endif /* MBEDTLS_CIPHER_MODE_WITH_PADDING */
767 #if defined(MBEDTLS_GCM_C)
768 int mbedtls_cipher_write_tag( mbedtls_cipher_context_t
*ctx
,
769 unsigned char *tag
, size_t tag_len
)
771 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
|| NULL
== tag
)
772 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
774 if( MBEDTLS_ENCRYPT
!= ctx
->operation
)
775 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
777 if( MBEDTLS_MODE_GCM
== ctx
->cipher_info
->mode
)
778 return mbedtls_gcm_finish( (mbedtls_gcm_context
*) ctx
->cipher_ctx
, tag
, tag_len
);
783 int mbedtls_cipher_check_tag( mbedtls_cipher_context_t
*ctx
,
784 const unsigned char *tag
, size_t tag_len
)
788 if( NULL
== ctx
|| NULL
== ctx
->cipher_info
||
789 MBEDTLS_DECRYPT
!= ctx
->operation
)
791 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
794 if( MBEDTLS_MODE_GCM
== ctx
->cipher_info
->mode
)
796 unsigned char check_tag
[16];
800 if( tag_len
> sizeof( check_tag
) )
801 return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA
);
803 if( 0 != ( ret
= mbedtls_gcm_finish( (mbedtls_gcm_context
*) ctx
->cipher_ctx
,
804 check_tag
, tag_len
) ) )
809 /* Check the tag in "constant-time" */
810 for( diff
= 0, i
= 0; i
< tag_len
; i
++ )
811 diff
|= tag
[i
] ^ check_tag
[i
];
814 return( MBEDTLS_ERR_CIPHER_AUTH_FAILED
);
821 #endif /* MBEDTLS_GCM_C */
824 * Packet-oriented wrapper for non-AEAD modes
826 int mbedtls_cipher_crypt( mbedtls_cipher_context_t
*ctx
,
827 const unsigned char *iv
, size_t iv_len
,
828 const unsigned char *input
, size_t ilen
,
829 unsigned char *output
, size_t *olen
)
834 if( ( ret
= mbedtls_cipher_set_iv( ctx
, iv
, iv_len
) ) != 0 )
837 if( ( ret
= mbedtls_cipher_reset( ctx
) ) != 0 )
840 if( ( ret
= mbedtls_cipher_update( ctx
, input
, ilen
, output
, olen
) ) != 0 )
843 if( ( ret
= mbedtls_cipher_finish( ctx
, output
+ *olen
, &finish_olen
) ) != 0 )
846 *olen
+= finish_olen
;
851 #if defined(MBEDTLS_CIPHER_MODE_AEAD)
853 * Packet-oriented encryption for AEAD modes
855 int mbedtls_cipher_auth_encrypt( mbedtls_cipher_context_t
*ctx
,
856 const unsigned char *iv
, size_t iv_len
,
857 const unsigned char *ad
, size_t ad_len
,
858 const unsigned char *input
, size_t ilen
,
859 unsigned char *output
, size_t *olen
,
860 unsigned char *tag
, size_t tag_len
)
862 #if defined(MBEDTLS_GCM_C)
863 if( MBEDTLS_MODE_GCM
== ctx
->cipher_info
->mode
)
866 return( mbedtls_gcm_crypt_and_tag( ctx
->cipher_ctx
, MBEDTLS_GCM_ENCRYPT
, ilen
,
867 iv
, iv_len
, ad
, ad_len
, input
, output
,
870 #endif /* MBEDTLS_GCM_C */
871 #if defined(MBEDTLS_CCM_C)
872 if( MBEDTLS_MODE_CCM
== ctx
->cipher_info
->mode
)
875 return( mbedtls_ccm_encrypt_and_tag( ctx
->cipher_ctx
, ilen
,
876 iv
, iv_len
, ad
, ad_len
, input
, output
,
879 #endif /* MBEDTLS_CCM_C */
881 return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
);
885 * Packet-oriented decryption for AEAD modes
887 int mbedtls_cipher_auth_decrypt( mbedtls_cipher_context_t
*ctx
,
888 const unsigned char *iv
, size_t iv_len
,
889 const unsigned char *ad
, size_t ad_len
,
890 const unsigned char *input
, size_t ilen
,
891 unsigned char *output
, size_t *olen
,
892 const unsigned char *tag
, size_t tag_len
)
894 #if defined(MBEDTLS_GCM_C)
895 if( MBEDTLS_MODE_GCM
== ctx
->cipher_info
->mode
)
900 ret
= mbedtls_gcm_auth_decrypt( ctx
->cipher_ctx
, ilen
,
901 iv
, iv_len
, ad
, ad_len
,
902 tag
, tag_len
, input
, output
);
904 if( ret
== MBEDTLS_ERR_GCM_AUTH_FAILED
)
905 ret
= MBEDTLS_ERR_CIPHER_AUTH_FAILED
;
909 #endif /* MBEDTLS_GCM_C */
910 #if defined(MBEDTLS_CCM_C)
911 if( MBEDTLS_MODE_CCM
== ctx
->cipher_info
->mode
)
916 ret
= mbedtls_ccm_auth_decrypt( ctx
->cipher_ctx
, ilen
,
917 iv
, iv_len
, ad
, ad_len
,
918 input
, output
, tag
, tag_len
);
920 if( ret
== MBEDTLS_ERR_CCM_AUTH_FAILED
)
921 ret
= MBEDTLS_ERR_CIPHER_AUTH_FAILED
;
925 #endif /* MBEDTLS_CCM_C */
927 return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE
);
929 #endif /* MBEDTLS_CIPHER_MODE_AEAD */
931 #endif /* MBEDTLS_CIPHER_C */