blob: a4cd862816505e9069c896bf7a7d5a85e4ae4be5 [file] [log] [blame]
Antonio de Angelis04debbd2019-10-14 12:12:52 +01001/*
Jamie Fox044bd8e2020-02-20 13:34:57 +00002 * Copyright (c) 2019-2020, Arm Limited. All rights reserved.
Antonio de Angelis04debbd2019-10-14 12:12:52 +01003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8#include <stddef.h>
9#include <stdint.h>
10
11/* FixMe: Use PSA_ERROR_CONNECTION_REFUSED when performing parameter
12 * integrity checks but this will have to be revised
13 * when the full set of error codes mandated by PSA FF
14 * is available.
15 */
16#include "tfm_mbedcrypto_include.h"
17
Jamie Fox044bd8e2020-02-20 13:34:57 +000018/* Required for mbedtls_calloc in tfm_crypto_huk_derivation_input_bytes */
19#include "mbedtls/platform.h"
20
Antonio de Angelis04debbd2019-10-14 12:12:52 +010021#include "tfm_crypto_api.h"
22#include "tfm_crypto_defs.h"
Jamie Fox044bd8e2020-02-20 13:34:57 +000023#include "tfm_memory_utils.h"
24
Mingyang Sun8a19e7a2020-06-04 15:36:58 +080025#include "tfm_plat_crypto_keys.h"
Jamie Fox044bd8e2020-02-20 13:34:57 +000026
Kevin Pengc6d74502020-03-04 16:55:37 +080027#ifdef TFM_PARTITION_TEST_PS
Jamie Fox044bd8e2020-02-20 13:34:57 +000028#include "psa_manifest/pid.h"
Kevin Pengc6d74502020-03-04 16:55:37 +080029#endif /* TFM_PARTITION_TEST_PS */
Jamie Fox044bd8e2020-02-20 13:34:57 +000030
31#ifndef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
32static psa_status_t tfm_crypto_huk_derivation_setup(
33 psa_key_derivation_operation_t *operation,
34 psa_algorithm_t alg)
35{
36 operation->alg = TFM_CRYPTO_ALG_HUK_DERIVATION;
37 return PSA_SUCCESS;
38}
39
40static psa_status_t tfm_crypto_huk_derivation_input_bytes(
41 psa_key_derivation_operation_t *operation,
42 psa_key_derivation_step_t step,
43 const uint8_t *data,
44 size_t data_length)
45{
46 psa_status_t status;
47 int32_t partition_id;
48
49 if (step != PSA_KEY_DERIVATION_INPUT_LABEL) {
50 return PSA_ERROR_INVALID_ARGUMENT;
51 }
52
53 /* Concatenate the caller's partition ID with the supplied label to prevent
54 * two different partitions from deriving the same key.
55 */
56 status = tfm_crypto_get_caller_id(&partition_id);
57 if (status != PSA_SUCCESS) {
58 return status;
59 }
60
Kevin Pengc6d74502020-03-04 16:55:37 +080061#ifdef TFM_PARTITION_TEST_PS
62 /* The PS tests run some operations under the wrong partition ID - this
Jamie Fox044bd8e2020-02-20 13:34:57 +000063 * causes the key derivation to change.
64 */
Kevin Pengc6d74502020-03-04 16:55:37 +080065 if (partition_id == TFM_SP_PS_TEST) {
66 partition_id = TFM_SP_PS;
Jamie Fox044bd8e2020-02-20 13:34:57 +000067 }
Kevin Pengc6d74502020-03-04 16:55:37 +080068#endif /* TFM_PARTITION_TEST_PS */
Jamie Fox044bd8e2020-02-20 13:34:57 +000069
70 /* Put the label in the tls12_prf ctx to make it available in the output key
71 * step.
72 */
73 operation->ctx.tls12_prf.label = mbedtls_calloc(1, sizeof(partition_id)
74 + data_length);
75 if (operation->ctx.tls12_prf.label == NULL) {
76 return PSA_ERROR_INSUFFICIENT_MEMORY;
77 }
78 (void)tfm_memcpy(operation->ctx.tls12_prf.label, &partition_id,
79 sizeof(partition_id));
80 (void)tfm_memcpy(operation->ctx.tls12_prf.label + sizeof(partition_id),
81 data, data_length);
82 operation->ctx.tls12_prf.label_length = sizeof(partition_id) + data_length;
83
84 return PSA_SUCCESS;
85}
86
87static psa_status_t tfm_crypto_huk_derivation_output_key(
88 const psa_key_attributes_t *attributes,
89 psa_key_derivation_operation_t *operation,
90 psa_key_handle_t *handle)
91{
92 enum tfm_plat_err_t err;
93 size_t bytes = PSA_BITS_TO_BYTES(psa_get_key_bits(attributes));
94
95 if (sizeof(operation->ctx.tls12_prf.output_block) < bytes) {
96 return PSA_ERROR_INSUFFICIENT_MEMORY;
97 }
98
99 /* Derive key material from the HUK and output it to the operation buffer */
100 err = tfm_plat_get_huk_derived_key(operation->ctx.tls12_prf.label,
101 operation->ctx.tls12_prf.label_length,
102 NULL, 0,
103 operation->ctx.tls12_prf.output_block,
104 bytes);
105 if (err != TFM_PLAT_ERR_SUCCESS) {
106 return PSA_ERROR_HARDWARE_FAILURE;
107 }
108
109 return psa_import_key(attributes, operation->ctx.tls12_prf.output_block,
110 bytes, handle);
111}
112
113static psa_status_t tfm_crypto_huk_derivation_abort(
114 psa_key_derivation_operation_t *operation)
115{
116 if (operation->ctx.tls12_prf.label != NULL) {
117 (void)tfm_memset(operation->ctx.tls12_prf.label, 0,
118 operation->ctx.tls12_prf.label_length);
119 mbedtls_free(operation->ctx.tls12_prf.label);
120 }
121
122 (void)tfm_memset(operation, 0, sizeof(*operation));
123
124 return PSA_SUCCESS;
125}
126#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100127
128/*!
129 * \defgroup public_psa Public functions, PSA
130 *
131 */
132
133/*!@{*/
134psa_status_t tfm_crypto_key_derivation_setup(psa_invec in_vec[],
135 size_t in_len,
136 psa_outvec out_vec[],
137 size_t out_len)
138{
139#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
140 return PSA_ERROR_NOT_SUPPORTED;
141#else
142 psa_status_t status = PSA_SUCCESS;
143 psa_key_derivation_operation_t *operation = NULL;
144
145 if ((in_len != 1) || (out_len != 1)) {
146 return PSA_ERROR_CONNECTION_REFUSED;
147 }
148
149 if ((out_vec[0].len != sizeof(uint32_t)) ||
150 (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec))) {
151 return PSA_ERROR_CONNECTION_REFUSED;
152 }
153 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
154 uint32_t handle = iov->op_handle;
155 uint32_t *handle_out = out_vec[0].base;
156 psa_algorithm_t alg = iov->alg;
157
158 /* Allocate the operation context in the secure world */
159 status = tfm_crypto_operation_alloc(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
160 &handle,
161 (void **)&operation);
162 if (status != PSA_SUCCESS) {
163 return status;
164 }
165
166 *handle_out = handle;
167
Jamie Fox044bd8e2020-02-20 13:34:57 +0000168 if (alg == TFM_CRYPTO_ALG_HUK_DERIVATION) {
169 status = tfm_crypto_huk_derivation_setup(operation, alg);
170 } else {
171 status = psa_key_derivation_setup(operation, alg);
172 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100173 if (status != PSA_SUCCESS) {
174 /* Release the operation context, ignore if the operation fails. */
175 (void)tfm_crypto_operation_release(handle_out);
176 return status;
177 }
178
179 return status;
180#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
181}
182
183psa_status_t tfm_crypto_key_derivation_get_capacity(psa_invec in_vec[],
184 size_t in_len,
185 psa_outvec out_vec[],
186 size_t out_len)
187{
188#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
189 return PSA_ERROR_NOT_SUPPORTED;
190#else
191 psa_status_t status;
192 if ((in_len != 1) || (out_len != 1)) {
193 return PSA_ERROR_CONNECTION_REFUSED;
194 }
195
196 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
197 (out_vec[0].len != sizeof(size_t))) {
198 return PSA_ERROR_CONNECTION_REFUSED;
199 }
200 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
201
202 uint32_t handle = iov->op_handle;
203 size_t *capacity = out_vec[0].base;
204 psa_key_derivation_operation_t *operation = NULL;
205
206 /* Look up the corresponding operation context */
207 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
208 handle,
209 (void **)&operation);
210 if (status != PSA_SUCCESS) {
211 *capacity = 0;
212 return status;
213 }
214
215 return psa_key_derivation_get_capacity(operation, capacity);
216#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
217}
218
219psa_status_t tfm_crypto_key_derivation_set_capacity(psa_invec in_vec[],
220 size_t in_len,
221 psa_outvec out_vec[],
222 size_t out_len)
223{
224#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
225 return PSA_ERROR_NOT_SUPPORTED;
226#else
227 psa_status_t status;
228 if ((in_len != 1) || (out_len != 0)) {
229 return PSA_ERROR_CONNECTION_REFUSED;
230 }
231
232 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec))) {
233 return PSA_ERROR_CONNECTION_REFUSED;
234 }
235 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
236
237 uint32_t handle = iov->op_handle;
238 size_t capacity = iov->capacity;
239 psa_key_derivation_operation_t *operation = NULL;
240
241 /* Look up the corresponding operation context */
242 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
243 handle,
244 (void **)&operation);
245 if (status != PSA_SUCCESS) {
246 return status;
247 }
248
249 return psa_key_derivation_set_capacity(operation, capacity);
250#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
251}
252
253psa_status_t tfm_crypto_key_derivation_input_bytes(psa_invec in_vec[],
254 size_t in_len,
255 psa_outvec out_vec[],
256 size_t out_len)
257{
258#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
259 return PSA_ERROR_NOT_SUPPORTED;
260#else
261 psa_status_t status;
262 if ((in_len != 2) || (out_len != 0)) {
263 return PSA_ERROR_CONNECTION_REFUSED;
264 }
265
266 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec))) {
267 return PSA_ERROR_CONNECTION_REFUSED;
268 }
269 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
270
271 uint32_t handle = iov->op_handle;
272 psa_key_derivation_step_t step = iov->step;
273 const uint8_t *data = in_vec[1].base;
274 size_t data_length = in_vec[1].len;
275 psa_key_derivation_operation_t *operation = NULL;
276
277 /* Look up the corresponding operation context */
278 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
279 handle,
280 (void **)&operation);
281 if (status != PSA_SUCCESS) {
282 return status;
283 }
284
Jamie Fox044bd8e2020-02-20 13:34:57 +0000285 if (operation->alg == TFM_CRYPTO_ALG_HUK_DERIVATION) {
286 return tfm_crypto_huk_derivation_input_bytes(operation, step, data,
287 data_length);
288 } else {
289 return psa_key_derivation_input_bytes(operation, step, data,
290 data_length);
291 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100292#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
293}
294
295psa_status_t tfm_crypto_key_derivation_output_bytes(psa_invec in_vec[],
296 size_t in_len,
297 psa_outvec out_vec[],
298 size_t out_len)
299{
300#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
301 return PSA_ERROR_NOT_SUPPORTED;
302#else
303 psa_status_t status;
304 if ((in_len != 1) || (out_len != 1)) {
305 return PSA_ERROR_CONNECTION_REFUSED;
306 }
307
308 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec))) {
309 return PSA_ERROR_CONNECTION_REFUSED;
310 }
311 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
312
313 uint32_t handle = iov->op_handle;
314 uint8_t *output = out_vec[0].base;
315 size_t output_length = out_vec[0].len;
316 psa_key_derivation_operation_t *operation = NULL;
317
318 /* Look up the corresponding operation context */
319 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
320 handle,
321 (void **)&operation);
322 if (status != PSA_SUCCESS) {
323 return status;
324 }
325
326 return psa_key_derivation_output_bytes(operation, output, output_length);
327#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
328}
329
330psa_status_t tfm_crypto_key_derivation_input_key(psa_invec in_vec[],
331 size_t in_len,
332 psa_outvec out_vec[],
333 size_t out_len)
334{
335#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
336 return PSA_ERROR_NOT_SUPPORTED;
337#else
338 psa_status_t status;
339 if ((in_len != 1) || (out_len != 0)) {
340 return PSA_ERROR_CONNECTION_REFUSED;
341 }
342
343 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec))) {
344 return PSA_ERROR_CONNECTION_REFUSED;
345 }
346 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
347
348 uint32_t handle = iov->op_handle;
349 psa_key_handle_t key_handle = iov->key_handle;
350 psa_key_derivation_step_t step = iov->step;
351 psa_key_derivation_operation_t *operation = NULL;
352
353 status = tfm_crypto_check_handle_owner(key_handle, NULL);
354 if (status != PSA_SUCCESS) {
355 return status;
356 }
357
358 /* Look up the corresponding operation context */
359 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
360 handle,
361 (void **)&operation);
362 if (status != PSA_SUCCESS) {
363 return status;
364 }
365
366 return psa_key_derivation_input_key(operation, step, key_handle);
367#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
368}
369
370psa_status_t tfm_crypto_key_derivation_output_key(psa_invec in_vec[],
371 size_t in_len,
372 psa_outvec out_vec[],
373 size_t out_len)
374{
375#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
376 return PSA_ERROR_NOT_SUPPORTED;
377#else
378 psa_status_t status;
379 if ((in_len != 2) || (out_len != 1)) {
380 return PSA_ERROR_CONNECTION_REFUSED;
381 }
382
383 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100384 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s)) ||
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100385 (out_vec[0].len != sizeof(psa_key_handle_t))) {
386 return PSA_ERROR_CONNECTION_REFUSED;
387 }
388 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
389
390 uint32_t handle = iov->op_handle;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100391 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100392 psa_key_derivation_operation_t *operation = NULL;
393 psa_key_handle_t *key_handle = out_vec[0].base;
Jamie Fox98ab4412020-01-17 17:12:30 +0000394 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
395 int32_t partition_id;
Jamie Fox99360e82020-02-20 16:00:09 +0000396 uint32_t index;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100397
398 /* Look up the corresponding operation context */
399 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
400 handle,
401 (void **)&operation);
402 if (status != PSA_SUCCESS) {
403 return status;
404 }
Jamie Fox99360e82020-02-20 16:00:09 +0000405
406 status = tfm_crypto_check_key_storage(&index);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100407 if (status != PSA_SUCCESS) {
408 return status;
409 }
Jamie Fox99360e82020-02-20 16:00:09 +0000410
Jamie Fox98ab4412020-01-17 17:12:30 +0000411 status = tfm_crypto_get_caller_id(&partition_id);
412 if (status != PSA_SUCCESS) {
413 return status;
414 }
415
416 status = tfm_crypto_key_attributes_from_client(client_key_attr,
417 partition_id,
418 &key_attributes);
419 if (status != PSA_SUCCESS) {
420 return status;
421 }
422
Jamie Fox044bd8e2020-02-20 13:34:57 +0000423 if (operation->alg == TFM_CRYPTO_ALG_HUK_DERIVATION) {
Jamie Fox98ab4412020-01-17 17:12:30 +0000424 status = tfm_crypto_huk_derivation_output_key(&key_attributes,
425 operation, key_handle);
Jamie Fox044bd8e2020-02-20 13:34:57 +0000426 } else {
Jamie Fox98ab4412020-01-17 17:12:30 +0000427 status = psa_key_derivation_output_key(&key_attributes, operation,
Jamie Fox044bd8e2020-02-20 13:34:57 +0000428 key_handle);
429 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100430 if (status == PSA_SUCCESS) {
Jamie Fox99360e82020-02-20 16:00:09 +0000431 status = tfm_crypto_set_key_storage(index, *key_handle);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100432 }
Jamie Fox99360e82020-02-20 16:00:09 +0000433
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100434 return status;
435#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
436}
437
438psa_status_t tfm_crypto_key_derivation_abort(psa_invec in_vec[],
439 size_t in_len,
440 psa_outvec out_vec[],
441 size_t out_len)
442{
443#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
444 return PSA_ERROR_NOT_SUPPORTED;
445#else
446 psa_status_t status;
447 if ((in_len != 1) || (out_len != 1)) {
448 return PSA_ERROR_CONNECTION_REFUSED;
449 }
450
451 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
452 (out_vec[0].len != sizeof(uint32_t))) {
453 return PSA_ERROR_CONNECTION_REFUSED;
454 }
455 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
456
457 uint32_t handle = iov->op_handle;
458 uint32_t *handle_out = out_vec[0].base;
459 psa_key_derivation_operation_t *operation = NULL;
460
461 /* Init the handle in the operation with the one passed from the iov */
462 *handle_out = iov->op_handle;
463
464 /* Look up the corresponding operation context */
465 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
466 handle,
467 (void **)&operation);
468 if (status != PSA_SUCCESS) {
469 /* Operation does not exist, so abort has no effect */
470 return PSA_SUCCESS;
471 }
472
473 *handle_out = handle;
474
Jamie Fox044bd8e2020-02-20 13:34:57 +0000475 if (operation->alg == TFM_CRYPTO_ALG_HUK_DERIVATION) {
476 status = tfm_crypto_huk_derivation_abort(operation);
477 } else {
478 status = psa_key_derivation_abort(operation);
479 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100480 if (status != PSA_SUCCESS) {
481 /* Release the operation context, ignore if the operation fails. */
482 (void)tfm_crypto_operation_release(handle_out);
483 return status;
484 }
485
486 status = tfm_crypto_operation_release(handle_out);
487
488 return status;
489#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
490}
491
492psa_status_t tfm_crypto_key_derivation_key_agreement(psa_invec in_vec[],
493 size_t in_len,
494 psa_outvec out_vec[],
495 size_t out_len)
496{
497#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
498 return PSA_ERROR_NOT_SUPPORTED;
499#else
500 psa_status_t status;
501 if ((in_len != 2) || (out_len != 0)) {
502 return PSA_ERROR_CONNECTION_REFUSED;
503 }
504
505 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec))) {
506 return PSA_ERROR_CONNECTION_REFUSED;
507 }
508 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
509
510 uint32_t handle = iov->op_handle;
511 psa_key_handle_t private_key = iov->key_handle;
512 const uint8_t *peer_key = in_vec[1].base;
513 size_t peer_key_length = in_vec[1].len;
514 psa_key_derivation_operation_t *operation = NULL;
515 psa_key_derivation_step_t step = iov->step;
516
517 status = tfm_crypto_check_handle_owner(private_key, NULL);
518 if (status != PSA_SUCCESS) {
519 return status;
520 }
521
522 /* Look up the corresponding operation context */
523 status = tfm_crypto_operation_lookup(TFM_CRYPTO_KEY_DERIVATION_OPERATION,
524 handle,
525 (void **)&operation);
526 if (status != PSA_SUCCESS) {
527 return status;
528 }
529
530 return psa_key_derivation_key_agreement(operation, step,
531 private_key,
532 peer_key,
533 peer_key_length);
534#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
535}
536
537psa_status_t tfm_crypto_generate_random(psa_invec in_vec[],
538 size_t in_len,
539 psa_outvec out_vec[],
540 size_t out_len)
541{
542#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
543 return PSA_ERROR_NOT_SUPPORTED;
544#else
545 if ((in_len != 1) || (out_len != 1)) {
546 return PSA_ERROR_CONNECTION_REFUSED;
547 }
548
549 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
550 return PSA_ERROR_CONNECTION_REFUSED;
551 }
552 uint8_t *output = out_vec[0].base;
553 size_t output_size = out_vec[0].len;
554
555 return psa_generate_random(output, output_size);
556#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
557}
558
559psa_status_t tfm_crypto_raw_key_agreement(psa_invec in_vec[],
560 size_t in_len,
561 psa_outvec out_vec[],
562 size_t out_len)
563{
564#ifdef TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED
565 return PSA_ERROR_NOT_SUPPORTED;
566#else
567 if ((in_len != 2) || (out_len != 1)) {
568 return PSA_ERROR_CONNECTION_REFUSED;
569 }
570
571 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
572 return PSA_ERROR_CONNECTION_REFUSED;
573 }
574 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
575 uint8_t *output = out_vec[0].base;
576 size_t output_size = out_vec[0].len;
577 psa_algorithm_t alg = iov->alg;
578 psa_key_handle_t private_key = iov->key_handle;
579 const uint8_t *peer_key = in_vec[1].base;
580 size_t peer_key_length = in_vec[1].len;
581
582 return psa_raw_key_agreement(alg, private_key, peer_key, peer_key_length,
583 output, output_size, &out_vec[0].len);
584#endif /* TFM_CRYPTO_KEY_DERIVATION_MODULE_DISABLED */
585}
586/*!@}*/