Merge pull request #69 from gilles-peskine-arm/psa-its_over_file

PSA ITS over file
diff --git a/configs/config-psa-crypto.h b/configs/config-psa-crypto.h
index a8e0634..4873c36 100644
--- a/configs/config-psa-crypto.h
+++ b/configs/config-psa-crypto.h
@@ -1146,16 +1146,6 @@
  */
 //#define MBEDTLS_ENTROPY_NV_SEED
 
-/**
- * \def MBEDTLS_PSA_HAS_ITS_IO
- *
- * Enable the non-volatile secure storage usage.
- *
- * This is crucial on systems that do not have a HW TRNG support.
- *
- */
-//#define MBEDTLS_PSA_HAS_ITS_IO
-
 /* MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER
  *
  * In PSA key storage, encode the owner of the key.
@@ -1242,14 +1232,17 @@
 //#define MBEDTLS_PSA_CRYPTO_SPM
 
 /**
- * \def MBEDTLS_PSA_HAS_ITS_IO
+ * \def MBEDTLS_PSA_INJECT_ENTROPY
  *
- * Enable the non-volatile secure storage usage.
+ * Enable support for entropy injection at first boot. This feature is
+ * required on systems that do not have a built-in entropy source (TRNG).
+ * This feature is currently not supported on systems that have a built-in
+ * entropy source.
  *
- * This is crucial on systems that do not have a HW TRNG support.
+ * Requires: MBEDTLS_PSA_CRYPTO_STORAGE_C, MBEDTLS_ENTROPY_NV_SEED
  *
  */
-//#define MBEDTLS_PSA_HAS_ITS_IO
+//#define MBEDTLS_PSA_INJECT_ENTROPY
 
 /**
  * \def MBEDTLS_RSA_NO_CRT
@@ -2719,38 +2712,23 @@
  *
  * Module:  library/psa_crypto_storage.c
  *
- * Requires: MBEDTLS_PSA_CRYPTO_C and one of either
- * MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C or MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
- * (but not both)
- *
+ * Requires: MBEDTLS_PSA_CRYPTO_C,
+ *           either MBEDTLS_PSA_ITS_FILE_C or a native implementation of
+ *           the PSA ITS interface
  */
 #define MBEDTLS_PSA_CRYPTO_STORAGE_C
 
 /**
- * \def MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+ * \def MBEDTLS_PSA_ITS_FILE_C
  *
- * Enable persistent key storage over files for the
- * Platform Security Architecture cryptography API.
+ * Enable the emulation of the Platform Security Architecture
+ * Internal Trusted Storage (PSA ITS) over files.
  *
- * Module:  library/psa_crypto_storage_file.c
+ * Module:  library/psa_its_file.c
  *
- * Requires: MBEDTLS_PSA_CRYPTO_C, MBEDTLS_FS_IO
- *
+ * Requires: MBEDTLS_FS_IO
  */
-#define MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
-
-/**
- * \def MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
- *
- * Enable persistent key storage over PSA ITS for the
- * Platform Security Architecture cryptography API.
- *
- * Module:  library/psa_crypto_storage_its.c
- *
- * Requires: MBEDTLS_PSA_CRYPTO_C, MBEDTLS_PSA_HAS_ITS_IO
- *
- */
-//#define MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
+#define MBEDTLS_PSA_ITS_FILE_C
 
 /**
  * \def MBEDTLS_RIPEMD160_C
diff --git a/include/mbedtls/check_config.h b/include/mbedtls/check_config.h
index 962d3db..c1450db 100644
--- a/include/mbedtls/check_config.h
+++ b/include/mbedtls/check_config.h
@@ -525,26 +525,25 @@
 #error "MBEDTLS_PSA_CRYPTO_SPM defined, but not all prerequisites"
 #endif
 
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C) && defined(MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C)
-#error "Only one of MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C or MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C can be defined"
-#endif
-
 #if defined(MBEDTLS_PSA_CRYPTO_STORAGE_C) &&            \
-    !( defined(MBEDTLS_PSA_CRYPTO_C) &&                 \
-       ( defined(MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C) ||  \
-         defined(MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C) ) )
+    ! defined(MBEDTLS_PSA_CRYPTO_C)
 #error "MBEDTLS_PSA_CRYPTO_STORAGE_C defined, but not all prerequisites"
 #endif
 
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C) &&            \
-    !( defined(MBEDTLS_PSA_CRYPTO_STORAGE_C) &&           \
-       defined(MBEDTLS_FS_IO) )
-#error "MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C defined, but not all prerequisites"
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY) &&      \
+    !( defined(MBEDTLS_PSA_CRYPTO_STORAGE_C) && \
+       defined(MBEDTLS_ENTROPY_NV_SEED) )
+#error "MBEDTLS_PSA_INJECT_ENTROPY defined, but not all prerequisites"
 #endif
 
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C) &&             \
-    ! defined(MBEDTLS_PSA_CRYPTO_STORAGE_C)
-#error "MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C defined, but not all prerequisites"
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY) &&              \
+    !defined(MBEDTLS_NO_DEFAULT_ENTROPY_SOURCES)
+#error "MBEDTLS_PSA_INJECT_ENTROPY is not compatible with actual entropy sources"
+#endif
+
+#if defined(MBEDTLS_PSA_ITS_FILE_C) && \
+    !defined(MBEDTLS_FS_IO)
+#error "MBEDTLS_PSA_ITS_FILE_C defined, but not all prerequisites"
 #endif
 
 #if defined(MBEDTLS_RSA_C) && ( !defined(MBEDTLS_BIGNUM_C) ||         \
diff --git a/include/mbedtls/config.h b/include/mbedtls/config.h
index 7f96e50..5621965 100644
--- a/include/mbedtls/config.h
+++ b/include/mbedtls/config.h
@@ -1166,16 +1166,6 @@
  */
 //#define MBEDTLS_ENTROPY_NV_SEED
 
-/**
- * \def MBEDTLS_PSA_HAS_ITS_IO
- *
- * Enable the non-volatile secure storage usage.
- *
- * This is crucial on systems that do not have a HW TRNG support.
- *
- */
-//#define MBEDTLS_PSA_HAS_ITS_IO
-
 /* MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER
  *
  * In PSA key storage, encode the owner of the key.
@@ -1262,14 +1252,17 @@
 //#define MBEDTLS_PSA_CRYPTO_SPM
 
 /**
- * \def MBEDTLS_PSA_HAS_ITS_IO
+ * \def MBEDTLS_PSA_INJECT_ENTROPY
  *
- * Enable the non-volatile secure storage usage.
+ * Enable support for entropy injection at first boot. This feature is
+ * required on systems that do not have a built-in entropy source (TRNG).
+ * This feature is currently not supported on systems that have a built-in
+ * entropy source.
  *
- * This is crucial on systems that do not have a HW TRNG support.
+ * Requires: MBEDTLS_PSA_CRYPTO_STORAGE_C, MBEDTLS_ENTROPY_NV_SEED
  *
  */
-//#define MBEDTLS_PSA_HAS_ITS_IO
+//#define MBEDTLS_PSA_INJECT_ENTROPY
 
 /**
  * \def MBEDTLS_RSA_NO_CRT
@@ -2761,38 +2754,23 @@
  *
  * Module:  library/psa_crypto_storage.c
  *
- * Requires: MBEDTLS_PSA_CRYPTO_C and one of either
- * MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C or MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
- * (but not both)
- *
+ * Requires: MBEDTLS_PSA_CRYPTO_C,
+ *           either MBEDTLS_PSA_ITS_FILE_C or a native implementation of
+ *           the PSA ITS interface
  */
 #define MBEDTLS_PSA_CRYPTO_STORAGE_C
 
 /**
- * \def MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+ * \def MBEDTLS_PSA_ITS_FILE_C
  *
- * Enable persistent key storage over files for the
- * Platform Security Architecture cryptography API.
+ * Enable the emulation of the Platform Security Architecture
+ * Internal Trusted Storage (PSA ITS) over files.
  *
- * Module:  library/psa_crypto_storage_file.c
+ * Module:  library/psa_its_file.c
  *
- * Requires: MBEDTLS_PSA_CRYPTO_C, MBEDTLS_FS_IO
- *
+ * Requires: MBEDTLS_FS_IO
  */
-#define MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
-
-/**
- * \def MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
- *
- * Enable persistent key storage over PSA ITS for the
- * Platform Security Architecture cryptography API.
- *
- * Module:  library/psa_crypto_storage_its.c
- *
- * Requires: MBEDTLS_PSA_CRYPTO_C, MBEDTLS_PSA_HAS_ITS_IO
- *
- */
-//#define MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
+#define MBEDTLS_PSA_ITS_FILE_C
 
 /**
  * \def MBEDTLS_RIPEMD160_C
diff --git a/include/psa/crypto_extra.h b/include/psa/crypto_extra.h
index 5dd4789..c89c55d 100644
--- a/include/psa/crypto_extra.h
+++ b/include/psa/crypto_extra.h
@@ -114,10 +114,9 @@
  * This is an Mbed TLS extension.
  *
  * \note This function is only available on the following platforms:
- * * If the compile-time options MBEDTLS_ENTROPY_NV_SEED and
- *   MBEDTLS_PSA_HAS_ITS_IO are both enabled. Note that you
- *   must provide compatible implementations of mbedtls_nv_seed_read
- *   and mbedtls_nv_seed_write.
+ * * If the compile-time option MBEDTLS_PSA_INJECT_ENTROPY is enabled.
+ *   Note that you must provide compatible implementations of
+ *   mbedtls_nv_seed_read and mbedtls_nv_seed_write.
  * * In a client-server integration of PSA Cryptography, on the client side,
  *   if the server supports this feature.
  * \param[in] seed          Buffer containing the seed value to inject.
diff --git a/library/CMakeLists.txt b/library/CMakeLists.txt
index e9372be..72378da 100644
--- a/library/CMakeLists.txt
+++ b/library/CMakeLists.txt
@@ -56,8 +56,7 @@
     psa_crypto.c
     psa_crypto_slot_management.c
     psa_crypto_storage.c
-    psa_crypto_storage_file.c
-    psa_crypto_storage_its.c
+    psa_its_file.c
     ripemd160.c
     rsa.c
     rsa_internal.c
diff --git a/library/Makefile b/library/Makefile
index 8533eaa..6ed5e68 100644
--- a/library/Makefile
+++ b/library/Makefile
@@ -85,8 +85,7 @@
 		psa_crypto.o					\
 		psa_crypto_slot_management.o			\
 		psa_crypto_storage.o				\
-		psa_crypto_storage_file.o			\
-		psa_crypto_storage_its.o			\
+		psa_its_file.o					\
 		ripemd160.o	rsa_internal.o	rsa.o  		\
 		sha1.o		sha256.o	sha512.o	\
 		threading.o	timing.o	version.o	\
diff --git a/library/psa_crypto.c b/library/psa_crypto.c
index cd1499a..3b9c78f 100644
--- a/library/psa_crypto.c
+++ b/library/psa_crypto.c
@@ -60,7 +60,6 @@
 #include "mbedtls/ecdh.h"
 #include "mbedtls/ecp.h"
 #include "mbedtls/entropy.h"
-#include "mbedtls/entropy_poll.h"
 #include "mbedtls/error.h"
 #include "mbedtls/gcm.h"
 #include "mbedtls/md2.h"
@@ -78,10 +77,6 @@
 #include "mbedtls/sha512.h"
 #include "mbedtls/xtea.h"
 
-#if ( defined(MBEDTLS_ENTROPY_NV_SEED) && defined(MBEDTLS_PSA_HAS_ITS_IO) )
-#include "psa/internal_trusted_storage.h"
-#endif
-
 #define ARRAY_LENGTH( array ) ( sizeof( array ) / sizeof( *( array ) ) )
 
 /* constant-time buffer comparison */
@@ -4423,13 +4418,12 @@
     return( mbedtls_to_psa_error( ret ) );
 }
 
-#if ( defined(MBEDTLS_ENTROPY_NV_SEED) && defined(MBEDTLS_PSA_HAS_ITS_IO) )
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY)
+#include "mbedtls/entropy_poll.h"
 
 psa_status_t mbedtls_psa_inject_entropy( const unsigned char *seed,
                                          size_t seed_size )
 {
-    psa_status_t status;
-    struct psa_storage_info_t p_info;
     if( global_data.initialized )
         return( PSA_ERROR_NOT_PERMITTED );
 
@@ -4438,20 +4432,9 @@
           ( seed_size > MBEDTLS_ENTROPY_MAX_SEED_SIZE ) )
             return( PSA_ERROR_INVALID_ARGUMENT );
 
-    status = psa_its_get_info( PSA_CRYPTO_ITS_RANDOM_SEED_UID, &p_info );
-
-    if( PSA_ERROR_DOES_NOT_EXIST == status ) /* No seed exists */
-    {
-        status = psa_its_set( PSA_CRYPTO_ITS_RANDOM_SEED_UID, seed_size, seed, 0 );
-    }
-    else if( PSA_SUCCESS == status )
-    {
-        /* You should not be here. Seed needs to be injected only once */
-        status = PSA_ERROR_NOT_PERMITTED;
-    }
-    return( status );
+    return( mbedtls_psa_storage_inject_entropy( seed, seed_size ) );
 }
-#endif
+#endif /* MBEDTLS_PSA_INJECT_ENTROPY */
 
 psa_status_t psa_generate_key( psa_key_handle_t handle,
                                psa_key_type_t type,
diff --git a/library/psa_crypto_its.h b/library/psa_crypto_its.h
new file mode 100644
index 0000000..44d5198
--- /dev/null
+++ b/library/psa_crypto_its.h
@@ -0,0 +1,142 @@
+/** \file psa_crypto_its.h
+ * \brief Interface of trusted storage that crypto is built on.
+ */
+/*  Copyright (C) 2019, ARM Limited, All Rights Reserved
+ *  SPDX-License-Identifier: Apache-2.0
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License"); you may
+ *  not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *  http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+#ifndef PSA_CRYPTO_ITS_H
+#define PSA_CRYPTO_ITS_H
+
+#include <stddef.h>
+#include <stdint.h>
+
+#include <psa/crypto_types.h>
+#include <psa/crypto_values.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** \brief Flags used when creating a data entry
+ */
+typedef uint32_t psa_storage_create_flags_t;
+
+/** \brief A type for UIDs used for identifying data
+ */
+typedef uint64_t psa_storage_uid_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`*/
+
+/**
+ * \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 **/
+    psa_storage_create_flags_t flags;    /**< The flags set when the uid was created **/
+};
+
+/** Flag indicating that \ref psa_storage_create and \ref psa_storage_set_extended are supported */
+#define PSA_STORAGE_SUPPORT_SET_EXTENDED (1 << 0)
+
+/** \brief PSA storage specific error codes
+ */
+#define PSA_ERROR_INVALID_SIGNATURE     ((psa_status_t)-149)
+#define PSA_ERROR_DATA_CORRUPT          ((psa_status_t)-152)
+
+#define PSA_ITS_API_VERSION_MAJOR  1  /**< The major version number of the PSA ITS API. It will be incremented on significant updates that may include breaking changes */
+#define PSA_ITS_API_VERSION_MINOR  1  /**< The minor version number of the PSA ITS API. It will be incremented in small updates that are unlikely to include breaking changes */
+
+/**
+ * \brief create a new or modify an existing uid/value pair
+ *
+ * \param[in] uid           the identifier for the data
+ * \param[in] data_length   The size in bytes of the data in `p_data`
+ * \param[in] p_data        A buffer containing the data
+ * \param[in] create_flags  The flags that the data will be stored with
+ *
+ * \return      A status indicating the success/failure of the operation
+ *
+ * \retval      PSA_SUCCESS                      The operation completed successfully
+ * \retval      PSA_ERROR_NOT_PERMITTED          The operation failed because the provided `uid` value was already created with PSA_STORAGE_WRITE_ONCE_FLAG
+ * \retval      PSA_ERROR_NOT_SUPPORTED          The operation failed because one or more of the flags provided in `create_flags` is not supported or is not valid
+ * \retval      PSA_ERROR_INSUFFICIENT_STORAGE   The operation failed because there was insufficient space on the storage medium
+ * \retval      PSA_ERROR_STORAGE_FAILURE        The operation failed because the physical storage has failed (Fatal error)
+ * \retval      PSA_ERROR_INVALID_ARGUMENT       The operation failed because one of the provided pointers(`p_data`)
+ *                                               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,
+                         const void *p_data,
+                         psa_storage_create_flags_t create_flags);
+
+/**
+ * \brief Retrieve the value associated with a provided uid
+ *
+ * \param[in] uid               The uid value
+ * \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
+ *
+ *
+ * \return      A status indicating the success/failure of the operation
+ *
+ * \retval      PSA_SUCCESS                  The operation completed successfully
+ * \retval      PSA_ERROR_DOES_NOT_EXIST     The operation failed because the provided `uid` value was not found in the storage
+ * \retval      PSA_ERROR_INVALID_SIZE       The operation failed because the data associated with provided uid is larger than `data_size`
+ * \retval      PSA_ERROR_STORAGE_FAILURE    The operation failed because the physical storage has failed (Fatal error)
+ * \retval      PSA_ERROR_INVALID_ARGUMENT   The operation failed because one of the provided pointers(`p_data`, `p_data_length`)
+ *                                           is invalid. For example is `NULL` or references memory the caller cannot access.
+ *                                           In addition, this can also happen if an invalid offset was provided.
+ */
+psa_status_t psa_its_get(psa_storage_uid_t uid,
+                         uint32_t data_offset,
+                         uint32_t data_length,
+                         void *p_data);
+
+/**
+ * \brief Retrieve the metadata about the provided uid
+ *
+ * \param[in] uid           The uid value
+ * \param[out] p_info       A pointer to the `psa_storage_info_t` struct that will be populated with the metadata
+ *
+ * \return      A status indicating the success/failure of the operation
+ *
+ * \retval      PSA_SUCCESS                  The operation completed successfully
+ * \retval      PSA_ERROR_DOES_NOT_EXIST     The operation failed because the provided uid value was not found in the storage
+ * \retval      PSA_ERROR_STORAGE_FAILURE    The operation failed because the physical storage has failed (Fatal error)
+ * \retval      PSA_ERROR_INVALID_ARGUMENT   The operation failed because one of the provided pointers(`p_info`)
+ *                                           is invalid, for example is `NULL` or references memory the caller cannot access
+ */
+psa_status_t psa_its_get_info(psa_storage_uid_t uid,
+                              struct psa_storage_info_t *p_info);
+
+/**
+ * \brief Remove the provided key and its associated data from the storage
+ *
+ * \param[in] uid   The uid value
+ *
+ * \return  A status indicating the success/failure of the operation
+ *
+ * \retval      PSA_SUCCESS                  The operation completed successfully
+ * \retval      PSA_ERROR_DOES_NOT_EXIST     The operation failed because the provided key value was not found in the storage
+ * \retval      PSA_ERROR_NOT_PERMITTED      The operation failed because the provided key value was created with PSA_STORAGE_WRITE_ONCE_FLAG
+ * \retval      PSA_ERROR_STORAGE_FAILURE    The operation failed because the physical storage has failed (Fatal error)
+ */
+psa_status_t psa_its_remove(psa_storage_uid_t uid);
+
+#endif /* PSA_CRYPTO_ITS_H */
diff --git a/library/psa_crypto_storage.c b/library/psa_crypto_storage.c
index 84a6ed5..840f418 100644
--- a/library/psa_crypto_storage.c
+++ b/library/psa_crypto_storage.c
@@ -33,9 +33,15 @@
 #include "psa_crypto_service_integration.h"
 #include "psa/crypto.h"
 #include "psa_crypto_storage.h"
-#include "psa_crypto_storage_backend.h"
 #include "mbedtls/platform_util.h"
 
+#if defined(MBEDTLS_PSA_ITS_FILE_C)
+#include "psa_crypto_its.h"
+#else /* Native ITS implementation */
+#include "psa/error.h"
+#include "psa/internal_trusted_storage.h"
+#endif
+
 #if defined(MBEDTLS_PLATFORM_C)
 #include "mbedtls/platform.h"
 #else
@@ -44,6 +50,173 @@
 #define mbedtls_free     free
 #endif
 
+/* Determine a file name (ITS file identifier) for the given key file
+ * identifier. The file name must be distinct from any file that is used
+ * for a purpose other than storing a key. Currently, the only such file
+ * is the random seed file whose name is PSA_CRYPTO_ITS_RANDOM_SEED_UID
+ * and whose value is 0xFFFFFF52. */
+static psa_storage_uid_t psa_its_identifier_of_slot( psa_key_file_id_t file_id )
+{
+#if defined(MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER) && \
+    defined(PSA_CRYPTO_SECURE)
+    /* Encode the owner in the upper 32 bits. This means that if
+     * owner values are nonzero (as they are on a PSA platform),
+     * no key file will ever have a value less than 0x100000000, so
+     * the whole range 0..0xffffffff is available for non-key files. */
+    uint32_t unsigned_owner = (uint32_t) file_id.owner;
+    return( (uint64_t) unsigned_owner << 32 | file_id.key_id );
+#else
+    /* Use the key id directly as a file name.
+     * psa_is_key_file_id_valid() in psa_crypto_slot_management.c
+     * is responsible for ensuring that key identifiers do not have a
+     * value that is reserved for non-key files. */
+    return( file_id );
+#endif
+}
+
+/**
+ * \brief Load persistent data for the given key slot number.
+ *
+ * This function reads data from a storage backend and returns the data in a
+ * buffer.
+ *
+ * \param key               Persistent identifier of the key to be loaded. This
+ *                          should be an occupied storage location.
+ * \param[out] data         Buffer where the data is to be written.
+ * \param data_size         Size of the \c data buffer in bytes.
+ *
+ * \retval PSA_SUCCESS
+ * \retval PSA_ERROR_STORAGE_FAILURE
+ * \retval PSA_ERROR_DOES_NOT_EXIST
+ */
+static psa_status_t psa_crypto_storage_load( const psa_key_file_id_t key,
+                                             uint8_t *data,
+                                             size_t data_size )
+{
+    psa_status_t status;
+    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
+    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 );
+
+    return( status );
+}
+
+int psa_is_key_present_in_storage( const psa_key_file_id_t key )
+{
+    psa_status_t ret;
+    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
+    struct psa_storage_info_t data_identifier_info;
+
+    ret = psa_its_get_info( data_identifier, &data_identifier_info );
+
+    if( ret == PSA_ERROR_DOES_NOT_EXIST )
+        return( 0 );
+    return( 1 );
+}
+
+/**
+ * \brief Store persistent data for the given key slot number.
+ *
+ * This function stores the given data buffer to a persistent storage.
+ *
+ * \param key           Persistent identifier of the key to be stored. This
+ *                      should be an unoccupied storage location.
+ * \param[in] data      Buffer containing the data to be stored.
+ * \param data_length   The number of bytes
+ *                      that make up the data.
+ *
+ * \retval PSA_SUCCESS
+ * \retval PSA_ERROR_INSUFFICIENT_STORAGE
+ * \retval PSA_ERROR_STORAGE_FAILURE
+ * \retval PSA_ERROR_ALREADY_EXISTS
+ */
+static psa_status_t psa_crypto_storage_store( const psa_key_file_id_t key,
+                                              const uint8_t *data,
+                                              size_t data_length )
+{
+    psa_status_t status;
+    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
+    struct psa_storage_info_t data_identifier_info;
+
+    if( psa_is_key_present_in_storage( key ) == 1 )
+        return( PSA_ERROR_ALREADY_EXISTS );
+
+    status = psa_its_set( data_identifier, (uint32_t) data_length, data, 0 );
+    if( status != PSA_SUCCESS )
+    {
+        return( PSA_ERROR_STORAGE_FAILURE );
+    }
+
+    status = psa_its_get_info( data_identifier, &data_identifier_info );
+    if( status != PSA_SUCCESS )
+    {
+        goto exit;
+    }
+
+    if( data_identifier_info.size != data_length )
+    {
+        status = PSA_ERROR_STORAGE_FAILURE;
+        goto exit;
+    }
+
+exit:
+    if( status != PSA_SUCCESS )
+        psa_its_remove( data_identifier );
+    return( status );
+}
+
+psa_status_t psa_destroy_persistent_key( const psa_key_file_id_t key )
+{
+    psa_status_t ret;
+    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
+    struct psa_storage_info_t data_identifier_info;
+
+    ret = psa_its_get_info( data_identifier, &data_identifier_info );
+    if( ret == PSA_ERROR_DOES_NOT_EXIST )
+        return( PSA_SUCCESS );
+
+    if( psa_its_remove( data_identifier ) != PSA_SUCCESS )
+        return( PSA_ERROR_STORAGE_FAILURE );
+
+    ret = psa_its_get_info( data_identifier, &data_identifier_info );
+    if( ret != PSA_ERROR_DOES_NOT_EXIST )
+        return( PSA_ERROR_STORAGE_FAILURE );
+
+    return( PSA_SUCCESS );
+}
+
+/**
+ * \brief Get data length for given key slot number.
+ *
+ * \param key               Persistent identifier whose stored data length
+ *                          is to be obtained.
+ * \param[out] data_length  The number of bytes that make up the data.
+ *
+ * \retval PSA_SUCCESS
+ * \retval PSA_ERROR_STORAGE_FAILURE
+ */
+static psa_status_t psa_crypto_storage_get_data_length(
+    const psa_key_file_id_t key,
+    size_t *data_length )
+{
+    psa_status_t status;
+    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
+    struct psa_storage_info_t data_identifier_info;
+
+    status = psa_its_get_info( data_identifier, &data_identifier_info );
+    if( status != PSA_SUCCESS )
+        return( status );
+
+    *data_length = (size_t) data_identifier_info.size;
+
+    return( PSA_SUCCESS );
+}
+
 /*
  * 32-bit integer manipulation macros (little endian)
  */
@@ -218,4 +391,26 @@
     return( status );
 }
 
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY)
+psa_status_t mbedtls_psa_storage_inject_entropy( const unsigned char *seed,
+                                                 size_t seed_size )
+{
+    psa_status_t status;
+    struct psa_storage_info_t p_info;
+
+    status = psa_its_get_info( PSA_CRYPTO_ITS_RANDOM_SEED_UID, &p_info );
+
+    if( PSA_ERROR_DOES_NOT_EXIST == status ) /* No seed exists */
+    {
+        status = psa_its_set( PSA_CRYPTO_ITS_RANDOM_SEED_UID, seed_size, seed, 0 );
+    }
+    else if( PSA_SUCCESS == status )
+    {
+        /* You should not be here. Seed needs to be injected only once */
+        status = PSA_ERROR_NOT_PERMITTED;
+    }
+    return( status );
+}
+#endif /* MBEDTLS_PSA_INJECT_ENTROPY */
+
 #endif /* MBEDTLS_PSA_CRYPTO_STORAGE_C */
diff --git a/library/psa_crypto_storage.h b/library/psa_crypto_storage.h
index 7e5aae9..5434d05 100644
--- a/library/psa_crypto_storage.h
+++ b/library/psa_crypto_storage.h
@@ -62,6 +62,21 @@
 #define PSA_MAX_PERSISTENT_KEY_IDENTIFIER 0xfffeffff
 
 /**
+ * \brief Checks if persistent data is stored for the given key slot number
+ *
+ * This function checks if any key data or metadata exists for the key slot in
+ * the persistent storage.
+ *
+ * \param key           Persistent identifier to check.
+ *
+ * \retval 0
+ *         No persistent data present for slot number
+ * \retval 1
+ *         Persistent data present for slot number
+ */
+int psa_is_key_present_in_storage( const psa_key_file_id_t key );
+
+/**
  * \brief Format key data and metadata and save to a location for given key
  *        slot.
  *
@@ -188,6 +203,22 @@
                                               psa_key_type_t *type,
                                               psa_key_policy_t *policy );
 
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY)
+/** Backend side of mbedtls_psa_inject_entropy().
+ *
+ * This function stores the supplied data into the entropy seed file.
+ *
+ * \retval #PSA_SUCCESS
+ *         Success
+ * \retval #PSA_ERROR_STORAGE_FAILURE
+ * \retval #PSA_ERROR_INSUFFICIENT_STORAGE
+ * \retval #PSA_ERROR_NOT_PERMITTED
+ *         The entropy seed file already exists.
+ */
+psa_status_t mbedtls_psa_storage_inject_entropy( const unsigned char *seed,
+                                                 size_t seed_size );
+#endif /* MBEDTLS_PSA_INJECT_ENTROPY */
+
 #ifdef __cplusplus
 }
 #endif
diff --git a/library/psa_crypto_storage_backend.h b/library/psa_crypto_storage_backend.h
deleted file mode 100644
index dd534d2..0000000
--- a/library/psa_crypto_storage_backend.h
+++ /dev/null
@@ -1,115 +0,0 @@
-/**
- * \file psa_crypto_storage_backend.h
- *
- * \brief PSA cryptography module: Mbed TLS key storage backend
- */
-/*
- *  Copyright (C) 2018, ARM Limited, All Rights Reserved
- *  SPDX-License-Identifier: Apache-2.0
- *
- *  Licensed under the Apache License, Version 2.0 (the "License"); you may
- *  not use this file except in compliance with the License.
- *  You may obtain a copy of the License at
- *
- *  http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing, software
- *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
- *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- *  See the License for the specific language governing permissions and
- *  limitations under the License.
- *
- *  This file is part of mbed TLS (https://tls.mbed.org)
- */
-
-#ifndef PSA_CRYPTO_STORAGE_BACKEND_H
-#define PSA_CRYPTO_STORAGE_BACKEND_H
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-/* Include the Mbed TLS configuration file, the way Mbed TLS does it
- * in each of its header files. */
-#if defined(MBEDTLS_CONFIG_FILE)
-#include MBEDTLS_CONFIG_FILE
-#else
-#include "mbedtls/config.h"
-#endif
-
-#include "psa/crypto.h"
-#include "psa_crypto_storage.h"
-#include <stdint.h>
-
-/**
- * \brief Load persistent data for the given key slot number.
- *
- * This function reads data from a storage backend and returns the data in a
- * buffer.
- *
- * \param key               Persistent identifier of the key to be loaded. This
- *                          should be an occupied storage location.
- * \param[out] data         Buffer where the data is to be written.
- * \param data_size         Size of the \c data buffer in bytes.
- *
- * \retval PSA_SUCCESS
- * \retval PSA_ERROR_STORAGE_FAILURE
- * \retval PSA_ERROR_DOES_NOT_EXIST
- */
-psa_status_t psa_crypto_storage_load( const psa_key_file_id_t key, uint8_t *data,
-                                      size_t data_size );
-
-/**
- * \brief Store persistent data for the given key slot number.
- *
- * This function stores the given data buffer to a persistent storage.
- *
- * \param key           Persistent identifier of the key to be stored. This
- *                      should be an unoccupied storage location.
- * \param[in] data      Buffer containing the data to be stored.
- * \param data_length   The number of bytes
- *                      that make up the data.
- *
- * \retval PSA_SUCCESS
- * \retval PSA_ERROR_INSUFFICIENT_STORAGE
- * \retval PSA_ERROR_STORAGE_FAILURE
- * \retval PSA_ERROR_ALREADY_EXISTS
- */
-psa_status_t psa_crypto_storage_store( const psa_key_file_id_t key,
-                                       const uint8_t *data,
-                                       size_t data_length );
-
-/**
- * \brief Checks if persistent data is stored for the given key slot number
- *
- * This function checks if any key data or metadata exists for the key slot in
- * the persistent storage.
- *
- * \param key           Persistent identifier to check.
- *
- * \retval 0
- *         No persistent data present for slot number
- * \retval 1
- *         Persistent data present for slot number
- */
-int psa_is_key_present_in_storage( const psa_key_file_id_t key );
-
-/**
- * \brief Get data length for given key slot number.
- *
- * \param key               Persistent identifier whose stored data length
- *                          is to be obtained.
- * \param[out] data_length  The number of bytes that make up the data.
- *
- * \retval PSA_SUCCESS
- * \retval PSA_ERROR_STORAGE_FAILURE
- */
-psa_status_t psa_crypto_storage_get_data_length( const psa_key_file_id_t key,
-                                                 size_t *data_length );
-
-
-#ifdef __cplusplus
-}
-#endif
-
-#endif /* PSA_CRYPTO_STORAGE_H */
diff --git a/library/psa_crypto_storage_file.c b/library/psa_crypto_storage_file.c
deleted file mode 100644
index c4a534f..0000000
--- a/library/psa_crypto_storage_file.c
+++ /dev/null
@@ -1,220 +0,0 @@
-/*
- *  PSA file storage backend for persistent keys
- */
-/*  Copyright (C) 2018, ARM Limited, All Rights Reserved
- *  SPDX-License-Identifier: Apache-2.0
- *
- *  Licensed under the Apache License, Version 2.0 (the "License"); you may
- *  not use this file except in compliance with the License.
- *  You may obtain a copy of the License at
- *
- *  http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing, software
- *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
- *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- *  See the License for the specific language governing permissions and
- *  limitations under the License.
- *
- *  This file is part of mbed TLS (https://tls.mbed.org)
- */
-
-#if defined(MBEDTLS_CONFIG_FILE)
-#include MBEDTLS_CONFIG_FILE
-#else
-#include "mbedtls/config.h"
-#endif
-
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C)
-
-#include <string.h>
-
-#include "psa/crypto.h"
-#include "psa_crypto_storage_backend.h"
-#include "mbedtls/platform_util.h"
-
-#if defined(MBEDTLS_PLATFORM_C)
-#include "mbedtls/platform.h"
-#else
-#include <stdio.h>
-#define mbedtls_snprintf snprintf
-#endif
-
-/* This option sets where files are to be stored. If this is left unset,
- * the files by default will be stored in the same location as the program,
- * which may not be desired or possible. */
-#if !defined(CRYPTO_STORAGE_FILE_LOCATION)
-#define CRYPTO_STORAGE_FILE_LOCATION ""
-#endif
-
-enum { MAX_LOCATION_LEN = sizeof(CRYPTO_STORAGE_FILE_LOCATION) + 40 };
-
-static void key_id_to_location( const psa_key_file_id_t key,
-                                char *location,
-                                size_t location_size )
-{
-    mbedtls_snprintf( location, location_size,
-                      CRYPTO_STORAGE_FILE_LOCATION "psa_key_slot_%lu",
-                      (unsigned long) key );
-}
-
-psa_status_t psa_crypto_storage_load( const psa_key_file_id_t key, uint8_t *data,
-                                      size_t data_size )
-{
-    psa_status_t status = PSA_SUCCESS;
-    FILE *file;
-    size_t num_read;
-    char slot_location[MAX_LOCATION_LEN];
-
-    key_id_to_location( key, slot_location, MAX_LOCATION_LEN );
-    file = fopen( slot_location, "rb" );
-    if( file == NULL )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-    num_read = fread( data, 1, data_size, file );
-    if( num_read != data_size )
-        status = PSA_ERROR_STORAGE_FAILURE;
-
-exit:
-    if( file != NULL )
-        fclose( file );
-    return( status );
-}
-
-int psa_is_key_present_in_storage( const psa_key_file_id_t key )
-{
-    char slot_location[MAX_LOCATION_LEN];
-    FILE *file;
-
-    key_id_to_location( key, slot_location, MAX_LOCATION_LEN );
-
-    file = fopen( slot_location, "r" );
-    if( file == NULL )
-    {
-        /* File doesn't exist */
-        return( 0 );
-    }
-
-    fclose( file );
-    return( 1 );
-}
-
-psa_status_t psa_crypto_storage_store( const psa_key_file_id_t key,
-                                       const uint8_t *data,
-                                       size_t data_length )
-{
-    psa_status_t status = PSA_SUCCESS;
-    int ret;
-    size_t num_written;
-    char slot_location[MAX_LOCATION_LEN];
-    FILE *file;
-    /* The storage location corresponding to "key slot 0" is used as a
-     * temporary location in order to make the apparition of the actual slot
-     * file atomic. 0 is not a valid key slot number, so this should not
-     * affect actual keys. */
-    const char *temp_location = CRYPTO_STORAGE_FILE_LOCATION "psa_key_slot_0";
-
-    key_id_to_location( key, slot_location, MAX_LOCATION_LEN );
-
-    if( psa_is_key_present_in_storage( key ) == 1 )
-        return( PSA_ERROR_ALREADY_EXISTS );
-
-    file = fopen( temp_location, "wb" );
-    if( file == NULL )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-    num_written = fwrite( data, 1, data_length, file );
-    if( num_written != data_length )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-    ret = fclose( file );
-    file = NULL;
-    if( ret != 0 )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-    if( rename( temp_location, slot_location ) != 0 )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-exit:
-    if( file != NULL )
-        fclose( file );
-    remove( temp_location );
-    return( status );
-}
-
-psa_status_t psa_destroy_persistent_key( const psa_key_file_id_t key )
-{
-    FILE *file;
-    char slot_location[MAX_LOCATION_LEN];
-
-    key_id_to_location( key, slot_location, MAX_LOCATION_LEN );
-
-    /* Only try remove the file if it exists */
-    file = fopen( slot_location, "rb" );
-    if( file != NULL )
-    {
-        fclose( file );
-
-        if( remove( slot_location ) != 0 )
-            return( PSA_ERROR_STORAGE_FAILURE );
-    }
-    return( PSA_SUCCESS );
-}
-
-psa_status_t psa_crypto_storage_get_data_length( const psa_key_file_id_t key,
-                                                 size_t *data_length )
-{
-    psa_status_t status = PSA_SUCCESS;
-    FILE *file;
-    long file_size;
-    char slot_location[MAX_LOCATION_LEN];
-
-    key_id_to_location( key, slot_location, MAX_LOCATION_LEN );
-
-    file = fopen( slot_location, "rb" );
-    if( file == NULL )
-        return( PSA_ERROR_DOES_NOT_EXIST );
-
-    if( fseek( file, 0, SEEK_END ) != 0 )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-    file_size = ftell( file );
-
-    if( file_size < 0 )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-#if LONG_MAX > SIZE_MAX
-    if( (unsigned long) file_size > SIZE_MAX )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-#endif
-    *data_length = (size_t) file_size;
-
-exit:
-    fclose( file );
-    return( status );
-}
-
-#endif /* MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C */
diff --git a/library/psa_crypto_storage_its.c b/library/psa_crypto_storage_its.c
deleted file mode 100644
index 447c0ae..0000000
--- a/library/psa_crypto_storage_its.c
+++ /dev/null
@@ -1,164 +0,0 @@
-/*
- *  PSA storage backend for persistent keys using psa_its APIs.
- */
-/*  Copyright (C) 2018, ARM Limited, All Rights Reserved
- *  SPDX-License-Identifier: Apache-2.0
- *
- *  Licensed under the Apache License, Version 2.0 (the "License"); you may
- *  not use this file except in compliance with the License.
- *  You may obtain a copy of the License at
- *
- *  http://www.apache.org/licenses/LICENSE-2.0
- *
- *  Unless required by applicable law or agreed to in writing, software
- *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
- *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- *  See the License for the specific language governing permissions and
- *  limitations under the License.
- *
- *  This file is part of mbed TLS (https://tls.mbed.org)
- */
-
-#if defined(MBEDTLS_CONFIG_FILE)
-#include MBEDTLS_CONFIG_FILE
-#else
-#include "mbedtls/config.h"
-#endif
-
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C)
-
-#include "psa/error.h"
-#include "psa_crypto_service_integration.h"
-#include "psa/crypto.h"
-#include "psa_crypto_storage_backend.h"
-#include "psa/internal_trusted_storage.h"
-
-#if defined(MBEDTLS_PLATFORM_C)
-#include "mbedtls/platform.h"
-#endif
-
-/* Determine a file name (ITS file identifier) for the given key file
- * identifier. The file name must be distinct from any file that is used
- * for a purpose other than storing a key. Currently, the only such file
- * is the random seed file whose name is PSA_CRYPTO_ITS_RANDOM_SEED_UID
- * and whose value is 0xFFFFFF52. */
-static psa_storage_uid_t psa_its_identifier_of_slot( psa_key_file_id_t file_id )
-{
-#if defined(MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER) && \
-    defined(PSA_CRYPTO_SECURE)
-    /* Encode the owner in the upper 32 bits. This means that if
-     * owner values are nonzero (as they are on a PSA platform),
-     * no key file will ever have a value less than 0x100000000, so
-     * the whole range 0..0xffffffff is available for non-key files. */
-    uint32_t unsigned_owner = (uint32_t) file_id.owner;
-    return( (uint64_t) unsigned_owner << 32 | file_id.key_id );
-#else
-    /* Use the key id directly as a file name.
-     * psa_is_key_file_id_valid() in psa_crypto_slot_management.c
-     * is responsible for ensuring that key identifiers do not have a
-     * value that is reserved for non-key files. */
-    return( file_id );
-#endif
-}
-
-psa_status_t psa_crypto_storage_load( const psa_key_file_id_t key, uint8_t *data,
-                                      size_t data_size )
-{
-    psa_status_t status;
-    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
-    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, data_size, data );
-
-    return( status );
-}
-
-int psa_is_key_present_in_storage( const psa_key_file_id_t key )
-{
-    psa_status_t ret;
-    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
-    struct psa_storage_info_t data_identifier_info;
-
-    ret = psa_its_get_info( data_identifier, &data_identifier_info );
-
-    if( ret == PSA_ERROR_DOES_NOT_EXIST )
-        return( 0 );
-    return( 1 );
-}
-
-psa_status_t psa_crypto_storage_store( const psa_key_file_id_t key,
-                                       const uint8_t *data,
-                                       size_t data_length )
-{
-    psa_status_t status;
-    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
-    struct psa_storage_info_t data_identifier_info;
-
-    if( psa_is_key_present_in_storage( key ) == 1 )
-        return( PSA_ERROR_ALREADY_EXISTS );
-
-    status = psa_its_set( data_identifier, data_length, data, 0 );
-    if( status != PSA_SUCCESS )
-    {
-        return( PSA_ERROR_STORAGE_FAILURE );
-    }
-
-    status = psa_its_get_info( data_identifier, &data_identifier_info );
-    if( status != PSA_SUCCESS )
-    {
-        goto exit;
-    }
-
-    if( data_identifier_info.size != data_length )
-    {
-        status = PSA_ERROR_STORAGE_FAILURE;
-        goto exit;
-    }
-
-exit:
-    if( status != PSA_SUCCESS )
-        psa_its_remove( data_identifier );
-    return( status );
-}
-
-psa_status_t psa_destroy_persistent_key( const psa_key_file_id_t key )
-{
-    psa_status_t ret;
-    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
-    struct psa_storage_info_t data_identifier_info;
-
-    ret = psa_its_get_info( data_identifier, &data_identifier_info );
-    if( ret == PSA_ERROR_DOES_NOT_EXIST )
-        return( PSA_SUCCESS );
-
-    if( psa_its_remove( data_identifier ) != PSA_SUCCESS )
-        return( PSA_ERROR_STORAGE_FAILURE );
-
-    ret = psa_its_get_info( data_identifier, &data_identifier_info );
-    if( ret != PSA_ERROR_DOES_NOT_EXIST )
-        return( PSA_ERROR_STORAGE_FAILURE );
-
-    return( PSA_SUCCESS );
-}
-
-psa_status_t psa_crypto_storage_get_data_length( const psa_key_file_id_t key,
-                                                 size_t *data_length )
-{
-    psa_status_t status;
-    psa_storage_uid_t data_identifier = psa_its_identifier_of_slot( key );
-    struct psa_storage_info_t data_identifier_info;
-
-    status = psa_its_get_info( data_identifier, &data_identifier_info );
-    if( status != PSA_SUCCESS )
-        return( status );
-
-    *data_length = (size_t) data_identifier_info.size;
-
-    return( PSA_SUCCESS );
-}
-
-#endif /* MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C */
diff --git a/library/psa_its_file.c b/library/psa_its_file.c
new file mode 100644
index 0000000..de60ecf
--- /dev/null
+++ b/library/psa_its_file.c
@@ -0,0 +1,233 @@
+/*
+ *  PSA ITS simulator over stdio files.
+ */
+/*  Copyright (C) 2018, ARM Limited, All Rights Reserved
+ *  SPDX-License-Identifier: Apache-2.0
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License"); you may
+ *  not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *  http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ *  This file is part of mbed TLS (https://tls.mbed.org)
+ */
+
+#if defined(MBEDTLS_CONFIG_FILE)
+#include MBEDTLS_CONFIG_FILE
+#else
+#include "mbedtls/config.h"
+#endif
+
+#if defined(MBEDTLS_PSA_ITS_FILE_C)
+
+#if defined(MBEDTLS_PLATFORM_C)
+#include "mbedtls/platform.h"
+#else
+#define mbedtls_snprintf   snprintf
+#endif
+
+#include "psa_crypto_its.h"
+
+#include <limits.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <string.h>
+
+#define PSA_ITS_STORAGE_PREFIX ""
+
+#define PSA_ITS_STORAGE_FILENAME_PATTERN "%08lx%08lx"
+#define PSA_ITS_STORAGE_SUFFIX ".psa_its"
+#define PSA_ITS_STORAGE_FILENAME_LENGTH         \
+    ( sizeof( PSA_ITS_STORAGE_PREFIX ) - 1 + /*prefix without terminating 0*/ \
+      16 + /*UID (64-bit number in hex)*/                               \
+      sizeof( PSA_ITS_STORAGE_SUFFIX ) - 1 + /*suffix without terminating 0*/ \
+      1 /*terminating null byte*/ )
+#define PSA_ITS_STORAGE_TEMP \
+    PSA_ITS_STORAGE_PREFIX "tempfile" PSA_ITS_STORAGE_SUFFIX
+
+/* The maximum value of psa_storage_info_t.size */
+#define PSA_ITS_MAX_SIZE 0xffffffff
+
+#define PSA_ITS_MAGIC_STRING "PSA\0ITS\0"
+#define PSA_ITS_MAGIC_LENGTH 8
+
+typedef struct
+{
+    uint8_t magic[PSA_ITS_MAGIC_LENGTH];
+    uint8_t size[sizeof( uint32_t )];
+    uint8_t flags[sizeof( psa_storage_create_flags_t )];
+} psa_its_file_header_t;
+
+static void psa_its_fill_filename( psa_storage_uid_t uid, char *filename )
+{
+    /* Break up the UID into two 32-bit pieces so as not to rely on
+     * long long support in snprintf. */
+    mbedtls_snprintf( filename, PSA_ITS_STORAGE_FILENAME_LENGTH,
+                      "%s" PSA_ITS_STORAGE_FILENAME_PATTERN "%s",
+                      PSA_ITS_STORAGE_PREFIX,
+                      (unsigned long) ( uid >> 32 ),
+                      (unsigned long) ( uid & 0xffffffff ),
+                      PSA_ITS_STORAGE_SUFFIX );
+}
+
+static psa_status_t psa_its_read_file( psa_storage_uid_t uid,
+                                       struct psa_storage_info_t *p_info,
+                                       FILE **p_stream )
+{
+    char filename[PSA_ITS_STORAGE_FILENAME_LENGTH];
+    psa_its_file_header_t header;
+    size_t n;
+
+    *p_stream = NULL;
+    psa_its_fill_filename( uid, filename );
+    *p_stream = fopen( filename, "rb" );
+    if( *p_stream == NULL )
+        return( PSA_ERROR_DOES_NOT_EXIST );
+
+    n = fread( &header, 1, sizeof( header ), *p_stream );
+    if( n != sizeof( header ) )
+        return( PSA_ERROR_DATA_CORRUPT );
+    if( memcmp( header.magic, PSA_ITS_MAGIC_STRING,
+                PSA_ITS_MAGIC_LENGTH ) != 0 )
+        return( PSA_ERROR_DATA_CORRUPT );
+
+    p_info->size = ( header.size[0] |
+                     header.size[1] << 8 |
+                     header.size[2] << 16 |
+                     header.size[3] << 24 );
+    p_info->flags = ( header.flags[0] |
+                      header.flags[1] << 8 |
+                      header.flags[2] << 16 |
+                      header.flags[3] << 24 );
+    return( PSA_SUCCESS );
+}
+
+psa_status_t psa_its_get_info( psa_storage_uid_t uid,
+                               struct psa_storage_info_t *p_info )
+{
+    psa_status_t status;
+    FILE *stream = NULL;
+    status = psa_its_read_file( uid, p_info, &stream );
+    if( stream != NULL )
+        fclose( stream );
+    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 status;
+    FILE *stream = NULL;
+    size_t n;
+    struct psa_storage_info_t info;
+
+    status = psa_its_read_file( uid, &info, &stream );
+    if( status != PSA_SUCCESS )
+        goto exit;
+    status = PSA_ERROR_INVALID_ARGUMENT;
+    if( data_offset + data_length < data_offset )
+        goto exit;
+#if SIZE_MAX < 0xffffffff
+    if( data_offset + data_length > SIZE_MAX )
+        goto exit;
+#endif
+    if( data_offset + data_length > info.size )
+        goto exit;
+
+    status = PSA_ERROR_STORAGE_FAILURE;
+#if LONG_MAX < 0xffffffff
+    while( data_offset > LONG_MAX )
+    {
+        if( fseek( stream, LONG_MAX, SEEK_CUR ) != 0 )
+            goto exit;
+        data_offset -= LONG_MAX;
+    }
+#endif
+    if( fseek( stream, data_offset, SEEK_CUR ) != 0 )
+        goto exit;
+    n = fread( p_data, 1, data_length, stream );
+    if( n != data_length )
+        goto exit;
+    status = PSA_SUCCESS;
+
+exit:
+    if( stream != NULL )
+        fclose( stream );
+    return( status );
+}
+
+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 status = PSA_ERROR_STORAGE_FAILURE;
+    char filename[PSA_ITS_STORAGE_FILENAME_LENGTH];
+    FILE *stream = NULL;
+    psa_its_file_header_t header;
+    size_t n;
+
+    memcpy( header.magic, PSA_ITS_MAGIC_STRING, PSA_ITS_MAGIC_LENGTH );
+    header.size[0] = data_length & 0xff;
+    header.size[1] = ( data_length >> 8 ) & 0xff;
+    header.size[2] = ( data_length >> 16 ) & 0xff;
+    header.size[3] = ( data_length >> 24 ) & 0xff;
+    header.flags[0] = create_flags & 0xff;
+    header.flags[1] = ( create_flags >> 8 ) & 0xff;
+    header.flags[2] = ( create_flags >> 16 ) & 0xff;
+    header.flags[3] = ( create_flags >> 24 ) & 0xff;
+
+    psa_its_fill_filename( uid, filename );
+    stream = fopen( PSA_ITS_STORAGE_TEMP, "wb" );
+    if( stream == NULL )
+        goto exit;
+
+    status = PSA_ERROR_INSUFFICIENT_STORAGE;
+    n = fwrite( &header, 1, sizeof( header ), stream );
+    if( n != sizeof( header ) )
+        goto exit;
+    n = fwrite( p_data, 1, data_length, stream );
+    if( n != data_length )
+        goto exit;
+    status = PSA_SUCCESS;
+
+exit:
+    if( stream != NULL )
+    {
+        int ret = fclose( stream );
+        if( status == PSA_SUCCESS && ret != 0 )
+            status = PSA_ERROR_INSUFFICIENT_STORAGE;
+    }
+    if( status == PSA_SUCCESS )
+    {
+        if( rename( PSA_ITS_STORAGE_TEMP, filename ) != 0 )
+            status = PSA_ERROR_STORAGE_FAILURE;
+    }
+    remove( PSA_ITS_STORAGE_TEMP );
+    return( status );
+}
+
+psa_status_t psa_its_remove( psa_storage_uid_t uid )
+{
+    char filename[PSA_ITS_STORAGE_FILENAME_LENGTH];
+    FILE *stream;
+    psa_its_fill_filename( uid, filename );
+    stream = fopen( filename, "rb" );
+    if( stream == NULL )
+        return( PSA_ERROR_DOES_NOT_EXIST );
+    fclose( stream );
+    if( remove( filename ) != 0 )
+        return( PSA_ERROR_STORAGE_FAILURE );
+    return( PSA_SUCCESS );
+}
+
+#endif /* MBEDTLS_PSA_ITS_FILE_C */
diff --git a/library/version_features.c b/library/version_features.c
index f01eace..00fd2e9 100644
--- a/library/version_features.c
+++ b/library/version_features.c
@@ -411,9 +411,6 @@
 #if defined(MBEDTLS_ENTROPY_NV_SEED)
     "MBEDTLS_ENTROPY_NV_SEED",
 #endif /* MBEDTLS_ENTROPY_NV_SEED */
-#if defined(MBEDTLS_PSA_HAS_ITS_IO)
-    "MBEDTLS_PSA_HAS_ITS_IO",
-#endif /* MBEDTLS_PSA_HAS_ITS_IO */
 #if defined(MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER)
     "MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER",
 #endif /* MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER */
@@ -435,9 +432,9 @@
 #if defined(MBEDTLS_PSA_CRYPTO_SPM)
     "MBEDTLS_PSA_CRYPTO_SPM",
 #endif /* MBEDTLS_PSA_CRYPTO_SPM */
-#if defined(MBEDTLS_PSA_HAS_ITS_IO)
-    "MBEDTLS_PSA_HAS_ITS_IO",
-#endif /* MBEDTLS_PSA_HAS_ITS_IO */
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY)
+    "MBEDTLS_PSA_INJECT_ENTROPY",
+#endif /* MBEDTLS_PSA_INJECT_ENTROPY */
 #if defined(MBEDTLS_RSA_NO_CRT)
     "MBEDTLS_RSA_NO_CRT",
 #endif /* MBEDTLS_RSA_NO_CRT */
@@ -714,12 +711,9 @@
 #if defined(MBEDTLS_PSA_CRYPTO_STORAGE_C)
     "MBEDTLS_PSA_CRYPTO_STORAGE_C",
 #endif /* MBEDTLS_PSA_CRYPTO_STORAGE_C */
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C)
-    "MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C",
-#endif /* MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C */
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C)
-    "MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C",
-#endif /* MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C */
+#if defined(MBEDTLS_PSA_ITS_FILE_C)
+    "MBEDTLS_PSA_ITS_FILE_C",
+#endif /* MBEDTLS_PSA_ITS_FILE_C */
 #if defined(MBEDTLS_RIPEMD160_C)
     "MBEDTLS_RIPEMD160_C",
 #endif /* MBEDTLS_RIPEMD160_C */
diff --git a/programs/test/query_config.c b/programs/test/query_config.c
index 345d1ec..d940b0d 100644
--- a/programs/test/query_config.c
+++ b/programs/test/query_config.c
@@ -1138,14 +1138,6 @@
     }
 #endif /* MBEDTLS_ENTROPY_NV_SEED */
 
-#if defined(MBEDTLS_PSA_HAS_ITS_IO)
-    if( strcmp( "MBEDTLS_PSA_HAS_ITS_IO", config ) == 0 )
-    {
-        MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_HAS_ITS_IO );
-        return( 0 );
-    }
-#endif /* MBEDTLS_PSA_HAS_ITS_IO */
-
 #if defined(MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER)
     if( strcmp( "MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER", config ) == 0 )
     {
@@ -1202,13 +1194,13 @@
     }
 #endif /* MBEDTLS_PSA_CRYPTO_SPM */
 
-#if defined(MBEDTLS_PSA_HAS_ITS_IO)
-    if( strcmp( "MBEDTLS_PSA_HAS_ITS_IO", config ) == 0 )
+#if defined(MBEDTLS_PSA_INJECT_ENTROPY)
+    if( strcmp( "MBEDTLS_PSA_INJECT_ENTROPY", config ) == 0 )
     {
-        MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_HAS_ITS_IO );
+        MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_INJECT_ENTROPY );
         return( 0 );
     }
-#endif /* MBEDTLS_PSA_HAS_ITS_IO */
+#endif /* MBEDTLS_PSA_INJECT_ENTROPY */
 
 #if defined(MBEDTLS_RSA_NO_CRT)
     if( strcmp( "MBEDTLS_RSA_NO_CRT", config ) == 0 )
@@ -1946,21 +1938,13 @@
     }
 #endif /* MBEDTLS_PSA_CRYPTO_STORAGE_C */
 
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C)
-    if( strcmp( "MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C", config ) == 0 )
+#if defined(MBEDTLS_PSA_ITS_FILE_C)
+    if( strcmp( "MBEDTLS_PSA_ITS_FILE_C", config ) == 0 )
     {
-        MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C );
+        MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_ITS_FILE_C );
         return( 0 );
     }
-#endif /* MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C */
-
-#if defined(MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C)
-    if( strcmp( "MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C", config ) == 0 )
-    {
-        MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C );
-        return( 0 );
-    }
-#endif /* MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C */
+#endif /* MBEDTLS_PSA_ITS_FILE_C */
 
 #if defined(MBEDTLS_RIPEMD160_C)
     if( strcmp( "MBEDTLS_RIPEMD160_C", config ) == 0 )
diff --git a/scripts/config.pl b/scripts/config.pl
index 624deca..6927c4b 100755
--- a/scripts/config.pl
+++ b/scripts/config.pl
@@ -101,9 +101,8 @@
 MBEDTLS_NO_UDBL_DIVISION
 MBEDTLS_NO_64BIT_MULTIPLICATION
 MBEDTLS_PSA_CRYPTO_SPM
-MBEDTLS_PSA_HAS_ITS_IO
 MBEDTLS_PSA_CRYPTO_KEY_FILE_ID_ENCODES_OWNER
-MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
+MBEDTLS_PSA_INJECT_ENTROPY
 MBEDTLS_USE_PSA_CRYPTO
 _ALT\s*$
 );
@@ -125,9 +124,8 @@
 MBEDTLS_PLATFORM_TIME_ALT
 MBEDTLS_PLATFORM_FPRINTF_ALT
 MBEDTLS_PSA_CRYPTO_STORAGE_C
-MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
 MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
-MBEDTLS_PSA_HAS_ITS_IO
+MBEDTLS_PSA_ITS_FILE_C
 );
 
 # Things that should be enabled in "full" even if they match @excluded
diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt
index 76a4608..1b239a4 100644
--- a/tests/CMakeLists.txt
+++ b/tests/CMakeLists.txt
@@ -141,7 +141,7 @@
 add_test_suite(psa_crypto_metadata)
 add_test_suite(psa_crypto_persistent_key)
 add_test_suite(psa_crypto_slot_management)
-add_test_suite(psa_crypto_storage_file)
+add_test_suite(psa_its)
 add_test_suite(shax)
 add_test_suite(timing)
 add_test_suite(rsa)
diff --git a/tests/scripts/all.sh b/tests/scripts/all.sh
index 2806426..d995ba5 100755
--- a/tests/scripts/all.sh
+++ b/tests/scripts/all.sh
@@ -689,8 +689,9 @@
     scripts/config.pl unset MBEDTLS_ENTROPY_NV_SEED
     scripts/config.pl unset MBEDTLS_MEMORY_BUFFER_ALLOC_C
     scripts/config.pl unset MBEDTLS_FS_IO
-    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
     scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_C
+    scripts/config.pl unset MBEDTLS_PSA_ITS_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
     # Note, _DEFAULT_SOURCE needs to be defined for platforms using glibc version >2.19,
     # to re-enable platform integration features otherwise disabled in C99 builds
     make CC=gcc CFLAGS='-Werror -Wall -Wextra -std=c99 -pedantic -O0 -D_DEFAULT_SOURCE' lib programs
@@ -870,7 +871,8 @@
     scripts/config.pl unset MBEDTLS_NET_C
     scripts/config.pl unset MBEDTLS_TIMING_C
     scripts/config.pl unset MBEDTLS_FS_IO
-    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_ITS_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
     scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_C
     scripts/config.pl unset MBEDTLS_ENTROPY_NV_SEED
     scripts/config.pl set MBEDTLS_NO_PLATFORM_ENTROPY
@@ -889,7 +891,8 @@
     scripts/config.pl unset MBEDTLS_NET_C
     scripts/config.pl unset MBEDTLS_TIMING_C
     scripts/config.pl unset MBEDTLS_FS_IO
-    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_ITS_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
     scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_C
     scripts/config.pl unset MBEDTLS_ENTROPY_NV_SEED
     scripts/config.pl set MBEDTLS_NO_PLATFORM_ENTROPY
@@ -911,7 +914,8 @@
     scripts/config.pl unset MBEDTLS_NET_C
     scripts/config.pl unset MBEDTLS_TIMING_C
     scripts/config.pl unset MBEDTLS_FS_IO
-    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_ITS_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
     scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_C
     scripts/config.pl unset MBEDTLS_ENTROPY_NV_SEED
     scripts/config.pl set MBEDTLS_NO_PLATFORM_ENTROPY
@@ -933,7 +937,8 @@
     scripts/config.pl unset MBEDTLS_NET_C
     scripts/config.pl unset MBEDTLS_TIMING_C
     scripts/config.pl unset MBEDTLS_FS_IO
-    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_ITS_FILE_C
+    scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_ITS_C
     scripts/config.pl unset MBEDTLS_PSA_CRYPTO_STORAGE_C
     scripts/config.pl unset MBEDTLS_ENTROPY_NV_SEED
     scripts/config.pl unset MBEDTLS_HAVE_TIME
diff --git a/tests/suites/test_suite_psa_crypto_entropy.function b/tests/suites/test_suite_psa_crypto_entropy.function
index a14657e..91e210e 100644
--- a/tests/suites/test_suite_psa_crypto_entropy.function
+++ b/tests/suites/test_suite_psa_crypto_entropy.function
@@ -2,17 +2,38 @@
 #include <stdint.h>
 
 #include "psa/crypto.h"
-#include "psa_prot_internal_storage.h"
 #include "mbedtls/entropy.h"
 #include "mbedtls/entropy_poll.h"
 
+#if defined(MBEDTLS_PSA_ITS_FILE_C)
+#include <stdio.h>
+#else
+#include <psa/internal_trusted_storage.h>
+#endif
+
 /* Calculating the minimum allowed entropy size in bytes */
 #define MBEDTLS_PSA_INJECT_ENTROPY_MIN_SIZE MAX(MBEDTLS_ENTROPY_MIN_PLATFORM, MBEDTLS_ENTROPY_BLOCK_SIZE)
 
+/* Remove the entropy seed file. Since the library does not expose a way
+ * to do this (it would be a security risk if such a function was ever
+ * accessible in production), implement this functionality in a white-box
+ * manner. */
+psa_status_t remove_seed_file( void )
+{
+#if defined(MBEDTLS_PSA_ITS_FILE_C)
+    if( remove( "00000000ffffff52.psa_its" ) == 0 )
+        return( PSA_SUCCESS );
+    else
+        return( PSA_ERROR_DOES_NOT_EXIST );
+#else
+    return( psa_its_remove( PSA_CRYPTO_ITS_RANDOM_SEED_UID ) );
+#endif
+}
+
 /* END_HEADER */
 
 /* BEGIN_DEPENDENCIES
- * depends_on:MBEDTLS_ENTROPY_NV_SEED:MBEDTLS_PSA_HAS_ITS_IO:MBEDTLS_PSA_CRYPTO_C
+ * depends_on:MBEDTLS_PSA_INJECT_ENTROPY
  * END_DEPENDENCIES
  */
 
@@ -42,7 +63,7 @@
     {
         seed[i] = i;
     }
-    status =  psa_its_remove( PSA_CRYPTO_ITS_RANDOM_SEED_UID );
+    status =  remove_seed_file( );
     TEST_ASSERT( ( status == PSA_SUCCESS ) ||
                  ( status == PSA_ERROR_DOES_NOT_EXIST ) );
     status = mbedtls_psa_inject_entropy( seed, seed_length_a );
@@ -55,7 +76,7 @@
     TEST_ASSERT( memcmp( output, zeros, sizeof( output ) ) != 0 );
 exit:
     mbedtls_free( seed );
-    psa_its_remove( PSA_CRYPTO_ITS_RANDOM_SEED_UID );
+    remove_seed_file( );
     mbedtls_psa_crypto_free( );
 }
 /* END_CASE */
@@ -64,19 +85,19 @@
 void run_entropy_inject_with_crypto_init( )
 {
     psa_status_t status;
-    int i;
+    size_t i;
     uint8_t seed[MBEDTLS_PSA_INJECT_ENTROPY_MIN_SIZE] = { 0 };
     /* fill seed with some data */
     for( i = 0; i < sizeof( seed ); ++i )
     {
         seed[i] = i;
     }
-    status =  psa_its_remove( PSA_CRYPTO_ITS_RANDOM_SEED_UID );
+    status =  remove_seed_file( );
     TEST_ASSERT( ( status == PSA_SUCCESS ) ||
                  ( status == PSA_ERROR_DOES_NOT_EXIST ) );
     status = mbedtls_psa_inject_entropy( seed, sizeof( seed ) );
     PSA_ASSERT( status );
-    status =  psa_its_remove( PSA_CRYPTO_ITS_RANDOM_SEED_UID );
+    status =  remove_seed_file( );
     TEST_EQUAL( status, PSA_SUCCESS );
     status = psa_crypto_init( );
     TEST_EQUAL( status, PSA_ERROR_INSUFFICIENT_ENTROPY );
@@ -89,7 +110,7 @@
     status = mbedtls_psa_inject_entropy( seed, sizeof( seed ) );
     TEST_EQUAL( status, PSA_ERROR_NOT_PERMITTED );
 exit:
-    psa_its_remove( PSA_CRYPTO_ITS_RANDOM_SEED_UID );
+    remove_seed_file( );
     mbedtls_psa_crypto_free( );
 }
 /* END_CASE */
diff --git a/tests/suites/test_suite_psa_crypto_persistent_key.data b/tests/suites/test_suite_psa_crypto_persistent_key.data
index 613968d..f97a5e0 100644
--- a/tests/suites/test_suite_psa_crypto_persistent_key.data
+++ b/tests/suites/test_suite_psa_crypto_persistent_key.data
@@ -18,7 +18,7 @@
 
 # Not specific to files, but only run this test in an environment where the maximum size could be reached.
 Save maximum size persistent raw key
-depends_on:MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
+depends_on:MBEDTLS_PSA_ITS_FILE_C
 save_large_persistent_key:0:PSA_SUCCESS
 
 Save larger than maximum size persistent raw key, should fail
diff --git a/tests/suites/test_suite_psa_crypto_persistent_key.function b/tests/suites/test_suite_psa_crypto_persistent_key.function
index 2fa307e..90e10f6 100644
--- a/tests/suites/test_suite_psa_crypto_persistent_key.function
+++ b/tests/suites/test_suite_psa_crypto_persistent_key.function
@@ -2,7 +2,6 @@
 #include <stdint.h>
 #include "psa/crypto.h"
 #include "psa_crypto_storage.h"
-#include "psa_crypto_storage_backend.h"
 #include "mbedtls/md.h"
 
 #define PSA_KEY_STORAGE_MAGIC_HEADER "PSA\0KEY"
diff --git a/tests/suites/test_suite_psa_crypto_storage_file.data b/tests/suites/test_suite_psa_crypto_storage_file.data
deleted file mode 100644
index 4b068e1..0000000
--- a/tests/suites/test_suite_psa_crypto_storage_file.data
+++ /dev/null
@@ -1,43 +0,0 @@
-PSA Storage Load verify loaded file
-depends_on:MBEDTLS_FS_IO
-load_data_from_file:1:"deadbeef":1:4:PSA_SUCCESS
-
-PSA Storage Load check slots dont share state
-depends_on:MBEDTLS_FS_IO
-load_data_from_file:2:"deadbeef":1:4:PSA_ERROR_STORAGE_FAILURE
-
-PSA Storage Load zero length file
-depends_on:MBEDTLS_FS_IO
-load_data_from_file:1:"":1:1:PSA_SUCCESS
-
-PSA Storage Load less than capacity of data buffer
-depends_on:MBEDTLS_FS_IO
-load_data_from_file:1:"deadbeef":1:5:PSA_SUCCESS
-
-PSA Storage Load nonexistent file location, should fail
-depends_on:MBEDTLS_FS_IO
-load_data_from_file:1:"deadbeef":0:4:PSA_ERROR_STORAGE_FAILURE
-
-PSA Storage Store verify stored file
-depends_on:MBEDTLS_FS_IO
-write_data_to_file:"deadbeef":PSA_SUCCESS
-
-PSA Storage Store into preexisting location, should fail
-depends_on:MBEDTLS_FS_IO
-write_data_to_prexisting_file:"psa_key_slot_1":"deadbeef":PSA_ERROR_ALREADY_EXISTS
-
-PSA Storage Store, preexisting temp_location file, should succeed
-depends_on:MBEDTLS_FS_IO
-write_data_to_prexisting_file:"psa_key_slot_0":"deadbeef":PSA_SUCCESS
-
-PSA Storage Get data size verify data size
-depends_on:MBEDTLS_FS_IO
-get_file_size:"deadbeef":4:PSA_SUCCESS:1
-
-PSA Storage Get data size verify data size zero length file
-depends_on:MBEDTLS_FS_IO
-get_file_size:"":0:PSA_SUCCESS:1
-
-PSA Storage Get data size nonexistent file location, should fail
-depends_on:MBEDTLS_FS_IO
-get_file_size:"deadbeef":4:PSA_ERROR_DOES_NOT_EXIST:0
diff --git a/tests/suites/test_suite_psa_crypto_storage_file.function b/tests/suites/test_suite_psa_crypto_storage_file.function
deleted file mode 100644
index e596be1..0000000
--- a/tests/suites/test_suite_psa_crypto_storage_file.function
+++ /dev/null
@@ -1,157 +0,0 @@
-/* BEGIN_HEADER */
-#include <stdint.h>
-#include "psa/crypto.h"
-#include "psa_crypto_storage_backend.h"
-
-/* END_HEADER */
-
-/* BEGIN_DEPENDENCIES
- * depends_on:MBEDTLS_PSA_CRYPTO_C:MBEDTLS_PSA_CRYPTO_STORAGE_FILE_C
- * END_DEPENDENCIES
- */
-
-/* BEGIN_CASE */
-void load_data_from_file( int id_to_load_arg,
-                          data_t *data, int should_make_file,
-                          int capacity_arg, int expected_status )
-{
-    psa_key_id_t id_to_load = id_to_load_arg;
-    char slot_location[] = "psa_key_slot_1";
-    psa_status_t status;
-    int ret;
-    size_t file_size = 0;
-    uint8_t *loaded_data = NULL;
-    size_t capacity = (size_t) capacity_arg;
-
-    if( should_make_file == 1 )
-    {
-        /* Create a file with data contents, with mask permissions. */
-        FILE *file;
-        file = fopen( slot_location, "wb+" );
-        TEST_ASSERT( file != NULL );
-        file_size = fwrite( data->x, 1, data->len, file );
-        TEST_EQUAL( file_size, data->len );
-        ret = fclose( file );
-        TEST_EQUAL( ret, 0 );
-    }
-
-    /* Read from the file with psa_crypto_storage_load. */
-    ASSERT_ALLOC( loaded_data, capacity );
-    status = psa_crypto_storage_load( id_to_load, loaded_data, file_size );
-
-    /* Check we get the expected status. */
-    TEST_EQUAL( status, expected_status );
-    if( status != PSA_SUCCESS )
-        goto exit;
-
-    /* Check that the file data and data length is what we expect. */
-    ASSERT_COMPARE( data->x, data->len, loaded_data, file_size );
-
-exit:
-    mbedtls_free( loaded_data );
-    remove( slot_location );
-}
-/* END_CASE */
-
-/* BEGIN_CASE */
-void write_data_to_file( data_t *data, int expected_status )
-{
-    char slot_location[] = "psa_key_slot_1";
-    psa_status_t status;
-    int ret;
-    FILE *file;
-    size_t file_size;
-    size_t num_read;
-    uint8_t *loaded_data = NULL;
-
-    /* Write data to file. */
-    status = psa_crypto_storage_store( 1, data->x, data->len );
-
-    /* Check that we got the expected status. */
-    TEST_EQUAL( status, expected_status );
-    if( status != PSA_SUCCESS )
-        goto exit;
-
-    /* Check that the file length is what we expect */
-    file = fopen( slot_location, "rb" );
-    TEST_ASSERT( file != NULL );
-    fseek( file, 0, SEEK_END );
-    file_size = (size_t) ftell( file );
-    fseek( file, 0, SEEK_SET );
-    TEST_EQUAL( file_size, data->len );
-
-    /* Check that the file contents are what we expect */
-    ASSERT_ALLOC( loaded_data, data->len );
-
-    num_read = fread( loaded_data, 1, file_size, file );
-    TEST_EQUAL( num_read, file_size );
-    ASSERT_COMPARE( data->x, data->len, loaded_data, file_size );
-    ret = fclose( file );
-    TEST_EQUAL( ret, 0 );
-
-exit:
-    mbedtls_free( loaded_data );
-    remove( slot_location );
-}
-/* END_CASE */
-
-/* BEGIN_CASE */
-void get_file_size( data_t *data, int expected_data_length,
-                    int expected_status, int should_make_file )
-{
-    char slot_location[] = "psa_key_slot_1";
-    psa_status_t status;
-    int ret;
-    size_t file_size;
-
-    if( should_make_file )
-    {
-        /* Create a file with data contents, with mask permissions. */
-        FILE *file;
-        file = fopen( slot_location, "wb+" );
-        TEST_ASSERT( file != NULL );
-        file_size = fwrite( data->x, 1, data->len, file );
-        TEST_EQUAL( file_size, data->len );
-        ret = fclose( file );
-        TEST_EQUAL( ret, 0 );
-    }
-
-    /* Check get data size is what we expect */
-    status = psa_crypto_storage_get_data_length( 1, &file_size );
-    TEST_EQUAL( status, expected_status );
-    if( expected_status == PSA_SUCCESS )
-        TEST_EQUAL( file_size, (size_t)expected_data_length );
-
-exit:
-    remove( slot_location );
-}
-/* END_CASE */
-
-/* BEGIN_CASE */
-void write_data_to_prexisting_file( char *preexist_file_location,
-                                    data_t *data, int expected_status )
-{
-    char slot_location[] = "psa_key_slot_1";
-    psa_status_t status;
-    int ret;
-    FILE *file;
-
-    /* Create file first */
-    file = fopen( preexist_file_location, "wb" );
-    TEST_ASSERT( file != NULL );
-    ret = fclose( file );
-    TEST_EQUAL( ret, 0 );
-
-    /* Write data to file. */
-    status = psa_crypto_storage_store( 1, data->x, data->len );
-
-    /* Check that we got the expected status. */
-    TEST_EQUAL( status, expected_status );
-    if( status != PSA_SUCCESS )
-        goto exit;
-
-exit:
-    remove( preexist_file_location );
-    remove( slot_location );
-}
-/* END_CASE */
diff --git a/tests/suites/test_suite_psa_its.data b/tests/suites/test_suite_psa_its.data
new file mode 100644
index 0000000..63ca129
--- /dev/null
+++ b/tests/suites/test_suite_psa_its.data
@@ -0,0 +1,65 @@
+Set/get/remove 0 bytes
+set_get_remove:0:0:""
+
+Set/get/remove 42 bytes
+set_get_remove:0:0:"000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f20212223242526272829"
+
+Set/get/remove 1000 bytes
+set_get_remove:0:0:"6a07ecfcc7c7bfe0129d56d2dcf2955a12845b9e6e0034b0ed7226764261c6222a07b9f654deb682130eb1cd07ed298324e60a46f9c76c8a5a0be000c69e93dd81054ca21fbc6190cef7745e9d5436f70e20e10cbf111d1d40c9ceb83be108775199d81abaf0fecfe30eaa08e7ed82517cba939de4449f7ac5c730fcbbf56e691640b0129db0e178045dd2034262de9138873d9bdca57685146a3d516ff13c29e6628a00097435a8e10fef7faff62d2963c303a93793e2211d8604556fec08cd59c0f5bd1f22eea64be13e88b3f454781e83fe6e771d3d81eb2fbe2021e276f42a93db5343d767d854115e74f5e129a8036b1e81aced9872709d515e00bcf2098ccdee23006b0e836b27dc8aaf30f53fe58a31a6408abb79b13098c22e262a98040f9b09809a3b43bd42eb01cf1d17bbc8b4dfe51fa6573d4d8741943e3ae71a649e194c1218f2e20556c7d8cfe8c64d8cc1aa94531fbf638768c7d19b3c079299cf4f26ed3f964efb8fd23d82b4157a51f46da11156c74e2d6e2fd788869ebb52429e12a82da2ba083e2e74565026162f29ca22582da72a2698e7c5d958b919bc2cdfe12f50364ccfed30efd5cd120a7d5f196b2bd7f911bb44d5871eb3dedcd70ece7faf464988f9fe361f23d7244b1e08bee921d0f28bdb4912675809d099876d4d15b7d13ece356e1f2a5dce64feb3d6749a07a4f2b7721190e17a9ab2966e48b6d25187070b81eb45b1c44608b2f0e175958ba57fcf1b2cd145eea5fd4de858d157ddac69dfbb5d5d6f0c1691b0fae5a143b6e58cdf5000f28d74b3322670ed11e740c828c7bfad4e2f392012da3ac931ea26ed15fd003e604071f5900c6e1329d021805d50da9f1e732a49bcc292d9f8e07737cfd59442e8d7aaa813b18183a68e22bf6b4519545dd7d2d519db3652be4131bad4f4b0625dbaa749e979f6ee8c1b97803cb50a2fa20dc883eac932a824b777b226e15294de6a80be3ddef41478fe18172d64407a004de6bae18bc60e90c902c1cbb0e1633395b42391f5011be0d480541987609b0cd8d902ea29f86f73e7362340119323eb0ea4f672b70d6e9a9df5235f9f1965f5cb0c2998c5a7f4754e83eeda5d95fefbbaaa0875fe37b7ca461e7281cc5479162627c5a709b45fd9ddcde4dfb40659e1d70fa7361d9fc7de24f9b8b13259423fdae4dbb98d691db687467a5a7eb027a4a0552a03e430ac8a32de0c30160ba60a036d6b9db2d6182193283337b92e7438dc5d6eb4fa00200d8efa9127f1c3a32ac8e202262773aaa5a965c6b8035b2e5706c32a55511560429ddf1df4ac34076b7eedd9cf94b6915a894fdd9084ffe3db0e7040f382c3cd04f0484595de95865c36b6bf20f46a78cdfb37228acbeb218de798b9586f6d99a0cbae47e80d"
+
+Set/get/remove with flags
+set_get_remove:0:0x12345678:"abcdef"
+
+Overwrite 0 -> 3
+set_overwrite:0:0x12345678:"":0x01020304:"abcdef"
+
+Overwrite 3 -> 0
+set_overwrite:0:0x12345678:"abcdef":0x01020304:""
+
+Overwrite 3 -> 3
+set_overwrite:0:0x12345678:"123456":0x01020304:"abcdef"
+
+Overwrite 3 -> 18
+set_overwrite:0:0x12345678:"abcdef":0x01020304:"404142434445464748494a4b4c4d4e4f5051"
+
+Overwrite 18 -> 3
+set_overwrite:0:0x12345678:"404142434445464748494a4b4c4d4e4f5051":0x01020304:"abcdef"
+
+Multiple files
+set_multiple:0:5
+
+Non-existent file
+nonexistent:0:0
+
+Removed file
+nonexistent:0:1
+
+Get 0 bytes of 10 at 10
+get_at:0:"40414243444546474849":10:0:PSA_SUCCESS
+
+Get 1 byte of 10 at 9
+get_at:0:"40414243444546474849":9:1:PSA_SUCCESS
+
+Get 0 bytes of 10 at 0
+get_at:0:"40414243444546474849":0:0:PSA_SUCCESS
+
+Get 1 byte of 10 at 0
+get_at:0:"40414243444546474849":0:1:PSA_SUCCESS
+
+Get 2 bytes of 10 at 1
+get_at:0:"40414243444546474849":1:2:PSA_SUCCESS
+
+Get 1 byte of 10 at 10: out of range
+get_at:0:"40414243444546474849":10:1:PSA_ERROR_INVALID_ARGUMENT
+
+Get 1 byte of 10 at 11: out of range
+get_at:0:"40414243444546474849":11:1:PSA_ERROR_INVALID_ARGUMENT
+
+Get 0 bytes of 10 at 11: out of range
+get_at:0:"40414243444546474849":11:0:PSA_ERROR_INVALID_ARGUMENT
+
+Get -1 byte of 10 at 10: out of range
+get_at:0:"40414243444546474849":10:-1:PSA_ERROR_INVALID_ARGUMENT
+
+Get 1 byte of 10 at -1: out of range
+get_at:0:"40414243444546474849":-1:1:PSA_ERROR_INVALID_ARGUMENT
diff --git a/tests/suites/test_suite_psa_its.function b/tests/suites/test_suite_psa_its.function
new file mode 100644
index 0000000..867f64f
--- /dev/null
+++ b/tests/suites/test_suite_psa_its.function
@@ -0,0 +1,213 @@
+/* BEGIN_HEADER */
+#include "../library/psa_crypto_its.h"
+
+/* Internal definitions of the implementation, copied for the sake of
+ * some of the tests and of the cleanup code. */
+#define PSA_ITS_STORAGE_PREFIX ""
+#define PSA_ITS_STORAGE_FILENAME_PATTERN "%08lx%08lx"
+#define PSA_ITS_STORAGE_SUFFIX ".psa_its"
+#define PSA_ITS_STORAGE_FILENAME_LENGTH         \
+    ( sizeof( PSA_ITS_STORAGE_PREFIX ) - 1 + /*prefix without terminating 0*/ \
+      16 + /*UID (64-bit number in hex)*/                               \
+      sizeof( PSA_ITS_STORAGE_SUFFIX ) - 1 + /*suffix without terminating 0*/ \
+      1 /*terminating null byte*/ )
+#define PSA_ITS_STORAGE_TEMP \
+    PSA_ITS_STORAGE_PREFIX "tempfile" PSA_ITS_STORAGE_SUFFIX
+static void psa_its_fill_filename( psa_storage_uid_t uid, char *filename )
+{
+    /* Break up the UID into two 32-bit pieces so as not to rely on
+     * long long support in snprintf. */
+    mbedtls_snprintf( filename, PSA_ITS_STORAGE_FILENAME_LENGTH,
+                      "%s" PSA_ITS_STORAGE_FILENAME_PATTERN "%s",
+                      PSA_ITS_STORAGE_PREFIX,
+                      (unsigned long) ( uid >> 32 ),
+                      (unsigned long) ( uid & 0xffffffff ),
+                      PSA_ITS_STORAGE_SUFFIX );
+}
+
+/* Maximum uid used by the test, recorded so that cleanup() can delete
+ * all files. 0xffffffffffffffff is always cleaned up, so it does not
+ * need to and should not be taken into account for uid_max. */
+static psa_storage_uid_t uid_max = 0;
+
+static void cleanup( void )
+{
+    char filename[PSA_ITS_STORAGE_FILENAME_LENGTH];
+    psa_storage_uid_t uid;
+    for( uid = 0; uid < uid_max; uid++ )
+    {
+        psa_its_fill_filename( uid, filename );
+        remove( filename );
+    }
+    psa_its_fill_filename( (psa_storage_uid_t)( -1 ), filename );
+    remove( filename );
+    remove( PSA_ITS_STORAGE_TEMP );
+    uid_max = 0;
+}
+
+static psa_status_t psa_its_set_wrap( psa_storage_uid_t uid,
+                                      uint32_t data_length,
+                                      const void *p_data,
+                                      psa_storage_create_flags_t create_flags )
+{
+    if( uid_max != (psa_storage_uid_t)( -1 ) && uid_max < uid )
+        uid_max = uid;
+    return( psa_its_set( uid, data_length, p_data, create_flags ) );
+}
+
+/* END_HEADER */
+
+/* BEGIN_DEPENDENCIES
+ * depends_on:MBEDTLS_PSA_ITS_FILE_C
+ * END_DEPENDENCIES
+ */
+
+/* BEGIN_CASE */
+void set_get_remove( int uid_arg, int flags_arg, data_t *data )
+{
+    psa_storage_uid_t uid = uid_arg;
+    uint32_t flags = flags_arg;
+    struct psa_storage_info_t info;
+    unsigned char *buffer = NULL;
+
+    ASSERT_ALLOC( buffer, data->len );
+
+    PSA_ASSERT( psa_its_set_wrap( uid, data->len, data->x, flags ) );
+
+    PSA_ASSERT( psa_its_get_info( uid, &info ) );
+    TEST_ASSERT( info.size == data->len );
+    TEST_ASSERT( info.flags == flags );
+    PSA_ASSERT( psa_its_get( uid, 0, data->len, buffer ) );
+    ASSERT_COMPARE( data->x, data->len, buffer, data->len );
+
+    PSA_ASSERT( psa_its_remove( uid ) );
+
+exit:
+    mbedtls_free( buffer );
+    cleanup( );
+}
+/* END_CASE */
+
+/* BEGIN_CASE */
+void set_overwrite( int uid_arg,
+                    int flags1_arg, data_t *data1,
+                    int flags2_arg, data_t *data2 )
+{
+    psa_storage_uid_t uid = uid_arg;
+    uint32_t flags1 = flags1_arg;
+    uint32_t flags2 = flags2_arg;
+    struct psa_storage_info_t info;
+    unsigned char *buffer = NULL;
+
+    ASSERT_ALLOC( buffer, MAX( data1->len, data2->len ) );
+
+    PSA_ASSERT( psa_its_set_wrap( uid, data1->len, data1->x, flags1 ) );
+    PSA_ASSERT( psa_its_get_info( uid, &info ) );
+    TEST_ASSERT( info.size == data1->len );
+    TEST_ASSERT( info.flags == flags1 );
+    PSA_ASSERT( psa_its_get( uid, 0, data1->len, buffer ) );
+    ASSERT_COMPARE( data1->x, data1->len, buffer, data1->len );
+
+    PSA_ASSERT( psa_its_set_wrap( uid, data2->len, data2->x, flags2 ) );
+    PSA_ASSERT( psa_its_get_info( uid, &info ) );
+    TEST_ASSERT( info.size == data2->len );
+    TEST_ASSERT( info.flags == flags2 );
+    PSA_ASSERT( psa_its_get( uid, 0, data2->len, buffer ) );
+    ASSERT_COMPARE( data2->x, data2->len, buffer, data2->len );
+
+    PSA_ASSERT( psa_its_remove( uid ) );
+
+exit:
+    mbedtls_free( buffer );
+    cleanup( );
+}
+/* END_CASE */
+
+/* BEGIN_CASE */
+void set_multiple( int first_id, int count )
+{
+    psa_storage_uid_t uid0 = first_id;
+    psa_storage_uid_t uid;
+    char stored[40];
+    char retrieved[40];
+
+    memset( stored, '.', sizeof( stored ) );
+    for( uid = uid0; uid < uid0 + count; uid++ )
+    {
+        mbedtls_snprintf( stored, sizeof( stored ),
+                          "Content of file 0x%08lx", (unsigned long) uid );
+        PSA_ASSERT( psa_its_set_wrap( uid, sizeof( stored ), stored, 0 ) );
+    }
+
+    for( uid = uid0; uid < uid0 + count; uid++ )
+    {
+        mbedtls_snprintf( stored, sizeof( stored ),
+                          "Content of file 0x%08lx", (unsigned long) uid );
+        PSA_ASSERT( psa_its_get( uid, 0, sizeof( stored ), retrieved ) );
+        ASSERT_COMPARE( retrieved, sizeof( stored ),
+                        stored, sizeof( stored ) );
+        PSA_ASSERT( psa_its_remove( uid ) );
+        TEST_ASSERT( psa_its_get( uid, 0, 0, NULL ) ==
+                     PSA_ERROR_DOES_NOT_EXIST );
+    }
+
+exit:
+    cleanup( );
+}
+/* END_CASE */
+
+/* BEGIN_CASE */
+void nonexistent( int uid_arg, int create_and_remove )
+{
+    psa_storage_uid_t uid = uid_arg;
+    struct psa_storage_info_t info;
+
+    if( create_and_remove )
+    {
+        PSA_ASSERT( psa_its_set_wrap( uid, 0, NULL, 0 ) );
+        PSA_ASSERT( psa_its_remove( uid ) );
+    }
+
+    TEST_ASSERT( psa_its_remove( uid ) == PSA_ERROR_DOES_NOT_EXIST );
+    TEST_ASSERT( psa_its_get_info( uid, &info ) ==
+                 PSA_ERROR_DOES_NOT_EXIST );
+    TEST_ASSERT( psa_its_get( uid, 0, 0, NULL ) ==
+                 PSA_ERROR_DOES_NOT_EXIST );
+
+exit:
+    cleanup( );
+}
+/* END_CASE */
+
+/* BEGIN_CASE */
+void get_at( int uid_arg, data_t *data,
+             int offset, int length_arg,
+             int expected_status )
+{
+    psa_storage_uid_t uid = uid_arg;
+    unsigned char *buffer = NULL;
+    psa_status_t status;
+    size_t length = length_arg >= 0 ? length_arg : 0;
+    unsigned char *trailer;
+    size_t i;
+
+    ASSERT_ALLOC( buffer, length + 16 );
+    trailer = buffer + length;
+    memset( trailer, '-', 16 );
+
+    PSA_ASSERT( psa_its_set_wrap( uid, data->len, data->x, 0 ) );
+
+    status = psa_its_get( uid, offset, length_arg, buffer );
+    TEST_ASSERT( status == (psa_status_t) expected_status );
+    if( status == PSA_SUCCESS )
+        ASSERT_COMPARE( data->x + offset, length,
+                        buffer, length );
+    for( i = 0; i < 16; i++ )
+        TEST_ASSERT( trailer[i] == '-' );
+    PSA_ASSERT( psa_its_remove( uid ) );
+
+exit:
+    mbedtls_free( buffer );
+    cleanup( );
+}
+/* END_CASE */
diff --git a/visualc/VS2010/mbedTLS.vcxproj b/visualc/VS2010/mbedTLS.vcxproj
index bb92d8f..c56e976 100644
--- a/visualc/VS2010/mbedTLS.vcxproj
+++ b/visualc/VS2010/mbedTLS.vcxproj
@@ -238,10 +238,10 @@
     <ClInclude Include="..\..\include\psa\crypto_values.h" />

     <ClInclude Include="..\..\library/psa_crypto_core.h" />

     <ClInclude Include="..\..\library/psa_crypto_invasive.h" />

+    <ClInclude Include="..\..\library/psa_crypto_its.h" />

     <ClInclude Include="..\..\library/psa_crypto_service_integration.h" />

     <ClInclude Include="..\..\library/psa_crypto_slot_management.h" />

     <ClInclude Include="..\..\library/psa_crypto_storage.h" />

-    <ClInclude Include="..\..\library/psa_crypto_storage_backend.h" />

   </ItemGroup>

   <ItemGroup>

     <ClCompile Include="..\..\library\aes.c" />

@@ -301,8 +301,7 @@
     <ClCompile Include="..\..\library\psa_crypto.c" />

     <ClCompile Include="..\..\library\psa_crypto_slot_management.c" />

     <ClCompile Include="..\..\library\psa_crypto_storage.c" />

-    <ClCompile Include="..\..\library\psa_crypto_storage_file.c" />

-    <ClCompile Include="..\..\library\psa_crypto_storage_its.c" />

+    <ClCompile Include="..\..\library\psa_its_file.c" />

     <ClCompile Include="..\..\library\ripemd160.c" />

     <ClCompile Include="..\..\library\rsa.c" />

     <ClCompile Include="..\..\library\rsa_internal.c" />