Squashed commit upgrading to mbedtls-2.28.1
Squash merging branch import/mbedtls-2.28.1
ebf1f6a58089 ("libmbedtls: compile new files added with 2.28.1")
3ffb51b58a54 ("libmbedtls: add SM2 curve")
c425755720b4 ("libmbedtls: mbedtls_mpi_exp_mod(): optimize mempool usage")
23493c822a82 ("libmbedtls: mbedtls_mpi_exp_mod(): reduce stack usage")
dcdca2348dff ("libmbedtls: mbedtls_mpi_exp_mod() initialize W")
dc2994976958 ("libmbedtls: fix no CRT issue")
c6628873b281 ("libmbedtls: add interfaces in mbedtls for context memory operation")
8acd202d3e55 ("libmedtls: mpi_miller_rabin: increase count limit")
37284e28d5d9 ("libmbedtls: add mbedtls_mpi_init_mempool()")
b499a75f29f3 ("libmbedtls: make mbedtls_mpi_mont*() available")
2080a8c96a5d ("mbedtls: configure mbedtls to reach for config")
e0858334327a ("mbedtls: remove default include/mbedtls/config.h")
dd9688e6b8ce ("Import mbedtls-2.28.1")
Signed-off-by: Jerome Forissier <jerome.forissier@linaro.org>
Acked-by: Jens Wiklander <jens.wiklander@linaro.org>
diff --git a/lib/libmbedtls/mbedtls/library/bignum.c b/lib/libmbedtls/mbedtls/library/bignum.c
index 31ef3ee..598a78c 100644
--- a/lib/libmbedtls/mbedtls/library/bignum.c
+++ b/lib/libmbedtls/mbedtls/library/bignum.c
@@ -41,7 +41,9 @@
#include "mbedtls/bn_mul.h"
#include "mbedtls/platform_util.h"
#include "mbedtls/error.h"
+#include "constant_time_internal.h"
+#include <limits.h>
#include <string.h>
#if defined(MBEDTLS_PLATFORM_C)
@@ -315,162 +317,6 @@
memcpy( Y, &T, sizeof( mbedtls_mpi ) );
}
-/**
- * Select between two sign values in constant-time.
- *
- * This is functionally equivalent to second ? a : b but uses only bit
- * operations in order to avoid branches.
- *
- * \param[in] a The first sign; must be either +1 or -1.
- * \param[in] b The second sign; must be either +1 or -1.
- * \param[in] second Must be either 1 (return b) or 0 (return a).
- *
- * \return The selected sign value.
- */
-static int mpi_safe_cond_select_sign( int a, int b, unsigned char second )
-{
- /* In order to avoid questions about what we can reasonnably assume about
- * the representations of signed integers, move everything to unsigned
- * by taking advantage of the fact that a and b are either +1 or -1. */
- unsigned ua = a + 1;
- unsigned ub = b + 1;
-
- /* second was 0 or 1, mask is 0 or 2 as are ua and ub */
- const unsigned mask = second << 1;
-
- /* select ua or ub */
- unsigned ur = ( ua & ~mask ) | ( ub & mask );
-
- /* ur is now 0 or 2, convert back to -1 or +1 */
- return( (int) ur - 1 );
-}
-
-/*
- * Conditionally assign dest = src, without leaking information
- * about whether the assignment was made or not.
- * dest and src must be arrays of limbs of size n.
- * assign must be 0 or 1.
- */
-static void mpi_safe_cond_assign( size_t n,
- mbedtls_mpi_uint *dest,
- const mbedtls_mpi_uint *src,
- unsigned char assign )
-{
- size_t i;
-
- /* MSVC has a warning about unary minus on unsigned integer types,
- * but this is well-defined and precisely what we want to do here. */
-#if defined(_MSC_VER)
-#pragma warning( push )
-#pragma warning( disable : 4146 )
-#endif
-
- /* all-bits 1 if assign is 1, all-bits 0 if assign is 0 */
- const mbedtls_mpi_uint mask = -assign;
-
-#if defined(_MSC_VER)
-#pragma warning( pop )
-#endif
-
- for( i = 0; i < n; i++ )
- dest[i] = ( src[i] & mask ) | ( dest[i] & ~mask );
-}
-
-/*
- * Conditionally assign X = Y, without leaking information
- * about whether the assignment was made or not.
- * (Leaking information about the respective sizes of X and Y is ok however.)
- */
-int mbedtls_mpi_safe_cond_assign( mbedtls_mpi *X, const mbedtls_mpi *Y, unsigned char assign )
-{
- int ret = 0;
- size_t i;
- mbedtls_mpi_uint limb_mask;
- MPI_VALIDATE_RET( X != NULL );
- MPI_VALIDATE_RET( Y != NULL );
-
- /* MSVC has a warning about unary minus on unsigned integer types,
- * but this is well-defined and precisely what we want to do here. */
-#if defined(_MSC_VER)
-#pragma warning( push )
-#pragma warning( disable : 4146 )
-#endif
-
- /* make sure assign is 0 or 1 in a time-constant manner */
- assign = (assign | (unsigned char)-assign) >> (sizeof( assign ) * 8 - 1);
- /* all-bits 1 if assign is 1, all-bits 0 if assign is 0 */
- limb_mask = -assign;
-
-#if defined(_MSC_VER)
-#pragma warning( pop )
-#endif
-
- MBEDTLS_MPI_CHK( mbedtls_mpi_grow( X, Y->n ) );
-
- X->s = mpi_safe_cond_select_sign( X->s, Y->s, assign );
-
- mpi_safe_cond_assign( Y->n, X->p, Y->p, assign );
-
- for( i = Y->n; i < X->n; i++ )
- X->p[i] &= ~limb_mask;
-
-cleanup:
- return( ret );
-}
-
-/*
- * Conditionally swap X and Y, without leaking information
- * about whether the swap was made or not.
- * Here it is not ok to simply swap the pointers, which whould lead to
- * different memory access patterns when X and Y are used afterwards.
- */
-int mbedtls_mpi_safe_cond_swap( mbedtls_mpi *X, mbedtls_mpi *Y, unsigned char swap )
-{
- int ret, s;
- size_t i;
- mbedtls_mpi_uint limb_mask;
- mbedtls_mpi_uint tmp;
- MPI_VALIDATE_RET( X != NULL );
- MPI_VALIDATE_RET( Y != NULL );
-
- if( X == Y )
- return( 0 );
-
- /* MSVC has a warning about unary minus on unsigned integer types,
- * but this is well-defined and precisely what we want to do here. */
-#if defined(_MSC_VER)
-#pragma warning( push )
-#pragma warning( disable : 4146 )
-#endif
-
- /* make sure swap is 0 or 1 in a time-constant manner */
- swap = (swap | (unsigned char)-swap) >> (sizeof( swap ) * 8 - 1);
- /* all-bits 1 if swap is 1, all-bits 0 if swap is 0 */
- limb_mask = -swap;
-
-#if defined(_MSC_VER)
-#pragma warning( pop )
-#endif
-
- MBEDTLS_MPI_CHK( mbedtls_mpi_grow( X, Y->n ) );
- MBEDTLS_MPI_CHK( mbedtls_mpi_grow( Y, X->n ) );
-
- s = X->s;
- X->s = mpi_safe_cond_select_sign( X->s, Y->s, swap );
- Y->s = mpi_safe_cond_select_sign( Y->s, s, swap );
-
-
- for( i = 0; i < X->n; i++ )
- {
- tmp = X->p[i];
- X->p[i] = ( X->p[i] & ~limb_mask ) | ( Y->p[i] & limb_mask );
- Y->p[i] = ( Y->p[i] & ~limb_mask ) | ( tmp & limb_mask );
- }
-
-cleanup:
- return( ret );
-}
-
/*
* Set value from integer
*/
@@ -1293,107 +1139,6 @@
return( 0 );
}
-/** Decide if an integer is less than the other, without branches.
- *
- * \param x First integer.
- * \param y Second integer.
- *
- * \return 1 if \p x is less than \p y, 0 otherwise
- */
-static unsigned ct_lt_mpi_uint( const mbedtls_mpi_uint x,
- const mbedtls_mpi_uint y )
-{
- mbedtls_mpi_uint ret;
- mbedtls_mpi_uint cond;
-
- /*
- * Check if the most significant bits (MSB) of the operands are different.
- */
- cond = ( x ^ y );
- /*
- * If the MSB are the same then the difference x-y will be negative (and
- * have its MSB set to 1 during conversion to unsigned) if and only if x<y.
- */
- ret = ( x - y ) & ~cond;
- /*
- * If the MSB are different, then the operand with the MSB of 1 is the
- * bigger. (That is if y has MSB of 1, then x<y is true and it is false if
- * the MSB of y is 0.)
- */
- ret |= y & cond;
-
-
- ret = ret >> ( biL - 1 );
-
- return (unsigned) ret;
-}
-
-/*
- * Compare signed values in constant time
- */
-int mbedtls_mpi_lt_mpi_ct( const mbedtls_mpi *X, const mbedtls_mpi *Y,
- unsigned *ret )
-{
- size_t i;
- /* The value of any of these variables is either 0 or 1 at all times. */
- unsigned cond, done, X_is_negative, Y_is_negative;
-
- MPI_VALIDATE_RET( X != NULL );
- MPI_VALIDATE_RET( Y != NULL );
- MPI_VALIDATE_RET( ret != NULL );
-
- if( X->n != Y->n )
- return MBEDTLS_ERR_MPI_BAD_INPUT_DATA;
-
- /*
- * Set sign_N to 1 if N >= 0, 0 if N < 0.
- * We know that N->s == 1 if N >= 0 and N->s == -1 if N < 0.
- */
- X_is_negative = ( X->s & 2 ) >> 1;
- Y_is_negative = ( Y->s & 2 ) >> 1;
-
- /*
- * If the signs are different, then the positive operand is the bigger.
- * That is if X is negative (X_is_negative == 1), then X < Y is true and it
- * is false if X is positive (X_is_negative == 0).
- */
- cond = ( X_is_negative ^ Y_is_negative );
- *ret = cond & X_is_negative;
-
- /*
- * This is a constant-time function. We might have the result, but we still
- * need to go through the loop. Record if we have the result already.
- */
- done = cond;
-
- for( i = X->n; i > 0; i-- )
- {
- /*
- * If Y->p[i - 1] < X->p[i - 1] then X < Y is true if and only if both
- * X and Y are negative.
- *
- * Again even if we can make a decision, we just mark the result and
- * the fact that we are done and continue looping.
- */
- cond = ct_lt_mpi_uint( Y->p[i - 1], X->p[i - 1] );
- *ret |= cond & ( 1 - done ) & X_is_negative;
- done |= cond;
-
- /*
- * If X->p[i - 1] < Y->p[i - 1] then X < Y is true if and only if both
- * X and Y are positive.
- *
- * Again even if we can make a decision, we just mark the result and
- * the fact that we are done and continue looping.
- */
- cond = ct_lt_mpi_uint( X->p[i - 1], Y->p[i - 1] );
- *ret |= cond & ( 1 - done ) & ( 1 - X_is_negative );
- done |= cond;
- }
-
- return( 0 );
-}
-
/*
* Compare signed values
*/
@@ -1634,17 +1379,17 @@
*/
int mbedtls_mpi_add_int( mbedtls_mpi *X, const mbedtls_mpi *A, mbedtls_mpi_sint b )
{
- mbedtls_mpi _B;
+ mbedtls_mpi B;
mbedtls_mpi_uint p[1];
MPI_VALIDATE_RET( X != NULL );
MPI_VALIDATE_RET( A != NULL );
p[0] = ( b < 0 ) ? -b : b;
- _B.s = ( b < 0 ) ? -1 : 1;
- _B.n = 1;
- _B.p = p;
+ B.s = ( b < 0 ) ? -1 : 1;
+ B.n = 1;
+ B.p = p;
- return( mbedtls_mpi_add_mpi( X, A, &_B ) );
+ return( mbedtls_mpi_add_mpi( X, A, &B ) );
}
/*
@@ -1652,17 +1397,17 @@
*/
int mbedtls_mpi_sub_int( mbedtls_mpi *X, const mbedtls_mpi *A, mbedtls_mpi_sint b )
{
- mbedtls_mpi _B;
+ mbedtls_mpi B;
mbedtls_mpi_uint p[1];
MPI_VALIDATE_RET( X != NULL );
MPI_VALIDATE_RET( A != NULL );
p[0] = ( b < 0 ) ? -b : b;
- _B.s = ( b < 0 ) ? -1 : 1;
- _B.n = 1;
- _B.p = p;
+ B.s = ( b < 0 ) ? -1 : 1;
+ B.n = 1;
+ B.p = p;
- return( mbedtls_mpi_sub_mpi( X, A, &_B ) );
+ return( mbedtls_mpi_sub_mpi( X, A, &B ) );
}
/** Helper for mbedtls_mpi multiplication.
@@ -2074,16 +1819,16 @@
const mbedtls_mpi *A,
mbedtls_mpi_sint b )
{
- mbedtls_mpi _B;
+ mbedtls_mpi B;
mbedtls_mpi_uint p[1];
MPI_VALIDATE_RET( A != NULL );
p[0] = ( b < 0 ) ? -b : b;
- _B.s = ( b < 0 ) ? -1 : 1;
- _B.n = 1;
- _B.p = p;
+ B.s = ( b < 0 ) ? -1 : 1;
+ B.n = 1;
+ B.p = p;
- return( mbedtls_mpi_div_mpi( Q, R, A, &_B ) );
+ return( mbedtls_mpi_div_mpi( Q, R, A, &B ) );
}
/*
@@ -2131,7 +1876,7 @@
/*
* handle trivial cases
*/
- if( b == 1 )
+ if( b == 1 || A->n == 0 )
{
*r = 0;
return( 0 );
@@ -2259,7 +2004,7 @@
* so d[n] == 1 and we want to set A to the result of the subtraction
* which is d - (2^biL)^n, i.e. the n least significant limbs of d.
* This exactly corresponds to a conditional assignment. */
- mpi_safe_cond_assign( n, A->p, d, (unsigned char) d[n] );
+ mbedtls_ct_mpi_uint_cond_assign( n, A->p, d, (unsigned char) d[n] );
}
void mbedtls_mpi_montmul( mbedtls_mpi *A, const mbedtls_mpi *B, const mbedtls_mpi *N, mbedtls_mpi_uint mm,
@@ -2291,42 +2036,6 @@
mpi_montred( A, N, mm, T );
}
-/*
- * Constant-flow boolean "equal" comparison:
- * return x == y
- *
- * This function can be used to write constant-time code by replacing branches
- * with bit operations - it can be used in conjunction with
- * mbedtls_ssl_cf_mask_from_bit().
- *
- * This function is implemented without using comparison operators, as those
- * might be translated to branches by some compilers on some platforms.
- */
-static size_t mbedtls_mpi_cf_bool_eq( size_t x, size_t y )
-{
- /* diff = 0 if x == y, non-zero otherwise */
- const size_t diff = x ^ y;
-
- /* MSVC has a warning about unary minus on unsigned integer types,
- * but this is well-defined and precisely what we want to do here. */
-#if defined(_MSC_VER)
-#pragma warning( push )
-#pragma warning( disable : 4146 )
-#endif
-
- /* diff_msb's most significant bit is equal to x != y */
- const size_t diff_msb = ( diff | (size_t) -diff );
-
-#if defined(_MSC_VER)
-#pragma warning( pop )
-#endif
-
- /* diff1 = (x != y) ? 1 : 0 */
- const size_t diff1 = diff_msb >> ( sizeof( diff_msb ) * 8 - 1 );
-
- return( 1 ^ diff1 );
-}
-
/**
* Select an MPI from a table without leaking the index.
*
@@ -2349,7 +2058,7 @@
for( size_t i = 0; i < T_size; i++ )
{
MBEDTLS_MPI_CHK( mbedtls_mpi_safe_cond_assign( R, &T[i],
- (unsigned char) mbedtls_mpi_cf_bool_eq( i, idx ) ) );
+ (unsigned char) mbedtls_ct_size_bool_eq( i, idx ) ) );
}
cleanup:
@@ -2361,7 +2070,7 @@
*/
int mbedtls_mpi_exp_mod( mbedtls_mpi *X, const mbedtls_mpi *A,
const mbedtls_mpi *E, const mbedtls_mpi *N,
- mbedtls_mpi *_RR )
+ mbedtls_mpi *prec_RR )
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
size_t wbits, wsize, one = 1;
@@ -2430,17 +2139,17 @@
/*
* If 1st call, pre-compute R^2 mod N
*/
- if( _RR == NULL || _RR->p == NULL )
+ if( prec_RR == NULL || prec_RR->p == NULL )
{
MBEDTLS_MPI_CHK( mbedtls_mpi_lset( &RR, 1 ) );
MBEDTLS_MPI_CHK( mbedtls_mpi_shift_l( &RR, N->n * 2 * biL ) );
MBEDTLS_MPI_CHK( mbedtls_mpi_mod_mpi( &RR, &RR, N ) );
- if( _RR != NULL )
- memcpy( _RR, &RR, sizeof( mbedtls_mpi ) );
+ if( prec_RR != NULL )
+ memcpy( prec_RR, &RR, sizeof( mbedtls_mpi ) );
}
else
- memcpy( &RR, _RR, sizeof( mbedtls_mpi ) );
+ memcpy( &RR, prec_RR, sizeof( mbedtls_mpi ) );
W = mempool_alloc( mbedtls_mpi_mempool,
sizeof( mbedtls_mpi ) * array_size_W );
@@ -2600,7 +2309,7 @@
mbedtls_mpi_free( &T ); mbedtls_mpi_free( &Apos );
mbedtls_mpi_free( &WW );
- if( _RR == NULL || _RR->p == NULL )
+ if( prec_RR == NULL || prec_RR->p == NULL )
mbedtls_mpi_free( &RR );
return( ret );
@@ -2685,7 +2394,7 @@
* TA-TB is even so the division by 2 has an integer result.
* Invariant (I) is preserved since any odd divisor of both TA and TB
* also divides |TA-TB|/2, and any odd divisor of both TA and |TA-TB|/2
- * also divides TB, and any odd divisior of both TB and |TA-TB|/2 also
+ * also divides TB, and any odd divisor of both TB and |TA-TB|/2 also
* divides TA.
*/
if( mbedtls_mpi_cmp_mpi( &TA, &TB ) >= 0 )