From 66ba48a3c8e6522b48acffca9cb6beb7c9d7a23e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Manuel=20P=C3=A9gouri=C3=A9-Gonnard?= Date: Thu, 27 Apr 2017 11:38:26 +0200 Subject: [PATCH] Make ECDH functions actually restartable --- include/mbedtls/ecdh.h | 3 ++ library/ecdh.c | 86 ++++++++++++++++++++++++++----- tests/suites/test_suite_ecdh.data | 12 +++++ 3 files changed, 89 insertions(+), 12 deletions(-) diff --git a/include/mbedtls/ecdh.h b/include/mbedtls/ecdh.h index 506a1cfb9..e707558a8 100644 --- a/include/mbedtls/ecdh.h +++ b/include/mbedtls/ecdh.h @@ -52,6 +52,9 @@ typedef struct mbedtls_ecp_point Vi; /*!< blinding value (for later) */ mbedtls_ecp_point Vf; /*!< un-blinding value (for later) */ mbedtls_mpi _d; /*!< previous d (for later) */ +#if defined(MBEDTLS_ECP_RESTARTABLE) + mbedtls_ecp_restart_ctx rs; /*!< restart context for EC computations */ +#endif } mbedtls_ecdh_context; diff --git a/library/ecdh.c b/library/ecdh.c index c0a814731..b2859c4b6 100644 --- a/library/ecdh.c +++ b/library/ecdh.c @@ -39,22 +39,48 @@ #include /* - * Generate public key: simple wrapper around mbedtls_ecp_gen_keypair + * Generate public key (restartable version) + */ +static int ecdh_gen_public_restartable( mbedtls_ecp_group *grp, + mbedtls_mpi *d, mbedtls_ecp_point *Q, + int (*f_rng)(void *, unsigned char *, size_t), + void *p_rng, + mbedtls_ecp_restart_ctx *rs_ctx ) +{ + int ret; + + /* If multiplication is in progress, we already generated a privkey */ +#if defined(MBEDTLS_ECP_RESTARTABLE) + if( rs_ctx == NULL || rs_ctx->rsm == NULL ) +#endif + MBEDTLS_MPI_CHK( mbedtls_ecp_gen_privkey( grp, d, f_rng, p_rng ) ); + + MBEDTLS_MPI_CHK( mbedtls_ecp_mul_restartable( grp, Q, d, &grp->G, + f_rng, p_rng, rs_ctx ) ); + +cleanup: + return( ret ); +} + +/* + * Generate public key */ int mbedtls_ecdh_gen_public( mbedtls_ecp_group *grp, mbedtls_mpi *d, mbedtls_ecp_point *Q, int (*f_rng)(void *, unsigned char *, size_t), void *p_rng ) { - return mbedtls_ecp_gen_keypair( grp, d, Q, f_rng, p_rng ); + return( ecdh_gen_public_restartable( grp, d, Q, f_rng, p_rng, NULL ) ); } /* * Compute shared secret (SEC1 3.3.1) */ -int mbedtls_ecdh_compute_shared( mbedtls_ecp_group *grp, mbedtls_mpi *z, +static int ecdh_compute_shared_restartable( mbedtls_ecp_group *grp, + mbedtls_mpi *z, const mbedtls_ecp_point *Q, const mbedtls_mpi *d, int (*f_rng)(void *, unsigned char *, size_t), - void *p_rng ) + void *p_rng, + mbedtls_ecp_restart_ctx *rs_ctx ) { int ret; mbedtls_ecp_point P; @@ -66,7 +92,8 @@ int mbedtls_ecdh_compute_shared( mbedtls_ecp_group *grp, mbedtls_mpi *z, */ MBEDTLS_MPI_CHK( mbedtls_ecp_check_pubkey( grp, Q ) ); - MBEDTLS_MPI_CHK( mbedtls_ecp_mul( grp, &P, d, Q, f_rng, p_rng ) ); + MBEDTLS_MPI_CHK( mbedtls_ecp_mul_restartable( grp, &P, d, Q, + f_rng, p_rng, rs_ctx ) ); if( mbedtls_ecp_is_zero( &P ) ) { @@ -82,12 +109,28 @@ cleanup: return( ret ); } +/* + * Compute shared secret (SEC1 3.3.1) + */ +int mbedtls_ecdh_compute_shared( mbedtls_ecp_group *grp, mbedtls_mpi *z, + const mbedtls_ecp_point *Q, const mbedtls_mpi *d, + int (*f_rng)(void *, unsigned char *, size_t), + void *p_rng ) +{ + return( ecdh_compute_shared_restartable( grp, z, Q, d, + f_rng, p_rng, NULL ) ); +} + /* * Initialize context */ void mbedtls_ecdh_init( mbedtls_ecdh_context *ctx ) { memset( ctx, 0, sizeof( mbedtls_ecdh_context ) ); + +#if defined(MBEDTLS_ECP_RESTARTABLE) + mbedtls_ecp_restart_init( &ctx->rs ); +#endif } /* @@ -106,6 +149,10 @@ void mbedtls_ecdh_free( mbedtls_ecdh_context *ctx ) mbedtls_mpi_free( &ctx->d ); mbedtls_mpi_free( &ctx->z ); mbedtls_mpi_free( &ctx->_d ); + +#if defined(MBEDTLS_ECP_RESTARTABLE) + mbedtls_ecp_restart_free( &ctx->rs ); +#endif } /* @@ -122,12 +169,17 @@ int mbedtls_ecdh_make_params( mbedtls_ecdh_context *ctx, size_t *olen, { int ret; size_t grp_len, pt_len; + mbedtls_ecp_restart_ctx *rs_ctx = NULL; if( ctx == NULL || ctx->grp.pbits == 0 ) return( MBEDTLS_ERR_ECP_BAD_INPUT_DATA ); - if( ( ret = mbedtls_ecdh_gen_public( &ctx->grp, &ctx->d, &ctx->Q, f_rng, p_rng ) ) - != 0 ) +#if defined(MBEDTLS_ECP_RESTARTABLE) + rs_ctx = &ctx->rs; +#endif + + if( ( ret = ecdh_gen_public_restartable( &ctx->grp, &ctx->d, &ctx->Q, + f_rng, p_rng, rs_ctx ) ) != 0 ) return( ret ); if( ( ret = mbedtls_ecp_tls_write_group( &ctx->grp, &grp_len, buf, blen ) ) @@ -202,12 +254,17 @@ int mbedtls_ecdh_make_public( mbedtls_ecdh_context *ctx, size_t *olen, void *p_rng ) { int ret; + mbedtls_ecp_restart_ctx *rs_ctx = NULL; if( ctx == NULL || ctx->grp.pbits == 0 ) return( MBEDTLS_ERR_ECP_BAD_INPUT_DATA ); - if( ( ret = mbedtls_ecdh_gen_public( &ctx->grp, &ctx->d, &ctx->Q, f_rng, p_rng ) ) - != 0 ) +#if defined(MBEDTLS_ECP_RESTARTABLE) + rs_ctx = &ctx->rs; +#endif + + if( ( ret = ecdh_gen_public_restartable( &ctx->grp, &ctx->d, &ctx->Q, + f_rng, p_rng, rs_ctx ) ) != 0 ) return( ret ); return mbedtls_ecp_tls_write_point( &ctx->grp, &ctx->Q, ctx->point_format, @@ -244,12 +301,17 @@ int mbedtls_ecdh_calc_secret( mbedtls_ecdh_context *ctx, size_t *olen, void *p_rng ) { int ret; + mbedtls_ecp_restart_ctx *rs_ctx = NULL; - if( ctx == NULL ) + if( ctx == NULL || ctx->grp.pbits == 0 ) return( MBEDTLS_ERR_ECP_BAD_INPUT_DATA ); - if( ( ret = mbedtls_ecdh_compute_shared( &ctx->grp, &ctx->z, &ctx->Qp, &ctx->d, - f_rng, p_rng ) ) != 0 ) +#if defined(MBEDTLS_ECP_RESTARTABLE) + rs_ctx = &ctx->rs; +#endif + + if( ( ret = ecdh_compute_shared_restartable( &ctx->grp, + &ctx->z, &ctx->Qp, &ctx->d, f_rng, p_rng, rs_ctx ) ) != 0 ) { return( ret ); } diff --git a/tests/suites/test_suite_ecdh.data b/tests/suites/test_suite_ecdh.data index 98c4f60c1..991d11388 100644 --- a/tests/suites/test_suite_ecdh.data +++ b/tests/suites/test_suite_ecdh.data @@ -41,3 +41,15 @@ ecdh_exchange:MBEDTLS_ECP_DP_SECP521R1 ECDH restartable rfc 5903 p256 restart disabled depends_on:MBEDTLS_ECP_DP_SECP256R1_ENABLED ecdh_restart:MBEDTLS_ECP_DP_SECP256R1:"C88F01F510D9AC3F70A292DAA2316DE544E9AAB8AFE84049C62A9C57862D1433":"C6EF9C5D78AE012A011164ACB397CE2088685D8F06BF9BE0B283AB46476BEE53":"D6840F6B42F6EDAFD13116E0E12565202FEF8E9ECE7DCE03812464D04B9442DE":0:0:0 + +ECDH restartable rfc 5903 p256 restart max_ops=1 +depends_on:MBEDTLS_ECP_DP_SECP256R1_ENABLED +ecdh_restart:MBEDTLS_ECP_DP_SECP256R1:"C88F01F510D9AC3F70A292DAA2316DE544E9AAB8AFE84049C62A9C57862D1433":"C6EF9C5D78AE012A011164ACB397CE2088685D8F06BF9BE0B283AB46476BEE53":"D6840F6B42F6EDAFD13116E0E12565202FEF8E9ECE7DCE03812464D04B9442DE":1:1:10000 + +ECDH restartable rfc 5903 p256 restart max_ops=10000 +depends_on:MBEDTLS_ECP_DP_SECP256R1_ENABLED +ecdh_restart:MBEDTLS_ECP_DP_SECP256R1:"C88F01F510D9AC3F70A292DAA2316DE544E9AAB8AFE84049C62A9C57862D1433":"C6EF9C5D78AE012A011164ACB397CE2088685D8F06BF9BE0B283AB46476BEE53":"D6840F6B42F6EDAFD13116E0E12565202FEF8E9ECE7DCE03812464D04B9442DE":10000:0:0 + +ECDH restartable rfc 5903 p256 restart max_ops=250 +depends_on:MBEDTLS_ECP_DP_SECP256R1_ENABLED +ecdh_restart:MBEDTLS_ECP_DP_SECP256R1:"C88F01F510D9AC3F70A292DAA2316DE544E9AAB8AFE84049C62A9C57862D1433":"C6EF9C5D78AE012A011164ACB397CE2088685D8F06BF9BE0B283AB46476BEE53":"D6840F6B42F6EDAFD13116E0E12565202FEF8E9ECE7DCE03812464D04B9442DE":250:2:32