1e1051a39Sopenharmony_ci/* 2e1051a39Sopenharmony_ci * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. 3e1051a39Sopenharmony_ci * 4e1051a39Sopenharmony_ci * Licensed under the Apache License 2.0 (the "License"). You may not use 5e1051a39Sopenharmony_ci * this file except in compliance with the License. You can obtain a copy 6e1051a39Sopenharmony_ci * in the file LICENSE in the source distribution or at 7e1051a39Sopenharmony_ci * https://www.openssl.org/source/license.html 8e1051a39Sopenharmony_ci */ 9e1051a39Sopenharmony_ci 10e1051a39Sopenharmony_ci/* 11e1051a39Sopenharmony_ci * RSA low level APIs are deprecated for public use, but still ok for 12e1051a39Sopenharmony_ci * internal use. 13e1051a39Sopenharmony_ci */ 14e1051a39Sopenharmony_ci#include "internal/deprecated.h" 15e1051a39Sopenharmony_ci 16e1051a39Sopenharmony_ci#include "internal/cryptlib.h" 17e1051a39Sopenharmony_ci#include "crypto/bn.h" 18e1051a39Sopenharmony_ci#include "rsa_local.h" 19e1051a39Sopenharmony_ci#include "internal/constant_time.h" 20e1051a39Sopenharmony_ci 21e1051a39Sopenharmony_cistatic int rsa_ossl_public_encrypt(int flen, const unsigned char *from, 22e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding); 23e1051a39Sopenharmony_cistatic int rsa_ossl_private_encrypt(int flen, const unsigned char *from, 24e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding); 25e1051a39Sopenharmony_cistatic int rsa_ossl_public_decrypt(int flen, const unsigned char *from, 26e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding); 27e1051a39Sopenharmony_cistatic int rsa_ossl_private_decrypt(int flen, const unsigned char *from, 28e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding); 29e1051a39Sopenharmony_cistatic int rsa_ossl_mod_exp(BIGNUM *r0, const BIGNUM *i, RSA *rsa, 30e1051a39Sopenharmony_ci BN_CTX *ctx); 31e1051a39Sopenharmony_cistatic int rsa_ossl_init(RSA *rsa); 32e1051a39Sopenharmony_cistatic int rsa_ossl_finish(RSA *rsa); 33e1051a39Sopenharmony_cistatic RSA_METHOD rsa_pkcs1_ossl_meth = { 34e1051a39Sopenharmony_ci "OpenSSL PKCS#1 RSA", 35e1051a39Sopenharmony_ci rsa_ossl_public_encrypt, 36e1051a39Sopenharmony_ci rsa_ossl_public_decrypt, /* signature verification */ 37e1051a39Sopenharmony_ci rsa_ossl_private_encrypt, /* signing */ 38e1051a39Sopenharmony_ci rsa_ossl_private_decrypt, 39e1051a39Sopenharmony_ci rsa_ossl_mod_exp, 40e1051a39Sopenharmony_ci BN_mod_exp_mont, /* XXX probably we should not use Montgomery 41e1051a39Sopenharmony_ci * if e == 3 */ 42e1051a39Sopenharmony_ci rsa_ossl_init, 43e1051a39Sopenharmony_ci rsa_ossl_finish, 44e1051a39Sopenharmony_ci RSA_FLAG_FIPS_METHOD, /* flags */ 45e1051a39Sopenharmony_ci NULL, 46e1051a39Sopenharmony_ci 0, /* rsa_sign */ 47e1051a39Sopenharmony_ci 0, /* rsa_verify */ 48e1051a39Sopenharmony_ci NULL, /* rsa_keygen */ 49e1051a39Sopenharmony_ci NULL /* rsa_multi_prime_keygen */ 50e1051a39Sopenharmony_ci}; 51e1051a39Sopenharmony_ci 52e1051a39Sopenharmony_cistatic const RSA_METHOD *default_RSA_meth = &rsa_pkcs1_ossl_meth; 53e1051a39Sopenharmony_ci 54e1051a39Sopenharmony_civoid RSA_set_default_method(const RSA_METHOD *meth) 55e1051a39Sopenharmony_ci{ 56e1051a39Sopenharmony_ci default_RSA_meth = meth; 57e1051a39Sopenharmony_ci} 58e1051a39Sopenharmony_ci 59e1051a39Sopenharmony_ciconst RSA_METHOD *RSA_get_default_method(void) 60e1051a39Sopenharmony_ci{ 61e1051a39Sopenharmony_ci return default_RSA_meth; 62e1051a39Sopenharmony_ci} 63e1051a39Sopenharmony_ci 64e1051a39Sopenharmony_ciconst RSA_METHOD *RSA_PKCS1_OpenSSL(void) 65e1051a39Sopenharmony_ci{ 66e1051a39Sopenharmony_ci return &rsa_pkcs1_ossl_meth; 67e1051a39Sopenharmony_ci} 68e1051a39Sopenharmony_ci 69e1051a39Sopenharmony_ciconst RSA_METHOD *RSA_null_method(void) 70e1051a39Sopenharmony_ci{ 71e1051a39Sopenharmony_ci return NULL; 72e1051a39Sopenharmony_ci} 73e1051a39Sopenharmony_ci 74e1051a39Sopenharmony_cistatic int rsa_ossl_public_encrypt(int flen, const unsigned char *from, 75e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding) 76e1051a39Sopenharmony_ci{ 77e1051a39Sopenharmony_ci BIGNUM *f, *ret; 78e1051a39Sopenharmony_ci int i, num = 0, r = -1; 79e1051a39Sopenharmony_ci unsigned char *buf = NULL; 80e1051a39Sopenharmony_ci BN_CTX *ctx = NULL; 81e1051a39Sopenharmony_ci 82e1051a39Sopenharmony_ci if (BN_num_bits(rsa->n) > OPENSSL_RSA_MAX_MODULUS_BITS) { 83e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_MODULUS_TOO_LARGE); 84e1051a39Sopenharmony_ci return -1; 85e1051a39Sopenharmony_ci } 86e1051a39Sopenharmony_ci 87e1051a39Sopenharmony_ci if (BN_ucmp(rsa->n, rsa->e) <= 0) { 88e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_BAD_E_VALUE); 89e1051a39Sopenharmony_ci return -1; 90e1051a39Sopenharmony_ci } 91e1051a39Sopenharmony_ci 92e1051a39Sopenharmony_ci /* for large moduli, enforce exponent limit */ 93e1051a39Sopenharmony_ci if (BN_num_bits(rsa->n) > OPENSSL_RSA_SMALL_MODULUS_BITS) { 94e1051a39Sopenharmony_ci if (BN_num_bits(rsa->e) > OPENSSL_RSA_MAX_PUBEXP_BITS) { 95e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_BAD_E_VALUE); 96e1051a39Sopenharmony_ci return -1; 97e1051a39Sopenharmony_ci } 98e1051a39Sopenharmony_ci } 99e1051a39Sopenharmony_ci 100e1051a39Sopenharmony_ci if ((ctx = BN_CTX_new_ex(rsa->libctx)) == NULL) 101e1051a39Sopenharmony_ci goto err; 102e1051a39Sopenharmony_ci BN_CTX_start(ctx); 103e1051a39Sopenharmony_ci f = BN_CTX_get(ctx); 104e1051a39Sopenharmony_ci ret = BN_CTX_get(ctx); 105e1051a39Sopenharmony_ci num = BN_num_bytes(rsa->n); 106e1051a39Sopenharmony_ci buf = OPENSSL_malloc(num); 107e1051a39Sopenharmony_ci if (ret == NULL || buf == NULL) { 108e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 109e1051a39Sopenharmony_ci goto err; 110e1051a39Sopenharmony_ci } 111e1051a39Sopenharmony_ci 112e1051a39Sopenharmony_ci switch (padding) { 113e1051a39Sopenharmony_ci case RSA_PKCS1_PADDING: 114e1051a39Sopenharmony_ci i = ossl_rsa_padding_add_PKCS1_type_2_ex(rsa->libctx, buf, num, 115e1051a39Sopenharmony_ci from, flen); 116e1051a39Sopenharmony_ci break; 117e1051a39Sopenharmony_ci case RSA_PKCS1_OAEP_PADDING: 118e1051a39Sopenharmony_ci i = ossl_rsa_padding_add_PKCS1_OAEP_mgf1_ex(rsa->libctx, buf, num, 119e1051a39Sopenharmony_ci from, flen, NULL, 0, 120e1051a39Sopenharmony_ci NULL, NULL); 121e1051a39Sopenharmony_ci break; 122e1051a39Sopenharmony_ci case RSA_NO_PADDING: 123e1051a39Sopenharmony_ci i = RSA_padding_add_none(buf, num, from, flen); 124e1051a39Sopenharmony_ci break; 125e1051a39Sopenharmony_ci default: 126e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_UNKNOWN_PADDING_TYPE); 127e1051a39Sopenharmony_ci goto err; 128e1051a39Sopenharmony_ci } 129e1051a39Sopenharmony_ci if (i <= 0) 130e1051a39Sopenharmony_ci goto err; 131e1051a39Sopenharmony_ci 132e1051a39Sopenharmony_ci if (BN_bin2bn(buf, num, f) == NULL) 133e1051a39Sopenharmony_ci goto err; 134e1051a39Sopenharmony_ci 135e1051a39Sopenharmony_ci if (BN_ucmp(f, rsa->n) >= 0) { 136e1051a39Sopenharmony_ci /* usually the padding functions would catch this */ 137e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); 138e1051a39Sopenharmony_ci goto err; 139e1051a39Sopenharmony_ci } 140e1051a39Sopenharmony_ci 141e1051a39Sopenharmony_ci if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) 142e1051a39Sopenharmony_ci if (!BN_MONT_CTX_set_locked(&rsa->_method_mod_n, rsa->lock, 143e1051a39Sopenharmony_ci rsa->n, ctx)) 144e1051a39Sopenharmony_ci goto err; 145e1051a39Sopenharmony_ci 146e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(ret, f, rsa->e, rsa->n, ctx, 147e1051a39Sopenharmony_ci rsa->_method_mod_n)) 148e1051a39Sopenharmony_ci goto err; 149e1051a39Sopenharmony_ci 150e1051a39Sopenharmony_ci /* 151e1051a39Sopenharmony_ci * BN_bn2binpad puts in leading 0 bytes if the number is less than 152e1051a39Sopenharmony_ci * the length of the modulus. 153e1051a39Sopenharmony_ci */ 154e1051a39Sopenharmony_ci r = BN_bn2binpad(ret, to, num); 155e1051a39Sopenharmony_ci err: 156e1051a39Sopenharmony_ci BN_CTX_end(ctx); 157e1051a39Sopenharmony_ci BN_CTX_free(ctx); 158e1051a39Sopenharmony_ci OPENSSL_clear_free(buf, num); 159e1051a39Sopenharmony_ci return r; 160e1051a39Sopenharmony_ci} 161e1051a39Sopenharmony_ci 162e1051a39Sopenharmony_cistatic BN_BLINDING *rsa_get_blinding(RSA *rsa, int *local, BN_CTX *ctx) 163e1051a39Sopenharmony_ci{ 164e1051a39Sopenharmony_ci BN_BLINDING *ret; 165e1051a39Sopenharmony_ci 166e1051a39Sopenharmony_ci if (!CRYPTO_THREAD_write_lock(rsa->lock)) 167e1051a39Sopenharmony_ci return NULL; 168e1051a39Sopenharmony_ci 169e1051a39Sopenharmony_ci if (rsa->blinding == NULL) { 170e1051a39Sopenharmony_ci rsa->blinding = RSA_setup_blinding(rsa, ctx); 171e1051a39Sopenharmony_ci } 172e1051a39Sopenharmony_ci 173e1051a39Sopenharmony_ci ret = rsa->blinding; 174e1051a39Sopenharmony_ci if (ret == NULL) 175e1051a39Sopenharmony_ci goto err; 176e1051a39Sopenharmony_ci 177e1051a39Sopenharmony_ci if (BN_BLINDING_is_current_thread(ret)) { 178e1051a39Sopenharmony_ci /* rsa->blinding is ours! */ 179e1051a39Sopenharmony_ci 180e1051a39Sopenharmony_ci *local = 1; 181e1051a39Sopenharmony_ci } else { 182e1051a39Sopenharmony_ci /* resort to rsa->mt_blinding instead */ 183e1051a39Sopenharmony_ci 184e1051a39Sopenharmony_ci /* 185e1051a39Sopenharmony_ci * instructs rsa_blinding_convert(), rsa_blinding_invert() that the 186e1051a39Sopenharmony_ci * BN_BLINDING is shared, meaning that accesses require locks, and 187e1051a39Sopenharmony_ci * that the blinding factor must be stored outside the BN_BLINDING 188e1051a39Sopenharmony_ci */ 189e1051a39Sopenharmony_ci *local = 0; 190e1051a39Sopenharmony_ci 191e1051a39Sopenharmony_ci if (rsa->mt_blinding == NULL) { 192e1051a39Sopenharmony_ci rsa->mt_blinding = RSA_setup_blinding(rsa, ctx); 193e1051a39Sopenharmony_ci } 194e1051a39Sopenharmony_ci ret = rsa->mt_blinding; 195e1051a39Sopenharmony_ci } 196e1051a39Sopenharmony_ci 197e1051a39Sopenharmony_ci err: 198e1051a39Sopenharmony_ci CRYPTO_THREAD_unlock(rsa->lock); 199e1051a39Sopenharmony_ci return ret; 200e1051a39Sopenharmony_ci} 201e1051a39Sopenharmony_ci 202e1051a39Sopenharmony_cistatic int rsa_blinding_convert(BN_BLINDING *b, BIGNUM *f, BIGNUM *unblind, 203e1051a39Sopenharmony_ci BN_CTX *ctx) 204e1051a39Sopenharmony_ci{ 205e1051a39Sopenharmony_ci if (unblind == NULL) { 206e1051a39Sopenharmony_ci /* 207e1051a39Sopenharmony_ci * Local blinding: store the unblinding factor in BN_BLINDING. 208e1051a39Sopenharmony_ci */ 209e1051a39Sopenharmony_ci return BN_BLINDING_convert_ex(f, NULL, b, ctx); 210e1051a39Sopenharmony_ci } else { 211e1051a39Sopenharmony_ci /* 212e1051a39Sopenharmony_ci * Shared blinding: store the unblinding factor outside BN_BLINDING. 213e1051a39Sopenharmony_ci */ 214e1051a39Sopenharmony_ci int ret; 215e1051a39Sopenharmony_ci 216e1051a39Sopenharmony_ci if (!BN_BLINDING_lock(b)) 217e1051a39Sopenharmony_ci return 0; 218e1051a39Sopenharmony_ci 219e1051a39Sopenharmony_ci ret = BN_BLINDING_convert_ex(f, unblind, b, ctx); 220e1051a39Sopenharmony_ci BN_BLINDING_unlock(b); 221e1051a39Sopenharmony_ci 222e1051a39Sopenharmony_ci return ret; 223e1051a39Sopenharmony_ci } 224e1051a39Sopenharmony_ci} 225e1051a39Sopenharmony_ci 226e1051a39Sopenharmony_cistatic int rsa_blinding_invert(BN_BLINDING *b, BIGNUM *f, BIGNUM *unblind, 227e1051a39Sopenharmony_ci BN_CTX *ctx) 228e1051a39Sopenharmony_ci{ 229e1051a39Sopenharmony_ci /* 230e1051a39Sopenharmony_ci * For local blinding, unblind is set to NULL, and BN_BLINDING_invert_ex 231e1051a39Sopenharmony_ci * will use the unblinding factor stored in BN_BLINDING. If BN_BLINDING 232e1051a39Sopenharmony_ci * is shared between threads, unblind must be non-null: 233e1051a39Sopenharmony_ci * BN_BLINDING_invert_ex will then use the local unblinding factor, and 234e1051a39Sopenharmony_ci * will only read the modulus from BN_BLINDING. In both cases it's safe 235e1051a39Sopenharmony_ci * to access the blinding without a lock. 236e1051a39Sopenharmony_ci */ 237e1051a39Sopenharmony_ci BN_set_flags(f, BN_FLG_CONSTTIME); 238e1051a39Sopenharmony_ci return BN_BLINDING_invert_ex(f, unblind, b, ctx); 239e1051a39Sopenharmony_ci} 240e1051a39Sopenharmony_ci 241e1051a39Sopenharmony_ci/* signing */ 242e1051a39Sopenharmony_cistatic int rsa_ossl_private_encrypt(int flen, const unsigned char *from, 243e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding) 244e1051a39Sopenharmony_ci{ 245e1051a39Sopenharmony_ci BIGNUM *f, *ret, *res; 246e1051a39Sopenharmony_ci int i, num = 0, r = -1; 247e1051a39Sopenharmony_ci unsigned char *buf = NULL; 248e1051a39Sopenharmony_ci BN_CTX *ctx = NULL; 249e1051a39Sopenharmony_ci int local_blinding = 0; 250e1051a39Sopenharmony_ci /* 251e1051a39Sopenharmony_ci * Used only if the blinding structure is shared. A non-NULL unblind 252e1051a39Sopenharmony_ci * instructs rsa_blinding_convert() and rsa_blinding_invert() to store 253e1051a39Sopenharmony_ci * the unblinding factor outside the blinding structure. 254e1051a39Sopenharmony_ci */ 255e1051a39Sopenharmony_ci BIGNUM *unblind = NULL; 256e1051a39Sopenharmony_ci BN_BLINDING *blinding = NULL; 257e1051a39Sopenharmony_ci 258e1051a39Sopenharmony_ci if ((ctx = BN_CTX_new_ex(rsa->libctx)) == NULL) 259e1051a39Sopenharmony_ci goto err; 260e1051a39Sopenharmony_ci BN_CTX_start(ctx); 261e1051a39Sopenharmony_ci f = BN_CTX_get(ctx); 262e1051a39Sopenharmony_ci ret = BN_CTX_get(ctx); 263e1051a39Sopenharmony_ci num = BN_num_bytes(rsa->n); 264e1051a39Sopenharmony_ci buf = OPENSSL_malloc(num); 265e1051a39Sopenharmony_ci if (ret == NULL || buf == NULL) { 266e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 267e1051a39Sopenharmony_ci goto err; 268e1051a39Sopenharmony_ci } 269e1051a39Sopenharmony_ci 270e1051a39Sopenharmony_ci switch (padding) { 271e1051a39Sopenharmony_ci case RSA_PKCS1_PADDING: 272e1051a39Sopenharmony_ci i = RSA_padding_add_PKCS1_type_1(buf, num, from, flen); 273e1051a39Sopenharmony_ci break; 274e1051a39Sopenharmony_ci case RSA_X931_PADDING: 275e1051a39Sopenharmony_ci i = RSA_padding_add_X931(buf, num, from, flen); 276e1051a39Sopenharmony_ci break; 277e1051a39Sopenharmony_ci case RSA_NO_PADDING: 278e1051a39Sopenharmony_ci i = RSA_padding_add_none(buf, num, from, flen); 279e1051a39Sopenharmony_ci break; 280e1051a39Sopenharmony_ci default: 281e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_UNKNOWN_PADDING_TYPE); 282e1051a39Sopenharmony_ci goto err; 283e1051a39Sopenharmony_ci } 284e1051a39Sopenharmony_ci if (i <= 0) 285e1051a39Sopenharmony_ci goto err; 286e1051a39Sopenharmony_ci 287e1051a39Sopenharmony_ci if (BN_bin2bn(buf, num, f) == NULL) 288e1051a39Sopenharmony_ci goto err; 289e1051a39Sopenharmony_ci 290e1051a39Sopenharmony_ci if (BN_ucmp(f, rsa->n) >= 0) { 291e1051a39Sopenharmony_ci /* usually the padding functions would catch this */ 292e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); 293e1051a39Sopenharmony_ci goto err; 294e1051a39Sopenharmony_ci } 295e1051a39Sopenharmony_ci 296e1051a39Sopenharmony_ci if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) 297e1051a39Sopenharmony_ci if (!BN_MONT_CTX_set_locked(&rsa->_method_mod_n, rsa->lock, 298e1051a39Sopenharmony_ci rsa->n, ctx)) 299e1051a39Sopenharmony_ci goto err; 300e1051a39Sopenharmony_ci 301e1051a39Sopenharmony_ci if (!(rsa->flags & RSA_FLAG_NO_BLINDING)) { 302e1051a39Sopenharmony_ci blinding = rsa_get_blinding(rsa, &local_blinding, ctx); 303e1051a39Sopenharmony_ci if (blinding == NULL) { 304e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_INTERNAL_ERROR); 305e1051a39Sopenharmony_ci goto err; 306e1051a39Sopenharmony_ci } 307e1051a39Sopenharmony_ci } 308e1051a39Sopenharmony_ci 309e1051a39Sopenharmony_ci if (blinding != NULL) { 310e1051a39Sopenharmony_ci if (!local_blinding && ((unblind = BN_CTX_get(ctx)) == NULL)) { 311e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 312e1051a39Sopenharmony_ci goto err; 313e1051a39Sopenharmony_ci } 314e1051a39Sopenharmony_ci if (!rsa_blinding_convert(blinding, f, unblind, ctx)) 315e1051a39Sopenharmony_ci goto err; 316e1051a39Sopenharmony_ci } 317e1051a39Sopenharmony_ci 318e1051a39Sopenharmony_ci if ((rsa->flags & RSA_FLAG_EXT_PKEY) || 319e1051a39Sopenharmony_ci (rsa->version == RSA_ASN1_VERSION_MULTI) || 320e1051a39Sopenharmony_ci ((rsa->p != NULL) && 321e1051a39Sopenharmony_ci (rsa->q != NULL) && 322e1051a39Sopenharmony_ci (rsa->dmp1 != NULL) && (rsa->dmq1 != NULL) && (rsa->iqmp != NULL))) { 323e1051a39Sopenharmony_ci if (!rsa->meth->rsa_mod_exp(ret, f, rsa, ctx)) 324e1051a39Sopenharmony_ci goto err; 325e1051a39Sopenharmony_ci } else { 326e1051a39Sopenharmony_ci BIGNUM *d = BN_new(); 327e1051a39Sopenharmony_ci if (d == NULL) { 328e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 329e1051a39Sopenharmony_ci goto err; 330e1051a39Sopenharmony_ci } 331e1051a39Sopenharmony_ci if (rsa->d == NULL) { 332e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_MISSING_PRIVATE_KEY); 333e1051a39Sopenharmony_ci BN_free(d); 334e1051a39Sopenharmony_ci goto err; 335e1051a39Sopenharmony_ci } 336e1051a39Sopenharmony_ci BN_with_flags(d, rsa->d, BN_FLG_CONSTTIME); 337e1051a39Sopenharmony_ci 338e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(ret, f, d, rsa->n, ctx, 339e1051a39Sopenharmony_ci rsa->_method_mod_n)) { 340e1051a39Sopenharmony_ci BN_free(d); 341e1051a39Sopenharmony_ci goto err; 342e1051a39Sopenharmony_ci } 343e1051a39Sopenharmony_ci /* We MUST free d before any further use of rsa->d */ 344e1051a39Sopenharmony_ci BN_free(d); 345e1051a39Sopenharmony_ci } 346e1051a39Sopenharmony_ci 347e1051a39Sopenharmony_ci if (blinding) 348e1051a39Sopenharmony_ci if (!rsa_blinding_invert(blinding, ret, unblind, ctx)) 349e1051a39Sopenharmony_ci goto err; 350e1051a39Sopenharmony_ci 351e1051a39Sopenharmony_ci if (padding == RSA_X931_PADDING) { 352e1051a39Sopenharmony_ci if (!BN_sub(f, rsa->n, ret)) 353e1051a39Sopenharmony_ci goto err; 354e1051a39Sopenharmony_ci if (BN_cmp(ret, f) > 0) 355e1051a39Sopenharmony_ci res = f; 356e1051a39Sopenharmony_ci else 357e1051a39Sopenharmony_ci res = ret; 358e1051a39Sopenharmony_ci } else { 359e1051a39Sopenharmony_ci res = ret; 360e1051a39Sopenharmony_ci } 361e1051a39Sopenharmony_ci 362e1051a39Sopenharmony_ci /* 363e1051a39Sopenharmony_ci * BN_bn2binpad puts in leading 0 bytes if the number is less than 364e1051a39Sopenharmony_ci * the length of the modulus. 365e1051a39Sopenharmony_ci */ 366e1051a39Sopenharmony_ci r = BN_bn2binpad(res, to, num); 367e1051a39Sopenharmony_ci err: 368e1051a39Sopenharmony_ci BN_CTX_end(ctx); 369e1051a39Sopenharmony_ci BN_CTX_free(ctx); 370e1051a39Sopenharmony_ci OPENSSL_clear_free(buf, num); 371e1051a39Sopenharmony_ci return r; 372e1051a39Sopenharmony_ci} 373e1051a39Sopenharmony_ci 374e1051a39Sopenharmony_cistatic int rsa_ossl_private_decrypt(int flen, const unsigned char *from, 375e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding) 376e1051a39Sopenharmony_ci{ 377e1051a39Sopenharmony_ci BIGNUM *f, *ret; 378e1051a39Sopenharmony_ci int j, num = 0, r = -1; 379e1051a39Sopenharmony_ci unsigned char *buf = NULL; 380e1051a39Sopenharmony_ci BN_CTX *ctx = NULL; 381e1051a39Sopenharmony_ci int local_blinding = 0; 382e1051a39Sopenharmony_ci /* 383e1051a39Sopenharmony_ci * Used only if the blinding structure is shared. A non-NULL unblind 384e1051a39Sopenharmony_ci * instructs rsa_blinding_convert() and rsa_blinding_invert() to store 385e1051a39Sopenharmony_ci * the unblinding factor outside the blinding structure. 386e1051a39Sopenharmony_ci */ 387e1051a39Sopenharmony_ci BIGNUM *unblind = NULL; 388e1051a39Sopenharmony_ci BN_BLINDING *blinding = NULL; 389e1051a39Sopenharmony_ci 390e1051a39Sopenharmony_ci if ((ctx = BN_CTX_new_ex(rsa->libctx)) == NULL) 391e1051a39Sopenharmony_ci goto err; 392e1051a39Sopenharmony_ci BN_CTX_start(ctx); 393e1051a39Sopenharmony_ci f = BN_CTX_get(ctx); 394e1051a39Sopenharmony_ci ret = BN_CTX_get(ctx); 395e1051a39Sopenharmony_ci num = BN_num_bytes(rsa->n); 396e1051a39Sopenharmony_ci buf = OPENSSL_malloc(num); 397e1051a39Sopenharmony_ci if (ret == NULL || buf == NULL) { 398e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 399e1051a39Sopenharmony_ci goto err; 400e1051a39Sopenharmony_ci } 401e1051a39Sopenharmony_ci 402e1051a39Sopenharmony_ci /* 403e1051a39Sopenharmony_ci * This check was for equality but PGP does evil things and chops off the 404e1051a39Sopenharmony_ci * top '0' bytes 405e1051a39Sopenharmony_ci */ 406e1051a39Sopenharmony_ci if (flen > num) { 407e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_DATA_GREATER_THAN_MOD_LEN); 408e1051a39Sopenharmony_ci goto err; 409e1051a39Sopenharmony_ci } 410e1051a39Sopenharmony_ci 411e1051a39Sopenharmony_ci /* make data into a big number */ 412e1051a39Sopenharmony_ci if (BN_bin2bn(from, (int)flen, f) == NULL) 413e1051a39Sopenharmony_ci goto err; 414e1051a39Sopenharmony_ci 415e1051a39Sopenharmony_ci if (BN_ucmp(f, rsa->n) >= 0) { 416e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); 417e1051a39Sopenharmony_ci goto err; 418e1051a39Sopenharmony_ci } 419e1051a39Sopenharmony_ci 420e1051a39Sopenharmony_ci if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) 421e1051a39Sopenharmony_ci if (!BN_MONT_CTX_set_locked(&rsa->_method_mod_n, rsa->lock, 422e1051a39Sopenharmony_ci rsa->n, ctx)) 423e1051a39Sopenharmony_ci goto err; 424e1051a39Sopenharmony_ci 425e1051a39Sopenharmony_ci if (!(rsa->flags & RSA_FLAG_NO_BLINDING)) { 426e1051a39Sopenharmony_ci blinding = rsa_get_blinding(rsa, &local_blinding, ctx); 427e1051a39Sopenharmony_ci if (blinding == NULL) { 428e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_INTERNAL_ERROR); 429e1051a39Sopenharmony_ci goto err; 430e1051a39Sopenharmony_ci } 431e1051a39Sopenharmony_ci } 432e1051a39Sopenharmony_ci 433e1051a39Sopenharmony_ci if (blinding != NULL) { 434e1051a39Sopenharmony_ci if (!local_blinding && ((unblind = BN_CTX_get(ctx)) == NULL)) { 435e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 436e1051a39Sopenharmony_ci goto err; 437e1051a39Sopenharmony_ci } 438e1051a39Sopenharmony_ci if (!rsa_blinding_convert(blinding, f, unblind, ctx)) 439e1051a39Sopenharmony_ci goto err; 440e1051a39Sopenharmony_ci } 441e1051a39Sopenharmony_ci 442e1051a39Sopenharmony_ci /* do the decrypt */ 443e1051a39Sopenharmony_ci if ((rsa->flags & RSA_FLAG_EXT_PKEY) || 444e1051a39Sopenharmony_ci (rsa->version == RSA_ASN1_VERSION_MULTI) || 445e1051a39Sopenharmony_ci ((rsa->p != NULL) && 446e1051a39Sopenharmony_ci (rsa->q != NULL) && 447e1051a39Sopenharmony_ci (rsa->dmp1 != NULL) && (rsa->dmq1 != NULL) && (rsa->iqmp != NULL))) { 448e1051a39Sopenharmony_ci if (!rsa->meth->rsa_mod_exp(ret, f, rsa, ctx)) 449e1051a39Sopenharmony_ci goto err; 450e1051a39Sopenharmony_ci } else { 451e1051a39Sopenharmony_ci BIGNUM *d = BN_new(); 452e1051a39Sopenharmony_ci if (d == NULL) { 453e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 454e1051a39Sopenharmony_ci goto err; 455e1051a39Sopenharmony_ci } 456e1051a39Sopenharmony_ci if (rsa->d == NULL) { 457e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_MISSING_PRIVATE_KEY); 458e1051a39Sopenharmony_ci BN_free(d); 459e1051a39Sopenharmony_ci goto err; 460e1051a39Sopenharmony_ci } 461e1051a39Sopenharmony_ci BN_with_flags(d, rsa->d, BN_FLG_CONSTTIME); 462e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(ret, f, d, rsa->n, ctx, 463e1051a39Sopenharmony_ci rsa->_method_mod_n)) { 464e1051a39Sopenharmony_ci BN_free(d); 465e1051a39Sopenharmony_ci goto err; 466e1051a39Sopenharmony_ci } 467e1051a39Sopenharmony_ci /* We MUST free d before any further use of rsa->d */ 468e1051a39Sopenharmony_ci BN_free(d); 469e1051a39Sopenharmony_ci } 470e1051a39Sopenharmony_ci 471e1051a39Sopenharmony_ci if (blinding) 472e1051a39Sopenharmony_ci if (!rsa_blinding_invert(blinding, ret, unblind, ctx)) 473e1051a39Sopenharmony_ci goto err; 474e1051a39Sopenharmony_ci 475e1051a39Sopenharmony_ci j = BN_bn2binpad(ret, buf, num); 476e1051a39Sopenharmony_ci if (j < 0) 477e1051a39Sopenharmony_ci goto err; 478e1051a39Sopenharmony_ci 479e1051a39Sopenharmony_ci switch (padding) { 480e1051a39Sopenharmony_ci case RSA_PKCS1_PADDING: 481e1051a39Sopenharmony_ci r = RSA_padding_check_PKCS1_type_2(to, num, buf, j, num); 482e1051a39Sopenharmony_ci break; 483e1051a39Sopenharmony_ci case RSA_PKCS1_OAEP_PADDING: 484e1051a39Sopenharmony_ci r = RSA_padding_check_PKCS1_OAEP(to, num, buf, j, num, NULL, 0); 485e1051a39Sopenharmony_ci break; 486e1051a39Sopenharmony_ci case RSA_NO_PADDING: 487e1051a39Sopenharmony_ci memcpy(to, buf, (r = j)); 488e1051a39Sopenharmony_ci break; 489e1051a39Sopenharmony_ci default: 490e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_UNKNOWN_PADDING_TYPE); 491e1051a39Sopenharmony_ci goto err; 492e1051a39Sopenharmony_ci } 493e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 494e1051a39Sopenharmony_ci /* 495e1051a39Sopenharmony_ci * This trick doesn't work in the FIPS provider because libcrypto manages 496e1051a39Sopenharmony_ci * the error stack. Instead we opt not to put an error on the stack at all 497e1051a39Sopenharmony_ci * in case of padding failure in the FIPS provider. 498e1051a39Sopenharmony_ci */ 499e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_PADDING_CHECK_FAILED); 500e1051a39Sopenharmony_ci err_clear_last_constant_time(1 & ~constant_time_msb(r)); 501e1051a39Sopenharmony_ci#endif 502e1051a39Sopenharmony_ci 503e1051a39Sopenharmony_ci err: 504e1051a39Sopenharmony_ci BN_CTX_end(ctx); 505e1051a39Sopenharmony_ci BN_CTX_free(ctx); 506e1051a39Sopenharmony_ci OPENSSL_clear_free(buf, num); 507e1051a39Sopenharmony_ci return r; 508e1051a39Sopenharmony_ci} 509e1051a39Sopenharmony_ci 510e1051a39Sopenharmony_ci/* signature verification */ 511e1051a39Sopenharmony_cistatic int rsa_ossl_public_decrypt(int flen, const unsigned char *from, 512e1051a39Sopenharmony_ci unsigned char *to, RSA *rsa, int padding) 513e1051a39Sopenharmony_ci{ 514e1051a39Sopenharmony_ci BIGNUM *f, *ret; 515e1051a39Sopenharmony_ci int i, num = 0, r = -1; 516e1051a39Sopenharmony_ci unsigned char *buf = NULL; 517e1051a39Sopenharmony_ci BN_CTX *ctx = NULL; 518e1051a39Sopenharmony_ci 519e1051a39Sopenharmony_ci if (BN_num_bits(rsa->n) > OPENSSL_RSA_MAX_MODULUS_BITS) { 520e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_MODULUS_TOO_LARGE); 521e1051a39Sopenharmony_ci return -1; 522e1051a39Sopenharmony_ci } 523e1051a39Sopenharmony_ci 524e1051a39Sopenharmony_ci if (BN_ucmp(rsa->n, rsa->e) <= 0) { 525e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_BAD_E_VALUE); 526e1051a39Sopenharmony_ci return -1; 527e1051a39Sopenharmony_ci } 528e1051a39Sopenharmony_ci 529e1051a39Sopenharmony_ci /* for large moduli, enforce exponent limit */ 530e1051a39Sopenharmony_ci if (BN_num_bits(rsa->n) > OPENSSL_RSA_SMALL_MODULUS_BITS) { 531e1051a39Sopenharmony_ci if (BN_num_bits(rsa->e) > OPENSSL_RSA_MAX_PUBEXP_BITS) { 532e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_BAD_E_VALUE); 533e1051a39Sopenharmony_ci return -1; 534e1051a39Sopenharmony_ci } 535e1051a39Sopenharmony_ci } 536e1051a39Sopenharmony_ci 537e1051a39Sopenharmony_ci if ((ctx = BN_CTX_new_ex(rsa->libctx)) == NULL) 538e1051a39Sopenharmony_ci goto err; 539e1051a39Sopenharmony_ci BN_CTX_start(ctx); 540e1051a39Sopenharmony_ci f = BN_CTX_get(ctx); 541e1051a39Sopenharmony_ci ret = BN_CTX_get(ctx); 542e1051a39Sopenharmony_ci num = BN_num_bytes(rsa->n); 543e1051a39Sopenharmony_ci buf = OPENSSL_malloc(num); 544e1051a39Sopenharmony_ci if (ret == NULL || buf == NULL) { 545e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, ERR_R_MALLOC_FAILURE); 546e1051a39Sopenharmony_ci goto err; 547e1051a39Sopenharmony_ci } 548e1051a39Sopenharmony_ci 549e1051a39Sopenharmony_ci /* 550e1051a39Sopenharmony_ci * This check was for equality but PGP does evil things and chops off the 551e1051a39Sopenharmony_ci * top '0' bytes 552e1051a39Sopenharmony_ci */ 553e1051a39Sopenharmony_ci if (flen > num) { 554e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_DATA_GREATER_THAN_MOD_LEN); 555e1051a39Sopenharmony_ci goto err; 556e1051a39Sopenharmony_ci } 557e1051a39Sopenharmony_ci 558e1051a39Sopenharmony_ci if (BN_bin2bn(from, flen, f) == NULL) 559e1051a39Sopenharmony_ci goto err; 560e1051a39Sopenharmony_ci 561e1051a39Sopenharmony_ci if (BN_ucmp(f, rsa->n) >= 0) { 562e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); 563e1051a39Sopenharmony_ci goto err; 564e1051a39Sopenharmony_ci } 565e1051a39Sopenharmony_ci 566e1051a39Sopenharmony_ci if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) 567e1051a39Sopenharmony_ci if (!BN_MONT_CTX_set_locked(&rsa->_method_mod_n, rsa->lock, 568e1051a39Sopenharmony_ci rsa->n, ctx)) 569e1051a39Sopenharmony_ci goto err; 570e1051a39Sopenharmony_ci 571e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(ret, f, rsa->e, rsa->n, ctx, 572e1051a39Sopenharmony_ci rsa->_method_mod_n)) 573e1051a39Sopenharmony_ci goto err; 574e1051a39Sopenharmony_ci 575e1051a39Sopenharmony_ci if ((padding == RSA_X931_PADDING) && ((bn_get_words(ret)[0] & 0xf) != 12)) 576e1051a39Sopenharmony_ci if (!BN_sub(ret, rsa->n, ret)) 577e1051a39Sopenharmony_ci goto err; 578e1051a39Sopenharmony_ci 579e1051a39Sopenharmony_ci i = BN_bn2binpad(ret, buf, num); 580e1051a39Sopenharmony_ci if (i < 0) 581e1051a39Sopenharmony_ci goto err; 582e1051a39Sopenharmony_ci 583e1051a39Sopenharmony_ci switch (padding) { 584e1051a39Sopenharmony_ci case RSA_PKCS1_PADDING: 585e1051a39Sopenharmony_ci r = RSA_padding_check_PKCS1_type_1(to, num, buf, i, num); 586e1051a39Sopenharmony_ci break; 587e1051a39Sopenharmony_ci case RSA_X931_PADDING: 588e1051a39Sopenharmony_ci r = RSA_padding_check_X931(to, num, buf, i, num); 589e1051a39Sopenharmony_ci break; 590e1051a39Sopenharmony_ci case RSA_NO_PADDING: 591e1051a39Sopenharmony_ci memcpy(to, buf, (r = i)); 592e1051a39Sopenharmony_ci break; 593e1051a39Sopenharmony_ci default: 594e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_UNKNOWN_PADDING_TYPE); 595e1051a39Sopenharmony_ci goto err; 596e1051a39Sopenharmony_ci } 597e1051a39Sopenharmony_ci if (r < 0) 598e1051a39Sopenharmony_ci ERR_raise(ERR_LIB_RSA, RSA_R_PADDING_CHECK_FAILED); 599e1051a39Sopenharmony_ci 600e1051a39Sopenharmony_ci err: 601e1051a39Sopenharmony_ci BN_CTX_end(ctx); 602e1051a39Sopenharmony_ci BN_CTX_free(ctx); 603e1051a39Sopenharmony_ci OPENSSL_clear_free(buf, num); 604e1051a39Sopenharmony_ci return r; 605e1051a39Sopenharmony_ci} 606e1051a39Sopenharmony_ci 607e1051a39Sopenharmony_cistatic int rsa_ossl_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx) 608e1051a39Sopenharmony_ci{ 609e1051a39Sopenharmony_ci BIGNUM *r1, *m1, *vrfy; 610e1051a39Sopenharmony_ci int ret = 0, smooth = 0; 611e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 612e1051a39Sopenharmony_ci BIGNUM *r2, *m[RSA_MAX_PRIME_NUM - 2]; 613e1051a39Sopenharmony_ci int i, ex_primes = 0; 614e1051a39Sopenharmony_ci RSA_PRIME_INFO *pinfo; 615e1051a39Sopenharmony_ci#endif 616e1051a39Sopenharmony_ci 617e1051a39Sopenharmony_ci BN_CTX_start(ctx); 618e1051a39Sopenharmony_ci 619e1051a39Sopenharmony_ci r1 = BN_CTX_get(ctx); 620e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 621e1051a39Sopenharmony_ci r2 = BN_CTX_get(ctx); 622e1051a39Sopenharmony_ci#endif 623e1051a39Sopenharmony_ci m1 = BN_CTX_get(ctx); 624e1051a39Sopenharmony_ci vrfy = BN_CTX_get(ctx); 625e1051a39Sopenharmony_ci if (vrfy == NULL) 626e1051a39Sopenharmony_ci goto err; 627e1051a39Sopenharmony_ci 628e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 629e1051a39Sopenharmony_ci if (rsa->version == RSA_ASN1_VERSION_MULTI 630e1051a39Sopenharmony_ci && ((ex_primes = sk_RSA_PRIME_INFO_num(rsa->prime_infos)) <= 0 631e1051a39Sopenharmony_ci || ex_primes > RSA_MAX_PRIME_NUM - 2)) 632e1051a39Sopenharmony_ci goto err; 633e1051a39Sopenharmony_ci#endif 634e1051a39Sopenharmony_ci 635e1051a39Sopenharmony_ci if (rsa->flags & RSA_FLAG_CACHE_PRIVATE) { 636e1051a39Sopenharmony_ci BIGNUM *factor = BN_new(); 637e1051a39Sopenharmony_ci 638e1051a39Sopenharmony_ci if (factor == NULL) 639e1051a39Sopenharmony_ci goto err; 640e1051a39Sopenharmony_ci 641e1051a39Sopenharmony_ci /* 642e1051a39Sopenharmony_ci * Make sure BN_mod_inverse in Montgomery initialization uses the 643e1051a39Sopenharmony_ci * BN_FLG_CONSTTIME flag 644e1051a39Sopenharmony_ci */ 645e1051a39Sopenharmony_ci if (!(BN_with_flags(factor, rsa->p, BN_FLG_CONSTTIME), 646e1051a39Sopenharmony_ci BN_MONT_CTX_set_locked(&rsa->_method_mod_p, rsa->lock, 647e1051a39Sopenharmony_ci factor, ctx)) 648e1051a39Sopenharmony_ci || !(BN_with_flags(factor, rsa->q, BN_FLG_CONSTTIME), 649e1051a39Sopenharmony_ci BN_MONT_CTX_set_locked(&rsa->_method_mod_q, rsa->lock, 650e1051a39Sopenharmony_ci factor, ctx))) { 651e1051a39Sopenharmony_ci BN_free(factor); 652e1051a39Sopenharmony_ci goto err; 653e1051a39Sopenharmony_ci } 654e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 655e1051a39Sopenharmony_ci for (i = 0; i < ex_primes; i++) { 656e1051a39Sopenharmony_ci pinfo = sk_RSA_PRIME_INFO_value(rsa->prime_infos, i); 657e1051a39Sopenharmony_ci BN_with_flags(factor, pinfo->r, BN_FLG_CONSTTIME); 658e1051a39Sopenharmony_ci if (!BN_MONT_CTX_set_locked(&pinfo->m, rsa->lock, factor, ctx)) { 659e1051a39Sopenharmony_ci BN_free(factor); 660e1051a39Sopenharmony_ci goto err; 661e1051a39Sopenharmony_ci } 662e1051a39Sopenharmony_ci } 663e1051a39Sopenharmony_ci#endif 664e1051a39Sopenharmony_ci /* 665e1051a39Sopenharmony_ci * We MUST free |factor| before any further use of the prime factors 666e1051a39Sopenharmony_ci */ 667e1051a39Sopenharmony_ci BN_free(factor); 668e1051a39Sopenharmony_ci 669e1051a39Sopenharmony_ci smooth = (rsa->meth->bn_mod_exp == BN_mod_exp_mont) 670e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 671e1051a39Sopenharmony_ci && (ex_primes == 0) 672e1051a39Sopenharmony_ci#endif 673e1051a39Sopenharmony_ci && (BN_num_bits(rsa->q) == BN_num_bits(rsa->p)); 674e1051a39Sopenharmony_ci } 675e1051a39Sopenharmony_ci 676e1051a39Sopenharmony_ci if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) 677e1051a39Sopenharmony_ci if (!BN_MONT_CTX_set_locked(&rsa->_method_mod_n, rsa->lock, 678e1051a39Sopenharmony_ci rsa->n, ctx)) 679e1051a39Sopenharmony_ci goto err; 680e1051a39Sopenharmony_ci 681e1051a39Sopenharmony_ci if (smooth) { 682e1051a39Sopenharmony_ci /* 683e1051a39Sopenharmony_ci * Conversion from Montgomery domain, a.k.a. Montgomery reduction, 684e1051a39Sopenharmony_ci * accepts values in [0-m*2^w) range. w is m's bit width rounded up 685e1051a39Sopenharmony_ci * to limb width. So that at the very least if |I| is fully reduced, 686e1051a39Sopenharmony_ci * i.e. less than p*q, we can count on from-to round to perform 687e1051a39Sopenharmony_ci * below modulo operations on |I|. Unlike BN_mod it's constant time. 688e1051a39Sopenharmony_ci */ 689e1051a39Sopenharmony_ci if (/* m1 = I moq q */ 690e1051a39Sopenharmony_ci !bn_from_mont_fixed_top(m1, I, rsa->_method_mod_q, ctx) 691e1051a39Sopenharmony_ci || !bn_to_mont_fixed_top(m1, m1, rsa->_method_mod_q, ctx) 692e1051a39Sopenharmony_ci /* r1 = I mod p */ 693e1051a39Sopenharmony_ci || !bn_from_mont_fixed_top(r1, I, rsa->_method_mod_p, ctx) 694e1051a39Sopenharmony_ci || !bn_to_mont_fixed_top(r1, r1, rsa->_method_mod_p, ctx) 695e1051a39Sopenharmony_ci /* 696e1051a39Sopenharmony_ci * Use parallel exponentiations optimization if possible, 697e1051a39Sopenharmony_ci * otherwise fallback to two sequential exponentiations: 698e1051a39Sopenharmony_ci * m1 = m1^dmq1 mod q 699e1051a39Sopenharmony_ci * r1 = r1^dmp1 mod p 700e1051a39Sopenharmony_ci */ 701e1051a39Sopenharmony_ci || !BN_mod_exp_mont_consttime_x2(m1, m1, rsa->dmq1, rsa->q, 702e1051a39Sopenharmony_ci rsa->_method_mod_q, 703e1051a39Sopenharmony_ci r1, r1, rsa->dmp1, rsa->p, 704e1051a39Sopenharmony_ci rsa->_method_mod_p, 705e1051a39Sopenharmony_ci ctx) 706e1051a39Sopenharmony_ci /* r1 = (r1 - m1) mod p */ 707e1051a39Sopenharmony_ci /* 708e1051a39Sopenharmony_ci * bn_mod_sub_fixed_top is not regular modular subtraction, 709e1051a39Sopenharmony_ci * it can tolerate subtrahend to be larger than modulus, but 710e1051a39Sopenharmony_ci * not bit-wise wider. This makes up for uncommon q>p case, 711e1051a39Sopenharmony_ci * when |m1| can be larger than |rsa->p|. 712e1051a39Sopenharmony_ci */ 713e1051a39Sopenharmony_ci || !bn_mod_sub_fixed_top(r1, r1, m1, rsa->p) 714e1051a39Sopenharmony_ci 715e1051a39Sopenharmony_ci /* r1 = r1 * iqmp mod p */ 716e1051a39Sopenharmony_ci || !bn_to_mont_fixed_top(r1, r1, rsa->_method_mod_p, ctx) 717e1051a39Sopenharmony_ci || !bn_mul_mont_fixed_top(r1, r1, rsa->iqmp, rsa->_method_mod_p, 718e1051a39Sopenharmony_ci ctx) 719e1051a39Sopenharmony_ci /* r0 = r1 * q + m1 */ 720e1051a39Sopenharmony_ci || !bn_mul_fixed_top(r0, r1, rsa->q, ctx) 721e1051a39Sopenharmony_ci || !bn_mod_add_fixed_top(r0, r0, m1, rsa->n)) 722e1051a39Sopenharmony_ci goto err; 723e1051a39Sopenharmony_ci 724e1051a39Sopenharmony_ci goto tail; 725e1051a39Sopenharmony_ci } 726e1051a39Sopenharmony_ci 727e1051a39Sopenharmony_ci /* compute I mod q */ 728e1051a39Sopenharmony_ci { 729e1051a39Sopenharmony_ci BIGNUM *c = BN_new(); 730e1051a39Sopenharmony_ci if (c == NULL) 731e1051a39Sopenharmony_ci goto err; 732e1051a39Sopenharmony_ci BN_with_flags(c, I, BN_FLG_CONSTTIME); 733e1051a39Sopenharmony_ci 734e1051a39Sopenharmony_ci if (!BN_mod(r1, c, rsa->q, ctx)) { 735e1051a39Sopenharmony_ci BN_free(c); 736e1051a39Sopenharmony_ci goto err; 737e1051a39Sopenharmony_ci } 738e1051a39Sopenharmony_ci 739e1051a39Sopenharmony_ci { 740e1051a39Sopenharmony_ci BIGNUM *dmq1 = BN_new(); 741e1051a39Sopenharmony_ci if (dmq1 == NULL) { 742e1051a39Sopenharmony_ci BN_free(c); 743e1051a39Sopenharmony_ci goto err; 744e1051a39Sopenharmony_ci } 745e1051a39Sopenharmony_ci BN_with_flags(dmq1, rsa->dmq1, BN_FLG_CONSTTIME); 746e1051a39Sopenharmony_ci 747e1051a39Sopenharmony_ci /* compute r1^dmq1 mod q */ 748e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(m1, r1, dmq1, rsa->q, ctx, 749e1051a39Sopenharmony_ci rsa->_method_mod_q)) { 750e1051a39Sopenharmony_ci BN_free(c); 751e1051a39Sopenharmony_ci BN_free(dmq1); 752e1051a39Sopenharmony_ci goto err; 753e1051a39Sopenharmony_ci } 754e1051a39Sopenharmony_ci /* We MUST free dmq1 before any further use of rsa->dmq1 */ 755e1051a39Sopenharmony_ci BN_free(dmq1); 756e1051a39Sopenharmony_ci } 757e1051a39Sopenharmony_ci 758e1051a39Sopenharmony_ci /* compute I mod p */ 759e1051a39Sopenharmony_ci if (!BN_mod(r1, c, rsa->p, ctx)) { 760e1051a39Sopenharmony_ci BN_free(c); 761e1051a39Sopenharmony_ci goto err; 762e1051a39Sopenharmony_ci } 763e1051a39Sopenharmony_ci /* We MUST free c before any further use of I */ 764e1051a39Sopenharmony_ci BN_free(c); 765e1051a39Sopenharmony_ci } 766e1051a39Sopenharmony_ci 767e1051a39Sopenharmony_ci { 768e1051a39Sopenharmony_ci BIGNUM *dmp1 = BN_new(); 769e1051a39Sopenharmony_ci if (dmp1 == NULL) 770e1051a39Sopenharmony_ci goto err; 771e1051a39Sopenharmony_ci BN_with_flags(dmp1, rsa->dmp1, BN_FLG_CONSTTIME); 772e1051a39Sopenharmony_ci 773e1051a39Sopenharmony_ci /* compute r1^dmp1 mod p */ 774e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(r0, r1, dmp1, rsa->p, ctx, 775e1051a39Sopenharmony_ci rsa->_method_mod_p)) { 776e1051a39Sopenharmony_ci BN_free(dmp1); 777e1051a39Sopenharmony_ci goto err; 778e1051a39Sopenharmony_ci } 779e1051a39Sopenharmony_ci /* We MUST free dmp1 before any further use of rsa->dmp1 */ 780e1051a39Sopenharmony_ci BN_free(dmp1); 781e1051a39Sopenharmony_ci } 782e1051a39Sopenharmony_ci 783e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 784e1051a39Sopenharmony_ci if (ex_primes > 0) { 785e1051a39Sopenharmony_ci BIGNUM *di = BN_new(), *cc = BN_new(); 786e1051a39Sopenharmony_ci 787e1051a39Sopenharmony_ci if (cc == NULL || di == NULL) { 788e1051a39Sopenharmony_ci BN_free(cc); 789e1051a39Sopenharmony_ci BN_free(di); 790e1051a39Sopenharmony_ci goto err; 791e1051a39Sopenharmony_ci } 792e1051a39Sopenharmony_ci 793e1051a39Sopenharmony_ci for (i = 0; i < ex_primes; i++) { 794e1051a39Sopenharmony_ci /* prepare m_i */ 795e1051a39Sopenharmony_ci if ((m[i] = BN_CTX_get(ctx)) == NULL) { 796e1051a39Sopenharmony_ci BN_free(cc); 797e1051a39Sopenharmony_ci BN_free(di); 798e1051a39Sopenharmony_ci goto err; 799e1051a39Sopenharmony_ci } 800e1051a39Sopenharmony_ci 801e1051a39Sopenharmony_ci pinfo = sk_RSA_PRIME_INFO_value(rsa->prime_infos, i); 802e1051a39Sopenharmony_ci 803e1051a39Sopenharmony_ci /* prepare c and d_i */ 804e1051a39Sopenharmony_ci BN_with_flags(cc, I, BN_FLG_CONSTTIME); 805e1051a39Sopenharmony_ci BN_with_flags(di, pinfo->d, BN_FLG_CONSTTIME); 806e1051a39Sopenharmony_ci 807e1051a39Sopenharmony_ci if (!BN_mod(r1, cc, pinfo->r, ctx)) { 808e1051a39Sopenharmony_ci BN_free(cc); 809e1051a39Sopenharmony_ci BN_free(di); 810e1051a39Sopenharmony_ci goto err; 811e1051a39Sopenharmony_ci } 812e1051a39Sopenharmony_ci /* compute r1 ^ d_i mod r_i */ 813e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(m[i], r1, di, pinfo->r, ctx, pinfo->m)) { 814e1051a39Sopenharmony_ci BN_free(cc); 815e1051a39Sopenharmony_ci BN_free(di); 816e1051a39Sopenharmony_ci goto err; 817e1051a39Sopenharmony_ci } 818e1051a39Sopenharmony_ci } 819e1051a39Sopenharmony_ci 820e1051a39Sopenharmony_ci BN_free(cc); 821e1051a39Sopenharmony_ci BN_free(di); 822e1051a39Sopenharmony_ci } 823e1051a39Sopenharmony_ci#endif 824e1051a39Sopenharmony_ci 825e1051a39Sopenharmony_ci if (!BN_sub(r0, r0, m1)) 826e1051a39Sopenharmony_ci goto err; 827e1051a39Sopenharmony_ci /* 828e1051a39Sopenharmony_ci * This will help stop the size of r0 increasing, which does affect the 829e1051a39Sopenharmony_ci * multiply if it optimised for a power of 2 size 830e1051a39Sopenharmony_ci */ 831e1051a39Sopenharmony_ci if (BN_is_negative(r0)) 832e1051a39Sopenharmony_ci if (!BN_add(r0, r0, rsa->p)) 833e1051a39Sopenharmony_ci goto err; 834e1051a39Sopenharmony_ci 835e1051a39Sopenharmony_ci if (!BN_mul(r1, r0, rsa->iqmp, ctx)) 836e1051a39Sopenharmony_ci goto err; 837e1051a39Sopenharmony_ci 838e1051a39Sopenharmony_ci { 839e1051a39Sopenharmony_ci BIGNUM *pr1 = BN_new(); 840e1051a39Sopenharmony_ci if (pr1 == NULL) 841e1051a39Sopenharmony_ci goto err; 842e1051a39Sopenharmony_ci BN_with_flags(pr1, r1, BN_FLG_CONSTTIME); 843e1051a39Sopenharmony_ci 844e1051a39Sopenharmony_ci if (!BN_mod(r0, pr1, rsa->p, ctx)) { 845e1051a39Sopenharmony_ci BN_free(pr1); 846e1051a39Sopenharmony_ci goto err; 847e1051a39Sopenharmony_ci } 848e1051a39Sopenharmony_ci /* We MUST free pr1 before any further use of r1 */ 849e1051a39Sopenharmony_ci BN_free(pr1); 850e1051a39Sopenharmony_ci } 851e1051a39Sopenharmony_ci 852e1051a39Sopenharmony_ci /* 853e1051a39Sopenharmony_ci * If p < q it is occasionally possible for the correction of adding 'p' 854e1051a39Sopenharmony_ci * if r0 is negative above to leave the result still negative. This can 855e1051a39Sopenharmony_ci * break the private key operations: the following second correction 856e1051a39Sopenharmony_ci * should *always* correct this rare occurrence. This will *never* happen 857e1051a39Sopenharmony_ci * with OpenSSL generated keys because they ensure p > q [steve] 858e1051a39Sopenharmony_ci */ 859e1051a39Sopenharmony_ci if (BN_is_negative(r0)) 860e1051a39Sopenharmony_ci if (!BN_add(r0, r0, rsa->p)) 861e1051a39Sopenharmony_ci goto err; 862e1051a39Sopenharmony_ci if (!BN_mul(r1, r0, rsa->q, ctx)) 863e1051a39Sopenharmony_ci goto err; 864e1051a39Sopenharmony_ci if (!BN_add(r0, r1, m1)) 865e1051a39Sopenharmony_ci goto err; 866e1051a39Sopenharmony_ci 867e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 868e1051a39Sopenharmony_ci /* add m_i to m in multi-prime case */ 869e1051a39Sopenharmony_ci if (ex_primes > 0) { 870e1051a39Sopenharmony_ci BIGNUM *pr2 = BN_new(); 871e1051a39Sopenharmony_ci 872e1051a39Sopenharmony_ci if (pr2 == NULL) 873e1051a39Sopenharmony_ci goto err; 874e1051a39Sopenharmony_ci 875e1051a39Sopenharmony_ci for (i = 0; i < ex_primes; i++) { 876e1051a39Sopenharmony_ci pinfo = sk_RSA_PRIME_INFO_value(rsa->prime_infos, i); 877e1051a39Sopenharmony_ci if (!BN_sub(r1, m[i], r0)) { 878e1051a39Sopenharmony_ci BN_free(pr2); 879e1051a39Sopenharmony_ci goto err; 880e1051a39Sopenharmony_ci } 881e1051a39Sopenharmony_ci 882e1051a39Sopenharmony_ci if (!BN_mul(r2, r1, pinfo->t, ctx)) { 883e1051a39Sopenharmony_ci BN_free(pr2); 884e1051a39Sopenharmony_ci goto err; 885e1051a39Sopenharmony_ci } 886e1051a39Sopenharmony_ci 887e1051a39Sopenharmony_ci BN_with_flags(pr2, r2, BN_FLG_CONSTTIME); 888e1051a39Sopenharmony_ci 889e1051a39Sopenharmony_ci if (!BN_mod(r1, pr2, pinfo->r, ctx)) { 890e1051a39Sopenharmony_ci BN_free(pr2); 891e1051a39Sopenharmony_ci goto err; 892e1051a39Sopenharmony_ci } 893e1051a39Sopenharmony_ci 894e1051a39Sopenharmony_ci if (BN_is_negative(r1)) 895e1051a39Sopenharmony_ci if (!BN_add(r1, r1, pinfo->r)) { 896e1051a39Sopenharmony_ci BN_free(pr2); 897e1051a39Sopenharmony_ci goto err; 898e1051a39Sopenharmony_ci } 899e1051a39Sopenharmony_ci if (!BN_mul(r1, r1, pinfo->pp, ctx)) { 900e1051a39Sopenharmony_ci BN_free(pr2); 901e1051a39Sopenharmony_ci goto err; 902e1051a39Sopenharmony_ci } 903e1051a39Sopenharmony_ci if (!BN_add(r0, r0, r1)) { 904e1051a39Sopenharmony_ci BN_free(pr2); 905e1051a39Sopenharmony_ci goto err; 906e1051a39Sopenharmony_ci } 907e1051a39Sopenharmony_ci } 908e1051a39Sopenharmony_ci BN_free(pr2); 909e1051a39Sopenharmony_ci } 910e1051a39Sopenharmony_ci#endif 911e1051a39Sopenharmony_ci 912e1051a39Sopenharmony_ci tail: 913e1051a39Sopenharmony_ci if (rsa->e && rsa->n) { 914e1051a39Sopenharmony_ci if (rsa->meth->bn_mod_exp == BN_mod_exp_mont) { 915e1051a39Sopenharmony_ci if (!BN_mod_exp_mont(vrfy, r0, rsa->e, rsa->n, ctx, 916e1051a39Sopenharmony_ci rsa->_method_mod_n)) 917e1051a39Sopenharmony_ci goto err; 918e1051a39Sopenharmony_ci } else { 919e1051a39Sopenharmony_ci bn_correct_top(r0); 920e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(vrfy, r0, rsa->e, rsa->n, ctx, 921e1051a39Sopenharmony_ci rsa->_method_mod_n)) 922e1051a39Sopenharmony_ci goto err; 923e1051a39Sopenharmony_ci } 924e1051a39Sopenharmony_ci /* 925e1051a39Sopenharmony_ci * If 'I' was greater than (or equal to) rsa->n, the operation will 926e1051a39Sopenharmony_ci * be equivalent to using 'I mod n'. However, the result of the 927e1051a39Sopenharmony_ci * verify will *always* be less than 'n' so we don't check for 928e1051a39Sopenharmony_ci * absolute equality, just congruency. 929e1051a39Sopenharmony_ci */ 930e1051a39Sopenharmony_ci if (!BN_sub(vrfy, vrfy, I)) 931e1051a39Sopenharmony_ci goto err; 932e1051a39Sopenharmony_ci if (BN_is_zero(vrfy)) { 933e1051a39Sopenharmony_ci bn_correct_top(r0); 934e1051a39Sopenharmony_ci ret = 1; 935e1051a39Sopenharmony_ci goto err; /* not actually error */ 936e1051a39Sopenharmony_ci } 937e1051a39Sopenharmony_ci if (!BN_mod(vrfy, vrfy, rsa->n, ctx)) 938e1051a39Sopenharmony_ci goto err; 939e1051a39Sopenharmony_ci if (BN_is_negative(vrfy)) 940e1051a39Sopenharmony_ci if (!BN_add(vrfy, vrfy, rsa->n)) 941e1051a39Sopenharmony_ci goto err; 942e1051a39Sopenharmony_ci if (!BN_is_zero(vrfy)) { 943e1051a39Sopenharmony_ci /* 944e1051a39Sopenharmony_ci * 'I' and 'vrfy' aren't congruent mod n. Don't leak 945e1051a39Sopenharmony_ci * miscalculated CRT output, just do a raw (slower) mod_exp and 946e1051a39Sopenharmony_ci * return that instead. 947e1051a39Sopenharmony_ci */ 948e1051a39Sopenharmony_ci 949e1051a39Sopenharmony_ci BIGNUM *d = BN_new(); 950e1051a39Sopenharmony_ci if (d == NULL) 951e1051a39Sopenharmony_ci goto err; 952e1051a39Sopenharmony_ci BN_with_flags(d, rsa->d, BN_FLG_CONSTTIME); 953e1051a39Sopenharmony_ci 954e1051a39Sopenharmony_ci if (!rsa->meth->bn_mod_exp(r0, I, d, rsa->n, ctx, 955e1051a39Sopenharmony_ci rsa->_method_mod_n)) { 956e1051a39Sopenharmony_ci BN_free(d); 957e1051a39Sopenharmony_ci goto err; 958e1051a39Sopenharmony_ci } 959e1051a39Sopenharmony_ci /* We MUST free d before any further use of rsa->d */ 960e1051a39Sopenharmony_ci BN_free(d); 961e1051a39Sopenharmony_ci } 962e1051a39Sopenharmony_ci } 963e1051a39Sopenharmony_ci /* 964e1051a39Sopenharmony_ci * It's unfortunate that we have to bn_correct_top(r0). What hopefully 965e1051a39Sopenharmony_ci * saves the day is that correction is highly unlike, and private key 966e1051a39Sopenharmony_ci * operations are customarily performed on blinded message. Which means 967e1051a39Sopenharmony_ci * that attacker won't observe correlation with chosen plaintext. 968e1051a39Sopenharmony_ci * Secondly, remaining code would still handle it in same computational 969e1051a39Sopenharmony_ci * time and even conceal memory access pattern around corrected top. 970e1051a39Sopenharmony_ci */ 971e1051a39Sopenharmony_ci bn_correct_top(r0); 972e1051a39Sopenharmony_ci ret = 1; 973e1051a39Sopenharmony_ci err: 974e1051a39Sopenharmony_ci BN_CTX_end(ctx); 975e1051a39Sopenharmony_ci return ret; 976e1051a39Sopenharmony_ci} 977e1051a39Sopenharmony_ci 978e1051a39Sopenharmony_cistatic int rsa_ossl_init(RSA *rsa) 979e1051a39Sopenharmony_ci{ 980e1051a39Sopenharmony_ci rsa->flags |= RSA_FLAG_CACHE_PUBLIC | RSA_FLAG_CACHE_PRIVATE; 981e1051a39Sopenharmony_ci return 1; 982e1051a39Sopenharmony_ci} 983e1051a39Sopenharmony_ci 984e1051a39Sopenharmony_cistatic int rsa_ossl_finish(RSA *rsa) 985e1051a39Sopenharmony_ci{ 986e1051a39Sopenharmony_ci#ifndef FIPS_MODULE 987e1051a39Sopenharmony_ci int i; 988e1051a39Sopenharmony_ci RSA_PRIME_INFO *pinfo; 989e1051a39Sopenharmony_ci 990e1051a39Sopenharmony_ci for (i = 0; i < sk_RSA_PRIME_INFO_num(rsa->prime_infos); i++) { 991e1051a39Sopenharmony_ci pinfo = sk_RSA_PRIME_INFO_value(rsa->prime_infos, i); 992e1051a39Sopenharmony_ci BN_MONT_CTX_free(pinfo->m); 993e1051a39Sopenharmony_ci } 994e1051a39Sopenharmony_ci#endif 995e1051a39Sopenharmony_ci 996e1051a39Sopenharmony_ci BN_MONT_CTX_free(rsa->_method_mod_n); 997e1051a39Sopenharmony_ci BN_MONT_CTX_free(rsa->_method_mod_p); 998e1051a39Sopenharmony_ci BN_MONT_CTX_free(rsa->_method_mod_q); 999e1051a39Sopenharmony_ci return 1; 1000e1051a39Sopenharmony_ci} 1001