summaryrefslogtreecommitdiffstats
path: root/crypto/rsa/rsa_ameth.c
diff options
context:
space:
mode:
authorDr. Stephen Henson <steve@openssl.org>2010-03-11 14:06:46 +0000
committerDr. Stephen Henson <steve@openssl.org>2010-03-11 14:06:46 +0000
commit17c63d1cca64c6b099904a3547ecf3a47234b11f (patch)
tree2e14ac1dd4c6b6311b4229c405862ecca93c074d /crypto/rsa/rsa_ameth.c
parent877669d69c747b5aa3573fdcad6bc81f8d6f09ae (diff)
RSA PSS ASN1 signing method
Diffstat (limited to 'crypto/rsa/rsa_ameth.c')
-rw-r--r--crypto/rsa/rsa_ameth.c95
1 files changed, 91 insertions, 4 deletions
diff --git a/crypto/rsa/rsa_ameth.c b/crypto/rsa/rsa_ameth.c
index f5c59b2339..dcf4a12585 100644
--- a/crypto/rsa/rsa_ameth.c
+++ b/crypto/rsa/rsa_ameth.c
@@ -535,13 +535,13 @@ static int rsa_item_verify(EVP_MD_CTX *ctx, const ASN1_ITEM *it, void *asn,
if (!EVP_DigestVerifyInit(ctx, &pkctx, md, NULL, pkey))
goto err;
- if (!EVP_PKEY_CTX_set_rsa_padding(pkctx, RSA_PKCS1_PSS_PADDING))
+ if (EVP_PKEY_CTX_set_rsa_padding(pkctx, RSA_PKCS1_PSS_PADDING) <= 0)
goto err;
- if (!EVP_PKEY_CTX_set_rsa_pss_saltlen(pkctx, saltlen))
+ if (EVP_PKEY_CTX_set_rsa_pss_saltlen(pkctx, saltlen) <= 0)
goto err;
- if (!EVP_PKEY_CTX_set_rsa_mgf1_md(pkctx, mgf1md))
+ if (EVP_PKEY_CTX_set_rsa_mgf1_md(pkctx, mgf1md) <= 0)
goto err;
/* Carry on */
rv = 2;
@@ -553,6 +553,92 @@ static int rsa_item_verify(EVP_MD_CTX *ctx, const ASN1_ITEM *it, void *asn,
return rv;
}
+static int rsa_item_sign(EVP_MD_CTX *ctx, const ASN1_ITEM *it, void *asn,
+ X509_ALGOR *alg1, X509_ALGOR *alg2,
+ ASN1_BIT_STRING *sig)
+ {
+ int pad_mode;
+ EVP_PKEY_CTX *pkctx = ctx->pctx;
+ if (EVP_PKEY_CTX_get_rsa_padding(pkctx, &pad_mode) <= 0)
+ return 0;
+ if (pad_mode == RSA_PKCS1_PADDING)
+ return 2;
+ if (pad_mode == RSA_PKCS1_PSS_PADDING)
+ {
+ const EVP_MD *sigmd, *mgf1md;
+ RSA_PSS_PARAMS *pss = NULL;
+ X509_ALGOR *mgf1alg = NULL;
+ ASN1_STRING *os1 = NULL, *os2 = NULL;
+ EVP_PKEY *pk = EVP_PKEY_CTX_get0_pkey(pkctx);
+ int saltlen, rv = 0;
+ sigmd = EVP_MD_CTX_md(ctx);
+ if (EVP_PKEY_CTX_get_rsa_mgf1_md(pkctx, &mgf1md) <= 0)
+ goto err;
+ if (!EVP_PKEY_CTX_get_rsa_pss_saltlen(pkctx, &saltlen))
+ goto err;
+ if (saltlen == -1)
+ saltlen = EVP_MD_size(sigmd);
+ else if (saltlen == -2)
+ saltlen = EVP_PKEY_size(pk) - EVP_MD_size(sigmd) - 2;
+ pss = RSA_PSS_PARAMS_new();
+ if (!pss)
+ goto err;
+ if (saltlen != 20)
+ {
+ pss->saltLength = ASN1_INTEGER_new();
+ if (!pss->saltLength)
+ goto err;
+ if (!ASN1_INTEGER_set(pss->saltLength, saltlen))
+ goto err;
+ }
+ if (EVP_MD_type(sigmd) != NID_sha1)
+ {
+ pss->hashAlgorithm = X509_ALGOR_new();
+ if (!pss->hashAlgorithm)
+ goto err;
+ X509_ALGOR_set_md(pss->hashAlgorithm, sigmd);
+ }
+ if (EVP_MD_type(mgf1md) != NID_sha1)
+ {
+ ASN1_STRING *stmp = NULL;
+ /* need to embed algorithm ID inside another */
+ mgf1alg = X509_ALGOR_new();
+ X509_ALGOR_set_md(mgf1alg, mgf1md);
+ if (!ASN1_item_pack(mgf1alg, ASN1_ITEM_rptr(X509_ALGOR),
+ &stmp))
+ goto err;
+ pss->maskGenAlgorithm = X509_ALGOR_new();
+ if (!pss->maskGenAlgorithm)
+ goto err;
+ X509_ALGOR_set0(pss->maskGenAlgorithm,
+ OBJ_nid2obj(NID_mgf1),
+ V_ASN1_SEQUENCE, stmp);
+ }
+ /* Finally create string with pss parameter encoding. */
+ if (!ASN1_item_pack(pss, ASN1_ITEM_rptr(RSA_PSS_PARAMS), &os1))
+ goto err;
+ os2 = ASN1_STRING_dup(os1);
+ if (!os2)
+ goto err;
+ X509_ALGOR_set0(alg1, OBJ_nid2obj(NID_rsassaPss),
+ V_ASN1_SEQUENCE, os1);
+ X509_ALGOR_set0(alg2, OBJ_nid2obj(NID_rsassaPss),
+ V_ASN1_SEQUENCE, os2);
+ os1 = os2 = NULL;
+ rv = 3;
+ err:
+ if (mgf1alg)
+ X509_ALGOR_free(mgf1alg);
+ if (pss)
+ RSA_PSS_PARAMS_free(pss);
+ if (os1)
+ ASN1_STRING_free(os1);
+ return rv;
+
+ }
+ return 2;
+ }
+
const EVP_PKEY_ASN1_METHOD rsa_asn1_meths[] =
{
{
@@ -582,7 +668,8 @@ const EVP_PKEY_ASN1_METHOD rsa_asn1_meths[] =
rsa_pkey_ctrl,
old_rsa_priv_decode,
old_rsa_priv_encode,
- rsa_item_verify
+ rsa_item_verify,
+ rsa_item_sign
},
{