Change signature of `mbedtls_rsa_deduce_private`
Make input arguments constant and adapt the implementation to use a temporary instead of in-place operations.
diff --git a/include/mbedtls/rsa.h b/include/mbedtls/rsa.h
index a7e8a33..e45520f 100644
--- a/include/mbedtls/rsa.h
+++ b/include/mbedtls/rsa.h
@@ -122,18 +122,11 @@
* \return
* - 0 if successful. In this case, D is set to a simultaneous
* modular inverse of E modulo both P-1 and Q-1.
- * - A non-zero error code otherwise. In this case, the values
- * of P, Q, E are undefined.
+ * - A non-zero error code otherwise.
*
- * \note The input MPI's are deliberately not declared as constant
- * and may therefore be used for in-place calculations by
- * the implementation. In particular, their values can be
- * corrupted when the function fails. If the user cannot
- * tolerate this, he has to make copies of the MPI's prior
- * to calling this function. See \c mbedtls_mpi_copy for this.
*/
-int mbedtls_rsa_deduce_private( mbedtls_mpi *P, mbedtls_mpi *Q, mbedtls_mpi *E,
- mbedtls_mpi *D );
+int mbedtls_rsa_deduce_private( mbedtls_mpi const *P, mbedtls_mpi const *Q,
+ mbedtls_mpi const *E, mbedtls_mpi *D );
/**
diff --git a/library/rsa.c b/library/rsa.c
index e01397e..3e58c85 100644
--- a/library/rsa.c
+++ b/library/rsa.c
@@ -252,11 +252,13 @@
* This is essentially a modular inversion.
*/
-int mbedtls_rsa_deduce_private( mbedtls_mpi *P, mbedtls_mpi *Q,
- mbedtls_mpi *D, mbedtls_mpi *E )
+int mbedtls_rsa_deduce_private( mbedtls_mpi const *P,
+ mbedtls_mpi const *Q,
+ mbedtls_mpi const *E,
+ mbedtls_mpi *D )
{
int ret = 0;
- mbedtls_mpi K;
+ mbedtls_mpi K, L;
if( D == NULL || mbedtls_mpi_cmp_int( D, 0 ) != 0 )
return( MBEDTLS_ERR_MPI_BAD_INPUT_DATA );
@@ -269,28 +271,26 @@
}
mbedtls_mpi_init( &K );
+ mbedtls_mpi_init( &L );
- /* Temporarily replace P and Q by P-1 and Q-1, respectively. */
- MBEDTLS_MPI_CHK( mbedtls_mpi_sub_int( P, P, 1 ) );
- MBEDTLS_MPI_CHK( mbedtls_mpi_sub_int( Q, Q, 1 ) );
+ /* Temporarily put K := P-1 and L := Q-1 */
+ MBEDTLS_MPI_CHK( mbedtls_mpi_sub_int( &K, P, 1 ) );
+ MBEDTLS_MPI_CHK( mbedtls_mpi_sub_int( &L, Q, 1 ) );
- /* Temporarily compute the gcd(P-1, Q-1) in D. */
- MBEDTLS_MPI_CHK( mbedtls_mpi_gcd( D, P, Q ) );
+ /* Temporarily put D := gcd(P-1, Q-1) */
+ MBEDTLS_MPI_CHK( mbedtls_mpi_gcd( D, &K, &L ) );
- /* Compute LCM(P-1, Q-1) in K */
- MBEDTLS_MPI_CHK( mbedtls_mpi_mul_mpi( &K, P, Q ) );
+ /* K := LCM(P-1, Q-1) */
+ MBEDTLS_MPI_CHK( mbedtls_mpi_mul_mpi( &K, &K, &L ) );
MBEDTLS_MPI_CHK( mbedtls_mpi_div_mpi( &K, NULL, &K, D ) );
/* Compute modular inverse of E in LCM(P-1, Q-1) */
MBEDTLS_MPI_CHK( mbedtls_mpi_inv_mod( D, E, &K ) );
- /* Restore P and Q. */
- MBEDTLS_MPI_CHK( mbedtls_mpi_add_int( P, P, 1 ) );
- MBEDTLS_MPI_CHK( mbedtls_mpi_add_int( Q, Q, 1 ) );
-
cleanup:
mbedtls_mpi_free( &K );
+ mbedtls_mpi_free( &L );
return( ret );
}
@@ -664,7 +664,7 @@
* so together with the primality test above all core parameters are
* guaranteed to be sane if this call succeeds. */
if( ( ret = mbedtls_rsa_deduce_private( &ctx->P, &ctx->Q,
- &ctx->D, &ctx->E ) ) != 0 )
+ &ctx->E, &ctx->D ) ) != 0 )
{
return( MBEDTLS_ERR_RSA_BAD_INPUT_DATA + ret );
}
diff --git a/tests/suites/test_suite_rsa.function b/tests/suites/test_suite_rsa.function
index 062b971..f321554 100644
--- a/tests/suites/test_suite_rsa.function
+++ b/tests/suites/test_suite_rsa.function
@@ -804,7 +804,7 @@
}
/* Try to deduce D from N, P, Q, E. */
- TEST_ASSERT( mbedtls_rsa_deduce_private( &P, &Q, &D, &E ) == result );
+ TEST_ASSERT( mbedtls_rsa_deduce_private( &P, &Q, &E, &D ) == result );
if( !corrupt )
{