1 /* $OpenBSD: pk7_asn1.c,v 1.13 2022/01/14 08:16:13 tb Exp $ */ 2 /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL 3 * project 2000. 4 */ 5 /* ==================================================================== 6 * Copyright (c) 2000 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 * This product includes cryptographic software written by Eric Young 54 * (eay@cryptsoft.com). This product includes software written by Tim 55 * Hudson (tjh@cryptsoft.com). 56 * 57 */ 58 59 #include <stdio.h> 60 61 #include <openssl/asn1t.h> 62 #include <openssl/pkcs7.h> 63 #include <openssl/x509.h> 64 65 /* PKCS#7 ASN1 module */ 66 67 /* This is the ANY DEFINED BY table for the top level PKCS#7 structure */ 68 69 static const ASN1_TEMPLATE p7default_tt = { 70 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL, 71 .tag = 0, 72 .offset = offsetof(PKCS7, d.other), 73 .field_name = "d.other", 74 .item = &ASN1_ANY_it, 75 }; 76 77 static const ASN1_ADB_TABLE PKCS7_adbtbl[] = { 78 { 79 .value = NID_pkcs7_data, 80 .tt = { 81 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL | ASN1_TFLG_NDEF, 82 .tag = 0, 83 .offset = offsetof(PKCS7, d.data), 84 .field_name = "d.data", 85 .item = &ASN1_OCTET_STRING_NDEF_it, 86 }, 87 88 }, 89 { 90 .value = NID_pkcs7_signed, 91 .tt = { 92 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL | ASN1_TFLG_NDEF, 93 .tag = 0, 94 .offset = offsetof(PKCS7, d.sign), 95 .field_name = "d.sign", 96 .item = &PKCS7_SIGNED_it, 97 }, 98 99 }, 100 { 101 .value = NID_pkcs7_enveloped, 102 .tt = { 103 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL | ASN1_TFLG_NDEF, 104 .tag = 0, 105 .offset = offsetof(PKCS7, d.enveloped), 106 .field_name = "d.enveloped", 107 .item = &PKCS7_ENVELOPE_it, 108 }, 109 110 }, 111 { 112 .value = NID_pkcs7_signedAndEnveloped, 113 .tt = { 114 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL | ASN1_TFLG_NDEF, 115 .tag = 0, 116 .offset = offsetof(PKCS7, d.signed_and_enveloped), 117 .field_name = "d.signed_and_enveloped", 118 .item = &PKCS7_SIGN_ENVELOPE_it, 119 }, 120 121 }, 122 { 123 .value = NID_pkcs7_digest, 124 .tt = { 125 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL | ASN1_TFLG_NDEF, 126 .tag = 0, 127 .offset = offsetof(PKCS7, d.digest), 128 .field_name = "d.digest", 129 .item = &PKCS7_DIGEST_it, 130 }, 131 132 }, 133 { 134 .value = NID_pkcs7_encrypted, 135 .tt = { 136 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_OPTIONAL | ASN1_TFLG_NDEF, 137 .tag = 0, 138 .offset = offsetof(PKCS7, d.encrypted), 139 .field_name = "d.encrypted", 140 .item = &PKCS7_ENCRYPT_it, 141 }, 142 143 }, 144 }; 145 146 static const ASN1_ADB PKCS7_adb = { 147 .flags = 0, 148 .offset = offsetof(PKCS7, type), 149 .tbl = PKCS7_adbtbl, 150 .tblcount = sizeof(PKCS7_adbtbl) / sizeof(ASN1_ADB_TABLE), 151 .default_tt = &p7default_tt, 152 .null_tt = NULL, 153 }; 154 155 /* PKCS#7 streaming support */ 156 static int 157 pk7_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it, void *exarg) 158 { 159 ASN1_STREAM_ARG *sarg = exarg; 160 PKCS7 **pp7 = (PKCS7 **)pval; 161 162 switch (operation) { 163 case ASN1_OP_STREAM_PRE: 164 if (PKCS7_stream(&sarg->boundary, *pp7) <= 0) 165 return 0; 166 167 case ASN1_OP_DETACHED_PRE: 168 sarg->ndef_bio = PKCS7_dataInit(*pp7, sarg->out); 169 if (!sarg->ndef_bio) 170 return 0; 171 break; 172 173 case ASN1_OP_STREAM_POST: 174 case ASN1_OP_DETACHED_POST: 175 if (PKCS7_dataFinal(*pp7, sarg->ndef_bio) <= 0) 176 return 0; 177 break; 178 } 179 return 1; 180 } 181 182 static const ASN1_AUX PKCS7_aux = { 183 .app_data = NULL, 184 .flags = 0, 185 .ref_offset = 0, 186 .ref_lock = 0, 187 .asn1_cb = pk7_cb, 188 .enc_offset = 0, 189 }; 190 static const ASN1_TEMPLATE PKCS7_seq_tt[] = { 191 { 192 .flags = 0, 193 .tag = 0, 194 .offset = offsetof(PKCS7, type), 195 .field_name = "type", 196 .item = &ASN1_OBJECT_it, 197 }, 198 { 199 .flags = ASN1_TFLG_ADB_OID, 200 .tag = -1, 201 .offset = 0, 202 .field_name = "PKCS7", 203 .item = (const ASN1_ITEM *)&PKCS7_adb, 204 }, 205 }; 206 207 const ASN1_ITEM PKCS7_it = { 208 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 209 .utype = V_ASN1_SEQUENCE, 210 .templates = PKCS7_seq_tt, 211 .tcount = sizeof(PKCS7_seq_tt) / sizeof(ASN1_TEMPLATE), 212 .funcs = &PKCS7_aux, 213 .size = sizeof(PKCS7), 214 .sname = "PKCS7", 215 }; 216 217 218 PKCS7 * 219 d2i_PKCS7(PKCS7 **a, const unsigned char **in, long len) 220 { 221 return (PKCS7 *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 222 &PKCS7_it); 223 } 224 225 int 226 i2d_PKCS7(PKCS7 *a, unsigned char **out) 227 { 228 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_it); 229 } 230 231 PKCS7 * 232 PKCS7_new(void) 233 { 234 return (PKCS7 *)ASN1_item_new(&PKCS7_it); 235 } 236 237 void 238 PKCS7_free(PKCS7 *a) 239 { 240 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_it); 241 } 242 243 int 244 i2d_PKCS7_NDEF(PKCS7 *a, unsigned char **out) 245 { 246 return ASN1_item_ndef_i2d((ASN1_VALUE *)a, out, &PKCS7_it); 247 } 248 249 PKCS7 * 250 PKCS7_dup(PKCS7 *x) 251 { 252 return ASN1_item_dup(&PKCS7_it, x); 253 } 254 255 static const ASN1_TEMPLATE PKCS7_SIGNED_seq_tt[] = { 256 { 257 .flags = 0, 258 .tag = 0, 259 .offset = offsetof(PKCS7_SIGNED, version), 260 .field_name = "version", 261 .item = &ASN1_INTEGER_it, 262 }, 263 { 264 .flags = ASN1_TFLG_SET_OF, 265 .tag = 0, 266 .offset = offsetof(PKCS7_SIGNED, md_algs), 267 .field_name = "md_algs", 268 .item = &X509_ALGOR_it, 269 }, 270 { 271 .flags = 0, 272 .tag = 0, 273 .offset = offsetof(PKCS7_SIGNED, contents), 274 .field_name = "contents", 275 .item = &PKCS7_it, 276 }, 277 { 278 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_SEQUENCE_OF | ASN1_TFLG_OPTIONAL, 279 .tag = 0, 280 .offset = offsetof(PKCS7_SIGNED, cert), 281 .field_name = "cert", 282 .item = &X509_it, 283 }, 284 { 285 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_SET_OF | ASN1_TFLG_OPTIONAL, 286 .tag = 1, 287 .offset = offsetof(PKCS7_SIGNED, crl), 288 .field_name = "crl", 289 .item = &X509_CRL_it, 290 }, 291 { 292 .flags = ASN1_TFLG_SET_OF, 293 .tag = 0, 294 .offset = offsetof(PKCS7_SIGNED, signer_info), 295 .field_name = "signer_info", 296 .item = &PKCS7_SIGNER_INFO_it, 297 }, 298 }; 299 300 const ASN1_ITEM PKCS7_SIGNED_it = { 301 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 302 .utype = V_ASN1_SEQUENCE, 303 .templates = PKCS7_SIGNED_seq_tt, 304 .tcount = sizeof(PKCS7_SIGNED_seq_tt) / sizeof(ASN1_TEMPLATE), 305 .funcs = NULL, 306 .size = sizeof(PKCS7_SIGNED), 307 .sname = "PKCS7_SIGNED", 308 }; 309 310 311 PKCS7_SIGNED * 312 d2i_PKCS7_SIGNED(PKCS7_SIGNED **a, const unsigned char **in, long len) 313 { 314 return (PKCS7_SIGNED *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 315 &PKCS7_SIGNED_it); 316 } 317 318 int 319 i2d_PKCS7_SIGNED(PKCS7_SIGNED *a, unsigned char **out) 320 { 321 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_SIGNED_it); 322 } 323 324 PKCS7_SIGNED * 325 PKCS7_SIGNED_new(void) 326 { 327 return (PKCS7_SIGNED *)ASN1_item_new(&PKCS7_SIGNED_it); 328 } 329 330 void 331 PKCS7_SIGNED_free(PKCS7_SIGNED *a) 332 { 333 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_SIGNED_it); 334 } 335 336 /* Minor tweak to operation: free up EVP_PKEY */ 337 static int 338 si_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it, void *exarg) 339 { 340 if (operation == ASN1_OP_FREE_POST) { 341 PKCS7_SIGNER_INFO *si = (PKCS7_SIGNER_INFO *)*pval; 342 EVP_PKEY_free(si->pkey); 343 } 344 return 1; 345 } 346 347 static const ASN1_AUX PKCS7_SIGNER_INFO_aux = { 348 .app_data = NULL, 349 .flags = 0, 350 .ref_offset = 0, 351 .ref_lock = 0, 352 .asn1_cb = si_cb, 353 .enc_offset = 0, 354 }; 355 static const ASN1_TEMPLATE PKCS7_SIGNER_INFO_seq_tt[] = { 356 { 357 .flags = 0, 358 .tag = 0, 359 .offset = offsetof(PKCS7_SIGNER_INFO, version), 360 .field_name = "version", 361 .item = &ASN1_INTEGER_it, 362 }, 363 { 364 .flags = 0, 365 .tag = 0, 366 .offset = offsetof(PKCS7_SIGNER_INFO, issuer_and_serial), 367 .field_name = "issuer_and_serial", 368 .item = &PKCS7_ISSUER_AND_SERIAL_it, 369 }, 370 { 371 .flags = 0, 372 .tag = 0, 373 .offset = offsetof(PKCS7_SIGNER_INFO, digest_alg), 374 .field_name = "digest_alg", 375 .item = &X509_ALGOR_it, 376 }, 377 /* NB this should be a SET OF but we use a SEQUENCE OF so the 378 * original order * is retained when the structure is reencoded. 379 * Since the attributes are implicitly tagged this will not affect 380 * the encoding. 381 */ 382 { 383 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_SEQUENCE_OF | ASN1_TFLG_OPTIONAL, 384 .tag = 0, 385 .offset = offsetof(PKCS7_SIGNER_INFO, auth_attr), 386 .field_name = "auth_attr", 387 .item = &X509_ATTRIBUTE_it, 388 }, 389 { 390 .flags = 0, 391 .tag = 0, 392 .offset = offsetof(PKCS7_SIGNER_INFO, digest_enc_alg), 393 .field_name = "digest_enc_alg", 394 .item = &X509_ALGOR_it, 395 }, 396 { 397 .flags = 0, 398 .tag = 0, 399 .offset = offsetof(PKCS7_SIGNER_INFO, enc_digest), 400 .field_name = "enc_digest", 401 .item = &ASN1_OCTET_STRING_it, 402 }, 403 { 404 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_SET_OF | ASN1_TFLG_OPTIONAL, 405 .tag = 1, 406 .offset = offsetof(PKCS7_SIGNER_INFO, unauth_attr), 407 .field_name = "unauth_attr", 408 .item = &X509_ATTRIBUTE_it, 409 }, 410 }; 411 412 const ASN1_ITEM PKCS7_SIGNER_INFO_it = { 413 .itype = ASN1_ITYPE_SEQUENCE, 414 .utype = V_ASN1_SEQUENCE, 415 .templates = PKCS7_SIGNER_INFO_seq_tt, 416 .tcount = sizeof(PKCS7_SIGNER_INFO_seq_tt) / sizeof(ASN1_TEMPLATE), 417 .funcs = &PKCS7_SIGNER_INFO_aux, 418 .size = sizeof(PKCS7_SIGNER_INFO), 419 .sname = "PKCS7_SIGNER_INFO", 420 }; 421 422 423 PKCS7_SIGNER_INFO * 424 d2i_PKCS7_SIGNER_INFO(PKCS7_SIGNER_INFO **a, const unsigned char **in, long len) 425 { 426 return (PKCS7_SIGNER_INFO *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 427 &PKCS7_SIGNER_INFO_it); 428 } 429 430 int 431 i2d_PKCS7_SIGNER_INFO(PKCS7_SIGNER_INFO *a, unsigned char **out) 432 { 433 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_SIGNER_INFO_it); 434 } 435 436 PKCS7_SIGNER_INFO * 437 PKCS7_SIGNER_INFO_new(void) 438 { 439 return (PKCS7_SIGNER_INFO *)ASN1_item_new(&PKCS7_SIGNER_INFO_it); 440 } 441 442 void 443 PKCS7_SIGNER_INFO_free(PKCS7_SIGNER_INFO *a) 444 { 445 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_SIGNER_INFO_it); 446 } 447 448 static const ASN1_TEMPLATE PKCS7_ISSUER_AND_SERIAL_seq_tt[] = { 449 { 450 .flags = 0, 451 .tag = 0, 452 .offset = offsetof(PKCS7_ISSUER_AND_SERIAL, issuer), 453 .field_name = "issuer", 454 .item = &X509_NAME_it, 455 }, 456 { 457 .flags = 0, 458 .tag = 0, 459 .offset = offsetof(PKCS7_ISSUER_AND_SERIAL, serial), 460 .field_name = "serial", 461 .item = &ASN1_INTEGER_it, 462 }, 463 }; 464 465 const ASN1_ITEM PKCS7_ISSUER_AND_SERIAL_it = { 466 .itype = ASN1_ITYPE_SEQUENCE, 467 .utype = V_ASN1_SEQUENCE, 468 .templates = PKCS7_ISSUER_AND_SERIAL_seq_tt, 469 .tcount = sizeof(PKCS7_ISSUER_AND_SERIAL_seq_tt) / sizeof(ASN1_TEMPLATE), 470 .funcs = NULL, 471 .size = sizeof(PKCS7_ISSUER_AND_SERIAL), 472 .sname = "PKCS7_ISSUER_AND_SERIAL", 473 }; 474 475 476 PKCS7_ISSUER_AND_SERIAL * 477 d2i_PKCS7_ISSUER_AND_SERIAL(PKCS7_ISSUER_AND_SERIAL **a, const unsigned char **in, long len) 478 { 479 return (PKCS7_ISSUER_AND_SERIAL *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 480 &PKCS7_ISSUER_AND_SERIAL_it); 481 } 482 483 int 484 i2d_PKCS7_ISSUER_AND_SERIAL(PKCS7_ISSUER_AND_SERIAL *a, unsigned char **out) 485 { 486 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_ISSUER_AND_SERIAL_it); 487 } 488 489 PKCS7_ISSUER_AND_SERIAL * 490 PKCS7_ISSUER_AND_SERIAL_new(void) 491 { 492 return (PKCS7_ISSUER_AND_SERIAL *)ASN1_item_new(&PKCS7_ISSUER_AND_SERIAL_it); 493 } 494 495 void 496 PKCS7_ISSUER_AND_SERIAL_free(PKCS7_ISSUER_AND_SERIAL *a) 497 { 498 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_ISSUER_AND_SERIAL_it); 499 } 500 501 static const ASN1_TEMPLATE PKCS7_ENVELOPE_seq_tt[] = { 502 { 503 .flags = 0, 504 .tag = 0, 505 .offset = offsetof(PKCS7_ENVELOPE, version), 506 .field_name = "version", 507 .item = &ASN1_INTEGER_it, 508 }, 509 { 510 .flags = ASN1_TFLG_SET_OF, 511 .tag = 0, 512 .offset = offsetof(PKCS7_ENVELOPE, recipientinfo), 513 .field_name = "recipientinfo", 514 .item = &PKCS7_RECIP_INFO_it, 515 }, 516 { 517 .flags = 0, 518 .tag = 0, 519 .offset = offsetof(PKCS7_ENVELOPE, enc_data), 520 .field_name = "enc_data", 521 .item = &PKCS7_ENC_CONTENT_it, 522 }, 523 }; 524 525 const ASN1_ITEM PKCS7_ENVELOPE_it = { 526 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 527 .utype = V_ASN1_SEQUENCE, 528 .templates = PKCS7_ENVELOPE_seq_tt, 529 .tcount = sizeof(PKCS7_ENVELOPE_seq_tt) / sizeof(ASN1_TEMPLATE), 530 .funcs = NULL, 531 .size = sizeof(PKCS7_ENVELOPE), 532 .sname = "PKCS7_ENVELOPE", 533 }; 534 535 536 PKCS7_ENVELOPE * 537 d2i_PKCS7_ENVELOPE(PKCS7_ENVELOPE **a, const unsigned char **in, long len) 538 { 539 return (PKCS7_ENVELOPE *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 540 &PKCS7_ENVELOPE_it); 541 } 542 543 int 544 i2d_PKCS7_ENVELOPE(PKCS7_ENVELOPE *a, unsigned char **out) 545 { 546 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_ENVELOPE_it); 547 } 548 549 PKCS7_ENVELOPE * 550 PKCS7_ENVELOPE_new(void) 551 { 552 return (PKCS7_ENVELOPE *)ASN1_item_new(&PKCS7_ENVELOPE_it); 553 } 554 555 void 556 PKCS7_ENVELOPE_free(PKCS7_ENVELOPE *a) 557 { 558 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_ENVELOPE_it); 559 } 560 561 /* Minor tweak to operation: free up X509 */ 562 static int 563 ri_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it, void *exarg) 564 { 565 if (operation == ASN1_OP_FREE_POST) { 566 PKCS7_RECIP_INFO *ri = (PKCS7_RECIP_INFO *)*pval; 567 X509_free(ri->cert); 568 } 569 return 1; 570 } 571 572 static const ASN1_AUX PKCS7_RECIP_INFO_aux = { 573 .app_data = NULL, 574 .flags = 0, 575 .ref_offset = 0, 576 .ref_lock = 0, 577 .asn1_cb = ri_cb, 578 .enc_offset = 0, 579 }; 580 static const ASN1_TEMPLATE PKCS7_RECIP_INFO_seq_tt[] = { 581 { 582 .flags = 0, 583 .tag = 0, 584 .offset = offsetof(PKCS7_RECIP_INFO, version), 585 .field_name = "version", 586 .item = &ASN1_INTEGER_it, 587 }, 588 { 589 .flags = 0, 590 .tag = 0, 591 .offset = offsetof(PKCS7_RECIP_INFO, issuer_and_serial), 592 .field_name = "issuer_and_serial", 593 .item = &PKCS7_ISSUER_AND_SERIAL_it, 594 }, 595 { 596 .flags = 0, 597 .tag = 0, 598 .offset = offsetof(PKCS7_RECIP_INFO, key_enc_algor), 599 .field_name = "key_enc_algor", 600 .item = &X509_ALGOR_it, 601 }, 602 { 603 .flags = 0, 604 .tag = 0, 605 .offset = offsetof(PKCS7_RECIP_INFO, enc_key), 606 .field_name = "enc_key", 607 .item = &ASN1_OCTET_STRING_it, 608 }, 609 }; 610 611 const ASN1_ITEM PKCS7_RECIP_INFO_it = { 612 .itype = ASN1_ITYPE_SEQUENCE, 613 .utype = V_ASN1_SEQUENCE, 614 .templates = PKCS7_RECIP_INFO_seq_tt, 615 .tcount = sizeof(PKCS7_RECIP_INFO_seq_tt) / sizeof(ASN1_TEMPLATE), 616 .funcs = &PKCS7_RECIP_INFO_aux, 617 .size = sizeof(PKCS7_RECIP_INFO), 618 .sname = "PKCS7_RECIP_INFO", 619 }; 620 621 622 PKCS7_RECIP_INFO * 623 d2i_PKCS7_RECIP_INFO(PKCS7_RECIP_INFO **a, const unsigned char **in, long len) 624 { 625 return (PKCS7_RECIP_INFO *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 626 &PKCS7_RECIP_INFO_it); 627 } 628 629 int 630 i2d_PKCS7_RECIP_INFO(PKCS7_RECIP_INFO *a, unsigned char **out) 631 { 632 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_RECIP_INFO_it); 633 } 634 635 PKCS7_RECIP_INFO * 636 PKCS7_RECIP_INFO_new(void) 637 { 638 return (PKCS7_RECIP_INFO *)ASN1_item_new(&PKCS7_RECIP_INFO_it); 639 } 640 641 void 642 PKCS7_RECIP_INFO_free(PKCS7_RECIP_INFO *a) 643 { 644 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_RECIP_INFO_it); 645 } 646 647 static const ASN1_TEMPLATE PKCS7_ENC_CONTENT_seq_tt[] = { 648 { 649 .flags = 0, 650 .tag = 0, 651 .offset = offsetof(PKCS7_ENC_CONTENT, content_type), 652 .field_name = "content_type", 653 .item = &ASN1_OBJECT_it, 654 }, 655 { 656 .flags = 0, 657 .tag = 0, 658 .offset = offsetof(PKCS7_ENC_CONTENT, algorithm), 659 .field_name = "algorithm", 660 .item = &X509_ALGOR_it, 661 }, 662 { 663 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_OPTIONAL, 664 .tag = 0, 665 .offset = offsetof(PKCS7_ENC_CONTENT, enc_data), 666 .field_name = "enc_data", 667 .item = &ASN1_OCTET_STRING_NDEF_it, 668 }, 669 }; 670 671 const ASN1_ITEM PKCS7_ENC_CONTENT_it = { 672 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 673 .utype = V_ASN1_SEQUENCE, 674 .templates = PKCS7_ENC_CONTENT_seq_tt, 675 .tcount = sizeof(PKCS7_ENC_CONTENT_seq_tt) / sizeof(ASN1_TEMPLATE), 676 .funcs = NULL, 677 .size = sizeof(PKCS7_ENC_CONTENT), 678 .sname = "PKCS7_ENC_CONTENT", 679 }; 680 681 682 PKCS7_ENC_CONTENT * 683 d2i_PKCS7_ENC_CONTENT(PKCS7_ENC_CONTENT **a, const unsigned char **in, long len) 684 { 685 return (PKCS7_ENC_CONTENT *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 686 &PKCS7_ENC_CONTENT_it); 687 } 688 689 int 690 i2d_PKCS7_ENC_CONTENT(PKCS7_ENC_CONTENT *a, unsigned char **out) 691 { 692 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_ENC_CONTENT_it); 693 } 694 695 PKCS7_ENC_CONTENT * 696 PKCS7_ENC_CONTENT_new(void) 697 { 698 return (PKCS7_ENC_CONTENT *)ASN1_item_new(&PKCS7_ENC_CONTENT_it); 699 } 700 701 void 702 PKCS7_ENC_CONTENT_free(PKCS7_ENC_CONTENT *a) 703 { 704 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_ENC_CONTENT_it); 705 } 706 707 static const ASN1_TEMPLATE PKCS7_SIGN_ENVELOPE_seq_tt[] = { 708 { 709 .flags = 0, 710 .tag = 0, 711 .offset = offsetof(PKCS7_SIGN_ENVELOPE, version), 712 .field_name = "version", 713 .item = &ASN1_INTEGER_it, 714 }, 715 { 716 .flags = ASN1_TFLG_SET_OF, 717 .tag = 0, 718 .offset = offsetof(PKCS7_SIGN_ENVELOPE, recipientinfo), 719 .field_name = "recipientinfo", 720 .item = &PKCS7_RECIP_INFO_it, 721 }, 722 { 723 .flags = ASN1_TFLG_SET_OF, 724 .tag = 0, 725 .offset = offsetof(PKCS7_SIGN_ENVELOPE, md_algs), 726 .field_name = "md_algs", 727 .item = &X509_ALGOR_it, 728 }, 729 { 730 .flags = 0, 731 .tag = 0, 732 .offset = offsetof(PKCS7_SIGN_ENVELOPE, enc_data), 733 .field_name = "enc_data", 734 .item = &PKCS7_ENC_CONTENT_it, 735 }, 736 { 737 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_SET_OF | ASN1_TFLG_OPTIONAL, 738 .tag = 0, 739 .offset = offsetof(PKCS7_SIGN_ENVELOPE, cert), 740 .field_name = "cert", 741 .item = &X509_it, 742 }, 743 { 744 .flags = ASN1_TFLG_IMPLICIT | ASN1_TFLG_SET_OF | ASN1_TFLG_OPTIONAL, 745 .tag = 1, 746 .offset = offsetof(PKCS7_SIGN_ENVELOPE, crl), 747 .field_name = "crl", 748 .item = &X509_CRL_it, 749 }, 750 { 751 .flags = ASN1_TFLG_SET_OF, 752 .tag = 0, 753 .offset = offsetof(PKCS7_SIGN_ENVELOPE, signer_info), 754 .field_name = "signer_info", 755 .item = &PKCS7_SIGNER_INFO_it, 756 }, 757 }; 758 759 const ASN1_ITEM PKCS7_SIGN_ENVELOPE_it = { 760 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 761 .utype = V_ASN1_SEQUENCE, 762 .templates = PKCS7_SIGN_ENVELOPE_seq_tt, 763 .tcount = sizeof(PKCS7_SIGN_ENVELOPE_seq_tt) / sizeof(ASN1_TEMPLATE), 764 .funcs = NULL, 765 .size = sizeof(PKCS7_SIGN_ENVELOPE), 766 .sname = "PKCS7_SIGN_ENVELOPE", 767 }; 768 769 770 PKCS7_SIGN_ENVELOPE * 771 d2i_PKCS7_SIGN_ENVELOPE(PKCS7_SIGN_ENVELOPE **a, const unsigned char **in, long len) 772 { 773 return (PKCS7_SIGN_ENVELOPE *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 774 &PKCS7_SIGN_ENVELOPE_it); 775 } 776 777 int 778 i2d_PKCS7_SIGN_ENVELOPE(PKCS7_SIGN_ENVELOPE *a, unsigned char **out) 779 { 780 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_SIGN_ENVELOPE_it); 781 } 782 783 PKCS7_SIGN_ENVELOPE * 784 PKCS7_SIGN_ENVELOPE_new(void) 785 { 786 return (PKCS7_SIGN_ENVELOPE *)ASN1_item_new(&PKCS7_SIGN_ENVELOPE_it); 787 } 788 789 void 790 PKCS7_SIGN_ENVELOPE_free(PKCS7_SIGN_ENVELOPE *a) 791 { 792 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_SIGN_ENVELOPE_it); 793 } 794 795 static const ASN1_TEMPLATE PKCS7_ENCRYPT_seq_tt[] = { 796 { 797 .flags = 0, 798 .tag = 0, 799 .offset = offsetof(PKCS7_ENCRYPT, version), 800 .field_name = "version", 801 .item = &ASN1_INTEGER_it, 802 }, 803 { 804 .flags = 0, 805 .tag = 0, 806 .offset = offsetof(PKCS7_ENCRYPT, enc_data), 807 .field_name = "enc_data", 808 .item = &PKCS7_ENC_CONTENT_it, 809 }, 810 }; 811 812 const ASN1_ITEM PKCS7_ENCRYPT_it = { 813 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 814 .utype = V_ASN1_SEQUENCE, 815 .templates = PKCS7_ENCRYPT_seq_tt, 816 .tcount = sizeof(PKCS7_ENCRYPT_seq_tt) / sizeof(ASN1_TEMPLATE), 817 .funcs = NULL, 818 .size = sizeof(PKCS7_ENCRYPT), 819 .sname = "PKCS7_ENCRYPT", 820 }; 821 822 823 PKCS7_ENCRYPT * 824 d2i_PKCS7_ENCRYPT(PKCS7_ENCRYPT **a, const unsigned char **in, long len) 825 { 826 return (PKCS7_ENCRYPT *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 827 &PKCS7_ENCRYPT_it); 828 } 829 830 int 831 i2d_PKCS7_ENCRYPT(PKCS7_ENCRYPT *a, unsigned char **out) 832 { 833 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_ENCRYPT_it); 834 } 835 836 PKCS7_ENCRYPT * 837 PKCS7_ENCRYPT_new(void) 838 { 839 return (PKCS7_ENCRYPT *)ASN1_item_new(&PKCS7_ENCRYPT_it); 840 } 841 842 void 843 PKCS7_ENCRYPT_free(PKCS7_ENCRYPT *a) 844 { 845 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_ENCRYPT_it); 846 } 847 848 static const ASN1_TEMPLATE PKCS7_DIGEST_seq_tt[] = { 849 { 850 .flags = 0, 851 .tag = 0, 852 .offset = offsetof(PKCS7_DIGEST, version), 853 .field_name = "version", 854 .item = &ASN1_INTEGER_it, 855 }, 856 { 857 .flags = 0, 858 .tag = 0, 859 .offset = offsetof(PKCS7_DIGEST, md), 860 .field_name = "md", 861 .item = &X509_ALGOR_it, 862 }, 863 { 864 .flags = 0, 865 .tag = 0, 866 .offset = offsetof(PKCS7_DIGEST, contents), 867 .field_name = "contents", 868 .item = &PKCS7_it, 869 }, 870 { 871 .flags = 0, 872 .tag = 0, 873 .offset = offsetof(PKCS7_DIGEST, digest), 874 .field_name = "digest", 875 .item = &ASN1_OCTET_STRING_it, 876 }, 877 }; 878 879 const ASN1_ITEM PKCS7_DIGEST_it = { 880 .itype = ASN1_ITYPE_NDEF_SEQUENCE, 881 .utype = V_ASN1_SEQUENCE, 882 .templates = PKCS7_DIGEST_seq_tt, 883 .tcount = sizeof(PKCS7_DIGEST_seq_tt) / sizeof(ASN1_TEMPLATE), 884 .funcs = NULL, 885 .size = sizeof(PKCS7_DIGEST), 886 .sname = "PKCS7_DIGEST", 887 }; 888 889 890 PKCS7_DIGEST * 891 d2i_PKCS7_DIGEST(PKCS7_DIGEST **a, const unsigned char **in, long len) 892 { 893 return (PKCS7_DIGEST *)ASN1_item_d2i((ASN1_VALUE **)a, in, len, 894 &PKCS7_DIGEST_it); 895 } 896 897 int 898 i2d_PKCS7_DIGEST(PKCS7_DIGEST *a, unsigned char **out) 899 { 900 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS7_DIGEST_it); 901 } 902 903 PKCS7_DIGEST * 904 PKCS7_DIGEST_new(void) 905 { 906 return (PKCS7_DIGEST *)ASN1_item_new(&PKCS7_DIGEST_it); 907 } 908 909 void 910 PKCS7_DIGEST_free(PKCS7_DIGEST *a) 911 { 912 ASN1_item_free((ASN1_VALUE *)a, &PKCS7_DIGEST_it); 913 } 914 915 /* Specials for authenticated attributes */ 916 917 /* When signing attributes we want to reorder them to match the sorted 918 * encoding. 919 */ 920 921 static const ASN1_TEMPLATE PKCS7_ATTR_SIGN_item_tt = { 922 .flags = ASN1_TFLG_SET_ORDER, 923 .tag = 0, 924 .offset = 0, 925 .field_name = "PKCS7_ATTRIBUTES", 926 .item = &X509_ATTRIBUTE_it, 927 }; 928 929 const ASN1_ITEM PKCS7_ATTR_SIGN_it = { 930 .itype = ASN1_ITYPE_PRIMITIVE, 931 .utype = -1, 932 .templates = &PKCS7_ATTR_SIGN_item_tt, 933 .tcount = 0, 934 .funcs = NULL, 935 .size = 0, 936 .sname = "PKCS7_ATTR_SIGN", 937 }; 938 939 /* When verifying attributes we need to use the received order. So 940 * we use SEQUENCE OF and tag it to SET OF 941 */ 942 943 static const ASN1_TEMPLATE PKCS7_ATTR_VERIFY_item_tt = { 944 .flags = ASN1_TFLG_SEQUENCE_OF | ASN1_TFLG_IMPTAG | ASN1_TFLG_UNIVERSAL, 945 .tag = V_ASN1_SET, 946 .offset = 0, 947 .field_name = "PKCS7_ATTRIBUTES", 948 .item = &X509_ATTRIBUTE_it, 949 }; 950 951 const ASN1_ITEM PKCS7_ATTR_VERIFY_it = { 952 .itype = ASN1_ITYPE_PRIMITIVE, 953 .utype = -1, 954 .templates = &PKCS7_ATTR_VERIFY_item_tt, 955 .tcount = 0, 956 .funcs = NULL, 957 .size = 0, 958 .sname = "PKCS7_ATTR_VERIFY", 959 }; 960 961 962 int 963 PKCS7_print_ctx(BIO *out, PKCS7 *x, int indent, const ASN1_PCTX *pctx) 964 { 965 return ASN1_item_print(out, (ASN1_VALUE *)x, indent, 966 &PKCS7_it, pctx); 967 } 968