1 /* 2 * PSA persistent key storage 3 */ 4 /* 5 * Copyright The Mbed TLS Contributors 6 * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later 7 */ 8 9 #include "common.h" 10 11 #if defined(MBEDTLS_PSA_CRYPTO_STORAGE_C) 12 13 #include <stdlib.h> 14 #include <string.h> 15 16 #include "psa/crypto.h" 17 #include "psa_crypto_storage.h" 18 #include "mbedtls/platform_util.h" 19 20 #if defined(MBEDTLS_PSA_ITS_FILE_C) 21 #include "psa_crypto_its.h" 22 #else /* Native ITS implementation */ 23 #include "psa/error.h" 24 #include "psa/internal_trusted_storage.h" 25 #endif 26 27 #include "mbedtls/platform.h" 28 29 30 31 /****************************************************************/ 32 /* Key storage */ 33 /****************************************************************/ 34 35 /* Determine a file name (ITS file identifier) for the given key identifier. 36 * The file name must be distinct from any file that is used for a purpose 37 * other than storing a key. Currently, the only such file is the random seed 38 * file whose name is PSA_CRYPTO_ITS_RANDOM_SEED_UID and whose value is 39 * 0xFFFFFF52. */ 40 static psa_storage_uid_t psa_its_identifier_of_slot(mbedtls_svc_key_id_t key) 41 { 42 #if defined(MBEDTLS_PSA_CRYPTO_KEY_ID_ENCODES_OWNER) 43 /* Encode the owner in the upper 32 bits. This means that if 44 * owner values are nonzero (as they are on a PSA platform), 45 * no key file will ever have a value less than 0x100000000, so 46 * the whole range 0..0xffffffff is available for non-key files. */ 47 uint32_t unsigned_owner_id = MBEDTLS_SVC_KEY_ID_GET_OWNER_ID(key); 48 return ((uint64_t) unsigned_owner_id << 32) | 49 MBEDTLS_SVC_KEY_ID_GET_KEY_ID(key); 50 #else 51 /* Use the key id directly as a file name. 52 * psa_is_key_id_valid() in psa_crypto_slot_management.c 53 * is responsible for ensuring that key identifiers do not have a 54 * value that is reserved for non-key files. */ 55 return key; 56 #endif 57 } 58 59 /** 60 * \brief Load persistent data for the given key slot number. 61 * 62 * This function reads data from a storage backend and returns the data in a 63 * buffer. 64 * 65 * \param key Persistent identifier of the key to be loaded. This 66 * should be an occupied storage location. 67 * \param[out] data Buffer where the data is to be written. 68 * \param data_size Size of the \c data buffer in bytes. 69 * 70 * \retval #PSA_SUCCESS \emptydescription 71 * \retval #PSA_ERROR_DATA_INVALID \emptydescription 72 * \retval #PSA_ERROR_DATA_CORRUPT \emptydescription 73 * \retval #PSA_ERROR_STORAGE_FAILURE \emptydescription 74 * \retval #PSA_ERROR_DOES_NOT_EXIST \emptydescription 75 */ 76 static psa_status_t psa_crypto_storage_load( 77 const mbedtls_svc_key_id_t key, uint8_t *data, size_t data_size) 78 { 79 psa_status_t status; 80 psa_storage_uid_t data_identifier = psa_its_identifier_of_slot(key); 81 struct psa_storage_info_t data_identifier_info; 82 size_t data_length = 0; 83 84 status = psa_its_get_info(data_identifier, &data_identifier_info); 85 if (status != PSA_SUCCESS) { 86 return status; 87 } 88 89 status = psa_its_get(data_identifier, 0, (uint32_t) data_size, data, &data_length); 90 if (data_size != data_length) { 91 return PSA_ERROR_DATA_INVALID; 92 } 93 94 return status; 95 } 96 97 int psa_is_key_present_in_storage(const mbedtls_svc_key_id_t key) 98 { 99 psa_status_t ret; 100 psa_storage_uid_t data_identifier = psa_its_identifier_of_slot(key); 101 struct psa_storage_info_t data_identifier_info; 102 103 ret = psa_its_get_info(data_identifier, &data_identifier_info); 104 105 if (ret == PSA_ERROR_DOES_NOT_EXIST) { 106 return 0; 107 } 108 return 1; 109 } 110 111 /** 112 * \brief Store persistent data for the given key slot number. 113 * 114 * This function stores the given data buffer to a persistent storage. 115 * 116 * \param key Persistent identifier of the key to be stored. This 117 * should be an unoccupied storage location. 118 * \param[in] data Buffer containing the data to be stored. 119 * \param data_length The number of bytes 120 * that make up the data. 121 * 122 * \retval #PSA_SUCCESS \emptydescription 123 * \retval #PSA_ERROR_INSUFFICIENT_STORAGE \emptydescription 124 * \retval #PSA_ERROR_ALREADY_EXISTS \emptydescription 125 * \retval #PSA_ERROR_STORAGE_FAILURE \emptydescription 126 * \retval #PSA_ERROR_DATA_INVALID \emptydescription 127 */ 128 static psa_status_t psa_crypto_storage_store(const mbedtls_svc_key_id_t key, 129 const uint8_t *data, 130 size_t data_length) 131 { 132 psa_status_t status; 133 psa_storage_uid_t data_identifier = psa_its_identifier_of_slot(key); 134 struct psa_storage_info_t data_identifier_info; 135 136 if (psa_is_key_present_in_storage(key) == 1) { 137 return PSA_ERROR_ALREADY_EXISTS; 138 } 139 140 status = psa_its_set(data_identifier, (uint32_t) data_length, data, 0); 141 if (status != PSA_SUCCESS) { 142 return PSA_ERROR_DATA_INVALID; 143 } 144 145 status = psa_its_get_info(data_identifier, &data_identifier_info); 146 if (status != PSA_SUCCESS) { 147 goto exit; 148 } 149 150 if (data_identifier_info.size != data_length) { 151 status = PSA_ERROR_DATA_INVALID; 152 goto exit; 153 } 154 155 exit: 156 if (status != PSA_SUCCESS) { 157 /* Remove the file in case we managed to create it but something 158 * went wrong. It's ok if the file doesn't exist. If the file exists 159 * but the removal fails, we're already reporting an error so there's 160 * nothing else we can do. */ 161 (void) psa_its_remove(data_identifier); 162 } 163 return status; 164 } 165 166 psa_status_t psa_destroy_persistent_key(const mbedtls_svc_key_id_t key) 167 { 168 psa_status_t ret; 169 psa_storage_uid_t data_identifier = psa_its_identifier_of_slot(key); 170 struct psa_storage_info_t data_identifier_info; 171 172 ret = psa_its_get_info(data_identifier, &data_identifier_info); 173 if (ret == PSA_ERROR_DOES_NOT_EXIST) { 174 return PSA_SUCCESS; 175 } 176 177 if (psa_its_remove(data_identifier) != PSA_SUCCESS) { 178 return PSA_ERROR_DATA_INVALID; 179 } 180 181 ret = psa_its_get_info(data_identifier, &data_identifier_info); 182 if (ret != PSA_ERROR_DOES_NOT_EXIST) { 183 return PSA_ERROR_DATA_INVALID; 184 } 185 186 return PSA_SUCCESS; 187 } 188 189 /** 190 * \brief Get data length for given key slot number. 191 * 192 * \param key Persistent identifier whose stored data length 193 * is to be obtained. 194 * \param[out] data_length The number of bytes that make up the data. 195 * 196 * \retval #PSA_SUCCESS \emptydescription 197 * \retval #PSA_ERROR_STORAGE_FAILURE \emptydescription 198 * \retval #PSA_ERROR_DOES_NOT_EXIST \emptydescription 199 * \retval #PSA_ERROR_DATA_CORRUPT \emptydescription 200 */ 201 static psa_status_t psa_crypto_storage_get_data_length( 202 const mbedtls_svc_key_id_t key, 203 size_t *data_length) 204 { 205 psa_status_t status; 206 psa_storage_uid_t data_identifier = psa_its_identifier_of_slot(key); 207 struct psa_storage_info_t data_identifier_info; 208 209 status = psa_its_get_info(data_identifier, &data_identifier_info); 210 if (status != PSA_SUCCESS) { 211 return status; 212 } 213 214 *data_length = (size_t) data_identifier_info.size; 215 216 return PSA_SUCCESS; 217 } 218 219 /** 220 * Persistent key storage magic header. 221 */ 222 #define PSA_KEY_STORAGE_MAGIC_HEADER "PSA\0KEY" 223 #define PSA_KEY_STORAGE_MAGIC_HEADER_LENGTH (sizeof(PSA_KEY_STORAGE_MAGIC_HEADER)) 224 225 typedef struct { 226 uint8_t magic[PSA_KEY_STORAGE_MAGIC_HEADER_LENGTH]; 227 uint8_t version[4]; 228 uint8_t lifetime[sizeof(psa_key_lifetime_t)]; 229 uint8_t type[2]; 230 uint8_t bits[2]; 231 uint8_t policy[sizeof(psa_key_policy_t)]; 232 uint8_t data_len[4]; 233 uint8_t key_data[]; 234 } psa_persistent_key_storage_format; 235 236 void psa_format_key_data_for_storage(const uint8_t *data, 237 const size_t data_length, 238 const psa_key_attributes_t *attr, 239 uint8_t *storage_data) 240 { 241 psa_persistent_key_storage_format *storage_format = 242 (psa_persistent_key_storage_format *) storage_data; 243 244 memcpy(storage_format->magic, PSA_KEY_STORAGE_MAGIC_HEADER, 245 PSA_KEY_STORAGE_MAGIC_HEADER_LENGTH); 246 MBEDTLS_PUT_UINT32_LE(0, storage_format->version, 0); 247 MBEDTLS_PUT_UINT32_LE(attr->lifetime, storage_format->lifetime, 0); 248 MBEDTLS_PUT_UINT16_LE((uint16_t) attr->type, storage_format->type, 0); 249 MBEDTLS_PUT_UINT16_LE((uint16_t) attr->bits, storage_format->bits, 0); 250 MBEDTLS_PUT_UINT32_LE(attr->policy.usage, storage_format->policy, 0); 251 MBEDTLS_PUT_UINT32_LE(attr->policy.alg, storage_format->policy, sizeof(uint32_t)); 252 MBEDTLS_PUT_UINT32_LE(attr->policy.alg2, storage_format->policy, 2 * sizeof(uint32_t)); 253 MBEDTLS_PUT_UINT32_LE(data_length, storage_format->data_len, 0); 254 memcpy(storage_format->key_data, data, data_length); 255 } 256 257 static psa_status_t check_magic_header(const uint8_t *data) 258 { 259 if (memcmp(data, PSA_KEY_STORAGE_MAGIC_HEADER, 260 PSA_KEY_STORAGE_MAGIC_HEADER_LENGTH) != 0) { 261 return PSA_ERROR_DATA_INVALID; 262 } 263 return PSA_SUCCESS; 264 } 265 266 psa_status_t psa_parse_key_data_from_storage(const uint8_t *storage_data, 267 size_t storage_data_length, 268 uint8_t **key_data, 269 size_t *key_data_length, 270 psa_key_attributes_t *attr) 271 { 272 psa_status_t status; 273 const psa_persistent_key_storage_format *storage_format = 274 (const psa_persistent_key_storage_format *) storage_data; 275 uint32_t version; 276 277 if (storage_data_length < sizeof(*storage_format)) { 278 return PSA_ERROR_DATA_INVALID; 279 } 280 281 status = check_magic_header(storage_data); 282 if (status != PSA_SUCCESS) { 283 return status; 284 } 285 286 version = MBEDTLS_GET_UINT32_LE(storage_format->version, 0); 287 if (version != 0) { 288 return PSA_ERROR_DATA_INVALID; 289 } 290 291 *key_data_length = MBEDTLS_GET_UINT32_LE(storage_format->data_len, 0); 292 if (*key_data_length > (storage_data_length - sizeof(*storage_format)) || 293 *key_data_length > PSA_CRYPTO_MAX_STORAGE_SIZE) { 294 return PSA_ERROR_DATA_INVALID; 295 } 296 297 if (*key_data_length == 0) { 298 *key_data = NULL; 299 } else { 300 *key_data = mbedtls_calloc(1, *key_data_length); 301 if (*key_data == NULL) { 302 return PSA_ERROR_INSUFFICIENT_MEMORY; 303 } 304 memcpy(*key_data, storage_format->key_data, *key_data_length); 305 } 306 307 attr->lifetime = MBEDTLS_GET_UINT32_LE(storage_format->lifetime, 0); 308 attr->type = MBEDTLS_GET_UINT16_LE(storage_format->type, 0); 309 attr->bits = MBEDTLS_GET_UINT16_LE(storage_format->bits, 0); 310 attr->policy.usage = MBEDTLS_GET_UINT32_LE(storage_format->policy, 0); 311 attr->policy.alg = MBEDTLS_GET_UINT32_LE(storage_format->policy, sizeof(uint32_t)); 312 attr->policy.alg2 = MBEDTLS_GET_UINT32_LE(storage_format->policy, 2 * sizeof(uint32_t)); 313 314 return PSA_SUCCESS; 315 } 316 317 psa_status_t psa_save_persistent_key(const psa_key_attributes_t *attr, 318 const uint8_t *data, 319 const size_t data_length) 320 { 321 size_t storage_data_length; 322 uint8_t *storage_data; 323 psa_status_t status; 324 325 /* All keys saved to persistent storage always have a key context */ 326 if (data == NULL || data_length == 0) { 327 return PSA_ERROR_INVALID_ARGUMENT; 328 } 329 330 if (data_length > PSA_CRYPTO_MAX_STORAGE_SIZE) { 331 return PSA_ERROR_INSUFFICIENT_STORAGE; 332 } 333 storage_data_length = data_length + sizeof(psa_persistent_key_storage_format); 334 335 storage_data = mbedtls_calloc(1, storage_data_length); 336 if (storage_data == NULL) { 337 return PSA_ERROR_INSUFFICIENT_MEMORY; 338 } 339 340 psa_format_key_data_for_storage(data, data_length, attr, storage_data); 341 342 status = psa_crypto_storage_store(attr->id, 343 storage_data, storage_data_length); 344 345 mbedtls_zeroize_and_free(storage_data, storage_data_length); 346 347 return status; 348 } 349 350 void psa_free_persistent_key_data(uint8_t *key_data, size_t key_data_length) 351 { 352 mbedtls_zeroize_and_free(key_data, key_data_length); 353 } 354 355 psa_status_t psa_load_persistent_key(psa_key_attributes_t *attr, 356 uint8_t **data, 357 size_t *data_length) 358 { 359 psa_status_t status = PSA_SUCCESS; 360 uint8_t *loaded_data; 361 size_t storage_data_length = 0; 362 mbedtls_svc_key_id_t key = attr->id; 363 364 status = psa_crypto_storage_get_data_length(key, &storage_data_length); 365 if (status != PSA_SUCCESS) { 366 return status; 367 } 368 369 loaded_data = mbedtls_calloc(1, storage_data_length); 370 371 if (loaded_data == NULL) { 372 return PSA_ERROR_INSUFFICIENT_MEMORY; 373 } 374 375 status = psa_crypto_storage_load(key, loaded_data, storage_data_length); 376 if (status != PSA_SUCCESS) { 377 goto exit; 378 } 379 380 status = psa_parse_key_data_from_storage(loaded_data, storage_data_length, 381 data, data_length, attr); 382 383 /* All keys saved to persistent storage always have a key context */ 384 if (status == PSA_SUCCESS && 385 (*data == NULL || *data_length == 0)) { 386 status = PSA_ERROR_STORAGE_FAILURE; 387 } 388 389 exit: 390 mbedtls_zeroize_and_free(loaded_data, storage_data_length); 391 return status; 392 } 393 394 395 396 /****************************************************************/ 397 /* Transactions */ 398 /****************************************************************/ 399 400 #if defined(PSA_CRYPTO_STORAGE_HAS_TRANSACTIONS) 401 402 psa_crypto_transaction_t psa_crypto_transaction; 403 404 psa_status_t psa_crypto_save_transaction(void) 405 { 406 struct psa_storage_info_t p_info; 407 psa_status_t status; 408 status = psa_its_get_info(PSA_CRYPTO_ITS_TRANSACTION_UID, &p_info); 409 if (status == PSA_SUCCESS) { 410 /* This shouldn't happen: we're trying to start a transaction while 411 * there is still a transaction that hasn't been replayed. */ 412 return PSA_ERROR_CORRUPTION_DETECTED; 413 } else if (status != PSA_ERROR_DOES_NOT_EXIST) { 414 return status; 415 } 416 return psa_its_set(PSA_CRYPTO_ITS_TRANSACTION_UID, 417 sizeof(psa_crypto_transaction), 418 &psa_crypto_transaction, 419 0); 420 } 421 422 psa_status_t psa_crypto_load_transaction(void) 423 { 424 psa_status_t status; 425 size_t length; 426 status = psa_its_get(PSA_CRYPTO_ITS_TRANSACTION_UID, 0, 427 sizeof(psa_crypto_transaction), 428 &psa_crypto_transaction, &length); 429 if (status != PSA_SUCCESS) { 430 return status; 431 } 432 if (length != sizeof(psa_crypto_transaction)) { 433 return PSA_ERROR_DATA_INVALID; 434 } 435 return PSA_SUCCESS; 436 } 437 438 psa_status_t psa_crypto_stop_transaction(void) 439 { 440 psa_status_t status = psa_its_remove(PSA_CRYPTO_ITS_TRANSACTION_UID); 441 /* Whether or not updating the storage succeeded, the transaction is 442 * finished now. It's too late to go back, so zero out the in-memory 443 * data. */ 444 memset(&psa_crypto_transaction, 0, sizeof(psa_crypto_transaction)); 445 return status; 446 } 447 448 #endif /* PSA_CRYPTO_STORAGE_HAS_TRANSACTIONS */ 449 450 451 452 /****************************************************************/ 453 /* Random generator state */ 454 /****************************************************************/ 455 456 #if defined(MBEDTLS_PSA_INJECT_ENTROPY) 457 psa_status_t mbedtls_psa_storage_inject_entropy(const unsigned char *seed, 458 size_t seed_size) 459 { 460 psa_status_t status; 461 struct psa_storage_info_t p_info; 462 463 status = psa_its_get_info(PSA_CRYPTO_ITS_RANDOM_SEED_UID, &p_info); 464 465 if (PSA_ERROR_DOES_NOT_EXIST == status) { /* No seed exists */ 466 status = psa_its_set(PSA_CRYPTO_ITS_RANDOM_SEED_UID, seed_size, seed, 0); 467 } else if (PSA_SUCCESS == status) { 468 /* You should not be here. Seed needs to be injected only once */ 469 status = PSA_ERROR_NOT_PERMITTED; 470 } 471 return status; 472 } 473 #endif /* MBEDTLS_PSA_INJECT_ENTROPY */ 474 475 476 477 /****************************************************************/ 478 /* The end */ 479 /****************************************************************/ 480 481 #endif /* MBEDTLS_PSA_CRYPTO_STORAGE_C */ 482