Key gen param support.
authorDr. Stephen Henson <steve@openssl.org>
Wed, 30 Nov 2016 16:55:30 +0000 (16:55 +0000)
committerDr. Stephen Henson <steve@openssl.org>
Sun, 8 Jan 2017 01:42:48 +0000 (01:42 +0000)
Reviewed-by: Rich Salz <rsalz@openssl.org>
Reviewed-by: Matt Caswell <matt@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/2177)

crypto/rsa/rsa_pmeth.c
include/openssl/rsa.h

index e720a0b2a3dcf766b75dcf61edcba5d19538300e..f226c055dc4e0946d11834dd3cea1f6ed99cca3b 100644 (file)
@@ -580,11 +580,20 @@ static int pkey_rsa_ctrl_str(EVP_PKEY_CTX *ctx,
                                EVP_PKEY_OP_TYPE_SIG | EVP_PKEY_OP_TYPE_CRYPT,
                                EVP_PKEY_CTRL_RSA_MGF1_MD, value);
 
-    if (strcmp(type, "rsa_oaep_md") == 0) {
-        const EVP_MD *md;
-        if ((md = EVP_get_digestbyname(value)) == NULL) {
-            RSAerr(RSA_F_PKEY_RSA_CTRL_STR, RSA_R_INVALID_DIGEST);
-            return 0;
+    if (ctx->pmeth->pkey_id == EVP_PKEY_RSA_PSS) {
+
+        if (strcmp(type, "rsa_pss_keygen_mgf1_md") == 0)
+            return EVP_PKEY_CTX_md(ctx, EVP_PKEY_OP_KEYGEN,
+                                   EVP_PKEY_CTRL_RSA_MGF1_MD, value);
+
+        if (strcmp(type, "rsa_pss_keygen_md") == 0)
+            return EVP_PKEY_CTX_md(ctx, EVP_PKEY_OP_KEYGEN,
+                                   EVP_PKEY_CTRL_MD, value);
+
+        if (strcmp(type, "rsa_pss_keygen_saltlen") == 0) {
+            int saltlen;
+            saltlen = atoi(value);
+            return EVP_PKEY_CTX_set_rsa_pss_keygen_saltlen(ctx, saltlen);
         }
     }
 
@@ -608,6 +617,21 @@ static int pkey_rsa_ctrl_str(EVP_PKEY_CTX *ctx,
     return -2;
 }
 
+/* Set PSS parameters when generating a key, if necessary */
+static int rsa_set_pss_param(RSA *rsa, EVP_PKEY_CTX *ctx)
+{
+    RSA_PKEY_CTX *rctx = ctx->data;
+    if (ctx->pmeth->pkey_id != EVP_PKEY_RSA_PSS)
+        return 1;
+    if (rctx->md == NULL && rctx->mgf1md == NULL && rctx->saltlen == -2)
+        return 1;
+    rsa->pss = rsa_pss_params_create(rctx->md, rctx->mgf1md,
+                                     rctx->saltlen == -2 ? 0 : rctx->saltlen);
+    if (rsa->pss == NULL)
+        return 0;
+    return 1;
+}
+
 static int pkey_rsa_keygen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
 {
     RSA *rsa = NULL;
@@ -633,6 +657,10 @@ static int pkey_rsa_keygen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
         pcb = NULL;
     ret = RSA_generate_key_ex(rsa, rctx->nbits, rctx->pub_exp, pcb);
     BN_GENCB_free(pcb);
+    if (ret > 0 && !rsa_set_pss_param(rsa, ctx)) {
+        RSA_free(rsa);
+        return 0;
+    }
     if (ret > 0)
         EVP_PKEY_assign(pkey, ctx->pmeth->pkey_id, rsa);
     else
index d46940aa1a0bcce269146cf41417973171733ea2..ededce089a5a103dac73aff000088c0bd87e5a7d 100644 (file)
@@ -97,10 +97,18 @@ extern "C" {
         RSA_pkey_ctx_ctrl(ctx, (EVP_PKEY_OP_SIGN|EVP_PKEY_OP_VERIFY), \
                           EVP_PKEY_CTRL_RSA_PSS_SALTLEN, len, NULL)
 
+# define EVP_PKEY_CTX_set_rsa_pss_keygen_saltlen(ctx, len) \
+        EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSA_PSS, EVP_PKEY_OP_KEYGEN, \
+                          EVP_PKEY_CTRL_RSA_PSS_SALTLEN, len, NULL)
+
 # define EVP_PKEY_CTX_get_rsa_pss_saltlen(ctx, plen) \
         RSA_pkey_ctx_ctrl(ctx, (EVP_PKEY_OP_SIGN|EVP_PKEY_OP_VERIFY), \
                           EVP_PKEY_CTRL_GET_RSA_PSS_SALTLEN, 0, plen)
 
+# define EVP_PKEY_CTX_set_rsa_pss_keygen_saltlen(ctx, len) \
+        EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSA_PSS, EVP_PKEY_OP_KEYGEN, \
+                          EVP_PKEY_CTRL_RSA_PSS_SALTLEN, len, NULL)
+
 # define EVP_PKEY_CTX_set_rsa_keygen_bits(ctx, bits) \
         RSA_pkey_ctx_ctrl(ctx, EVP_PKEY_OP_KEYGEN, \
                           EVP_PKEY_CTRL_RSA_KEYGEN_BITS, bits, NULL)
@@ -113,6 +121,10 @@ extern "C" {
         RSA_pkey_ctx_ctrl(ctx, EVP_PKEY_OP_TYPE_SIG | EVP_PKEY_OP_TYPE_CRYPT, \
                           EVP_PKEY_CTRL_RSA_MGF1_MD, 0, (void *)md)
 
+# define  EVP_PKEY_CTX_set_rsa_pss_keygen_mgf1_md(ctx, md)  \
+        EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSA_PSS, EVP_PKEY_OP_KEYGEN, \
+                          EVP_PKEY_CTRL_RSA_MGF1_MD, 0, (void *)md)
+
 # define  EVP_PKEY_CTX_set_rsa_oaep_md(ctx, md)  \
                 EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSA, EVP_PKEY_OP_TYPE_CRYPT,  \
                                 EVP_PKEY_CTRL_RSA_OAEP_MD, 0, (void *)md)
@@ -133,6 +145,11 @@ extern "C" {
                 EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSA, EVP_PKEY_OP_TYPE_CRYPT,  \
                                 EVP_PKEY_CTRL_GET_RSA_OAEP_LABEL, 0, (void *)l)
 
+# define  EVP_PKEY_CTX_rsa_pss_key_digest(ctx, md)  \
+                EVP_PKEY_CTX_ctrl(ctx, EVP_PKEY_RSAi_PSS, \
+                                  EVP_PKEY_OP_TYPE_CRYPT, EVP_PKEY_CTRL_MD, \
+                                  0, (void *)md)
+
 # define EVP_PKEY_CTRL_RSA_PADDING       (EVP_PKEY_ALG_CTRL + 1)
 # define EVP_PKEY_CTRL_RSA_PSS_SALTLEN   (EVP_PKEY_ALG_CTRL + 2)