Remove link between digests and signature algorithms.
[openssl.git] / crypto / asn1 / a_verify.c
index fdce6e4380b6534a782717c87fd8c1564ef4fb48..4885539c262ef95a2ae56c1de8722d6a9c7d8c6a 100644 (file)
@@ -60,6 +60,7 @@
 #include <time.h>
 
 #include "cryptlib.h"
+#include "asn1_locl.h"
 
 #ifndef NO_SYS_TYPES_H
 # include <sys/types.h>
@@ -129,19 +130,34 @@ int ASN1_item_verify(const ASN1_ITEM *it, X509_ALGOR *a, ASN1_BIT_STRING *signat
             void *asn, EVP_PKEY *pkey)
        {
        EVP_MD_CTX ctx;
-       const EVP_MD *type;
+       const EVP_MD *type = NULL;
        unsigned char *buf_in=NULL;
-       int ret= -1,i,inl;
+       int ret= -1,inl;
 
-       EVP_MD_CTX_init(&ctx);
-       i=OBJ_obj2nid(a->algorithm);
-       type=EVP_get_digestbyname(OBJ_nid2sn(i));
+       int mdnid, pknid;
+
+       /* Convert signature OID into digest and public key OIDs */
+
+       if (!OBJ_find_sigid_algs(OBJ_obj2nid(a->algorithm), &mdnid, &pknid))
+               {
+               ASN1err(ASN1_F_ASN1_ITEM_VERIFY,ASN1_R_UNKNOWN_SIGNATURE_ALGORITHM);
+               goto err;
+               }
+       type=EVP_get_digestbynid(mdnid);
        if (type == NULL)
                {
                ASN1err(ASN1_F_ASN1_ITEM_VERIFY,ASN1_R_UNKNOWN_MESSAGE_DIGEST_ALGORITHM);
                goto err;
                }
 
+       /* Check public key OID matches public key type */
+       if (EVP_PKEY_type(pknid) != pkey->ameth->pkey_id)
+               {
+               ASN1err(ASN1_F_ASN1_ITEM_VERIFY,ASN1_R_WRONG_PUBLIC_KEY_TYPE);
+               goto err;
+               }
+
+       EVP_MD_CTX_init(&ctx);
        if (!EVP_VerifyInit_ex(&ctx,type, NULL))
                {
                ASN1err(ASN1_F_ASN1_ITEM_VERIFY,ERR_R_EVP_LIB);