forked from wolfSSL/wolfssl
Make RSA CRT constant time
Identifying which part of the CRT failed, through timing, reveals information useful to an attacker.
This commit is contained in:
@ -961,10 +961,17 @@ static int wc_RsaFunctionSync(const byte* in, word32 inLen, byte* out,
|
|||||||
if (mp_exptmod(&tmp, &key->d, &key->n, &tmp) != MP_OKAY)
|
if (mp_exptmod(&tmp, &key->d, &key->n, &tmp) != MP_OKAY)
|
||||||
ERROR_OUT(MP_EXPTMOD_E);
|
ERROR_OUT(MP_EXPTMOD_E);
|
||||||
#else
|
#else
|
||||||
#define INNER_ERROR_OUT(x) { ret = (x); goto inner_done; }
|
/* Return 0 when cond is false and n when cond is true. */
|
||||||
|
#define COND_N(cond, n) ((0 - (cond)) & (n))
|
||||||
|
/* If ret has an error value return it otherwise if r is OK then return
|
||||||
|
* 0 otherwise return e.
|
||||||
|
*/
|
||||||
|
#define RET_ERR(ret, r, e) \
|
||||||
|
((ret) | (COND_N((ret) == 0, COND_N((r) != MP_OKAY, (e)))))
|
||||||
|
|
||||||
{ /* tmpa/b scope */
|
{ /* tmpa/b scope */
|
||||||
mp_int tmpa, tmpb;
|
mp_int tmpa, tmpb;
|
||||||
|
int r;
|
||||||
|
|
||||||
if (mp_init(&tmpa) != MP_OKAY)
|
if (mp_init(&tmpa) != MP_OKAY)
|
||||||
ERROR_OUT(MP_INIT_E);
|
ERROR_OUT(MP_INIT_E);
|
||||||
@ -975,35 +982,35 @@ static int wc_RsaFunctionSync(const byte* in, word32 inLen, byte* out,
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* tmpa = tmp^dP mod p */
|
/* tmpa = tmp^dP mod p */
|
||||||
if (mp_exptmod(&tmp, &key->dP, &key->p, &tmpa) != MP_OKAY)
|
r = mp_exptmod(&tmp, &key->dP, &key->p, &tmpa);
|
||||||
INNER_ERROR_OUT(MP_EXPTMOD_E);
|
ret = RET_ERR(ret, r, MP_EXPTMOD_E);
|
||||||
|
|
||||||
/* tmpb = tmp^dQ mod q */
|
/* tmpb = tmp^dQ mod q */
|
||||||
if (mp_exptmod(&tmp, &key->dQ, &key->q, &tmpb) != MP_OKAY)
|
r = mp_exptmod(&tmp, &key->dQ, &key->q, &tmpb);
|
||||||
INNER_ERROR_OUT(MP_EXPTMOD_E);
|
ret = RET_ERR(ret, r, MP_EXPTMOD_E);
|
||||||
|
|
||||||
/* tmp = (tmpa - tmpb) * qInv (mod p) */
|
/* tmp = (tmpa - tmpb) * qInv (mod p) */
|
||||||
if (mp_sub(&tmpa, &tmpb, &tmp) != MP_OKAY)
|
r = mp_sub(&tmpa, &tmpb, &tmp);
|
||||||
INNER_ERROR_OUT(MP_SUB_E);
|
ret = RET_ERR(ret, r, MP_SUB_E);
|
||||||
|
|
||||||
if (mp_mulmod(&tmp, &key->u, &key->p, &tmp) != MP_OKAY)
|
r = mp_mulmod(&tmp, &key->u, &key->p, &tmp);
|
||||||
INNER_ERROR_OUT(MP_MULMOD_E);
|
ret = RET_ERR(ret, r, MP_MULMOD_E);
|
||||||
|
|
||||||
/* tmp = tmpb + q * tmp */
|
/* tmp = tmpb + q * tmp */
|
||||||
if (mp_mul(&tmp, &key->q, &tmp) != MP_OKAY)
|
r = mp_mul(&tmp, &key->q, &tmp);
|
||||||
INNER_ERROR_OUT(MP_MUL_E);
|
ret = RET_ERR(ret, r, MP_MUL_E);
|
||||||
|
|
||||||
if (mp_add(&tmp, &tmpb, &tmp) != MP_OKAY)
|
r = mp_add(&tmp, &tmpb, &tmp);
|
||||||
INNER_ERROR_OUT(MP_ADD_E);
|
ret = RET_ERR(ret, r, MP_ADD_E);
|
||||||
|
|
||||||
inner_done:
|
|
||||||
mp_clear(&tmpa);
|
mp_clear(&tmpa);
|
||||||
mp_clear(&tmpb);
|
mp_clear(&tmpb);
|
||||||
|
|
||||||
if (ret != 0) {
|
if (ret != 0) {
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
#undef INNER_ERROR_OUT
|
#undef RET_ERR
|
||||||
|
#undef COND_N
|
||||||
} /* tmpa/b scope */
|
} /* tmpa/b scope */
|
||||||
#endif /* RSA_LOW_MEM */
|
#endif /* RSA_LOW_MEM */
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user