From 879bd6e38cad7fc932b37ca0b3ceb34d582910f6 Mon Sep 17 00:00:00 2001 From: "Dr. Stephen Henson" Date: Wed, 26 Jan 2011 16:59:47 +0000 Subject: [PATCH] Internal version of BN_mod_inverse allowing checking of no-inverse without need to inspect error queue. --- crypto/bn/bn_blind.c | 7 +++---- crypto/bn/bn_gcd.c | 18 +++++++++++++++++- crypto/bn/bn_lcl.h | 3 +++ 3 files changed, 23 insertions(+), 5 deletions(-) diff --git a/crypto/bn/bn_blind.c b/crypto/bn/bn_blind.c index e060592fdc..6e00f43c66 100644 --- a/crypto/bn/bn_blind.c +++ b/crypto/bn/bn_blind.c @@ -331,12 +331,12 @@ BN_BLINDING *BN_BLINDING_create_param(BN_BLINDING *b, ret->m_ctx = m_ctx; do { + int rv; if (!BN_rand_range(ret->A, ret->mod)) goto err; - if (BN_mod_inverse(ret->Ai, ret->A, ret->mod, ctx) == NULL) + if (!int_bn_mod_inverse(ret->Ai, ret->A, ret->mod, ctx, &rv)) { /* this should almost never happen for good RSA keys */ - unsigned long error = ERR_peek_last_error(); - if (ERR_GET_REASON(error) == BN_R_NO_INVERSE) + if (rv) { if (retry_counter-- == 0) { @@ -344,7 +344,6 @@ BN_BLINDING *BN_BLINDING_create_param(BN_BLINDING *b, BN_R_TOO_MANY_ITERATIONS); goto err; } - ERR_clear_error(); } else goto err; diff --git a/crypto/bn/bn_gcd.c b/crypto/bn/bn_gcd.c index 4a352119ba..45b417bddc 100644 --- a/crypto/bn/bn_gcd.c +++ b/crypto/bn/bn_gcd.c @@ -205,13 +205,28 @@ err: /* solves ax == 1 (mod n) */ static BIGNUM *BN_mod_inverse_no_branch(BIGNUM *in, const BIGNUM *a, const BIGNUM *n, BN_CTX *ctx); + BIGNUM *BN_mod_inverse(BIGNUM *in, const BIGNUM *a, const BIGNUM *n, BN_CTX *ctx) { + BIGNUM *rv; + int noinv; + rv = int_bn_mod_inverse(in, a, n, ctx, &noinv); + if (noinv) + BNerr(BN_F_BN_MOD_INVERSE,BN_R_NO_INVERSE); + return rv; + } + +BIGNUM *int_bn_mod_inverse(BIGNUM *in, + const BIGNUM *a, const BIGNUM *n, BN_CTX *ctx, int *pnoinv) + { BIGNUM *A,*B,*X,*Y,*M,*D,*T,*R=NULL; BIGNUM *ret=NULL; int sign; + if (pnoinv) + *pnoinv = 0; + if ((BN_get_flags(a, BN_FLG_CONSTTIME) != 0) || (BN_get_flags(n, BN_FLG_CONSTTIME) != 0)) { return BN_mod_inverse_no_branch(in, a, n, ctx); @@ -488,7 +503,8 @@ BIGNUM *BN_mod_inverse(BIGNUM *in, } else { - BNerr(BN_F_BN_MOD_INVERSE,BN_R_NO_INVERSE); + if (pnoinv) + *pnoinv = 1; goto err; } ret=R; diff --git a/crypto/bn/bn_lcl.h b/crypto/bn/bn_lcl.h index d7dff0d90c..ce085b5d3f 100644 --- a/crypto/bn/bn_lcl.h +++ b/crypto/bn/bn_lcl.h @@ -497,6 +497,9 @@ BN_ULONG bn_sub_part_words(BN_ULONG *r, const BN_ULONG *a, const BN_ULONG *b, int cl, int dl); int bn_mul_mont(BN_ULONG *rp, const BN_ULONG *ap, const BN_ULONG *bp, const BN_ULONG *np,const BN_ULONG *n0, int num); +BIGNUM *int_bn_mod_inverse(BIGNUM *in, + const BIGNUM *a, const BIGNUM *n, BN_CTX *ctx, int *noinv); + #ifdef __cplusplus } #endif -- 2.34.1