xref: /openbsd/usr.bin/openssl/cms.c (revision 6156097a)
1 /* $OpenBSD: cms.c,v 1.36 2024/08/12 15:34:58 job Exp $ */
2 /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
3  * project.
4  */
5 /* ====================================================================
6  * Copyright (c) 2008 The OpenSSL Project.  All rights reserved.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  *
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  *
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in
17  *    the documentation and/or other materials provided with the
18  *    distribution.
19  *
20  * 3. All advertising materials mentioning features or use of this
21  *    software must display the following acknowledgment:
22  *    "This product includes software developed by the OpenSSL Project
23  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
24  *
25  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
26  *    endorse or promote products derived from this software without
27  *    prior written permission. For written permission, please contact
28  *    licensing@OpenSSL.org.
29  *
30  * 5. Products derived from this software may not be called "OpenSSL"
31  *    nor may "OpenSSL" appear in their names without prior written
32  *    permission of the OpenSSL Project.
33  *
34  * 6. Redistributions of any form whatsoever must retain the following
35  *    acknowledgment:
36  *    "This product includes software developed by the OpenSSL Project
37  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
38  *
39  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
40  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
41  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
42  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
43  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
44  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
45  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
46  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
47  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
48  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
49  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
50  * OF THE POSSIBILITY OF SUCH DAMAGE.
51  * ====================================================================
52  */
53 
54 /* CMS utility function */
55 
56 #include <stdio.h>
57 #include <string.h>
58 
59 #include "apps.h"
60 
61 #ifndef OPENSSL_NO_CMS
62 
63 #include <openssl/crypto.h>
64 #include <openssl/err.h>
65 #include <openssl/pem.h>
66 #include <openssl/x509_vfy.h>
67 #include <openssl/x509v3.h>
68 
69 #include <openssl/cms.h>
70 
71 static int save_certs(char *signerfile, STACK_OF(X509) *signers);
72 static void receipt_request_print(BIO *out, CMS_ContentInfo *cms);
73 static CMS_ReceiptRequest *make_receipt_request(
74     STACK_OF(OPENSSL_STRING) *rr_to, int rr_allorfirst,
75     STACK_OF(OPENSSL_STRING) *rr_from);
76 static int cms_set_pkey_param(EVP_PKEY_CTX *pctx,
77     STACK_OF(OPENSSL_STRING) *param);
78 
79 #define SMIME_OP	0x10
80 #define SMIME_IP	0x20
81 #define SMIME_SIGNERS	0x40
82 #define SMIME_ENCRYPT		(1 | SMIME_OP)
83 #define SMIME_DECRYPT		(2 | SMIME_IP)
84 #define SMIME_SIGN		(3 | SMIME_OP | SMIME_SIGNERS)
85 #define SMIME_VERIFY		(4 | SMIME_IP)
86 #define SMIME_CMSOUT		(5 | SMIME_IP | SMIME_OP)
87 #define SMIME_RESIGN		(6 | SMIME_IP | SMIME_OP | SMIME_SIGNERS)
88 #define SMIME_DATAOUT		(7 | SMIME_IP)
89 #define SMIME_DATA_CREATE	(8 | SMIME_OP)
90 #define SMIME_DIGEST_VERIFY	(9 | SMIME_IP)
91 #define SMIME_DIGEST_CREATE	(10 | SMIME_OP)
92 #define SMIME_UNCOMPRESS	(11 | SMIME_IP)
93 #define SMIME_COMPRESS		(12 | SMIME_OP)
94 #define SMIME_ENCRYPTED_DECRYPT	(13 | SMIME_IP)
95 #define SMIME_ENCRYPTED_ENCRYPT	(14 | SMIME_OP)
96 #define SMIME_SIGN_RECEIPT	(15 | SMIME_IP | SMIME_OP)
97 #define SMIME_VERIFY_RECEIPT	(16 | SMIME_IP)
98 
99 int verify_err = 0;
100 
101 struct cms_key_param {
102 	int idx;
103 	STACK_OF(OPENSSL_STRING) *param;
104 	struct cms_key_param *next;
105 };
106 
107 static struct {
108 	char *CAfile;
109 	char *CApath;
110 	X509 *cert;
111 	char *certfile;
112 	char *certsoutfile;
113 	char *crlfile;
114 	const EVP_CIPHER *cipher;
115 	char *contfile;
116 	ASN1_OBJECT *econtent_type;
117 	STACK_OF(X509) *encerts;
118 	int flags;
119 	char *from;
120 	char *infile;
121 	int informat;
122 	struct cms_key_param *key_first;
123 	struct cms_key_param *key_param;
124 	char *keyfile;
125 	int keyform;
126 	int noout;
127 	int operation;
128 	char *outfile;
129 	int outformat;
130 	char *passargin;
131 	int print;
132 	unsigned char *pwri_pass;
133 	int rr_allorfirst;
134 	STACK_OF(OPENSSL_STRING) *rr_from;
135 	int rr_print;
136 	STACK_OF(OPENSSL_STRING) *rr_to;
137 	char *rctfile;
138 	int rctformat;
139 	char *recipfile;
140 	unsigned char *secret_key;
141 	unsigned char *secret_keyid;
142 	size_t secret_keyidlen;
143 	size_t secret_keylen;
144 	const EVP_MD *sign_md;
145 	char *signerfile;
146 	STACK_OF(OPENSSL_STRING) *skkeys;
147 	STACK_OF(OPENSSL_STRING) *sksigners;
148 	char *subject;
149 	char *to;
150 	int verify_retcode;
151 	X509_VERIFY_PARAM *vpm;
152 } cfg;
153 
154 static const EVP_CIPHER *
get_cipher_by_name(char * name)155 get_cipher_by_name(char *name)
156 {
157 	if (name == NULL || strcmp(name, "") == 0)
158 		return (NULL);
159 #ifndef OPENSSL_NO_AES
160 	else if (strcmp(name, "aes128") == 0)
161 		return EVP_aes_128_cbc();
162 	else if (strcmp(name, "aes192") == 0)
163 		return EVP_aes_192_cbc();
164 	else if (strcmp(name, "aes256") == 0)
165 		return EVP_aes_256_cbc();
166 #endif
167 #ifndef OPENSSL_NO_CAMELLIA
168 	else if (strcmp(name, "camellia128") == 0)
169 		return EVP_camellia_128_cbc();
170 	else if (strcmp(name, "camellia192") == 0)
171 		return EVP_camellia_192_cbc();
172 	else if (strcmp(name, "camellia256") == 0)
173 		return EVP_camellia_256_cbc();
174 #endif
175 #ifndef OPENSSL_NO_DES
176 	else if (strcmp(name, "des") == 0)
177 		return EVP_des_cbc();
178 	else if (strcmp(name, "des3") == 0)
179 		return EVP_des_ede3_cbc();
180 #endif
181 #ifndef OPENSSL_NO_RC2
182 	else if (!strcmp(name, "rc2-40"))
183 		return EVP_rc2_40_cbc();
184 	else if (!strcmp(name, "rc2-64"))
185 		return EVP_rc2_64_cbc();
186 	else if (!strcmp(name, "rc2-128"))
187 		return EVP_rc2_cbc();
188 #endif
189 	else
190 		return (NULL);
191 }
192 
193 static int
cms_opt_cipher(int argc,char ** argv,int * argsused)194 cms_opt_cipher(int argc, char **argv, int *argsused)
195 {
196 	char *name = argv[0];
197 
198 	if (*name++ != '-')
199 		return (1);
200 
201 	if ((cfg.cipher = get_cipher_by_name(name)) == NULL)
202 		if ((cfg.cipher = EVP_get_cipherbyname(name)) == NULL)
203 			return (1);
204 
205 	*argsused = 1;
206 	return (0);
207 }
208 
209 static int
cms_opt_econtent_type(char * arg)210 cms_opt_econtent_type(char *arg)
211 {
212 	ASN1_OBJECT_free(cfg.econtent_type);
213 
214 	if ((cfg.econtent_type = OBJ_txt2obj(arg, 0)) == NULL) {
215 		BIO_printf(bio_err, "Invalid OID %s\n", arg);
216 		return (1);
217 	}
218 	return (0);
219 }
220 
221 static int
cms_opt_inkey(char * arg)222 cms_opt_inkey(char *arg)
223 {
224 	if (cfg.keyfile == NULL) {
225 		cfg.keyfile = arg;
226 		return (0);
227 	}
228 
229 	if (cfg.signerfile == NULL) {
230 		BIO_puts(bio_err, "Illegal -inkey without -signer\n");
231 		return (1);
232 	}
233 
234 	if (cfg.sksigners == NULL)
235 		cfg.sksigners = sk_OPENSSL_STRING_new_null();
236 	if (cfg.sksigners == NULL)
237 		return (1);
238 	if (!sk_OPENSSL_STRING_push(cfg.sksigners, cfg.signerfile))
239 		return (1);
240 
241 	cfg.signerfile = NULL;
242 
243 	if (cfg.skkeys == NULL)
244 		cfg.skkeys = sk_OPENSSL_STRING_new_null();
245 	if (cfg.skkeys == NULL)
246 		return (1);
247 	if (!sk_OPENSSL_STRING_push(cfg.skkeys, cfg.keyfile))
248 		return (1);
249 
250 	cfg.keyfile = arg;
251 	return (0);
252 }
253 
254 static int
cms_opt_keyopt(char * arg)255 cms_opt_keyopt(char *arg)
256 {
257 	int keyidx = -1;
258 
259 	if (cfg.operation == SMIME_ENCRYPT) {
260 		if (cfg.encerts != NULL)
261 			keyidx += sk_X509_num(cfg.encerts);
262 	} else {
263 		if (cfg.keyfile != NULL || cfg.signerfile != NULL)
264 			keyidx++;
265 		if (cfg.skkeys != NULL)
266 			keyidx += sk_OPENSSL_STRING_num(cfg.skkeys);
267 	}
268 
269 	if (keyidx < 0) {
270 		BIO_printf(bio_err, "No key specified\n");
271 		return (1);
272 	}
273 
274 	if (cfg.key_param == NULL ||
275 	    cfg.key_param->idx != keyidx) {
276 		struct cms_key_param *nparam;
277 
278 		if ((nparam = calloc(1, sizeof(struct cms_key_param))) == NULL)
279 			return (1);
280 
281 		nparam->idx = keyidx;
282 		if ((nparam->param = sk_OPENSSL_STRING_new_null()) == NULL) {
283 			free(nparam);
284 			return (1);
285 		}
286 
287 		nparam->next = NULL;
288 		if (cfg.key_first == NULL)
289 			cfg.key_first = nparam;
290 		else
291 			cfg.key_param->next = nparam;
292 
293 		cfg.key_param = nparam;
294 	}
295 
296 	if (!sk_OPENSSL_STRING_push(cfg.key_param->param, arg))
297 		return (1);
298 
299 	return (0);
300 }
301 
302 static int
cms_opt_md(char * arg)303 cms_opt_md(char *arg)
304 {
305 	if ((cfg.sign_md = EVP_get_digestbyname(arg)) == NULL) {
306 		BIO_printf(bio_err, "Unknown digest %s\n", arg);
307 		return (1);
308 	}
309 	return (0);
310 }
311 
312 static int
cms_opt_print(void)313 cms_opt_print(void)
314 {
315 	cfg.noout = 1;
316 	cfg.print = 1;
317 	return (0);
318 }
319 
320 static int
cms_opt_pwri_pass(char * arg)321 cms_opt_pwri_pass(char *arg)
322 {
323 	cfg.pwri_pass = (unsigned char *)arg;
324 	return (0);
325 }
326 
327 static int
cms_opt_recip(char * arg)328 cms_opt_recip(char *arg)
329 {
330 	if (cfg.operation == SMIME_ENCRYPT) {
331 		if (cfg.encerts == NULL) {
332 			if ((cfg.encerts = sk_X509_new_null()) == NULL)
333 				return (1);
334 		}
335 
336 		cfg.cert = load_cert(bio_err, arg, FORMAT_PEM,
337 		    NULL, "recipient certificate file");
338 		if (cfg.cert == NULL)
339 			return (1);
340 
341 		if (!sk_X509_push(cfg.encerts, cfg.cert))
342 			return (1);
343 
344 		cfg.cert = NULL;
345 	} else {
346 		cfg.recipfile = arg;
347 	}
348 	return (0);
349 }
350 
351 static int
cms_opt_receipt_request_from(char * arg)352 cms_opt_receipt_request_from(char *arg)
353 {
354 	if (cfg.rr_from == NULL)
355 		cfg.rr_from = sk_OPENSSL_STRING_new_null();
356 	if (cfg.rr_from == NULL)
357 		return (1);
358 	if (!sk_OPENSSL_STRING_push(cfg.rr_from, arg))
359 		return (1);
360 
361 	return (0);
362 }
363 
364 static int
cms_opt_receipt_request_to(char * arg)365 cms_opt_receipt_request_to(char *arg)
366 {
367 	if (cfg.rr_to == NULL)
368 		cfg.rr_to = sk_OPENSSL_STRING_new_null();
369 	if (cfg.rr_to == NULL)
370 		return (1);
371 	if (!sk_OPENSSL_STRING_push(cfg.rr_to, arg))
372 		return (1);
373 
374 	return (0);
375 }
376 
377 static int
cms_opt_secretkey(char * arg)378 cms_opt_secretkey(char *arg)
379 {
380 	long ltmp;
381 
382 	free(cfg.secret_key);
383 
384 	if ((cfg.secret_key = string_to_hex(arg, &ltmp)) == NULL) {
385 		BIO_printf(bio_err, "Invalid key %s\n", arg);
386 		return (1);
387 	}
388 	cfg.secret_keylen = (size_t)ltmp;
389 	return (0);
390 }
391 
392 static int
cms_opt_secretkeyid(char * arg)393 cms_opt_secretkeyid(char *arg)
394 {
395 	long ltmp;
396 
397 	free(cfg.secret_keyid);
398 
399 	if ((cfg.secret_keyid = string_to_hex(arg, &ltmp)) == NULL) {
400 		BIO_printf(bio_err, "Invalid id %s\n", arg);
401 		return (1);
402 	}
403 	cfg.secret_keyidlen = (size_t)ltmp;
404 	return (0);
405 }
406 
407 static int
cms_opt_signer(char * arg)408 cms_opt_signer(char *arg)
409 {
410 	if (cfg.signerfile == NULL) {
411 		cfg.signerfile = arg;
412 		return (0);
413 	}
414 
415 	if (cfg.sksigners == NULL)
416 		cfg.sksigners = sk_OPENSSL_STRING_new_null();
417 	if (cfg.sksigners == NULL)
418 		return (1);
419 	if (!sk_OPENSSL_STRING_push(cfg.sksigners, cfg.signerfile))
420 		return (1);
421 
422 	if (cfg.keyfile == NULL)
423 		cfg.keyfile = cfg.signerfile;
424 
425 	if (cfg.skkeys == NULL)
426 		cfg.skkeys = sk_OPENSSL_STRING_new_null();
427 	if (cfg.skkeys == NULL)
428 		return (1);
429 	if (!sk_OPENSSL_STRING_push(cfg.skkeys, cfg.keyfile))
430 		return (1);
431 
432 	cfg.keyfile = NULL;
433 
434 	cfg.signerfile = arg;
435 	return (0);
436 }
437 
438 static int
cms_opt_verify_param(int argc,char ** argv,int * argsused)439 cms_opt_verify_param(int argc, char **argv, int *argsused)
440 {
441 	int oargc = argc;
442 	int badarg = 0;
443 
444 	if (!args_verify(&argv, &argc, &badarg, bio_err, &cfg.vpm))
445 		return (1);
446 	if (badarg)
447 		return (1);
448 
449 	*argsused = oargc - argc;
450 
451 	return (0);
452 }
453 
454 static int
cms_opt_verify_receipt(char * arg)455 cms_opt_verify_receipt(char *arg)
456 {
457 	cfg.operation = SMIME_VERIFY_RECEIPT;
458 	cfg.rctfile = arg;
459 	return (0);
460 }
461 
462 static const struct option cms_options[] = {
463 #ifndef OPENSSL_NO_AES
464 	{
465 		.name = "aes128",
466 		.desc = "Encrypt PEM output with CBC AES",
467 		.type = OPTION_ARGV_FUNC,
468 		.opt.argvfunc = cms_opt_cipher,
469 	},
470 	{
471 		.name = "aes192",
472 		.desc = "Encrypt PEM output with CBC AES",
473 		.type = OPTION_ARGV_FUNC,
474 		.opt.argvfunc = cms_opt_cipher,
475 	},
476 	{
477 		.name = "aes256",
478 		.desc = "Encrypt PEM output with CBC AES",
479 		.type = OPTION_ARGV_FUNC,
480 		.opt.argvfunc = cms_opt_cipher,
481 	},
482 #endif
483 #ifndef OPENSSL_NO_CAMELLIA
484 	{
485 		.name = "camellia128",
486 		.desc = "Encrypt PEM output with CBC Camellia",
487 		.type = OPTION_ARGV_FUNC,
488 		.opt.argvfunc = cms_opt_cipher,
489 	},
490 	{
491 		.name = "camellia192",
492 		.desc = "Encrypt PEM output with CBC Camellia",
493 		.type = OPTION_ARGV_FUNC,
494 		.opt.argvfunc = cms_opt_cipher,
495 	},
496 	{
497 		.name = "camellia256",
498 		.desc = "Encrypt PEM output with CBC Camellia",
499 		.type = OPTION_ARGV_FUNC,
500 		.opt.argvfunc = cms_opt_cipher,
501 	},
502 #endif
503 #ifndef OPENSSL_NO_DES
504 	{
505 		.name = "des",
506 		.desc = "Encrypt with DES",
507 		.type = OPTION_ARGV_FUNC,
508 		.opt.argvfunc = cms_opt_cipher,
509 	},
510 	{
511 		.name = "des3",
512 		.desc = "Encrypt with triple DES (default)",
513 		.type = OPTION_ARGV_FUNC,
514 		.opt.argvfunc = cms_opt_cipher,
515 	},
516 #endif
517 #ifndef OPENSSL_NO_RC2
518 	{
519 		.name = "rc2-40",
520 		.desc = "Encrypt with RC2-40",
521 		.type = OPTION_ARGV_FUNC,
522 		.opt.argvfunc = cms_opt_cipher,
523 	},
524 	{
525 		.name = "rc2-64",
526 		.desc = "Encrypt with RC2-64",
527 		.type = OPTION_ARGV_FUNC,
528 		.opt.argvfunc = cms_opt_cipher,
529 	},
530 	{
531 		.name = "rc2-128",
532 		.desc = "Encrypt with RC2-128",
533 		.type = OPTION_ARGV_FUNC,
534 		.opt.argvfunc = cms_opt_cipher,
535 	},
536 #endif
537 	{
538 		.name = "CAfile",
539 		.argname = "file",
540 		.desc = "Certificate Authority file",
541 		.type = OPTION_ARG,
542 		.opt.arg = &cfg.CAfile,
543 	},
544 	{
545 		.name = "CApath",
546 		.argname = "path",
547 		.desc = "Certificate Authority path",
548 		.type = OPTION_ARG,
549 		.opt.arg = &cfg.CApath,
550 	},
551 	{
552 		.name = "CRLfile",
553 		.argname = "file",
554 		.desc = "Other certificate revocation lists file",
555 		.type = OPTION_ARG,
556 		.opt.arg = &cfg.crlfile,
557 	},
558 	{
559 		.name = "binary",
560 		.desc = "Do not translate message to text",
561 		.type = OPTION_VALUE_OR,
562 		.opt.value = &cfg.flags,
563 		.value = CMS_BINARY,
564 	},
565 	{
566 		.name = "certfile",
567 		.argname = "file",
568 		.desc = "Other certificates file",
569 		.type = OPTION_ARG,
570 		.opt.arg = &cfg.certfile,
571 	},
572 	{
573 		.name = "certsout",
574 		.argname = "file",
575 		.desc = "Certificate output file",
576 		.type = OPTION_ARG,
577 		.opt.arg = &cfg.certsoutfile,
578 	},
579 	{
580 		.name = "cmsout",
581 		.desc = "Output CMS structure",
582 		.type = OPTION_VALUE,
583 		.opt.value = &cfg.operation,
584 		.value = SMIME_CMSOUT,
585 	},
586 	{
587 		.name = "compress",
588 		.desc = "Create CMS CompressedData type",
589 		.type = OPTION_VALUE,
590 		.opt.value = &cfg.operation,
591 		.value = SMIME_COMPRESS,
592 	},
593 	{
594 		.name = "content",
595 		.argname = "file",
596 		.desc = "Supply or override content for detached signature",
597 		.type = OPTION_ARG,
598 		.opt.arg = &cfg.contfile,
599 	},
600 	{
601 		.name = "crlfeol",
602 		.desc = "Use CRLF as EOL termination instead of CR only",
603 		.type = OPTION_VALUE_OR,
604 		.opt.value = &cfg.flags,
605 		.value = CMS_CRLFEOL,
606 	},
607 	{
608 		.name = "data_create",
609 		.desc = "Create CMS Data type",
610 		.type = OPTION_VALUE,
611 		.opt.value = &cfg.operation,
612 		.value = SMIME_DATA_CREATE,
613 	},
614 	{
615 		.name = "data_out",
616 		.desc = "Output content from the input CMS Data type",
617 		.type = OPTION_VALUE,
618 		.opt.value = &cfg.operation,
619 		.value = SMIME_DATAOUT,
620 	},
621 	{
622 		.name = "debug_decrypt",
623 		.desc = "Set the CMS_DEBUG_DECRYPT flag when decrypting",
624 		.type = OPTION_VALUE_OR,
625 		.opt.value = &cfg.flags,
626 		.value = CMS_DEBUG_DECRYPT,
627 	},
628 	{
629 		.name = "decrypt",
630 		.desc = "Decrypt encrypted message",
631 		.type = OPTION_VALUE,
632 		.opt.value = &cfg.operation,
633 		.value = SMIME_DECRYPT,
634 	},
635 	{
636 		.name = "digest_create",
637 		.desc = "Create CMS DigestedData type",
638 		.type = OPTION_VALUE,
639 		.opt.value = &cfg.operation,
640 		.value = SMIME_DIGEST_CREATE,
641 	},
642 	{
643 		.name = "digest_verify",
644 		.desc = "Verify CMS DigestedData type and output the content",
645 		.type = OPTION_VALUE,
646 		.opt.value = &cfg.operation,
647 		.value = SMIME_DIGEST_VERIFY,
648 	},
649 	{
650 		.name = "econtent_type",
651 		.argname = "type",
652 		.desc = "Set the encapsulated content type",
653 		.type = OPTION_ARG_FUNC,
654 		.opt.argfunc = cms_opt_econtent_type,
655 	},
656 	{
657 		.name = "encrypt",
658 		.desc = "Encrypt message",
659 		.type = OPTION_VALUE,
660 		.opt.value = &cfg.operation,
661 		.value = SMIME_ENCRYPT,
662 	},
663 	{
664 		.name = "EncryptedData_decrypt",
665 		.desc = "Decrypt CMS EncryptedData",
666 		.type = OPTION_VALUE,
667 		.opt.value = &cfg.operation,
668 		.value = SMIME_ENCRYPTED_DECRYPT,
669 	},
670 	{
671 		.name = "EncryptedData_encrypt",
672 		.desc = "Encrypt content using supplied symmetric key and algorithm",
673 		.type = OPTION_VALUE,
674 		.opt.value = &cfg.operation,
675 		.value = SMIME_ENCRYPTED_ENCRYPT,
676 	},
677 	{
678 		.name = "from",
679 		.argname = "addr",
680 		.desc = "From address",
681 		.type = OPTION_ARG,
682 		.opt.arg = &cfg.from,
683 	},
684 	{
685 		.name = "in",
686 		.argname = "file",
687 		.desc = "Input file",
688 		.type = OPTION_ARG,
689 		.opt.arg = &cfg.infile,
690 	},
691 	{
692 		.name = "indef",
693 		.desc = "Same as -stream",
694 		.type = OPTION_VALUE_OR,
695 		.opt.value = &cfg.flags,
696 		.value = CMS_STREAM,
697 	},
698 	{
699 		.name = "inform",
700 		.argname = "fmt",
701 		.desc = "Input format (DER, PEM or SMIME (default))",
702 		.type = OPTION_ARG_FORMAT,
703 		.opt.value = &cfg.informat,
704 	},
705 	{
706 		.name = "inkey",
707 		.argname = "file",
708 		.desc = "Input key file",
709 		.type = OPTION_ARG_FUNC,
710 		.opt.argfunc = cms_opt_inkey,
711 	},
712 	{
713 		.name = "keyform",
714 		.argname = "fmt",
715 		.desc = "Input key format (DER or PEM (default))",
716 		.type = OPTION_ARG_FORMAT,
717 		.opt.value = &cfg.keyform,
718 	},
719 	{
720 		.name = "keyid",
721 		.desc = "Use subject key identifier",
722 		.type = OPTION_VALUE_OR,
723 		.opt.value = &cfg.flags,
724 		.value = CMS_USE_KEYID,
725 	},
726 	{
727 		.name = "keyopt",
728 		.argname = "nm:v",
729 		.desc = "Set public key parameters",
730 		.type = OPTION_ARG_FUNC,
731 		.opt.argfunc = cms_opt_keyopt,
732 	},
733 	{
734 		.name = "md",
735 		.argname = "digest",
736 		.desc = "Digest to use when signing or resigning",
737 		.type = OPTION_ARG_FUNC,
738 		.opt.argfunc = cms_opt_md,
739 	},
740 	{
741 		.name = "no_attr_verify",
742 		.desc = "Do not verify the signer's attribute of a signature",
743 		.type = OPTION_VALUE_OR,
744 		.opt.value = &cfg.flags,
745 		.value = CMS_NO_ATTR_VERIFY,
746 	},
747 	{
748 		.name = "no_content_verify",
749 		.desc = "Do not verify the content of a signed message",
750 		.type = OPTION_VALUE_OR,
751 		.opt.value = &cfg.flags,
752 		.value = CMS_NO_CONTENT_VERIFY,
753 	},
754 	{
755 		.name = "no_signer_cert_verify",
756 		.desc = "Do not verify the signer's certificate",
757 		.type = OPTION_VALUE_OR,
758 		.opt.value = &cfg.flags,
759 		.value = CMS_NO_SIGNER_CERT_VERIFY,
760 	},
761 	{
762 		.name = "noattr",
763 		.desc = "Do not include any signed attributes",
764 		.type = OPTION_VALUE_OR,
765 		.opt.value = &cfg.flags,
766 		.value = CMS_NOATTR,
767 	},
768 	{
769 		.name = "nocerts",
770 		.desc = "Do not include signer's certificate when signing",
771 		.type = OPTION_VALUE_OR,
772 		.opt.value = &cfg.flags,
773 		.value = CMS_NOCERTS,
774 	},
775 	{
776 		.name = "nodetach",
777 		.desc = "Use opaque signing",
778 		.type = OPTION_VALUE_AND,
779 		.opt.value = &cfg.flags,
780 		.value = ~CMS_DETACHED,
781 	},
782 	{
783 		.name = "noindef",
784 		.desc = "Disable CMS streaming",
785 		.type = OPTION_VALUE_AND,
786 		.opt.value = &cfg.flags,
787 		.value = ~CMS_STREAM,
788 	},
789 	{
790 		.name = "nointern",
791 		.desc = "Do not search certificates in message for signer",
792 		.type = OPTION_VALUE_OR,
793 		.opt.value = &cfg.flags,
794 		.value = CMS_NOINTERN,
795 	},
796 	{
797 		.name = "nooldmime",
798 		.desc = "Output old S/MIME content type",
799 		.type = OPTION_VALUE_OR,
800 		.opt.value = &cfg.flags,
801 		.value = CMS_NOOLDMIMETYPE,
802 	},
803 	{
804 		.name = "noout",
805 		.desc = "Do not output the parsed CMS structure",
806 		.type = OPTION_FLAG,
807 		.opt.flag = &cfg.noout,
808 	},
809 	{
810 		.name = "nosigs",
811 		.desc = "Do not verify message signature",
812 		.type = OPTION_VALUE_OR,
813 		.opt.value = &cfg.flags,
814 		.value = CMS_NOSIGS,
815 	},
816 	{
817 		.name = "nosmimecap",
818 		.desc = "Omit the SMIMECapabilities attribute",
819 		.type = OPTION_VALUE_OR,
820 		.opt.value = &cfg.flags,
821 		.value = CMS_NOSMIMECAP,
822 	},
823 	{
824 		.name = "noverify",
825 		.desc = "Do not verify signer's certificate",
826 		.type = OPTION_VALUE_OR,
827 		.opt.value = &cfg.flags,
828 		.value = CMS_NO_SIGNER_CERT_VERIFY,
829 	},
830 	{
831 		.name = "out",
832 		.argname = "file",
833 		.desc = "Output file",
834 		.type = OPTION_ARG,
835 		.opt.arg = &cfg.outfile,
836 	},
837 	{
838 		.name = "outform",
839 		.argname = "fmt",
840 		.desc = "Output format (DER, PEM or SMIME (default))",
841 		.type = OPTION_ARG_FORMAT,
842 		.opt.value = &cfg.outformat,
843 	},
844 	{
845 		.name = "passin",
846 		.argname = "src",
847 		.desc = "Private key password source",
848 		.type = OPTION_ARG,
849 		.opt.arg = &cfg.passargin,
850 	},
851 	{
852 		.name = "print",
853 		.desc = "Print out all fields of the CMS structure for the -cmsout",
854 		.type = OPTION_FUNC,
855 		.opt.func = cms_opt_print,
856 	},
857 	{
858 		.name = "pwri_password",
859 		.argname = "arg",
860 		.desc = "Specify PasswordRecipientInfo (PWRI) password to use",
861 		.type = OPTION_ARG_FUNC,
862 		.opt.argfunc = cms_opt_pwri_pass,
863 	},
864 	{
865 		.name = "rctform",
866 		.argname = "fmt",
867 		.desc = "Receipt file format (DER, PEM or SMIME (default))",
868 		.type = OPTION_ARG_FORMAT,
869 		.opt.value = &cfg.rctformat,
870 	},
871 	{
872 		.name = "receipt_request_all",
873 		.desc = "Indicate requests should be provided by all recipients",
874 		.type = OPTION_VALUE,
875 		.opt.value = &cfg.rr_allorfirst,
876 		.value = 0,
877 	},
878 	{
879 		.name = "receipt_request_first",
880 		.desc = "Indicate requests should be provided by first tier recipient",
881 		.type = OPTION_VALUE,
882 		.opt.value = &cfg.rr_allorfirst,
883 		.value = 1,
884 	},
885 	{
886 		.name = "receipt_request_from",
887 		.argname = "addr",
888 		.desc = "Add explicit email address where receipts should be supplied",
889 		.type = OPTION_ARG_FUNC,
890 		.opt.argfunc = cms_opt_receipt_request_from,
891 	},
892 	{
893 		.name = "receipt_request_print",
894 		.desc = "Print out the contents of any signed receipt requests",
895 		.type = OPTION_FLAG,
896 		.opt.flag = &cfg.rr_print,
897 	},
898 	{
899 		.name = "receipt_request_to",
900 		.argname = "addr",
901 		.desc = "Add explicit email address where receipts should be sent to",
902 		.type = OPTION_ARG_FUNC,
903 		.opt.argfunc = cms_opt_receipt_request_to,
904 	},
905 	{
906 		.name = "recip",
907 		.argname = "file",
908 		.desc = "Recipient certificate file for decryption",
909 		.type = OPTION_ARG_FUNC,
910 		.opt.argfunc = cms_opt_recip,
911 	},
912 	{
913 		.name = "resign",
914 		.desc = "Resign a signed message",
915 		.type = OPTION_VALUE,
916 		.opt.value = &cfg.operation,
917 		.value = SMIME_RESIGN,
918 	},
919 	{
920 		.name = "secretkey",
921 		.argname = "key",
922 		.desc = "Specify symmetric key to use",
923 		.type = OPTION_ARG_FUNC,
924 		.opt.argfunc = cms_opt_secretkey,
925 	},
926 	{
927 		.name = "secretkeyid",
928 		.argname = "id",
929 		.desc = "The key identifier for the supplied symmetric key",
930 		.type = OPTION_ARG_FUNC,
931 		.opt.argfunc = cms_opt_secretkeyid,
932 	},
933 	{
934 		.name = "sign",
935 		.desc = "Sign message",
936 		.type = OPTION_VALUE,
937 		.opt.value = &cfg.operation,
938 		.value = SMIME_SIGN,
939 	},
940 	{
941 		.name = "sign_receipt",
942 		.desc = "Generate a signed receipt for the message",
943 		.type = OPTION_VALUE,
944 		.opt.value = &cfg.operation,
945 		.value = SMIME_SIGN_RECEIPT,
946 	},
947 	{
948 		.name = "signer",
949 		.argname = "file",
950 		.desc = "Signer certificate file",
951 		.type = OPTION_ARG_FUNC,
952 		.opt.argfunc = cms_opt_signer,
953 	},
954 	{
955 		.name = "stream",
956 		.desc = "Enable CMS streaming",
957 		.type = OPTION_VALUE_OR,
958 		.opt.value = &cfg.flags,
959 		.value = CMS_STREAM,
960 	},
961 	{
962 		.name = "subject",
963 		.argname = "s",
964 		.desc = "Subject",
965 		.type = OPTION_ARG,
966 		.opt.arg = &cfg.subject,
967 	},
968 	{
969 		.name = "text",
970 		.desc = "Include or delete text MIME headers",
971 		.type = OPTION_VALUE_OR,
972 		.opt.value = &cfg.flags,
973 		.value = CMS_TEXT,
974 	},
975 	{
976 		.name = "to",
977 		.argname = "addr",
978 		.desc = "To address",
979 		.type = OPTION_ARG,
980 		.opt.arg = &cfg.to,
981 	},
982 	{
983 		.name = "uncompress",
984 		.desc = "Uncompress CMS CompressedData type",
985 		.type = OPTION_VALUE,
986 		.opt.value = &cfg.operation,
987 		.value = SMIME_UNCOMPRESS,
988 	},
989 	{
990 		.name = "verify",
991 		.desc = "Verify signed message",
992 		.type = OPTION_VALUE,
993 		.opt.value = &cfg.operation,
994 		.value = SMIME_VERIFY,
995 	},
996 	{
997 		.name = "verify_receipt",
998 		.argname = "file",
999 		.desc = "Verify a signed receipt in file",
1000 		.type = OPTION_ARG_FUNC,
1001 		.opt.argfunc = cms_opt_verify_receipt,
1002 	},
1003 	{
1004 		.name = "verify_retcode",
1005 		.desc = "Set verification error code to exit code",
1006 		.type = OPTION_FLAG,
1007 		.opt.flag = &cfg.verify_retcode,
1008 	},
1009 	{
1010 		.name = "check_ss_sig",
1011 		.type = OPTION_ARGV_FUNC,
1012 		.opt.argvfunc = cms_opt_verify_param,
1013 	},
1014 	{
1015 		.name = "crl_check",
1016 		.type = OPTION_ARGV_FUNC,
1017 		.opt.argvfunc = cms_opt_verify_param,
1018 	},
1019 	{
1020 		.name = "crl_check_all",
1021 		.type = OPTION_ARGV_FUNC,
1022 		.opt.argvfunc = cms_opt_verify_param,
1023 	},
1024 	{
1025 		.name = "extended_crl",
1026 		.type = OPTION_ARGV_FUNC,
1027 		.opt.argvfunc = cms_opt_verify_param,
1028 	},
1029 	{
1030 		.name = "ignore_critical",
1031 		.type = OPTION_ARGV_FUNC,
1032 		.opt.argvfunc = cms_opt_verify_param,
1033 	},
1034 	{
1035 		.name = "issuer_checks",
1036 		.type = OPTION_ARGV_FUNC,
1037 		.opt.argvfunc = cms_opt_verify_param,
1038 	},
1039 	{
1040 		.name = "policy",
1041 		.type = OPTION_ARGV_FUNC,
1042 		.opt.argvfunc = cms_opt_verify_param,
1043 	},
1044 	{
1045 		.name = "policy_check",
1046 		.type = OPTION_ARGV_FUNC,
1047 		.opt.argvfunc = cms_opt_verify_param,
1048 	},
1049 	{
1050 		.name = "purpose",
1051 		.type = OPTION_ARGV_FUNC,
1052 		.opt.argvfunc = cms_opt_verify_param,
1053 	},
1054 	{
1055 		.name = "x509_strict",
1056 		.type = OPTION_ARGV_FUNC,
1057 		.opt.argvfunc = cms_opt_verify_param,
1058 	},
1059 	{
1060 		.name = NULL,
1061 		.type = OPTION_ARGV_FUNC,
1062 		.opt.argvfunc = cms_opt_cipher,
1063 	},
1064 	{ NULL },
1065 };
1066 
1067 static const struct option verify_shared_options[] = {
1068 	{
1069 		.name = "check_ss_sig",
1070 		.desc = "Check the root CA self-signed certificate signature",
1071 	},
1072 	{
1073 		.name = "crl_check",
1074 		.desc = "Enable CRL checking for the leaf certificate",
1075 	},
1076 	{
1077 		.name = "crl_check_all",
1078 		.desc = "Enable CRL checking for the entire certificate chain",
1079 	},
1080 	{
1081 		.name = "extended_crl",
1082 		.desc = "Enable extended CRL support",
1083 	},
1084 	{
1085 		.name = "ignore_critical",
1086 		.desc = "Disable critical extension checking",
1087 	},
1088 	{
1089 		.name = "issuer_checks",
1090 		.desc = "Enable debugging of certificate issuer checks",
1091 	},
1092 	{
1093 		.name = "policy",
1094 		.argname = "name",
1095 		.desc = "Add given policy to the acceptable set",
1096 	},
1097 	{
1098 		.name = "policy_check",
1099 		.desc = "Enable certificate policy checking",
1100 	},
1101 	{
1102 		.name = "purpose",
1103 		.argname = "name",
1104 		.desc = "Verify for the given purpose",
1105 	},
1106 	{
1107 		.name = "x509_strict",
1108 		.desc = "Use strict X.509 rules (disables workarounds)",
1109 	},
1110 	{ NULL },
1111 };
1112 
1113 static void
cms_usage(void)1114 cms_usage(void)
1115 {
1116 	int i;
1117 
1118 	fprintf(stderr, "usage: cms "
1119 	    "[-aes128 | -aes192 | -aes256 | -camellia128 |\n"
1120 	    "    -camellia192 | -camellia256 | -des | -des3 |\n"
1121 	    "    -rc2-40 | -rc2-64 | -rc2-128] [-CAfile file]\n"
1122 	    "    [-CApath directory] [-CRLfile file] [-binary]\n"
1123 	    "    [-certfile file] [-certsout file] [-cmsout] [-compress]\n"
1124 	    "    [-content file] [-crlfeol] [-data_create] [-data_out]\n"
1125 	    "    [-debug_decrypt] [-decrypt] [-digest_create] [-digest_verify]\n"
1126 	    "    [-econtent_type type] [-encrypt] [-EncryptedData_decrypt]\n"
1127 	    "    [-EncryptedData_encrypt] [-from addr] [-in file]\n"
1128 	    "    [-inform der | pem | smime] [-inkey file]\n"
1129 	    "    [-keyform der | pem] [-keyid] [-keyopt nm:v] [-md digest]\n"
1130 	    "    [-no_attr_verify] [-no_content_verify]\n"
1131 	    "    [-no_signer_cert_verify] [-noattr] [-nocerts] [-nodetach]\n"
1132 	    "    [-nointern] [-nooldmime] [-noout] [-nosigs] [-nosmimecap]\n"
1133 	    "    [-noverify] [-out file] [-outform der | pem | smime]\n"
1134 	    "    [-passin src] [-print] [-pwri_password arg]\n"
1135 	    "    [-rctform der | pem | smime]\n"
1136 	    "    [-receipt_request_all | -receipt_request_first]\n"
1137 	    "    [-receipt_request_from addr] [-receipt_request_print]\n"
1138 	    "    [-receipt_request_to addr] [-recip file] [-resign]\n"
1139 	    "    [-secretkey key] [-secretkeyid id] [-sign] [-sign_receipt]\n"
1140 	    "    [-signer file] [-stream | -indef | -noindef] [-subject s]\n"
1141 	    "    [-text] [-to addr] [-uncompress] [-verify]\n"
1142 	    "    [-verify_receipt file] [-verify_retcode] [cert.pem ...]\n\n");
1143 
1144 	options_usage(cms_options);
1145 
1146 	fprintf(stderr, "\nVerification options:\n\n");
1147 	options_usage(verify_shared_options);
1148 
1149 	fprintf(stderr, "\nValid purposes:\n\n");
1150 	for (i = 0; i < X509_PURPOSE_get_count(); i++) {
1151 		const X509_PURPOSE *ptmp = X509_PURPOSE_get0(i);
1152 		fprintf(stderr, "  %-18s%s\n", X509_PURPOSE_get0_sname(ptmp),
1153 		    X509_PURPOSE_get0_name(ptmp));
1154 	}
1155 }
1156 
1157 int
cms_main(int argc,char ** argv)1158 cms_main(int argc, char **argv)
1159 {
1160 	int ret = 0;
1161 	char **args;
1162 	int argsused = 0;
1163 	const char *inmode = "r", *outmode = "w";
1164 	CMS_ContentInfo *cms = NULL, *rcms = NULL;
1165 	X509_STORE *store = NULL;
1166 	X509 *recip = NULL, *signer = NULL;
1167 	EVP_PKEY *key = NULL;
1168 	STACK_OF(X509) *other = NULL;
1169 	STACK_OF(X509_CRL) *crls = NULL;
1170 	BIO *in = NULL, *out = NULL, *indata = NULL, *rctin = NULL;
1171 	int badarg = 0;
1172 	CMS_ReceiptRequest *rr = NULL;
1173 	char *passin = NULL;
1174 	unsigned char *pwri_tmp = NULL;
1175 
1176 	if (pledge("stdio rpath wpath cpath tty", NULL) == -1) {
1177 		perror("pledge");
1178 		exit(1);
1179 	}
1180 
1181 	memset(&cfg, 0, sizeof(cfg));
1182 	cfg.flags = CMS_DETACHED;
1183 	cfg.rr_allorfirst = -1;
1184 	cfg.informat = FORMAT_SMIME;
1185 	cfg.outformat = FORMAT_SMIME;
1186 	cfg.rctformat = FORMAT_SMIME;
1187 	cfg.keyform = FORMAT_PEM;
1188 	if (options_parse(argc, argv, cms_options, NULL, &argsused) != 0) {
1189 		goto argerr;
1190 	}
1191 	args = argv + argsused;
1192 	ret = 1;
1193 
1194 	if (((cfg.rr_allorfirst != -1) || cfg.rr_from != NULL) &&
1195 	    cfg.rr_to == NULL) {
1196 		BIO_puts(bio_err, "No Signed Receipts Recipients\n");
1197 		goto argerr;
1198 	}
1199 	if (!(cfg.operation & SMIME_SIGNERS) &&
1200 	    (cfg.rr_to != NULL || cfg.rr_from != NULL)) {
1201 		BIO_puts(bio_err, "Signed receipts only allowed with -sign\n");
1202 		goto argerr;
1203 	}
1204 	if (!(cfg.operation & SMIME_SIGNERS) &&
1205 	    (cfg.skkeys != NULL || cfg.sksigners != NULL)) {
1206 		BIO_puts(bio_err, "Multiple signers or keys not allowed\n");
1207 		goto argerr;
1208 	}
1209 	if (cfg.operation & SMIME_SIGNERS) {
1210 		if (cfg.keyfile != NULL &&
1211 		    cfg.signerfile == NULL) {
1212 			BIO_puts(bio_err, "Illegal -inkey without -signer\n");
1213 			goto argerr;
1214 		}
1215 		/* Check to see if any final signer needs to be appended */
1216 		if (cfg.signerfile != NULL) {
1217 			if (cfg.sksigners == NULL &&
1218 			    (cfg.sksigners =
1219 			    sk_OPENSSL_STRING_new_null()) == NULL)
1220 				goto end;
1221 			if (!sk_OPENSSL_STRING_push(cfg.sksigners,
1222 			    cfg.signerfile))
1223 				goto end;
1224 			if (cfg.skkeys == NULL &&
1225 			    (cfg.skkeys =
1226 			    sk_OPENSSL_STRING_new_null()) == NULL)
1227 				goto end;
1228 			if (cfg.keyfile == NULL)
1229 				cfg.keyfile = cfg.signerfile;
1230 			if (!sk_OPENSSL_STRING_push(cfg.skkeys,
1231 			    cfg.keyfile))
1232 				goto end;
1233 		}
1234 		if (cfg.sksigners == NULL) {
1235 			BIO_printf(bio_err,
1236 			    "No signer certificate specified\n");
1237 			badarg = 1;
1238 		}
1239 		cfg.signerfile = NULL;
1240 		cfg.keyfile = NULL;
1241 	} else if (cfg.operation == SMIME_DECRYPT) {
1242 		if (cfg.recipfile == NULL &&
1243 		    cfg.keyfile == NULL &&
1244 		    cfg.secret_key == NULL &&
1245 		    cfg.pwri_pass == NULL) {
1246 			BIO_printf(bio_err,
1247 			    "No recipient certificate or key specified\n");
1248 			badarg = 1;
1249 		}
1250 	} else if (cfg.operation == SMIME_ENCRYPT) {
1251 		if (*args == NULL && cfg.secret_key == NULL &&
1252 		    cfg.pwri_pass == NULL &&
1253 		    cfg.encerts == NULL) {
1254 			BIO_printf(bio_err,
1255 			    "No recipient(s) certificate(s) specified\n");
1256 			badarg = 1;
1257 		}
1258 	} else if (!cfg.operation) {
1259 		badarg = 1;
1260 	}
1261 
1262 	if (badarg) {
1263  argerr:
1264 		cms_usage();
1265 		goto end;
1266 	}
1267 
1268 	if (!app_passwd(bio_err, cfg.passargin, NULL, &passin, NULL)) {
1269 		BIO_printf(bio_err, "Error getting password\n");
1270 		goto end;
1271 	}
1272 	ret = 2;
1273 
1274 	if (!(cfg.operation & SMIME_SIGNERS))
1275 		cfg.flags &= ~CMS_DETACHED;
1276 
1277 	if (cfg.operation & SMIME_OP) {
1278 		if (cfg.outformat == FORMAT_ASN1)
1279 			outmode = "wb";
1280 	} else {
1281 		if (cfg.flags & CMS_BINARY)
1282 			outmode = "wb";
1283 	}
1284 
1285 	if (cfg.operation & SMIME_IP) {
1286 		if (cfg.informat == FORMAT_ASN1)
1287 			inmode = "rb";
1288 	} else {
1289 		if (cfg.flags & CMS_BINARY)
1290 			inmode = "rb";
1291 	}
1292 
1293 	if (cfg.operation == SMIME_ENCRYPT) {
1294 		if (cfg.cipher == NULL) {
1295 #ifndef OPENSSL_NO_DES
1296 			cfg.cipher = EVP_des_ede3_cbc();
1297 #else
1298 			BIO_printf(bio_err, "No cipher selected\n");
1299 			goto end;
1300 #endif
1301 		}
1302 		if (cfg.secret_key != NULL &&
1303 		    cfg.secret_keyid == NULL) {
1304 			BIO_printf(bio_err, "No secret key id\n");
1305 			goto end;
1306 		}
1307 		if (*args != NULL && cfg.encerts == NULL)
1308 			if ((cfg.encerts = sk_X509_new_null()) == NULL)
1309 				goto end;
1310 		while (*args) {
1311 			if ((cfg.cert = load_cert(bio_err, *args,
1312 			    FORMAT_PEM, NULL,
1313 			    "recipient certificate file")) == NULL)
1314 				goto end;
1315 			if (!sk_X509_push(cfg.encerts, cfg.cert))
1316 				goto end;
1317 			cfg.cert = NULL;
1318 			args++;
1319 		}
1320 	}
1321 	if (cfg.certfile != NULL) {
1322 		if ((other = load_certs(bio_err, cfg.certfile,
1323 		    FORMAT_PEM, NULL, "certificate file")) == NULL) {
1324 			ERR_print_errors(bio_err);
1325 			goto end;
1326 		}
1327 	}
1328 
1329 	if (cfg.crlfile != NULL) {
1330 		crls = load_crls(bio_err, cfg.crlfile, FORMAT_PEM, NULL,
1331 		    "other CRLs");
1332 		if (crls == NULL)
1333 			goto end;
1334 	}
1335 
1336 	if (cfg.recipfile != NULL &&
1337 	    (cfg.operation == SMIME_DECRYPT)) {
1338 		if ((recip = load_cert(bio_err, cfg.recipfile,
1339 		    FORMAT_PEM, NULL, "recipient certificate file")) == NULL) {
1340 			ERR_print_errors(bio_err);
1341 			goto end;
1342 		}
1343 	}
1344 	if (cfg.operation == SMIME_SIGN_RECEIPT) {
1345 		if ((signer = load_cert(bio_err, cfg.signerfile,
1346 		    FORMAT_PEM, NULL,
1347 		    "receipt signer certificate file")) == NULL) {
1348 			ERR_print_errors(bio_err);
1349 			goto end;
1350 		}
1351 	}
1352 	if (cfg.operation == SMIME_DECRYPT) {
1353 		if (cfg.keyfile == NULL)
1354 			cfg.keyfile = cfg.recipfile;
1355 	} else if ((cfg.operation == SMIME_SIGN) ||
1356 	    (cfg.operation == SMIME_SIGN_RECEIPT)) {
1357 		if (cfg.keyfile == NULL)
1358 			cfg.keyfile = cfg.signerfile;
1359 	} else {
1360 		cfg.keyfile = NULL;
1361 	}
1362 
1363 	if (cfg.keyfile != NULL) {
1364 		key = load_key(bio_err, cfg.keyfile, cfg.keyform,
1365 		    0, passin, "signing key file");
1366 		if (key == NULL)
1367 			goto end;
1368 	}
1369 	if (cfg.infile != NULL) {
1370 		if ((in = BIO_new_file(cfg.infile, inmode)) == NULL) {
1371 			BIO_printf(bio_err,
1372 			    "Can't open input file %s\n", cfg.infile);
1373 			goto end;
1374 		}
1375 	} else {
1376 		if ((in = BIO_new_fp(stdin, BIO_NOCLOSE)) == NULL)
1377 			goto end;
1378 	}
1379 
1380 	if (cfg.operation & SMIME_IP) {
1381 		if (cfg.informat == FORMAT_SMIME)
1382 			cms = SMIME_read_CMS(in, &indata);
1383 		else if (cfg.informat == FORMAT_PEM)
1384 			cms = PEM_read_bio_CMS(in, NULL, NULL, NULL);
1385 		else if (cfg.informat == FORMAT_ASN1)
1386 			cms = d2i_CMS_bio(in, NULL);
1387 		else {
1388 			BIO_printf(bio_err, "Bad input format for CMS file\n");
1389 			goto end;
1390 		}
1391 
1392 		if (cms == NULL) {
1393 			BIO_printf(bio_err, "Error reading S/MIME message\n");
1394 			goto end;
1395 		}
1396 		if (cfg.contfile != NULL) {
1397 			BIO_free(indata);
1398 			if ((indata = BIO_new_file(cfg.contfile,
1399 			    "rb")) == NULL) {
1400 				BIO_printf(bio_err,
1401 				    "Can't read content file %s\n",
1402 				    cfg.contfile);
1403 				goto end;
1404 			}
1405 		}
1406 		if (cfg.certsoutfile != NULL) {
1407 			STACK_OF(X509) *allcerts;
1408 			if ((allcerts = CMS_get1_certs(cms)) == NULL)
1409 				goto end;
1410 			if (!save_certs(cfg.certsoutfile, allcerts)) {
1411 				BIO_printf(bio_err,
1412 				    "Error writing certs to %s\n",
1413 				    cfg.certsoutfile);
1414 				sk_X509_pop_free(allcerts, X509_free);
1415 				ret = 5;
1416 				goto end;
1417 			}
1418 			sk_X509_pop_free(allcerts, X509_free);
1419 		}
1420 	}
1421 	if (cfg.rctfile != NULL) {
1422 		char *rctmode = (cfg.rctformat == FORMAT_ASN1) ?
1423 		    "rb" : "r";
1424 		if ((rctin = BIO_new_file(cfg.rctfile, rctmode)) == NULL) {
1425 			BIO_printf(bio_err,
1426 			    "Can't open receipt file %s\n", cfg.rctfile);
1427 			goto end;
1428 		}
1429 		if (cfg.rctformat == FORMAT_SMIME)
1430 			rcms = SMIME_read_CMS(rctin, NULL);
1431 		else if (cfg.rctformat == FORMAT_PEM)
1432 			rcms = PEM_read_bio_CMS(rctin, NULL, NULL, NULL);
1433 		else if (cfg.rctformat == FORMAT_ASN1)
1434 			rcms = d2i_CMS_bio(rctin, NULL);
1435 		else {
1436 			BIO_printf(bio_err, "Bad input format for receipt\n");
1437 			goto end;
1438 		}
1439 
1440 		if (rcms == NULL) {
1441 			BIO_printf(bio_err, "Error reading receipt\n");
1442 			goto end;
1443 		}
1444 	}
1445 	if (cfg.outfile != NULL) {
1446 		if ((out = BIO_new_file(cfg.outfile, outmode)) == NULL) {
1447 			BIO_printf(bio_err,
1448 			    "Can't open output file %s\n", cfg.outfile);
1449 			goto end;
1450 		}
1451 	} else {
1452 		if ((out = BIO_new_fp(stdout, BIO_NOCLOSE)) == NULL)
1453 			goto end;
1454 	}
1455 
1456 	if ((cfg.operation == SMIME_VERIFY) ||
1457 	    (cfg.operation == SMIME_VERIFY_RECEIPT)) {
1458 		if ((store = setup_verify(bio_err, cfg.CAfile,
1459 		    cfg.CApath)) == NULL)
1460 			goto end;
1461 		if (cfg.vpm != NULL) {
1462 			if (!X509_STORE_set1_param(store, cfg.vpm))
1463 				goto end;
1464 		}
1465 	}
1466 	ret = 3;
1467 
1468 	if (cfg.operation == SMIME_DATA_CREATE) {
1469 		cms = CMS_data_create(in, cfg.flags);
1470 	} else if (cfg.operation == SMIME_DIGEST_CREATE) {
1471 		cms = CMS_digest_create(in, cfg.sign_md,
1472 		    cfg.flags);
1473 	} else if (cfg.operation == SMIME_COMPRESS) {
1474 		cms = CMS_compress(in, -1, cfg.flags);
1475 	} else if (cfg.operation == SMIME_ENCRYPT) {
1476 		int i;
1477 		cfg.flags |= CMS_PARTIAL;
1478 		cms = CMS_encrypt(NULL, in, cfg.cipher,
1479 		    cfg.flags);
1480 		if (cms == NULL)
1481 			goto end;
1482 		for (i = 0; i < sk_X509_num(cfg.encerts); i++) {
1483 			CMS_RecipientInfo *ri;
1484 			struct cms_key_param *kparam;
1485 			int tflags = cfg.flags;
1486 			X509 *x;
1487 
1488 			if ((x = sk_X509_value(cfg.encerts, i)) == NULL)
1489 				goto end;
1490 			for (kparam = cfg.key_first; kparam != NULL;
1491 			    kparam = kparam->next) {
1492 				if (kparam->idx == i) {
1493 					tflags |= CMS_KEY_PARAM;
1494 					break;
1495 				}
1496 			}
1497 			ri = CMS_add1_recipient_cert(cms, x, tflags);
1498 			if (ri == NULL)
1499 				goto end;
1500 			if (kparam != NULL) {
1501 				EVP_PKEY_CTX *pctx;
1502 				if ((pctx = CMS_RecipientInfo_get0_pkey_ctx(
1503 				    ri)) == NULL)
1504 					goto end;
1505 				if (!cms_set_pkey_param(pctx, kparam->param))
1506 					goto end;
1507 			}
1508 		}
1509 
1510 		if (cfg.secret_key != NULL) {
1511 			if (CMS_add0_recipient_key(cms, NID_undef,
1512 			    cfg.secret_key, cfg.secret_keylen,
1513 			    cfg.secret_keyid, cfg.secret_keyidlen,
1514 			    NULL, NULL, NULL) == NULL)
1515 				goto end;
1516 			/* NULL these because call absorbs them */
1517 			cfg.secret_key = NULL;
1518 			cfg.secret_keyid = NULL;
1519 		}
1520 		if (cfg.pwri_pass != NULL) {
1521 			pwri_tmp = strdup(cfg.pwri_pass);
1522 			if (pwri_tmp == NULL)
1523 				goto end;
1524 			if (CMS_add0_recipient_password(cms, -1, NID_undef,
1525 			    NID_undef, pwri_tmp, -1, NULL) == NULL)
1526 				goto end;
1527 			pwri_tmp = NULL;
1528 		}
1529 		if (!(cfg.flags & CMS_STREAM)) {
1530 			if (!CMS_final(cms, in, NULL, cfg.flags))
1531 				goto end;
1532 		}
1533 	} else if (cfg.operation == SMIME_ENCRYPTED_ENCRYPT) {
1534 		cms = CMS_EncryptedData_encrypt(in, cfg.cipher,
1535 		    cfg.secret_key, cfg.secret_keylen,
1536 		    cfg.flags);
1537 
1538 	} else if (cfg.operation == SMIME_SIGN_RECEIPT) {
1539 		CMS_ContentInfo *srcms = NULL;
1540 		STACK_OF(CMS_SignerInfo) *sis;
1541 		CMS_SignerInfo *si;
1542 		sis = CMS_get0_SignerInfos(cms);
1543 		if (sis == NULL)
1544 			goto end;
1545 		si = sk_CMS_SignerInfo_value(sis, 0);
1546 		if (si == NULL)
1547 			goto end;
1548 		srcms = CMS_sign_receipt(si, signer, key, other,
1549 		    cfg.flags);
1550 		if (srcms == NULL)
1551 			goto end;
1552 		CMS_ContentInfo_free(cms);
1553 		cms = srcms;
1554 	} else if (cfg.operation & SMIME_SIGNERS) {
1555 		int i;
1556 		/*
1557 		 * If detached data content we enable streaming if S/MIME
1558 		 * output format.
1559 		 */
1560 		if (cfg.operation == SMIME_SIGN) {
1561 
1562 			if (cfg.flags & CMS_DETACHED) {
1563 				if (cfg.outformat == FORMAT_SMIME)
1564 					cfg.flags |= CMS_STREAM;
1565 			}
1566 			cfg.flags |= CMS_PARTIAL;
1567 			cms = CMS_sign(NULL, NULL, other, in, cfg.flags);
1568 			if (cms == NULL)
1569 				goto end;
1570 			if (cfg.econtent_type != NULL)
1571 				if (!CMS_set1_eContentType(cms,
1572 				    cfg.econtent_type))
1573 					goto end;
1574 
1575 			if (cfg.rr_to != NULL) {
1576 				rr = make_receipt_request(cfg.rr_to,
1577 				    cfg.rr_allorfirst,
1578 				    cfg.rr_from);
1579 				if (rr == NULL) {
1580 					BIO_puts(bio_err,
1581 					    "Signed Receipt Request Creation Error\n");
1582 					goto end;
1583 				}
1584 			}
1585 		} else {
1586 			cfg.flags |= CMS_REUSE_DIGEST;
1587 		}
1588 
1589 		for (i = 0; i < sk_OPENSSL_STRING_num(cfg.sksigners); i++) {
1590 			CMS_SignerInfo *si;
1591 			struct cms_key_param *kparam;
1592 			int tflags = cfg.flags;
1593 
1594 			cfg.signerfile = sk_OPENSSL_STRING_value(
1595 			    cfg.sksigners, i);
1596 			cfg.keyfile = sk_OPENSSL_STRING_value(
1597 			    cfg.skkeys, i);
1598 
1599 			signer = load_cert(bio_err, cfg.signerfile,
1600 			    FORMAT_PEM, NULL, "signer certificate");
1601 			if (signer == NULL)
1602 				goto end;
1603 			key = load_key(bio_err, cfg.keyfile,
1604 			    cfg.keyform, 0, passin, "signing key file");
1605 			if (key == NULL)
1606 				goto end;
1607 			for (kparam = cfg.key_first; kparam != NULL;
1608 			    kparam = kparam->next) {
1609 				if (kparam->idx == i) {
1610 					tflags |= CMS_KEY_PARAM;
1611 					break;
1612 				}
1613 			}
1614 			si = CMS_add1_signer(cms, signer, key,
1615 			    cfg.sign_md, tflags);
1616 			if (si == NULL)
1617 				goto end;
1618 			if (kparam != NULL) {
1619 				EVP_PKEY_CTX *pctx;
1620 				if ((pctx = CMS_SignerInfo_get0_pkey_ctx(
1621 				    si)) == NULL)
1622 					goto end;
1623 				if (!cms_set_pkey_param(pctx, kparam->param))
1624 					goto end;
1625 			}
1626 			if (rr != NULL && !CMS_add1_ReceiptRequest(si, rr))
1627 				goto end;
1628 			X509_free(signer);
1629 			signer = NULL;
1630 			EVP_PKEY_free(key);
1631 			key = NULL;
1632 		}
1633 		/* If not streaming or resigning finalize structure */
1634 		if ((cfg.operation == SMIME_SIGN) &&
1635 		    !(cfg.flags & CMS_STREAM)) {
1636 			if (!CMS_final(cms, in, NULL, cfg.flags))
1637 				goto end;
1638 		}
1639 	}
1640 	if (cms == NULL) {
1641 		BIO_printf(bio_err, "Error creating CMS structure\n");
1642 		goto end;
1643 	}
1644 	ret = 4;
1645 	if (cfg.operation == SMIME_DECRYPT) {
1646 		if (cfg.flags & CMS_DEBUG_DECRYPT)
1647 			CMS_decrypt(cms, NULL, NULL, NULL, NULL,
1648 			    cfg.flags);
1649 
1650 		if (cfg.secret_key != NULL) {
1651 			if (!CMS_decrypt_set1_key(cms, cfg.secret_key,
1652 			    cfg.secret_keylen, cfg.secret_keyid,
1653 			    cfg.secret_keyidlen)) {
1654 				BIO_puts(bio_err,
1655 				    "Error decrypting CMS using secret key\n");
1656 				goto end;
1657 			}
1658 		}
1659 		if (key != NULL) {
1660 			if (!CMS_decrypt_set1_pkey(cms, key, recip)) {
1661 				BIO_puts(bio_err,
1662 				    "Error decrypting CMS using private key\n");
1663 				goto end;
1664 			}
1665 		}
1666 		if (cfg.pwri_pass != NULL) {
1667 			if (!CMS_decrypt_set1_password(cms,
1668 			    cfg.pwri_pass, -1)) {
1669 				BIO_puts(bio_err,
1670 				    "Error decrypting CMS using password\n");
1671 				goto end;
1672 			}
1673 		}
1674 		if (!CMS_decrypt(cms, NULL, NULL, indata, out,
1675 		    cfg.flags)) {
1676 			BIO_printf(bio_err, "Error decrypting CMS structure\n");
1677 			goto end;
1678 		}
1679 	} else if (cfg.operation == SMIME_DATAOUT) {
1680 		if (!CMS_data(cms, out, cfg.flags))
1681 			goto end;
1682 	} else if (cfg.operation == SMIME_UNCOMPRESS) {
1683 		if (!CMS_uncompress(cms, indata, out, cfg.flags))
1684 			goto end;
1685 	} else if (cfg.operation == SMIME_DIGEST_VERIFY) {
1686 		if (CMS_digest_verify(cms, indata, out, cfg.flags) > 0)
1687 			BIO_printf(bio_err, "Verification successful\n");
1688 		else {
1689 			BIO_printf(bio_err, "Verification failure\n");
1690 			goto end;
1691 		}
1692 	} else if (cfg.operation == SMIME_ENCRYPTED_DECRYPT) {
1693 		if (!CMS_EncryptedData_decrypt(cms, cfg.secret_key,
1694 		    cfg.secret_keylen, indata, out, cfg.flags))
1695 			goto end;
1696 	} else if (cfg.operation == SMIME_VERIFY) {
1697 		if (cfg.crlfile != NULL) {
1698 			int i;
1699 
1700 			for (i = 0; i < sk_X509_CRL_num(crls); i++) {
1701 				X509_CRL *crl = sk_X509_CRL_value(crls, i);
1702 				if (!CMS_add1_crl(cms, crl))
1703 					goto end;
1704 			}
1705 		}
1706 		if (CMS_verify(cms, other, store, indata, out,
1707 		    cfg.flags) > 0) {
1708 			BIO_printf(bio_err, "Verification successful\n");
1709 		} else {
1710 			BIO_printf(bio_err, "Verification failure\n");
1711 			if (cfg.verify_retcode)
1712 				ret = verify_err + 32;
1713 			goto end;
1714 		}
1715 		if (cfg.signerfile != NULL) {
1716 			STACK_OF(X509) *signers;
1717 			if ((signers = CMS_get0_signers(cms)) == NULL)
1718 				goto end;
1719 			if (!save_certs(cfg.signerfile, signers)) {
1720 				BIO_printf(bio_err,
1721 				    "Error writing signers to %s\n",
1722 				    cfg.signerfile);
1723 				sk_X509_free(signers);
1724 				ret = 5;
1725 				goto end;
1726 			}
1727 			sk_X509_free(signers);
1728 		}
1729 		if (cfg.rr_print)
1730 			receipt_request_print(bio_err, cms);
1731 
1732 	} else if (cfg.operation == SMIME_VERIFY_RECEIPT) {
1733 		if (CMS_verify_receipt(rcms, cms, other, store,
1734 		    cfg.flags) > 0) {
1735 			BIO_printf(bio_err, "Verification successful\n");
1736 		} else {
1737 			BIO_printf(bio_err, "Verification failure\n");
1738 			goto end;
1739 		}
1740 	} else {
1741 		if (cfg.noout) {
1742 			if (cfg.print &&
1743 			    !CMS_ContentInfo_print_ctx(out, cms, 0, NULL))
1744 				goto end;
1745 		} else if (cfg.outformat == FORMAT_SMIME) {
1746 			if (cfg.to != NULL)
1747 				BIO_printf(out, "To: %s\n", cfg.to);
1748 			if (cfg.from != NULL)
1749 				BIO_printf(out, "From: %s\n", cfg.from);
1750 			if (cfg.subject != NULL)
1751 				BIO_printf(out, "Subject: %s\n",
1752 				    cfg.subject);
1753 			if (cfg.operation == SMIME_RESIGN)
1754 				ret = SMIME_write_CMS(out, cms, indata,
1755 				    cfg.flags);
1756 			else
1757 				ret = SMIME_write_CMS(out, cms, in,
1758 				    cfg.flags);
1759 		} else if (cfg.outformat == FORMAT_PEM) {
1760 			ret = PEM_write_bio_CMS_stream(out, cms, in,
1761 			    cfg.flags);
1762 		} else if (cfg.outformat == FORMAT_ASN1) {
1763 			ret = i2d_CMS_bio_stream(out, cms, in, cfg.flags);
1764 		} else {
1765 			BIO_printf(bio_err, "Bad output format for CMS file\n");
1766 			goto end;
1767 		}
1768 		if (ret <= 0) {
1769 			ret = 6;
1770 			goto end;
1771 		}
1772 	}
1773 	ret = 0;
1774 
1775  end:
1776 	if (ret)
1777 		ERR_print_errors(bio_err);
1778 
1779 	sk_X509_pop_free(cfg.encerts, X509_free);
1780 	sk_X509_pop_free(other, X509_free);
1781 	sk_X509_CRL_pop_free(crls, X509_CRL_free);
1782 	X509_VERIFY_PARAM_free(cfg.vpm);
1783 	sk_OPENSSL_STRING_free(cfg.sksigners);
1784 	sk_OPENSSL_STRING_free(cfg.skkeys);
1785 	free(cfg.secret_key);
1786 	free(cfg.secret_keyid);
1787 	free(pwri_tmp);
1788 	ASN1_OBJECT_free(cfg.econtent_type);
1789 	CMS_ReceiptRequest_free(rr);
1790 	sk_OPENSSL_STRING_free(cfg.rr_to);
1791 	sk_OPENSSL_STRING_free(cfg.rr_from);
1792 	for (cfg.key_param = cfg.key_first; cfg.key_param;) {
1793 		struct cms_key_param *tparam;
1794 		sk_OPENSSL_STRING_free(cfg.key_param->param);
1795 		tparam = cfg.key_param->next;
1796 		free(cfg.key_param);
1797 		cfg.key_param = tparam;
1798 	}
1799 	X509_STORE_free(store);
1800 	X509_free(cfg.cert);
1801 	X509_free(recip);
1802 	X509_free(signer);
1803 	EVP_PKEY_free(key);
1804 	CMS_ContentInfo_free(cms);
1805 	CMS_ContentInfo_free(rcms);
1806 	BIO_free(rctin);
1807 	BIO_free(in);
1808 	BIO_free(indata);
1809 	BIO_free_all(out);
1810 	free(passin);
1811 
1812 	return (ret);
1813 }
1814 
1815 static int
save_certs(char * signerfile,STACK_OF (X509)* signers)1816 save_certs(char *signerfile, STACK_OF(X509) *signers)
1817 {
1818 	int i;
1819 	BIO *tmp;
1820 
1821 	if (signerfile == NULL)
1822 		return 1;
1823 	tmp = BIO_new_file(signerfile, "w");
1824 	if (tmp == NULL)
1825 		return 0;
1826 	for (i = 0; i < sk_X509_num(signers); i++)
1827 		PEM_write_bio_X509(tmp, sk_X509_value(signers, i));
1828 	BIO_free(tmp);
1829 	return 1;
1830 }
1831 
1832 static void
gnames_stack_print(BIO * out,STACK_OF (GENERAL_NAMES)* gns)1833 gnames_stack_print(BIO *out, STACK_OF(GENERAL_NAMES) *gns)
1834 {
1835 	STACK_OF(GENERAL_NAME) *gens;
1836 	GENERAL_NAME *gen;
1837 	int i, j;
1838 
1839 	for (i = 0; i < sk_GENERAL_NAMES_num(gns); i++) {
1840 		gens = sk_GENERAL_NAMES_value(gns, i);
1841 		for (j = 0; j < sk_GENERAL_NAME_num(gens); j++) {
1842 			gen = sk_GENERAL_NAME_value(gens, j);
1843 			BIO_puts(out, "    ");
1844 			GENERAL_NAME_print(out, gen);
1845 			BIO_puts(out, "\n");
1846 		}
1847 	}
1848 	return;
1849 }
1850 
1851 static void
receipt_request_print(BIO * out,CMS_ContentInfo * cms)1852 receipt_request_print(BIO *out, CMS_ContentInfo *cms)
1853 {
1854 	STACK_OF(CMS_SignerInfo) *sis;
1855 	CMS_SignerInfo *si;
1856 	CMS_ReceiptRequest *rr;
1857 	int allorfirst;
1858 	STACK_OF(GENERAL_NAMES) *rto, *rlist;
1859 	ASN1_STRING *scid;
1860 	int i, rv;
1861 
1862 	if ((sis = CMS_get0_SignerInfos(cms)) == NULL)
1863 		return;
1864 	for (i = 0; i < sk_CMS_SignerInfo_num(sis); i++) {
1865 		if ((si = sk_CMS_SignerInfo_value(sis, i)) == NULL)
1866 			return;
1867 		rv = CMS_get1_ReceiptRequest(si, &rr);
1868 		BIO_printf(bio_err, "Signer %d:\n", i + 1);
1869 		if (rv == 0) {
1870 			BIO_puts(bio_err, "  No Receipt Request\n");
1871 		} else if (rv < 0) {
1872 			BIO_puts(bio_err, "  Receipt Request Parse Error\n");
1873 			ERR_print_errors(bio_err);
1874 		} else {
1875 			char *id;
1876 			int idlen;
1877 
1878 			CMS_ReceiptRequest_get0_values(rr, &scid, &allorfirst,
1879 			    &rlist, &rto);
1880 			BIO_puts(out, "  Signed Content ID:\n");
1881 			idlen = ASN1_STRING_length(scid);
1882 			id = (char *) ASN1_STRING_data(scid);
1883 			BIO_dump_indent(out, id, idlen, 4);
1884 			BIO_puts(out, "  Receipts From");
1885 			if (rlist != NULL) {
1886 				BIO_puts(out, " List:\n");
1887 				gnames_stack_print(out, rlist);
1888 			} else if (allorfirst == 1) {
1889 				BIO_puts(out, ": First Tier\n");
1890 			} else if (allorfirst == 0) {
1891 				BIO_puts(out, ": All\n");
1892 			} else {
1893 				BIO_printf(out, " Unknown (%d)\n", allorfirst);
1894 			}
1895 			BIO_puts(out, "  Receipts To:\n");
1896 			gnames_stack_print(out, rto);
1897 		}
1898 		CMS_ReceiptRequest_free(rr);
1899 	}
1900 }
1901 
STACK_OF(GENERAL_NAMES)1902 static STACK_OF(GENERAL_NAMES) *
1903 make_names_stack(STACK_OF(OPENSSL_STRING) *ns)
1904 {
1905 	int i;
1906 	STACK_OF(GENERAL_NAMES) *ret;
1907 	GENERAL_NAMES *gens = NULL;
1908 	GENERAL_NAME *gen = NULL;
1909 
1910 	if ((ret = sk_GENERAL_NAMES_new_null()) == NULL)
1911 		goto err;
1912 	for (i = 0; i < sk_OPENSSL_STRING_num(ns); i++) {
1913 		char *str = sk_OPENSSL_STRING_value(ns, i);
1914 		gen = a2i_GENERAL_NAME(NULL, NULL, NULL, GEN_EMAIL, str, 0);
1915 		if (gen == NULL)
1916 			goto err;
1917 		gens = GENERAL_NAMES_new();
1918 		if (gens == NULL)
1919 			goto err;
1920 		if (!sk_GENERAL_NAME_push(gens, gen))
1921 			goto err;
1922 		gen = NULL;
1923 		if (!sk_GENERAL_NAMES_push(ret, gens))
1924 			goto err;
1925 		gens = NULL;
1926 	}
1927 
1928 	return ret;
1929 
1930  err:
1931 	sk_GENERAL_NAMES_pop_free(ret, GENERAL_NAMES_free);
1932 	GENERAL_NAMES_free(gens);
1933 	GENERAL_NAME_free(gen);
1934 
1935 	return NULL;
1936 }
1937 
1938 
1939 static CMS_ReceiptRequest *
make_receipt_request(STACK_OF (OPENSSL_STRING)* rr_to,int rr_allorfirst,STACK_OF (OPENSSL_STRING)* rr_from)1940 make_receipt_request(STACK_OF(OPENSSL_STRING) *rr_to, int rr_allorfirst,
1941     STACK_OF(OPENSSL_STRING) *rr_from)
1942 {
1943 	STACK_OF(GENERAL_NAMES) *rct_to = NULL, *rct_from = NULL;
1944 	CMS_ReceiptRequest *rr;
1945 
1946 	rct_to = make_names_stack(rr_to);
1947 	if (rct_to == NULL)
1948 		goto err;
1949 	if (rr_from != NULL) {
1950 		rct_from = make_names_stack(rr_from);
1951 		if (rct_from == NULL)
1952 			goto err;
1953 	} else {
1954 		rct_from = NULL;
1955 	}
1956 
1957 	if ((rr = CMS_ReceiptRequest_create0(NULL, -1, rr_allorfirst, rct_from,
1958 	    rct_to)) == NULL)
1959 		goto err;
1960 
1961 	return rr;
1962 
1963  err:
1964 	sk_GENERAL_NAMES_pop_free(rct_to, GENERAL_NAMES_free);
1965 	sk_GENERAL_NAMES_pop_free(rct_from, GENERAL_NAMES_free);
1966 	return NULL;
1967 }
1968 
1969 static int
cms_set_pkey_param(EVP_PKEY_CTX * pctx,STACK_OF (OPENSSL_STRING)* param)1970 cms_set_pkey_param(EVP_PKEY_CTX *pctx, STACK_OF(OPENSSL_STRING) *param)
1971 {
1972 	char *keyopt;
1973 	int i;
1974 
1975 	if (sk_OPENSSL_STRING_num(param) <= 0)
1976 		return 1;
1977 	for (i = 0; i < sk_OPENSSL_STRING_num(param); i++) {
1978 		keyopt = sk_OPENSSL_STRING_value(param, i);
1979 		if (pkey_ctrl_string(pctx, keyopt) <= 0) {
1980 			BIO_printf(bio_err, "parameter error \"%s\"\n", keyopt);
1981 			ERR_print_errors(bio_err);
1982 			return 0;
1983 		}
1984 	}
1985 	return 1;
1986 }
1987 
1988 #endif
1989