Merge pull request #3895 from gilles-peskine-arm/psa-external-random
Alternative random generator support for PSA
This commit is contained in:
commit
a51e1dbe76
5
ChangeLog.d/psa-crypto-hmac-drbg.txt
Normal file
5
ChangeLog.d/psa-crypto-hmac-drbg.txt
Normal file
@ -0,0 +1,5 @@
|
||||
Features
|
||||
* The PSA crypto subsystem can now use HMAC_DRBG instead of CTR_DRBG.
|
||||
CTR_DRBG is used by default if it is available, but you can override
|
||||
this choice by setting MBEDTLS_PSA_HMAC_DRBG_MD_TYPE at compile time.
|
||||
Fix #3354.
|
@ -572,10 +572,11 @@
|
||||
#error "MBEDTLS_PLATFORM_NV_SEED_WRITE_MACRO and MBEDTLS_PLATFORM_STD_NV_SEED_WRITE cannot be defined simultaneously"
|
||||
#endif
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_C) && \
|
||||
!( defined(MBEDTLS_CTR_DRBG_C) && \
|
||||
defined(MBEDTLS_ENTROPY_C) )
|
||||
#error "MBEDTLS_PSA_CRYPTO_C defined, but not all prerequisites"
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_C) && \
|
||||
!( ( ( defined(MBEDTLS_CTR_DRBG_C) || defined(MBEDTLS_HMAC_DRBG_C) ) && \
|
||||
defined(MBEDTLS_ENTROPY_C) ) || \
|
||||
defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG) )
|
||||
#error "MBEDTLS_PSA_CRYPTO_C defined, but not all prerequisites (missing RNG)"
|
||||
#endif
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_SPM) && !defined(MBEDTLS_PSA_CRYPTO_C)
|
||||
@ -604,6 +605,11 @@
|
||||
#error "MBEDTLS_PSA_INJECT_ENTROPY is not compatible with actual entropy sources"
|
||||
#endif
|
||||
|
||||
#if defined(MBEDTLS_PSA_INJECT_ENTROPY) && \
|
||||
defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
#error "MBEDTLS_PSA_INJECT_ENTROPY is not compatible with MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG"
|
||||
#endif
|
||||
|
||||
#if defined(MBEDTLS_PSA_ITS_FILE_C) && \
|
||||
!defined(MBEDTLS_FS_IO)
|
||||
#error "MBEDTLS_PSA_ITS_FILE_C defined, but not all prerequisites"
|
||||
|
@ -1337,6 +1337,44 @@
|
||||
*/
|
||||
//#define MBEDTLS_PSA_CRYPTO_DRIVERS
|
||||
|
||||
/** \def MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG
|
||||
*
|
||||
* Make the PSA Crypto module use an external random generator provided
|
||||
* by a driver, instead of Mbed TLS's entropy and DRBG modules.
|
||||
*
|
||||
* \note This random generator must deliver random numbers with cryptographic
|
||||
* quality and high performance. It must supply unpredictable numbers
|
||||
* with a uniform distribution. The implementation of this function
|
||||
* is responsible for ensuring that the random generator is seeded
|
||||
* with sufficient entropy. If you have a hardware TRNG which is slow
|
||||
* or delivers non-uniform output, declare it as an entropy source
|
||||
* with mbedtls_entropy_add_source() instead of enabling this option.
|
||||
*
|
||||
* If you enable this option, you must configure the type
|
||||
* ::mbedtls_psa_external_random_context_t in psa/crypto_platform.h
|
||||
* and define a function called mbedtls_psa_external_get_random()
|
||||
* with the following prototype:
|
||||
* ```
|
||||
* psa_status_t mbedtls_psa_external_get_random(
|
||||
* mbedtls_psa_external_random_context_t *context,
|
||||
* uint8_t *output, size_t output_size, size_t *output_length);
|
||||
* );
|
||||
* ```
|
||||
* The \c context value is initialized to 0 before the first call.
|
||||
* The function must fill the \c output buffer with \p output_size bytes
|
||||
* of random data and set \c *output_length to \p output_size.
|
||||
*
|
||||
* Requires: MBEDTLS_PSA_CRYPTO_C
|
||||
*
|
||||
* \warning If you enable this option, code that uses the PSA cryptography
|
||||
* interface will not use any of the entropy sources set up for
|
||||
* the entropy module, nor the NV seed that MBEDTLS_ENTROPY_NV_SEED
|
||||
* enables.
|
||||
*
|
||||
* \note This option is experimental and may be removed without notice.
|
||||
*/
|
||||
//#define MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG
|
||||
|
||||
/**
|
||||
* \def MBEDTLS_PSA_CRYPTO_SPM
|
||||
*
|
||||
@ -3115,7 +3153,9 @@
|
||||
*
|
||||
* Module: library/psa_crypto.c
|
||||
*
|
||||
* Requires: MBEDTLS_CTR_DRBG_C, MBEDTLS_ENTROPY_C
|
||||
* Requires: either MBEDTLS_CTR_DRBG_C and MBEDTLS_ENTROPY_C,
|
||||
* or MBEDTLS_HMAC_DRBG_C and MBEDTLS_ENTROPY_C,
|
||||
* or MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG.
|
||||
*
|
||||
*/
|
||||
#define MBEDTLS_PSA_CRYPTO_C
|
||||
@ -3603,6 +3643,19 @@
|
||||
*/
|
||||
//#define MBEDTLS_PARAM_FAILED( cond ) assert( cond )
|
||||
|
||||
/* PSA options */
|
||||
/**
|
||||
* Use HMAC_DRBG with the specified hash algorithm for HMAC_DRBG for the
|
||||
* PSA crypto subsystem.
|
||||
*
|
||||
* If this option is unset:
|
||||
* - If CTR_DRBG is available, the PSA subsystem uses it rather than HMAC_DRBG.
|
||||
* - Otherwise, the PSA subsystem uses HMAC_DRBG with either
|
||||
* #MBEDTLS_MD_SHA512 or #MBEDTLS_MD_SHA256 based on availability and
|
||||
* on unspecified heuristics.
|
||||
*/
|
||||
//#define MBEDTLS_PSA_HMAC_DRBG_MD_TYPE MBEDTLS_MD_SHA256
|
||||
|
||||
/* SSL Cache options */
|
||||
//#define MBEDTLS_SSL_CACHE_DEFAULT_TIMEOUT 86400 /**< 1 day */
|
||||
//#define MBEDTLS_SSL_CACHE_DEFAULT_MAX_ENTRIES 50 /**< Maximum entries in cache */
|
||||
|
@ -649,6 +649,57 @@ mbedtls_ecp_group_id mbedtls_ecc_group_of_psa( psa_ecc_family_t curve,
|
||||
|
||||
/**@}*/
|
||||
|
||||
/** \defgroup psa_external_rng External random generator
|
||||
* @{
|
||||
*/
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
/** External random generator function, implemented by the platform.
|
||||
*
|
||||
* When the compile-time option #MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG is enabled,
|
||||
* this function replaces Mbed TLS's entropy and DRBG modules for all
|
||||
* random generation triggered via PSA crypto interfaces.
|
||||
*
|
||||
* \note This random generator must deliver random numbers with cryptographic
|
||||
* quality and high performance. It must supply unpredictable numbers
|
||||
* with a uniform distribution. The implementation of this function
|
||||
* is responsible for ensuring that the random generator is seeded
|
||||
* with sufficient entropy. If you have a hardware TRNG which is slow
|
||||
* or delivers non-uniform output, declare it as an entropy source
|
||||
* with mbedtls_entropy_add_source() instead of enabling this option.
|
||||
*
|
||||
* \param[in,out] context Pointer to the random generator context.
|
||||
* This is all-bits-zero on the first call
|
||||
* and preserved between successive calls.
|
||||
* \param[out] output Output buffer. On success, this buffer
|
||||
* contains random data with a uniform
|
||||
* distribution.
|
||||
* \param output_size The size of the \p output buffer in bytes.
|
||||
* \param[out] output_length On success, set this value to \p output_size.
|
||||
*
|
||||
* \retval #PSA_SUCCESS
|
||||
* Success. The output buffer contains \p output_size bytes of
|
||||
* cryptographic-quality random data, and \c *output_length is
|
||||
* set to \p output_size.
|
||||
* \retval #PSA_ERROR_INSUFFICIENT_ENTROPY
|
||||
* The random generator requires extra entropy and there is no
|
||||
* way to obtain entropy under current environment conditions.
|
||||
* This error should not happen under normal circumstances since
|
||||
* this function is responsible for obtaining as much entropy as
|
||||
* it needs. However implementations of this function may return
|
||||
* #PSA_ERROR_INSUFFICIENT_ENTROPY if there is no way to obtain
|
||||
* entropy without blocking indefinitely.
|
||||
* \retval #PSA_ERROR_HARDWARE_FAILURE
|
||||
* A failure of the random generator hardware that isn't covered
|
||||
* by #PSA_ERROR_INSUFFICIENT_ENTROPY.
|
||||
*/
|
||||
psa_status_t mbedtls_psa_external_get_random(
|
||||
mbedtls_psa_external_random_context_t *context,
|
||||
uint8_t *output, size_t output_size, size_t *output_length );
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
/**@}*/
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
@ -81,4 +81,19 @@ static inline int mbedtls_key_owner_id_equal( mbedtls_key_owner_id_t id1,
|
||||
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_KEY_ID_ENCODES_OWNER */
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
/** The type of the context passed to mbedtls_psa_external_get_random().
|
||||
*
|
||||
* Mbed TLS initializes the context to all-bits-zero before calling
|
||||
* mbedtls_psa_external_get_random() for the first time.
|
||||
*
|
||||
* The definition of this type in the Mbed TLS source code is for
|
||||
* demonstration purposes. Implementers of mbedtls_psa_external_get_random()
|
||||
* are expected to replace it with a custom definition.
|
||||
*/
|
||||
typedef struct {
|
||||
uintptr_t opaque[2];
|
||||
} mbedtls_psa_external_random_context_t;
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
#endif /* PSA_CRYPTO_PLATFORM_H */
|
||||
|
@ -40,6 +40,8 @@
|
||||
* stored keys. */
|
||||
#include "psa_crypto_storage.h"
|
||||
|
||||
#include "psa_crypto_random_impl.h"
|
||||
|
||||
#include <assert.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@ -49,6 +51,7 @@
|
||||
#define mbedtls_free free
|
||||
#endif
|
||||
|
||||
#include "mbedtls/aes.h"
|
||||
#include "mbedtls/arc4.h"
|
||||
#include "mbedtls/asn1.h"
|
||||
#include "mbedtls/asn1write.h"
|
||||
@ -60,7 +63,6 @@
|
||||
#include "mbedtls/cipher.h"
|
||||
#include "mbedtls/ccm.h"
|
||||
#include "mbedtls/cmac.h"
|
||||
#include "mbedtls/ctr_drbg.h"
|
||||
#include "mbedtls/des.h"
|
||||
#include "mbedtls/ecdh.h"
|
||||
#include "mbedtls/ecp.h"
|
||||
@ -115,16 +117,18 @@ static int key_type_is_raw_bytes( psa_key_type_t type )
|
||||
|
||||
typedef struct
|
||||
{
|
||||
void (* entropy_init )( mbedtls_entropy_context *ctx );
|
||||
void (* entropy_free )( mbedtls_entropy_context *ctx );
|
||||
mbedtls_entropy_context entropy;
|
||||
mbedtls_ctr_drbg_context ctr_drbg;
|
||||
mbedtls_psa_random_context_t rng;
|
||||
unsigned initialized : 1;
|
||||
unsigned rng_state : 2;
|
||||
} psa_global_data_t;
|
||||
|
||||
static psa_global_data_t global_data;
|
||||
|
||||
#if !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
mbedtls_psa_drbg_context_t *const mbedtls_psa_random_state =
|
||||
&global_data.rng.drbg;
|
||||
#endif
|
||||
|
||||
#define GUARD_MODULE_INITIALIZED \
|
||||
if( global_data.initialized == 0 ) \
|
||||
return( PSA_ERROR_BAD_STATE );
|
||||
@ -214,6 +218,10 @@ psa_status_t mbedtls_to_psa_error( int ret )
|
||||
case MBEDTLS_ERR_CMAC_HW_ACCEL_FAILED:
|
||||
return( PSA_ERROR_HARDWARE_FAILURE );
|
||||
|
||||
#if !( defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG) || \
|
||||
defined(MBEDTLS_PSA_HMAC_DRBG_MD_TYPE) )
|
||||
/* Only check CTR_DRBG error codes if underlying mbedtls_xxx
|
||||
* functions are passed a CTR_DRBG instance. */
|
||||
case MBEDTLS_ERR_CTR_DRBG_ENTROPY_SOURCE_FAILED:
|
||||
return( PSA_ERROR_INSUFFICIENT_ENTROPY );
|
||||
case MBEDTLS_ERR_CTR_DRBG_REQUEST_TOO_BIG:
|
||||
@ -221,6 +229,7 @@ psa_status_t mbedtls_to_psa_error( int ret )
|
||||
return( PSA_ERROR_NOT_SUPPORTED );
|
||||
case MBEDTLS_ERR_CTR_DRBG_FILE_IO_ERROR:
|
||||
return( PSA_ERROR_INSUFFICIENT_ENTROPY );
|
||||
#endif
|
||||
|
||||
case MBEDTLS_ERR_DES_INVALID_INPUT_LENGTH:
|
||||
return( PSA_ERROR_NOT_SUPPORTED );
|
||||
@ -239,6 +248,19 @@ psa_status_t mbedtls_to_psa_error( int ret )
|
||||
case MBEDTLS_ERR_GCM_HW_ACCEL_FAILED:
|
||||
return( PSA_ERROR_HARDWARE_FAILURE );
|
||||
|
||||
#if !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG) && \
|
||||
defined(MBEDTLS_PSA_HMAC_DRBG_MD_TYPE)
|
||||
/* Only check HMAC_DRBG error codes if underlying mbedtls_xxx
|
||||
* functions are passed a HMAC_DRBG instance. */
|
||||
case MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED:
|
||||
return( PSA_ERROR_INSUFFICIENT_ENTROPY );
|
||||
case MBEDTLS_ERR_HMAC_DRBG_REQUEST_TOO_BIG:
|
||||
case MBEDTLS_ERR_HMAC_DRBG_INPUT_TOO_BIG:
|
||||
return( PSA_ERROR_NOT_SUPPORTED );
|
||||
case MBEDTLS_ERR_HMAC_DRBG_FILE_IO_ERROR:
|
||||
return( PSA_ERROR_INSUFFICIENT_ENTROPY );
|
||||
#endif
|
||||
|
||||
case MBEDTLS_ERR_MD2_HW_ACCEL_FAILED:
|
||||
case MBEDTLS_ERR_MD4_HW_ACCEL_FAILED:
|
||||
case MBEDTLS_ERR_MD5_HW_ACCEL_FAILED:
|
||||
@ -867,7 +889,7 @@ static psa_status_t psa_export_ecp_key( psa_key_type_t type,
|
||||
/* Calculate the public key */
|
||||
status = mbedtls_to_psa_error(
|
||||
mbedtls_ecp_mul( &ecp->grp, &ecp->Q, &ecp->d, &ecp->grp.G,
|
||||
mbedtls_ctr_drbg_random, &global_data.ctr_drbg ) );
|
||||
mbedtls_psa_get_random, MBEDTLS_PSA_RANDOM_STATE ) );
|
||||
if( status != PSA_SUCCESS )
|
||||
return( status );
|
||||
}
|
||||
@ -3682,8 +3704,8 @@ static psa_status_t psa_rsa_sign( mbedtls_rsa_context *rsa,
|
||||
mbedtls_rsa_set_padding( rsa, MBEDTLS_RSA_PKCS_V15,
|
||||
MBEDTLS_MD_NONE );
|
||||
ret = mbedtls_rsa_pkcs1_sign( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PRIVATE,
|
||||
md_alg,
|
||||
(unsigned int) hash_length,
|
||||
@ -3697,8 +3719,8 @@ static psa_status_t psa_rsa_sign( mbedtls_rsa_context *rsa,
|
||||
{
|
||||
mbedtls_rsa_set_padding( rsa, MBEDTLS_RSA_PKCS_V21, md_alg );
|
||||
ret = mbedtls_rsa_rsassa_pss_sign( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PRIVATE,
|
||||
MBEDTLS_MD_NONE,
|
||||
(unsigned int) hash_length,
|
||||
@ -3740,8 +3762,8 @@ static psa_status_t psa_rsa_verify( mbedtls_rsa_context *rsa,
|
||||
mbedtls_rsa_set_padding( rsa, MBEDTLS_RSA_PKCS_V15,
|
||||
MBEDTLS_MD_NONE );
|
||||
ret = mbedtls_rsa_pkcs1_verify( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PUBLIC,
|
||||
md_alg,
|
||||
(unsigned int) hash_length,
|
||||
@ -3755,8 +3777,8 @@ static psa_status_t psa_rsa_verify( mbedtls_rsa_context *rsa,
|
||||
{
|
||||
mbedtls_rsa_set_padding( rsa, MBEDTLS_RSA_PKCS_V21, md_alg );
|
||||
ret = mbedtls_rsa_rsassa_pss_verify( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PUBLIC,
|
||||
MBEDTLS_MD_NONE,
|
||||
(unsigned int) hash_length,
|
||||
@ -3813,8 +3835,8 @@ static psa_status_t psa_ecdsa_sign( mbedtls_ecp_keypair *ecp,
|
||||
MBEDTLS_MPI_CHK( mbedtls_ecdsa_sign_det_ext( &ecp->grp, &r, &s,
|
||||
&ecp->d, hash,
|
||||
hash_length, md_alg,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg ) );
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE ) );
|
||||
}
|
||||
else
|
||||
#endif /* defined(MBEDTLS_PSA_BUILTIN_ALG_DETERMINISTIC_ECDSA) */
|
||||
@ -3822,8 +3844,8 @@ static psa_status_t psa_ecdsa_sign( mbedtls_ecp_keypair *ecp,
|
||||
(void) alg;
|
||||
MBEDTLS_MPI_CHK( mbedtls_ecdsa_sign( &ecp->grp, &r, &s, &ecp->d,
|
||||
hash, hash_length,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg ) );
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE ) );
|
||||
}
|
||||
|
||||
MBEDTLS_MPI_CHK( mbedtls_mpi_write_binary( &r,
|
||||
@ -3868,7 +3890,7 @@ static psa_status_t psa_ecdsa_verify( mbedtls_ecp_keypair *ecp,
|
||||
{
|
||||
MBEDTLS_MPI_CHK(
|
||||
mbedtls_ecp_mul( &ecp->grp, &ecp->Q, &ecp->d, &ecp->grp.G,
|
||||
mbedtls_ctr_drbg_random, &global_data.ctr_drbg ) );
|
||||
mbedtls_psa_get_random, MBEDTLS_PSA_RANDOM_STATE ) );
|
||||
}
|
||||
|
||||
ret = mbedtls_ecdsa_verify( &ecp->grp, hash, hash_length,
|
||||
@ -4168,8 +4190,8 @@ psa_status_t psa_asymmetric_encrypt( mbedtls_svc_key_id_t key,
|
||||
{
|
||||
status = mbedtls_to_psa_error(
|
||||
mbedtls_rsa_pkcs1_encrypt( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PUBLIC,
|
||||
input_length,
|
||||
input,
|
||||
@ -4183,8 +4205,8 @@ psa_status_t psa_asymmetric_encrypt( mbedtls_svc_key_id_t key,
|
||||
psa_rsa_oaep_set_padding_mode( alg, rsa );
|
||||
status = mbedtls_to_psa_error(
|
||||
mbedtls_rsa_rsaes_oaep_encrypt( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PUBLIC,
|
||||
salt, salt_length,
|
||||
input_length,
|
||||
@ -4275,8 +4297,8 @@ psa_status_t psa_asymmetric_decrypt( mbedtls_svc_key_id_t key,
|
||||
{
|
||||
status = mbedtls_to_psa_error(
|
||||
mbedtls_rsa_pkcs1_decrypt( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PRIVATE,
|
||||
output_length,
|
||||
input,
|
||||
@ -4291,8 +4313,8 @@ psa_status_t psa_asymmetric_decrypt( mbedtls_svc_key_id_t key,
|
||||
psa_rsa_oaep_set_padding_mode( alg, rsa );
|
||||
status = mbedtls_to_psa_error(
|
||||
mbedtls_rsa_rsaes_oaep_decrypt( rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
MBEDTLS_RSA_PRIVATE,
|
||||
salt, salt_length,
|
||||
output_length,
|
||||
@ -4526,8 +4548,8 @@ psa_status_t psa_cipher_generate_iv( psa_cipher_operation_t *operation,
|
||||
status = PSA_ERROR_BUFFER_TOO_SMALL;
|
||||
goto exit;
|
||||
}
|
||||
ret = mbedtls_ctr_drbg_random( &global_data.ctr_drbg,
|
||||
iv, operation->iv_size );
|
||||
ret = mbedtls_psa_get_random( MBEDTLS_PSA_RANDOM_STATE,
|
||||
iv, operation->iv_size );
|
||||
if( ret != 0 )
|
||||
{
|
||||
status = mbedtls_to_psa_error( ret );
|
||||
@ -6142,8 +6164,8 @@ static psa_status_t psa_key_agreement_ecdh( const uint8_t *peer_key,
|
||||
mbedtls_ecdh_calc_secret( &ecdh,
|
||||
shared_secret_length,
|
||||
shared_secret, shared_secret_size,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg ) );
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE ) );
|
||||
if( status != PSA_SUCCESS )
|
||||
goto exit;
|
||||
if( PSA_BITS_TO_BYTES( bits ) != *shared_secret_length )
|
||||
@ -6321,31 +6343,139 @@ exit:
|
||||
}
|
||||
|
||||
|
||||
|
||||
/****************************************************************/
|
||||
/* Random generation */
|
||||
/****************************************************************/
|
||||
|
||||
/** Initialize the PSA random generator.
|
||||
*/
|
||||
static void mbedtls_psa_random_init( mbedtls_psa_random_context_t *rng )
|
||||
{
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
memset( rng, 0, sizeof( *rng ) );
|
||||
#else /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
/* Set default configuration if
|
||||
* mbedtls_psa_crypto_configure_entropy_sources() hasn't been called. */
|
||||
if( rng->entropy_init == NULL )
|
||||
rng->entropy_init = mbedtls_entropy_init;
|
||||
if( rng->entropy_free == NULL )
|
||||
rng->entropy_free = mbedtls_entropy_free;
|
||||
|
||||
rng->entropy_init( &rng->entropy );
|
||||
#if defined(MBEDTLS_PSA_INJECT_ENTROPY) && \
|
||||
defined(MBEDTLS_NO_DEFAULT_ENTROPY_SOURCES)
|
||||
/* The PSA entropy injection feature depends on using NV seed as an entropy
|
||||
* source. Add NV seed as an entropy source for PSA entropy injection. */
|
||||
mbedtls_entropy_add_source( &rng->entropy,
|
||||
mbedtls_nv_seed_poll, NULL,
|
||||
MBEDTLS_ENTROPY_BLOCK_SIZE,
|
||||
MBEDTLS_ENTROPY_SOURCE_STRONG );
|
||||
#endif
|
||||
|
||||
mbedtls_psa_drbg_init( MBEDTLS_PSA_RANDOM_STATE );
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
}
|
||||
|
||||
/** Deinitialize the PSA random generator.
|
||||
*/
|
||||
static void mbedtls_psa_random_free( mbedtls_psa_random_context_t *rng )
|
||||
{
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
memset( rng, 0, sizeof( *rng ) );
|
||||
#else /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
mbedtls_psa_drbg_free( MBEDTLS_PSA_RANDOM_STATE );
|
||||
rng->entropy_free( &rng->entropy );
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
}
|
||||
|
||||
/** Seed the PSA random generator.
|
||||
*/
|
||||
static psa_status_t mbedtls_psa_random_seed( mbedtls_psa_random_context_t *rng )
|
||||
{
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
/* Do nothing: the external RNG seeds itself. */
|
||||
(void) rng;
|
||||
return( PSA_SUCCESS );
|
||||
#else /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
const unsigned char drbg_seed[] = "PSA";
|
||||
int ret = mbedtls_psa_drbg_seed( &rng->entropy,
|
||||
drbg_seed, sizeof( drbg_seed ) - 1 );
|
||||
return mbedtls_to_psa_error( ret );
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
}
|
||||
|
||||
psa_status_t psa_generate_random( uint8_t *output,
|
||||
size_t output_size )
|
||||
{
|
||||
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
|
||||
GUARD_MODULE_INITIALIZED;
|
||||
|
||||
while( output_size > MBEDTLS_CTR_DRBG_MAX_REQUEST )
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
|
||||
size_t output_length = 0;
|
||||
psa_status_t status = mbedtls_psa_external_get_random( &global_data.rng,
|
||||
output, output_size,
|
||||
&output_length );
|
||||
if( status != PSA_SUCCESS )
|
||||
return( status );
|
||||
/* Breaking up a request into smaller chunks is currently not supported
|
||||
* for the extrernal RNG interface. */
|
||||
if( output_length != output_size )
|
||||
return( PSA_ERROR_INSUFFICIENT_ENTROPY );
|
||||
return( PSA_SUCCESS );
|
||||
|
||||
#else /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
while( output_size > 0 )
|
||||
{
|
||||
ret = mbedtls_ctr_drbg_random( &global_data.ctr_drbg,
|
||||
output,
|
||||
MBEDTLS_CTR_DRBG_MAX_REQUEST );
|
||||
size_t request_size =
|
||||
( output_size > MBEDTLS_PSA_RANDOM_MAX_REQUEST ?
|
||||
MBEDTLS_PSA_RANDOM_MAX_REQUEST :
|
||||
output_size );
|
||||
int ret = mbedtls_psa_get_random( MBEDTLS_PSA_RANDOM_STATE,
|
||||
output, request_size );
|
||||
if( ret != 0 )
|
||||
return( mbedtls_to_psa_error( ret ) );
|
||||
output += MBEDTLS_CTR_DRBG_MAX_REQUEST;
|
||||
output_size -= MBEDTLS_CTR_DRBG_MAX_REQUEST;
|
||||
output_size -= request_size;
|
||||
output += request_size;
|
||||
}
|
||||
|
||||
ret = mbedtls_ctr_drbg_random( &global_data.ctr_drbg, output, output_size );
|
||||
return( mbedtls_to_psa_error( ret ) );
|
||||
return( PSA_SUCCESS );
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
}
|
||||
|
||||
/* Wrapper function allowing the classic API to use the PSA RNG.
|
||||
*
|
||||
* `mbedtls_psa_get_random(MBEDTLS_PSA_RANDOM_STATE, ...)` calls
|
||||
* `psa_generate_random(...)`. The state parameter is ignored since the
|
||||
* PSA API doesn't support passing an explicit state.
|
||||
*
|
||||
* In the non-external case, psa_generate_random() calls an
|
||||
* `mbedtls_xxx_drbg_random` function which has exactly the same signature
|
||||
* and semantics as mbedtls_psa_get_random(). As an optimization,
|
||||
* instead of doing this back-and-forth between the PSA API and the
|
||||
* classic API, psa_crypto_random_impl.h defines `mbedtls_psa_get_random`
|
||||
* as a constant function pointer to `mbedtls_xxx_drbg_random`.
|
||||
*/
|
||||
#if defined (MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
int mbedtls_psa_get_random( void *p_rng,
|
||||
unsigned char *output,
|
||||
size_t output_size )
|
||||
{
|
||||
/* This function takes a pointer to the RNG state because that's what
|
||||
* classic mbedtls functions using an RNG expect. The PSA RNG manages
|
||||
* its own state internally and doesn't let the caller access that state.
|
||||
* So we just ignore the state parameter, and in practice we'll pass
|
||||
* NULL. */
|
||||
(void) p_rng;
|
||||
psa_status_t status = psa_generate_random( output, output_size );
|
||||
if( status == PSA_SUCCESS )
|
||||
return( 0 );
|
||||
else
|
||||
return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
|
||||
}
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
#if defined(MBEDTLS_PSA_INJECT_ENTROPY)
|
||||
#include "mbedtls/entropy_poll.h"
|
||||
|
||||
@ -6448,8 +6578,8 @@ static psa_status_t psa_generate_key_internal(
|
||||
return( status );
|
||||
mbedtls_rsa_init( &rsa, MBEDTLS_RSA_PKCS_V15, MBEDTLS_MD_NONE );
|
||||
ret = mbedtls_rsa_gen_key( &rsa,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg,
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE,
|
||||
(unsigned int) bits,
|
||||
exponent );
|
||||
if( ret != 0 )
|
||||
@ -6494,8 +6624,8 @@ static psa_status_t psa_generate_key_internal(
|
||||
return( PSA_ERROR_NOT_SUPPORTED );
|
||||
mbedtls_ecp_keypair_init( &ecp );
|
||||
ret = mbedtls_ecp_gen_key( grp_id, &ecp,
|
||||
mbedtls_ctr_drbg_random,
|
||||
&global_data.ctr_drbg );
|
||||
mbedtls_psa_get_random,
|
||||
MBEDTLS_PSA_RANDOM_STATE );
|
||||
if( ret != 0 )
|
||||
{
|
||||
mbedtls_ecp_keypair_free( &ecp );
|
||||
@ -6575,24 +6705,25 @@ exit:
|
||||
/* Module setup */
|
||||
/****************************************************************/
|
||||
|
||||
#if !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
psa_status_t mbedtls_psa_crypto_configure_entropy_sources(
|
||||
void (* entropy_init )( mbedtls_entropy_context *ctx ),
|
||||
void (* entropy_free )( mbedtls_entropy_context *ctx ) )
|
||||
{
|
||||
if( global_data.rng_state != RNG_NOT_INITIALIZED )
|
||||
return( PSA_ERROR_BAD_STATE );
|
||||
global_data.entropy_init = entropy_init;
|
||||
global_data.entropy_free = entropy_free;
|
||||
global_data.rng.entropy_init = entropy_init;
|
||||
global_data.rng.entropy_free = entropy_free;
|
||||
return( PSA_SUCCESS );
|
||||
}
|
||||
#endif /* !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG) */
|
||||
|
||||
void mbedtls_psa_crypto_free( void )
|
||||
{
|
||||
psa_wipe_all_key_slots( );
|
||||
if( global_data.rng_state != RNG_NOT_INITIALIZED )
|
||||
{
|
||||
mbedtls_ctr_drbg_free( &global_data.ctr_drbg );
|
||||
global_data.entropy_free( &global_data.entropy );
|
||||
mbedtls_psa_random_free( &global_data.rng );
|
||||
}
|
||||
/* Wipe all remaining data, including configuration.
|
||||
* In particular, this sets all state indicator to the value
|
||||
@ -6634,37 +6765,15 @@ static psa_status_t psa_crypto_recover_transaction(
|
||||
psa_status_t psa_crypto_init( void )
|
||||
{
|
||||
psa_status_t status;
|
||||
const unsigned char drbg_seed[] = "PSA";
|
||||
|
||||
/* Double initialization is explicitly allowed. */
|
||||
if( global_data.initialized != 0 )
|
||||
return( PSA_SUCCESS );
|
||||
|
||||
/* Set default configuration if
|
||||
* mbedtls_psa_crypto_configure_entropy_sources() hasn't been called. */
|
||||
if( global_data.entropy_init == NULL )
|
||||
global_data.entropy_init = mbedtls_entropy_init;
|
||||
if( global_data.entropy_free == NULL )
|
||||
global_data.entropy_free = mbedtls_entropy_free;
|
||||
|
||||
/* Initialize the random generator. */
|
||||
global_data.entropy_init( &global_data.entropy );
|
||||
#if defined(MBEDTLS_PSA_INJECT_ENTROPY) && \
|
||||
defined(MBEDTLS_NO_DEFAULT_ENTROPY_SOURCES)
|
||||
/* The PSA entropy injection feature depends on using NV seed as an entropy
|
||||
* source. Add NV seed as an entropy source for PSA entropy injection. */
|
||||
mbedtls_entropy_add_source( &global_data.entropy,
|
||||
mbedtls_nv_seed_poll, NULL,
|
||||
MBEDTLS_ENTROPY_BLOCK_SIZE,
|
||||
MBEDTLS_ENTROPY_SOURCE_STRONG );
|
||||
#endif
|
||||
mbedtls_ctr_drbg_init( &global_data.ctr_drbg );
|
||||
/* Initialize and seed the random generator. */
|
||||
mbedtls_psa_random_init( &global_data.rng );
|
||||
global_data.rng_state = RNG_INITIALIZED;
|
||||
status = mbedtls_to_psa_error(
|
||||
mbedtls_ctr_drbg_seed( &global_data.ctr_drbg,
|
||||
mbedtls_entropy_func,
|
||||
&global_data.entropy,
|
||||
drbg_seed, sizeof( drbg_seed ) - 1 ) );
|
||||
status = mbedtls_psa_random_seed( &global_data.rng );
|
||||
if( status != PSA_SUCCESS )
|
||||
goto exit;
|
||||
global_data.rng_state = RNG_SEEDED;
|
||||
|
@ -38,6 +38,7 @@
|
||||
|
||||
#include "mbedtls/entropy.h"
|
||||
|
||||
#if !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
/** \brief Configure entropy sources.
|
||||
*
|
||||
* This function may only be called before a call to psa_crypto_init(),
|
||||
@ -73,5 +74,6 @@
|
||||
psa_status_t mbedtls_psa_crypto_configure_entropy_sources(
|
||||
void (* entropy_init )( mbedtls_entropy_context *ctx ),
|
||||
void (* entropy_free )( mbedtls_entropy_context *ctx ) );
|
||||
#endif /* !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG) */
|
||||
|
||||
#endif /* PSA_CRYPTO_INVASIVE_H */
|
||||
|
215
library/psa_crypto_random_impl.h
Normal file
215
library/psa_crypto_random_impl.h
Normal file
@ -0,0 +1,215 @@
|
||||
/** \file psa_crypto_random_impl.h
|
||||
*
|
||||
* \brief PSA crypto random generator implementation abstraction.
|
||||
*/
|
||||
/*
|
||||
* Copyright The Mbed TLS Contributors
|
||||
* 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_RANDOM_IMPL_H
|
||||
#define PSA_CRYPTO_RANDOM_IMPL_H
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
|
||||
#include <string.h>
|
||||
#include <mbedtls/entropy.h> // only for error codes
|
||||
#include <psa/crypto.h>
|
||||
|
||||
typedef mbedtls_psa_external_random_context_t mbedtls_psa_random_context_t;
|
||||
|
||||
/* Trivial wrapper around psa_generate_random(). */
|
||||
int mbedtls_psa_get_random( void *p_rng,
|
||||
unsigned char *output,
|
||||
size_t output_size );
|
||||
|
||||
/* The PSA RNG API doesn't need any externally maintained state. */
|
||||
#define MBEDTLS_PSA_RANDOM_STATE NULL
|
||||
|
||||
#else /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
/* Choose a DRBG based on configuration and availability */
|
||||
#if defined(MBEDTLS_PSA_HMAC_DRBG_MD_TYPE)
|
||||
|
||||
#include "mbedtls/hmac_drbg.h"
|
||||
|
||||
#elif defined(MBEDTLS_CTR_DRBG_C)
|
||||
|
||||
#include "mbedtls/ctr_drbg.h"
|
||||
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
|
||||
#include "mbedtls/hmac_drbg.h"
|
||||
#if defined(MBEDTLS_SHA512_C) && defined(MBEDTLS_SHA256_C)
|
||||
#include <limits.h>
|
||||
#if SIZE_MAX > 0xffffffff
|
||||
/* Looks like a 64-bit system, so prefer SHA-512. */
|
||||
#define MBEDTLS_PSA_HMAC_DRBG_MD_TYPE MBEDTLS_MD_SHA512
|
||||
#else
|
||||
/* Looks like a 32-bit system, so prefer SHA-256. */
|
||||
#define MBEDTLS_PSA_HMAC_DRBG_MD_TYPE MBEDTLS_MD_SHA256
|
||||
#endif
|
||||
#elif defined(MBEDTLS_SHA512_C)
|
||||
#define MBEDTLS_PSA_HMAC_DRBG_MD_TYPE MBEDTLS_MD_SHA512
|
||||
#elif defined(MBEDTLS_SHA256_C)
|
||||
#define MBEDTLS_PSA_HMAC_DRBG_MD_TYPE MBEDTLS_MD_SHA256
|
||||
#else
|
||||
#error "No hash algorithm available for HMAC_DBRG."
|
||||
#endif
|
||||
|
||||
#else
|
||||
#error "No DRBG module available for the psa_crypto module."
|
||||
#endif
|
||||
|
||||
#include "mbedtls/entropy.h"
|
||||
|
||||
/** The type of the PSA DRBG context.
|
||||
*/
|
||||
#if defined(MBEDTLS_CTR_DRBG_C)
|
||||
typedef mbedtls_ctr_drbg_context mbedtls_psa_drbg_context_t;
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
typedef mbedtls_hmac_drbg_context mbedtls_psa_drbg_context_t;
|
||||
#endif
|
||||
|
||||
/** Initialize the PSA DRBG.
|
||||
*
|
||||
* \param p_rng Pointer to the Mbed TLS DRBG state.
|
||||
*/
|
||||
static inline void mbedtls_psa_drbg_init( mbedtls_psa_drbg_context_t *p_rng )
|
||||
{
|
||||
#if defined(MBEDTLS_CTR_DRBG_C)
|
||||
mbedtls_ctr_drbg_init( p_rng );
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
mbedtls_hmac_drbg_init( p_rng );
|
||||
#endif
|
||||
}
|
||||
|
||||
/** Deinitialize the PSA DRBG.
|
||||
*
|
||||
* \param p_rng Pointer to the Mbed TLS DRBG state.
|
||||
*/
|
||||
static inline void mbedtls_psa_drbg_free( mbedtls_psa_drbg_context_t *p_rng )
|
||||
{
|
||||
#if defined(MBEDTLS_CTR_DRBG_C)
|
||||
mbedtls_ctr_drbg_free( p_rng );
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
mbedtls_hmac_drbg_free( p_rng );
|
||||
#endif
|
||||
}
|
||||
|
||||
/** The type of the PSA random generator context.
|
||||
*
|
||||
* The random generator context is composed of an entropy context and
|
||||
* a DRBG context.
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
void (* entropy_init )( mbedtls_entropy_context *ctx );
|
||||
void (* entropy_free )( mbedtls_entropy_context *ctx );
|
||||
mbedtls_entropy_context entropy;
|
||||
mbedtls_psa_drbg_context_t drbg;
|
||||
} mbedtls_psa_random_context_t;
|
||||
|
||||
/* The type of an Mbed TLS random generator function. This should be
|
||||
* part of the public API instead of repeating the type everywhere.
|
||||
* For the time being, declare it here. Declaring a type is necessary
|
||||
* to define mbedtls_psa_get_random as a variable of a function pointer
|
||||
* type without incurring the wrath of check-names.sh. */
|
||||
typedef int mbedtls_f_rng_t( void *p_rng, unsigned char *output, size_t output_size );
|
||||
|
||||
/** Return random data.
|
||||
*
|
||||
* This function is suitable as the \p f_rng parameter to Mbed TLS functions
|
||||
* that require a random generator. Use #MBEDTLS_PSA_RANDOM_STATE to
|
||||
* obtain the \p p_rng parameter.
|
||||
*
|
||||
* \param p_rng The DRBG context. This must be
|
||||
* #MBEDTLS_PSA_RANDOM_STATE.
|
||||
* \param output The buffer to fill.
|
||||
* \param output_len The length of the buffer in bytes.
|
||||
* It must be at most #MBEDTLS_PSA_RANDOM_MAX_REQUEST.
|
||||
*
|
||||
* \retval \c 0 on success.
|
||||
* \return \c MBEDTLS_ERR_xxx_DRBG_xxx or
|
||||
* \c MBEDTLS_ERR_PLATFORM_xxx on failure.
|
||||
*/
|
||||
#if defined(MBEDTLS_CTR_DRBG_C)
|
||||
static mbedtls_f_rng_t *const mbedtls_psa_get_random = mbedtls_ctr_drbg_random;
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
static mbedtls_f_rng_t *const mbedtls_psa_get_random = mbedtls_hmac_drbg_random;
|
||||
#endif
|
||||
|
||||
/** The maximum number of bytes that mbedtls_psa_get_random() is expected to
|
||||
* return.
|
||||
*/
|
||||
#if defined(MBEDTLS_CTR_DRBG_C)
|
||||
#define MBEDTLS_PSA_RANDOM_MAX_REQUEST MBEDTLS_CTR_DRBG_MAX_REQUEST
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
#define MBEDTLS_PSA_RANDOM_MAX_REQUEST MBEDTLS_HMAC_DRBG_MAX_REQUEST
|
||||
#endif
|
||||
|
||||
/** A pointer to the PSA DRBG state.
|
||||
*
|
||||
* This variable is only intended to be used through the macro
|
||||
* #MBEDTLS_PSA_RANDOM_STATE.
|
||||
*/
|
||||
/* psa_crypto.c sets this variable to a pointer to the DRBG state in the
|
||||
* global PSA crypto state. */
|
||||
extern mbedtls_psa_drbg_context_t *const mbedtls_psa_random_state;
|
||||
|
||||
/** A pointer to the PSA DRBG state.
|
||||
*
|
||||
* This macro expands to an expression that is suitable as the \c p_rng
|
||||
* parameter to pass to mbedtls_psa_get_random().
|
||||
*
|
||||
* This macro exists in all configurations where the psa_crypto module is
|
||||
* enabled. Its expansion depends on the configuration.
|
||||
*/
|
||||
#define MBEDTLS_PSA_RANDOM_STATE mbedtls_psa_random_state
|
||||
|
||||
/** Seed the PSA DRBG.
|
||||
*
|
||||
* \param entropy An entropy context to read the seed from.
|
||||
* \param custom The personalization string.
|
||||
* This can be \c NULL, in which case the personalization
|
||||
* string is empty regardless of the value of \p len.
|
||||
* \param len The length of the personalization string.
|
||||
*
|
||||
* \return \c 0 on success.
|
||||
* \return An Mbed TLS error code (\c MBEDTLS_ERR_xxx) on failure.
|
||||
*/
|
||||
static inline int mbedtls_psa_drbg_seed(
|
||||
mbedtls_entropy_context *entropy,
|
||||
const unsigned char *custom, size_t len )
|
||||
{
|
||||
#if defined(MBEDTLS_CTR_DRBG_C)
|
||||
return( mbedtls_ctr_drbg_seed( MBEDTLS_PSA_RANDOM_STATE,
|
||||
mbedtls_entropy_func,
|
||||
entropy,
|
||||
custom, len ) );
|
||||
#elif defined(MBEDTLS_HMAC_DRBG_C)
|
||||
const mbedtls_md_info_t *md_info =
|
||||
mbedtls_md_info_from_type( MBEDTLS_PSA_HMAC_DRBG_MD_TYPE );
|
||||
return( mbedtls_hmac_drbg_seed( MBEDTLS_PSA_RANDOM_STATE,
|
||||
md_info,
|
||||
mbedtls_entropy_func,
|
||||
entropy,
|
||||
custom, len ) );
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
#endif /* PSA_CRYPTO_RANDOM_IMPL_H */
|
@ -438,6 +438,9 @@ static const char * const features[] = {
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_DRIVERS)
|
||||
"MBEDTLS_PSA_CRYPTO_DRIVERS",
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_DRIVERS */
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
"MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG",
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_SPM)
|
||||
"MBEDTLS_PSA_CRYPTO_SPM",
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_SPM */
|
||||
|
@ -1224,6 +1224,14 @@ int query_config( const char *config )
|
||||
}
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_DRIVERS */
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
if( strcmp( "MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG", config ) == 0 )
|
||||
{
|
||||
MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG );
|
||||
return( 0 );
|
||||
}
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_SPM)
|
||||
if( strcmp( "MBEDTLS_PSA_CRYPTO_SPM", config ) == 0 )
|
||||
{
|
||||
@ -2608,6 +2616,14 @@ int query_config( const char *config )
|
||||
}
|
||||
#endif /* MBEDTLS_PLATFORM_NV_SEED_WRITE_MACRO */
|
||||
|
||||
#if defined(MBEDTLS_PSA_HMAC_DRBG_MD_TYPE)
|
||||
if( strcmp( "MBEDTLS_PSA_HMAC_DRBG_MD_TYPE", config ) == 0 )
|
||||
{
|
||||
MACRO_EXPANSION_TO_STR( MBEDTLS_PSA_HMAC_DRBG_MD_TYPE );
|
||||
return( 0 );
|
||||
}
|
||||
#endif /* MBEDTLS_PSA_HMAC_DRBG_MD_TYPE */
|
||||
|
||||
#if defined(MBEDTLS_SSL_CACHE_DEFAULT_TIMEOUT)
|
||||
if( strcmp( "MBEDTLS_SSL_CACHE_DEFAULT_TIMEOUT", config ) == 0 )
|
||||
{
|
||||
|
@ -185,6 +185,7 @@ EXCLUDE_FROM_FULL = frozenset([
|
||||
'MBEDTLS_PKCS11_C', # build dependency (libpkcs11-helper)
|
||||
'MBEDTLS_PLATFORM_NO_STD_FUNCTIONS', # removes a feature
|
||||
'MBEDTLS_PSA_CRYPTO_CONFIG', # toggles old/new style PSA config
|
||||
'MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG', # behavior change + build dependency
|
||||
'MBEDTLS_PSA_CRYPTO_KEY_ID_ENCODES_OWNER', # incompatible with USE_PSA_CRYPTO
|
||||
'MBEDTLS_PSA_CRYPTO_SPM', # platform dependency (PSA SPM)
|
||||
'MBEDTLS_PSA_INJECT_ENTROPY', # build dependency (hook functions)
|
||||
|
@ -915,10 +915,6 @@ component_test_no_ctr_drbg () {
|
||||
msg "build: Full minus CTR_DRBG"
|
||||
scripts/config.py full
|
||||
scripts/config.py unset MBEDTLS_CTR_DRBG_C
|
||||
scripts/config.py unset MBEDTLS_PSA_CRYPTO_C # requires CTR_DRBG
|
||||
scripts/config.py unset MBEDTLS_PSA_CRYPTO_STORAGE_C # requires PSA Crypto
|
||||
scripts/config.py unset MBEDTLS_PSA_CRYPTO_SE_C # requires PSA Crypto
|
||||
scripts/config.py unset MBEDTLS_USE_PSA_CRYPTO # requires PSA Crypto
|
||||
|
||||
CC=gcc cmake -D CMAKE_BUILD_TYPE:String=Asan .
|
||||
make
|
||||
@ -945,6 +941,36 @@ component_test_no_hmac_drbg () {
|
||||
# so there's little value in running those lengthy tests here.
|
||||
}
|
||||
|
||||
component_test_psa_external_rng_no_drbg () {
|
||||
msg "build: PSA_CRYPTO_EXTERNAL_RNG minus *_DRBG"
|
||||
scripts/config.py full
|
||||
scripts/config.py set MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG
|
||||
scripts/config.py unset MBEDTLS_CTR_DRBG_C
|
||||
scripts/config.py unset MBEDTLS_HMAC_DRBG_C
|
||||
scripts/config.py unset MBEDTLS_ECDSA_DETERMINISTIC # requires HMAC_DRBG
|
||||
scripts/config.py set MBEDTLS_ECP_NO_INTERNAL_RNG
|
||||
make CFLAGS="$ASAN_CFLAGS -O2" LDFLAGS="$ASAN_CFLAGS"
|
||||
|
||||
msg "test: PSA_CRYPTO_EXTERNAL_RNG minus *_DRBG"
|
||||
make test
|
||||
|
||||
# No ssl-opt.sh/compat.sh because they require CTR_DRBG.
|
||||
}
|
||||
|
||||
component_test_psa_external_rng_use_psa_crypto () {
|
||||
msg "build: full + PSA_CRYPTO_EXTERNAL_RNG + USE_PSA_CRYPTO minus CTR_DRBG"
|
||||
scripts/config.py full
|
||||
scripts/config.py set MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG
|
||||
scripts/config.py set MBEDTLS_USE_PSA_CRYPTO
|
||||
scripts/config.py unset MBEDTLS_CTR_DRBG_C
|
||||
make CFLAGS="$ASAN_CFLAGS -O2" LDFLAGS="$ASAN_CFLAGS"
|
||||
|
||||
msg "test: full + PSA_CRYPTO_EXTERNAL_RNG + USE_PSA_CRYPTO minus CTR_DRBG"
|
||||
make test
|
||||
|
||||
# No ssl-opt.sh/compat.sh because they require CTR_DRBG.
|
||||
}
|
||||
|
||||
component_test_ecp_no_internal_rng () {
|
||||
msg "build: Default plus ECP_NO_INTERNAL_RNG minus DRBG modules"
|
||||
scripts/config.py set MBEDTLS_ECP_NO_INTERNAL_RNG
|
||||
|
46
tests/src/psa_crypto_helpers.c
Normal file
46
tests/src/psa_crypto_helpers.c
Normal file
@ -0,0 +1,46 @@
|
||||
/** \file psa_crypto_helpers.c
|
||||
*
|
||||
* \brief Helper functions to test PSA crypto functionality.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright The Mbed TLS Contributors
|
||||
* 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.
|
||||
*/
|
||||
|
||||
#include <test/helpers.h>
|
||||
#include <test/macros.h>
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_C)
|
||||
|
||||
#include <psa/crypto.h>
|
||||
|
||||
#if defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
#include <test/random.h>
|
||||
|
||||
psa_status_t mbedtls_psa_external_get_random(
|
||||
mbedtls_psa_external_random_context_t *context,
|
||||
uint8_t *output, size_t output_size, size_t *output_length )
|
||||
{
|
||||
/* This implementation is for test purposes only!
|
||||
* Use the libc non-cryptographic random generator. */
|
||||
(void) context;
|
||||
mbedtls_test_rnd_std_rand( NULL, output, output_size );
|
||||
*output_length = output_size;
|
||||
return( PSA_SUCCESS );
|
||||
}
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
|
||||
#endif /* MBEDTLS_PSA_CRYPTO_C */
|
@ -11,11 +11,23 @@
|
||||
#define ENTROPY_MIN_NV_SEED_SIZE \
|
||||
MAX(MBEDTLS_ENTROPY_MIN_PLATFORM, MBEDTLS_ENTROPY_BLOCK_SIZE)
|
||||
|
||||
#include "psa_crypto_random_impl.h"
|
||||
#if defined(MBEDTLS_PSA_HMAC_DRBG_MD_TYPE)
|
||||
/* PSA crypto uses the HMAC_DRBG module. It reads from the entropy source twice:
|
||||
* once for the initial entropy and once for a nonce. The nonce length is
|
||||
* half the entropy length. For SHA-256, SHA-384 or SHA-512, the
|
||||
* entropy length is 256 per the documentation of mbedtls_hmac_drbg_seed(),
|
||||
* and PSA crypto doesn't support other hashes for HMAC_DRBG. */
|
||||
#define ENTROPY_NONCE_LEN ( 256 / 2 )
|
||||
#else
|
||||
/* PSA crypto uses the CTR_DRBG module. In some configurations, it needs
|
||||
* to read from the entropy source twice: once for the initial entropy
|
||||
* and once for a nonce. */
|
||||
#include "mbedtls/ctr_drbg.h"
|
||||
#define ENTROPY_NONCE_LEN MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN
|
||||
#endif
|
||||
|
||||
#if !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG)
|
||||
|
||||
typedef struct
|
||||
{
|
||||
@ -118,6 +130,8 @@ static void custom_entropy_init( mbedtls_entropy_context *ctx )
|
||||
MBEDTLS_ENTROPY_SOURCE_STRONG );
|
||||
}
|
||||
|
||||
#endif /* !defined(MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG) */
|
||||
|
||||
/* END_HEADER */
|
||||
|
||||
/* BEGIN_DEPENDENCIES
|
||||
@ -125,7 +139,7 @@ static void custom_entropy_init( mbedtls_entropy_context *ctx )
|
||||
* END_DEPENDENCIES
|
||||
*/
|
||||
|
||||
/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED */
|
||||
/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED:!MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
void create_nv_seed( )
|
||||
{
|
||||
static unsigned char seed[ENTROPY_MIN_NV_SEED_SIZE];
|
||||
@ -201,7 +215,7 @@ void validate_module_init_key_based( int count )
|
||||
}
|
||||
/* END_CASE */
|
||||
|
||||
/* BEGIN_CASE */
|
||||
/* BEGIN_CASE depends_on:!MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
void custom_entropy_sources( int sources_arg, int expected_init_status_arg )
|
||||
{
|
||||
psa_status_t expected_init_status = expected_init_status_arg;
|
||||
@ -222,7 +236,7 @@ exit:
|
||||
}
|
||||
/* END_CASE */
|
||||
|
||||
/* BEGIN_CASE */
|
||||
/* BEGIN_CASE depends_on:!MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
void fake_entropy_source( int threshold,
|
||||
int amount1,
|
||||
int amount2,
|
||||
@ -262,7 +276,7 @@ exit:
|
||||
}
|
||||
/* END_CASE */
|
||||
|
||||
/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED */
|
||||
/* BEGIN_CASE depends_on:MBEDTLS_ENTROPY_NV_SEED:!MBEDTLS_PSA_CRYPTO_EXTERNAL_RNG */
|
||||
void entropy_from_nv_seed( int seed_size_arg,
|
||||
int expected_init_status_arg )
|
||||
{
|
||||
|
@ -249,6 +249,7 @@
|
||||
<ClInclude Include="..\..\library\psa_crypto_driver_wrappers.h" />
|
||||
<ClInclude Include="..\..\library\psa_crypto_invasive.h" />
|
||||
<ClInclude Include="..\..\library\psa_crypto_its.h" />
|
||||
<ClInclude Include="..\..\library\psa_crypto_random_impl.h" />
|
||||
<ClInclude Include="..\..\library\psa_crypto_se.h" />
|
||||
<ClInclude Include="..\..\library\psa_crypto_service_integration.h" />
|
||||
<ClInclude Include="..\..\library\psa_crypto_slot_management.h" />
|
||||
@ -348,6 +349,7 @@
|
||||
<ClCompile Include="..\..\library\x509write_csr.c" />
|
||||
<ClCompile Include="..\..\library\xtea.c" />
|
||||
<ClCompile Include="..\..\tests\src\helpers.c" />
|
||||
<ClCompile Include="..\..\tests\src\psa_crypto_helpers.c" />
|
||||
<ClCompile Include="..\..\tests\src\random.c" />
|
||||
<ClCompile Include="..\..\3rdparty\everest\library\everest.c" />
|
||||
<ClCompile Include="..\..\3rdparty\everest\library\Hacl_Curve25519_joined.c" />
|
||||
|
Loading…
Reference in New Issue
Block a user