Adjust mpi_gcd_modinv_odd() internals
Signed-off-by: Felix Conway <felix.conway@arm.com>
diff --git a/library/bignum.c b/library/bignum.c
index 53ff95e..4f7ca16 100644
--- a/library/bignum.c
+++ b/library/bignum.c
@@ -1774,11 +1774,11 @@
G = &local_g;
}
+ /* We can't modify the values of G or I before use in the main function,
+ * as they could be aliased to A or N. */
MBEDTLS_MPI_CHK(mbedtls_mpi_grow(G, N->n));
- G->s = 1;
if (I != NULL) {
MBEDTLS_MPI_CHK(mbedtls_mpi_grow(I, N->n));
- I->s = 1;
}
T = mbedtls_calloc(sizeof(mbedtls_mpi_uint) * N->n, T_factor);
@@ -1787,16 +1787,19 @@
goto cleanup;
}
- /* We have to handle G and I carefully as they could be aliased
- * to A or N. */
mbedtls_mpi_uint *Ip = I != NULL ? I->p : NULL;
- /* If A is 0 (null), then A->p would be null, which would be an issue if
- * A->p was passed to mbedtls_mpi_core_gcd_modinv_odd below. */
+ /* If A is 0 (null), then A->p would be null, and A->n would be 0,
+ * which would be an issue if A->p and A->n were passed to
+ * mbedtls_mpi_core_gcd_modinv_odd below. */
const mbedtls_mpi_uint *Ap = A->p != NULL ? A->p : &zero;
- size_t An = A->p == NULL ? 0 : A->n;
- An = A->n <= N->n ? A->n : N->n;
+ size_t An = A->n >= N->n ? N->n : A->p != NULL ? A->n : 1;
mbedtls_mpi_core_gcd_modinv_odd(G->p, Ip, Ap, An, N->p, N->n, T);
+ G->s = 1;
+ if (I != NULL) {
+ I->s = 1;
+ }
+
if (G->n > N->n) {
memset(G->p + N->n, 0, ciL * (G->n - N->n));
}