xref: /reactos/dll/3rdparty/mbedtls/cipher.c (revision 682f85ad)
1 /**
2  * \file cipher.c
3  *
4  * \brief Generic cipher wrapper for mbed TLS
5  *
6  * \author Adriaan de Jong <dejong@fox-it.com>
7  *
8  *  Copyright (C) 2006-2015, ARM Limited, All Rights Reserved
9  *  SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
10  *
11  *  This file is provided under the Apache License 2.0, or the
12  *  GNU General Public License v2.0 or later.
13  *
14  *  **********
15  *  Apache License 2.0:
16  *
17  *  Licensed under the Apache License, Version 2.0 (the "License"); you may
18  *  not use this file except in compliance with the License.
19  *  You may obtain a copy of the License at
20  *
21  *  http://www.apache.org/licenses/LICENSE-2.0
22  *
23  *  Unless required by applicable law or agreed to in writing, software
24  *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
25  *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
26  *  See the License for the specific language governing permissions and
27  *  limitations under the License.
28  *
29  *  **********
30  *
31  *  **********
32  *  GNU General Public License v2.0 or later:
33  *
34  *  This program is free software; you can redistribute it and/or modify
35  *  it under the terms of the GNU General Public License as published by
36  *  the Free Software Foundation; either version 2 of the License, or
37  *  (at your option) any later version.
38  *
39  *  This program is distributed in the hope that it will be useful,
40  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
41  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
42  *  GNU General Public License for more details.
43  *
44  *  You should have received a copy of the GNU General Public License along
45  *  with this program; if not, write to the Free Software Foundation, Inc.,
46  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
47  *
48  *  **********
49  *
50  *  This file is part of mbed TLS (https://tls.mbed.org)
51  */
52 
53 #if !defined(MBEDTLS_CONFIG_FILE)
54 #include "mbedtls/config.h"
55 #else
56 #include MBEDTLS_CONFIG_FILE
57 #endif
58 
59 #if defined(MBEDTLS_CIPHER_C)
60 
61 #include "mbedtls/cipher.h"
62 #include "mbedtls/cipher_internal.h"
63 
64 #include <stdlib.h>
65 #include <string.h>
66 
67 #if defined(MBEDTLS_GCM_C)
68 #include "mbedtls/gcm.h"
69 #endif
70 
71 #if defined(MBEDTLS_CCM_C)
72 #include "mbedtls/ccm.h"
73 #endif
74 
75 #if defined(MBEDTLS_CMAC_C)
76 #include "mbedtls/cmac.h"
77 #endif
78 
79 #if defined(MBEDTLS_PLATFORM_C)
80 #include "mbedtls/platform.h"
81 #else
82 #define mbedtls_calloc calloc
83 #define mbedtls_free   free
84 #endif
85 
86 /* Implementation that should never be optimized out by the compiler */
87 static void mbedtls_zeroize( void *v, size_t n ) {
88     volatile unsigned char *p = (unsigned char*)v; while( n-- ) *p++ = 0;
89 }
90 
91 static int supported_init = 0;
92 
93 const int *mbedtls_cipher_list( void )
94 {
95     const mbedtls_cipher_definition_t *def;
96     int *type;
97 
98     if( ! supported_init )
99     {
100         def = mbedtls_cipher_definitions;
101         type = mbedtls_cipher_supported;
102 
103         while( def->type != 0 )
104             *type++ = (*def++).type;
105 
106         *type = 0;
107 
108         supported_init = 1;
109     }
110 
111     return( mbedtls_cipher_supported );
112 }
113 
114 const mbedtls_cipher_info_t *mbedtls_cipher_info_from_type( const mbedtls_cipher_type_t cipher_type )
115 {
116     const mbedtls_cipher_definition_t *def;
117 
118     for( def = mbedtls_cipher_definitions; def->info != NULL; def++ )
119         if( def->type == cipher_type )
120             return( def->info );
121 
122     return( NULL );
123 }
124 
125 const mbedtls_cipher_info_t *mbedtls_cipher_info_from_string( const char *cipher_name )
126 {
127     const mbedtls_cipher_definition_t *def;
128 
129     if( NULL == cipher_name )
130         return( NULL );
131 
132     for( def = mbedtls_cipher_definitions; def->info != NULL; def++ )
133         if( !  strcmp( def->info->name, cipher_name ) )
134             return( def->info );
135 
136     return( NULL );
137 }
138 
139 const mbedtls_cipher_info_t *mbedtls_cipher_info_from_values( const mbedtls_cipher_id_t cipher_id,
140                                               int key_bitlen,
141                                               const mbedtls_cipher_mode_t mode )
142 {
143     const mbedtls_cipher_definition_t *def;
144 
145     for( def = mbedtls_cipher_definitions; def->info != NULL; def++ )
146         if( def->info->base->cipher == cipher_id &&
147             def->info->key_bitlen == (unsigned) key_bitlen &&
148             def->info->mode == mode )
149             return( def->info );
150 
151     return( NULL );
152 }
153 
154 void mbedtls_cipher_init( mbedtls_cipher_context_t *ctx )
155 {
156     memset( ctx, 0, sizeof( mbedtls_cipher_context_t ) );
157 }
158 
159 void mbedtls_cipher_free( mbedtls_cipher_context_t *ctx )
160 {
161     if( ctx == NULL )
162         return;
163 
164 #if defined(MBEDTLS_CMAC_C)
165     if( ctx->cmac_ctx )
166     {
167        mbedtls_zeroize( ctx->cmac_ctx, sizeof( mbedtls_cmac_context_t ) );
168        mbedtls_free( ctx->cmac_ctx );
169     }
170 #endif
171 
172     if( ctx->cipher_ctx )
173         ctx->cipher_info->base->ctx_free_func( ctx->cipher_ctx );
174 
175     mbedtls_zeroize( ctx, sizeof(mbedtls_cipher_context_t) );
176 }
177 
178 int mbedtls_cipher_setup( mbedtls_cipher_context_t *ctx, const mbedtls_cipher_info_t *cipher_info )
179 {
180     if( NULL == cipher_info || NULL == ctx )
181         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
182 
183     memset( ctx, 0, sizeof( mbedtls_cipher_context_t ) );
184 
185     if( NULL == ( ctx->cipher_ctx = cipher_info->base->ctx_alloc_func() ) )
186         return( MBEDTLS_ERR_CIPHER_ALLOC_FAILED );
187 
188     ctx->cipher_info = cipher_info;
189 
190 #if defined(MBEDTLS_CIPHER_MODE_WITH_PADDING)
191     /*
192      * Ignore possible errors caused by a cipher mode that doesn't use padding
193      */
194 #if defined(MBEDTLS_CIPHER_PADDING_PKCS7)
195     (void) mbedtls_cipher_set_padding_mode( ctx, MBEDTLS_PADDING_PKCS7 );
196 #else
197     (void) mbedtls_cipher_set_padding_mode( ctx, MBEDTLS_PADDING_NONE );
198 #endif
199 #endif /* MBEDTLS_CIPHER_MODE_WITH_PADDING */
200 
201     return( 0 );
202 }
203 
204 int mbedtls_cipher_setkey( mbedtls_cipher_context_t *ctx, const unsigned char *key,
205         int key_bitlen, const mbedtls_operation_t operation )
206 {
207     if( NULL == ctx || NULL == ctx->cipher_info )
208         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
209 
210     if( ( ctx->cipher_info->flags & MBEDTLS_CIPHER_VARIABLE_KEY_LEN ) == 0 &&
211         (int) ctx->cipher_info->key_bitlen != key_bitlen )
212     {
213         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
214     }
215 
216     ctx->key_bitlen = key_bitlen;
217     ctx->operation = operation;
218 
219     /*
220      * For CFB and CTR mode always use the encryption key schedule
221      */
222     if( MBEDTLS_ENCRYPT == operation ||
223         MBEDTLS_MODE_CFB == ctx->cipher_info->mode ||
224         MBEDTLS_MODE_CTR == ctx->cipher_info->mode )
225     {
226         return ctx->cipher_info->base->setkey_enc_func( ctx->cipher_ctx, key,
227                 ctx->key_bitlen );
228     }
229 
230     if( MBEDTLS_DECRYPT == operation )
231         return ctx->cipher_info->base->setkey_dec_func( ctx->cipher_ctx, key,
232                 ctx->key_bitlen );
233 
234     return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
235 }
236 
237 int mbedtls_cipher_set_iv( mbedtls_cipher_context_t *ctx,
238                    const unsigned char *iv, size_t iv_len )
239 {
240     size_t actual_iv_size;
241     if( NULL == ctx || NULL == ctx->cipher_info )
242         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
243     else if( NULL == iv && iv_len != 0  )
244         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
245 
246     if( NULL == iv && iv_len == 0 )
247         ctx->iv_size = 0;
248 
249     /* avoid buffer overflow in ctx->iv */
250     if( iv_len > MBEDTLS_MAX_IV_LENGTH )
251         return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
252 
253     if( ( ctx->cipher_info->flags & MBEDTLS_CIPHER_VARIABLE_IV_LEN ) != 0 )
254         actual_iv_size = iv_len;
255     else
256     {
257         actual_iv_size = ctx->cipher_info->iv_size;
258 
259         /* avoid reading past the end of input buffer */
260         if( actual_iv_size > iv_len )
261             return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
262     }
263     if ( actual_iv_size != 0 )
264     {
265         memcpy( ctx->iv, iv, actual_iv_size );
266         ctx->iv_size = actual_iv_size;
267     }
268 
269     return( 0 );
270 }
271 
272 int mbedtls_cipher_reset( mbedtls_cipher_context_t *ctx )
273 {
274     if( NULL == ctx || NULL == ctx->cipher_info )
275         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
276 
277     ctx->unprocessed_len = 0;
278 
279     return( 0 );
280 }
281 
282 #if defined(MBEDTLS_GCM_C)
283 int mbedtls_cipher_update_ad( mbedtls_cipher_context_t *ctx,
284                       const unsigned char *ad, size_t ad_len )
285 {
286     if( NULL == ctx || NULL == ctx->cipher_info )
287         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
288 
289     if( MBEDTLS_MODE_GCM == ctx->cipher_info->mode )
290     {
291         return mbedtls_gcm_starts( (mbedtls_gcm_context *) ctx->cipher_ctx, ctx->operation,
292                            ctx->iv, ctx->iv_size, ad, ad_len );
293     }
294 
295     return( 0 );
296 }
297 #endif /* MBEDTLS_GCM_C */
298 
299 int mbedtls_cipher_update( mbedtls_cipher_context_t *ctx, const unsigned char *input,
300                    size_t ilen, unsigned char *output, size_t *olen )
301 {
302     int ret;
303     size_t block_size = 0;
304 
305     if( NULL == ctx || NULL == ctx->cipher_info || NULL == olen )
306     {
307         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
308     }
309 
310     *olen = 0;
311     block_size = mbedtls_cipher_get_block_size( ctx );
312     if ( 0 == block_size )
313     {
314         return( MBEDTLS_ERR_CIPHER_INVALID_CONTEXT );
315     }
316 
317     if( ctx->cipher_info->mode == MBEDTLS_MODE_ECB )
318     {
319         if( ilen != block_size )
320             return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED );
321 
322         *olen = ilen;
323 
324         if( 0 != ( ret = ctx->cipher_info->base->ecb_func( ctx->cipher_ctx,
325                     ctx->operation, input, output ) ) )
326         {
327             return( ret );
328         }
329 
330         return( 0 );
331     }
332 
333 #if defined(MBEDTLS_GCM_C)
334     if( ctx->cipher_info->mode == MBEDTLS_MODE_GCM )
335     {
336         *olen = ilen;
337         return mbedtls_gcm_update( (mbedtls_gcm_context *) ctx->cipher_ctx, ilen, input,
338                            output );
339     }
340 #endif
341 
342     if( input == output &&
343        ( ctx->unprocessed_len != 0 || ilen % block_size ) )
344     {
345         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
346     }
347 
348 #if defined(MBEDTLS_CIPHER_MODE_CBC)
349     if( ctx->cipher_info->mode == MBEDTLS_MODE_CBC )
350     {
351         size_t copy_len = 0;
352 
353         /*
354          * If there is not enough data for a full block, cache it.
355          */
356         if( ( ctx->operation == MBEDTLS_DECRYPT && NULL != ctx->add_padding &&
357                 ilen <= block_size - ctx->unprocessed_len ) ||
358             ( ctx->operation == MBEDTLS_DECRYPT && NULL == ctx->add_padding &&
359                 ilen < block_size - ctx->unprocessed_len ) ||
360              ( ctx->operation == MBEDTLS_ENCRYPT &&
361                 ilen < block_size - ctx->unprocessed_len ) )
362         {
363             memcpy( &( ctx->unprocessed_data[ctx->unprocessed_len] ), input,
364                     ilen );
365 
366             ctx->unprocessed_len += ilen;
367             return( 0 );
368         }
369 
370         /*
371          * Process cached data first
372          */
373         if( 0 != ctx->unprocessed_len )
374         {
375             copy_len = block_size - ctx->unprocessed_len;
376 
377             memcpy( &( ctx->unprocessed_data[ctx->unprocessed_len] ), input,
378                     copy_len );
379 
380             if( 0 != ( ret = ctx->cipher_info->base->cbc_func( ctx->cipher_ctx,
381                     ctx->operation, block_size, ctx->iv,
382                     ctx->unprocessed_data, output ) ) )
383             {
384                 return( ret );
385             }
386 
387             *olen += block_size;
388             output += block_size;
389             ctx->unprocessed_len = 0;
390 
391             input += copy_len;
392             ilen -= copy_len;
393         }
394 
395         /*
396          * Cache final, incomplete block
397          */
398         if( 0 != ilen )
399         {
400             /* Encryption: only cache partial blocks
401              * Decryption w/ padding: always keep at least one whole block
402              * Decryption w/o padding: only cache partial blocks
403              */
404             copy_len = ilen % block_size;
405             if( copy_len == 0 &&
406                 ctx->operation == MBEDTLS_DECRYPT &&
407                 NULL != ctx->add_padding)
408             {
409                 copy_len = block_size;
410             }
411 
412             memcpy( ctx->unprocessed_data, &( input[ilen - copy_len] ),
413                     copy_len );
414 
415             ctx->unprocessed_len += copy_len;
416             ilen -= copy_len;
417         }
418 
419         /*
420          * Process remaining full blocks
421          */
422         if( ilen )
423         {
424             if( 0 != ( ret = ctx->cipher_info->base->cbc_func( ctx->cipher_ctx,
425                     ctx->operation, ilen, ctx->iv, input, output ) ) )
426             {
427                 return( ret );
428             }
429 
430             *olen += ilen;
431         }
432 
433         return( 0 );
434     }
435 #endif /* MBEDTLS_CIPHER_MODE_CBC */
436 
437 #if defined(MBEDTLS_CIPHER_MODE_CFB)
438     if( ctx->cipher_info->mode == MBEDTLS_MODE_CFB )
439     {
440         if( 0 != ( ret = ctx->cipher_info->base->cfb_func( ctx->cipher_ctx,
441                 ctx->operation, ilen, &ctx->unprocessed_len, ctx->iv,
442                 input, output ) ) )
443         {
444             return( ret );
445         }
446 
447         *olen = ilen;
448 
449         return( 0 );
450     }
451 #endif /* MBEDTLS_CIPHER_MODE_CFB */
452 
453 #if defined(MBEDTLS_CIPHER_MODE_CTR)
454     if( ctx->cipher_info->mode == MBEDTLS_MODE_CTR )
455     {
456         if( 0 != ( ret = ctx->cipher_info->base->ctr_func( ctx->cipher_ctx,
457                 ilen, &ctx->unprocessed_len, ctx->iv,
458                 ctx->unprocessed_data, input, output ) ) )
459         {
460             return( ret );
461         }
462 
463         *olen = ilen;
464 
465         return( 0 );
466     }
467 #endif /* MBEDTLS_CIPHER_MODE_CTR */
468 
469 #if defined(MBEDTLS_CIPHER_MODE_STREAM)
470     if( ctx->cipher_info->mode == MBEDTLS_MODE_STREAM )
471     {
472         if( 0 != ( ret = ctx->cipher_info->base->stream_func( ctx->cipher_ctx,
473                                                     ilen, input, output ) ) )
474         {
475             return( ret );
476         }
477 
478         *olen = ilen;
479 
480         return( 0 );
481     }
482 #endif /* MBEDTLS_CIPHER_MODE_STREAM */
483 
484     return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
485 }
486 
487 #if defined(MBEDTLS_CIPHER_MODE_WITH_PADDING)
488 #if defined(MBEDTLS_CIPHER_PADDING_PKCS7)
489 /*
490  * PKCS7 (and PKCS5) padding: fill with ll bytes, with ll = padding_len
491  */
492 static void add_pkcs_padding( unsigned char *output, size_t output_len,
493         size_t data_len )
494 {
495     size_t padding_len = output_len - data_len;
496     unsigned char i;
497 
498     for( i = 0; i < padding_len; i++ )
499         output[data_len + i] = (unsigned char) padding_len;
500 }
501 
502 static int get_pkcs_padding( unsigned char *input, size_t input_len,
503         size_t *data_len )
504 {
505     size_t i, pad_idx;
506     unsigned char padding_len, bad = 0;
507 
508     if( NULL == input || NULL == data_len )
509         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
510 
511     padding_len = input[input_len - 1];
512     *data_len = input_len - padding_len;
513 
514     /* Avoid logical || since it results in a branch */
515     bad |= padding_len > input_len;
516     bad |= padding_len == 0;
517 
518     /* The number of bytes checked must be independent of padding_len,
519      * so pick input_len, which is usually 8 or 16 (one block) */
520     pad_idx = input_len - padding_len;
521     for( i = 0; i < input_len; i++ )
522         bad |= ( input[i] ^ padding_len ) * ( i >= pad_idx );
523 
524     return( MBEDTLS_ERR_CIPHER_INVALID_PADDING * ( bad != 0 ) );
525 }
526 #endif /* MBEDTLS_CIPHER_PADDING_PKCS7 */
527 
528 #if defined(MBEDTLS_CIPHER_PADDING_ONE_AND_ZEROS)
529 /*
530  * One and zeros padding: fill with 80 00 ... 00
531  */
532 static void add_one_and_zeros_padding( unsigned char *output,
533                                        size_t output_len, size_t data_len )
534 {
535     size_t padding_len = output_len - data_len;
536     unsigned char i = 0;
537 
538     output[data_len] = 0x80;
539     for( i = 1; i < padding_len; i++ )
540         output[data_len + i] = 0x00;
541 }
542 
543 static int get_one_and_zeros_padding( unsigned char *input, size_t input_len,
544                                       size_t *data_len )
545 {
546     size_t i;
547     unsigned char done = 0, prev_done, bad;
548 
549     if( NULL == input || NULL == data_len )
550         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
551 
552     bad = 0x80;
553     *data_len = 0;
554     for( i = input_len; i > 0; i-- )
555     {
556         prev_done = done;
557         done |= ( input[i - 1] != 0 );
558         *data_len |= ( i - 1 ) * ( done != prev_done );
559         bad ^= input[i - 1] * ( done != prev_done );
560     }
561 
562     return( MBEDTLS_ERR_CIPHER_INVALID_PADDING * ( bad != 0 ) );
563 
564 }
565 #endif /* MBEDTLS_CIPHER_PADDING_ONE_AND_ZEROS */
566 
567 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS_AND_LEN)
568 /*
569  * Zeros and len padding: fill with 00 ... 00 ll, where ll is padding length
570  */
571 static void add_zeros_and_len_padding( unsigned char *output,
572                                        size_t output_len, size_t data_len )
573 {
574     size_t padding_len = output_len - data_len;
575     unsigned char i = 0;
576 
577     for( i = 1; i < padding_len; i++ )
578         output[data_len + i - 1] = 0x00;
579     output[output_len - 1] = (unsigned char) padding_len;
580 }
581 
582 static int get_zeros_and_len_padding( unsigned char *input, size_t input_len,
583                                       size_t *data_len )
584 {
585     size_t i, pad_idx;
586     unsigned char padding_len, bad = 0;
587 
588     if( NULL == input || NULL == data_len )
589         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
590 
591     padding_len = input[input_len - 1];
592     *data_len = input_len - padding_len;
593 
594     /* Avoid logical || since it results in a branch */
595     bad |= padding_len > input_len;
596     bad |= padding_len == 0;
597 
598     /* The number of bytes checked must be independent of padding_len */
599     pad_idx = input_len - padding_len;
600     for( i = 0; i < input_len - 1; i++ )
601         bad |= input[i] * ( i >= pad_idx );
602 
603     return( MBEDTLS_ERR_CIPHER_INVALID_PADDING * ( bad != 0 ) );
604 }
605 #endif /* MBEDTLS_CIPHER_PADDING_ZEROS_AND_LEN */
606 
607 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS)
608 /*
609  * Zero padding: fill with 00 ... 00
610  */
611 static void add_zeros_padding( unsigned char *output,
612                                size_t output_len, size_t data_len )
613 {
614     size_t i;
615 
616     for( i = data_len; i < output_len; i++ )
617         output[i] = 0x00;
618 }
619 
620 static int get_zeros_padding( unsigned char *input, size_t input_len,
621                               size_t *data_len )
622 {
623     size_t i;
624     unsigned char done = 0, prev_done;
625 
626     if( NULL == input || NULL == data_len )
627         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
628 
629     *data_len = 0;
630     for( i = input_len; i > 0; i-- )
631     {
632         prev_done = done;
633         done |= ( input[i-1] != 0 );
634         *data_len |= i * ( done != prev_done );
635     }
636 
637     return( 0 );
638 }
639 #endif /* MBEDTLS_CIPHER_PADDING_ZEROS */
640 
641 /*
642  * No padding: don't pad :)
643  *
644  * There is no add_padding function (check for NULL in mbedtls_cipher_finish)
645  * but a trivial get_padding function
646  */
647 static int get_no_padding( unsigned char *input, size_t input_len,
648                               size_t *data_len )
649 {
650     if( NULL == input || NULL == data_len )
651         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
652 
653     *data_len = input_len;
654 
655     return( 0 );
656 }
657 #endif /* MBEDTLS_CIPHER_MODE_WITH_PADDING */
658 
659 int mbedtls_cipher_finish( mbedtls_cipher_context_t *ctx,
660                    unsigned char *output, size_t *olen )
661 {
662     if( NULL == ctx || NULL == ctx->cipher_info || NULL == olen )
663         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
664 
665     *olen = 0;
666 
667     if( MBEDTLS_MODE_CFB == ctx->cipher_info->mode ||
668         MBEDTLS_MODE_CTR == ctx->cipher_info->mode ||
669         MBEDTLS_MODE_GCM == ctx->cipher_info->mode ||
670         MBEDTLS_MODE_STREAM == ctx->cipher_info->mode )
671     {
672         return( 0 );
673     }
674 
675     if( MBEDTLS_MODE_ECB == ctx->cipher_info->mode )
676     {
677         if( ctx->unprocessed_len != 0 )
678             return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED );
679 
680         return( 0 );
681     }
682 
683 #if defined(MBEDTLS_CIPHER_MODE_CBC)
684     if( MBEDTLS_MODE_CBC == ctx->cipher_info->mode )
685     {
686         int ret = 0;
687 
688         if( MBEDTLS_ENCRYPT == ctx->operation )
689         {
690             /* check for 'no padding' mode */
691             if( NULL == ctx->add_padding )
692             {
693                 if( 0 != ctx->unprocessed_len )
694                     return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED );
695 
696                 return( 0 );
697             }
698 
699             ctx->add_padding( ctx->unprocessed_data, mbedtls_cipher_get_iv_size( ctx ),
700                     ctx->unprocessed_len );
701         }
702         else if( mbedtls_cipher_get_block_size( ctx ) != ctx->unprocessed_len )
703         {
704             /*
705              * For decrypt operations, expect a full block,
706              * or an empty block if no padding
707              */
708             if( NULL == ctx->add_padding && 0 == ctx->unprocessed_len )
709                 return( 0 );
710 
711             return( MBEDTLS_ERR_CIPHER_FULL_BLOCK_EXPECTED );
712         }
713 
714         /* cipher block */
715         if( 0 != ( ret = ctx->cipher_info->base->cbc_func( ctx->cipher_ctx,
716                 ctx->operation, mbedtls_cipher_get_block_size( ctx ), ctx->iv,
717                 ctx->unprocessed_data, output ) ) )
718         {
719             return( ret );
720         }
721 
722         /* Set output size for decryption */
723         if( MBEDTLS_DECRYPT == ctx->operation )
724             return ctx->get_padding( output, mbedtls_cipher_get_block_size( ctx ),
725                                      olen );
726 
727         /* Set output size for encryption */
728         *olen = mbedtls_cipher_get_block_size( ctx );
729         return( 0 );
730     }
731 #else
732     ((void) output);
733 #endif /* MBEDTLS_CIPHER_MODE_CBC */
734 
735     return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
736 }
737 
738 #if defined(MBEDTLS_CIPHER_MODE_WITH_PADDING)
739 int mbedtls_cipher_set_padding_mode( mbedtls_cipher_context_t *ctx, mbedtls_cipher_padding_t mode )
740 {
741     if( NULL == ctx ||
742         MBEDTLS_MODE_CBC != ctx->cipher_info->mode )
743     {
744         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
745     }
746 
747     switch( mode )
748     {
749 #if defined(MBEDTLS_CIPHER_PADDING_PKCS7)
750     case MBEDTLS_PADDING_PKCS7:
751         ctx->add_padding = add_pkcs_padding;
752         ctx->get_padding = get_pkcs_padding;
753         break;
754 #endif
755 #if defined(MBEDTLS_CIPHER_PADDING_ONE_AND_ZEROS)
756     case MBEDTLS_PADDING_ONE_AND_ZEROS:
757         ctx->add_padding = add_one_and_zeros_padding;
758         ctx->get_padding = get_one_and_zeros_padding;
759         break;
760 #endif
761 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS_AND_LEN)
762     case MBEDTLS_PADDING_ZEROS_AND_LEN:
763         ctx->add_padding = add_zeros_and_len_padding;
764         ctx->get_padding = get_zeros_and_len_padding;
765         break;
766 #endif
767 #if defined(MBEDTLS_CIPHER_PADDING_ZEROS)
768     case MBEDTLS_PADDING_ZEROS:
769         ctx->add_padding = add_zeros_padding;
770         ctx->get_padding = get_zeros_padding;
771         break;
772 #endif
773     case MBEDTLS_PADDING_NONE:
774         ctx->add_padding = NULL;
775         ctx->get_padding = get_no_padding;
776         break;
777 
778     default:
779         return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
780     }
781 
782     return( 0 );
783 }
784 #endif /* MBEDTLS_CIPHER_MODE_WITH_PADDING */
785 
786 #if defined(MBEDTLS_GCM_C)
787 int mbedtls_cipher_write_tag( mbedtls_cipher_context_t *ctx,
788                       unsigned char *tag, size_t tag_len )
789 {
790     if( NULL == ctx || NULL == ctx->cipher_info || NULL == tag )
791         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
792 
793     if( MBEDTLS_ENCRYPT != ctx->operation )
794         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
795 
796     if( MBEDTLS_MODE_GCM == ctx->cipher_info->mode )
797         return mbedtls_gcm_finish( (mbedtls_gcm_context *) ctx->cipher_ctx, tag, tag_len );
798 
799     return( 0 );
800 }
801 
802 int mbedtls_cipher_check_tag( mbedtls_cipher_context_t *ctx,
803                       const unsigned char *tag, size_t tag_len )
804 {
805     int ret;
806 
807     if( NULL == ctx || NULL == ctx->cipher_info ||
808         MBEDTLS_DECRYPT != ctx->operation )
809     {
810         return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
811     }
812 
813     if( MBEDTLS_MODE_GCM == ctx->cipher_info->mode )
814     {
815         unsigned char check_tag[16];
816         size_t i;
817         int diff;
818 
819         if( tag_len > sizeof( check_tag ) )
820             return( MBEDTLS_ERR_CIPHER_BAD_INPUT_DATA );
821 
822         if( 0 != ( ret = mbedtls_gcm_finish( (mbedtls_gcm_context *) ctx->cipher_ctx,
823                                      check_tag, tag_len ) ) )
824         {
825             return( ret );
826         }
827 
828         /* Check the tag in "constant-time" */
829         for( diff = 0, i = 0; i < tag_len; i++ )
830             diff |= tag[i] ^ check_tag[i];
831 
832         if( diff != 0 )
833             return( MBEDTLS_ERR_CIPHER_AUTH_FAILED );
834 
835         return( 0 );
836     }
837 
838     return( 0 );
839 }
840 #endif /* MBEDTLS_GCM_C */
841 
842 /*
843  * Packet-oriented wrapper for non-AEAD modes
844  */
845 int mbedtls_cipher_crypt( mbedtls_cipher_context_t *ctx,
846                   const unsigned char *iv, size_t iv_len,
847                   const unsigned char *input, size_t ilen,
848                   unsigned char *output, size_t *olen )
849 {
850     int ret;
851     size_t finish_olen;
852 
853     if( ( ret = mbedtls_cipher_set_iv( ctx, iv, iv_len ) ) != 0 )
854         return( ret );
855 
856     if( ( ret = mbedtls_cipher_reset( ctx ) ) != 0 )
857         return( ret );
858 
859     if( ( ret = mbedtls_cipher_update( ctx, input, ilen, output, olen ) ) != 0 )
860         return( ret );
861 
862     if( ( ret = mbedtls_cipher_finish( ctx, output + *olen, &finish_olen ) ) != 0 )
863         return( ret );
864 
865     *olen += finish_olen;
866 
867     return( 0 );
868 }
869 
870 #if defined(MBEDTLS_CIPHER_MODE_AEAD)
871 /*
872  * Packet-oriented encryption for AEAD modes
873  */
874 int mbedtls_cipher_auth_encrypt( mbedtls_cipher_context_t *ctx,
875                          const unsigned char *iv, size_t iv_len,
876                          const unsigned char *ad, size_t ad_len,
877                          const unsigned char *input, size_t ilen,
878                          unsigned char *output, size_t *olen,
879                          unsigned char *tag, size_t tag_len )
880 {
881 #if defined(MBEDTLS_GCM_C)
882     if( MBEDTLS_MODE_GCM == ctx->cipher_info->mode )
883     {
884         *olen = ilen;
885         return( mbedtls_gcm_crypt_and_tag( ctx->cipher_ctx, MBEDTLS_GCM_ENCRYPT, ilen,
886                                    iv, iv_len, ad, ad_len, input, output,
887                                    tag_len, tag ) );
888     }
889 #endif /* MBEDTLS_GCM_C */
890 #if defined(MBEDTLS_CCM_C)
891     if( MBEDTLS_MODE_CCM == ctx->cipher_info->mode )
892     {
893         *olen = ilen;
894         return( mbedtls_ccm_encrypt_and_tag( ctx->cipher_ctx, ilen,
895                                      iv, iv_len, ad, ad_len, input, output,
896                                      tag, tag_len ) );
897     }
898 #endif /* MBEDTLS_CCM_C */
899 
900     return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
901 }
902 
903 /*
904  * Packet-oriented decryption for AEAD modes
905  */
906 int mbedtls_cipher_auth_decrypt( mbedtls_cipher_context_t *ctx,
907                          const unsigned char *iv, size_t iv_len,
908                          const unsigned char *ad, size_t ad_len,
909                          const unsigned char *input, size_t ilen,
910                          unsigned char *output, size_t *olen,
911                          const unsigned char *tag, size_t tag_len )
912 {
913 #if defined(MBEDTLS_GCM_C)
914     if( MBEDTLS_MODE_GCM == ctx->cipher_info->mode )
915     {
916         int ret;
917 
918         *olen = ilen;
919         ret = mbedtls_gcm_auth_decrypt( ctx->cipher_ctx, ilen,
920                                 iv, iv_len, ad, ad_len,
921                                 tag, tag_len, input, output );
922 
923         if( ret == MBEDTLS_ERR_GCM_AUTH_FAILED )
924             ret = MBEDTLS_ERR_CIPHER_AUTH_FAILED;
925 
926         return( ret );
927     }
928 #endif /* MBEDTLS_GCM_C */
929 #if defined(MBEDTLS_CCM_C)
930     if( MBEDTLS_MODE_CCM == ctx->cipher_info->mode )
931     {
932         int ret;
933 
934         *olen = ilen;
935         ret = mbedtls_ccm_auth_decrypt( ctx->cipher_ctx, ilen,
936                                 iv, iv_len, ad, ad_len,
937                                 input, output, tag, tag_len );
938 
939         if( ret == MBEDTLS_ERR_CCM_AUTH_FAILED )
940             ret = MBEDTLS_ERR_CIPHER_AUTH_FAILED;
941 
942         return( ret );
943     }
944 #endif /* MBEDTLS_CCM_C */
945 
946     return( MBEDTLS_ERR_CIPHER_FEATURE_UNAVAILABLE );
947 }
948 #endif /* MBEDTLS_CIPHER_MODE_AEAD */
949 
950 #endif /* MBEDTLS_CIPHER_C */
951