xref: /openbsd/lib/libcrypto/cms/cms_env.c (revision 5819369a)
1 /* $OpenBSD: cms_env.c,v 1.28 2024/11/01 18:42:10 tb Exp $ */
2 /*
3  * Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
4  * project.
5  */
6 /* ====================================================================
7  * Copyright (c) 2008 The OpenSSL Project.  All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  *
16  * 2. Redistributions in binary form must reproduce the above copyright
17  *    notice, this list of conditions and the following disclaimer in
18  *    the documentation and/or other materials provided with the
19  *    distribution.
20  *
21  * 3. All advertising materials mentioning features or use of this
22  *    software must display the following acknowledgment:
23  *    "This product includes software developed by the OpenSSL Project
24  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
25  *
26  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
27  *    endorse or promote products derived from this software without
28  *    prior written permission. For written permission, please contact
29  *    licensing@OpenSSL.org.
30  *
31  * 5. Products derived from this software may not be called "OpenSSL"
32  *    nor may "OpenSSL" appear in their names without prior written
33  *    permission of the OpenSSL Project.
34  *
35  * 6. Redistributions of any form whatsoever must retain the following
36  *    acknowledgment:
37  *    "This product includes software developed by the OpenSSL Project
38  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
39  *
40  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
41  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
42  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
43  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
44  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
45  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
46  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
47  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
49  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
50  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
51  * OF THE POSSIBILITY OF SUCH DAMAGE.
52  * ====================================================================
53  */
54 
55 #include <stdlib.h>
56 #include <string.h>
57 
58 #include <openssl/aes.h>
59 #include <openssl/asn1.h>
60 #include <openssl/bio.h>
61 #include <openssl/cms.h>
62 #include <openssl/err.h>
63 #include <openssl/evp.h>
64 #include <openssl/objects.h>
65 #include <openssl/x509.h>
66 
67 #include "cms_local.h"
68 #include "evp_local.h"
69 
70 /* CMS EnvelopedData Utilities */
71 
72 CMS_EnvelopedData *
cms_get0_enveloped(CMS_ContentInfo * cms)73 cms_get0_enveloped(CMS_ContentInfo *cms)
74 {
75 	if (OBJ_obj2nid(cms->contentType) != NID_pkcs7_enveloped) {
76 		CMSerror(CMS_R_CONTENT_TYPE_NOT_ENVELOPED_DATA);
77 		return NULL;
78 	}
79 	return cms->d.envelopedData;
80 }
81 
82 static CMS_EnvelopedData *
cms_enveloped_data_init(CMS_ContentInfo * cms)83 cms_enveloped_data_init(CMS_ContentInfo *cms)
84 {
85 	if (cms->d.other == NULL) {
86 		cms->d.envelopedData = (CMS_EnvelopedData *)ASN1_item_new(&CMS_EnvelopedData_it);
87 		if (!cms->d.envelopedData) {
88 			CMSerror(ERR_R_MALLOC_FAILURE);
89 			return NULL;
90 		}
91 		cms->d.envelopedData->version = 0;
92 		cms->d.envelopedData->encryptedContentInfo->contentType =
93 			OBJ_nid2obj(NID_pkcs7_data);
94 		ASN1_OBJECT_free(cms->contentType);
95 		cms->contentType = OBJ_nid2obj(NID_pkcs7_enveloped);
96 		return cms->d.envelopedData;
97 	}
98 	return cms_get0_enveloped(cms);
99 }
100 
101 int
cms_env_asn1_ctrl(CMS_RecipientInfo * ri,int cmd)102 cms_env_asn1_ctrl(CMS_RecipientInfo *ri, int cmd)
103 {
104 	EVP_PKEY *pkey;
105 	int i;
106 
107 	if (ri->type == CMS_RECIPINFO_TRANS)
108 		pkey = ri->d.ktri->pkey;
109 	else if (ri->type == CMS_RECIPINFO_AGREE) {
110 		EVP_PKEY_CTX *pctx = ri->d.kari->pctx;
111 		if (!pctx)
112 			return 0;
113 		pkey = EVP_PKEY_CTX_get0_pkey(pctx);
114 		if (!pkey)
115 			return 0;
116 	} else
117 		return 0;
118 	if (!pkey->ameth || !pkey->ameth->pkey_ctrl)
119 		return 1;
120 	i = pkey->ameth->pkey_ctrl(pkey, ASN1_PKEY_CTRL_CMS_ENVELOPE, cmd, ri);
121 	if (i == -2) {
122 		CMSerror(CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
123 		return 0;
124 	}
125 	if (i <= 0) {
126 		CMSerror(CMS_R_CTRL_FAILURE);
127 		return 0;
128 	}
129 
130 	return 1;
131 }
132 
STACK_OF(CMS_RecipientInfo)133 STACK_OF(CMS_RecipientInfo) *
134 CMS_get0_RecipientInfos(CMS_ContentInfo *cms)
135 {
136 	CMS_EnvelopedData *env;
137 
138 	env = cms_get0_enveloped(cms);
139 	if (!env)
140 		return NULL;
141 
142 	return env->recipientInfos;
143 }
144 LCRYPTO_ALIAS(CMS_get0_RecipientInfos);
145 
146 int
CMS_RecipientInfo_type(CMS_RecipientInfo * ri)147 CMS_RecipientInfo_type(CMS_RecipientInfo *ri)
148 {
149 	return ri->type;
150 }
151 LCRYPTO_ALIAS(CMS_RecipientInfo_type);
152 
153 EVP_PKEY_CTX *
CMS_RecipientInfo_get0_pkey_ctx(CMS_RecipientInfo * ri)154 CMS_RecipientInfo_get0_pkey_ctx(CMS_RecipientInfo *ri)
155 {
156 	if (ri->type == CMS_RECIPINFO_TRANS)
157 		return ri->d.ktri->pctx;
158 	else if (ri->type == CMS_RECIPINFO_AGREE)
159 		return ri->d.kari->pctx;
160 
161 	return NULL;
162 }
163 LCRYPTO_ALIAS(CMS_RecipientInfo_get0_pkey_ctx);
164 
165 CMS_ContentInfo *
CMS_EnvelopedData_create(const EVP_CIPHER * cipher)166 CMS_EnvelopedData_create(const EVP_CIPHER *cipher)
167 {
168 	CMS_ContentInfo *cms;
169 	CMS_EnvelopedData *env;
170 
171 	cms = CMS_ContentInfo_new();
172 	if (cms == NULL)
173 		goto merr;
174 	env = cms_enveloped_data_init(cms);
175 	if (env == NULL)
176 		goto merr;
177 	if (!cms_EncryptedContent_init(env->encryptedContentInfo, cipher,
178 	    NULL, 0))
179 		goto merr;
180 
181 	return cms;
182 
183  merr:
184 	CMS_ContentInfo_free(cms);
185 	CMSerror(ERR_R_MALLOC_FAILURE);
186 	return NULL;
187 }
188 LCRYPTO_ALIAS(CMS_EnvelopedData_create);
189 
190 /* Key Transport Recipient Info (KTRI) routines */
191 
192 /* Initialise a ktri based on passed certificate and key */
193 
194 static int
cms_RecipientInfo_ktri_init(CMS_RecipientInfo * ri,X509 * recip,EVP_PKEY * pk,unsigned int flags)195 cms_RecipientInfo_ktri_init(CMS_RecipientInfo *ri, X509 *recip, EVP_PKEY *pk,
196     unsigned int flags)
197 {
198 	CMS_KeyTransRecipientInfo *ktri;
199 	int idtype;
200 
201 	ri->d.ktri = (CMS_KeyTransRecipientInfo *)ASN1_item_new(&CMS_KeyTransRecipientInfo_it);
202 	if (!ri->d.ktri)
203 		return 0;
204 	ri->type = CMS_RECIPINFO_TRANS;
205 
206 	ktri = ri->d.ktri;
207 
208 	if (flags & CMS_USE_KEYID) {
209 		ktri->version = 2;
210 		idtype = CMS_RECIPINFO_KEYIDENTIFIER;
211 	} else {
212 		ktri->version = 0;
213 		idtype = CMS_RECIPINFO_ISSUER_SERIAL;
214 	}
215 
216 	/*
217 	 * Not a typo: RecipientIdentifier and SignerIdentifier are the same
218 	 * structure.
219 	 */
220 
221 	if (!cms_set1_SignerIdentifier(ktri->rid, recip, idtype))
222 		return 0;
223 
224 	X509_up_ref(recip);
225 	EVP_PKEY_up_ref(pk);
226 
227 	ktri->pkey = pk;
228 	ktri->recip = recip;
229 
230 	if (flags & CMS_KEY_PARAM) {
231 		ktri->pctx = EVP_PKEY_CTX_new(ktri->pkey, NULL);
232 		if (ktri->pctx == NULL)
233 			return 0;
234 		if (EVP_PKEY_encrypt_init(ktri->pctx) <= 0)
235 			return 0;
236 	} else if (!cms_env_asn1_ctrl(ri, 0))
237 		return 0;
238 
239 	return 1;
240 }
241 
242 /*
243  * Add a recipient certificate using appropriate type of RecipientInfo
244  */
245 
246 CMS_RecipientInfo *
CMS_add1_recipient_cert(CMS_ContentInfo * cms,X509 * recip,unsigned int flags)247 CMS_add1_recipient_cert(CMS_ContentInfo *cms, X509 *recip, unsigned int flags)
248 {
249 	CMS_RecipientInfo *ri = NULL;
250 	CMS_EnvelopedData *env;
251 	EVP_PKEY *pk = NULL;
252 
253 	env = cms_get0_enveloped(cms);
254 	if (!env)
255 		goto err;
256 
257 	/* Initialize recipient info */
258 	ri = (CMS_RecipientInfo *)ASN1_item_new(&CMS_RecipientInfo_it);
259 	if (!ri)
260 		goto merr;
261 
262 	pk = X509_get0_pubkey(recip);
263 	if (!pk) {
264 		CMSerror(CMS_R_ERROR_GETTING_PUBLIC_KEY);
265 		goto err;
266 	}
267 
268 	switch (cms_pkey_get_ri_type(pk)) {
269 
270 	case CMS_RECIPINFO_TRANS:
271 		if (!cms_RecipientInfo_ktri_init(ri, recip, pk, flags))
272 			goto err;
273 		break;
274 
275 	case CMS_RECIPINFO_AGREE:
276 		if (!cms_RecipientInfo_kari_init(ri, recip, pk, flags))
277 			goto err;
278 		break;
279 
280 	default:
281 		CMSerror(CMS_R_NOT_SUPPORTED_FOR_THIS_KEY_TYPE);
282 		goto err;
283 
284 	}
285 
286 	if (!sk_CMS_RecipientInfo_push(env->recipientInfos, ri))
287 		goto merr;
288 
289 	return ri;
290 
291  merr:
292 	CMSerror(ERR_R_MALLOC_FAILURE);
293  err:
294 	ASN1_item_free((ASN1_VALUE *)ri, &CMS_RecipientInfo_it);
295 	return NULL;
296 }
297 LCRYPTO_ALIAS(CMS_add1_recipient_cert);
298 
299 int
CMS_RecipientInfo_ktri_get0_algs(CMS_RecipientInfo * ri,EVP_PKEY ** pk,X509 ** recip,X509_ALGOR ** palg)300 CMS_RecipientInfo_ktri_get0_algs(CMS_RecipientInfo *ri, EVP_PKEY **pk,
301     X509 **recip, X509_ALGOR **palg)
302 {
303 	CMS_KeyTransRecipientInfo *ktri;
304 
305 	if (ri->type != CMS_RECIPINFO_TRANS) {
306 		CMSerror(CMS_R_NOT_KEY_TRANSPORT);
307 		return 0;
308 	}
309 
310 	ktri = ri->d.ktri;
311 
312 	if (pk)
313 		*pk = ktri->pkey;
314 	if (recip)
315 		*recip = ktri->recip;
316 	if (palg)
317 		*palg = ktri->keyEncryptionAlgorithm;
318 
319 	return 1;
320 }
321 LCRYPTO_ALIAS(CMS_RecipientInfo_ktri_get0_algs);
322 
323 int
CMS_RecipientInfo_ktri_get0_signer_id(CMS_RecipientInfo * ri,ASN1_OCTET_STRING ** keyid,X509_NAME ** issuer,ASN1_INTEGER ** sno)324 CMS_RecipientInfo_ktri_get0_signer_id(CMS_RecipientInfo *ri,
325     ASN1_OCTET_STRING **keyid, X509_NAME **issuer, ASN1_INTEGER **sno)
326 {
327 	CMS_KeyTransRecipientInfo *ktri;
328 
329 	if (ri->type != CMS_RECIPINFO_TRANS) {
330 		CMSerror(CMS_R_NOT_KEY_TRANSPORT);
331 		return 0;
332 	}
333 	ktri = ri->d.ktri;
334 
335 	return cms_SignerIdentifier_get0_signer_id(ktri->rid, keyid, issuer, sno);
336 }
337 LCRYPTO_ALIAS(CMS_RecipientInfo_ktri_get0_signer_id);
338 
339 int
CMS_RecipientInfo_ktri_cert_cmp(CMS_RecipientInfo * ri,X509 * cert)340 CMS_RecipientInfo_ktri_cert_cmp(CMS_RecipientInfo *ri, X509 *cert)
341 {
342 	if (ri->type != CMS_RECIPINFO_TRANS) {
343 		CMSerror(CMS_R_NOT_KEY_TRANSPORT);
344 		return -2;
345 	}
346 
347 	return cms_SignerIdentifier_cert_cmp(ri->d.ktri->rid, cert);
348 }
349 LCRYPTO_ALIAS(CMS_RecipientInfo_ktri_cert_cmp);
350 
351 int
CMS_RecipientInfo_set0_pkey(CMS_RecipientInfo * ri,EVP_PKEY * pkey)352 CMS_RecipientInfo_set0_pkey(CMS_RecipientInfo *ri, EVP_PKEY *pkey)
353 {
354 	if (ri->type != CMS_RECIPINFO_TRANS) {
355 		CMSerror(CMS_R_NOT_KEY_TRANSPORT);
356 		return 0;
357 	}
358 	EVP_PKEY_free(ri->d.ktri->pkey);
359 	ri->d.ktri->pkey = pkey;
360 
361 	return 1;
362 }
363 LCRYPTO_ALIAS(CMS_RecipientInfo_set0_pkey);
364 
365 /* Encrypt content key in key transport recipient info */
366 
367 static int
cms_RecipientInfo_ktri_encrypt(CMS_ContentInfo * cms,CMS_RecipientInfo * ri)368 cms_RecipientInfo_ktri_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
369 {
370 	CMS_KeyTransRecipientInfo *ktri;
371 	CMS_EncryptedContentInfo *ec;
372 	EVP_PKEY_CTX *pctx;
373 	unsigned char *ek = NULL;
374 	size_t eklen;
375 
376 	int ret = 0;
377 
378 	if (ri->type != CMS_RECIPINFO_TRANS) {
379 		CMSerror(CMS_R_NOT_KEY_TRANSPORT);
380 		return 0;
381 	}
382 	ktri = ri->d.ktri;
383 	ec = cms->d.envelopedData->encryptedContentInfo;
384 
385 	pctx = ktri->pctx;
386 
387 	if (pctx) {
388 		if (!cms_env_asn1_ctrl(ri, 0))
389 			goto err;
390 	} else {
391 		pctx = EVP_PKEY_CTX_new(ktri->pkey, NULL);
392 		if (pctx == NULL)
393 			return 0;
394 
395 		if (EVP_PKEY_encrypt_init(pctx) <= 0)
396 			goto err;
397 	}
398 
399 	if (EVP_PKEY_CTX_ctrl(pctx, -1, EVP_PKEY_OP_ENCRYPT,
400 			              EVP_PKEY_CTRL_CMS_ENCRYPT, 0, ri) <= 0) {
401 		CMSerror(CMS_R_CTRL_ERROR);
402 		goto err;
403 	}
404 
405 	if (EVP_PKEY_encrypt(pctx, NULL, &eklen, ec->key, ec->keylen) <= 0)
406 		goto err;
407 
408 	ek = malloc(eklen);
409 
410 	if (ek == NULL) {
411 		CMSerror(ERR_R_MALLOC_FAILURE);
412 		goto err;
413 	}
414 
415 	if (EVP_PKEY_encrypt(pctx, ek, &eklen, ec->key, ec->keylen) <= 0)
416 		goto err;
417 
418 	ASN1_STRING_set0(ktri->encryptedKey, ek, eklen);
419 	ek = NULL;
420 
421 	ret = 1;
422 
423  err:
424 	EVP_PKEY_CTX_free(pctx);
425 	ktri->pctx = NULL;
426 	free(ek);
427 
428 	return ret;
429 }
430 
431 /* Decrypt content key from KTRI */
432 
433 static int
cms_RecipientInfo_ktri_decrypt(CMS_ContentInfo * cms,CMS_RecipientInfo * ri)434 cms_RecipientInfo_ktri_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
435 {
436 	CMS_KeyTransRecipientInfo *ktri = ri->d.ktri;
437 	EVP_PKEY *pkey = ktri->pkey;
438 	unsigned char *ek = NULL;
439 	size_t eklen;
440 	size_t fixlen = 0;
441 	int ret = 0;
442 	CMS_EncryptedContentInfo *ec;
443 
444 	ec = cms->d.envelopedData->encryptedContentInfo;
445 
446 	if (ktri->pkey == NULL) {
447 		CMSerror(CMS_R_NO_PRIVATE_KEY);
448 		return 0;
449 	}
450 
451 	if (cms->d.envelopedData->encryptedContentInfo->havenocert &&
452 	    !cms->d.envelopedData->encryptedContentInfo->debug) {
453 		X509_ALGOR *calg = ec->contentEncryptionAlgorithm;
454 		const EVP_CIPHER *ciph;
455 
456 		if ((ciph = EVP_get_cipherbyobj(calg->algorithm)) == NULL) {
457 			CMSerror(CMS_R_UNKNOWN_CIPHER);
458 			return 0;
459 		}
460 
461 		fixlen = EVP_CIPHER_key_length(ciph);
462 	}
463 
464 	ktri->pctx = EVP_PKEY_CTX_new(pkey, NULL);
465 	if (ktri->pctx == NULL)
466 		return 0;
467 
468 	if (EVP_PKEY_decrypt_init(ktri->pctx) <= 0)
469 		goto err;
470 
471 	if (!cms_env_asn1_ctrl(ri, 1))
472 		goto err;
473 
474 	if (EVP_PKEY_CTX_ctrl(ktri->pctx, -1, EVP_PKEY_OP_DECRYPT,
475 	    EVP_PKEY_CTRL_CMS_DECRYPT, 0, ri) <= 0) {
476 		CMSerror(CMS_R_CTRL_ERROR);
477 		goto err;
478 	}
479 
480 	if (EVP_PKEY_decrypt(ktri->pctx, NULL, &eklen, ktri->encryptedKey->data,
481 	    ktri->encryptedKey->length) <= 0 || eklen == 0 ||
482 	    (fixlen != 0 && eklen != fixlen)) {
483 		CMSerror(CMS_R_CMS_LIB);
484 		goto err;
485 	}
486 
487 	ek = malloc(eklen);
488 
489 	if (ek == NULL) {
490 		CMSerror(ERR_R_MALLOC_FAILURE);
491 		goto err;
492 	}
493 
494 	if (EVP_PKEY_decrypt(ktri->pctx, ek, &eklen, ktri->encryptedKey->data,
495 	    ktri->encryptedKey->length) <= 0) {
496 		CMSerror(CMS_R_CMS_LIB);
497 		goto err;
498 	}
499 
500 	ret = 1;
501 
502 	freezero(ec->key, ec->keylen);
503 	ec->key = ek;
504 	ec->keylen = eklen;
505 
506  err:
507 	EVP_PKEY_CTX_free(ktri->pctx);
508 	ktri->pctx = NULL;
509 	if (!ret)
510 		free(ek);
511 
512 	return ret;
513 }
514 
515 /* Key Encrypted Key (KEK) RecipientInfo routines */
516 
517 int
CMS_RecipientInfo_kekri_id_cmp(CMS_RecipientInfo * ri,const unsigned char * id,size_t idlen)518 CMS_RecipientInfo_kekri_id_cmp(CMS_RecipientInfo *ri, const unsigned char *id,
519     size_t idlen)
520 {
521 	ASN1_OCTET_STRING tmp_os;
522 	CMS_KEKRecipientInfo *kekri;
523 
524 	if (ri->type != CMS_RECIPINFO_KEK) {
525 		CMSerror(CMS_R_NOT_KEK);
526 		return -2;
527 	}
528 	kekri = ri->d.kekri;
529 	tmp_os.type = V_ASN1_OCTET_STRING;
530 	tmp_os.flags = 0;
531 	tmp_os.data = (unsigned char *)id;
532 	tmp_os.length = (int)idlen;
533 
534 	return ASN1_OCTET_STRING_cmp(&tmp_os, kekri->kekid->keyIdentifier);
535 }
536 LCRYPTO_ALIAS(CMS_RecipientInfo_kekri_id_cmp);
537 
538 /* For now hard code AES key wrap info */
539 
540 static size_t
aes_wrap_keylen(int nid)541 aes_wrap_keylen(int nid)
542 {
543 	switch (nid) {
544 	case NID_id_aes128_wrap:
545 		return 16;
546 
547 	case NID_id_aes192_wrap:
548 		return 24;
549 
550 	case NID_id_aes256_wrap:
551 		return 32;
552 
553 	default:
554 		return 0;
555 	}
556 }
557 
558 CMS_RecipientInfo *
CMS_add0_recipient_key(CMS_ContentInfo * cms,int nid,unsigned char * key,size_t keylen,unsigned char * id,size_t idlen,ASN1_GENERALIZEDTIME * date,ASN1_OBJECT * otherTypeId,ASN1_TYPE * otherType)559 CMS_add0_recipient_key(CMS_ContentInfo *cms, int nid, unsigned char *key,
560     size_t keylen, unsigned char *id, size_t idlen, ASN1_GENERALIZEDTIME *date,
561     ASN1_OBJECT *otherTypeId, ASN1_TYPE *otherType)
562 {
563 	CMS_RecipientInfo *ri = NULL;
564 	CMS_EnvelopedData *env;
565 	CMS_KEKRecipientInfo *kekri;
566 
567 	env = cms_get0_enveloped(cms);
568 	if (!env)
569 		goto err;
570 
571 	if (nid == NID_undef) {
572 		switch (keylen) {
573 		case 16:
574 			nid = NID_id_aes128_wrap;
575 			break;
576 
577 		case 24:
578 			nid = NID_id_aes192_wrap;
579 			break;
580 
581 		case 32:
582 			nid = NID_id_aes256_wrap;
583 			break;
584 
585 		default:
586 			CMSerror(CMS_R_INVALID_KEY_LENGTH);
587 			goto err;
588 		}
589 
590 	} else {
591 
592 		size_t exp_keylen = aes_wrap_keylen(nid);
593 
594 		if (!exp_keylen) {
595 			CMSerror(CMS_R_UNSUPPORTED_KEK_ALGORITHM);
596 			goto err;
597 		}
598 
599 		if (keylen != exp_keylen) {
600 			CMSerror(CMS_R_INVALID_KEY_LENGTH);
601 			goto err;
602 		}
603 
604 	}
605 
606 	/* Initialize recipient info */
607 	ri = (CMS_RecipientInfo *)ASN1_item_new(&CMS_RecipientInfo_it);
608 	if (!ri)
609 		goto merr;
610 
611 	ri->d.kekri = (CMS_KEKRecipientInfo *)ASN1_item_new(&CMS_KEKRecipientInfo_it);
612 	if (!ri->d.kekri)
613 		goto merr;
614 	ri->type = CMS_RECIPINFO_KEK;
615 
616 	kekri = ri->d.kekri;
617 
618 	if (otherTypeId) {
619 		kekri->kekid->other = (CMS_OtherKeyAttribute *)ASN1_item_new(&CMS_OtherKeyAttribute_it);
620 		if (kekri->kekid->other == NULL)
621 			goto merr;
622 	}
623 
624 	if (!sk_CMS_RecipientInfo_push(env->recipientInfos, ri))
625 		goto merr;
626 
627 	/* After this point no calls can fail */
628 
629 	kekri->version = 4;
630 
631 	kekri->key = key;
632 	kekri->keylen = keylen;
633 
634 	ASN1_STRING_set0(kekri->kekid->keyIdentifier, id, idlen);
635 
636 	kekri->kekid->date = date;
637 
638 	if (kekri->kekid->other) {
639 		kekri->kekid->other->keyAttrId = otherTypeId;
640 		kekri->kekid->other->keyAttr = otherType;
641 	}
642 
643 	X509_ALGOR_set0(kekri->keyEncryptionAlgorithm,
644 			        OBJ_nid2obj(nid), V_ASN1_UNDEF, NULL);
645 
646 	return ri;
647 
648  merr:
649 	CMSerror(ERR_R_MALLOC_FAILURE);
650  err:
651 	ASN1_item_free((ASN1_VALUE *)ri, &CMS_RecipientInfo_it);
652 	return NULL;
653 }
654 LCRYPTO_ALIAS(CMS_add0_recipient_key);
655 
656 int
CMS_RecipientInfo_kekri_get0_id(CMS_RecipientInfo * ri,X509_ALGOR ** palg,ASN1_OCTET_STRING ** pid,ASN1_GENERALIZEDTIME ** pdate,ASN1_OBJECT ** potherid,ASN1_TYPE ** pothertype)657 CMS_RecipientInfo_kekri_get0_id(CMS_RecipientInfo *ri, X509_ALGOR **palg,
658     ASN1_OCTET_STRING **pid, ASN1_GENERALIZEDTIME **pdate,
659     ASN1_OBJECT **potherid, ASN1_TYPE **pothertype)
660 {
661 	CMS_KEKIdentifier *rkid;
662 
663 	if (ri->type != CMS_RECIPINFO_KEK) {
664 		CMSerror(CMS_R_NOT_KEK);
665 		return 0;
666 	}
667 	rkid = ri->d.kekri->kekid;
668 	if (palg)
669 		*palg = ri->d.kekri->keyEncryptionAlgorithm;
670 	if (pid)
671 		*pid = rkid->keyIdentifier;
672 	if (pdate)
673 		*pdate = rkid->date;
674 	if (potherid) {
675 		if (rkid->other)
676 			*potherid = rkid->other->keyAttrId;
677 		else
678 			*potherid = NULL;
679 	}
680 	if (pothertype) {
681 		if (rkid->other)
682 			*pothertype = rkid->other->keyAttr;
683 		else
684 			*pothertype = NULL;
685 	}
686 
687 	return 1;
688 }
689 LCRYPTO_ALIAS(CMS_RecipientInfo_kekri_get0_id);
690 
691 int
CMS_RecipientInfo_set0_key(CMS_RecipientInfo * ri,unsigned char * key,size_t keylen)692 CMS_RecipientInfo_set0_key(CMS_RecipientInfo *ri, unsigned char *key,
693     size_t keylen)
694 {
695 	CMS_KEKRecipientInfo *kekri;
696 
697 	if (ri->type != CMS_RECIPINFO_KEK) {
698 		CMSerror(CMS_R_NOT_KEK);
699 		return 0;
700 	}
701 
702 	kekri = ri->d.kekri;
703 	kekri->key = key;
704 	kekri->keylen = keylen;
705 	return 1;
706 }
707 LCRYPTO_ALIAS(CMS_RecipientInfo_set0_key);
708 
709 /* Encrypt content key in KEK recipient info */
710 
711 static int
cms_RecipientInfo_kekri_encrypt(CMS_ContentInfo * cms,CMS_RecipientInfo * ri)712 cms_RecipientInfo_kekri_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
713 {
714 	CMS_EncryptedContentInfo *ec;
715 	CMS_KEKRecipientInfo *kekri;
716 	AES_KEY actx;
717 	unsigned char *wkey = NULL;
718 	int wkeylen;
719 	int r = 0;
720 
721 	ec = cms->d.envelopedData->encryptedContentInfo;
722 	kekri = ri->d.kekri;
723 
724 	if (!kekri->key) {
725 		CMSerror(CMS_R_NO_KEY);
726 		return 0;
727 	}
728 
729 	if (AES_set_encrypt_key(kekri->key, kekri->keylen << 3, &actx)) {
730 		CMSerror(CMS_R_ERROR_SETTING_KEY);
731 		goto err;
732 	}
733 
734 	wkey = malloc(ec->keylen + 8);
735 	if (wkey == NULL) {
736 		CMSerror(ERR_R_MALLOC_FAILURE);
737 		goto err;
738 	}
739 
740 	wkeylen = AES_wrap_key(&actx, NULL, wkey, ec->key, ec->keylen);
741 	if (wkeylen <= 0) {
742 		CMSerror(CMS_R_WRAP_ERROR);
743 		goto err;
744 	}
745 
746 	ASN1_STRING_set0(kekri->encryptedKey, wkey, wkeylen);
747 
748 	r = 1;
749 
750  err:
751 	if (!r)
752 		free(wkey);
753 	explicit_bzero(&actx, sizeof(actx));
754 
755 	return r;
756 }
757 
758 /* Decrypt content key in KEK recipient info */
759 
760 static int
cms_RecipientInfo_kekri_decrypt(CMS_ContentInfo * cms,CMS_RecipientInfo * ri)761 cms_RecipientInfo_kekri_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
762 {
763 	CMS_EncryptedContentInfo *ec;
764 	CMS_KEKRecipientInfo *kekri;
765 	AES_KEY actx;
766 	unsigned char *ukey = NULL;
767 	int ukeylen;
768 	int r = 0, wrap_nid;
769 
770 	ec = cms->d.envelopedData->encryptedContentInfo;
771 	kekri = ri->d.kekri;
772 
773 	if (!kekri->key) {
774 		CMSerror(CMS_R_NO_KEY);
775 		return 0;
776 	}
777 
778 	wrap_nid = OBJ_obj2nid(kekri->keyEncryptionAlgorithm->algorithm);
779 	if (aes_wrap_keylen(wrap_nid) != kekri->keylen) {
780 		CMSerror(CMS_R_INVALID_KEY_LENGTH);
781 		return 0;
782 	}
783 
784 	/* If encrypted key length is invalid don't bother */
785 
786 	if (kekri->encryptedKey->length < 16) {
787 		CMSerror(CMS_R_INVALID_ENCRYPTED_KEY_LENGTH);
788 		goto err;
789 	}
790 
791 	if (AES_set_decrypt_key(kekri->key, kekri->keylen << 3, &actx)) {
792 		CMSerror(CMS_R_ERROR_SETTING_KEY);
793 		goto err;
794 	}
795 
796 	ukey = malloc(kekri->encryptedKey->length - 8);
797 	if (ukey == NULL) {
798 		CMSerror(ERR_R_MALLOC_FAILURE);
799 		goto err;
800 	}
801 
802 	ukeylen = AES_unwrap_key(&actx, NULL, ukey, kekri->encryptedKey->data,
803 	    kekri->encryptedKey->length);
804 
805 	if (ukeylen <= 0) {
806 		CMSerror(CMS_R_UNWRAP_ERROR);
807 		goto err;
808 	}
809 
810 	freezero(ec->key, ec->keylen);
811 	ec->key = ukey;
812 	ec->keylen = ukeylen;
813 
814 	r = 1;
815 
816  err:
817 
818 	if (!r)
819 		free(ukey);
820 	explicit_bzero(&actx, sizeof(actx));
821 
822 	return r;
823 }
824 
825 int
CMS_RecipientInfo_decrypt(CMS_ContentInfo * cms,CMS_RecipientInfo * ri)826 CMS_RecipientInfo_decrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
827 {
828 	switch (ri->type) {
829 	case CMS_RECIPINFO_TRANS:
830 		return cms_RecipientInfo_ktri_decrypt(cms, ri);
831 
832 	case CMS_RECIPINFO_KEK:
833 		return cms_RecipientInfo_kekri_decrypt(cms, ri);
834 
835 	case CMS_RECIPINFO_PASS:
836 		return cms_RecipientInfo_pwri_crypt(cms, ri, 0);
837 
838 	default:
839 		CMSerror(CMS_R_UNSUPPORTED_RECIPIENTINFO_TYPE);
840 		return 0;
841 	}
842 }
843 LCRYPTO_ALIAS(CMS_RecipientInfo_decrypt);
844 
845 int
CMS_RecipientInfo_encrypt(CMS_ContentInfo * cms,CMS_RecipientInfo * ri)846 CMS_RecipientInfo_encrypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri)
847 {
848 	switch (ri->type) {
849 	case CMS_RECIPINFO_TRANS:
850 		return cms_RecipientInfo_ktri_encrypt(cms, ri);
851 
852 	case CMS_RECIPINFO_AGREE:
853 		return cms_RecipientInfo_kari_encrypt(cms, ri);
854 
855 	case CMS_RECIPINFO_KEK:
856 		return cms_RecipientInfo_kekri_encrypt(cms, ri);
857 
858 	case CMS_RECIPINFO_PASS:
859 		return cms_RecipientInfo_pwri_crypt(cms, ri, 1);
860 
861 	default:
862 		CMSerror(CMS_R_UNSUPPORTED_RECIPIENT_TYPE);
863 		return 0;
864 	}
865 }
866 LCRYPTO_ALIAS(CMS_RecipientInfo_encrypt);
867 
868 /* Check structures and fixup version numbers (if necessary) */
869 
870 static void
cms_env_set_originfo_version(CMS_EnvelopedData * env)871 cms_env_set_originfo_version(CMS_EnvelopedData *env)
872 {
873 	CMS_OriginatorInfo *org = env->originatorInfo;
874 	int i;
875 
876 	if (org == NULL)
877 		return;
878 	for (i = 0; i < sk_CMS_CertificateChoices_num(org->certificates); i++) {
879 		CMS_CertificateChoices *cch;
880 
881 		cch = sk_CMS_CertificateChoices_value(org->certificates, i);
882 		if (cch->type == CMS_CERTCHOICE_OTHER) {
883 			env->version = 4;
884 			return;
885 		} else if (cch->type == CMS_CERTCHOICE_V2ACERT) {
886 			if (env->version < 3)
887 			    env->version = 3;
888 		}
889 	}
890 
891 	for (i = 0; i < sk_CMS_RevocationInfoChoice_num(org->crls); i++) {
892 		CMS_RevocationInfoChoice *rch;
893 
894 		rch = sk_CMS_RevocationInfoChoice_value(org->crls, i);
895 		if (rch->type == CMS_REVCHOICE_OTHER) {
896 			env->version = 4;
897 			return;
898 		}
899 	}
900 }
901 
902 static void
cms_env_set_version(CMS_EnvelopedData * env)903 cms_env_set_version(CMS_EnvelopedData *env)
904 {
905 	int i;
906 	CMS_RecipientInfo *ri;
907 
908 	/*
909 	 * Can't set version higher than 4 so if 4 or more already nothing to do.
910 	 */
911 	if (env->version >= 4)
912 		return;
913 
914 	cms_env_set_originfo_version(env);
915 
916 	if (env->version >= 3)
917 		return;
918 
919 	for (i = 0; i < sk_CMS_RecipientInfo_num(env->recipientInfos); i++) {
920 		ri = sk_CMS_RecipientInfo_value(env->recipientInfos, i);
921 		if (ri->type == CMS_RECIPINFO_PASS || ri->type == CMS_RECIPINFO_OTHER) {
922 			env->version = 3;
923 			return;
924 		} else if (ri->type != CMS_RECIPINFO_TRANS
925 			       || ri->d.ktri->version != 0) {
926 			env->version = 2;
927 		}
928 	}
929 	if (env->originatorInfo || env->unprotectedAttrs)
930 		env->version = 2;
931 	if (env->version == 2)
932 		return;
933 	env->version = 0;
934 }
935 
936 BIO *
cms_EnvelopedData_init_bio(CMS_ContentInfo * cms)937 cms_EnvelopedData_init_bio(CMS_ContentInfo *cms)
938 {
939 	CMS_EncryptedContentInfo *ec;
940 	STACK_OF(CMS_RecipientInfo) *rinfos;
941 	CMS_RecipientInfo *ri;
942 	int i, ok = 0;
943 	BIO *ret;
944 
945 	/* Get BIO first to set up key */
946 
947 	ec = cms->d.envelopedData->encryptedContentInfo;
948 	ret = cms_EncryptedContent_init_bio(ec);
949 
950 	/* If error or no cipher end of processing */
951 
952 	if (!ret || !ec->cipher)
953 		return ret;
954 
955 	/* Now encrypt content key according to each RecipientInfo type */
956 
957 	rinfos = cms->d.envelopedData->recipientInfos;
958 
959 	for (i = 0; i < sk_CMS_RecipientInfo_num(rinfos); i++) {
960 		ri = sk_CMS_RecipientInfo_value(rinfos, i);
961 		if (CMS_RecipientInfo_encrypt(cms, ri) <= 0) {
962 			CMSerror(CMS_R_ERROR_SETTING_RECIPIENTINFO);
963 			goto err;
964 		}
965 	}
966 	cms_env_set_version(cms->d.envelopedData);
967 
968 	ok = 1;
969 
970  err:
971 	ec->cipher = NULL;
972 	freezero(ec->key, ec->keylen);
973 	ec->key = NULL;
974 	ec->keylen = 0;
975 	if (ok)
976 		return ret;
977 	BIO_free(ret);
978 	return NULL;
979 }
980 
981 /*
982  * Get RecipientInfo type (if any) supported by a key (public or private). To
983  * retain compatibility with previous behaviour if the ctrl value isn't
984  * supported we assume key transport.
985  */
986 int
cms_pkey_get_ri_type(EVP_PKEY * pk)987 cms_pkey_get_ri_type(EVP_PKEY *pk)
988 {
989 	if (pk->ameth && pk->ameth->pkey_ctrl) {
990 		int i, r;
991 		i = pk->ameth->pkey_ctrl(pk, ASN1_PKEY_CTRL_CMS_RI_TYPE, 0, &r);
992 		if (i > 0)
993 			return r;
994 	}
995 	return CMS_RECIPINFO_TRANS;
996 }
997