blob: caf5387b16338f5d59607ac775db7b05aecdefa0 [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
Summer Qin4b1d03b2019-07-02 14:56:08 +080011/* FixMe: Use PSA_ERROR_CONNECTION_REFUSED when performing parameter
Antonio de Angelis4743e672019-04-11 11:38:48 +010012 * 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 */
Jamie Fox0e54ebc2019-04-09 14:21:04 +010016#include "tfm_mbedcrypto_include.h"
Antonio de Angelis4743e672019-04-11 11:38:48 +010017
Jamie Fox0e54ebc2019-04-09 14:21:04 +010018#include "tfm_crypto_api.h"
19#include "tfm_crypto_defs.h"
Soby Mathewd8abdfd2020-10-14 10:28:01 +010020#include "tfm_crypto_private.h"
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010021#include <stdbool.h>
Jamie Fox82b87ca2018-12-11 16:41:11 +000022
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010023#ifndef TFM_CRYPTO_MAX_KEY_HANDLES
24#define TFM_CRYPTO_MAX_KEY_HANDLES (16)
25#endif
26struct tfm_crypto_handle_owner_s {
27 int32_t owner; /*!< Owner of the allocated handle */
28 psa_key_handle_t handle; /*!< Allocated handle */
29 uint8_t in_use; /*!< Flag to indicate if this in use */
30};
31
Kevin Peng96f802e2019-12-26 16:10:25 +080032#ifndef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010033static struct tfm_crypto_handle_owner_s
34 handle_owner[TFM_CRYPTO_MAX_KEY_HANDLES] = {0};
Antonio de Angelis7740b382019-07-16 10:59:25 +010035#endif
Jamie Foxdadb4e82019-09-03 17:59:41 +010036
Antonio de Angelis8908f472018-08-31 15:44:25 +010037/*!
38 * \defgroup public Public functions
39 *
40 */
Antonio de Angelis8908f472018-08-31 15:44:25 +010041/*!@{*/
Jamie Fox98ab4412020-01-17 17:12:30 +000042psa_status_t tfm_crypto_key_attributes_from_client(
Soby Mathewd7b79f22020-05-21 15:06:54 +010043 const struct psa_client_key_attributes_s *client_key_attr,
Jamie Fox98ab4412020-01-17 17:12:30 +000044 int32_t client_id,
45 psa_key_attributes_t *key_attributes)
46{
47 if (client_key_attr == NULL || key_attributes == NULL) {
48 return PSA_ERROR_PROGRAMMER_ERROR;
49 }
50
Soby Mathewd7b79f22020-05-21 15:06:54 +010051 *key_attributes = psa_key_attributes_init();
Jamie Fox98ab4412020-01-17 17:12:30 +000052
53 /* Copy core key attributes from the client core key attributes */
Soby Mathewd7b79f22020-05-21 15:06:54 +010054 key_attributes->core.type = client_key_attr->type;
55 key_attributes->core.lifetime = client_key_attr->lifetime;
56 key_attributes->core.policy.usage = client_key_attr->usage;
57 key_attributes->core.policy.alg = client_key_attr->alg;
58 key_attributes->core.bits = client_key_attr->bits;
Jamie Fox98ab4412020-01-17 17:12:30 +000059
60 /* Use the client key id as the key_id and its partition id as the owner */
Soby Mathewd7b79f22020-05-21 15:06:54 +010061 key_attributes->core.id.key_id = client_key_attr->id;
Jamie Fox98ab4412020-01-17 17:12:30 +000062 key_attributes->core.id.owner = client_id;
63
64 return PSA_SUCCESS;
65}
66
67psa_status_t tfm_crypto_key_attributes_to_client(
68 const psa_key_attributes_t *key_attributes,
Soby Mathewd7b79f22020-05-21 15:06:54 +010069 struct psa_client_key_attributes_s *client_key_attr)
Jamie Fox98ab4412020-01-17 17:12:30 +000070{
71 if (client_key_attr == NULL || key_attributes == NULL) {
72 return PSA_ERROR_PROGRAMMER_ERROR;
73 }
74
Soby Mathewd7b79f22020-05-21 15:06:54 +010075 struct psa_client_key_attributes_s v = PSA_CLIENT_KEY_ATTRIBUTES_INIT;
76 *client_key_attr = v;
Jamie Fox98ab4412020-01-17 17:12:30 +000077
Soby Mathewd7b79f22020-05-21 15:06:54 +010078 /* Copy core key attributes from the client core key attributes */
79 client_key_attr->type = key_attributes->core.type;
80 client_key_attr->lifetime = key_attributes->core.lifetime;
81 client_key_attr->usage = key_attributes->core.policy.usage;
82 client_key_attr->alg = key_attributes->core.policy.alg;
83 client_key_attr->bits = key_attributes->core.bits;
Jamie Fox98ab4412020-01-17 17:12:30 +000084
85 /* Return the key_id as the client key id, do not return the owner */
Soby Mathewd7b79f22020-05-21 15:06:54 +010086 client_key_attr->id = key_attributes->core.id.key_id;
Jamie Fox98ab4412020-01-17 17:12:30 +000087
88 return PSA_SUCCESS;
89}
90
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010091psa_status_t tfm_crypto_check_handle_owner(psa_key_handle_t handle,
92 uint32_t *index)
93{
Kevin Peng96f802e2019-12-26 16:10:25 +080094#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +010095 return PSA_ERROR_NOT_SUPPORTED;
96#else
Antonio de Angelis60a6fe62019-06-18 15:27:34 +010097 int32_t partition_id = 0;
98 uint32_t i = 0;
99 psa_status_t status;
100
101 status = tfm_crypto_get_caller_id(&partition_id);
102 if (status != PSA_SUCCESS) {
103 return status;
104 }
105
106 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
107 if (handle_owner[i].in_use && handle_owner[i].handle == handle) {
108 if (handle_owner[i].owner == partition_id) {
109 if (index != NULL) {
110 *index = i;
111 }
112 return PSA_SUCCESS;
113 } else {
114 return PSA_ERROR_NOT_PERMITTED;
115 }
116 }
117 }
118
119 return PSA_ERROR_INVALID_HANDLE;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100120#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100121}
122
Jamie Fox99360e82020-02-20 16:00:09 +0000123psa_status_t tfm_crypto_check_key_storage(uint32_t *index)
124{
125#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
126 return PSA_ERROR_NOT_SUPPORTED;
127#else
128 uint32_t i;
129
130 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
131 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
132 *index = i;
133 return PSA_SUCCESS;
134 }
135 }
136
137 return PSA_ERROR_INSUFFICIENT_MEMORY;
138#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
139}
140
141psa_status_t tfm_crypto_set_key_storage(uint32_t index,
142 psa_key_handle_t key_handle)
143{
144#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
145 return PSA_ERROR_NOT_SUPPORTED;
146#else
147 psa_status_t status;
148 int32_t partition_id;
149
150 status = tfm_crypto_get_caller_id(&partition_id);
151 if (status != PSA_SUCCESS) {
152 return status;
153 }
154
155 handle_owner[index].owner = partition_id;
156 handle_owner[index].handle = key_handle;
157 handle_owner[index].in_use = TFM_CRYPTO_IN_USE;
158
159 return PSA_SUCCESS;
160#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
161}
162
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100163psa_status_t tfm_crypto_set_key_domain_parameters(psa_invec in_vec[],
164 size_t in_len,
165 psa_outvec out_vec[],
166 size_t out_len)
Antonio de Angeliscf85ba22018-10-09 13:29:40 +0100167{
Kevin Peng96f802e2019-12-26 16:10:25 +0800168#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100169 return PSA_ERROR_NOT_SUPPORTED;
170#else
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100171 /* FixMe: To be implemented */
172 return PSA_ERROR_NOT_SUPPORTED;
173#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
174}
175
176psa_status_t tfm_crypto_get_key_domain_parameters(psa_invec in_vec[],
177 size_t in_len,
178 psa_outvec out_vec[],
179 size_t out_len)
180{
181#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
182 return PSA_ERROR_NOT_SUPPORTED;
183#else
184 /* FixMe: To be implemented */
185 return PSA_ERROR_NOT_SUPPORTED;
186#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
187}
188
189psa_status_t tfm_crypto_import_key(psa_invec in_vec[],
190 size_t in_len,
191 psa_outvec out_vec[],
192 size_t out_len)
193{
194#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
195 return PSA_ERROR_NOT_SUPPORTED;
196#else
197
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100198 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 3, out_len, 1, 1);
Jamie Foxefd82732018-11-26 10:34:32 +0000199
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100200 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100201 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s)) ||
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100202 (out_vec[0].len != sizeof(psa_key_handle_t))) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800203 return PSA_ERROR_CONNECTION_REFUSED;
Jamie Foxefd82732018-11-26 10:34:32 +0000204 }
Soby Mathewd7b79f22020-05-21 15:06:54 +0100205 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100206 const uint8_t *data = in_vec[2].base;
207 size_t data_length = in_vec[2].len;
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100208 psa_key_handle_t *key_handle = out_vec[0].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100209 psa_status_t status;
Jamie Fox98ab4412020-01-17 17:12:30 +0000210 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100211 uint32_t i = 0;
212 int32_t partition_id = 0;
213 bool empty_found = false;
Jamie Foxefd82732018-11-26 10:34:32 +0000214
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100215 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
216 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
217 empty_found = true;
218 break;
219 }
220 }
221
222 if (!empty_found) {
223 return PSA_ERROR_INSUFFICIENT_MEMORY;
224 }
225
226 status = tfm_crypto_get_caller_id(&partition_id);
227 if (status != PSA_SUCCESS) {
228 return status;
229 }
230
Jamie Fox98ab4412020-01-17 17:12:30 +0000231 status = tfm_crypto_key_attributes_from_client(client_key_attr,
232 partition_id,
233 &key_attributes);
234 if (status != PSA_SUCCESS) {
235 return status;
236 }
237
238 status = psa_import_key(&key_attributes, data, data_length, key_handle);
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100239
240 if (status == PSA_SUCCESS) {
241 handle_owner[i].owner = partition_id;
242 handle_owner[i].handle = *key_handle;
243 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
244 }
245
246 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100247#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Jamie Foxefd82732018-11-26 10:34:32 +0000248}
249
Jamie Foxdadb4e82019-09-03 17:59:41 +0100250psa_status_t tfm_crypto_open_key(psa_invec in_vec[],
251 size_t in_len,
252 psa_outvec out_vec[],
253 size_t out_len)
254{
Kevin Peng96f802e2019-12-26 16:10:25 +0800255#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Jamie Foxdadb4e82019-09-03 17:59:41 +0100256 return PSA_ERROR_NOT_SUPPORTED;
257#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100258
259 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 2, out_len, 1, 1);
Jamie Foxdadb4e82019-09-03 17:59:41 +0100260
261 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Jamie Fox98ab4412020-01-17 17:12:30 +0000262 (in_vec[1].len != sizeof(psa_app_key_id_t)) ||
Jamie Foxdadb4e82019-09-03 17:59:41 +0100263 (out_vec[0].len != sizeof(psa_key_handle_t))) {
264 return PSA_ERROR_CONNECTION_REFUSED;
265 }
266
Jamie Fox98ab4412020-01-17 17:12:30 +0000267 psa_app_key_id_t client_key_id = *((psa_app_key_id_t *)in_vec[1].base);
268 psa_key_handle_t *key_handle = out_vec[0].base;
269 psa_status_t status;
270 psa_key_id_t id;
271 int32_t partition_id;
272 uint32_t i;
273
274 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
275 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
276 break;
277 }
278 }
279
280 if (i == TFM_CRYPTO_MAX_KEY_HANDLES) {
281 return PSA_ERROR_INSUFFICIENT_MEMORY;
282 }
283
284 status = tfm_crypto_get_caller_id(&partition_id);
285 if (status != PSA_SUCCESS) {
286 return status;
287 }
288
289 /* Use the client key id as the key_id and its partition id as the owner */
290 id = (psa_key_id_t){ .key_id = client_key_id, .owner = partition_id };
291
292 status = psa_open_key(id, key_handle);
293
294 if (status == PSA_SUCCESS) {
295 handle_owner[i].owner = partition_id;
296 handle_owner[i].handle = *key_handle;
297 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
298 }
299
300 return status;
Jamie Foxdadb4e82019-09-03 17:59:41 +0100301#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
302}
303
304psa_status_t tfm_crypto_close_key(psa_invec in_vec[],
305 size_t in_len,
306 psa_outvec out_vec[],
307 size_t out_len)
308{
Kevin Peng96f802e2019-12-26 16:10:25 +0800309#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Jamie Foxdadb4e82019-09-03 17:59:41 +0100310 return PSA_ERROR_NOT_SUPPORTED;
311#else
312 (void)out_vec;
313
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100314 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 0);
Jamie Foxdadb4e82019-09-03 17:59:41 +0100315
316 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
317 return PSA_ERROR_CONNECTION_REFUSED;
318 }
319 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
320
321 psa_key_handle_t key = iov->key_handle;
322 uint32_t index;
323 psa_status_t status = tfm_crypto_check_handle_owner(key, &index);
324
325 if (status != PSA_SUCCESS) {
326 return status;
327 }
328
329 status = psa_close_key(key);
330
331 if (status == PSA_SUCCESS) {
332 handle_owner[index].owner = 0;
333 handle_owner[index].handle = 0;
334 handle_owner[index].in_use = TFM_CRYPTO_NOT_IN_USE;
335 }
336
337 return status;
338#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
339}
340
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000341psa_status_t tfm_crypto_destroy_key(psa_invec in_vec[],
342 size_t in_len,
343 psa_outvec out_vec[],
344 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100345{
Kevin Peng96f802e2019-12-26 16:10:25 +0800346#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100347 return PSA_ERROR_NOT_SUPPORTED;
348#else
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100349 (void)out_vec;
Antonio de Angelis8908f472018-08-31 15:44:25 +0100350
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100351 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 0);
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000352
Antonio de Angelis4743e672019-04-11 11:38:48 +0100353 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800354 return PSA_ERROR_CONNECTION_REFUSED;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000355 }
Antonio de Angelis4743e672019-04-11 11:38:48 +0100356 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000357
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100358 psa_key_handle_t key = iov->key_handle;
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100359 uint32_t index;
360 psa_status_t status = tfm_crypto_check_handle_owner(key, &index);
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000361
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100362 if (status != PSA_SUCCESS) {
363 return status;
364 }
365
366 status = psa_destroy_key(key);
367
368 if (status == PSA_SUCCESS) {
369 handle_owner[index].owner = 0;
370 handle_owner[index].handle = 0;
371 handle_owner[index].in_use = TFM_CRYPTO_NOT_IN_USE;
372 }
373
374 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100375#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis8908f472018-08-31 15:44:25 +0100376}
377
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100378psa_status_t tfm_crypto_get_key_attributes(psa_invec in_vec[],
379 size_t in_len,
380 psa_outvec out_vec[],
381 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100382{
Kevin Peng96f802e2019-12-26 16:10:25 +0800383#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100384 return PSA_ERROR_NOT_SUPPORTED;
385#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100386
387 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 1, 1);
Jamie Foxefd82732018-11-26 10:34:32 +0000388
Antonio de Angelis4743e672019-04-11 11:38:48 +0100389 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100390 (out_vec[0].len != sizeof(struct psa_client_key_attributes_s))) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800391 return PSA_ERROR_CONNECTION_REFUSED;
Jamie Foxefd82732018-11-26 10:34:32 +0000392 }
Antonio de Angelis4743e672019-04-11 11:38:48 +0100393 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
Jamie Foxefd82732018-11-26 10:34:32 +0000394
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100395 psa_key_handle_t key = iov->key_handle;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100396 struct psa_client_key_attributes_s *client_key_attr = out_vec[0].base;
Jamie Fox98ab4412020-01-17 17:12:30 +0000397 psa_status_t status;
398 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000399
Jamie Fox98ab4412020-01-17 17:12:30 +0000400 status = tfm_crypto_check_handle_owner(key, NULL);
401 if (status != PSA_SUCCESS) {
402 return status;
403 }
404
405 status = psa_get_key_attributes(key, &key_attributes);
406
407 if (status == PSA_SUCCESS) {
408 status = tfm_crypto_key_attributes_to_client(&key_attributes,
409 client_key_attr);
410 }
411
412 return status;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100413#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
414}
415
416psa_status_t tfm_crypto_reset_key_attributes(psa_invec in_vec[],
417 size_t in_len,
418 psa_outvec out_vec[],
419 size_t out_len)
420{
421#if (TFM_CRYPTO_KEY_MODULE_DISABLED != 0)
422 return PSA_ERROR_NOT_SUPPORTED;
423#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100424
425 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 1, 1);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100426
427 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100428 (out_vec[0].len != sizeof(struct psa_client_key_attributes_s))) {
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100429 return PSA_ERROR_CONNECTION_REFUSED;
430 }
431
Soby Mathewd7b79f22020-05-21 15:06:54 +0100432 struct psa_client_key_attributes_s *client_key_attr = out_vec[0].base;
Jamie Fox98ab4412020-01-17 17:12:30 +0000433 psa_status_t status;
434 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
435 int32_t partition_id;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100436
Jamie Fox98ab4412020-01-17 17:12:30 +0000437 status = tfm_crypto_get_caller_id(&partition_id);
438 if (status != PSA_SUCCESS) {
439 return status;
440 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100441
Jamie Fox98ab4412020-01-17 17:12:30 +0000442 status = tfm_crypto_key_attributes_from_client(client_key_attr,
443 partition_id,
444 &key_attributes);
445 if (status != PSA_SUCCESS) {
446 return status;
447 }
448
449 psa_reset_key_attributes(&key_attributes);
450
451 return tfm_crypto_key_attributes_to_client(&key_attributes,
452 client_key_attr);
Antonio de Angelis7740b382019-07-16 10:59:25 +0100453#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis8908f472018-08-31 15:44:25 +0100454}
455
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000456psa_status_t tfm_crypto_export_key(psa_invec in_vec[],
457 size_t in_len,
458 psa_outvec out_vec[],
459 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100460{
Kevin Peng96f802e2019-12-26 16:10:25 +0800461#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100462 return PSA_ERROR_NOT_SUPPORTED;
463#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100464
465 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 1);
Antonio de Angelis8908f472018-08-31 15:44:25 +0100466
Antonio de Angelis4743e672019-04-11 11:38:48 +0100467 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800468 return PSA_ERROR_CONNECTION_REFUSED;
Antonio de Angelis8908f472018-08-31 15:44:25 +0100469 }
Antonio de Angelis4743e672019-04-11 11:38:48 +0100470 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
Antonio de Angelis8908f472018-08-31 15:44:25 +0100471
Jamie Fox0e54ebc2019-04-09 14:21:04 +0100472 psa_key_handle_t key = iov->key_handle;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000473 uint8_t *data = out_vec[0].base;
474 size_t data_size = out_vec[0].len;
475
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100476 return psa_export_key(key, data, data_size, &(out_vec[0].len));
Antonio de Angelis7740b382019-07-16 10:59:25 +0100477#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis8908f472018-08-31 15:44:25 +0100478}
479
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000480psa_status_t tfm_crypto_export_public_key(psa_invec in_vec[],
481 size_t in_len,
482 psa_outvec out_vec[],
483 size_t out_len)
Antonio de Angelis8908f472018-08-31 15:44:25 +0100484{
Kevin Peng96f802e2019-12-26 16:10:25 +0800485#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100486 return PSA_ERROR_NOT_SUPPORTED;
487#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100488
489 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 1, 1, out_len, 0, 1);
Hugues de Valon8b442442019-02-19 14:30:52 +0000490
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100491 if (in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800492 return PSA_ERROR_CONNECTION_REFUSED;
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100493 }
494 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
495
496 psa_key_handle_t key = iov->key_handle;
497 uint8_t *data = out_vec[0].base;
498 size_t data_size = out_vec[0].len;
499
500 return psa_export_public_key(key, data, data_size, &(out_vec[0].len));
Antonio de Angelis7740b382019-07-16 10:59:25 +0100501#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100502}
503
504psa_status_t tfm_crypto_copy_key(psa_invec in_vec[],
505 size_t in_len,
506 psa_outvec out_vec[],
507 size_t out_len)
508{
Kevin Peng96f802e2019-12-26 16:10:25 +0800509#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100510 return PSA_ERROR_NOT_SUPPORTED;
511#else
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100512
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100513 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 2, out_len, 1, 1);
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100514
515 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100516 (out_vec[0].len != sizeof(psa_key_handle_t)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100517 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s))) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800518 return PSA_ERROR_CONNECTION_REFUSED;
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100519 }
520 const struct tfm_crypto_pack_iovec *iov = in_vec[0].base;
521
522 psa_key_handle_t source_handle = iov->key_handle;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100523 psa_key_handle_t *target_handle = out_vec[0].base;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100524 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100525 psa_status_t status;
Jamie Fox98ab4412020-01-17 17:12:30 +0000526 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100527 uint32_t i = 0;
528 int32_t partition_id = 0;
529 bool empty_found = false;
Antonio de Angelis25e2b2d2019-04-25 14:49:50 +0100530
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100531 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
532 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
533 empty_found = true;
534 break;
535 }
Jamie Foxefd82732018-11-26 10:34:32 +0000536 }
537
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100538 if (!empty_found) {
539 return PSA_ERROR_INSUFFICIENT_MEMORY;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000540 }
541
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100542 status = tfm_crypto_get_caller_id(&partition_id);
543 if (status != PSA_SUCCESS) {
Antonio de Angelis60a6fe62019-06-18 15:27:34 +0100544 return status;
545 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100546
Jamie Fox98ab4412020-01-17 17:12:30 +0000547 status = tfm_crypto_key_attributes_from_client(client_key_attr,
548 partition_id,
549 &key_attributes);
550 if (status != PSA_SUCCESS) {
551 return status;
552 }
553
554 status = psa_copy_key(source_handle, &key_attributes, target_handle);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100555
556 if (status == PSA_SUCCESS) {
557 handle_owner[i].owner = partition_id;
558 handle_owner[i].handle = *target_handle;
559 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
560 }
561
562 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100563#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Jamie Foxefd82732018-11-26 10:34:32 +0000564}
565
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100566psa_status_t tfm_crypto_generate_key(psa_invec in_vec[],
567 size_t in_len,
568 psa_outvec out_vec[],
569 size_t out_len)
Jamie Foxefd82732018-11-26 10:34:32 +0000570{
Kevin Peng96f802e2019-12-26 16:10:25 +0800571#ifdef TFM_CRYPTO_KEY_MODULE_DISABLED
Antonio de Angelis7740b382019-07-16 10:59:25 +0100572 return PSA_ERROR_NOT_SUPPORTED;
573#else
Soby Mathewd8abdfd2020-10-14 10:28:01 +0100574
575 CRYPTO_IN_OUT_LEN_VALIDATE(in_len, 2, 2, out_len, 1, 1);
Jamie Foxefd82732018-11-26 10:34:32 +0000576
Antonio de Angelis4743e672019-04-11 11:38:48 +0100577 if ((in_vec[0].len != sizeof(struct tfm_crypto_pack_iovec)) ||
Soby Mathewd7b79f22020-05-21 15:06:54 +0100578 (in_vec[1].len != sizeof(struct psa_client_key_attributes_s)) ||
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100579 (out_vec[0].len != sizeof(psa_key_handle_t))) {
Summer Qin4b1d03b2019-07-02 14:56:08 +0800580 return PSA_ERROR_CONNECTION_REFUSED;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000581 }
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100582 psa_key_handle_t *key_handle = out_vec[0].base;
Soby Mathewd7b79f22020-05-21 15:06:54 +0100583 const struct psa_client_key_attributes_s *client_key_attr = in_vec[1].base;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100584 psa_status_t status;
Jamie Fox98ab4412020-01-17 17:12:30 +0000585 psa_key_attributes_t key_attributes = PSA_KEY_ATTRIBUTES_INIT;
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100586 uint32_t i = 0;
587 int32_t partition_id = 0;
588 bool empty_found = false;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000589
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100590 for (i = 0; i < TFM_CRYPTO_MAX_KEY_HANDLES; i++) {
591 if (handle_owner[i].in_use == TFM_CRYPTO_NOT_IN_USE) {
592 empty_found = true;
593 break;
594 }
Jamie Foxefd82732018-11-26 10:34:32 +0000595 }
596
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100597 if (!empty_found) {
598 return PSA_ERROR_INSUFFICIENT_MEMORY;
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000599 }
600
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100601 status = tfm_crypto_get_caller_id(&partition_id);
602 if (status != PSA_SUCCESS) {
603 return status;
604 }
Antonio de Angelisab85ccd2019-03-25 15:14:29 +0000605
Jamie Fox98ab4412020-01-17 17:12:30 +0000606 status = tfm_crypto_key_attributes_from_client(client_key_attr,
607 partition_id,
608 &key_attributes);
609 if (status != PSA_SUCCESS) {
610 return status;
611 }
612
613 status = psa_generate_key(&key_attributes, key_handle);
Antonio de Angelis04debbd2019-10-14 12:12:52 +0100614
615 if (status == PSA_SUCCESS) {
616 handle_owner[i].owner = partition_id;
617 handle_owner[i].handle = *key_handle;
618 handle_owner[i].in_use = TFM_CRYPTO_IN_USE;
619 }
620
621 return status;
Antonio de Angelis7740b382019-07-16 10:59:25 +0100622#endif /* TFM_CRYPTO_KEY_MODULE_DISABLED */
Jamie Foxefd82732018-11-26 10:34:32 +0000623}
Antonio de Angelis8908f472018-08-31 15:44:25 +0100624/*!@}*/