blob: 29dbedeb7b8a5c813bd655584dc51824c9d567e6 [file] [log] [blame]
Ronald Cron7ceee8d2021-03-17 16:55:43 +01001/*
2 * PSA AEAD entry points
3 */
4/*
5 * Copyright The Mbed TLS Contributors
6 * SPDX-License-Identifier: Apache-2.0
7 *
8 * Licensed under the Apache License, Version 2.0 (the "License"); you may
9 * not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
11 *
12 * http://www.apache.org/licenses/LICENSE-2.0
13 *
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
16 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
19 */
20
21#include "common.h"
22
23#if defined(MBEDTLS_PSA_CRYPTO_C)
24
25#include "psa_crypto_aead.h"
Ronald Cron46f91782021-03-17 08:16:34 +010026#include "psa_crypto_core.h"
27
Paul Elliottadb8b162021-04-20 16:06:57 +010028#include <string.h>
29#include "mbedtls/platform.h"
30#if !defined(MBEDTLS_PLATFORM_C)
31#define mbedtls_calloc calloc
32#define mbedtls_free free
33#endif
34
Ronald Cron46f91782021-03-17 08:16:34 +010035#include "mbedtls/ccm.h"
36#include "mbedtls/chachapoly.h"
37#include "mbedtls/cipher.h"
38#include "mbedtls/gcm.h"
Paul Elliottadb8b162021-04-20 16:06:57 +010039#include "mbedtls/error.h"
Ronald Cron46f91782021-03-17 08:16:34 +010040
Ronald Cron46f91782021-03-17 08:16:34 +010041static psa_status_t psa_aead_setup(
Paul Elliottcbbde5f2021-05-10 18:19:46 +010042 mbedtls_psa_aead_operation_t *operation,
Ronald Cron46f91782021-03-17 08:16:34 +010043 const psa_key_attributes_t *attributes,
44 const uint8_t *key_buffer,
45 psa_algorithm_t alg )
46{
47 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
48 size_t key_bits;
Ronald Cronecbc0682021-03-26 13:25:17 +010049 const mbedtls_cipher_info_t *cipher_info;
Ronald Cron46f91782021-03-17 08:16:34 +010050 mbedtls_cipher_id_t cipher_id;
Ronald Cronecbc0682021-03-26 13:25:17 +010051 size_t full_tag_length = 0;
Ronald Cron46f91782021-03-17 08:16:34 +010052
53 key_bits = attributes->core.bits;
54
Ronald Cronecbc0682021-03-26 13:25:17 +010055 cipher_info = mbedtls_cipher_info_from_psa( alg,
56 attributes->core.type, key_bits,
57 &cipher_id );
58 if( cipher_info == NULL )
Ronald Cron46f91782021-03-17 08:16:34 +010059 return( PSA_ERROR_NOT_SUPPORTED );
60
61 switch( PSA_ALG_AEAD_WITH_SHORTENED_TAG( alg, 0 ) )
62 {
63#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
64 case PSA_ALG_AEAD_WITH_SHORTENED_TAG( PSA_ALG_CCM, 0 ):
Paul Elliott07a30c42021-04-20 14:13:23 +010065 operation->alg = PSA_ALG_CCM;
Ronald Cronecbc0682021-03-26 13:25:17 +010066 full_tag_length = 16;
Ronald Cron46f91782021-03-17 08:16:34 +010067 /* CCM allows the following tag lengths: 4, 6, 8, 10, 12, 14, 16.
68 * The call to mbedtls_ccm_encrypt_and_tag or
69 * mbedtls_ccm_auth_decrypt will validate the tag length. */
70 if( PSA_BLOCK_CIPHER_BLOCK_LENGTH( attributes->core.type ) != 16 )
71 return( PSA_ERROR_INVALID_ARGUMENT );
72
73 mbedtls_ccm_init( &operation->ctx.ccm );
74 status = mbedtls_to_psa_error(
75 mbedtls_ccm_setkey( &operation->ctx.ccm, cipher_id,
76 key_buffer, (unsigned int) key_bits ) );
77 if( status != PSA_SUCCESS )
78 return( status );
79 break;
80#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
81
82#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
83 case PSA_ALG_AEAD_WITH_SHORTENED_TAG( PSA_ALG_GCM, 0 ):
Paul Elliott07a30c42021-04-20 14:13:23 +010084 operation->alg = PSA_ALG_GCM;
Ronald Cronecbc0682021-03-26 13:25:17 +010085 full_tag_length = 16;
Ronald Cron46f91782021-03-17 08:16:34 +010086 /* GCM allows the following tag lengths: 4, 8, 12, 13, 14, 15, 16.
87 * The call to mbedtls_gcm_crypt_and_tag or
88 * mbedtls_gcm_auth_decrypt will validate the tag length. */
89 if( PSA_BLOCK_CIPHER_BLOCK_LENGTH( attributes->core.type ) != 16 )
90 return( PSA_ERROR_INVALID_ARGUMENT );
91
92 mbedtls_gcm_init( &operation->ctx.gcm );
93 status = mbedtls_to_psa_error(
94 mbedtls_gcm_setkey( &operation->ctx.gcm, cipher_id,
95 key_buffer, (unsigned int) key_bits ) );
96 if( status != PSA_SUCCESS )
97 return( status );
98 break;
99#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
100
101#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
102 case PSA_ALG_AEAD_WITH_SHORTENED_TAG( PSA_ALG_CHACHA20_POLY1305, 0 ):
Paul Elliott07a30c42021-04-20 14:13:23 +0100103 operation->alg = PSA_ALG_CHACHA20_POLY1305;
Ronald Cronecbc0682021-03-26 13:25:17 +0100104 full_tag_length = 16;
Ronald Cron46f91782021-03-17 08:16:34 +0100105 /* We only support the default tag length. */
106 if( alg != PSA_ALG_CHACHA20_POLY1305 )
107 return( PSA_ERROR_NOT_SUPPORTED );
108
109 mbedtls_chachapoly_init( &operation->ctx.chachapoly );
110 status = mbedtls_to_psa_error(
111 mbedtls_chachapoly_setkey( &operation->ctx.chachapoly,
112 key_buffer ) );
113 if( status != PSA_SUCCESS )
114 return( status );
115 break;
116#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
117
118 default:
119 return( PSA_ERROR_NOT_SUPPORTED );
120 }
121
Bence Szépkútiec174e22021-03-19 18:46:15 +0100122 if( PSA_AEAD_TAG_LENGTH( attributes->core.type,
123 key_bits, alg )
124 > full_tag_length )
Ronald Cron46f91782021-03-17 08:16:34 +0100125 return( PSA_ERROR_INVALID_ARGUMENT );
126
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100127 operation->key_type = psa_get_key_type( attributes );
128
129 operation->tag_length = PSA_AEAD_TAG_LENGTH( operation->key_type,
Bence Szépkútiec174e22021-03-19 18:46:15 +0100130 key_bits,
131 alg );
Ronald Cron46f91782021-03-17 08:16:34 +0100132
133 return( PSA_SUCCESS );
134}
135
136psa_status_t mbedtls_psa_aead_encrypt(
137 const psa_key_attributes_t *attributes,
138 const uint8_t *key_buffer, size_t key_buffer_size,
139 psa_algorithm_t alg,
140 const uint8_t *nonce, size_t nonce_length,
141 const uint8_t *additional_data, size_t additional_data_length,
142 const uint8_t *plaintext, size_t plaintext_length,
143 uint8_t *ciphertext, size_t ciphertext_size, size_t *ciphertext_length )
144{
145 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100146 mbedtls_psa_aead_operation_t operation = MBEDTLS_PSA_AEAD_OPERATION_INIT;
Ronald Cron46f91782021-03-17 08:16:34 +0100147 uint8_t *tag;
148 (void) key_buffer_size;
149
150 status = psa_aead_setup( &operation, attributes, key_buffer, alg );
151 if( status != PSA_SUCCESS )
152 goto exit;
153
154 /* For all currently supported modes, the tag is at the end of the
155 * ciphertext. */
156 if( ciphertext_size < ( plaintext_length + operation.tag_length ) )
157 {
158 status = PSA_ERROR_BUFFER_TOO_SMALL;
159 goto exit;
160 }
161 tag = ciphertext + plaintext_length;
162
Ronald Cron46f91782021-03-17 08:16:34 +0100163#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
Paul Elliott07a30c42021-04-20 14:13:23 +0100164 if( operation.alg == PSA_ALG_CCM )
Ronald Cron46f91782021-03-17 08:16:34 +0100165 {
166 status = mbedtls_to_psa_error(
167 mbedtls_ccm_encrypt_and_tag( &operation.ctx.ccm,
168 plaintext_length,
169 nonce, nonce_length,
170 additional_data,
171 additional_data_length,
172 plaintext, ciphertext,
173 tag, operation.tag_length ) );
174 }
175 else
176#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
Ronald Cron810eb162021-04-06 09:01:39 +0200177#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
Paul Elliott07a30c42021-04-20 14:13:23 +0100178 if( operation.alg == PSA_ALG_GCM )
Ronald Cron810eb162021-04-06 09:01:39 +0200179 {
180 status = mbedtls_to_psa_error(
181 mbedtls_gcm_crypt_and_tag( &operation.ctx.gcm,
182 MBEDTLS_GCM_ENCRYPT,
183 plaintext_length,
184 nonce, nonce_length,
185 additional_data, additional_data_length,
186 plaintext, ciphertext,
187 operation.tag_length, tag ) );
188 }
189 else
190#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
Ronald Cron46f91782021-03-17 08:16:34 +0100191#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
Paul Elliott07a30c42021-04-20 14:13:23 +0100192 if( operation.alg == PSA_ALG_CHACHA20_POLY1305 )
Ronald Cron46f91782021-03-17 08:16:34 +0100193 {
194 if( nonce_length != 12 || operation.tag_length != 16 )
195 {
196 status = PSA_ERROR_NOT_SUPPORTED;
197 goto exit;
198 }
199 status = mbedtls_to_psa_error(
200 mbedtls_chachapoly_encrypt_and_tag( &operation.ctx.chachapoly,
201 plaintext_length,
202 nonce,
203 additional_data,
204 additional_data_length,
205 plaintext,
206 ciphertext,
207 tag ) );
208 }
209 else
210#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
211 {
212 (void) tag;
213 return( PSA_ERROR_NOT_SUPPORTED );
214 }
215
216 if( status == PSA_SUCCESS )
217 *ciphertext_length = plaintext_length + operation.tag_length;
218
219exit:
Paul Elliottadb8b162021-04-20 16:06:57 +0100220 mbedtls_psa_aead_abort( &operation );
Ronald Cron46f91782021-03-17 08:16:34 +0100221
222 return( status );
223}
224
225/* Locate the tag in a ciphertext buffer containing the encrypted data
226 * followed by the tag. Return the length of the part preceding the tag in
227 * *plaintext_length. This is the size of the plaintext in modes where
228 * the encrypted data has the same size as the plaintext, such as
229 * CCM and GCM. */
230static psa_status_t psa_aead_unpadded_locate_tag( size_t tag_length,
231 const uint8_t *ciphertext,
232 size_t ciphertext_length,
233 size_t plaintext_size,
234 const uint8_t **p_tag )
235{
236 size_t payload_length;
237 if( tag_length > ciphertext_length )
238 return( PSA_ERROR_INVALID_ARGUMENT );
239 payload_length = ciphertext_length - tag_length;
240 if( payload_length > plaintext_size )
241 return( PSA_ERROR_BUFFER_TOO_SMALL );
242 *p_tag = ciphertext + payload_length;
243 return( PSA_SUCCESS );
244}
245
246psa_status_t mbedtls_psa_aead_decrypt(
247 const psa_key_attributes_t *attributes,
248 const uint8_t *key_buffer, size_t key_buffer_size,
249 psa_algorithm_t alg,
250 const uint8_t *nonce, size_t nonce_length,
251 const uint8_t *additional_data, size_t additional_data_length,
252 const uint8_t *ciphertext, size_t ciphertext_length,
253 uint8_t *plaintext, size_t plaintext_size, size_t *plaintext_length )
254{
255 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100256 mbedtls_psa_aead_operation_t operation = MBEDTLS_PSA_AEAD_OPERATION_INIT;
Ronald Cron46f91782021-03-17 08:16:34 +0100257 const uint8_t *tag = NULL;
258 (void) key_buffer_size;
259
260 status = psa_aead_setup( &operation, attributes, key_buffer, alg );
261 if( status != PSA_SUCCESS )
262 goto exit;
263
264 status = psa_aead_unpadded_locate_tag( operation.tag_length,
265 ciphertext, ciphertext_length,
266 plaintext_size, &tag );
267 if( status != PSA_SUCCESS )
268 goto exit;
269
Ronald Cron46f91782021-03-17 08:16:34 +0100270#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
Paul Elliott07a30c42021-04-20 14:13:23 +0100271 if( operation.alg == PSA_ALG_CCM )
Ronald Cron46f91782021-03-17 08:16:34 +0100272 {
273 status = mbedtls_to_psa_error(
274 mbedtls_ccm_auth_decrypt( &operation.ctx.ccm,
275 ciphertext_length - operation.tag_length,
276 nonce, nonce_length,
277 additional_data,
278 additional_data_length,
279 ciphertext, plaintext,
280 tag, operation.tag_length ) );
281 }
282 else
283#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
Ronald Cron810eb162021-04-06 09:01:39 +0200284#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
Paul Elliott07a30c42021-04-20 14:13:23 +0100285 if( operation.alg == PSA_ALG_GCM )
Ronald Cron810eb162021-04-06 09:01:39 +0200286 {
287 status = mbedtls_to_psa_error(
288 mbedtls_gcm_auth_decrypt( &operation.ctx.gcm,
289 ciphertext_length - operation.tag_length,
290 nonce, nonce_length,
291 additional_data,
292 additional_data_length,
293 tag, operation.tag_length,
294 ciphertext, plaintext ) );
295 }
296 else
297#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
Ronald Cron46f91782021-03-17 08:16:34 +0100298#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
Paul Elliott07a30c42021-04-20 14:13:23 +0100299 if( operation.alg == PSA_ALG_CHACHA20_POLY1305 )
Ronald Cron46f91782021-03-17 08:16:34 +0100300 {
301 if( nonce_length != 12 || operation.tag_length != 16 )
302 {
303 status = PSA_ERROR_NOT_SUPPORTED;
304 goto exit;
305 }
306 status = mbedtls_to_psa_error(
307 mbedtls_chachapoly_auth_decrypt( &operation.ctx.chachapoly,
308 ciphertext_length - operation.tag_length,
309 nonce,
310 additional_data,
311 additional_data_length,
312 tag,
313 ciphertext,
314 plaintext ) );
315 }
316 else
317#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
318 {
319 return( PSA_ERROR_NOT_SUPPORTED );
320 }
321
322 if( status == PSA_SUCCESS )
323 *plaintext_length = ciphertext_length - operation.tag_length;
324
325exit:
Paul Elliottadb8b162021-04-20 16:06:57 +0100326 mbedtls_psa_aead_abort( &operation );
Ronald Cron46f91782021-03-17 08:16:34 +0100327
328 if( status == PSA_SUCCESS )
329 *plaintext_length = ciphertext_length - operation.tag_length;
330 return( status );
331}
Ronald Cron7ceee8d2021-03-17 16:55:43 +0100332
Paul Elliottadb8b162021-04-20 16:06:57 +0100333/* Set the key and algorithm for a multipart authenticated encryption
334 * operation. */
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100335psa_status_t mbedtls_psa_aead_encrypt_setup( mbedtls_psa_aead_operation_t
336 *operation,
Paul Elliott2df40052021-05-07 17:52:18 +0100337 const psa_key_attributes_t
338 *attributes,
339 const uint8_t *key_buffer,
340 size_t key_buffer_size,
Paul Elliottadb8b162021-04-20 16:06:57 +0100341 psa_algorithm_t alg )
342{
343 psa_status_t status;
344
345 (void) key_buffer_size;
346
347 status = psa_aead_setup( operation, attributes, key_buffer, alg );
348
349 if( status == PSA_SUCCESS )
350 {
351 operation->is_encrypt = 1;
352 }
353
354 return ( status );
355}
356
357/* Set the key and algorithm for a multipart authenticated decryption
358 * operation. */
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100359psa_status_t mbedtls_psa_aead_decrypt_setup( mbedtls_psa_aead_operation_t
360 *operation,
Paul Elliott2df40052021-05-07 17:52:18 +0100361 const psa_key_attributes_t
362 *attributes,
363 const uint8_t *key_buffer,
364 size_t key_buffer_size,
Paul Elliottadb8b162021-04-20 16:06:57 +0100365 psa_algorithm_t alg )
366{
367 psa_status_t status;
368
369 (void) key_buffer_size;
370
371 status = psa_aead_setup( operation, attributes, key_buffer, alg );
372
373 if( status == PSA_SUCCESS )
374 {
375 operation->is_encrypt = 0;
376 }
377
378 return ( status );
379}
380
Paul Elliottadb8b162021-04-20 16:06:57 +0100381/* Set a nonce for the multipart AEAD operation*/
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100382psa_status_t mbedtls_psa_aead_set_nonce( mbedtls_psa_aead_operation_t
383 *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100384 const uint8_t *nonce,
385 size_t nonce_length )
386{
387 psa_status_t status;
388
Paul Elliottadb8b162021-04-20 16:06:57 +0100389 #if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
390 if( operation->alg == PSA_ALG_GCM )
391 {
392 /* GCM sets nonce once additional data has been supplied */
393 memcpy(operation->nonce, nonce, nonce_length);
394
395 /* We know that nonce size cannot exceed the uint8_t size */
396 operation->nonce_length = ( uint8_t ) nonce_length;
397 status = PSA_SUCCESS;
398 }
399 else
400#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
401#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
402 if( operation->alg == PSA_ALG_CCM )
403 {
404 /* Multipart CCM not supported as yet, so CCM is basically operating
405 in oneshot mode. Store the nonce as we need this later */
406 memcpy(operation->nonce, nonce, nonce_length);
407
408 /* We know that nonce size cannot exceed the uint8_t size */
409 operation->nonce_length = ( uint8_t ) nonce_length;
410 status = PSA_SUCCESS;
411 }
412 else
413#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
414#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
415 if( operation->alg == PSA_ALG_CHACHA20_POLY1305 )
416 {
417 if( nonce_length != 12 && nonce_length != 8)
418 {
419 return( PSA_ERROR_INVALID_ARGUMENT );
420 }
421
Paul Elliott2df40052021-05-07 17:52:18 +0100422 status = mbedtls_to_psa_error(
423 mbedtls_chachapoly_starts( &operation->ctx.chachapoly,
424 nonce,
425 operation->is_encrypt ?
426 MBEDTLS_CHACHAPOLY_ENCRYPT :
427 MBEDTLS_CHACHAPOLY_DECRYPT ) );
Paul Elliottadb8b162021-04-20 16:06:57 +0100428 }
429 else
430#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
431 {
432 ( void ) nonce;
433 ( void ) nonce_length;
434
435 return ( PSA_ERROR_NOT_SUPPORTED );
436 }
437
Paul Elliottadb8b162021-04-20 16:06:57 +0100438 return( status );
439}
440 /* Declare the lengths of the message and additional data for AEAD. */
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100441psa_status_t mbedtls_psa_aead_set_lengths( mbedtls_psa_aead_operation_t
442 *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100443 size_t ad_length,
444 size_t plaintext_length )
445{
446
Paul Elliottadb8b162021-04-20 16:06:57 +0100447#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
448 if( operation->alg == PSA_ALG_GCM )
449 {
Paul Elliottef29e172021-05-10 19:33:03 +0100450 /* Lengths can only be too large for GCM if size_t is bigger than 32
451 * bits. Without the guard this code will generate warnings on 32bit
452 builds */
Paul Elliottadb8b162021-04-20 16:06:57 +0100453#if SIZE_MAX > UINT32_MAX
454 if( ( (uint64_t) ad_length ) >> 61 != 0 ||
455 ( (uint64_t) plaintext_length ) > 0xFFFFFFFE0ull )
456 {
457 return ( PSA_ERROR_INVALID_ARGUMENT );
458 }
459#endif
460 }
461 else
462#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
463#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
464 if( operation->alg == PSA_ALG_CCM )
465 {
466 if( ad_length > 0xFF00 )
467 {
468 return ( PSA_ERROR_INVALID_ARGUMENT );
469 }
470 }
471 else
472#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
473#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
474 if( operation->alg == PSA_ALG_CHACHA20_POLY1305 )
475 {
476 /* No length restrictions for ChaChaPoly. */
477 }
478 else
479#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
480 {
481 ( void ) ad_length;
482 ( void ) plaintext_length;
483
484 return ( PSA_ERROR_NOT_SUPPORTED );
485 }
486
487 operation->ad_remaining = ad_length;
488 operation->body_remaining = plaintext_length;
489 operation->lengths_set = 1;
490
491 return ( PSA_SUCCESS );
492}
493
494/* Pass additional data to an active multipart AEAD operation. */
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100495psa_status_t mbedtls_psa_aead_update_ad( mbedtls_psa_aead_operation_t
496 *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100497 const uint8_t *input,
498 size_t input_length )
499{
500 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
501
Paul Elliottadb8b162021-04-20 16:06:57 +0100502 if( operation->lengths_set )
503 {
504 if ( operation->ad_remaining < input_length )
505 {
506 return( PSA_ERROR_INVALID_ARGUMENT );
507 }
508
509 operation->ad_remaining -= input_length;
510 }
511
512#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
513 if( operation->alg == PSA_ALG_GCM )
514 {
515 if( !operation->lengths_set || operation->ad_started )
516 {
517 return( PSA_ERROR_BAD_STATE );
518 }
519
520 /* GCM currently requires all the additional data to be passed in in
521 * one contigious buffer, so until that is re-done, we have to enforce
522 * this, as we cannot allocate a buffer to collate multiple calls into.
523 */
Paul Elliott72c10082021-04-23 19:02:16 +0100524 if( operation->ad_remaining != 0 )
Paul Elliottadb8b162021-04-20 16:06:57 +0100525 {
526 return ( PSA_ERROR_INVALID_ARGUMENT );
527 }
528
Paul Elliott2df40052021-05-07 17:52:18 +0100529 status = mbedtls_to_psa_error(
530 mbedtls_gcm_starts( &operation->ctx.gcm,
531 operation->is_encrypt ?
532 MBEDTLS_GCM_ENCRYPT : MBEDTLS_GCM_DECRYPT,
533 operation->nonce,
534 operation->nonce_length,
535 input,
536 input_length ) );
Paul Elliottadb8b162021-04-20 16:06:57 +0100537
538 }
539 else
540#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
541#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
542 if( operation->alg == PSA_ALG_CCM )
543 {
544 /* CCM requires all additional data to be passed in in one go at the
545 minute, as we are basically operating in oneshot mode. */
Paul Elliott72c10082021-04-23 19:02:16 +0100546 if( operation->ad_started )
Paul Elliottadb8b162021-04-20 16:06:57 +0100547 {
548 return( PSA_ERROR_BAD_STATE );
549 }
550
551 /* Save the additional data for later, this will be passed in
552 when we have the body. */
553 operation->ad_buffer = ( uint8_t * ) mbedtls_calloc(1, input_length );
554
555 if( operation->ad_buffer )
556 {
557 memcpy( operation->ad_buffer, input, input_length );
558 operation->ad_length = input_length;
Paul Elliott72c10082021-04-23 19:02:16 +0100559 status = PSA_SUCCESS;
Paul Elliottadb8b162021-04-20 16:06:57 +0100560 }
561 else
562 {
563 return ( PSA_ERROR_INSUFFICIENT_MEMORY );
564 }
565 }
566 else
567#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
568#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
569 if( operation->alg == PSA_ALG_CHACHA20_POLY1305 )
570 {
Paul Elliott2df40052021-05-07 17:52:18 +0100571 status = mbedtls_to_psa_error(
572 mbedtls_chachapoly_update_aad( &operation->ctx.chachapoly,
573 input,
574 input_length ) );
Paul Elliottadb8b162021-04-20 16:06:57 +0100575 }
576 else
577#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
578 {
579 (void) input;
580 (void) input_length;
581
582 return ( PSA_ERROR_NOT_SUPPORTED );
583 }
584
585 if( status == PSA_SUCCESS )
586 {
587 operation->ad_started = 1;
588 }
589
590 return ( status );
591}
592
593/* Encrypt or decrypt a message fragment in an active multipart AEAD
594 * operation.*/
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100595psa_status_t mbedtls_psa_aead_update( mbedtls_psa_aead_operation_t *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100596 const uint8_t *input,
597 size_t input_length,
598 uint8_t *output,
599 size_t output_size,
600 size_t *output_length )
601{
602 size_t update_output_size;
603 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
Paul Elliottfd3ca242021-04-25 18:10:42 +0100604 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Paul Elliottadb8b162021-04-20 16:06:57 +0100605
Paul Elliottfd3ca242021-04-25 18:10:42 +0100606 update_output_size = input_length;
Paul Elliottadb8b162021-04-20 16:06:57 +0100607
Paul Elliott72c10082021-04-23 19:02:16 +0100608 if( PSA_AEAD_UPDATE_OUTPUT_SIZE( operation->key_type, operation->alg,
609 input_length ) > output_size )
Paul Elliottadb8b162021-04-20 16:06:57 +0100610 {
611 return ( PSA_ERROR_BUFFER_TOO_SMALL );
612 }
613
614 if( operation->lengths_set)
615 {
616 /* Additional data length was supplied, but not all the additional
617 data was supplied.*/
618 if( operation->ad_remaining != 0 )
619 {
620 return ( PSA_ERROR_INVALID_ARGUMENT );
621 }
622
623 /* Too much data provided. */
624 if( operation->body_remaining < input_length )
625 {
626 return ( PSA_ERROR_INVALID_ARGUMENT );
627 }
628
629 operation->body_remaining -= input_length;
630 }
631
632#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
633 if( operation->alg == PSA_ALG_GCM )
634 {
635 /* For the time being set the requirement that all of the body data
636 * must be passed in in one update, rather than deal with the complexity
637 * of non block size aligned updates. This will be fixed in 3.0 when
638 we can change the signature of the GCM multipart functions */
639 if( !operation->lengths_set || operation->body_remaining != 0 )
640 {
641 return( PSA_ERROR_BAD_STATE );
642 }
643
Paul Elliott72c10082021-04-23 19:02:16 +0100644 if( !operation->ad_started )
Paul Elliottadb8b162021-04-20 16:06:57 +0100645 {
646 return( PSA_ERROR_BAD_STATE );
647 }
648
649 status = mbedtls_to_psa_error( mbedtls_gcm_update( &operation->ctx.gcm,
650 input_length,
651 input,
652 output ) );
653 }
654 else
655#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
656#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
657 if( operation->alg == PSA_ALG_CCM )
658 {
659 /* CCM dooes not support multipart yet, so all the input has to be
Paul Elliottfd3ca242021-04-25 18:10:42 +0100660 passed in in one go. */
Paul Elliott72c10082021-04-23 19:02:16 +0100661 if( operation->body_started )
Paul Elliottadb8b162021-04-20 16:06:57 +0100662 {
663 return( PSA_ERROR_BAD_STATE );
664 }
665
Paul Elliottfd3ca242021-04-25 18:10:42 +0100666 /* Need to store tag for Finish() / Verify() */
Paul Elliott2df40052021-05-07 17:52:18 +0100667 operation->tag_buffer =
668 ( uint8_t * ) mbedtls_calloc(1, operation->tag_length );
Paul Elliottadb8b162021-04-20 16:06:57 +0100669
Paul Elliottfd3ca242021-04-25 18:10:42 +0100670 if( operation->tag_buffer )
Paul Elliottadb8b162021-04-20 16:06:57 +0100671 {
Paul Elliottfd3ca242021-04-25 18:10:42 +0100672
673 if( operation->is_encrypt )
674 {
675 /* Perform oneshot CCM encryption with additional data already
676 stored, as CCM does not support multipart yet.*/
Paul Elliott2df40052021-05-07 17:52:18 +0100677 status = mbedtls_to_psa_error(
678 mbedtls_ccm_encrypt_and_tag( &operation->ctx.ccm,
679 input_length,
680 operation->nonce,
681 operation->nonce_length,
682 operation->ad_buffer,
683 operation->ad_length,
684 input,
685 output,
686 operation->tag_buffer,
687 operation->tag_length ) );
Paul Elliottfd3ca242021-04-25 18:10:42 +0100688
689 /* Even if the above operation fails, we no longer need the
690 additional data.*/
691 mbedtls_free(operation->ad_buffer);
692 operation->ad_buffer = NULL;
693 operation->ad_length = 0;
694 }
695 else
696 {
697 /* Need to back up the body data so we can do this again
698 later.*/
Paul Elliott2df40052021-05-07 17:52:18 +0100699 operation->body_buffer =
700 ( uint8_t * ) mbedtls_calloc(1, input_length );
Paul Elliottfd3ca242021-04-25 18:10:42 +0100701
702 if( operation->body_buffer )
703 {
704 memcpy( operation->body_buffer, input, input_length );
705 operation->body_length = input_length;
706
Paul Elliott2df40052021-05-07 17:52:18 +0100707 /* this will fail, as the tag is clearly false, but will
708 write the decrypted data to the output buffer.*/
709 ret = mbedtls_ccm_auth_decrypt( &operation->ctx.ccm,
710 input_length,
711 operation->nonce,
712 operation->nonce_length,
713 operation->ad_buffer,
714 operation->ad_length,
Paul Elliottfd3ca242021-04-25 18:10:42 +0100715 input, output,
716 operation->tag_buffer,
717 operation->tag_length );
718
719 if( ret == MBEDTLS_ERR_CCM_AUTH_FAILED )
720 {
721 status = PSA_SUCCESS;
722 }
723 else
724 {
725 status = mbedtls_to_psa_error( ret );
726 }
727 }
728 else
729 {
730 status = PSA_ERROR_INSUFFICIENT_MEMORY;
731 }
732 }
Paul Elliottadb8b162021-04-20 16:06:57 +0100733 }
734 else
735 {
Paul Elliottfd3ca242021-04-25 18:10:42 +0100736 status = PSA_ERROR_INSUFFICIENT_MEMORY;
Paul Elliottadb8b162021-04-20 16:06:57 +0100737 }
Paul Elliottadb8b162021-04-20 16:06:57 +0100738 }
739 else
740#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
741#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
742 if( operation->alg == PSA_ALG_CHACHA20_POLY1305 )
743 {
Paul Elliott2df40052021-05-07 17:52:18 +0100744 status = mbedtls_to_psa_error(
745 mbedtls_chachapoly_update( &operation->ctx.chachapoly,
746 input_length,
747 input,
748 output ) );
Paul Elliottadb8b162021-04-20 16:06:57 +0100749 }
750 else
751#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
752 {
753 (void) input;
754 (void) input_length;
755
756 return ( PSA_ERROR_NOT_SUPPORTED );
757 }
758
759 if( status == PSA_SUCCESS )
760 {
761 *output_length = update_output_size;
762 operation->body_started = 1;
763 }
764
765 return( status );
766}
767
768/* Common checks for both mbedtls_psa_aead_finish() and
769 mbedtls_psa_aead_verify() */
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100770static psa_status_t mbedtls_psa_aead_finish_checks( mbedtls_psa_aead_operation_t
Paul Elliott2df40052021-05-07 17:52:18 +0100771 *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100772 size_t output_size,
Paul Elliottfd3ca242021-04-25 18:10:42 +0100773 size_t tag_size )
Paul Elliottadb8b162021-04-20 16:06:57 +0100774{
Paul Elliottfd3ca242021-04-25 18:10:42 +0100775 size_t finish_output_size;
776
Paul Elliottadb8b162021-04-20 16:06:57 +0100777 if( operation->lengths_set )
778 {
779 if( operation->ad_remaining != 0 || operation->body_remaining != 0 )
780 {
781 return( PSA_ERROR_BAD_STATE );
782 }
783 }
784
Paul Elliottfd3ca242021-04-25 18:10:42 +0100785 if( tag_size < operation->tag_length )
Paul Elliottadb8b162021-04-20 16:06:57 +0100786 {
787 return ( PSA_ERROR_BUFFER_TOO_SMALL );
788 }
789
Paul Elliottfd3ca242021-04-25 18:10:42 +0100790 if( operation->is_encrypt )
Paul Elliottadb8b162021-04-20 16:06:57 +0100791 {
Paul Elliott2df40052021-05-07 17:52:18 +0100792 finish_output_size =
793 PSA_AEAD_FINISH_OUTPUT_SIZE( operation->key_type,
794 operation->alg );
Paul Elliottadb8b162021-04-20 16:06:57 +0100795 }
796 else
797 {
Paul Elliott2df40052021-05-07 17:52:18 +0100798 finish_output_size =
799 PSA_AEAD_VERIFY_OUTPUT_SIZE( operation->key_type,
800 operation->alg );
Paul Elliottadb8b162021-04-20 16:06:57 +0100801 }
802
Paul Elliottfd3ca242021-04-25 18:10:42 +0100803 if( output_size < finish_output_size )
Paul Elliottadb8b162021-04-20 16:06:57 +0100804 {
805 return ( PSA_ERROR_BUFFER_TOO_SMALL );
806 }
807
808 return ( PSA_SUCCESS );
Paul Elliottadb8b162021-04-20 16:06:57 +0100809}
810
811/* Finish encrypting a message in a multipart AEAD operation. */
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100812psa_status_t mbedtls_psa_aead_finish( mbedtls_psa_aead_operation_t *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100813 uint8_t *ciphertext,
814 size_t ciphertext_size,
815 size_t *ciphertext_length,
816 uint8_t *tag,
817 size_t tag_size,
818 size_t *tag_length )
819{
820 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
Paul Elliottfd3ca242021-04-25 18:10:42 +0100821 size_t finish_output_size = 0;
Paul Elliottadb8b162021-04-20 16:06:57 +0100822
Paul Elliott2df40052021-05-07 17:52:18 +0100823 status = mbedtls_psa_aead_finish_checks( operation, ciphertext_size,
824 tag_size );
Paul Elliottadb8b162021-04-20 16:06:57 +0100825
826 if( status != PSA_SUCCESS )
827 {
828 return status;
829 }
830
831#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
832 if( operation->alg == PSA_ALG_GCM )
833 {
834 /* We will need to do final GCM pass in here when multipart is done. */
835 status = mbedtls_to_psa_error( mbedtls_gcm_finish( &operation->ctx.gcm,
836 tag,
837 tag_size ) );
838 }
839 else
840#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
841#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
842 if( operation->alg == PSA_ALG_CCM )
843 {
Paul Elliottfd3ca242021-04-25 18:10:42 +0100844 /* Copy the previously generated tag into place */
845 memcpy( tag, operation->tag_buffer, operation->tag_length );
Paul Elliottadb8b162021-04-20 16:06:57 +0100846
Paul Elliottfd3ca242021-04-25 18:10:42 +0100847 mbedtls_free(operation->tag_buffer);
848 operation->tag_buffer = NULL;
Paul Elliottadb8b162021-04-20 16:06:57 +0100849
Paul Elliottfd3ca242021-04-25 18:10:42 +0100850 status = PSA_SUCCESS;
Paul Elliottadb8b162021-04-20 16:06:57 +0100851 }
852 else
853#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
854#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
855 if( operation->alg == PSA_ALG_CHACHA20_POLY1305 )
856 {
Paul Elliott2df40052021-05-07 17:52:18 +0100857 status = mbedtls_to_psa_error(
858 mbedtls_chachapoly_finish( &operation->ctx.chachapoly,
859 tag ) );
Paul Elliottadb8b162021-04-20 16:06:57 +0100860 }
861 else
862#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
863 {
864 ( void ) ciphertext;
865 ( void ) ciphertext_size;
866 ( void ) ciphertext_length;
867 ( void ) tag;
868 ( void ) tag_size;
869 ( void ) tag_length;
870
871 return ( PSA_ERROR_NOT_SUPPORTED );
872 }
873
874 if( status == PSA_SUCCESS )
875 {
876 *ciphertext_length = finish_output_size;
Paul Elliottfd3ca242021-04-25 18:10:42 +0100877 *tag_length = operation->tag_length;
Paul Elliottadb8b162021-04-20 16:06:57 +0100878 }
879
880 mbedtls_psa_aead_abort(operation);
881
882 return ( status );
883}
884
885/* Finish authenticating and decrypting a message in a multipart AEAD
886 * operation.*/
Paul Elliottcbbde5f2021-05-10 18:19:46 +0100887psa_status_t mbedtls_psa_aead_verify( mbedtls_psa_aead_operation_t *operation,
Paul Elliottadb8b162021-04-20 16:06:57 +0100888 uint8_t *plaintext,
889 size_t plaintext_size,
890 size_t *plaintext_length,
891 const uint8_t *tag,
892 size_t tag_length )
893{
894 psa_status_t status = PSA_ERROR_CORRUPTION_DETECTED;
895 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
896
Paul Elliottfd3ca242021-04-25 18:10:42 +0100897 uint8_t * temp_buffer;
898 size_t temp_buffer_size;
899
900 size_t finish_output_size = 0;
Paul Elliottadb8b162021-04-20 16:06:57 +0100901
902 int do_tag_check = 1;
903 uint8_t check_tag[16];
904
Paul Elliott2df40052021-05-07 17:52:18 +0100905 status = mbedtls_psa_aead_finish_checks( operation, plaintext_size,
906 tag_length );
Paul Elliottadb8b162021-04-20 16:06:57 +0100907
908 if( status != PSA_SUCCESS )
909 {
910 return status;
911 }
912
913#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
914 if( operation->alg == PSA_ALG_GCM )
915 {
916 /* Call finish to get the tag for comparison */
Paul Elliott2df40052021-05-07 17:52:18 +0100917 status = mbedtls_to_psa_error(
918 mbedtls_gcm_finish( &operation->ctx.gcm,
919 check_tag,
920 operation->tag_length ) );
Paul Elliottadb8b162021-04-20 16:06:57 +0100921 }
922 else
923#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
924#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
925 if( operation->alg == PSA_ALG_CCM )
926 {
Paul Elliottfd3ca242021-04-25 18:10:42 +0100927 if( !operation->ad_buffer || !operation->body_buffer )
Paul Elliottadb8b162021-04-20 16:06:57 +0100928 {
929 return( PSA_ERROR_BAD_STATE );
930 }
931
Paul Elliottfd3ca242021-04-25 18:10:42 +0100932 /* Perform oneshot CCM decryption *again*, as its the
933 * only way to get the tag, but this time throw away the
934 results, as verify cannot write that much data. */
935 temp_buffer_size = PSA_AEAD_UPDATE_OUTPUT_SIZE( operation->key_type,
Paul Elliott2df40052021-05-07 17:52:18 +0100936 operation->alg,
937 operation->body_length
938 );
Paul Elliottadb8b162021-04-20 16:06:57 +0100939
Paul Elliottfd3ca242021-04-25 18:10:42 +0100940 temp_buffer = ( uint8_t * ) mbedtls_calloc(1, temp_buffer_size );
Paul Elliottadb8b162021-04-20 16:06:57 +0100941
Paul Elliottfd3ca242021-04-25 18:10:42 +0100942 if( temp_buffer )
Paul Elliottadb8b162021-04-20 16:06:57 +0100943 {
Paul Elliott2df40052021-05-07 17:52:18 +0100944 ret = mbedtls_ccm_auth_decrypt( &operation->ctx.ccm,
945 operation->body_length,
946 operation->nonce,
947 operation->nonce_length,
948 operation->ad_buffer,
949 operation->ad_length,
950 operation->body_buffer,
951 temp_buffer, tag, tag_length );
Paul Elliottfd3ca242021-04-25 18:10:42 +0100952
953 if( ret == MBEDTLS_ERR_CCM_AUTH_FAILED )
954 {
955 status = PSA_ERROR_INVALID_SIGNATURE;
956 }
957 else
958 {
959 status = mbedtls_to_psa_error( ret );
960 do_tag_check = 0;
961 }
Paul Elliottadb8b162021-04-20 16:06:57 +0100962 }
963 else
964 {
Paul Elliottfd3ca242021-04-25 18:10:42 +0100965 status = PSA_ERROR_INSUFFICIENT_MEMORY;
Paul Elliottadb8b162021-04-20 16:06:57 +0100966 }
967
968 /* Even if the above operation fails, we no longer need the data */
Paul Elliottfd3ca242021-04-25 18:10:42 +0100969 mbedtls_free(temp_buffer);
Paul Elliottadb8b162021-04-20 16:06:57 +0100970
Paul Elliottfd3ca242021-04-25 18:10:42 +0100971 mbedtls_free(operation->body_buffer);
972 operation->body_buffer = NULL;
973 operation->body_length = 0;
974
975 mbedtls_free(operation->tag_buffer);
976 operation->tag_buffer = NULL;
Paul Elliottadb8b162021-04-20 16:06:57 +0100977 }
978 else
979#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
980#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
981 if( operation->alg == PSA_ALG_CHACHA20_POLY1305 )
982 {
983 // call finish to get the tag for comparison.
Paul Elliott2df40052021-05-07 17:52:18 +0100984 status = mbedtls_to_psa_error(
985 mbedtls_chachapoly_finish( &operation->ctx.chachapoly,
986 check_tag ) );
Paul Elliottfd3ca242021-04-25 18:10:42 +0100987
Paul Elliottadb8b162021-04-20 16:06:57 +0100988 }
989 else
990#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
991 {
992 ( void ) plaintext;
993 ( void ) plaintext_size;
994 ( void ) plaintext_length;
995 ( void ) tag;
996 ( void ) tag_length;
997
998 return ( PSA_ERROR_NOT_SUPPORTED );
999 }
1000
1001 if( status == PSA_SUCCESS )
1002 {
Paul Elliott72c10082021-04-23 19:02:16 +01001003 *plaintext_length = finish_output_size;
1004
Paul Elliott6edb7472021-05-10 19:29:35 +01001005 if( do_tag_check &&
1006 mbedtls_psa_safer_memcmp(tag, check_tag, tag_length) != 0 )
Paul Elliottadb8b162021-04-20 16:06:57 +01001007 {
Paul Elliott811d8d42021-04-22 11:31:14 +01001008 status = PSA_ERROR_INVALID_SIGNATURE;
Paul Elliottadb8b162021-04-20 16:06:57 +01001009 }
1010 }
1011
1012 mbedtls_psa_aead_abort(operation);
1013
1014 return ( status );
1015}
1016
1017/* Abort an AEAD operation */
Paul Elliottcbbde5f2021-05-10 18:19:46 +01001018psa_status_t mbedtls_psa_aead_abort( mbedtls_psa_aead_operation_t *operation )
Paul Elliottadb8b162021-04-20 16:06:57 +01001019{
Paul Elliott811d8d42021-04-22 11:31:14 +01001020 switch( operation->alg )
Paul Elliottadb8b162021-04-20 16:06:57 +01001021 {
Paul Elliott811d8d42021-04-22 11:31:14 +01001022#if defined(MBEDTLS_PSA_BUILTIN_ALG_CCM)
1023 case PSA_ALG_CCM:
Paul Elliottadb8b162021-04-20 16:06:57 +01001024 mbedtls_ccm_free( &operation->ctx.ccm );
1025 break;
1026#endif /* MBEDTLS_PSA_BUILTIN_ALG_CCM */
1027#if defined(MBEDTLS_PSA_BUILTIN_ALG_GCM)
1028 case PSA_ALG_GCM:
1029 mbedtls_gcm_free( &operation->ctx.gcm );
1030 break;
1031#endif /* MBEDTLS_PSA_BUILTIN_ALG_GCM */
1032#if defined(MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305)
Paul Elliott811d8d42021-04-22 11:31:14 +01001033 case PSA_ALG_CHACHA20_POLY1305:
1034 mbedtls_chachapoly_free( &operation->ctx.chachapoly );
1035 break;
Paul Elliottadb8b162021-04-20 16:06:57 +01001036#endif /* MBEDTLS_PSA_BUILTIN_ALG_CHACHA20_POLY1305 */
1037 }
1038
Paul Elliottcbbde5f2021-05-10 18:19:46 +01001039 operation->lengths_set = 0;
1040 operation->is_encrypt = 0;
1041 operation->ad_started = 0;
1042 operation->body_started = 0;
1043
Paul Elliottfd3ca242021-04-25 18:10:42 +01001044 mbedtls_free(operation->ad_buffer);
1045 operation->ad_buffer = NULL;
1046 operation->ad_length = 0;
1047
1048 mbedtls_free(operation->body_buffer);
1049 operation->body_buffer = NULL;
1050 operation->body_length = 0;
1051
1052 mbedtls_free(operation->tag_buffer);
1053 operation->tag_buffer = NULL;
1054
Paul Elliottadb8b162021-04-20 16:06:57 +01001055 return( PSA_SUCCESS );
1056}
1057
Ronald Cron7ceee8d2021-03-17 16:55:43 +01001058#endif /* MBEDTLS_PSA_CRYPTO_C */
1059