blob: 89fc86d99e535f01609a2b2eea3792836910a4b0 [file] [log] [blame]
Julian Hallc02fffb2020-11-23 18:22:06 +01001/*
julhal01c3f4e9a2020-12-15 13:39:01 +00002 * Copyright (c) 2020-2021, Arm Limited and Contributors. All rights reserved.
Julian Hallc02fffb2020-11-23 18:22:06 +01003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6#include <stdint.h>
7#include <stdlib.h>
8#include <protocols/service/crypto/packed-c/opcodes.h>
Julian Hall9061e6c2021-06-29 14:24:20 +01009#include <service/crypto/provider/crypto_provider.h>
Julian Hallc02fffb2020-11-23 18:22:06 +010010#include <protocols/rpc/common/packed-c/status.h>
11#include <psa/crypto.h>
12
13/* Service request handlers */
Julian Hallc02fffb2020-11-23 18:22:06 +010014static rpc_status_t generate_key_handler(void *context, struct call_req* req);
15static rpc_status_t destroy_key_handler(void *context, struct call_req* req);
Julian Hallc02fffb2020-11-23 18:22:06 +010016static rpc_status_t export_key_handler(void *context, struct call_req* req);
17static rpc_status_t export_public_key_handler(void *context, struct call_req* req);
18static rpc_status_t import_key_handler(void *context, struct call_req* req);
19static rpc_status_t sign_hash_handler(void *context, struct call_req* req);
20static rpc_status_t verify_hash_handler(void *context, struct call_req* req);
21static rpc_status_t asymmetric_decrypt_handler(void *context, struct call_req* req);
22static rpc_status_t asymmetric_encrypt_handler(void *context, struct call_req* req);
23static rpc_status_t generate_random_handler(void *context, struct call_req* req);
Julian Hall8359a632021-07-08 15:10:30 +010024static rpc_status_t copy_key_handler(void *context, struct call_req* req);
25static rpc_status_t purge_key_handler(void *context, struct call_req* req);
26static rpc_status_t get_key_attributes_handler(void *context, struct call_req* req);
Julian Hallc02fffb2020-11-23 18:22:06 +010027
28/* Handler mapping table for service */
29static const struct service_handler handler_table[] = {
Julian Hallf5728962021-06-24 09:40:23 +010030 {TS_CRYPTO_OPCODE_GENERATE_KEY, generate_key_handler},
31 {TS_CRYPTO_OPCODE_DESTROY_KEY, destroy_key_handler},
32 {TS_CRYPTO_OPCODE_EXPORT_KEY, export_key_handler},
33 {TS_CRYPTO_OPCODE_EXPORT_PUBLIC_KEY, export_public_key_handler},
34 {TS_CRYPTO_OPCODE_IMPORT_KEY, import_key_handler},
35 {TS_CRYPTO_OPCODE_SIGN_HASH, sign_hash_handler},
36 {TS_CRYPTO_OPCODE_VERIFY_HASH, verify_hash_handler},
37 {TS_CRYPTO_OPCODE_ASYMMETRIC_DECRYPT, asymmetric_decrypt_handler},
38 {TS_CRYPTO_OPCODE_ASYMMETRIC_ENCRYPT, asymmetric_encrypt_handler},
39 {TS_CRYPTO_OPCODE_GENERATE_RANDOM, generate_random_handler},
Julian Hall8359a632021-07-08 15:10:30 +010040 {TS_CRYPTO_OPCODE_COPY_KEY, copy_key_handler},
41 {TS_CRYPTO_OPCODE_PURGE_KEY, purge_key_handler},
42 {TS_CRYPTO_OPCODE_GET_KEY_ATTRIBUTES, get_key_attributes_handler},
Julian Hallc02fffb2020-11-23 18:22:06 +010043};
44
Julian Hall9061e6c2021-06-29 14:24:20 +010045struct rpc_interface *crypto_provider_init(struct crypto_provider *context)
Julian Hallc02fffb2020-11-23 18:22:06 +010046{
Julian Hall9061e6c2021-06-29 14:24:20 +010047 for (size_t encoding = 0; encoding < TS_RPC_ENCODING_LIMIT; ++encoding)
48 context->serializers[encoding] = NULL;
Julian Hallc02fffb2020-11-23 18:22:06 +010049
Julian Hall9061e6c2021-06-29 14:24:20 +010050 service_provider_init(&context->base_provider, context,
Julian Hallf5728962021-06-24 09:40:23 +010051 handler_table, sizeof(handler_table)/sizeof(struct service_handler));
Julian Hallc02fffb2020-11-23 18:22:06 +010052
Julian Hall9061e6c2021-06-29 14:24:20 +010053 return service_provider_get_rpc_interface(&context->base_provider);
Julian Hallc02fffb2020-11-23 18:22:06 +010054}
55
Julian Hall9061e6c2021-06-29 14:24:20 +010056void crypto_provider_deinit(struct crypto_provider *context)
Julian Hallc02fffb2020-11-23 18:22:06 +010057{
Julian Hall7bfb18e2021-07-13 15:48:13 +010058
Julian Hallc02fffb2020-11-23 18:22:06 +010059}
60
Julian Hall9061e6c2021-06-29 14:24:20 +010061void crypto_provider_register_serializer(struct crypto_provider *context,
62 unsigned int encoding, const struct crypto_provider_serializer *serializer)
Julian Hallc02fffb2020-11-23 18:22:06 +010063{
Julian Hallf5728962021-06-24 09:40:23 +010064 if (encoding < TS_RPC_ENCODING_LIMIT)
65 context->serializers[encoding] = serializer;
julhal01c3f4e9a2020-12-15 13:39:01 +000066}
67
Julian Hall13e76952021-07-13 12:17:09 +010068void crypto_provider_extend(struct crypto_provider *context,
69 struct service_provider *sub_provider)
70{
71 service_provider_extend(&context->base_provider, sub_provider);
72}
73
julhal01c3f4e9a2020-12-15 13:39:01 +000074static const struct crypto_provider_serializer* get_crypto_serializer(void *context,
Julian Hallf5728962021-06-24 09:40:23 +010075 const struct call_req *req)
julhal01c3f4e9a2020-12-15 13:39:01 +000076{
Julian Hall9061e6c2021-06-29 14:24:20 +010077 struct crypto_provider *this_instance = (struct crypto_provider*)context;
Julian Hallf5728962021-06-24 09:40:23 +010078 const struct crypto_provider_serializer* serializer = NULL;
79 unsigned int encoding = call_req_get_encoding(req);
julhal01c3f4e9a2020-12-15 13:39:01 +000080
Julian Hallf5728962021-06-24 09:40:23 +010081 if (encoding < TS_RPC_ENCODING_LIMIT) serializer = this_instance->serializers[encoding];
julhal01c3f4e9a2020-12-15 13:39:01 +000082
Julian Hallf5728962021-06-24 09:40:23 +010083 return serializer;
Julian Hallc02fffb2020-11-23 18:22:06 +010084}
85
Julian Hallc02fffb2020-11-23 18:22:06 +010086static rpc_status_t generate_key_handler(void *context, struct call_req* req)
87{
Julian Hallf5728962021-06-24 09:40:23 +010088 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
89 struct call_param_buf *req_buf = call_req_get_req_buf(req);
90 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +010091
Julian Hallf5728962021-06-24 09:40:23 +010092 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Julian Hallc02fffb2020-11-23 18:22:06 +010093
Julian Hallf5728962021-06-24 09:40:23 +010094 if (serializer)
95 rpc_status = serializer->deserialize_generate_key_req(req_buf, &attributes);
Julian Hallc02fffb2020-11-23 18:22:06 +010096
Julian Hallf5728962021-06-24 09:40:23 +010097 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +010098
Julian Hallf5728962021-06-24 09:40:23 +010099 psa_status_t psa_status;
100 psa_key_id_t id;
Julian Hallc02fffb2020-11-23 18:22:06 +0100101
Julian Hallf5728962021-06-24 09:40:23 +0100102 psa_status = psa_generate_key(&attributes, &id);
Julian Hallc02fffb2020-11-23 18:22:06 +0100103
Julian Hallf5728962021-06-24 09:40:23 +0100104 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100105
Julian Hallf5728962021-06-24 09:40:23 +0100106 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
107 rpc_status = serializer->serialize_generate_key_resp(resp_buf, id);
108 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100109
Julian Hallf5728962021-06-24 09:40:23 +0100110 call_req_set_opstatus(req, psa_status);
111 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100112
Julian Hallf5728962021-06-24 09:40:23 +0100113 psa_reset_key_attributes(&attributes);
Julian Hallc02fffb2020-11-23 18:22:06 +0100114
Julian Hallf5728962021-06-24 09:40:23 +0100115 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100116}
117
118static rpc_status_t destroy_key_handler(void *context, struct call_req* req)
119{
Julian Hallf5728962021-06-24 09:40:23 +0100120 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
121 struct call_param_buf *req_buf = call_req_get_req_buf(req);
122 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100123
Julian Hallf5728962021-06-24 09:40:23 +0100124 psa_key_id_t id;
Julian Hallc02fffb2020-11-23 18:22:06 +0100125
Julian Hallf5728962021-06-24 09:40:23 +0100126 if (serializer)
127 rpc_status = serializer->deserialize_destroy_key_req(req_buf, &id);
Julian Hallc02fffb2020-11-23 18:22:06 +0100128
Julian Hallf5728962021-06-24 09:40:23 +0100129 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100130
Julian Hallf5728962021-06-24 09:40:23 +0100131 psa_status_t psa_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100132
Julian Hallf5728962021-06-24 09:40:23 +0100133 psa_status = psa_destroy_key(id);
134 call_req_set_opstatus(req, psa_status);
135 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100136
Julian Hallf5728962021-06-24 09:40:23 +0100137 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100138}
139
140static rpc_status_t export_key_handler(void *context, struct call_req* req)
141{
Julian Hallf5728962021-06-24 09:40:23 +0100142 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
143 struct call_param_buf *req_buf = call_req_get_req_buf(req);
144 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100145
Julian Hallf5728962021-06-24 09:40:23 +0100146 psa_key_id_t id;
Julian Hallc02fffb2020-11-23 18:22:06 +0100147
Julian Hallf5728962021-06-24 09:40:23 +0100148 if (serializer)
149 rpc_status = serializer->deserialize_export_key_req(req_buf, &id);
Julian Hallc02fffb2020-11-23 18:22:06 +0100150
Julian Hallf5728962021-06-24 09:40:23 +0100151 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100152
Julian Hallf5728962021-06-24 09:40:23 +0100153 psa_status_t psa_status;
154 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Julian Hallc02fffb2020-11-23 18:22:06 +0100155
Julian Hallf5728962021-06-24 09:40:23 +0100156 psa_status = psa_get_key_attributes(id, &attributes);
Julian Hallc02fffb2020-11-23 18:22:06 +0100157
Julian Hallf5728962021-06-24 09:40:23 +0100158 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100159
Julian Hallf5728962021-06-24 09:40:23 +0100160 size_t max_export_size = PSA_EXPORT_KEY_OUTPUT_SIZE(
161 psa_get_key_type(&attributes),
162 psa_get_key_bits(&attributes));
Julian Hallc02fffb2020-11-23 18:22:06 +0100163
Julian Hallec81a502021-07-12 11:36:37 +0100164 if (max_export_size) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100165
Julian Hallec81a502021-07-12 11:36:37 +0100166 uint8_t *key_buffer = malloc(max_export_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100167
Julian Hallec81a502021-07-12 11:36:37 +0100168 if (key_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100169
Julian Hallec81a502021-07-12 11:36:37 +0100170 size_t export_size;
171 psa_status_t psa_status = psa_export_key(id, key_buffer,
172 max_export_size, &export_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100173
Julian Hallec81a502021-07-12 11:36:37 +0100174 if (psa_status == PSA_SUCCESS) {
175
176 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
177 rpc_status = serializer->serialize_export_key_resp(resp_buf,
178 key_buffer, export_size);
179 }
180
181 free(key_buffer);
Julian Hallf5728962021-06-24 09:40:23 +0100182 }
Julian Hallec81a502021-07-12 11:36:37 +0100183 else {
184 /* Failed to allocate key buffer */
185 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
186 }
Julian Hallf5728962021-06-24 09:40:23 +0100187 }
188 else {
Julian Hallec81a502021-07-12 11:36:37 +0100189
190 /* No sensible export size was returned so
191 * key attributes must be in an invalid state.
192 */
193 psa_status = PSA_ERROR_GENERIC_ERROR;
Julian Hallf5728962021-06-24 09:40:23 +0100194 }
195 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100196
Julian Hallf5728962021-06-24 09:40:23 +0100197 call_req_set_opstatus(req, psa_status);
198 psa_reset_key_attributes(&attributes);
199 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100200
Julian Hallf5728962021-06-24 09:40:23 +0100201 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100202}
203
204static rpc_status_t export_public_key_handler(void *context, struct call_req* req)
205{
Julian Hallf5728962021-06-24 09:40:23 +0100206 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
207 struct call_param_buf *req_buf = call_req_get_req_buf(req);
208 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100209
Julian Hallf5728962021-06-24 09:40:23 +0100210 psa_key_id_t id;
Julian Hallc02fffb2020-11-23 18:22:06 +0100211
Julian Hallf5728962021-06-24 09:40:23 +0100212 if (serializer)
213 rpc_status = serializer->deserialize_export_public_key_req(req_buf, &id);
Julian Hallc02fffb2020-11-23 18:22:06 +0100214
Julian Hallf5728962021-06-24 09:40:23 +0100215 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100216
Julian Hallec81a502021-07-12 11:36:37 +0100217 size_t max_export_size = PSA_EXPORT_PUBLIC_KEY_MAX_SIZE;
218 uint8_t *key_buffer = malloc(max_export_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100219
Julian Hallec81a502021-07-12 11:36:37 +0100220 if (key_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100221
Julian Hallec81a502021-07-12 11:36:37 +0100222 size_t export_size;
223 psa_status_t psa_status = psa_export_public_key(id, key_buffer,
224 max_export_size, &export_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100225
Julian Hallec81a502021-07-12 11:36:37 +0100226 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100227
Julian Hallec81a502021-07-12 11:36:37 +0100228 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
229 rpc_status = serializer->serialize_export_public_key_resp(resp_buf,
230 key_buffer, export_size);
Julian Hallf5728962021-06-24 09:40:23 +0100231 }
Julian Hallec81a502021-07-12 11:36:37 +0100232
233 free(key_buffer);
234 call_req_set_opstatus(req, psa_status);
Julian Hallf5728962021-06-24 09:40:23 +0100235 }
Julian Hallec81a502021-07-12 11:36:37 +0100236 else {
237 /* Failed to allocate key buffer */
238 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
239 }
Julian Hallf5728962021-06-24 09:40:23 +0100240 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100241
Julian Hallf5728962021-06-24 09:40:23 +0100242 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100243}
244
245static rpc_status_t import_key_handler(void *context, struct call_req* req)
246{
Julian Hallf5728962021-06-24 09:40:23 +0100247 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
248 struct call_param_buf *req_buf = call_req_get_req_buf(req);
249 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100250
Julian Hallf5728962021-06-24 09:40:23 +0100251 if (serializer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100252
Julian Hallf5728962021-06-24 09:40:23 +0100253 size_t key_data_len = serializer->max_deserialised_parameter_size(req_buf);
254 uint8_t *key_buffer = malloc(key_data_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100255
Julian Hallf5728962021-06-24 09:40:23 +0100256 if (key_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100257
Julian Hallf5728962021-06-24 09:40:23 +0100258 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Julian Hallec81a502021-07-12 11:36:37 +0100259 rpc_status = serializer->deserialize_import_key_req(req_buf, &attributes,
260 key_buffer, &key_data_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100261
Julian Hallf5728962021-06-24 09:40:23 +0100262 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100263
Julian Hallf5728962021-06-24 09:40:23 +0100264 psa_status_t psa_status;
265 psa_key_id_t id;
Julian Hallc02fffb2020-11-23 18:22:06 +0100266
Julian Hallf5728962021-06-24 09:40:23 +0100267 psa_status = psa_import_key(&attributes, key_buffer, key_data_len, &id);
Julian Hallc02fffb2020-11-23 18:22:06 +0100268
Julian Hallf5728962021-06-24 09:40:23 +0100269 if (psa_status == PSA_SUCCESS) {
julhal01c3f4e9a2020-12-15 13:39:01 +0000270
Julian Hallf5728962021-06-24 09:40:23 +0100271 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
272 rpc_status = serializer->serialize_import_key_resp(resp_buf, id);
273 }
julhal01c3f4e9a2020-12-15 13:39:01 +0000274
Julian Hallf5728962021-06-24 09:40:23 +0100275 call_req_set_opstatus(req, psa_status);
276 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100277
Julian Hallf5728962021-06-24 09:40:23 +0100278 psa_reset_key_attributes(&attributes);
279 free(key_buffer);
280 }
281 else {
Julian Hallc02fffb2020-11-23 18:22:06 +0100282
Julian Hallf5728962021-06-24 09:40:23 +0100283 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
284 }
285 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100286
Julian Hallf5728962021-06-24 09:40:23 +0100287 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100288}
289
290static rpc_status_t sign_hash_handler(void *context, struct call_req* req)
291{
Julian Hallf5728962021-06-24 09:40:23 +0100292 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
293 struct call_param_buf *req_buf = call_req_get_req_buf(req);
294 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100295
Julian Hallf5728962021-06-24 09:40:23 +0100296 psa_key_id_t id;
297 psa_algorithm_t alg;
298 size_t hash_len = PSA_HASH_MAX_SIZE;
299 uint8_t hash_buffer[PSA_HASH_MAX_SIZE];
Julian Hallc02fffb2020-11-23 18:22:06 +0100300
Julian Hallf5728962021-06-24 09:40:23 +0100301 if (serializer)
302 rpc_status = serializer->deserialize_sign_hash_req(req_buf, &id, &alg, hash_buffer, &hash_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100303
Julian Hallf5728962021-06-24 09:40:23 +0100304 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100305
Julian Hallf5728962021-06-24 09:40:23 +0100306 psa_status_t psa_status;
307 size_t sig_len;
308 uint8_t sig_buffer[PSA_SIGNATURE_MAX_SIZE];
Julian Hallc02fffb2020-11-23 18:22:06 +0100309
Julian Hallf5728962021-06-24 09:40:23 +0100310 psa_status = psa_sign_hash(id, alg,
311 hash_buffer, hash_len,
312 sig_buffer, sizeof(sig_buffer), &sig_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100313
Julian Hallf5728962021-06-24 09:40:23 +0100314 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100315
Julian Hallf5728962021-06-24 09:40:23 +0100316 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
317 rpc_status = serializer->serialize_sign_hash_resp(resp_buf, sig_buffer, sig_len);
318 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100319
Julian Hallf5728962021-06-24 09:40:23 +0100320 call_req_set_opstatus(req, psa_status);
321 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100322
Julian Hallf5728962021-06-24 09:40:23 +0100323 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100324}
325
326static rpc_status_t verify_hash_handler(void *context, struct call_req* req)
327{
Julian Hallf5728962021-06-24 09:40:23 +0100328 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
329 struct call_param_buf *req_buf = call_req_get_req_buf(req);
330 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100331
Julian Hallf5728962021-06-24 09:40:23 +0100332 psa_key_id_t id;
333 psa_algorithm_t alg;
334 size_t hash_len = PSA_HASH_MAX_SIZE;
335 uint8_t hash_buffer[PSA_HASH_MAX_SIZE];
336 size_t sig_len = PSA_SIGNATURE_MAX_SIZE;
337 uint8_t sig_buffer[PSA_SIGNATURE_MAX_SIZE];
Julian Hallc02fffb2020-11-23 18:22:06 +0100338
Julian Hallf5728962021-06-24 09:40:23 +0100339 if (serializer)
340 rpc_status = serializer->deserialize_verify_hash_req(req_buf, &id, &alg,
341 hash_buffer, &hash_len,
342 sig_buffer, &sig_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100343
Julian Hallf5728962021-06-24 09:40:23 +0100344 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100345
Julian Hallf5728962021-06-24 09:40:23 +0100346 psa_status_t psa_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100347
Julian Hallf5728962021-06-24 09:40:23 +0100348 psa_status = psa_verify_hash(id, alg,
349 hash_buffer, hash_len,
350 sig_buffer, sig_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100351
Julian Hallf5728962021-06-24 09:40:23 +0100352 call_req_set_opstatus(req, psa_status);
353 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100354
Julian Hallf5728962021-06-24 09:40:23 +0100355 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100356}
357
358static rpc_status_t asymmetric_decrypt_handler(void *context, struct call_req* req)
359{
Julian Hallf5728962021-06-24 09:40:23 +0100360 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
361 struct call_param_buf *req_buf = call_req_get_req_buf(req);
362 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100363
Julian Hallf5728962021-06-24 09:40:23 +0100364 if (serializer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100365
Julian Hallf5728962021-06-24 09:40:23 +0100366 size_t max_param_size = serializer->max_deserialised_parameter_size(req_buf);
Julian Hallc02fffb2020-11-23 18:22:06 +0100367
Julian Hallf5728962021-06-24 09:40:23 +0100368 psa_key_id_t id;
369 psa_algorithm_t alg;
370 size_t ciphertext_len = max_param_size;
371 uint8_t *ciphertext_buffer = malloc(ciphertext_len);
372 size_t salt_len = max_param_size;
373 uint8_t *salt_buffer = malloc(salt_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100374
Julian Hallf5728962021-06-24 09:40:23 +0100375 if (ciphertext_buffer && salt_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100376
Julian Hallf5728962021-06-24 09:40:23 +0100377 rpc_status = serializer->deserialize_asymmetric_decrypt_req(req_buf,
378 &id, &alg,
379 ciphertext_buffer, &ciphertext_len,
380 salt_buffer, &salt_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100381
Julian Hallf5728962021-06-24 09:40:23 +0100382 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100383
Julian Hallf5728962021-06-24 09:40:23 +0100384 psa_status_t psa_status;
385 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Julian Hallc02fffb2020-11-23 18:22:06 +0100386
Julian Hallf5728962021-06-24 09:40:23 +0100387 psa_status = psa_get_key_attributes(id, &attributes);
Julian Hallc02fffb2020-11-23 18:22:06 +0100388
Julian Hallf5728962021-06-24 09:40:23 +0100389 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100390
Julian Hallf5728962021-06-24 09:40:23 +0100391 size_t max_decrypt_size = PSA_ASYMMETRIC_DECRYPT_OUTPUT_SIZE(
392 psa_get_key_type(&attributes),
393 psa_get_key_bits(&attributes),
394 alg);
Julian Hallc02fffb2020-11-23 18:22:06 +0100395
Julian Hallf5728962021-06-24 09:40:23 +0100396 size_t plaintext_len;
397 uint8_t *plaintext_buffer = malloc(max_decrypt_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100398
Julian Hallf5728962021-06-24 09:40:23 +0100399 if (plaintext_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100400
Julian Hallf5728962021-06-24 09:40:23 +0100401 /* Salt is an optional parameter */
402 uint8_t *salt = (salt_len) ? salt_buffer : NULL;
Julian Hallf688a0b2021-04-09 11:58:30 +0100403
Julian Hallf5728962021-06-24 09:40:23 +0100404 psa_status = psa_asymmetric_decrypt(id, alg,
405 ciphertext_buffer, ciphertext_len,
406 salt, salt_len,
407 plaintext_buffer, max_decrypt_size, &plaintext_len);
julhal01c3f4e9a2020-12-15 13:39:01 +0000408
Julian Hallf5728962021-06-24 09:40:23 +0100409 if (psa_status == PSA_SUCCESS) {
julhal01c3f4e9a2020-12-15 13:39:01 +0000410
Julian Hallf5728962021-06-24 09:40:23 +0100411 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
412 rpc_status = serializer->serialize_asymmetric_decrypt_resp(resp_buf,
413 plaintext_buffer, plaintext_len);
414 }
julhal01c3f4e9a2020-12-15 13:39:01 +0000415
Julian Hallf5728962021-06-24 09:40:23 +0100416 free(plaintext_buffer);
417 }
418 else {
419 /* Failed to allocate ouptput buffer */
420 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
421 }
422 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100423
Julian Hallf5728962021-06-24 09:40:23 +0100424 call_req_set_opstatus(req, psa_status);
425 psa_reset_key_attributes(&attributes);
426 }
427 }
428 else {
429 /* Failed to allocate buffers */
430 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
431 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100432
Julian Hallf5728962021-06-24 09:40:23 +0100433 free(ciphertext_buffer);
434 free(salt_buffer);
435 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100436
Julian Hallf5728962021-06-24 09:40:23 +0100437 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100438}
439
440static rpc_status_t asymmetric_encrypt_handler(void *context, struct call_req* req)
441{
Julian Hallf5728962021-06-24 09:40:23 +0100442 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
443 struct call_param_buf *req_buf = call_req_get_req_buf(req);
444 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100445
Julian Hallf5728962021-06-24 09:40:23 +0100446 if (serializer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100447
Julian Hallf5728962021-06-24 09:40:23 +0100448 size_t max_param_size = serializer->max_deserialised_parameter_size(req_buf);
Julian Hallc02fffb2020-11-23 18:22:06 +0100449
Julian Hallf5728962021-06-24 09:40:23 +0100450 psa_key_id_t id;
451 psa_algorithm_t alg;
452 size_t plaintext_len = max_param_size;
453 uint8_t *plaintext_buffer = malloc(plaintext_len);
454 size_t salt_len = max_param_size;
455 uint8_t *salt_buffer = malloc(salt_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100456
Julian Hallf5728962021-06-24 09:40:23 +0100457 if (plaintext_buffer && salt_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100458
Julian Hallf5728962021-06-24 09:40:23 +0100459 rpc_status = serializer->deserialize_asymmetric_encrypt_req(req_buf,
460 &id, &alg,
461 plaintext_buffer, &plaintext_len,
462 salt_buffer, &salt_len);
Julian Hallc02fffb2020-11-23 18:22:06 +0100463
Julian Hallf5728962021-06-24 09:40:23 +0100464 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100465
Julian Hallf5728962021-06-24 09:40:23 +0100466 psa_status_t psa_status;
467 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
Julian Hallc02fffb2020-11-23 18:22:06 +0100468
Julian Hallf5728962021-06-24 09:40:23 +0100469 psa_status = psa_get_key_attributes(id, &attributes);
Julian Hallc02fffb2020-11-23 18:22:06 +0100470
Julian Hallf5728962021-06-24 09:40:23 +0100471 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100472
Julian Hallf5728962021-06-24 09:40:23 +0100473 size_t max_encrypt_size = PSA_ASYMMETRIC_ENCRYPT_OUTPUT_SIZE(
474 psa_get_key_type(&attributes),
475 psa_get_key_bits(&attributes),
476 alg);
Julian Hallc02fffb2020-11-23 18:22:06 +0100477
Julian Hallf5728962021-06-24 09:40:23 +0100478 size_t ciphertext_len;
479 uint8_t *ciphertext_buffer = malloc(max_encrypt_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100480
Julian Hallf5728962021-06-24 09:40:23 +0100481 if (ciphertext_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100482
Julian Hallf5728962021-06-24 09:40:23 +0100483 /* Salt is an optional parameter */
484 uint8_t *salt = (salt_len) ? salt_buffer : NULL;
Julian Hallf688a0b2021-04-09 11:58:30 +0100485
Julian Hallf5728962021-06-24 09:40:23 +0100486 psa_status = psa_asymmetric_encrypt(id, alg,
487 plaintext_buffer, plaintext_len,
488 salt, salt_len,
489 ciphertext_buffer, max_encrypt_size, &ciphertext_len);
julhal01c3f4e9a2020-12-15 13:39:01 +0000490
Julian Hallf5728962021-06-24 09:40:23 +0100491 if (psa_status == PSA_SUCCESS) {
julhal01c3f4e9a2020-12-15 13:39:01 +0000492
Julian Hallf5728962021-06-24 09:40:23 +0100493 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
494 rpc_status = serializer->serialize_asymmetric_encrypt_resp(resp_buf,
495 ciphertext_buffer, ciphertext_len);
496 }
julhal01c3f4e9a2020-12-15 13:39:01 +0000497
Julian Hallf5728962021-06-24 09:40:23 +0100498 free(ciphertext_buffer);
499 }
500 else {
501 /* Failed to allocate ouptput buffer */
502 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
503 }
504 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100505
Julian Hallf5728962021-06-24 09:40:23 +0100506 call_req_set_opstatus(req, psa_status);
507 psa_reset_key_attributes(&attributes);
508 }
509 }
510 else {
511 /* Failed to allocate buffers */
512 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
513 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100514
Julian Hallf5728962021-06-24 09:40:23 +0100515 free(plaintext_buffer);
516 free(salt_buffer);
517 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100518
Julian Hallf5728962021-06-24 09:40:23 +0100519 return rpc_status;
Julian Hallc02fffb2020-11-23 18:22:06 +0100520}
521
522static rpc_status_t generate_random_handler(void *context, struct call_req* req)
523{
Julian Hallf5728962021-06-24 09:40:23 +0100524 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
525 struct call_param_buf *req_buf = call_req_get_req_buf(req);
526 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
Julian Hallc02fffb2020-11-23 18:22:06 +0100527
Julian Hallf5728962021-06-24 09:40:23 +0100528 size_t output_size;
Julian Hallc02fffb2020-11-23 18:22:06 +0100529
Julian Hallf5728962021-06-24 09:40:23 +0100530 if (serializer)
531 rpc_status = serializer->deserialize_generate_random_req(req_buf, &output_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100532
Julian Hallf5728962021-06-24 09:40:23 +0100533 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100534
Julian Hallf5728962021-06-24 09:40:23 +0100535 psa_status_t psa_status;
536 uint8_t *output_buffer = malloc(output_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100537
Julian Hallf5728962021-06-24 09:40:23 +0100538 if (output_buffer) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100539
Julian Hallf5728962021-06-24 09:40:23 +0100540 psa_status = psa_generate_random(output_buffer, output_size);
Julian Hallc02fffb2020-11-23 18:22:06 +0100541
Julian Hallf5728962021-06-24 09:40:23 +0100542 if (psa_status == PSA_SUCCESS) {
Julian Hallc02fffb2020-11-23 18:22:06 +0100543
Julian Hallf5728962021-06-24 09:40:23 +0100544 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
545 rpc_status = serializer->serialize_generate_random_resp(resp_buf,
546 output_buffer, output_size);
547 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100548
Julian Hallf5728962021-06-24 09:40:23 +0100549 call_req_set_opstatus(req, psa_status);
550 free(output_buffer);
551 }
552 else {
553 /* Failed to allocate output buffer */
554 rpc_status = TS_RPC_ERROR_RESOURCE_FAILURE;
555 }
556 }
Julian Hallc02fffb2020-11-23 18:22:06 +0100557
Julian Hallf5728962021-06-24 09:40:23 +0100558 return rpc_status;
559}
560
Julian Hall8359a632021-07-08 15:10:30 +0100561static rpc_status_t copy_key_handler(void *context, struct call_req* req)
562{
563 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
564 struct call_param_buf *req_buf = call_req_get_req_buf(req);
565 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
566
567 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
568 psa_key_id_t source_key_id;
569
570 if (serializer)
571 rpc_status = serializer->deserialize_copy_key_req(req_buf, &attributes, &source_key_id);
572
573 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
574
575 psa_key_id_t target_key_id;
576
577 psa_status_t psa_status = psa_copy_key(source_key_id, &attributes, &target_key_id);
578
579 if (psa_status == PSA_SUCCESS) {
580
581 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
582 rpc_status = serializer->serialize_copy_key_resp(resp_buf, target_key_id);
583 }
584
585 call_req_set_opstatus(req, psa_status);
586 }
587
588 psa_reset_key_attributes(&attributes);
589
590 return rpc_status;
591}
592
593static rpc_status_t purge_key_handler(void *context, struct call_req* req)
594{
595 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
596 struct call_param_buf *req_buf = call_req_get_req_buf(req);
597 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
598
599 psa_key_id_t id;
600
601 if (serializer)
602 rpc_status = serializer->deserialize_purge_key_req(req_buf, &id);
603
604 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
605
606 psa_status_t psa_status = psa_purge_key(id);
607 call_req_set_opstatus(req, psa_status);
608 }
609
610 return rpc_status;
611}
612
613static rpc_status_t get_key_attributes_handler(void *context, struct call_req* req)
614{
615 rpc_status_t rpc_status = TS_RPC_ERROR_SERIALIZATION_NOT_SUPPORTED;
616 struct call_param_buf *req_buf = call_req_get_req_buf(req);
617 const struct crypto_provider_serializer *serializer = get_crypto_serializer(context, req);
618
619 psa_key_id_t id;
620
621 if (serializer)
622 rpc_status = serializer->deserialize_get_key_attributes_req(req_buf, &id);
623
624 if (rpc_status == TS_RPC_CALL_ACCEPTED) {
625
626 psa_key_attributes_t attributes = PSA_KEY_ATTRIBUTES_INIT;
627
628 psa_status_t psa_status = psa_get_key_attributes(id, &attributes);
629
630 if (psa_status == PSA_SUCCESS) {
631
632 struct call_param_buf *resp_buf = call_req_get_resp_buf(req);
633 rpc_status = serializer->serialize_get_key_attributes_resp(resp_buf, &attributes);
634 }
635
636 psa_reset_key_attributes(&attributes);
637 call_req_set_opstatus(req, psa_status);
638 }
639
640 return rpc_status;
641}