Expanded the random number generator in the platform_util.c
file
The earlier implementation had two problems: the random generator always returned 0 if the MBEDTLS_ENTROPY_HARDWARE_ALT flag was not defined and there was no protection needed if the HW RNG was malfunctioning. Both these problems have been solved in this commit by adding the linear congruential generator algorithm. Signed-off-by: Piotr Nowicki <piotr.nowicki@arm.com>
This commit is contained in:
parent
8656fc6525
commit
77b7a7754c
2 changed files with 75 additions and 54 deletions
library
|
@ -51,9 +51,20 @@
|
|||
#include <stddef.h>
|
||||
#include <string.h>
|
||||
|
||||
/* Max number of loops for mbedtls_platform_random_delay */
|
||||
/* Max number of loops for mbedtls_platform_random_delay. */
|
||||
#define MAX_RAND_DELAY 100
|
||||
|
||||
/* Parameters for the linear congruential generator used as a non-cryptographic
|
||||
* random number generator. The same parameters are used by e.g. ANSI C. */
|
||||
#define RAND_MULTIPLIER 1103515245
|
||||
#define RAND_INCREMENT 12345
|
||||
#define RAND_MODULUS 0x80000000
|
||||
|
||||
/* The number of iterations after which the seed of the non-cryptographic
|
||||
* random number generator will be changed. This is used only if the
|
||||
* MBEDTLS_ENTROPY_HARDWARE_ALT option is enabled. */
|
||||
#define RAND_SEED_LIFE 10000
|
||||
|
||||
#if !defined(MBEDTLS_PLATFORM_ZEROIZE_ALT)
|
||||
/*
|
||||
* This implementation should never be optimized out by the compiler
|
||||
|
@ -172,50 +183,78 @@ int mbedtls_platform_memequal( const void *buf1, const void *buf2, size_t num )
|
|||
return( (int) diff | (int) ( flow_counter ^ num ) );
|
||||
}
|
||||
|
||||
uint32_t mbedtls_platform_random_uint32( )
|
||||
/* This function implements a non-cryptographic random number generator based
|
||||
* on the linear congruential generator algorithm. Additionally, if the
|
||||
* MBEDTLS_ENTROPY_HARDWARE_ALT flag is defined, the seed is set at the first
|
||||
* call of this function with using a hardware random number generator and
|
||||
* changed every RAND_SEED_LIFE number of iterations.
|
||||
*
|
||||
* The value of the returned number is in the range [0; 0xffff].
|
||||
*
|
||||
* Note: The range of values with a 16-bit precision is related to the modulo
|
||||
* parameter of the generator and the fact that the function does not return the
|
||||
* full value of the internal state of the generator.
|
||||
*/
|
||||
static uint32_t mbedtls_platform_random_uint16( void )
|
||||
{
|
||||
#if !defined(MBEDTLS_ENTROPY_HARDWARE_ALT)
|
||||
return 0;
|
||||
#else
|
||||
uint32_t result = 0;
|
||||
size_t olen = 0;
|
||||
/* Set random_state - the first random value should not be zero. */
|
||||
static uint32_t random_state = RAND_INCREMENT;
|
||||
|
||||
mbedtls_hardware_poll( NULL, (unsigned char *) &result, sizeof( result ),
|
||||
&olen );
|
||||
return( result );
|
||||
#endif
|
||||
#if defined(MBEDTLS_ENTROPY_HARDWARE_ALT)
|
||||
|
||||
static uint32_t random_seed_life = 0;
|
||||
|
||||
if( 0 < random_seed_life )
|
||||
{
|
||||
--random_seed_life;
|
||||
}
|
||||
else
|
||||
{
|
||||
size_t olen = 0;
|
||||
uint32_t hw_random;
|
||||
mbedtls_hardware_poll( NULL,
|
||||
(unsigned char *) &hw_random, sizeof( hw_random ),
|
||||
&olen );
|
||||
if( olen == sizeof( hw_random ) )
|
||||
{
|
||||
random_state ^= hw_random;
|
||||
random_seed_life = RAND_SEED_LIFE;
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* MBEDTLS_ENTROPY_HARDWARE_ALT */
|
||||
|
||||
random_state = ( ( random_state * RAND_MULTIPLIER ) + RAND_INCREMENT ) % RAND_MODULUS;
|
||||
|
||||
/* Do not return the entire random_state to hide generator predictability for
|
||||
* the next iteration */
|
||||
return( ( random_state >> 15 ) & 0xffff );
|
||||
}
|
||||
|
||||
uint32_t mbedtls_platform_random_uint32( void )
|
||||
{
|
||||
return( ( mbedtls_platform_random_uint16() << 16 ) |
|
||||
mbedtls_platform_random_uint16() );
|
||||
}
|
||||
|
||||
uint32_t mbedtls_platform_random_in_range( uint32_t num )
|
||||
{
|
||||
#if !defined(MBEDTLS_ENTROPY_HARDWARE_ALT)
|
||||
(void) num;
|
||||
return 0;
|
||||
#else
|
||||
uint32_t result = 0;
|
||||
size_t olen = 0;
|
||||
uint32_t result;
|
||||
|
||||
mbedtls_hardware_poll( NULL, (unsigned char *) &result, sizeof( result ),
|
||||
&olen );
|
||||
|
||||
if( num == 0 )
|
||||
if( num <= 1 )
|
||||
{
|
||||
result = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
result %= num;
|
||||
result = mbedtls_platform_random_uint32() % num;
|
||||
}
|
||||
|
||||
return( result );
|
||||
#endif
|
||||
}
|
||||
|
||||
void mbedtls_platform_random_delay( void )
|
||||
{
|
||||
#if !defined(MBEDTLS_ENTROPY_HARDWARE_ALT)
|
||||
return;
|
||||
#else
|
||||
uint32_t rn_1, rn_2, rn_3;
|
||||
volatile size_t i = 0;
|
||||
uint8_t shift;
|
||||
|
@ -237,9 +276,6 @@ void mbedtls_platform_random_delay( void )
|
|||
rn_3 = ( rn_3 << shift ) | ( rn_3 >> ( 32 - shift ) );
|
||||
rn_2 ^= rn_3;
|
||||
} while( i < rn_1 || rn_2 == 0 || rn_3 == 0 );
|
||||
|
||||
return;
|
||||
#endif /* !MBEDTLS_ENTROPY_HARDWARE_ALT */
|
||||
}
|
||||
|
||||
#if defined(MBEDTLS_HAVE_TIME_DATE) && !defined(MBEDTLS_PLATFORM_GMTIME_R_ALT)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue