summaryrefslogtreecommitdiffstats
path: root/crypto/ec/ecdsa_ossl.c
diff options
context:
space:
mode:
Diffstat (limited to 'crypto/ec/ecdsa_ossl.c')
-rw-r--r--crypto/ec/ecdsa_ossl.c73
1 files changed, 61 insertions, 12 deletions
diff --git a/crypto/ec/ecdsa_ossl.c b/crypto/ec/ecdsa_ossl.c
index 96dab38adf..30e130dbba 100644
--- a/crypto/ec/ecdsa_ossl.c
+++ b/crypto/ec/ecdsa_ossl.c
@@ -19,6 +19,13 @@
#include <openssl/rand.h>
#include "crypto/bn.h"
#include "ec_local.h"
+#include "internal/deterministic_nonce.h"
+
+static int ecdsa_sign_setup(EC_KEY *eckey, BN_CTX *ctx_in,
+ BIGNUM **kinvp, BIGNUM **rp,
+ const unsigned char *dgst, int dlen,
+ unsigned int nonce_type, const char *digestname,
+ OSSL_LIB_CTX *libctx, const char *propq);
int ossl_ecdsa_sign_setup(EC_KEY *eckey, BN_CTX *ctx_in, BIGNUM **kinvp,
BIGNUM **rp)
@@ -71,9 +78,39 @@ int ossl_ecdsa_sign(int type, const unsigned char *dgst, int dlen,
return 1;
}
+int ossl_ecdsa_deterministic_sign(const unsigned char *dgst, int dlen,
+ unsigned char *sig, unsigned int *siglen,
+ EC_KEY *eckey, unsigned int nonce_type,
+ const char *digestname,
+ OSSL_LIB_CTX *libctx, const char *propq)
+{
+ ECDSA_SIG *s;
+ BIGNUM *kinv = NULL, *r = NULL;
+ int ret = 0;
+
+ *siglen = 0;
+ if (!ecdsa_sign_setup(eckey, NULL, &kinv, &r, dgst, dlen,
+ nonce_type, digestname, libctx, propq))
+ return 0;
+
+ s = ECDSA_do_sign_ex(dgst, dlen, kinv, r, eckey);
+ if (s == NULL)
+ goto end;
+
+ *siglen = i2d_ECDSA_SIG(s, &sig);
+ ECDSA_SIG_free(s);
+ ret = 1;
+end:
+ BN_clear_free(kinv);
+ BN_clear_free(r);
+ return ret;
+}
+
static int ecdsa_sign_setup(EC_KEY *eckey, BN_CTX *ctx_in,
BIGNUM **kinvp, BIGNUM **rp,
- const unsigned char *dgst, int dlen)
+ const unsigned char *dgst, int dlen,
+ unsigned int nonce_type, const char *digestname,
+ OSSL_LIB_CTX *libctx, const char *propq)
{
BN_CTX *ctx = NULL;
BIGNUM *k = NULL, *r = NULL, *X = NULL;
@@ -126,19 +163,29 @@ static int ecdsa_sign_setup(EC_KEY *eckey, BN_CTX *ctx_in,
goto err;
do {
- /* get random k */
+ /* get random or determinstic value of k */
do {
+ int res = 0;
+
if (dgst != NULL) {
- if (!BN_generate_dsa_nonce(k, order, priv_key,
- dgst, dlen, ctx)) {
- ERR_raise(ERR_LIB_EC, EC_R_RANDOM_NUMBER_GENERATION_FAILED);
- goto err;
+ if (nonce_type == 1) {
+#ifndef FIPS_MODULE
+ res = ossl_gen_deterministic_nonce_rfc6979(k, order,
+ priv_key,
+ dgst, dlen,
+ digestname,
+ libctx, propq);
+#endif
+ } else {
+ res = BN_generate_dsa_nonce(k, order, priv_key, dgst, dlen,
+ ctx);
}
} else {
- if (!BN_priv_rand_range_ex(k, order, 0, ctx)) {
- ERR_raise(ERR_LIB_EC, EC_R_RANDOM_NUMBER_GENERATION_FAILED);
- goto err;
- }
+ res = BN_priv_rand_range_ex(k, order, 0, ctx);
+ }
+ if (!res) {
+ ERR_raise(ERR_LIB_EC, EC_R_RANDOM_NUMBER_GENERATION_FAILED);
+ goto err;
}
} while (BN_is_zero(k));
@@ -187,7 +234,8 @@ static int ecdsa_sign_setup(EC_KEY *eckey, BN_CTX *ctx_in,
int ossl_ecdsa_simple_sign_setup(EC_KEY *eckey, BN_CTX *ctx_in, BIGNUM **kinvp,
BIGNUM **rp)
{
- return ecdsa_sign_setup(eckey, ctx_in, kinvp, rp, NULL, 0);
+ return ecdsa_sign_setup(eckey, ctx_in, kinvp, rp, NULL, 0,
+ 0, NULL, NULL, NULL);
}
ECDSA_SIG *ossl_ecdsa_simple_sign_sig(const unsigned char *dgst, int dgst_len,
@@ -256,7 +304,8 @@ ECDSA_SIG *ossl_ecdsa_simple_sign_sig(const unsigned char *dgst, int dgst_len,
}
do {
if (in_kinv == NULL || in_r == NULL) {
- if (!ecdsa_sign_setup(eckey, ctx, &kinv, &ret->r, dgst, dgst_len)) {
+ if (!ecdsa_sign_setup(eckey, ctx, &kinv, &ret->r, dgst, dgst_len,
+ 0, NULL, NULL, NULL)) {
ERR_raise(ERR_LIB_EC, ERR_R_ECDSA_LIB);
goto err;
}