blob: a2ca7d8d64d625c44bcb568ab932ce19375ac1c9 [file] [log] [blame]
Antonio de Angelis8908f472018-08-31 15:44:25 +01001/*
Antonio de Angelis04debbd2019-10-14 12:12:52 +01002 * Copyright (c) 2018-2020, Arm Limited. All rights reserved.
Antonio de Angelis8908f472018-08-31 15:44:25 +01003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
Jamie Foxefd82732018-11-26 10:34:32 +00008#include <stddef.h>
Jamie Fox0e54ebc2019-04-09 14:21:04 +01009#include <stdint.h>
Antonio de Angelis8908f472018-08-31 15:44:25 +010010
Jamie Fox0e54ebc2019-04-09 14:21:04 +010011#include "tfm_mbedcrypto_include.h"
Antonio de Angelis4743e672019-04-11 11:38:48 +010012
Jamie Fox0e54ebc2019-04-09 14:21:04 +010013#include "tfm_crypto_api.h"
14#include "tfm_crypto_defs.h"
Soby Mathewd8abdfd2020-10-14 10:28:01 +010015#include "tfm_crypto_private.h"
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010016#include <stdbool.h>
Jamie Fox82b87ca2018-12-11 16:41:11 +000017
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010018#ifndef TFM_CRYPTO_MAX_KEY_HANDLES
19#define TFM_CRYPTO_MAX_KEY_HANDLES (16)
20#endif
21struct tfm_crypto_handle_owner_s {
22 int32_t owner; /*!< Owner of the allocated handle */
23 psa_key_handle_t handle; /*!< Allocated handle */
24 uint8_t in_use; /*!< Flag to indicate if this in use */
25};
26
Kevin Peng96f802e2019-12-26 16:10:25 +080027#ifndef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010028static struct tfm_crypto_handle_owner_s
29 handle_owner[TFM_CRYPTO_MAX_KEY_HANDLES] = {0};
Antonio de Angelis7740b382019-07-16 10:59:25 +010030#endif
Jamie Foxdadb4e82019-09-03 17:59:41 +010031
Antonio de Angelis8908f472018-08-31 15:44:25 +010032/*!
33 * \defgroup public Public functions
34 *
35 */
Antonio de Angelis8908f472018-08-31 15:44:25 +010036/*!@{*/
Jamie Fox98ab4412020-01-17 17:12:30 +000037psa_status_t tfm_crypto_key_attributes_from_client(
Soby Mathewd7b79f22020-05-21 15:06:54 +010038 const struct psa_client_key_attributes_s *client_key_attr,
Jamie Fox98ab4412020-01-17 17:12:30 +000039 int32_t client_id,
40 psa_key_attributes_t *key_attributes)
41{
42 if (client_key_attr == NULL || key_attributes == NULL) {
43 return PSA_ERROR_PROGRAMMER_ERROR;
44 }
45
Soby Mathewd7b79f22020-05-21 15:06:54 +010046 *key_attributes = psa_key_attributes_init();
Jamie Fox98ab4412020-01-17 17:12:30 +000047
48 /* Copy core key attributes from the client core key attributes */
Soby Mathewd7b79f22020-05-21 15:06:54 +010049 key_attributes->core.type = client_key_attr->type;
50 key_attributes->core.lifetime = client_key_attr->lifetime;
51 key_attributes->core.policy.usage = client_key_attr->usage;
52 key_attributes->core.policy.alg = client_key_attr->alg;
53 key_attributes->core.bits = client_key_attr->bits;
Jamie Fox98ab4412020-01-17 17:12:30 +000054
55 /* Use the client key id as the key_id and its partition id as the owner */
Soby Mathewd7b79f22020-05-21 15:06:54 +010056 key_attributes->core.id.key_id = client_key_attr->id;
Jamie Fox98ab4412020-01-17 17:12:30 +000057 key_attributes->core.id.owner = client_id;
58
59 return PSA_SUCCESS;
60}
61
62psa_status_t tfm_crypto_key_attributes_to_client(
63 const psa_key_attributes_t *key_attributes,
Soby Mathewd7b79f22020-05-21 15:06:54 +010064 struct psa_client_key_attributes_s *client_key_attr)
Jamie Fox98ab4412020-01-17 17:12:30 +000065{
66 if (client_key_attr == NULL || key_attributes == NULL) {
67 return PSA_ERROR_PROGRAMMER_ERROR;
68 }
69
Soby Mathewd7b79f22020-05-21 15:06:54 +010070 struct psa_client_key_attributes_s v = PSA_CLIENT_KEY_ATTRIBUTES_INIT;
71 *client_key_attr = v;
Jamie Fox98ab4412020-01-17 17:12:30 +000072
Soby Mathewd7b79f22020-05-21 15:06:54 +010073 /* Copy core key attributes from the client core key attributes */
74 client_key_attr->type = key_attributes->core.type;
75 client_key_attr->lifetime = key_attributes->core.lifetime;
76 client_key_attr->usage = key_attributes->core.policy.usage;
77 client_key_attr->alg = key_attributes->core.policy.alg;
78 client_key_attr->bits = key_attributes->core.bits;
Jamie Fox98ab4412020-01-17 17:12:30 +000079
80 /* Return the key_id as the client key id, do not return the owner */
Soby Mathewd7b79f22020-05-21 15:06:54 +010081 client_key_attr->id = key_attributes->core.id.key_id;
Jamie Fox98ab4412020-01-17 17:12:30 +000082
83 return PSA_SUCCESS;
84}
85
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010086psa_status_t tfm_crypto_check_handle_owner(psa_key_handle_t handle,
87 uint32_t *index)
88{
Kevin Peng96f802e2019-12-26 16:10:25 +080089#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +010090 return PSA_ERROR_NOT_SUPPORTED;
91#else
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010092 int32_t partition_id = 0;
93 uint32_t i = 0;
94 psa_status_t status;
95
96 status = tfm_crypto_get_caller_id(&partition_id);
97 if (status != PSA_SUCCESS) {
98 return status;
99 }
100
101 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
102 if (handle_owner[i].in_use && handle_owner[i].handle == handle) {
103 if (handle_owner[i].owner == partition_id) {
104 if (index != NULL) {
105 *index = i;
106 }
107 return PSA_SUCCESS;
108 } else {
109 return PSA_ERROR_NOT_PERMITTED;
110 }
111 }
112 }
113
114 return PSA_ERROR_INVALID_HANDLE;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100115#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100116}
117
Jamie Fox99360e82020-02-20 16:00:09 +0000118psa_status_t tfm_crypto_check_key_storage(uint32_t *index)
119{
120#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
121 return PSA_ERROR_NOT_SUPPORTED;
122#else
123 uint32_t i;
124
125 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
126 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
127 *index = i;
128 return PSA_SUCCESS;
129 }
130 }
131
132 return PSA_ERROR_INSUFFICIENT_MEMORY;
133#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
134}
135
136psa_status_t tfm_crypto_set_key_storage(uint32_t index,
137 psa_key_handle_t key_handle)
138{
139#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
140 return PSA_ERROR_NOT_SUPPORTED;
141#else
142 psa_status_t status;
143 int32_t partition_id;
144
145 status = tfm_crypto_get_caller_id(&partition_id);
146 if (status != PSA_SUCCESS) {
147 return status;
148 }
149
150 handle_owner[index].owner = partition_id;
151 handle_owner[index].handle = key_handle;
152 handle_owner[index].in_use = TFM_CRYPTO_IN_USE;
153
154 return PSA_SUCCESS;
155#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
156}
157
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100158psa_status_t tfm_crypto_set_key_domain_parameters(psa_invec in_vec[],
159 size_t in_len,
160 psa_outvec out_vec[],
161 size_t out_len)
Antonio de Angeliscf85ba22018-10-09 13:29:40 +0100162{
Kevin Peng96f802e2019-12-26 16:10:25 +0800163#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100164 return PSA_ERROR_NOT_SUPPORTED;
165#else
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100166 /* FixMe: To be implemented */
167 return PSA_ERROR_NOT_SUPPORTED;
168#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
169}
170
171psa_status_t tfm_crypto_get_key_domain_parameters(psa_invec in_vec[],
172 size_t in_len,
173 psa_outvec out_vec[],
174 size_t out_len)
175{
176#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
177 return PSA_ERROR_NOT_SUPPORTED;
178#else
179 /* FixMe: To be implemented */
180 return PSA_ERROR_NOT_SUPPORTED;
181#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
182}
183
184psa_status_t tfm_crypto_import_key(psa_invec in_vec[],
185 size_t in_len,
186 psa_outvec out_vec[],
187 size_t out_len)
188{
189#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
190 return PSA_ERROR_NOT_SUPPORTED;
191#else
192
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100193 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 3, out_len, 1, 1);
Jamie Foxefd82732018-11-26 10:34:32 +0000194
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100195 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100196 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s)) ||
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100197 (out_vec[0].len != sizeof(psa_key_handle_t))) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100198 return PSA_ERROR_PROGRAMMER_ERROR;
Jamie Foxefd82732018-11-26 10:34:32 +0000199 }
Soby Mathewd7b79f22020-05-21 15:06:54 +0100200 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100201 const uint8_t *data = in_vec[2].base;
202 size_t data_length = in_vec[2].len;
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100203 psa_key_handle_t *key_handle = out_vec[0].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100204 psa_status_t status;
Jamie Fox98ab4412020-01-17 17:12:30 +0000205 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100206 uint32_t i = 0;
207 int32_t partition_id = 0;
208 bool empty_found = false;
Jamie Foxefd82732018-11-26 10:34:32 +0000209
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100210 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
211 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
212 empty_found = true;
213 break;
214 }
215 }
216
217 if (!empty_found) {
218 return PSA_ERROR_INSUFFICIENT_MEMORY;
219 }
220
221 status = tfm_crypto_get_caller_id(&partition_id);
222 if (status != PSA_SUCCESS) {
223 return status;
224 }
225
Jamie Fox98ab4412020-01-17 17:12:30 +0000226 status = tfm_crypto_key_attributes_from_client(client_key_attr,
227 partition_id,
228 &key_attributes);
229 if (status != PSA_SUCCESS) {
230 return status;
231 }
232
233 status = psa_import_key(&key_attributes, data, data_length, key_handle);
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100234
235 if (status == PSA_SUCCESS) {
236 handle_owner[i].owner = partition_id;
237 handle_owner[i].handle = *key_handle;
238 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
239 }
240
241 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100242#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Jamie Foxefd82732018-11-26 10:34:32 +0000243}
244
Jamie Foxdadb4e82019-09-03 17:59:41 +0100245psa_status_t tfm_crypto_open_key(psa_invec in_vec[],
246 size_t in_len,
247 psa_outvec out_vec[],
248 size_t out_len)
249{
Kevin Peng96f802e2019-12-26 16:10:25 +0800250#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Jamie Foxdadb4e82019-09-03 17:59:41 +0100251 return PSA_ERROR_NOT_SUPPORTED;
252#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100253
254 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 2, out_len, 1, 1);
Jamie Foxdadb4e82019-09-03 17:59:41 +0100255
256 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Jamie Fox98ab4412020-01-17 17:12:30 +0000257 (in_vec[1].len != sizeof(psa_app_key_id_t)) ||
Jamie Foxdadb4e82019-09-03 17:59:41 +0100258 (out_vec[0].len != sizeof(psa_key_handle_t))) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100259 return PSA_ERROR_PROGRAMMER_ERROR;
Jamie Foxdadb4e82019-09-03 17:59:41 +0100260 }
261
Jamie Fox98ab4412020-01-17 17:12:30 +0000262 psa_app_key_id_t client_key_id = *((psa_app_key_id_t *)in_vec[1].base);
263 psa_key_handle_t *key_handle = out_vec[0].base;
264 psa_status_t status;
265 psa_key_id_t id;
266 int32_t partition_id;
267 uint32_t i;
268
269 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
270 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
271 break;
272 }
273 }
274
275 if (i == TFM_CRYPTO_MAX_KEY_HANDLES) {
276 return PSA_ERROR_INSUFFICIENT_MEMORY;
277 }
278
279 status = tfm_crypto_get_caller_id(&partition_id);
280 if (status != PSA_SUCCESS) {
281 return status;
282 }
283
284 /* Use the client key id as the key_id and its partition id as the owner */
285 id = (psa_key_id_t){ .key_id = client_key_id, .owner = partition_id };
286
287 status = psa_open_key(id, key_handle);
288
289 if (status == PSA_SUCCESS) {
290 handle_owner[i].owner = partition_id;
291 handle_owner[i].handle = *key_handle;
292 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
293 }
294
295 return status;
Jamie Foxdadb4e82019-09-03 17:59:41 +0100296#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
297}
298
299psa_status_t tfm_crypto_close_key(psa_invec in_vec[],
300 size_t in_len,
301 psa_outvec out_vec[],
302 size_t out_len)
303{
Kevin Peng96f802e2019-12-26 16:10:25 +0800304#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Jamie Foxdadb4e82019-09-03 17:59:41 +0100305 return PSA_ERROR_NOT_SUPPORTED;
306#else
307 (void)out_vec;
308
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100309 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 0);
Jamie Foxdadb4e82019-09-03 17:59:41 +0100310
311 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100312 return PSA_ERROR_PROGRAMMER_ERROR;
Jamie Foxdadb4e82019-09-03 17:59:41 +0100313 }
314 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
315
316 psa_key_handle_t key = iov->key_handle;
317 uint32_t index;
318 psa_status_t status = tfm_crypto_check_handle_owner(key, &index);
319
320 if (status != PSA_SUCCESS) {
321 return status;
322 }
323
324 status = psa_close_key(key);
325
326 if (status == PSA_SUCCESS) {
327 handle_owner[index].owner = 0;
328 handle_owner[index].handle = 0;
329 handle_owner[index].in_use = TFM_CRYPTO_NOT_IN_USE;
330 }
331
332 return status;
333#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
334}
335
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000336psa_status_t tfm_crypto_destroy_key(psa_invec in_vec[],
337 size_t in_len,
338 psa_outvec out_vec[],
339 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100340{
Kevin Peng96f802e2019-12-26 16:10:25 +0800341#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100342 return PSA_ERROR_NOT_SUPPORTED;
343#else
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100344 (void)out_vec;
Antonio de Angelis8908f472018-08-31 15:44:25 +0100345
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100346 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 0);
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000347
Antonio de Angelis4743e672019-04-11 11:38:48 +0100348 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100349 return PSA_ERROR_PROGRAMMER_ERROR;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000350 }
Antonio de Angelis4743e672019-04-11 11:38:48 +0100351 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000352
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100353 psa_key_handle_t key = iov->key_handle;
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100354 uint32_t index;
355 psa_status_t status = tfm_crypto_check_handle_owner(key, &index);
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000356
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100357 if (status != PSA_SUCCESS) {
358 return status;
359 }
360
361 status = psa_destroy_key(key);
362
363 if (status == PSA_SUCCESS) {
364 handle_owner[index].owner = 0;
365 handle_owner[index].handle = 0;
366 handle_owner[index].in_use = TFM_CRYPTO_NOT_IN_USE;
367 }
368
369 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100370#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis8908f472018-08-31 15:44:25 +0100371}
372
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100373psa_status_t tfm_crypto_get_key_attributes(psa_invec in_vec[],
374 size_t in_len,
375 psa_outvec out_vec[],
376 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100377{
Kevin Peng96f802e2019-12-26 16:10:25 +0800378#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100379 return PSA_ERROR_NOT_SUPPORTED;
380#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100381
382 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 1, 1);
Jamie Foxefd82732018-11-26 10:34:32 +0000383
Antonio de Angelis4743e672019-04-11 11:38:48 +0100384 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100385 (out_vec[0].len != sizeof(struct psa_client_key_attributes_s))) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100386 return PSA_ERROR_PROGRAMMER_ERROR;
Jamie Foxefd82732018-11-26 10:34:32 +0000387 }
Antonio de Angelis4743e672019-04-11 11:38:48 +0100388 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
Jamie Foxefd82732018-11-26 10:34:32 +0000389
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100390 psa_key_handle_t key = iov->key_handle;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100391 struct psa_client_key_attributes_s *client_key_attr = out_vec[0].base;
Jamie Fox98ab4412020-01-17 17:12:30 +0000392 psa_status_t status;
393 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000394
Jamie Fox98ab4412020-01-17 17:12:30 +0000395 status = tfm_crypto_check_handle_owner(key, NULL);
396 if (status != PSA_SUCCESS) {
397 return status;
398 }
399
400 status = psa_get_key_attributes(key, &key_attributes);
401
402 if (status == PSA_SUCCESS) {
403 status = tfm_crypto_key_attributes_to_client(&key_attributes,
404 client_key_attr);
405 }
406
407 return status;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100408#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
409}
410
411psa_status_t tfm_crypto_reset_key_attributes(psa_invec in_vec[],
412 size_t in_len,
413 psa_outvec out_vec[],
414 size_t out_len)
415{
416#if (TFM_CRYPTO_KEY_MODULE_DISABLED != 0)
417 return PSA_ERROR_NOT_SUPPORTED;
418#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100419
420 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 1, 1);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100421
422 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100423 (out_vec[0].len != sizeof(struct psa_client_key_attributes_s))) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100424 return PSA_ERROR_PROGRAMMER_ERROR;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100425 }
426
Soby Mathewd7b79f22020-05-21 15:06:54 +0100427 struct psa_client_key_attributes_s *client_key_attr = out_vec[0].base;
Jamie Fox98ab4412020-01-17 17:12:30 +0000428 psa_status_t status;
429 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
430 int32_t partition_id;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100431
Jamie Fox98ab4412020-01-17 17:12:30 +0000432 status = tfm_crypto_get_caller_id(&partition_id);
433 if (status != PSA_SUCCESS) {
434 return status;
435 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100436
Jamie Fox98ab4412020-01-17 17:12:30 +0000437 status = tfm_crypto_key_attributes_from_client(client_key_attr,
438 partition_id,
439 &key_attributes);
440 if (status != PSA_SUCCESS) {
441 return status;
442 }
443
444 psa_reset_key_attributes(&key_attributes);
445
446 return tfm_crypto_key_attributes_to_client(&key_attributes,
447 client_key_attr);
Antonio de Angelis7740b382019-07-16 10:59:25 +0100448#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis8908f472018-08-31 15:44:25 +0100449}
450
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000451psa_status_t tfm_crypto_export_key(psa_invec in_vec[],
452 size_t in_len,
453 psa_outvec out_vec[],
454 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100455{
Kevin Peng96f802e2019-12-26 16:10:25 +0800456#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100457 return PSA_ERROR_NOT_SUPPORTED;
458#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100459
460 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 1);
Antonio de Angelis8908f472018-08-31 15:44:25 +0100461
Antonio de Angelis4743e672019-04-11 11:38:48 +0100462 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100463 return PSA_ERROR_PROGRAMMER_ERROR;
Antonio de Angelis8908f472018-08-31 15:44:25 +0100464 }
Antonio de Angelis4743e672019-04-11 11:38:48 +0100465 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
Antonio de Angelis8908f472018-08-31 15:44:25 +0100466
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100467 psa_key_handle_t key = iov->key_handle;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000468 uint8_t *data = out_vec[0].base;
469 size_t data_size = out_vec[0].len;
470
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100471 return psa_export_key(key, data, data_size, &(out_vec[0].len));
Antonio de Angelis7740b382019-07-16 10:59:25 +0100472#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis8908f472018-08-31 15:44:25 +0100473}
474
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000475psa_status_t tfm_crypto_export_public_key(psa_invec in_vec[],
476 size_t in_len,
477 psa_outvec out_vec[],
478 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100479{
Kevin Peng96f802e2019-12-26 16:10:25 +0800480#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100481 return PSA_ERROR_NOT_SUPPORTED;
482#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100483
484 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 1);
Hugues de Valon8b442442019-02-19 14:30:52 +0000485
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100486 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100487 return PSA_ERROR_PROGRAMMER_ERROR;
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100488 }
489 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
490
491 psa_key_handle_t key = iov->key_handle;
492 uint8_t *data = out_vec[0].base;
493 size_t data_size = out_vec[0].len;
494
495 return psa_export_public_key(key, data, data_size, &(out_vec[0].len));
Antonio de Angelis7740b382019-07-16 10:59:25 +0100496#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100497}
498
499psa_status_t tfm_crypto_copy_key(psa_invec in_vec[],
500 size_t in_len,
501 psa_outvec out_vec[],
502 size_t out_len)
503{
Kevin Peng96f802e2019-12-26 16:10:25 +0800504#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100505 return PSA_ERROR_NOT_SUPPORTED;
506#else
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100507
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100508 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 2, out_len, 1, 1);
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100509
510 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100511 (out_vec[0].len != sizeof(psa_key_handle_t)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100512 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s))) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100513 return PSA_ERROR_PROGRAMMER_ERROR;
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100514 }
515 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
516
517 psa_key_handle_t source_handle = iov->key_handle;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100518 psa_key_handle_t *target_handle = out_vec[0].base;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100519 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100520 psa_status_t status;
Jamie Fox98ab4412020-01-17 17:12:30 +0000521 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100522 uint32_t i = 0;
523 int32_t partition_id = 0;
524 bool empty_found = false;
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100525
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100526 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
527 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
528 empty_found = true;
529 break;
530 }
Jamie Foxefd82732018-11-26 10:34:32 +0000531 }
532
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100533 if (!empty_found) {
534 return PSA_ERROR_INSUFFICIENT_MEMORY;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000535 }
536
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100537 status = tfm_crypto_get_caller_id(&partition_id);
538 if (status != PSA_SUCCESS) {
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100539 return status;
540 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100541
Jamie Fox98ab4412020-01-17 17:12:30 +0000542 status = tfm_crypto_key_attributes_from_client(client_key_attr,
543 partition_id,
544 &key_attributes);
545 if (status != PSA_SUCCESS) {
546 return status;
547 }
548
549 status = psa_copy_key(source_handle, &key_attributes, target_handle);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100550
551 if (status == PSA_SUCCESS) {
552 handle_owner[i].owner = partition_id;
553 handle_owner[i].handle = *target_handle;
554 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
555 }
556
557 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100558#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Jamie Foxefd82732018-11-26 10:34:32 +0000559}
560
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100561psa_status_t tfm_crypto_generate_key(psa_invec in_vec[],
562 size_t in_len,
563 psa_outvec out_vec[],
564 size_t out_len)
Jamie Foxefd82732018-11-26 10:34:32 +0000565{
Kevin Peng96f802e2019-12-26 16:10:25 +0800566#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100567 return PSA_ERROR_NOT_SUPPORTED;
568#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100569
570 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 2, out_len, 1, 1);
Jamie Foxefd82732018-11-26 10:34:32 +0000571
Antonio de Angelis4743e672019-04-11 11:38:48 +0100572 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100573 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s)) ||
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100574 (out_vec[0].len != sizeof(psa_key_handle_t))) {
Soby Mathewc6e89362020-10-19 16:55:16 +0100575 return PSA_ERROR_PROGRAMMER_ERROR;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000576 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100577 psa_key_handle_t *key_handle = out_vec[0].base;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100578 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100579 psa_status_t status;
Jamie Fox98ab4412020-01-17 17:12:30 +0000580 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100581 uint32_t i = 0;
582 int32_t partition_id = 0;
583 bool empty_found = false;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000584
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100585 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
586 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
587 empty_found = true;
588 break;
589 }
Jamie Foxefd82732018-11-26 10:34:32 +0000590 }
591
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100592 if (!empty_found) {
593 return PSA_ERROR_INSUFFICIENT_MEMORY;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000594 }
595
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100596 status = tfm_crypto_get_caller_id(&partition_id);
597 if (status != PSA_SUCCESS) {
598 return status;
599 }
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000600
Jamie Fox98ab4412020-01-17 17:12:30 +0000601 status = tfm_crypto_key_attributes_from_client(client_key_attr,
602 partition_id,
603 &key_attributes);
604 if (status != PSA_SUCCESS) {
605 return status;
606 }
607
608 status = psa_generate_key(&key_attributes, key_handle);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100609
610 if (status == PSA_SUCCESS) {
611 handle_owner[i].owner = partition_id;
612 handle_owner[i].handle = *key_handle;
613 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
614 }
615
616 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100617#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Jamie Foxefd82732018-11-26 10:34:32 +0000618}
Antonio de Angelis8908f472018-08-31 15:44:25 +0100619/*!@}*/