Refactor mpi_write_hlp to not be recursive

Refactor `mpi_write_hlp()` to not be recursive, to fix stack overflows.
Iterate over the `mbedtls_mpi` division of the radix requested,
until it is zero. Each iteration, put the residue in the next LSB
of the output buffer. Fixes #2190
This commit is contained in:
Ron Eldor 2018-11-20 14:07:01 +02:00
parent 556d7d9e3b
commit a16fa297f7

View file

@ -499,26 +499,38 @@ cleanup:
} }
/* /*
* Helper to write the digits high-order first * Helper to write the digits high-order first.
*/ */
static int mpi_write_hlp( mbedtls_mpi *X, int radix, char **p ) static int mpi_write_hlp( mbedtls_mpi *X, int radix,
char **p, const size_t buflen )
{ {
int ret; int ret;
mbedtls_mpi_uint r; mbedtls_mpi_uint r;
size_t length = 0;
char *p_end = *p + buflen;
if( radix < 2 || radix > 16 ) do
return( MBEDTLS_ERR_MPI_BAD_INPUT_DATA ); {
if( length >= buflen )
{
return( MBEDTLS_ERR_MPI_BUFFER_TOO_SMALL );
}
MBEDTLS_MPI_CHK( mbedtls_mpi_mod_int( &r, X, radix ) ); MBEDTLS_MPI_CHK( mbedtls_mpi_mod_int( &r, X, radix ) );
MBEDTLS_MPI_CHK( mbedtls_mpi_div_int( X, NULL, X, radix ) ); MBEDTLS_MPI_CHK( mbedtls_mpi_div_int( X, NULL, X, radix ) );
/*
* Write the residue in the current position, as an ASCII character.
*/
if( r < 0xA )
*(--p_end) = (char)( '0' + r );
else
*(--p_end) = (char)( 'A' + ( r - 0xA ) );
if( mbedtls_mpi_cmp_int( X, 0 ) != 0 ) length++;
MBEDTLS_MPI_CHK( mpi_write_hlp( X, radix, p ) ); } while( mbedtls_mpi_cmp_int( X, 0 ) != 0 );
if( r < 10 ) memmove( *p, p_end, length );
*(*p)++ = (char)( r + 0x30 ); *p += length;
else
*(*p)++ = (char)( r + 0x37 );
cleanup: cleanup:
@ -588,7 +600,7 @@ int mbedtls_mpi_write_string( const mbedtls_mpi *X, int radix,
if( T.s == -1 ) if( T.s == -1 )
T.s = 1; T.s = 1;
MBEDTLS_MPI_CHK( mpi_write_hlp( &T, radix, &p ) ); MBEDTLS_MPI_CHK( mpi_write_hlp( &T, radix, &p, buflen ) );
} }
*p++ = '\0'; *p++ = '\0';