diff options
-rw-r--r-- | src/crypto/bigint.c | 47 | ||||
-rw-r--r-- | src/include/ipxe/bigint.h | 13 |
2 files changed, 60 insertions, 0 deletions
diff --git a/src/crypto/bigint.c b/src/crypto/bigint.c index e5e6e2f12..dd75cd9d1 100644 --- a/src/crypto/bigint.c +++ b/src/crypto/bigint.c @@ -26,6 +26,7 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); #include <stdint.h> #include <string.h> #include <assert.h> +#include <stdio.h> #include <ipxe/profile.h> #include <ipxe/bigint.h> @@ -38,6 +39,52 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); static struct profiler bigint_mod_profiler __profiler = { .name = "bigint_mod" }; +/** Minimum number of least significant bytes included in transcription */ +#define BIGINT_NTOA_LSB_MIN 16 + +/** + * Transcribe big integer (for debugging) + * + * @v value0 Element 0 of big integer to be transcribed + * @v size Number of elements + * @ret string Big integer in string form (may be abbreviated) + */ +const char * bigint_ntoa_raw ( const bigint_element_t *value0, + unsigned int size ) { + const bigint_t ( size ) __attribute__ (( may_alias )) + *value = ( ( const void * ) value0 ); + bigint_element_t element; + static char buf[256]; + unsigned int count; + int threshold; + uint8_t byte; + char *tmp; + int i; + + /* Calculate abbreviation threshold, if any */ + count = ( size * sizeof ( element ) ); + threshold = count; + if ( count >= ( ( sizeof ( buf ) - 1 /* NUL */ ) / 2 /* "xx" */ ) ) { + threshold -= ( ( sizeof ( buf ) - 3 /* "..." */ + - ( BIGINT_NTOA_LSB_MIN * 2 /* "xx" */ ) + - 1 /* NUL */ ) / 2 /* "xx" */ ); + } + + /* Transcribe bytes, abbreviating with "..." if necessary */ + for ( tmp = buf, i = ( count - 1 ) ; i >= 0 ; i-- ) { + element = value->element[ i / sizeof ( element ) ]; + byte = ( element >> ( 8 * ( i % sizeof ( element ) ) ) ); + tmp += sprintf ( tmp, "%02x", byte ); + if ( i == threshold ) { + tmp += sprintf ( tmp, "..." ); + i = BIGINT_NTOA_LSB_MIN; + } + } + assert ( tmp < ( buf + sizeof ( buf ) ) ); + + return buf; +} + /** * Conditionally swap big integers (in constant time) * diff --git a/src/include/ipxe/bigint.h b/src/include/ipxe/bigint.h index 2dd99380d..1cc606b89 100644 --- a/src/include/ipxe/bigint.h +++ b/src/include/ipxe/bigint.h @@ -41,6 +41,17 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); ( sizeof ( *(bigint) ) / sizeof ( (bigint)->element[0] ) ) /** + * Transcribe big integer (for debugging) + * + * @v value Big integer to be transcribed + * @ret string Big integer in string form (may be abbreviated) + */ +#define bigint_ntoa( value ) ( { \ + unsigned int size = bigint_size (value); \ + bigint_ntoa_raw ( (value)->element, size ); \ + } ) + +/** * Initialise big integer * * @v value Big integer to initialise @@ -360,6 +371,8 @@ bigint_msb_is_set_raw ( const bigint_element_t *value0, unsigned int size ) { return ( !! ( value->element[index] & ( 1UL << subindex ) ) ); } +const char * bigint_ntoa_raw ( const bigint_element_t *value0, + unsigned int size ); void bigint_init_raw ( bigint_element_t *value0, unsigned int size, const void *data, size_t len ); void bigint_done_raw ( const bigint_element_t *value0, unsigned int size, |