diff --git a/TESTS/psa/its_ps/main.cpp b/TESTS/psa/its_ps/main.cpp index 7aab27ad64..843adba061 100644 --- a/TESTS/psa/its_ps/main.cpp +++ b/TESTS/psa/its_ps/main.cpp @@ -28,10 +28,15 @@ #include "psa/internal_trusted_storage.h" #include "psa/protected_storage.h" #include "psa/lifecycle.h" +#include "KVMap.h" +#include "KVStore.h" +#include "kv_config.h" +#include "psa_storage_common_impl.h" using namespace utest::v1; #define TEST_BUFF_SIZE 16 +#define STR_EXPAND(tok) #tok typedef enum { its, @@ -40,7 +45,7 @@ typedef enum { extern "C" psa_status_t psa_ps_reset(); -static psa_status_t set_func(storage_type_t stype, psa_storage_uid_t uid, uint32_t data_length, +static psa_status_t set_func(storage_type_t stype, psa_storage_uid_t uid, size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) { return (stype == its) ? @@ -48,12 +53,12 @@ static psa_status_t set_func(storage_type_t stype, psa_storage_uid_t uid, uint32 psa_ps_set(uid, data_length, p_data, create_flags); } -static psa_status_t get_func(storage_type_t stype, psa_storage_uid_t uid, uint32_t data_offset, - uint32_t data_length, void *p_data) +static psa_status_t get_func(storage_type_t stype, psa_storage_uid_t uid, size_t data_offset, + size_t data_length, void *p_data, size_t *actual_length) { return (stype == its) ? - psa_its_get(uid, data_offset, data_length, p_data) : - psa_ps_get(uid, data_offset, data_length, p_data); + psa_its_get(uid, data_offset, data_length, p_data, actual_length) : + psa_ps_get(uid, data_offset, data_length, p_data, actual_length); } static psa_status_t get_info_func(storage_type_t stype, psa_storage_uid_t uid, @@ -78,6 +83,8 @@ void pits_ps_test() psa_status_t status = PSA_SUCCESS; uint8_t write_buff[TEST_BUFF_SIZE] = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F}; uint8_t read_buff[TEST_BUFF_SIZE] = {0}; + size_t actual_size; + psa_storage_create_flags_t flags; struct psa_storage_info_t info = {0, PSA_STORAGE_FLAG_WRITE_ONCE}; memset(read_buff, 0, TEST_BUFF_SIZE); @@ -92,15 +99,15 @@ void pits_ps_test() TEST_ASSERT_EQUAL(TEST_BUFF_SIZE, info.size); TEST_ASSERT_EQUAL(0, info.flags); - status = get_func(stype, 5, 0, TEST_BUFF_SIZE, read_buff); + status = get_func(stype, 5, 0, TEST_BUFF_SIZE, read_buff, &actual_size); TEST_ASSERT_EQUAL(PSA_SUCCESS, status); TEST_ASSERT_EQUAL_MEMORY(write_buff, read_buff, TEST_BUFF_SIZE); memset(read_buff, 0, TEST_BUFF_SIZE); - status = get_func(stype, 5, 1, TEST_BUFF_SIZE, read_buff); + status = get_func(stype, 5, 1, TEST_BUFF_SIZE, read_buff, &actual_size); TEST_ASSERT_NOT_EQUAL(PSA_SUCCESS, status); - status = get_func(stype, 5, 1, TEST_BUFF_SIZE - 1, read_buff); + status = get_func(stype, 5, 1, TEST_BUFF_SIZE - 1, read_buff, &actual_size); TEST_ASSERT_EQUAL(PSA_SUCCESS, status); TEST_ASSERT_EQUAL_MEMORY(write_buff + 1, read_buff, TEST_BUFF_SIZE - 1); @@ -109,6 +116,38 @@ void pits_ps_test() status = get_info_func(stype, 5, &info); TEST_ASSERT_EQUAL(PSA_ERROR_DOES_NOT_EXIST, status); + + if (stype == its) { + return; + } + + mbed::KVMap &kv_map = mbed::KVMap::get_instance(); + mbed::KVStore *kvstore = kv_map.get_main_kv_instance(STR_EXPAND(MBED_CONF_STORAGE_DEFAULT_KV)); + uint32_t kv_get_flags; + + flags = PSA_STORAGE_FLAG_NO_REPLAY_PROTECTION; + status = set_func(stype, 6, TEST_BUFF_SIZE, write_buff, flags); + TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + + status = get_info_func(stype, 6, &info); + TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + TEST_ASSERT_EQUAL(flags, info.flags); + + status = psa_storage_get_info_impl(kvstore, 1, 6, &info, &kv_get_flags); + TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + TEST_ASSERT_EQUAL(kv_get_flags, mbed::KVStore::REQUIRE_CONFIDENTIALITY_FLAG); + + flags = PSA_STORAGE_FLAG_NO_REPLAY_PROTECTION | PSA_STORAGE_FLAG_NO_CONFIDENTIALITY | PSA_STORAGE_FLAG_WRITE_ONCE; + status = set_func(stype, 6, TEST_BUFF_SIZE, write_buff, flags); + TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + + status = get_info_func(stype, 6, &info); + TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + TEST_ASSERT_EQUAL(flags, info.flags); + + status = psa_storage_get_info_impl(kvstore, 1, 6, &info, &kv_get_flags); + TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + TEST_ASSERT_EQUAL(kv_get_flags, mbed::KVStore::WRITE_ONCE_FLAG); } template @@ -117,6 +156,7 @@ void pits_ps_write_once_test() psa_status_t status = PSA_SUCCESS; uint8_t write_buff[TEST_BUFF_SIZE] = {0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00}; uint8_t read_buff[TEST_BUFF_SIZE] = {0}; + size_t actual_size; struct psa_storage_info_t info = {0, 0}; status = get_info_func(stype, 5, &info); @@ -132,8 +172,9 @@ void pits_ps_write_once_test() TEST_ASSERT_EQUAL(TEST_BUFF_SIZE, info.size); TEST_ASSERT_EQUAL(PSA_STORAGE_FLAG_WRITE_ONCE, info.flags); - status = get_func(stype, 5, 0, TEST_BUFF_SIZE, read_buff); + status = get_func(stype, 5, 0, TEST_BUFF_SIZE, read_buff, &actual_size); TEST_ASSERT_EQUAL(PSA_SUCCESS, status); + TEST_ASSERT_EQUAL(TEST_BUFF_SIZE, actual_size); TEST_ASSERT_EQUAL_MEMORY(write_buff, read_buff, TEST_BUFF_SIZE); status = set_func(stype, 5, TEST_BUFF_SIZE, write_buff, PSA_STORAGE_FLAG_WRITE_ONCE); diff --git a/components/TARGET_PSA/inc/psa/protected_storage.h b/components/TARGET_PSA/inc/psa/protected_storage.h index eb010adb17..6b299a3352 100644 --- a/components/TARGET_PSA/inc/psa/protected_storage.h +++ b/components/TARGET_PSA/inc/psa/protected_storage.h @@ -54,7 +54,7 @@ extern "C" { * \retval PSA_ERROR_GENERIC_ERROR The operation failed because of an unspecified internal failure */ psa_status_t psa_ps_set(psa_storage_uid_t uid, - uint32_t data_length, + size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags); @@ -65,22 +65,24 @@ psa_status_t psa_ps_set(psa_storage_uid_t uid, * \param[in] data_offset The offset within the data associated with the `uid` to start retrieving data * \param[in] data_length The amount of data to read (and the minimum allocated size of the `p_data` buffer) * \param[out] p_data The buffer where the data will be placed upon successful completion + * \param[out] p_data_length The actual amount of data returned * * \return A status indicating the success/failure of the operation * * \retval PSA_SUCCESS The operation completed successfully * \retval PSA_ERROR_INVALID_ARGUMENT The operation failed because one or more of the given arguments were invalid (null pointer, wrong flags etc.) * \retval PSA_ERROR_DOES_NOT_EXIST The operation failed because the provided uid value was not found in the storage - * \retval PSA_ERROR_BUFFER_TOO_SMALL The operation failed because the data associated with provided uid is not the same size as `data_size` + * \retval PSA_ERROR_BUFFER_TOO_SMALL The operation failed because the data associated with provided uid does not fit `data_size` * \retval PSA_ERROR_STORAGE_FAILURE The operation failed because the physical storage has failed (Fatal error) * \retval PSA_ERROR_GENERIC_ERROR The operation failed because of an unspecified internal failure * \retval PSA_ERROR_DATA_CORRUPT The operation failed because of an authentication failure when attempting to get the key * \retval PSA_ERROR_INVALID_SIGNATURE The operation failed because the data associated with the UID failed authentication */ psa_status_t psa_ps_get(psa_storage_uid_t uid, - uint32_t data_offset, - uint32_t data_length, - void *p_data); + size_t data_offset, + size_t data_length, + void *p_data, + size_t *p_data_length); /** * \brief Retrieve the metadata about the provided uid @@ -149,7 +151,7 @@ psa_status_t psa_ps_remove(psa_storage_uid_t uid); * \retval PSA_ERROR_GENERIC_ERROR The operation has failed due to an unspecified error */ psa_status_t psa_ps_create(psa_storage_uid_t uid, - uint32_t size, + size_t size, psa_storage_create_flags_t create_flags); /** @@ -179,8 +181,8 @@ psa_status_t psa_ps_create(psa_storage_uid_t uid, * \retval PSA_ERROR_INVALID_SIGNATURE The operation failed because the existing data failed authentication (MAC check failed) */ psa_status_t psa_ps_set_extended(psa_storage_uid_t uid, - uint32_t data_offset, - uint32_t data_length, + size_t data_offset, + size_t data_length, const void *p_data); /** diff --git a/components/TARGET_PSA/inc/psa/storage_common.h b/components/TARGET_PSA/inc/psa/storage_common.h index 4008d48524..1747f14b33 100644 --- a/components/TARGET_PSA/inc/psa/storage_common.h +++ b/components/TARGET_PSA/inc/psa/storage_common.h @@ -33,8 +33,10 @@ extern "C" { */ typedef uint32_t psa_storage_create_flags_t; -#define PSA_STORAGE_FLAG_NONE 0 /**< No flags to pass */ -#define PSA_STORAGE_FLAG_WRITE_ONCE (1 << 0) /**< The data associated with the uid will not be able to be modified or deleted. Intended to be used to set bits in `psa_storage_create_flags_t`*/ +#define PSA_STORAGE_FLAG_NONE 0 /**< No flags to pass */ +#define PSA_STORAGE_FLAG_WRITE_ONCE (1 << 0) /**< The data associated with the uid will not be able to be modified or deleted. Intended to be used to set bits in `psa_storage_create_flags_t`*/ +#define PSA_STORAGE_FLAG_NO_CONFIDENTIALITY (1 << 1) /**< The data associated with the uid is public and therefore does not require confidentiality. It therefore only needs to be integrity protected */ +#define PSA_STORAGE_FLAG_NO_REPLAY_PROTECTION (1 << 2) /**< The data associated with the uid does not require replay protection. This may permit faster storage - but it permits an attecker with physical access to revert to an earlier version of the data. */ /** \brief A type for UIDs used for identifying data */ @@ -44,7 +46,8 @@ typedef uint64_t psa_storage_uid_t; * \brief A container for metadata associated with a specific uid */ struct psa_storage_info_t { - uint32_t size; /**< The size of the data associated with a uid **/ + size_t capacity; /**< The allocated capacity of the storage associated with a UID **/ + size_t size; /**< The size of the data associated with a uid **/ psa_storage_create_flags_t flags; /**< The flags set when the uid was created **/ }; diff --git a/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.cpp b/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.cpp index d8ff8647f9..1f68596443 100644 --- a/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.cpp +++ b/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.cpp @@ -184,7 +184,7 @@ static void generate_fn(char *tdb_filename, uint32_t tdb_filename_size, psa_stor } psa_status_t psa_storage_set_impl(KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, - uint32_t data_length, const void *p_data, + size_t data_length, const void *p_data, uint32_t kv_create_flags) { if (uid == 0) { @@ -200,7 +200,7 @@ psa_status_t psa_storage_set_impl(KVStore *kvstore, int32_t pid, psa_storage_uid } psa_status_t psa_storage_get_impl(KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, - uint32_t data_offset, uint32_t data_length, void *p_data) + size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length) { if (uid == 0) { return PSA_ERROR_INVALID_ARGUMENT; @@ -227,18 +227,14 @@ psa_status_t psa_storage_get_impl(KVStore *kvstore, int32_t pid, psa_storage_uid return PSA_ERROR_BUFFER_TOO_SMALL; } - size_t actual_size = 0; - status = kvstore->get(kv_key, p_data, data_length, &actual_size, data_offset); - if ((status == MBED_SUCCESS) && (actual_size < data_length)) { - return PSA_ERROR_BUFFER_TOO_SMALL; - } + status = kvstore->get(kv_key, p_data, data_length, p_data_length, data_offset); } return convert_status(status); } psa_status_t psa_storage_get_info_impl(KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, - struct psa_storage_info_t *p_info) + struct psa_storage_info_t *p_info, uint32_t *kv_get_flags) { if (uid == 0) { @@ -257,7 +253,9 @@ psa_status_t psa_storage_get_info_impl(KVStore *kvstore, int32_t pid, psa_storag if (kv_info.flags & KVStore::WRITE_ONCE_FLAG) { p_info->flags |= PSA_STORAGE_FLAG_WRITE_ONCE; } - p_info->size = (uint32_t)(kv_info.size); // kv_info.size is of type size_t + *kv_get_flags = kv_info.flags; + p_info->size = kv_info.size; + p_info->capacity = kv_info.size; } return convert_status(status); diff --git a/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.h b/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.h index 50c86963da..86f361764d 100644 --- a/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.h +++ b/components/TARGET_PSA/services/storage/common/psa_storage_common_impl.h @@ -36,9 +36,9 @@ typedef psa_status_t (*migrate_func_t)(mbed::KVStore *kvstore, const psa_storage void psa_storage_handle_version(mbed::KVStore *kvstore, const char *version_key, const psa_storage_version_t *version, migrate_func_t migrate_func); -psa_status_t psa_storage_set_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, uint32_t data_length, const void *p_data, uint32_t kv_create_flags); -psa_status_t psa_storage_get_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, void *p_data); -psa_status_t psa_storage_get_info_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, struct psa_storage_info_t *p_info); +psa_status_t psa_storage_set_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, size_t data_length, const void *p_data, uint32_t kv_create_flags); +psa_status_t psa_storage_get_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length); +psa_status_t psa_storage_get_info_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid, struct psa_storage_info_t *p_info, uint32_t *kv_get_flags); psa_status_t psa_storage_remove_impl(mbed::KVStore *kvstore, int32_t pid, psa_storage_uid_t uid); psa_status_t psa_storage_reset_impl(mbed::KVStore *kvstore); diff --git a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_EMUL/psa_prot_internal_storage.cpp b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_EMUL/psa_prot_internal_storage.cpp index 902dc0df28..bce3709868 100644 --- a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_EMUL/psa_prot_internal_storage.cpp +++ b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_EMUL/psa_prot_internal_storage.cpp @@ -28,7 +28,7 @@ // So here we set a global pid value to be used for when calling IMPL functions #define PSA_ITS_EMUL_PID 1 -psa_status_t psa_its_set(psa_storage_uid_t uid, uint32_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) +psa_status_t psa_its_set(psa_storage_uid_t uid, size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) { if (!p_data && data_length) { return PSA_ERROR_INVALID_ARGUMENT; @@ -47,9 +47,9 @@ psa_status_t psa_its_set(psa_storage_uid_t uid, uint32_t data_length, const void return res; } -psa_status_t psa_its_get(psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, void *p_data) +psa_status_t psa_its_get(psa_storage_uid_t uid, size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length) { - if (!p_data && data_length) { + if ((!p_data && data_length) || !p_data_length) { return PSA_ERROR_INVALID_ARGUMENT; } @@ -61,7 +61,7 @@ psa_status_t psa_its_get(psa_storage_uid_t uid, uint32_t data_offset, uint32_t d return PSA_ERROR_STORAGE_FAILURE; } - return psa_its_get_impl(PSA_ITS_EMUL_PID, uid, data_offset, data_length, p_data); + return psa_its_get_impl(PSA_ITS_EMUL_PID, uid, data_offset, data_length, p_data, p_data_length); } psa_status_t psa_its_get_info(psa_storage_uid_t uid, struct psa_storage_info_t *p_info) diff --git a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.cpp b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.cpp index 106e9bd7e4..6f0835da8f 100644 --- a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.cpp +++ b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.cpp @@ -43,7 +43,7 @@ extern "C" #define ITS_VERSION_KEY "PSA_ITS_VERSION" // ITS version entry identifier in TDBStore static KVStore *kvstore = NULL; - +static bool initialized = false; MBED_WEAK psa_status_t its_version_migrate(KVStore *kvstore, @@ -72,18 +72,20 @@ static void its_init(void) } psa_storage_handle_version(kvstore, ITS_VERSION_KEY, &version, its_version_migrate); + initialized = true; } // used from test only void its_deinit(void) { kvstore = NULL; + initialized = false; } -psa_status_t psa_its_set_impl(int32_t pid, psa_storage_uid_t uid, uint32_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) +psa_status_t psa_its_set_impl(int32_t pid, psa_storage_uid_t uid, size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) { - if (!kvstore) { + if (!initialized) { its_init(); } @@ -94,27 +96,28 @@ psa_status_t psa_its_set_impl(int32_t pid, psa_storage_uid_t uid, uint32_t data_ return psa_storage_set_impl(kvstore, pid, uid, data_length, p_data, create_flags); } -psa_status_t psa_its_get_impl(int32_t pid, psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, void *p_data) +psa_status_t psa_its_get_impl(int32_t pid, psa_storage_uid_t uid, size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length) { - if (!kvstore) { + if (!initialized) { its_init(); } - return psa_storage_get_impl(kvstore, pid, uid, data_offset, data_length, p_data); + return psa_storage_get_impl(kvstore, pid, uid, data_offset, data_length, p_data, p_data_length); } psa_status_t psa_its_get_info_impl(int32_t pid, psa_storage_uid_t uid, struct psa_storage_info_t *p_info) { - if (!kvstore) { + uint32_t kv_get_flags; + if (!initialized) { its_init(); } - return psa_storage_get_info_impl(kvstore, pid, uid, p_info); + return psa_storage_get_info_impl(kvstore, pid, uid, p_info, &kv_get_flags); } psa_status_t psa_its_remove_impl(int32_t pid, psa_storage_uid_t uid) { - if (!kvstore) { + if (!initialized) { its_init(); } diff --git a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.h b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.h index 19a98809fd..43d076d8c8 100644 --- a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.h +++ b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IMPL/pits_impl.h @@ -26,8 +26,8 @@ extern "C" { #endif -psa_status_t psa_its_set_impl(int32_t pid, psa_storage_uid_t uid, uint32_t data_length, const void *p_data, psa_storage_create_flags_t create_flags); -psa_status_t psa_its_get_impl(int32_t pid, psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, void *p_data); +psa_status_t psa_its_set_impl(int32_t pid, psa_storage_uid_t uid, size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags); +psa_status_t psa_its_get_impl(int32_t pid, psa_storage_uid_t uid, size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length); psa_status_t psa_its_get_info_impl(int32_t pid, psa_storage_uid_t uid, struct psa_storage_info_t *p_info); psa_status_t psa_its_remove_impl(int32_t pid, psa_storage_uid_t uid); psa_status_t psa_its_reset_impl(); diff --git a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IPC/psa_prot_internal_storage.c b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IPC/psa_prot_internal_storage.c index 65f19ac5ea..fb999af51f 100644 --- a/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IPC/psa_prot_internal_storage.c +++ b/components/TARGET_PSA/services/storage/its/COMPONENT_PSA_SRV_IPC/psa_prot_internal_storage.c @@ -20,7 +20,7 @@ #include "psa/internal_trusted_storage.h" #include "psa_manifest/sid.h" -psa_status_t psa_its_set(psa_storage_uid_t uid, uint32_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) +psa_status_t psa_its_set(psa_storage_uid_t uid, size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) { if (!p_data && data_length) { return PSA_ERROR_INVALID_ARGUMENT; @@ -46,9 +46,11 @@ psa_status_t psa_its_set(psa_storage_uid_t uid, uint32_t data_length, const void return status; } -psa_status_t psa_its_get(psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, void *p_data) +psa_status_t psa_its_get(psa_storage_uid_t uid, size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length) { - if (!p_data && data_length) { + size_t actual_size = 0; + + if ((!p_data && data_length) || !p_data_length) { return PSA_ERROR_INVALID_ARGUMENT; } @@ -56,18 +58,20 @@ psa_status_t psa_its_get(psa_storage_uid_t uid, uint32_t data_offset, uint32_t d { &uid, sizeof(uid) }, { &data_offset, sizeof(data_offset) } }; - psa_outvec resp = { p_data, data_length }; + + psa_outvec resp[2] = { + { p_data, data_length }, + { &actual_size, sizeof(actual_size) } + }; psa_handle_t conn = psa_connect(PSA_ITS_GET, 1); if (conn <= PSA_NULL_HANDLE) { return PSA_ERROR_STORAGE_FAILURE; } - psa_status_t status = psa_call(conn, msg, 2, &resp, 1); + psa_status_t status = psa_call(conn, msg, 2, resp, 2); - if (status == PSA_DROP_CONNECTION) { - status = PSA_ERROR_STORAGE_FAILURE; - } + *p_data_length = actual_size; psa_close(conn); return status; diff --git a/components/TARGET_PSA/services/storage/its/COMPONENT_SPE/its_partition.c b/components/TARGET_PSA/services/storage/its/COMPONENT_SPE/its_partition.c index 305783e8cb..7743d52ad6 100644 --- a/components/TARGET_PSA/services/storage/its/COMPONENT_SPE/its_partition.c +++ b/components/TARGET_PSA/services/storage/its/COMPONENT_SPE/its_partition.c @@ -76,8 +76,11 @@ static psa_status_t storage_get(psa_msg_t *msg) { psa_storage_uid_t key = 0; uint32_t offset = 0; + size_t actual_size; - if ((msg->in_size[0] != sizeof(key)) || (msg->in_size[1] != sizeof(offset))) { + if ((msg->in_size[0] != sizeof(key)) || + (msg->in_size[1] != sizeof(offset)) || + (msg->out_size[1] != sizeof(actual_size))) { return PSA_DROP_CONNECTION; } @@ -94,9 +97,10 @@ static psa_status_t storage_get(psa_msg_t *msg) return PSA_ERROR_STORAGE_FAILURE; } - psa_status_t status = psa_its_get_impl(msg->client_id, key, offset, msg->out_size[0], data); + psa_status_t status = psa_its_get_impl(msg->client_id, key, offset, msg->out_size[0], data, &actual_size); if (status == PSA_SUCCESS) { - psa_write(msg->handle, 0, data, msg->out_size[0]); + psa_write(msg->handle, 0, data, actual_size); + psa_write(msg->handle, 1, &actual_size, sizeof(actual_size)); } memset(data, 0, msg->out_size[0]); diff --git a/components/TARGET_PSA/services/storage/its/psa_prot_internal_storage.h b/components/TARGET_PSA/services/storage/its/psa_prot_internal_storage.h index 5ce5cf6aaa..b4e1a0e898 100644 --- a/components/TARGET_PSA/services/storage/its/psa_prot_internal_storage.h +++ b/components/TARGET_PSA/services/storage/its/psa_prot_internal_storage.h @@ -97,7 +97,7 @@ MBED_DEPRECATED("PS specific types should not be used") * is invalid, for example is `NULL` or references memory the caller cannot access */ psa_status_t psa_its_set(psa_storage_uid_t uid, - uint32_t data_length, + size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags); @@ -108,6 +108,7 @@ psa_status_t psa_its_set(psa_storage_uid_t uid, * \param[in] data_offset The starting offset of the data requested * \param[in] data_length the amount of data requested (and the minimum allocated size of the `p_data` buffer) * \param[out] p_data The buffer where the data will be placed upon successful completion + * \param[out] p_data_length The actual amount of data returned * * \return A status indicating the success/failure of the operation @@ -120,9 +121,10 @@ psa_status_t psa_its_set(psa_storage_uid_t uid, * is invalid. For example is `NULL` or references memory the caller cannot access */ psa_status_t psa_its_get(psa_storage_uid_t uid, - uint32_t data_offset, - uint32_t data_length, - void *p_data); + size_t data_offset, + size_t data_length, + void *p_data, + size_t *p_data_length); /** * \brief Retrieve the metadata about the provided uid diff --git a/components/TARGET_PSA/services/storage/ps/COMPONENT_NSPE/protected_storage.cpp b/components/TARGET_PSA/services/storage/ps/COMPONENT_NSPE/protected_storage.cpp index 8555a2fc73..65aea410ea 100644 --- a/components/TARGET_PSA/services/storage/ps/COMPONENT_NSPE/protected_storage.cpp +++ b/components/TARGET_PSA/services/storage/ps/COMPONENT_NSPE/protected_storage.cpp @@ -39,7 +39,7 @@ extern "C" #define PSA_PS_GLOBAL_PID 1 static KVStore *kvstore = NULL; -static uint32_t def_kvstore_flags = 0; +static bool initialized = false; MBED_WEAK psa_status_t ps_version_migrate(KVStore *kvstore, const psa_storage_version_t *old_version, const psa_storage_version_t *new_version) @@ -69,32 +69,38 @@ static void ps_init(void) error("Failed getting kvstore instance\n"); } - def_kvstore_flags = 0; - if (kvstore != int_kvstore) { - def_kvstore_flags = KVStore::REQUIRE_CONFIDENTIALITY_FLAG | KVStore::REQUIRE_REPLAY_PROTECTION_FLAG; - } - psa_storage_handle_version(kvstore, PS_VERSION_KEY, &version, ps_version_migrate); + initialized = true; } // used from test only void ps_deinit(void) { kvstore = NULL; + initialized = false; } -psa_status_t psa_ps_set(psa_storage_uid_t uid, uint32_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) +psa_status_t psa_ps_set(psa_storage_uid_t uid, size_t data_length, const void *p_data, psa_storage_create_flags_t create_flags) { - if (!kvstore) { + if (!initialized) { ps_init(); } - if (create_flags & ~PSA_STORAGE_FLAG_WRITE_ONCE) { + if (create_flags & ~ + (PSA_STORAGE_FLAG_WRITE_ONCE | PSA_STORAGE_FLAG_NO_CONFIDENTIALITY | PSA_STORAGE_FLAG_NO_REPLAY_PROTECTION)) { return PSA_ERROR_NOT_SUPPORTED; } - uint32_t kv_create_flags = def_kvstore_flags; + // Assume confidentiality and replay protection are set by default + uint32_t kv_create_flags = KVStore::REQUIRE_CONFIDENTIALITY_FLAG | KVStore::REQUIRE_REPLAY_PROTECTION_FLAG; + + if (create_flags & PSA_STORAGE_FLAG_NO_CONFIDENTIALITY) { + kv_create_flags &= ~KVStore::REQUIRE_CONFIDENTIALITY_FLAG; + } + if (create_flags & PSA_STORAGE_FLAG_NO_REPLAY_PROTECTION) { + kv_create_flags &= ~KVStore::REQUIRE_REPLAY_PROTECTION_FLAG; + } if (create_flags & PSA_STORAGE_FLAG_WRITE_ONCE) { kv_create_flags |= KVStore::WRITE_ONCE_FLAG; } @@ -102,27 +108,39 @@ psa_status_t psa_ps_set(psa_storage_uid_t uid, uint32_t data_length, const void return psa_storage_set_impl(kvstore, PSA_PS_GLOBAL_PID, uid, data_length, p_data, kv_create_flags); } -psa_status_t psa_ps_get(psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, void *p_data) +psa_status_t psa_ps_get(psa_storage_uid_t uid, size_t data_offset, size_t data_length, void *p_data, size_t *p_data_length) { - if (!kvstore) { + if (!initialized) { ps_init(); } - return psa_storage_get_impl(kvstore, PSA_PS_GLOBAL_PID, uid, data_offset, data_length, p_data); + return psa_storage_get_impl(kvstore, PSA_PS_GLOBAL_PID, uid, data_offset, data_length, p_data, p_data_length); } psa_status_t psa_ps_get_info(psa_storage_uid_t uid, struct psa_storage_info_t *p_info) { - if (!kvstore) { + psa_status_t ret; + uint32_t kv_get_flags; + + if (!initialized) { ps_init(); } - return psa_storage_get_info_impl(kvstore, PSA_PS_GLOBAL_PID, uid, p_info); + ret = psa_storage_get_info_impl(kvstore, PSA_PS_GLOBAL_PID, uid, p_info, &kv_get_flags); + + if ((kv_get_flags & ~KVStore::REQUIRE_CONFIDENTIALITY_FLAG) == kv_get_flags) { + p_info->flags |= PSA_STORAGE_FLAG_NO_CONFIDENTIALITY; + } + if ((kv_get_flags & ~KVStore::REQUIRE_REPLAY_PROTECTION_FLAG) == kv_get_flags) { + p_info->flags |= PSA_STORAGE_FLAG_NO_REPLAY_PROTECTION; + } + + return ret; } psa_status_t psa_ps_remove(psa_storage_uid_t uid) { - if (!kvstore) { + if (!initialized) { ps_init(); } diff --git a/features/frameworks/TARGET_PSA/pal/pal_internal_trusted_storage_intf.c b/features/frameworks/TARGET_PSA/pal/pal_internal_trusted_storage_intf.c index 3cf9068151..3f6623e735 100644 --- a/features/frameworks/TARGET_PSA/pal/pal_internal_trusted_storage_intf.c +++ b/features/frameworks/TARGET_PSA/pal/pal_internal_trusted_storage_intf.c @@ -34,6 +34,11 @@ uint32_t pal_its_function(int type, va_list valist) //psa_ps_create_flags_t ps_create_flags; struct psa_its_info_t *its_p_info; //struct psa_eps_info_t *ps_p_info; + /* TODO: Actual size argument is currently not supported by the testing framework. + * Changes need to be implemented in the actual tests. + * Should be fixed by the next import of the tests. + */ + size_t actual_size; switch (type) { @@ -48,7 +53,11 @@ uint32_t pal_its_function(int type, va_list valist) offset = va_arg(valist, uint32_t); data_length = va_arg(valist, uint32_t); p_read_data = va_arg(valist, void*); - return psa_its_get(uid, offset, data_length, p_read_data); + /* TODO: Actual size argument is currently not supported by the testing framework. + * Changes need to be implemented in the actual tests. + * Should be fixed by the next import of the tests. + */ + return psa_its_get(uid, offset, data_length, p_read_data, &actual_size); case PAL_ITS_GET_INFO: uid = va_arg(valist, psa_storage_uid_t); its_p_info = va_arg(valist, struct psa_its_info_t*); diff --git a/features/frameworks/TARGET_PSA/pal/pal_protected_storage_intf.c b/features/frameworks/TARGET_PSA/pal/pal_protected_storage_intf.c index cfabb5e8ad..558f94df17 100644 --- a/features/frameworks/TARGET_PSA/pal/pal_protected_storage_intf.c +++ b/features/frameworks/TARGET_PSA/pal/pal_protected_storage_intf.c @@ -28,6 +28,7 @@ uint32_t pal_ps_function(int type, va_list valist) { #if PSA_PROTECTED_STORAGE_IMPLEMENTED uint32_t uid, data_length, offset; + size_t actual_length; const void *p_write_data; void *p_read_data; psa_storage_create_flags_t ps_create_flags; @@ -46,7 +47,7 @@ uint32_t pal_ps_function(int type, va_list valist) offset = va_arg(valist, uint32_t); data_length = va_arg(valist, uint32_t); p_read_data = va_arg(valist, void*); - return psa_ps_get(uid, offset, data_length, p_read_data); + return psa_ps_get(uid, offset, data_length, p_read_data, &actual_length); case PAL_PS_GET_INFO: uid = va_arg(valist, psa_storage_uid_t); ps_p_info = va_arg(valist, struct psa_ps_info_t*); diff --git a/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_its.h b/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_its.h index 44d51982a4..b9b3b5c694 100644 --- a/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_its.h +++ b/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_its.h @@ -106,7 +106,8 @@ psa_status_t psa_its_set(psa_storage_uid_t uid, psa_status_t psa_its_get(psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, - void *p_data); + void *p_data, + size_t *p_data_length); /** * \brief Retrieve the metadata about the provided uid diff --git a/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_storage.c b/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_storage.c index babc5bb95a..0810d86b76 100644 --- a/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_storage.c +++ b/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_crypto_storage.c @@ -95,13 +95,15 @@ static psa_status_t psa_crypto_storage_load( const psa_key_file_id_t key, { psa_status_t status; psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key ); + size_t actual_size; + struct psa_storage_info_t data_identifier_info; status = psa_its_get_info( data_identifier, &data_identifier_info ); if( status != PSA_SUCCESS ) return( status ); - status = psa_its_get( data_identifier, 0, (uint32_t) data_size, data ); + status = psa_its_get( data_identifier, 0, (uint32_t) data_size, data, &actual_size ); return( status ); } diff --git a/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_its_file.c b/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_its_file.c index 8cdf783a7b..90a741f05e 100644 --- a/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_its_file.c +++ b/features/mbedtls/mbed-crypto/platform/COMPONENT_PSA_SRV_IMPL/psa_its_file.c @@ -137,7 +137,8 @@ psa_status_t psa_its_get_info( psa_storage_uid_t uid, psa_status_t psa_its_get( psa_storage_uid_t uid, uint32_t data_offset, uint32_t data_length, - void *p_data ) + void *p_data, + size_t *p_data_length ) { psa_status_t status; FILE *stream = NULL; diff --git a/features/mbedtls/platform/TARGET_PSA/COMPONENT_PSA_SRV_IMPL/src/default_random_seed.cpp b/features/mbedtls/platform/TARGET_PSA/COMPONENT_PSA_SRV_IMPL/src/default_random_seed.cpp index 22a58f72f3..4f50749a3e 100644 --- a/features/mbedtls/platform/TARGET_PSA/COMPONENT_PSA_SRV_IMPL/src/default_random_seed.cpp +++ b/features/mbedtls/platform/TARGET_PSA/COMPONENT_PSA_SRV_IMPL/src/default_random_seed.cpp @@ -5,7 +5,8 @@ int mbed_default_seed_read(unsigned char *buf, size_t buf_len) { - psa_status_t rc = psa_its_get(PSA_CRYPTO_ITS_RANDOM_SEED_UID, 0, buf_len, buf); + size_t actual_size; + psa_status_t rc = psa_its_get(PSA_CRYPTO_ITS_RANDOM_SEED_UID, 0, buf_len, buf, &actual_size); return ( rc ); } diff --git a/features/storage/kvstore/filesystemstore/FileSystemStore.cpp b/features/storage/kvstore/filesystemstore/FileSystemStore.cpp index 01ac336e3e..5af3781ea4 100644 --- a/features/storage/kvstore/filesystemstore/FileSystemStore.cpp +++ b/features/storage/kvstore/filesystemstore/FileSystemStore.cpp @@ -34,7 +34,9 @@ #define FSST_DEFAULT_FOLDER_PATH "kvstore" //default FileSystemStore folder path on fs -static const uint32_t supported_flags = mbed::KVStore::WRITE_ONCE_FLAG; +// Only write once flag is supported, other two are kept in storage but ignored +static const uint32_t supported_flags = mbed::KVStore::WRITE_ONCE_FLAG | mbed::KVStore::REQUIRE_CONFIDENTIALITY_FLAG | + mbed::KVStore::REQUIRE_REPLAY_PROTECTION_FLAG; using namespace mbed; diff --git a/features/storage/kvstore/tdbstore/TDBStore.cpp b/features/storage/kvstore/tdbstore/TDBStore.cpp index 0ab8dcecb3..f33cf5ea5c 100644 --- a/features/storage/kvstore/tdbstore/TDBStore.cpp +++ b/features/storage/kvstore/tdbstore/TDBStore.cpp @@ -35,7 +35,8 @@ using namespace mbed; static const uint32_t delete_flag = (1UL << 31); static const uint32_t internal_flags = delete_flag; -static const uint32_t supported_flags = KVStore::WRITE_ONCE_FLAG; +// Only write once flag is supported, other two are kept in storage but ignored +static const uint32_t supported_flags = KVStore::WRITE_ONCE_FLAG | KVStore::REQUIRE_CONFIDENTIALITY_FLAG | KVStore::REQUIRE_REPLAY_PROTECTION_FLAG; namespace {