[crypto] Use generic implementations of slow-path big integer functions

In the original big integer implementation, big integers were entirely
opaque to the caller and only the architecture-dependent code knew any
details of the internal structure.

This has long since ceased to be the case: for the sake of arithmetic
efficiency, many portions of the codebase now presume that big
integers are represented as an array of elements, with each element
being a native-endian unsigned value (with the precise type being
chosen by the architecture-specific header file) and with the least
significant element being first in the array.

The functions bigint_init(), bigint_done(), bigint_is_zero(),
bigint_is_geq(), and bigint_max_bit_set() are never used on fast code
paths, and most architectures use a generic C implementation of these
functions.

Provide generic implementations of these slow-path functions to be
used on all architectures.

Signed-off-by: Michael Brown <mcb30@ipxe.org>
This commit is contained in:
Michael Brown
2026-06-13 15:28:52 +01:00
parent 05a459f795
commit e68ca57f46
8 changed files with 136 additions and 588 deletions
-112
View File
@@ -10,33 +10,10 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
#include <stdint.h>
#include <string.h>
#include <strings.h>
/** Element of a big integer */
typedef uint32_t bigint_element_t;
/**
* Initialise big integer
*
* @v value0 Element 0 of big integer to initialise
* @v size Number of elements
* @v data Raw data
* @v len Length of raw data
*/
static inline __attribute__ (( always_inline )) void
bigint_init_raw ( uint32_t *value0, unsigned int size,
const void *data, size_t len ) {
size_t pad_len = ( sizeof ( bigint_t ( size ) ) - len );
uint8_t *value_byte = ( ( void * ) value0 );
const uint8_t *data_byte = ( data + len );
/* Copy raw data in reverse order, padding with zeros */
while ( len-- )
*(value_byte++) = *(--data_byte);
while ( pad_len-- )
*(value_byte++) = 0;
}
/**
* Add big integers
*
@@ -182,76 +159,6 @@ bigint_shr_raw ( uint32_t *value0, unsigned int size ) {
return carry;
}
/**
* Test if big integer is equal to zero
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret is_zero Big integer is equal to zero
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_zero_raw ( const uint32_t *value0, unsigned int size ) {
const uint32_t *value = value0;
uint32_t value_i;
do {
value_i = *(value++);
if ( value_i )
break;
} while ( --size );
return ( value_i == 0 );
}
/**
* Compare big integers
*
* @v value0 Element 0 of big integer
* @v reference0 Element 0 of reference big integer
* @v size Number of elements
* @ret geq Big integer is greater than or equal to the reference
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_geq_raw ( const uint32_t *value0, const uint32_t *reference0,
unsigned int size ) {
const uint32_t *value = ( value0 + size );
const uint32_t *reference = ( reference0 + size );
uint32_t value_i;
uint32_t reference_i;
do {
value_i = *(--value);
reference_i = *(--reference);
if ( value_i != reference_i )
break;
} while ( --size );
return ( value_i >= reference_i );
}
/**
* Find highest bit set in big integer
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret max_bit Highest bit set + 1 (or 0 if no bits set)
*/
static inline __attribute__ (( always_inline )) int
bigint_max_set_bit_raw ( const uint32_t *value0, unsigned int size ) {
const uint32_t *value = ( value0 + size );
int max_bit = ( 8 * sizeof ( bigint_t ( size ) ) );
uint32_t value_i;
do {
value_i = *(--value);
max_bit -= ( 32 - fls ( value_i ) );
if ( value_i )
break;
} while ( --size );
return max_bit;
}
/**
* Grow big integer
*
@@ -284,25 +191,6 @@ bigint_shrink_raw ( const uint32_t *source0, unsigned int source_size __unused,
memcpy ( dest0, source0, sizeof ( bigint_t ( dest_size ) ) );
}
/**
* Finalise big integer
*
* @v value0 Element 0 of big integer to finalise
* @v size Number of elements
* @v out Output buffer
* @v len Length of output buffer
*/
static inline __attribute__ (( always_inline )) void
bigint_done_raw ( const uint32_t *value0, unsigned int size __unused,
void *out, size_t len ) {
const uint8_t *value_byte = ( ( const void * ) value0 );
uint8_t *out_byte = ( out + len );
/* Copy raw data in reverse order */
while ( len-- )
*(--out_byte) = *(value_byte++);
}
/**
* Multiply big integer elements
*
-112
View File
@@ -11,33 +11,10 @@ FILE_SECBOOT ( PERMITTED );
#include <stdint.h>
#include <string.h>
#include <strings.h>
/** Element of a big integer */
typedef uint64_t bigint_element_t;
/**
* Initialise big integer
*
* @v value0 Element 0 of big integer to initialise
* @v size Number of elements
* @v data Raw data
* @v len Length of raw data
*/
static inline __attribute__ (( always_inline )) void
bigint_init_raw ( uint64_t *value0, unsigned int size,
const void *data, size_t len ) {
size_t pad_len = ( sizeof ( bigint_t ( size ) ) - len );
uint8_t *value_byte = ( ( void * ) value0 );
const uint8_t *data_byte = ( data + len );
/* Copy raw data in reverse order, padding with zeros */
while ( len-- )
*(value_byte++) = *(--data_byte);
while ( pad_len-- )
*(value_byte++) = 0;
}
/**
* Add big integers
*
@@ -183,76 +160,6 @@ bigint_shr_raw ( uint64_t *value0, unsigned int size ) {
return ( low & 1 );
}
/**
* Test if big integer is equal to zero
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret is_zero Big integer is equal to zero
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_zero_raw ( const uint64_t *value0, unsigned int size ) {
const uint64_t *value = value0;
uint64_t value_i;
do {
value_i = *(value++);
if ( value_i )
break;
} while ( --size );
return ( value_i == 0 );
}
/**
* Compare big integers
*
* @v value0 Element 0 of big integer
* @v reference0 Element 0 of reference big integer
* @v size Number of elements
* @ret geq Big integer is greater than or equal to the reference
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_geq_raw ( const uint64_t *value0, const uint64_t *reference0,
unsigned int size ) {
const uint64_t *value = ( value0 + size );
const uint64_t *reference = ( reference0 + size );
uint64_t value_i;
uint64_t reference_i;
do {
value_i = *(--value);
reference_i = *(--reference);
if ( value_i != reference_i )
break;
} while ( --size );
return ( value_i >= reference_i );
}
/**
* Find highest bit set in big integer
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret max_bit Highest bit set + 1 (or 0 if no bits set)
*/
static inline __attribute__ (( always_inline )) int
bigint_max_set_bit_raw ( const uint64_t *value0, unsigned int size ) {
const uint64_t *value = ( value0 + size );
int max_bit = ( 8 * sizeof ( bigint_t ( size ) ) );
uint64_t value_i;
do {
value_i = *(--value);
max_bit -= ( 64 - fls ( value_i ) );
if ( value_i )
break;
} while ( --size );
return max_bit;
}
/**
* Grow big integer
*
@@ -285,25 +192,6 @@ bigint_shrink_raw ( const uint64_t *source0, unsigned int source_size __unused,
memcpy ( dest0, source0, sizeof ( bigint_t ( dest_size ) ) );
}
/**
* Finalise big integer
*
* @v value0 Element 0 of big integer to finalise
* @v size Number of elements
* @v out Output buffer
* @v len Length of output buffer
*/
static inline __attribute__ (( always_inline )) void
bigint_done_raw ( const uint64_t *value0, unsigned int size __unused,
void *out, size_t len ) {
const uint8_t *value_byte = ( ( const void * ) value0 );
uint8_t *out_byte = ( out + len );
/* Copy raw data in reverse order */
while ( len-- )
*(--out_byte) = *(value_byte++);
}
/**
* Multiply big integer elements
*
-112
View File
@@ -11,33 +11,10 @@ FILE_SECBOOT ( PERMITTED );
#include <stdint.h>
#include <string.h>
#include <strings.h>
/** Element of a big integer */
typedef uint64_t bigint_element_t;
/**
* Initialise big integer
*
* @v value0 Element 0 of big integer to initialise
* @v size Number of elements
* @v data Raw data
* @v len Length of raw data
*/
static inline __attribute__ (( always_inline )) void
bigint_init_raw ( uint64_t *value0, unsigned int size,
const void *data, size_t len ) {
size_t pad_len = ( sizeof ( bigint_t ( size ) ) - len );
uint8_t *value_byte = ( ( void * ) value0 );
const uint8_t *data_byte = ( data + len );
/* Copy raw data in reverse order, padding with zeros */
while ( len-- )
*(value_byte++) = *(--data_byte);
while ( pad_len-- )
*(value_byte++) = 0;
}
/**
* Add big integers
*
@@ -226,76 +203,6 @@ bigint_shr_raw ( uint64_t *value0, unsigned int size ) {
return ( carry & 1 );
}
/**
* Test if big integer is equal to zero
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret is_zero Big integer is equal to zero
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_zero_raw ( const uint64_t *value0, unsigned int size ) {
const uint64_t *value = value0;
uint64_t value_i;
do {
value_i = *(value++);
if ( value_i )
break;
} while ( --size );
return ( value_i == 0 );
}
/**
* Compare big integers
*
* @v value0 Element 0 of big integer
* @v reference0 Element 0 of reference big integer
* @v size Number of elements
* @ret geq Big integer is greater than or equal to the reference
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_geq_raw ( const uint64_t *value0, const uint64_t *reference0,
unsigned int size ) {
const uint64_t *value = ( value0 + size );
const uint64_t *reference = ( reference0 + size );
uint64_t value_i;
uint64_t reference_i;
do {
value_i = *(--value);
reference_i = *(--reference);
if ( value_i != reference_i )
break;
} while ( --size );
return ( value_i >= reference_i );
}
/**
* Find highest bit set in big integer
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret max_bit Highest bit set + 1 (or 0 if no bits set)
*/
static inline __attribute__ (( always_inline )) int
bigint_max_set_bit_raw ( const uint64_t *value0, unsigned int size ) {
const uint64_t *value = ( value0 + size );
int max_bit = ( 8 * sizeof ( bigint_t ( size ) ) );
uint64_t value_i;
do {
value_i = *(--value);
max_bit -= ( 64 - fls ( value_i ) );
if ( value_i )
break;
} while ( --size );
return max_bit;
}
/**
* Grow big integer
*
@@ -328,25 +235,6 @@ bigint_shrink_raw ( const uint64_t *source0, unsigned int source_size __unused,
memcpy ( dest0, source0, sizeof ( bigint_t ( dest_size ) ) );
}
/**
* Finalise big integer
*
* @v value0 Element 0 of big integer to finalise
* @v size Number of elements
* @v out Output buffer
* @v len Length of output buffer
*/
static inline __attribute__ (( always_inline )) void
bigint_done_raw ( const uint64_t *value0, unsigned int size __unused,
void *out, size_t len ) {
const uint8_t *value_byte = ( ( const void * ) value0 );
uint8_t *out_byte = ( out + len );
/* Copy raw data in reverse order */
while ( len-- )
*(--out_byte) = *(value_byte++);
}
/**
* Multiply big integer elements
*
-112
View File
@@ -11,33 +11,10 @@ FILE_SECBOOT ( PERMITTED );
#include <stdint.h>
#include <string.h>
#include <strings.h>
/** Element of a big integer */
typedef unsigned long bigint_element_t;
/**
* Initialise big integer
*
* @v value0 Element 0 of big integer to initialise
* @v size Number of elements
* @v data Raw data
* @v len Length of raw data
*/
static inline __attribute__ (( always_inline )) void
bigint_init_raw ( unsigned long *value0, unsigned int size,
const void *data, size_t len ) {
size_t pad_len = ( sizeof ( bigint_t ( size ) ) - len );
uint8_t *value_byte = ( ( void * ) value0 );
const uint8_t *data_byte = ( data + len );
/* Copy raw data in reverse order, padding with zeros */
while ( len-- )
*(value_byte++) = *(--data_byte);
while ( pad_len-- )
*(value_byte++) = 0;
}
/**
* Add big integers
*
@@ -221,76 +198,6 @@ bigint_shr_raw ( unsigned long *value0, unsigned int size ) {
return ( !! carry );
}
/**
* Test if big integer is equal to zero
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret is_zero Big integer is equal to zero
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_zero_raw ( const unsigned long *value0, unsigned int size ) {
const unsigned long *value = value0;
unsigned long value_i;
do {
value_i = *(value++);
if ( value_i )
break;
} while ( --size );
return ( value_i == 0 );
}
/**
* Compare big integers
*
* @v value0 Element 0 of big integer
* @v reference0 Element 0 of reference big integer
* @v size Number of elements
* @ret geq Big integer is greater than or equal to the reference
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_geq_raw ( const unsigned long *value0,
const unsigned long *reference0, unsigned int size ) {
const unsigned long *value = ( value0 + size );
const unsigned long *reference = ( reference0 + size );
unsigned long value_i;
unsigned long reference_i;
do {
value_i = *(--value);
reference_i = *(--reference);
if ( value_i != reference_i )
break;
} while ( --size );
return ( value_i >= reference_i );
}
/**
* Find highest bit set in big integer
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret max_bit Highest bit set + 1 (or 0 if no bits set)
*/
static inline __attribute__ (( always_inline )) int
bigint_max_set_bit_raw ( const unsigned long *value0, unsigned int size ) {
const unsigned long *value = ( value0 + size );
int max_bit = ( 8 * sizeof ( bigint_t ( size ) ) );
unsigned long value_i;
do {
value_i = *(--value);
max_bit -= ( ( 8 * sizeof ( *value0 ) ) - fls ( value_i ) );
if ( value_i )
break;
} while ( --size );
return max_bit;
}
/**
* Grow big integer
*
@@ -324,25 +231,6 @@ bigint_shrink_raw ( const unsigned long *source0,
memcpy ( dest0, source0, sizeof ( bigint_t ( dest_size ) ) );
}
/**
* Finalise big integer
*
* @v value0 Element 0 of big integer to finalise
* @v size Number of elements
* @v out Output buffer
* @v len Length of output buffer
*/
static inline __attribute__ (( always_inline )) void
bigint_done_raw ( const unsigned long *value0, unsigned int size __unused,
void *out, size_t len ) {
const uint8_t *value_byte = ( ( const void * ) value0 );
uint8_t *out_byte = ( out + len );
/* Copy raw data in reverse order */
while ( len-- )
*(--out_byte) = *(value_byte++);
}
/**
* Multiply big integer elements
*
-140
View File
@@ -10,45 +10,10 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
FILE_SECBOOT ( PERMITTED );
#include <stdint.h>
#include <string.h>
/** Element of a big integer */
typedef uint32_t bigint_element_t;
/**
* Initialise big integer
*
* @v value0 Element 0 of big integer to initialise
* @v size Number of elements
* @v data Raw data
* @v len Length of raw data
*/
static inline __attribute__ (( always_inline )) void
bigint_init_raw ( uint32_t *value0, unsigned int size,
const void *data, size_t len ) {
bigint_t ( size ) __attribute__ (( may_alias )) *value =
( ( void * ) value0 );
long pad_len = ( sizeof ( *value ) - len );
void *discard_D;
long discard_c;
/* Copy raw data in reverse order, padding with zeros */
__asm__ __volatile__ ( "jecxz 2f\n\t"
"\n1:\n\t"
"movb -1(%3,%1), %%al\n\t"
"stosb\n\t"
"loop 1b\n\t"
"\n2:\n\t"
"xorl %%eax, %%eax\n\t"
"mov %4, %1\n\t"
"rep stosb\n\t"
: "=&D" ( discard_D ), "=&c" ( discard_c ),
"+m" ( *value )
: "r" ( data ), "g" ( pad_len ), "0" ( value0 ),
"1" ( len )
: "eax" );
}
/**
* Add big integers
*
@@ -164,81 +129,6 @@ bigint_shr_raw ( uint32_t *value0, unsigned int size ) {
return out;
}
/**
* Test if big integer is equal to zero
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret is_zero Big integer is equal to zero
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_zero_raw ( const uint32_t *value0, unsigned int size ) {
void *discard_D;
long discard_c;
int result;
__asm__ __volatile__ ( "xor %0, %0\n\t" /* Set ZF */
"repe scasl\n\t"
"sete %b0\n\t"
: "=&a" ( result ), "=&D" ( discard_D ),
"=&c" ( discard_c )
: "1" ( value0 ), "2" ( size ) );
return result;
}
/**
* Compare big integers
*
* @v value0 Element 0 of big integer
* @v reference0 Element 0 of reference big integer
* @v size Number of elements
* @ret geq Big integer is greater than or equal to the reference
*/
static inline __attribute__ (( always_inline, pure )) int
bigint_is_geq_raw ( const uint32_t *value0, const uint32_t *reference0,
unsigned int size ) {
long discard_c;
long discard_tmp;
int result;
__asm__ __volatile__ ( "\n1:\n\t"
"movl -4(%3, %1, 4), %k2\n\t"
"cmpl -4(%4, %1, 4), %k2\n\t"
"loope 1b\n\t"
"setae %b0\n\t"
: "=q" ( result ), "=&c" ( discard_c ),
"=&r" ( discard_tmp )
: "r" ( value0 ), "r" ( reference0 ),
"0" ( 0 ), "1" ( size ) );
return result;
}
/**
* Find highest bit set in big integer
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret max_bit Highest bit set + 1 (or 0 if no bits set)
*/
static inline __attribute__ (( always_inline )) int
bigint_max_set_bit_raw ( const uint32_t *value0, unsigned int size ) {
long discard_c;
int result;
__asm__ __volatile__ ( "\n1:\n\t"
"bsrl -4(%2,%1,4), %0\n\t"
"loopz 1b\n\t"
"rol %1\n\t" /* Does not affect ZF */
"rol %1\n\t"
"leal 1(%k0,%k1,8), %k0\n\t"
"jnz 2f\n\t"
"xor %0, %0\n\t"
"\n2:\n\t"
: "=&r" ( result ), "=&c" ( discard_c )
: "r" ( value0 ), "1" ( size ) );
return result;
}
/**
* Grow big integer
*
@@ -293,36 +183,6 @@ bigint_shrink_raw ( const uint32_t *source0, unsigned int source_size __unused,
: "eax" );
}
/**
* Finalise big integer
*
* @v value0 Element 0 of big integer to finalise
* @v size Number of elements
* @v out Output buffer
* @v len Length of output buffer
*/
static inline __attribute__ (( always_inline )) void
bigint_done_raw ( const uint32_t *value0, unsigned int size __unused,
void *out, size_t len ) {
struct {
uint8_t bytes[len];
} __attribute__ (( may_alias )) *out_bytes = out;
void *discard_D;
long discard_c;
/* Copy raw data in reverse order */
__asm__ __volatile__ ( "jecxz 2f\n\t"
"\n1:\n\t"
"movb -1(%3,%1), %%al\n\t"
"stosb\n\t"
"loop 1b\n\t"
"\n2:\n\t"
: "=&D" ( discard_D ), "=&c" ( discard_c ),
"+m" ( *out_bytes )
: "r" ( value0 ), "0" ( out ), "1" ( len )
: "eax" );
}
/**
* Multiply big integer elements
*
+134
View File
@@ -26,7 +26,9 @@ FILE_SECBOOT ( PERMITTED );
#include <stdint.h>
#include <string.h>
#include <strings.h>
#include <assert.h>
#include <byteswap.h>
#include <stdio.h>
#include <ipxe/bigint.h>
@@ -81,6 +83,138 @@ const char * bigint_ntoa_raw ( const bigint_element_t *value0,
return buf;
}
/**
* Initialise big integer
*
* @v value0 Element 0 of big integer to initialise
* @v size Number of elements
* @v data Raw data
* @v len Length of raw data
*/
void bigint_init_raw ( bigint_element_t *value0, unsigned int size,
const void *data, size_t len ) {
bigint_t ( size ) __attribute__ (( may_alias ))
*value = ( ( void * ) value0 );
uint8_t *value_byte = ( ( void * ) value0 );
const uint8_t *data_byte = data;
unsigned int toggle;
unsigned int i;
/* Zero big integer */
memset ( value, 0, sizeof ( *value ) );
/* Copy data, byte-swapping as needed */
toggle = ( ( __BYTE_ORDER == __LITTLE_ENDIAN ) ? 0 :
( sizeof ( value->element[0] ) - 1 ) );
for ( i = 0 ; len-- ; i++ )
value_byte[ i ^ toggle ] = data_byte[len];
}
/**
* Finalise big integer
*
* @v value0 Element 0 of big integer to finalise
* @v size Number of elements
* @v out Output buffer
* @v len Length of output buffer
*/
void bigint_done_raw ( const bigint_element_t *value0, unsigned int size,
void *out, size_t len ) {
const bigint_t ( size ) __attribute__ (( may_alias ))
*value = ( ( const void * ) value0 );
const uint8_t *value_byte = ( ( const void * ) value0 );
uint8_t *out_byte = out;
unsigned int toggle;
unsigned int i;
/* Zero output buffer */
memset ( out, 0, len );
/* Copy data, byte-swapping as needed */
toggle = ( ( __BYTE_ORDER == __LITTLE_ENDIAN ) ? 0 :
( sizeof ( value->element[0] ) - 1 ) );
for ( i = 0 ; len-- ; i++ )
out_byte[len] = value_byte[ i ^ toggle ];
}
/**
* Test if big integer is equal to zero
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret is_zero Big integer is equal to zero
*/
int bigint_is_zero_raw ( const bigint_element_t *value0, unsigned int size ) {
const bigint_t ( size ) __attribute__ (( may_alias )) *value =
( ( const void * ) value0 );
bigint_element_t or;
unsigned int i;
/* Construct binary OR of all elements */
for ( i = 0, or = 0 ; i < size ; i++ )
or |= value->element[i];
return ( or == 0 );
}
/**
* Compare big integers
*
* @v value0 Element 0 of big integer
* @v reference0 Element 0 of reference big integer
* @v size Number of elements
* @ret geq Big integer is greater than or equal to the reference
*/
int bigint_is_geq_raw ( const bigint_element_t *value0,
const bigint_element_t *reference0,
unsigned int size ) {
const bigint_t ( size ) __attribute__ (( may_alias )) *value =
( ( const void * ) value0 );
const bigint_t ( size ) __attribute__ (( may_alias )) *reference =
( ( const void * ) reference0 );
bigint_element_t value_element;
bigint_element_t reference_element;
/* Find highest differing element */
do {
value_element = value->element[ size - 1 ];
reference_element = reference->element[ size - 1 ];
if ( value_element != reference_element )
break;
} while ( --size );
return ( value_element >= reference_element );
}
/**
* Find highest bit set in big integer
*
* @v value0 Element 0 of big integer
* @v size Number of elements
* @ret max_bit Highest bit set + 1 (or 0 if no bits set)
*/
int bigint_max_set_bit_raw ( const bigint_element_t *value0,
unsigned int size ) {
const bigint_t ( size ) __attribute__ (( may_alias )) *value =
( ( const void * ) value0 );
bigint_element_t element;
unsigned int max_bit;
unsigned int i;
/* Find highest set bit in highest non-zero element */
max_bit = ( sizeof ( *value ) * 8 );
for ( i = 0 ; i < size ; i++ ) {
element = value->element[ size - i - 1 ];
max_bit -= ( sizeof ( element) * 8 );
if ( element ) {
max_bit += flsll ( element );
break;
}
}
return max_bit;
}
/**
* Conditionally swap big integers (in constant time)
*
+1
View File
@@ -42,6 +42,7 @@ FILE_SECBOOT ( PERMITTED );
*/
#include <stdint.h>
#include <string.h>
#include <errno.h>
#include <ipxe/ffdhe.h>
+1
View File
@@ -45,6 +45,7 @@ FILE_SECBOOT ( PERMITTED );
* implementation of the big integer operations.
*/
#include <string.h>
#include <errno.h>
#include <ipxe/weierstrass.h>