X-Git-Url: https://git.openssl.org/gitweb/?p=openssl.git;a=blobdiff_plain;f=crypto%2Fdsa%2Fdsa_ameth.c;h=aa3f55e2185e1bf5820d5ef6aef5848d6f7f95e2;hp=d39833ca0d4b4cbdcb34ea288680da5e86985ed0;hb=2514fa79acba998c2a8d4e5a8288a5b3ae990377;hpb=de12116417081f7b834bca4a583f97169040ce52 diff --git a/crypto/dsa/dsa_ameth.c b/crypto/dsa/dsa_ameth.c index d39833ca0d..aa3f55e218 100644 --- a/crypto/dsa/dsa_ameth.c +++ b/crypto/dsa/dsa_ameth.c @@ -1,4 +1,4 @@ -/* Written by Dr Stephen N Henson (shenson@bigfoot.com) for the OpenSSL +/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 2006. */ /* ==================================================================== @@ -60,6 +60,10 @@ #include #include #include +#include +#ifndef OPENSSL_NO_CMS +#include +#endif #include "asn1_locl.h" static int dsa_pub_decode(EVP_PKEY *pkey, X509_PUBKEY *pubkey) @@ -123,7 +127,7 @@ static int dsa_pub_decode(EVP_PKEY *pkey, X509_PUBKEY *pubkey) return 1; err: - if (pubkey) + if (public_key) ASN1_INTEGER_free(public_key); if (dsa) DSA_free(dsa); @@ -205,7 +209,7 @@ static int dsa_priv_decode(EVP_PKEY *pkey, PKCS8_PRIV_KEY_INFO *p8) if (*p == (V_ASN1_SEQUENCE|V_ASN1_CONSTRUCTED)) { ASN1_TYPE *t1, *t2; - if(!(ndsa = d2i_ASN1_SEQUENCE_ANY(NULL, &p, pklen))); + if(!(ndsa = d2i_ASN1_SEQUENCE_ANY(NULL, &p, pklen))) goto decerr; if (sk_ASN1_TYPE_num(ndsa) != 2) goto decerr; @@ -233,8 +237,16 @@ static int dsa_priv_decode(EVP_PKEY *pkey, PKCS8_PRIV_KEY_INFO *p8) } else { + const unsigned char *q = p; if (!(privkey=d2i_ASN1_INTEGER(NULL, &p, pklen))) goto decerr; + if (privkey->type == V_ASN1_NEG_INTEGER) + { + p8->broken = PKCS8_NEG_PRIVKEY; + ASN1_INTEGER_free(privkey); + if (!(privkey=d2i_ASN1_UINTEGER(NULL, &q, pklen))) + goto decerr; + } if (ptype != V_ASN1_SEQUENCE) goto decerr; } @@ -295,6 +307,12 @@ static int dsa_priv_encode(PKCS8_PRIV_KEY_INFO *p8, const EVP_PKEY *pkey) unsigned char *dp = NULL; int dplen; + if (!pkey->pkey.dsa->priv_key) + { + DSAerr(DSA_F_DSA_PRIV_ENCODE,DSA_R_MISSING_PARAMETERS); + goto err; + } + params = ASN1_STRING_new(); if (!params) @@ -350,6 +368,11 @@ static int dsa_bits(const EVP_PKEY *pkey) return BN_num_bits(pkey->pkey.dsa->p); } +static int dsa_security_bits(const EVP_PKEY *pkey) + { + return DSA_security_bits(pkey->pkey.dsa); + } + static int dsa_missing_parameters(const EVP_PKEY *pkey) { DSA *dsa; @@ -530,6 +553,52 @@ static int old_dsa_priv_encode(const EVP_PKEY *pkey, unsigned char **pder) return i2d_DSAPrivateKey(pkey->pkey.dsa, pder); } +static int dsa_sig_print(BIO *bp, const X509_ALGOR *sigalg, + const ASN1_STRING *sig, + int indent, ASN1_PCTX *pctx) + { + DSA_SIG *dsa_sig; + const unsigned char *p; + if (!sig) + { + if (BIO_puts(bp, "\n") <= 0) + return 0; + else + return 1; + } + p = sig->data; + dsa_sig = d2i_DSA_SIG(NULL, &p, sig->length); + if (dsa_sig) + { + int rv = 0; + size_t buf_len = 0; + unsigned char *m=NULL; + update_buflen(dsa_sig->r, &buf_len); + update_buflen(dsa_sig->s, &buf_len); + m = OPENSSL_malloc(buf_len+10); + if (m == NULL) + { + DSAerr(DSA_F_DSA_SIG_PRINT,ERR_R_MALLOC_FAILURE); + goto err; + } + + if (BIO_write(bp, "\n", 1) != 1) + goto err; + + if (!ASN1_bn_print(bp,"r: ",dsa_sig->r,m,indent)) + goto err; + if (!ASN1_bn_print(bp,"s: ",dsa_sig->s,m,indent)) + goto err; + rv = 1; + err: + if (m) + OPENSSL_free(m); + DSA_SIG_free(dsa_sig); + return rv; + } + return X509_signature_dump(bp, sig, indent); + } + static int dsa_pkey_ctrl(EVP_PKEY *pkey, int op, long arg1, void *arg2) { switch (op) @@ -537,15 +606,42 @@ static int dsa_pkey_ctrl(EVP_PKEY *pkey, int op, long arg1, void *arg2) case ASN1_PKEY_CTRL_PKCS7_SIGN: if (arg1 == 0) { + int snid, hnid; X509_ALGOR *alg1, *alg2; PKCS7_SIGNER_INFO_get0_algs(arg2, NULL, &alg1, &alg2); - X509_ALGOR_set0(alg1, OBJ_nid2obj(NID_sha1), - V_ASN1_NULL, 0); - X509_ALGOR_set0(alg2, OBJ_nid2obj(NID_dsaWithSHA1), - V_ASN1_UNDEF, 0); + if (alg1 == NULL || alg1->algorithm == NULL) + return -1; + hnid = OBJ_obj2nid(alg1->algorithm); + if (hnid == NID_undef) + return -1; + if (!OBJ_find_sigid_by_algs(&snid, hnid, EVP_PKEY_id(pkey))) + return -1; + X509_ALGOR_set0(alg2, OBJ_nid2obj(snid), V_ASN1_UNDEF, 0); + } + return 1; +#ifndef OPENSSL_NO_CMS + case ASN1_PKEY_CTRL_CMS_SIGN: + if (arg1 == 0) + { + int snid, hnid; + X509_ALGOR *alg1, *alg2; + CMS_SignerInfo_get0_algs(arg2, NULL, NULL, &alg1, &alg2); + if (alg1 == NULL || alg1->algorithm == NULL) + return -1; + hnid = OBJ_obj2nid(alg1->algorithm); + if (hnid == NID_undef) + return -1; + if (!OBJ_find_sigid_by_algs(&snid, hnid, EVP_PKEY_id(pkey))) + return -1; + X509_ALGOR_set0(alg2, OBJ_nid2obj(snid), V_ASN1_UNDEF, 0); } return 1; + case ASN1_PKEY_CTRL_CMS_RI_TYPE: + *(int *)arg2 = CMS_RECIPINFO_NONE; + return 1; +#endif + case ASN1_PKEY_CTRL_DEFAULT_MD_NID: *(int *)arg2 = NID_sha1; return 2; @@ -605,6 +701,7 @@ const EVP_PKEY_ASN1_METHOD dsa_asn1_meths[] = int_dsa_size, dsa_bits, + dsa_security_bits, dsa_param_decode, dsa_param_encode, @@ -612,6 +709,7 @@ const EVP_PKEY_ASN1_METHOD dsa_asn1_meths[] = dsa_copy_parameters, dsa_cmp_parameters, dsa_param_print, + dsa_sig_print, int_dsa_free, dsa_pkey_ctrl,