crypto/cms: add CAdES-BES signed attributes validation
[openssl.git] / crypto / cms / cms_smime.c
1 /*
2  * Copyright 2008-2020 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9
10 #include "internal/cryptlib.h"
11 #include <openssl/asn1t.h>
12 #include <openssl/x509.h>
13 #include <openssl/x509v3.h>
14 #include <openssl/err.h>
15 #include <openssl/cms.h>
16 #include "cms_local.h"
17 #include "crypto/asn1.h"
18
19 DEFINE_STACK_OF(CMS_SignerInfo)
20 DEFINE_STACK_OF(X509)
21 DEFINE_STACK_OF(X509_CRL)
22 DEFINE_STACK_OF(CMS_RecipientEncryptedKey)
23 DEFINE_STACK_OF(CMS_RecipientInfo)
24
25 static BIO *cms_get_text_bio(BIO *out, unsigned int flags)
26 {
27     BIO *rbio;
28     if (out == NULL)
29         rbio = BIO_new(BIO_s_null());
30     else if (flags & CMS_TEXT) {
31         rbio = BIO_new(BIO_s_mem());
32         BIO_set_mem_eof_return(rbio, 0);
33     } else
34         rbio = out;
35     return rbio;
36 }
37
38 static int cms_copy_content(BIO *out, BIO *in, unsigned int flags)
39 {
40     unsigned char buf[4096];
41     int r = 0, i;
42     BIO *tmpout;
43
44     tmpout = cms_get_text_bio(out, flags);
45
46     if (tmpout == NULL) {
47         CMSerr(CMS_F_CMS_COPY_CONTENT, ERR_R_MALLOC_FAILURE);
48         goto err;
49     }
50
51     /* Read all content through chain to process digest, decrypt etc */
52     for (;;) {
53         i = BIO_read(in, buf, sizeof(buf));
54         if (i <= 0) {
55             if (BIO_method_type(in) == BIO_TYPE_CIPHER) {
56                 if (!BIO_get_cipher_status(in))
57                     goto err;
58             }
59             if (i < 0)
60                 goto err;
61             break;
62         }
63
64         if (tmpout && (BIO_write(tmpout, buf, i) != i))
65             goto err;
66     }
67
68     if (flags & CMS_TEXT) {
69         if (!SMIME_text(tmpout, out)) {
70             CMSerr(CMS_F_CMS_COPY_CONTENT, CMS_R_SMIME_TEXT_ERROR);
71             goto err;
72         }
73     }
74
75     r = 1;
76
77  err:
78     if (tmpout != out)
79         BIO_free(tmpout);
80     return r;
81
82 }
83
84 static int check_content(CMS_ContentInfo *cms)
85 {
86     ASN1_OCTET_STRING **pos = CMS_get0_content(cms);
87
88     if (pos == NULL || *pos == NULL) {
89         CMSerr(CMS_F_CHECK_CONTENT, CMS_R_NO_CONTENT);
90         return 0;
91     }
92     return 1;
93 }
94
95 static void do_free_upto(BIO *f, BIO *upto)
96 {
97     if (upto != NULL) {
98         BIO *tbio;
99         do {
100             tbio = BIO_pop(f);
101             BIO_free(f);
102             f = tbio;
103         } while (f != NULL && f != upto);
104     } else
105         BIO_free_all(f);
106 }
107
108 int CMS_data(CMS_ContentInfo *cms, BIO *out, unsigned int flags)
109 {
110     BIO *cont;
111     int r;
112     if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_data) {
113         CMSerr(CMS_F_CMS_DATA, CMS_R_TYPE_NOT_DATA);
114         return 0;
115     }
116     cont = CMS_dataInit(cms, NULL);
117     if (!cont)
118         return 0;
119     r = cms_copy_content(out, cont, flags);
120     BIO_free_all(cont);
121     return r;
122 }
123
124 CMS_ContentInfo *CMS_data_create(BIO *in, unsigned int flags)
125 {
126     CMS_ContentInfo *cms;
127     cms = cms_Data_create();
128     if (!cms)
129         return NULL;
130
131     if ((flags & CMS_STREAM) || CMS_final(cms, in, NULL, flags))
132         return cms;
133
134     CMS_ContentInfo_free(cms);
135
136     return NULL;
137 }
138
139 int CMS_digest_verify(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
140                       unsigned int flags)
141 {
142     BIO *cont;
143     int r;
144     if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_digest) {
145         CMSerr(CMS_F_CMS_DIGEST_VERIFY, CMS_R_TYPE_NOT_DIGESTED_DATA);
146         return 0;
147     }
148
149     if (!dcont && !check_content(cms))
150         return 0;
151
152     cont = CMS_dataInit(cms, dcont);
153     if (!cont)
154         return 0;
155     r = cms_copy_content(out, cont, flags);
156     if (r)
157         r = cms_DigestedData_do_final(cms, cont, 1);
158     do_free_upto(cont, dcont);
159     return r;
160 }
161
162 CMS_ContentInfo *CMS_digest_create(BIO *in, const EVP_MD *md,
163                                    unsigned int flags)
164 {
165     CMS_ContentInfo *cms;
166     if (!md)
167         md = EVP_sha1();
168     cms = cms_DigestedData_create(md);
169     if (!cms)
170         return NULL;
171
172     if (!(flags & CMS_DETACHED))
173         CMS_set_detached(cms, 0);
174
175     if ((flags & CMS_STREAM) || CMS_final(cms, in, NULL, flags))
176         return cms;
177
178     CMS_ContentInfo_free(cms);
179     return NULL;
180 }
181
182 int CMS_EncryptedData_decrypt(CMS_ContentInfo *cms,
183                               const unsigned char *key, size_t keylen,
184                               BIO *dcont, BIO *out, unsigned int flags)
185 {
186     BIO *cont;
187     int r;
188     if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_encrypted) {
189         CMSerr(CMS_F_CMS_ENCRYPTEDDATA_DECRYPT,
190                CMS_R_TYPE_NOT_ENCRYPTED_DATA);
191         return 0;
192     }
193
194     if (!dcont && !check_content(cms))
195         return 0;
196
197     if (CMS_EncryptedData_set1_key(cms, NULL, key, keylen) <= 0)
198         return 0;
199     cont = CMS_dataInit(cms, dcont);
200     if (!cont)
201         return 0;
202     r = cms_copy_content(out, cont, flags);
203     do_free_upto(cont, dcont);
204     return r;
205 }
206
207 CMS_ContentInfo *CMS_EncryptedData_encrypt(BIO *in, const EVP_CIPHER *cipher,
208                                            const unsigned char *key,
209                                            size_t keylen, unsigned int flags)
210 {
211     CMS_ContentInfo *cms;
212     if (!cipher) {
213         CMSerr(CMS_F_CMS_ENCRYPTEDDATA_ENCRYPT, CMS_R_NO_CIPHER);
214         return NULL;
215     }
216     cms = CMS_ContentInfo_new();
217     if (cms == NULL)
218         return NULL;
219     if (!CMS_EncryptedData_set1_key(cms, cipher, key, keylen))
220         return NULL;
221
222     if (!(flags & CMS_DETACHED))
223         CMS_set_detached(cms, 0);
224
225     if ((flags & (CMS_STREAM | CMS_PARTIAL))
226         || CMS_final(cms, in, NULL, flags))
227         return cms;
228
229     CMS_ContentInfo_free(cms);
230     return NULL;
231 }
232
233 static int cms_signerinfo_verify_cert(CMS_SignerInfo *si,
234                                       X509_STORE *store,
235                                       STACK_OF(X509) *certs,
236                                       STACK_OF(X509_CRL) *crls,
237                                       STACK_OF(X509) **chain)
238 {
239     X509_STORE_CTX *ctx = X509_STORE_CTX_new();
240     X509 *signer;
241     int i, j, r = 0;
242
243     if (ctx == NULL) {
244         CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CERT, ERR_R_MALLOC_FAILURE);
245         goto err;
246     }
247     CMS_SignerInfo_get0_algs(si, NULL, &signer, NULL, NULL);
248     if (!X509_STORE_CTX_init(ctx, store, signer, certs)) {
249         CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CERT, CMS_R_STORE_INIT_ERROR);
250         goto err;
251     }
252     X509_STORE_CTX_set_default(ctx, "smime_sign");
253     if (crls)
254         X509_STORE_CTX_set0_crls(ctx, crls);
255
256     i = X509_verify_cert(ctx);
257     if (i <= 0) {
258         j = X509_STORE_CTX_get_error(ctx);
259         CMSerr(CMS_F_CMS_SIGNERINFO_VERIFY_CERT,
260                CMS_R_CERTIFICATE_VERIFY_ERROR);
261         ERR_add_error_data(2, "Verify error:",
262                            X509_verify_cert_error_string(j));
263         goto err;
264     }
265     r = 1;
266
267     /* also send back the trust chain when required */
268     if (chain != NULL)
269         *chain = X509_STORE_CTX_get1_chain(ctx);
270  err:
271     X509_STORE_CTX_free(ctx);
272     return r;
273
274 }
275
276 int CMS_verify(CMS_ContentInfo *cms, STACK_OF(X509) *certs,
277                X509_STORE *store, BIO *dcont, BIO *out, unsigned int flags)
278 {
279     CMS_SignerInfo *si;
280     STACK_OF(CMS_SignerInfo) *sinfos;
281     STACK_OF(X509) *cms_certs = NULL;
282     STACK_OF(X509_CRL) *crls = NULL;
283     STACK_OF(X509) **si_chains = NULL;
284     X509 *signer;
285     int i, scount = 0, ret = 0;
286     BIO *cmsbio = NULL, *tmpin = NULL, *tmpout = NULL;
287     int cadesVerify = (flags & CMS_CADES) != 0;
288
289     if (!dcont && !check_content(cms))
290         return 0;
291     if (dcont && !(flags & CMS_BINARY)) {
292         const ASN1_OBJECT *coid = CMS_get0_eContentType(cms);
293         if (OBJ_obj2nid(coid) == NID_id_ct_asciiTextWithCRLF)
294             flags |= CMS_ASCIICRLF;
295     }
296
297     /* Attempt to find all signer certificates */
298
299     sinfos = CMS_get0_SignerInfos(cms);
300
301     if (sk_CMS_SignerInfo_num(sinfos) <= 0) {
302         CMSerr(CMS_F_CMS_VERIFY, CMS_R_NO_SIGNERS);
303         goto err;
304     }
305
306     for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
307         si = sk_CMS_SignerInfo_value(sinfos, i);
308         CMS_SignerInfo_get0_algs(si, NULL, &signer, NULL, NULL);
309         if (signer)
310             scount++;
311     }
312
313     if (scount != sk_CMS_SignerInfo_num(sinfos))
314         scount += CMS_set1_signers_certs(cms, certs, flags);
315
316     if (scount != sk_CMS_SignerInfo_num(sinfos)) {
317         CMSerr(CMS_F_CMS_VERIFY, CMS_R_SIGNER_CERTIFICATE_NOT_FOUND);
318         goto err;
319     }
320
321     /* Attempt to verify all signers certs */
322     /* at this point scount == sk_CMS_SignerInfo_num(sinfos) */
323
324     if ((flags & CMS_NO_SIGNER_CERT_VERIFY) == 0 || cadesVerify) {
325         if (cadesVerify) {
326             /* Certificate trust chain is required to check CAdES signature */
327             si_chains = OPENSSL_zalloc(scount * sizeof(si_chains[0]));
328             if (si_chains == NULL) {
329                 CMSerr(CMS_F_CMS_VERIFY, ERR_R_MALLOC_FAILURE);
330                 goto err;
331             }
332         }
333         cms_certs = CMS_get1_certs(cms);
334         if (!(flags & CMS_NOCRL))
335             crls = CMS_get1_crls(cms);
336         for (i = 0; i < scount; i++) {
337             si = sk_CMS_SignerInfo_value(sinfos, i);
338
339             if (!cms_signerinfo_verify_cert(si, store, cms_certs, crls,
340                                             si_chains ? &si_chains[i] : NULL))
341                 goto err;
342         }
343     }
344
345     /* Attempt to verify all SignerInfo signed attribute signatures */
346
347     if ((flags & CMS_NO_ATTR_VERIFY) == 0 || cadesVerify) {
348         for (i = 0; i < scount; i++) {
349             si = sk_CMS_SignerInfo_value(sinfos, i);
350             if (CMS_signed_get_attr_count(si) < 0)
351                 continue;
352             if (CMS_SignerInfo_verify(si) <= 0)
353                 goto err;
354             if (cadesVerify) {
355                 STACK_OF(X509) *si_chain = si_chains ? si_chains[i] : NULL;
356
357                 if (ess_check_signing_certs(si, si_chain) <= 0)
358                     goto err;
359             }
360         }
361     }
362
363     /*
364      * Performance optimization: if the content is a memory BIO then store
365      * its contents in a temporary read only memory BIO. This avoids
366      * potentially large numbers of slow copies of data which will occur when
367      * reading from a read write memory BIO when signatures are calculated.
368      */
369
370     if (dcont && (BIO_method_type(dcont) == BIO_TYPE_MEM)) {
371         char *ptr;
372         long len;
373         len = BIO_get_mem_data(dcont, &ptr);
374         tmpin = BIO_new_mem_buf(ptr, len);
375         if (tmpin == NULL) {
376             CMSerr(CMS_F_CMS_VERIFY, ERR_R_MALLOC_FAILURE);
377             goto err2;
378         }
379     } else
380         tmpin = dcont;
381     /*
382      * If not binary mode and detached generate digests by *writing* through
383      * the BIO. That makes it possible to canonicalise the input.
384      */
385     if (!(flags & SMIME_BINARY) && dcont) {
386         /*
387          * Create output BIO so we can either handle text or to ensure
388          * included content doesn't override detached content.
389          */
390         tmpout = cms_get_text_bio(out, flags);
391         if (!tmpout) {
392             CMSerr(CMS_F_CMS_VERIFY, ERR_R_MALLOC_FAILURE);
393             goto err;
394         }
395         cmsbio = CMS_dataInit(cms, tmpout);
396         if (!cmsbio)
397             goto err;
398         /*
399          * Don't use SMIME_TEXT for verify: it adds headers and we want to
400          * remove them.
401          */
402         SMIME_crlf_copy(dcont, cmsbio, flags & ~SMIME_TEXT);
403
404         if (flags & CMS_TEXT) {
405             if (!SMIME_text(tmpout, out)) {
406                 CMSerr(CMS_F_CMS_VERIFY, CMS_R_SMIME_TEXT_ERROR);
407                 goto err;
408             }
409         }
410     } else {
411         cmsbio = CMS_dataInit(cms, tmpin);
412         if (!cmsbio)
413             goto err;
414
415         if (!cms_copy_content(out, cmsbio, flags))
416             goto err;
417
418     }
419     if (!(flags & CMS_NO_CONTENT_VERIFY)) {
420         for (i = 0; i < sk_CMS_SignerInfo_num(sinfos); i++) {
421             si = sk_CMS_SignerInfo_value(sinfos, i);
422             if (CMS_SignerInfo_verify_content(si, cmsbio) <= 0) {
423                 CMSerr(CMS_F_CMS_VERIFY, CMS_R_CONTENT_VERIFY_ERROR);
424                 goto err;
425             }
426         }
427     }
428
429     ret = 1;
430
431  err:
432     if (!(flags & SMIME_BINARY) && dcont) {
433         do_free_upto(cmsbio, tmpout);
434         if (tmpin != dcont)
435             BIO_free(tmpin);
436     } else {
437         if (dcont && (tmpin == dcont))
438             do_free_upto(cmsbio, dcont);
439         else
440             BIO_free_all(cmsbio);
441     }
442
443     if (out != tmpout)
444         BIO_free_all(tmpout);
445
446  err2:
447     if (si_chains != NULL) {
448         for (i = 0; i < scount; ++i)
449             sk_X509_pop_free(si_chains[i], X509_free);
450         OPENSSL_free(si_chains);
451     }
452     sk_X509_pop_free(cms_certs, X509_free);
453     sk_X509_CRL_pop_free(crls, X509_CRL_free);
454
455     return ret;
456 }
457
458 int CMS_verify_receipt(CMS_ContentInfo *rcms, CMS_ContentInfo *ocms,
459                        STACK_OF(X509) *certs,
460                        X509_STORE *store, unsigned int flags)
461 {
462     int r;
463     flags &= ~(CMS_DETACHED | CMS_TEXT);
464     r = CMS_verify(rcms, certs, store, NULL, NULL, flags);
465     if (r <= 0)
466         return r;
467     return cms_Receipt_verify(rcms, ocms);
468 }
469
470 CMS_ContentInfo *CMS_sign(X509 *signcert, EVP_PKEY *pkey,
471                           STACK_OF(X509) *certs, BIO *data,
472                           unsigned int flags)
473 {
474     CMS_ContentInfo *cms;
475     int i;
476
477     cms = CMS_ContentInfo_new();
478     if (cms == NULL || !CMS_SignedData_init(cms))
479         goto merr;
480     if (flags & CMS_ASCIICRLF
481         && !CMS_set1_eContentType(cms,
482                                   OBJ_nid2obj(NID_id_ct_asciiTextWithCRLF)))
483         goto err;
484
485     if (pkey && !CMS_add1_signer(cms, signcert, pkey, NULL, flags)) {
486         CMSerr(CMS_F_CMS_SIGN, CMS_R_ADD_SIGNER_ERROR);
487         goto err;
488     }
489
490     for (i = 0; i < sk_X509_num(certs); i++) {
491         X509 *x = sk_X509_value(certs, i);
492         if (!CMS_add1_cert(cms, x))
493             goto merr;
494     }
495
496     if (!(flags & CMS_DETACHED))
497         CMS_set_detached(cms, 0);
498
499     if ((flags & (CMS_STREAM | CMS_PARTIAL))
500         || CMS_final(cms, data, NULL, flags))
501         return cms;
502     else
503         goto err;
504
505  merr:
506     CMSerr(CMS_F_CMS_SIGN, ERR_R_MALLOC_FAILURE);
507
508  err:
509     CMS_ContentInfo_free(cms);
510     return NULL;
511 }
512
513 CMS_ContentInfo *CMS_sign_receipt(CMS_SignerInfo *si,
514                                   X509 *signcert, EVP_PKEY *pkey,
515                                   STACK_OF(X509) *certs, unsigned int flags)
516 {
517     CMS_SignerInfo *rct_si;
518     CMS_ContentInfo *cms = NULL;
519     ASN1_OCTET_STRING **pos, *os;
520     BIO *rct_cont = NULL;
521     int r = 0;
522
523     flags &= ~(CMS_STREAM | CMS_TEXT);
524     /* Not really detached but avoids content being allocated */
525     flags |= CMS_PARTIAL | CMS_BINARY | CMS_DETACHED;
526     if (pkey == NULL || signcert == NULL) {
527         CMSerr(CMS_F_CMS_SIGN_RECEIPT, CMS_R_NO_KEY_OR_CERT);
528         return NULL;
529     }
530
531     /* Initialize signed data */
532
533     cms = CMS_sign(NULL, NULL, certs, NULL, flags);
534     if (!cms)
535         goto err;
536
537     /* Set inner content type to signed receipt */
538     if (!CMS_set1_eContentType(cms, OBJ_nid2obj(NID_id_smime_ct_receipt)))
539         goto err;
540
541     rct_si = CMS_add1_signer(cms, signcert, pkey, NULL, flags);
542     if (!rct_si) {
543         CMSerr(CMS_F_CMS_SIGN_RECEIPT, CMS_R_ADD_SIGNER_ERROR);
544         goto err;
545     }
546
547     os = cms_encode_Receipt(si);
548
549     if (!os)
550         goto err;
551
552     /* Set content to digest */
553     rct_cont = BIO_new_mem_buf(os->data, os->length);
554     if (!rct_cont)
555         goto err;
556
557     /* Add msgSigDigest attribute */
558
559     if (!cms_msgSigDigest_add1(rct_si, si))
560         goto err;
561
562     /* Finalize structure */
563     if (!CMS_final(cms, rct_cont, NULL, flags))
564         goto err;
565
566     /* Set embedded content */
567     pos = CMS_get0_content(cms);
568     *pos = os;
569
570     r = 1;
571
572  err:
573     BIO_free(rct_cont);
574     if (r)
575         return cms;
576     CMS_ContentInfo_free(cms);
577     return NULL;
578
579 }
580
581 CMS_ContentInfo *CMS_encrypt(STACK_OF(X509) *certs, BIO *data,
582                              const EVP_CIPHER *cipher, unsigned int flags)
583 {
584     CMS_ContentInfo *cms;
585     int i;
586     X509 *recip;
587     cms = CMS_EnvelopedData_create(cipher);
588     if (!cms)
589         goto merr;
590     for (i = 0; i < sk_X509_num(certs); i++) {
591         recip = sk_X509_value(certs, i);
592         if (!CMS_add1_recipient_cert(cms, recip, flags)) {
593             CMSerr(CMS_F_CMS_ENCRYPT, CMS_R_RECIPIENT_ERROR);
594             goto err;
595         }
596     }
597
598     if (!(flags & CMS_DETACHED))
599         CMS_set_detached(cms, 0);
600
601     if ((flags & (CMS_STREAM | CMS_PARTIAL))
602         || CMS_final(cms, data, NULL, flags))
603         return cms;
604     else
605         goto err;
606
607  merr:
608     CMSerr(CMS_F_CMS_ENCRYPT, ERR_R_MALLOC_FAILURE);
609  err:
610     CMS_ContentInfo_free(cms);
611     return NULL;
612 }
613
614 static int cms_kari_set1_pkey_and_peer(CMS_ContentInfo *cms, CMS_RecipientInfo *ri,
615                                        EVP_PKEY *pk, X509 *cert, X509 *peer)
616 {
617     int i;
618     STACK_OF(CMS_RecipientEncryptedKey) *reks;
619     CMS_RecipientEncryptedKey *rek;
620
621     reks = CMS_RecipientInfo_kari_get0_reks(ri);
622     for (i = 0; i < sk_CMS_RecipientEncryptedKey_num(reks); i++) {
623         int rv;
624         rek = sk_CMS_RecipientEncryptedKey_value(reks, i);
625         if (cert != NULL && CMS_RecipientEncryptedKey_cert_cmp(rek, cert))
626             continue;
627         CMS_RecipientInfo_kari_set0_pkey_and_peer(ri, pk, peer);
628         rv = CMS_RecipientInfo_kari_decrypt(cms, ri, rek);
629         CMS_RecipientInfo_kari_set0_pkey(ri, NULL);
630         if (rv > 0)
631             return 1;
632         return cert == NULL ? 0 : -1;
633     }
634     return 0;
635 }
636
637 int CMS_decrypt_set1_pkey(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert)
638 {
639      return CMS_decrypt_set1_pkey_and_peer(cms, pk, cert, NULL);
640 }
641
642 int CMS_decrypt_set1_pkey_and_peer(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert, X509 *peer)
643 {
644     STACK_OF(CMS_RecipientInfo) *ris;
645     CMS_RecipientInfo *ri;
646     int i, r, cms_pkey_ri_type;
647     int debug = 0, match_ri = 0;
648     ris = CMS_get0_RecipientInfos(cms);
649     if (ris)
650         debug = cms->d.envelopedData->encryptedContentInfo->debug;
651
652     cms_pkey_ri_type = cms_pkey_get_ri_type(pk);
653     if (cms_pkey_ri_type == CMS_RECIPINFO_NONE) {
654          CMSerr(CMS_F_CMS_DECRYPT_SET1_PKEY_AND_PEER,
655               CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
656          return 0;
657     }
658
659     for (i = 0; i < sk_CMS_RecipientInfo_num(ris); i++) {
660         int ri_type;
661
662         ri = sk_CMS_RecipientInfo_value(ris, i);
663         ri_type = CMS_RecipientInfo_type(ri);
664         if (!cms_pkey_is_ri_type_supported(pk, ri_type))
665             continue;
666         match_ri = 1;
667         if (ri_type == CMS_RECIPINFO_AGREE) {
668             r = cms_kari_set1_pkey_and_peer(cms, ri, pk, cert, peer);
669             if (r > 0)
670                 return 1;
671             if (r < 0)
672                 return 0;
673         }
674         /*
675          * If we have a cert try matching RecipientInfo otherwise try them
676          * all.
677          */
678         else if (!cert || !CMS_RecipientInfo_ktri_cert_cmp(ri, cert)) {
679             EVP_PKEY_up_ref(pk);
680             CMS_RecipientInfo_set0_pkey(ri, pk);
681             r = CMS_RecipientInfo_decrypt(cms, ri);
682             CMS_RecipientInfo_set0_pkey(ri, NULL);
683             if (cert) {
684                 /*
685                  * If not debugging clear any error and return success to
686                  * avoid leaking of information useful to MMA
687                  */
688                 if (!debug) {
689                     ERR_clear_error();
690                     return 1;
691                 }
692                 if (r > 0)
693                     return 1;
694                 CMSerr(CMS_F_CMS_DECRYPT_SET1_PKEY_AND_PEER, CMS_R_DECRYPT_ERROR);
695                 return 0;
696             }
697             /*
698              * If no cert and not debugging don't leave loop after first
699              * successful decrypt. Always attempt to decrypt all recipients
700              * to avoid leaking timing of a successful decrypt.
701              */
702             else if (r > 0 && (debug || cms_pkey_ri_type != CMS_RECIPINFO_TRANS))
703                 return 1;
704         }
705     }
706     /* If no cert, key transport and not debugging always return success */
707     if (cert == NULL && cms_pkey_ri_type == CMS_RECIPINFO_TRANS && match_ri && !debug) {
708         ERR_clear_error();
709         return 1;
710     }
711
712     CMSerr(CMS_F_CMS_DECRYPT_SET1_PKEY_AND_PEER, CMS_R_NO_MATCHING_RECIPIENT);
713     return 0;
714
715 }
716
717 int CMS_decrypt_set1_key(CMS_ContentInfo *cms,
718                          unsigned char *key, size_t keylen,
719                          const unsigned char *id, size_t idlen)
720 {
721     STACK_OF(CMS_RecipientInfo) *ris;
722     CMS_RecipientInfo *ri;
723     int i, r;
724     ris = CMS_get0_RecipientInfos(cms);
725     for (i = 0; i < sk_CMS_RecipientInfo_num(ris); i++) {
726         ri = sk_CMS_RecipientInfo_value(ris, i);
727         if (CMS_RecipientInfo_type(ri) != CMS_RECIPINFO_KEK)
728             continue;
729
730         /*
731          * If we have an id try matching RecipientInfo otherwise try them
732          * all.
733          */
734         if (!id || (CMS_RecipientInfo_kekri_id_cmp(ri, id, idlen) == 0)) {
735             CMS_RecipientInfo_set0_key(ri, key, keylen);
736             r = CMS_RecipientInfo_decrypt(cms, ri);
737             CMS_RecipientInfo_set0_key(ri, NULL, 0);
738             if (r > 0)
739                 return 1;
740             if (id) {
741                 CMSerr(CMS_F_CMS_DECRYPT_SET1_KEY, CMS_R_DECRYPT_ERROR);
742                 return 0;
743             }
744             ERR_clear_error();
745         }
746     }
747
748     CMSerr(CMS_F_CMS_DECRYPT_SET1_KEY, CMS_R_NO_MATCHING_RECIPIENT);
749     return 0;
750
751 }
752
753 int CMS_decrypt_set1_password(CMS_ContentInfo *cms,
754                               unsigned char *pass, ossl_ssize_t passlen)
755 {
756     STACK_OF(CMS_RecipientInfo) *ris;
757     CMS_RecipientInfo *ri;
758     int i, r;
759     ris = CMS_get0_RecipientInfos(cms);
760     for (i = 0; i < sk_CMS_RecipientInfo_num(ris); i++) {
761         ri = sk_CMS_RecipientInfo_value(ris, i);
762         if (CMS_RecipientInfo_type(ri) != CMS_RECIPINFO_PASS)
763             continue;
764         CMS_RecipientInfo_set0_password(ri, pass, passlen);
765         r = CMS_RecipientInfo_decrypt(cms, ri);
766         CMS_RecipientInfo_set0_password(ri, NULL, 0);
767         if (r > 0)
768             return 1;
769     }
770
771     CMSerr(CMS_F_CMS_DECRYPT_SET1_PASSWORD, CMS_R_NO_MATCHING_RECIPIENT);
772     return 0;
773
774 }
775
776 int CMS_decrypt(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert,
777                 BIO *dcont, BIO *out, unsigned int flags)
778 {
779     int r;
780     BIO *cont;
781
782     if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_pkcs7_enveloped) {
783         CMSerr(CMS_F_CMS_DECRYPT, CMS_R_TYPE_NOT_ENVELOPED_DATA);
784         return 0;
785     }
786     if (!dcont && !check_content(cms))
787         return 0;
788     if (flags & CMS_DEBUG_DECRYPT)
789         cms->d.envelopedData->encryptedContentInfo->debug = 1;
790     else
791         cms->d.envelopedData->encryptedContentInfo->debug = 0;
792     if (!cert)
793         cms->d.envelopedData->encryptedContentInfo->havenocert = 1;
794     else
795         cms->d.envelopedData->encryptedContentInfo->havenocert = 0;
796     if (pk == NULL && cert == NULL && dcont == NULL && out == NULL)
797         return 1;
798     if (pk != NULL && !CMS_decrypt_set1_pkey(cms, pk, cert))
799         return 0;
800     cont = CMS_dataInit(cms, dcont);
801     if (cont == NULL)
802         return 0;
803     r = cms_copy_content(out, cont, flags);
804     do_free_upto(cont, dcont);
805     return r;
806 }
807
808 int CMS_final(CMS_ContentInfo *cms, BIO *data, BIO *dcont, unsigned int flags)
809 {
810     BIO *cmsbio;
811     int ret = 0;
812
813     if ((cmsbio = CMS_dataInit(cms, dcont)) == NULL) {
814         CMSerr(CMS_F_CMS_FINAL, CMS_R_CMS_LIB);
815         return 0;
816     }
817
818     SMIME_crlf_copy(data, cmsbio, flags);
819
820     (void)BIO_flush(cmsbio);
821
822     if (!CMS_dataFinal(cms, cmsbio)) {
823         CMSerr(CMS_F_CMS_FINAL, CMS_R_CMS_DATAFINAL_ERROR);
824         goto err;
825     }
826
827     ret = 1;
828
829  err:
830     do_free_upto(cmsbio, dcont);
831
832     return ret;
833
834 }
835
836 #ifdef ZLIB
837
838 int CMS_uncompress(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
839                    unsigned int flags)
840 {
841     BIO *cont;
842     int r;
843     if (OBJ_obj2nid(CMS_get0_type(cms)) != NID_id_smime_ct_compressedData) {
844         CMSerr(CMS_F_CMS_UNCOMPRESS, CMS_R_TYPE_NOT_COMPRESSED_DATA);
845         return 0;
846     }
847
848     if (!dcont && !check_content(cms))
849         return 0;
850
851     cont = CMS_dataInit(cms, dcont);
852     if (!cont)
853         return 0;
854     r = cms_copy_content(out, cont, flags);
855     do_free_upto(cont, dcont);
856     return r;
857 }
858
859 CMS_ContentInfo *CMS_compress(BIO *in, int comp_nid, unsigned int flags)
860 {
861     CMS_ContentInfo *cms;
862     if (comp_nid <= 0)
863         comp_nid = NID_zlib_compression;
864     cms = cms_CompressedData_create(comp_nid);
865     if (!cms)
866         return NULL;
867
868     if (!(flags & CMS_DETACHED))
869         CMS_set_detached(cms, 0);
870
871     if ((flags & CMS_STREAM) || CMS_final(cms, in, NULL, flags))
872         return cms;
873
874     CMS_ContentInfo_free(cms);
875     return NULL;
876 }
877
878 #else
879
880 int CMS_uncompress(CMS_ContentInfo *cms, BIO *dcont, BIO *out,
881                    unsigned int flags)
882 {
883     CMSerr(CMS_F_CMS_UNCOMPRESS, CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM);
884     return 0;
885 }
886
887 CMS_ContentInfo *CMS_compress(BIO *in, int comp_nid, unsigned int flags)
888 {
889     CMSerr(CMS_F_CMS_COMPRESS, CMS_R_UNSUPPORTED_COMPRESSION_ALGORITHM);
890     return NULL;
891 }
892
893 #endif