Convert curve 448 to use ecp core functions

Signed-off-by: Paul Elliott <paul.elliott@arm.com>
This commit is contained in:
Paul Elliott 2023-05-01 22:30:54 +01:00
parent f0806bee66
commit 4fa8334bae
3 changed files with 71 additions and 33 deletions

View File

@ -22,6 +22,7 @@
#if defined(MBEDTLS_ECP_LIGHT)
#include "mbedtls/ecp.h"
#include "mbedtls/platform.h"
#include "mbedtls/platform_util.h"
#include "mbedtls/error.h"
@ -4608,7 +4609,7 @@ static int ecp_mod_p255(mbedtls_mpi *);
#if defined(MBEDTLS_ECP_DP_CURVE448_ENABLED)
static int ecp_mod_p448(mbedtls_mpi *);
MBEDTLS_STATIC_TESTABLE
int mbedtls_ecp_mod_p448(mbedtls_mpi *);
int mbedtls_ecp_mod_p448(mbedtls_mpi_uint *, size_t);
#endif
#if defined(MBEDTLS_ECP_DP_SECP192K1_ENABLED)
static int ecp_mod_p192k1(mbedtls_mpi *);
@ -5455,7 +5456,18 @@ static int ecp_mod_p255(mbedtls_mpi *N)
static int ecp_mod_p448(mbedtls_mpi *N)
{
return mbedtls_ecp_mod_p448(N);
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
size_t expected_width = 2 * ((448 + biL - 1) / biL);
/* This is required as some tests and use cases do not pass in a Bignum of
* the correct size, and expect the growth to be done automatically, which
* will no longer happen. */
MBEDTLS_MPI_CHK(mbedtls_mpi_grow(N, expected_width));
ret = mbedtls_ecp_mod_p448(N->p, N->n);
cleanup:
return ret;
}
/*
@ -5470,56 +5482,82 @@ static int ecp_mod_p448(mbedtls_mpi *N)
* the reduction with 224-bit limbs, since mpi_add_mpi will then use 64-bit adds.
*/
MBEDTLS_STATIC_TESTABLE
int mbedtls_ecp_mod_p448(mbedtls_mpi *N)
int mbedtls_ecp_mod_p448(mbedtls_mpi_uint *N, size_t N_limbs)
{
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
size_t i;
mbedtls_mpi M, Q;
mbedtls_mpi_uint Mp[P448_WIDTH + 1], Qp[P448_WIDTH];
int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
if (N->n <= P448_WIDTH) {
if (N_limbs <= P448_WIDTH) {
return 0;
}
/* M = A1 */
M.s = 1;
M.n = N->n - (P448_WIDTH);
if (M.n > P448_WIDTH) {
size_t M_limbs = N_limbs - (P448_WIDTH);
size_t Q_limbs = M_limbs;
if (M_limbs > P448_WIDTH) {
/* Shouldn't be called with N larger than 2^896! */
return MBEDTLS_ERR_ECP_BAD_INPUT_DATA;
}
M.p = Mp;
memset(Mp, 0, sizeof(Mp));
memcpy(Mp, N->p + P448_WIDTH, M.n * sizeof(mbedtls_mpi_uint));
/* N = A0 */
for (i = P448_WIDTH; i < N->n; i++) {
N->p[i] = 0;
/* Extra limb for carry below. */
M_limbs++;
mbedtls_mpi_uint *M = mbedtls_calloc(M_limbs, ciL);
if (M == NULL) {
return MBEDTLS_ERR_ECP_ALLOC_FAILED;
}
/* N += A1 */
MBEDTLS_MPI_CHK(mbedtls_mpi_add_mpi(N, N, &M));
/* M = A1 */
memset(M, 0, (M_limbs * ciL));
/* Do not copy into the overflow limb, as this would read past the end of
* N. */
memcpy(M, N + P448_WIDTH, ((M_limbs - 1) * ciL));
/* N = A0 */
for (i = P448_WIDTH; i < N_limbs; i++) {
N[i] = 0;
}
/* N += A1 - Carry here dealt with by oversize M and N. */
(void) mbedtls_mpi_core_add(N, N, M, M_limbs);
/* Q = B1, N += B1 */
Q = M;
Q.p = Qp;
memcpy(Qp, Mp, sizeof(Qp));
MBEDTLS_MPI_CHK(mbedtls_mpi_shift_r(&Q, 224));
MBEDTLS_MPI_CHK(mbedtls_mpi_add_mpi(N, N, &Q));
mbedtls_mpi_uint *Q = mbedtls_calloc(Q_limbs, ciL);
if (Q == NULL) {
ret = MBEDTLS_ERR_ECP_ALLOC_FAILED;
goto cleanup;
}
memcpy(Q, M, (Q_limbs * ciL));
mbedtls_mpi_core_shift_r(Q, Q_limbs, 224);
/* No carry here - only max 224 bits */
(void) mbedtls_mpi_core_add(N, N, Q, Q_limbs);
/* M = (B0 + B1) * 2^224, N += M */
if (sizeof(mbedtls_mpi_uint) > 4) {
Mp[P224_WIDTH_MIN] &= ((mbedtls_mpi_uint)-1) >> (P224_UNUSED_BITS);
M[P224_WIDTH_MIN] &= ((mbedtls_mpi_uint)-1) >> (P224_UNUSED_BITS);
}
for (i = P224_WIDTH_MAX; i < M.n; ++i) {
Mp[i] = 0;
for (i = P224_WIDTH_MAX; i < M_limbs; ++i) {
M[i] = 0;
}
MBEDTLS_MPI_CHK(mbedtls_mpi_add_mpi(&M, &M, &Q));
M.n = P448_WIDTH + 1; /* Make room for shifted carry bit from the addition */
MBEDTLS_MPI_CHK(mbedtls_mpi_shift_l(&M, 224));
MBEDTLS_MPI_CHK(mbedtls_mpi_add_mpi(N, N, &M));
(void) mbedtls_mpi_core_add(M, M, Q, Q_limbs);
/* Shifted carry bit from the addition is dealt with by oversize M */
mbedtls_mpi_core_shift_l(M, M_limbs, 224);
(void) mbedtls_mpi_core_add(N, N, M, M_limbs);
ret = 0;
cleanup:
mbedtls_free(M);
mbedtls_free(Q);
return ret;
}
#endif /* MBEDTLS_ECP_DP_CURVE448_ENABLED */

View File

@ -196,7 +196,7 @@ int mbedtls_ecp_mod_p256k1(mbedtls_mpi *N);
#if defined(MBEDTLS_ECP_DP_CURVE448_ENABLED)
MBEDTLS_STATIC_TESTABLE
int mbedtls_ecp_mod_p448(mbedtls_mpi *N);
int mbedtls_ecp_mod_p448(mbedtls_mpi_uint *N, size_t N_limbs);
#endif /* MBEDTLS_ECP_DP_CURVE448_ENABLED */

View File

@ -1499,7 +1499,7 @@ void ecp_mod_p448(char *input_N,
TEST_LE_U(X.n, 2 * limbs);
TEST_EQUAL(res.n, limbs);
TEST_EQUAL(mbedtls_ecp_mod_p448(&X), 0);
TEST_EQUAL(mbedtls_ecp_mod_p448(X.p, X.n), 0);
TEST_EQUAL(mbedtls_mpi_mod_mpi(&X, &X, &N), 0);
TEST_LE_U(mbedtls_mpi_core_bitlen(X.p, X.n), 448);
ASSERT_COMPARE(X.p, bytes, res.p, bytes);