diff --git a/include/mbedtls/ctr_drbg.h b/include/mbedtls/ctr_drbg.h index 09f4e620e2..a0750e0d42 100644 --- a/include/mbedtls/ctr_drbg.h +++ b/include/mbedtls/ctr_drbg.h @@ -147,6 +147,24 @@ extern "C" { #endif +#if MBEDTLS_CTR_DRBG_ENTROPY_LEN >= MBEDTLS_CTR_DRBG_KEYSIZE * 3 / 2 +/** The default length of the nonce read from the entropy source. + * + * This is \c 0 because a single read from the entropy source is sufficient + * to include a nonce. + * See the documentation of mbedtls_ctr_drbg_seed() for more information. + */ +#define MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN 0 +#else +/** The default length of the nonce read from the entropy source. + * + * This is half of the default entropy length because a single read from + * the entropy source does not provide enough material to form a nonce. + * See the documentation of mbedtls_ctr_drbg_seed() for more information. + */ +#define MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN ( MBEDTLS_CTR_DRBG_ENTROPY_LEN + 1 ) / 2 +#endif + /** * \brief The CTR_DRBG context structure. */ @@ -216,20 +234,9 @@ void mbedtls_ctr_drbg_init( mbedtls_ctr_drbg_context *ctx ); * by the key size and entropy length according to NIST SP 800-90A §10.2.1; * - Half the entropy length otherwise. * You can override it by calling mbedtls_ctr_drbg_set_nonce_len(). - */ -#if MBEDTLS_CTR_DRBG_ENTROPY_LEN >= MBEDTLS_CTR_DRBG_KEYSIZE * 3 / 2 -/** With the default entropy length, the entropy nonce length is \c 0. - */ -#elif MBEDTLS_CTR_DRBG_ENTROPY_LEN & 1 -/** With the default entropy length, the entropy nonce length is - * (#MBEDTLS_CTR_DRBG_ENTROPY_LEN + 1) / 2. - */ -#else -/** With the default entropy length, the entropy nonce length is - * #MBEDTLS_CTR_DRBG_ENTROPY_LEN / 2. - */ -#endif -/** + * With the default entropy length, the entropy nonce length is + * #MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN. + * * You can provide a nonce and personalization string in addition to the * entropy source, to make this instantiation as unique as possible. * See SP 800-90A §8.6.7 for more details about nonces. @@ -240,7 +247,7 @@ void mbedtls_ctr_drbg_init( mbedtls_ctr_drbg_context *ctx ); * - A string obtained by calling \p f_entropy function for the entropy * length. */ -#if MBEDTLS_CTR_DRBG_ENTROPY_LEN >= MBEDTLS_CTR_DRBG_KEYSIZE * 3 / 2 +#if MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN == 0 /** * - If mbedtls_ctr_drbg_set_nonce_len() has been called, a string * obtained by calling \p f_entropy function for the specified length. diff --git a/tests/suites/test_suite_ctr_drbg.data b/tests/suites/test_suite_ctr_drbg.data index 461e50255e..b50df2ba33 100644 --- a/tests/suites/test_suite_ctr_drbg.data +++ b/tests/suites/test_suite_ctr_drbg.data @@ -1070,12 +1070,7 @@ CTR_DRBG CAVS 14.3 (AES-128 use df,True,128,64,0,0) #0 depends_on:MBEDTLS_CTR_DRBG_USE_128_BIT_KEY ctr_drbg_validate_pr:"d4f1f4ae08bcb3e1":"5d4041942bcf68864a4997d8171f1f9fef55a769b7eaf03fe082029bb32a2b9d8239e865c0a42e14b964b9c09de85a20":"":"":"4155320287eedcf7d484c2c2a1e2eb64b9c9ce77c87202a1ae1616c7a5cfd1c687c7a0bfcc85bda48fdd4629fd330c22d0a76076f88fc7cd04037ee06b7af602" -CTR_DRBG entropy usage (entropy_nonce_len=0 by default) -depends_on:!DEFAULT_ENTROPY_NONCE -ctr_drbg_entropy_usage:-1 - -CTR_DRBG entropy usage (entropy_nonce_len=entropy_len/2 by default) -depends_on:DEFAULT_ENTROPY_NONCE +CTR_DRBG entropy usage (default entropy_nonce_len) ctr_drbg_entropy_usage:-1 CTR_DRBG entropy usage (entropy_nonce_len=0) @@ -1084,6 +1079,14 @@ ctr_drbg_entropy_usage:0 CTR_DRBG entropy usage (entropy_nonce_len=7) ctr_drbg_entropy_usage:7 +CTR_DRBG entropy strength: 128 bits +depends_on:MBEDTLS_CTR_DRBG_USE_128_BIT_KEY +ctr_drbg_entropy_strength:128 + +CTR_DRBG entropy strength: 256 bits +depends_on:!MBEDTLS_CTR_DRBG_USE_128_BIT_KEY +ctr_drbg_entropy_strength:256 + CTR_DRBG write/update seed file [#1] ctr_drbg_seed_file:"data_files/ctr_drbg_seed":0 diff --git a/tests/suites/test_suite_ctr_drbg.function b/tests/suites/test_suite_ctr_drbg.function index c28438587f..8317c08c80 100644 --- a/tests/suites/test_suite_ctr_drbg.function +++ b/tests/suites/test_suite_ctr_drbg.function @@ -3,14 +3,6 @@ #include "mbedtls/ctr_drbg.h" #include "string.h" -/* mbedtls_ctr_drbg_seed() grabs a nonce by default if the entropy - * length is smaller than 3/2 times the maximum security strength. */ -#if MBEDTLS_CTR_DRBG_ENTROPY_LEN >= MBEDTLS_CTR_DRBG_KEYSIZE * 3 / 2 -#undef DEFAULT_ENTROPY_NONCE -#else -#define DEFAULT_ENTROPY_NONCE -#endif - /* Modes for ctr_drbg_validate */ enum reseed_mode { @@ -196,7 +188,37 @@ void ctr_drbg_validate_reseed_first( data_t * add_init, data_t * entropy, } /* END_CASE */ +/* BEGIN_CASE */ +void ctr_drbg_entropy_strength( int expected_bit_strength ) +{ + unsigned char entropy[/*initial entropy*/ MBEDTLS_CTR_DRBG_ENTROPY_LEN + + /*nonce*/ MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN + + /*reseed*/ MBEDTLS_CTR_DRBG_ENTROPY_LEN]; + mbedtls_ctr_drbg_context ctx; + size_t last_idx; + size_t byte_strength = expected_bit_strength / 8; + mbedtls_ctr_drbg_init( &ctx ); + test_offset_idx = 0; + test_max_idx = sizeof( entropy ); + memset( entropy, 0, sizeof( entropy ) ); + + /* The initial seeding must grab at least byte_strength bytes of entropy + * for the entropy input and byte_strength/2 bytes for a nonce. */ + TEST_ASSERT( mbedtls_ctr_drbg_seed( &ctx, + mbedtls_test_entropy_func, entropy, + NULL, 0 ) == 0 ); + TEST_ASSERT( test_offset_idx >= ( byte_strength * 3 + 1 ) / 2 ); + last_idx = test_offset_idx; + + /* A reseed must grab at least byte_strength bytes of entropy. */ + TEST_ASSERT( mbedtls_ctr_drbg_reseed( &ctx, NULL, 0 ) == 0 ); + TEST_ASSERT( test_offset_idx - last_idx >= byte_strength ); + +exit: + mbedtls_ctr_drbg_free( &ctx ); +} +/* END_CASE */ /* BEGIN_CASE */ void ctr_drbg_entropy_usage( int entropy_nonce_len ) @@ -224,11 +246,7 @@ void ctr_drbg_entropy_usage( int entropy_nonce_len ) if( entropy_nonce_len >= 0 ) expected_idx += entropy_nonce_len; else - { -#if defined(DEFAULT_ENTROPY_NONCE) - expected_idx += ( MBEDTLS_CTR_DRBG_ENTROPY_LEN + 1 ) / 2; -#endif - } + expected_idx += MBEDTLS_CTR_DRBG_ENTROPY_NONCE_LEN; TEST_EQUAL( test_offset_idx, expected_idx ); /* By default, PR is off and reseed_interval is large, diff --git a/tests/suites/test_suite_psa_crypto_init.data b/tests/suites/test_suite_psa_crypto_init.data index c57a764efe..9620a642a0 100644 --- a/tests/suites/test_suite_psa_crypto_init.data +++ b/tests/suites/test_suite_psa_crypto_init.data @@ -34,15 +34,25 @@ fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:0:0:0:0:PSA_ERROR_INSUFFICIENT_EN Fake entropy: less than the block size fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:MBEDTLS_ENTROPY_BLOCK_SIZE - 1:-1:-1:-1:PSA_ERROR_INSUFFICIENT_ENTROPY +Fake entropy: not enough for a nonce +depends_on:ENTROPY_NONCE_LEN != 0 +fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:ENTROPY_NONCE_LEN - 1:-1:-1:-1:PSA_ERROR_INSUFFICIENT_ENTROPY + Fake entropy: one block eventually +depends_on:ENTROPY_NONCE_LEN == 0 fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:0:0:0:MBEDTLS_ENTROPY_BLOCK_SIZE:PSA_SUCCESS Fake entropy: one block in two steps +depends_on:ENTROPY_NONCE_LEN == 0 fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:MBEDTLS_ENTROPY_BLOCK_SIZE - 1:1:-1:-1:PSA_SUCCESS Fake entropy: more than one block in two steps +depends_on:ENTROPY_NONCE_LEN == 0 fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:MBEDTLS_ENTROPY_BLOCK_SIZE - 1:MBEDTLS_ENTROPY_BLOCK_SIZE - 1:-1:-1:PSA_SUCCESS +Fake entropy: two blocks eventually +fake_entropy_source:MBEDTLS_ENTROPY_BLOCK_SIZE:0:MBEDTLS_ENTROPY_BLOCK_SIZE:0:MBEDTLS_ENTROPY_BLOCK_SIZE:PSA_SUCCESS + NV seed only: less than minimum entropy_from_nv_seed:MBEDTLS_ENTROPY_MIN_PLATFORM - 1:PSA_ERROR_INSUFFICIENT_ENTROPY diff --git a/tests/suites/test_suite_psa_crypto_init.function b/tests/suites/test_suite_psa_crypto_init.function index 3c4b42e03f..3283ac9f6d 100644 --- a/tests/suites/test_suite_psa_crypto_init.function +++ b/tests/suites/test_suite_psa_crypto_init.function @@ -11,6 +11,12 @@ #define ENTROPY_MIN_NV_SEED_SIZE \ MAX(MBEDTLS_ENTROPY_MIN_PLATFORM, MBEDTLS_ENTROPY_BLOCK_SIZE) +/* 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 + typedef struct { size_t threshold; /* Minimum bytes to make mbedtls_entropy_func happy */