1 /* $OpenBSD: p12_asn.c,v 1.15 2024/03/02 10:15:16 tb Exp $ */
2 /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
3 * project 1999.
4 */
5 /* ====================================================================
6 * Copyright (c) 1999 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/pkcs12.h>
63
64 #include "pkcs12_local.h"
65
66 /* PKCS#12 ASN1 module */
67
68 static const ASN1_TEMPLATE PKCS12_seq_tt[] = {
69 {
70 .flags = 0,
71 .tag = 0,
72 .offset = offsetof(PKCS12, version),
73 .field_name = "version",
74 .item = &ASN1_INTEGER_it,
75 },
76 {
77 .flags = 0,
78 .tag = 0,
79 .offset = offsetof(PKCS12, authsafes),
80 .field_name = "authsafes",
81 .item = &PKCS7_it,
82 },
83 {
84 .flags = ASN1_TFLG_OPTIONAL,
85 .tag = 0,
86 .offset = offsetof(PKCS12, mac),
87 .field_name = "mac",
88 .item = &PKCS12_MAC_DATA_it,
89 },
90 };
91
92 const ASN1_ITEM PKCS12_it = {
93 .itype = ASN1_ITYPE_SEQUENCE,
94 .utype = V_ASN1_SEQUENCE,
95 .templates = PKCS12_seq_tt,
96 .tcount = sizeof(PKCS12_seq_tt) / sizeof(ASN1_TEMPLATE),
97 .funcs = NULL,
98 .size = sizeof(PKCS12),
99 .sname = "PKCS12",
100 };
101
102
103 PKCS12 *
d2i_PKCS12(PKCS12 ** a,const unsigned char ** in,long len)104 d2i_PKCS12(PKCS12 **a, const unsigned char **in, long len)
105 {
106 return (PKCS12 *)ASN1_item_d2i((ASN1_VALUE **)a, in, len,
107 &PKCS12_it);
108 }
109 LCRYPTO_ALIAS(d2i_PKCS12);
110
111 int
i2d_PKCS12(PKCS12 * a,unsigned char ** out)112 i2d_PKCS12(PKCS12 *a, unsigned char **out)
113 {
114 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS12_it);
115 }
116 LCRYPTO_ALIAS(i2d_PKCS12);
117
118 PKCS12 *
PKCS12_new(void)119 PKCS12_new(void)
120 {
121 return (PKCS12 *)ASN1_item_new(&PKCS12_it);
122 }
123 LCRYPTO_ALIAS(PKCS12_new);
124
125 void
PKCS12_free(PKCS12 * a)126 PKCS12_free(PKCS12 *a)
127 {
128 ASN1_item_free((ASN1_VALUE *)a, &PKCS12_it);
129 }
130 LCRYPTO_ALIAS(PKCS12_free);
131
132 static const ASN1_TEMPLATE PKCS12_MAC_DATA_seq_tt[] = {
133 {
134 .flags = 0,
135 .tag = 0,
136 .offset = offsetof(PKCS12_MAC_DATA, dinfo),
137 .field_name = "dinfo",
138 .item = &X509_SIG_it,
139 },
140 {
141 .flags = 0,
142 .tag = 0,
143 .offset = offsetof(PKCS12_MAC_DATA, salt),
144 .field_name = "salt",
145 .item = &ASN1_OCTET_STRING_it,
146 },
147 {
148 .flags = ASN1_TFLG_OPTIONAL,
149 .tag = 0,
150 .offset = offsetof(PKCS12_MAC_DATA, iter),
151 .field_name = "iter",
152 .item = &ASN1_INTEGER_it,
153 },
154 };
155
156 const ASN1_ITEM PKCS12_MAC_DATA_it = {
157 .itype = ASN1_ITYPE_SEQUENCE,
158 .utype = V_ASN1_SEQUENCE,
159 .templates = PKCS12_MAC_DATA_seq_tt,
160 .tcount = sizeof(PKCS12_MAC_DATA_seq_tt) / sizeof(ASN1_TEMPLATE),
161 .funcs = NULL,
162 .size = sizeof(PKCS12_MAC_DATA),
163 .sname = "PKCS12_MAC_DATA",
164 };
165
166
167 PKCS12_MAC_DATA *
d2i_PKCS12_MAC_DATA(PKCS12_MAC_DATA ** a,const unsigned char ** in,long len)168 d2i_PKCS12_MAC_DATA(PKCS12_MAC_DATA **a, const unsigned char **in, long len)
169 {
170 return (PKCS12_MAC_DATA *)ASN1_item_d2i((ASN1_VALUE **)a, in, len,
171 &PKCS12_MAC_DATA_it);
172 }
173
174 int
i2d_PKCS12_MAC_DATA(PKCS12_MAC_DATA * a,unsigned char ** out)175 i2d_PKCS12_MAC_DATA(PKCS12_MAC_DATA *a, unsigned char **out)
176 {
177 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS12_MAC_DATA_it);
178 }
179
180 PKCS12_MAC_DATA *
PKCS12_MAC_DATA_new(void)181 PKCS12_MAC_DATA_new(void)
182 {
183 return (PKCS12_MAC_DATA *)ASN1_item_new(&PKCS12_MAC_DATA_it);
184 }
185
186 void
PKCS12_MAC_DATA_free(PKCS12_MAC_DATA * a)187 PKCS12_MAC_DATA_free(PKCS12_MAC_DATA *a)
188 {
189 ASN1_item_free((ASN1_VALUE *)a, &PKCS12_MAC_DATA_it);
190 }
191
192 static const ASN1_TEMPLATE bag_default_tt = {
193 .flags = ASN1_TFLG_EXPLICIT,
194 .tag = 0,
195 .offset = offsetof(PKCS12_BAGS, value.other),
196 .field_name = "value.other",
197 .item = &ASN1_ANY_it,
198 };
199
200 static const ASN1_ADB_TABLE PKCS12_BAGS_adbtbl[] = {
201 {
202 .value = NID_x509Certificate,
203 .tt = {
204 .flags = ASN1_TFLG_EXPLICIT,
205 .tag = 0,
206 .offset = offsetof(PKCS12_BAGS, value.x509cert),
207 .field_name = "value.x509cert",
208 .item = &ASN1_OCTET_STRING_it,
209 },
210
211 },
212 {
213 .value = NID_x509Crl,
214 .tt = {
215 .flags = ASN1_TFLG_EXPLICIT,
216 .tag = 0,
217 .offset = offsetof(PKCS12_BAGS, value.x509crl),
218 .field_name = "value.x509crl",
219 .item = &ASN1_OCTET_STRING_it,
220 },
221
222 },
223 {
224 .value = NID_sdsiCertificate,
225 .tt = {
226 .flags = ASN1_TFLG_EXPLICIT,
227 .tag = 0,
228 .offset = offsetof(PKCS12_BAGS, value.sdsicert),
229 .field_name = "value.sdsicert",
230 .item = &ASN1_IA5STRING_it,
231 },
232
233 },
234 };
235
236 static const ASN1_ADB PKCS12_BAGS_adb = {
237 .flags = 0,
238 .offset = offsetof(PKCS12_BAGS, type),
239 .tbl = PKCS12_BAGS_adbtbl,
240 .tblcount = sizeof(PKCS12_BAGS_adbtbl) / sizeof(ASN1_ADB_TABLE),
241 .default_tt = &bag_default_tt,
242 .null_tt = NULL,
243 };
244
245 static const ASN1_TEMPLATE PKCS12_BAGS_seq_tt[] = {
246 {
247 .flags = 0,
248 .tag = 0,
249 .offset = offsetof(PKCS12_BAGS, type),
250 .field_name = "type",
251 .item = &ASN1_OBJECT_it,
252 },
253 {
254 .flags = ASN1_TFLG_ADB_OID,
255 .tag = -1,
256 .offset = 0,
257 .field_name = "PKCS12_BAGS",
258 .item = (const ASN1_ITEM *)&PKCS12_BAGS_adb,
259 },
260 };
261
262 const ASN1_ITEM PKCS12_BAGS_it = {
263 .itype = ASN1_ITYPE_SEQUENCE,
264 .utype = V_ASN1_SEQUENCE,
265 .templates = PKCS12_BAGS_seq_tt,
266 .tcount = sizeof(PKCS12_BAGS_seq_tt) / sizeof(ASN1_TEMPLATE),
267 .funcs = NULL,
268 .size = sizeof(PKCS12_BAGS),
269 .sname = "PKCS12_BAGS",
270 };
271
272
273 PKCS12_BAGS *
d2i_PKCS12_BAGS(PKCS12_BAGS ** a,const unsigned char ** in,long len)274 d2i_PKCS12_BAGS(PKCS12_BAGS **a, const unsigned char **in, long len)
275 {
276 return (PKCS12_BAGS *)ASN1_item_d2i((ASN1_VALUE **)a, in, len,
277 &PKCS12_BAGS_it);
278 }
279
280 int
i2d_PKCS12_BAGS(PKCS12_BAGS * a,unsigned char ** out)281 i2d_PKCS12_BAGS(PKCS12_BAGS *a, unsigned char **out)
282 {
283 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS12_BAGS_it);
284 }
285
286 PKCS12_BAGS *
PKCS12_BAGS_new(void)287 PKCS12_BAGS_new(void)
288 {
289 return (PKCS12_BAGS *)ASN1_item_new(&PKCS12_BAGS_it);
290 }
291
292 void
PKCS12_BAGS_free(PKCS12_BAGS * a)293 PKCS12_BAGS_free(PKCS12_BAGS *a)
294 {
295 ASN1_item_free((ASN1_VALUE *)a, &PKCS12_BAGS_it);
296 }
297
298 static const ASN1_TEMPLATE safebag_default_tt = {
299 .flags = ASN1_TFLG_EXPLICIT,
300 .tag = 0,
301 .offset = offsetof(PKCS12_SAFEBAG, value.other),
302 .field_name = "value.other",
303 .item = &ASN1_ANY_it,
304 };
305
306 static const ASN1_ADB_TABLE PKCS12_SAFEBAG_adbtbl[] = {
307 {
308 .value = NID_keyBag,
309 .tt = {
310 .flags = ASN1_TFLG_EXPLICIT,
311 .tag = 0,
312 .offset = offsetof(PKCS12_SAFEBAG, value.keybag),
313 .field_name = "value.keybag",
314 .item = &PKCS8_PRIV_KEY_INFO_it,
315 },
316
317 },
318 {
319 .value = NID_pkcs8ShroudedKeyBag,
320 .tt = {
321 .flags = ASN1_TFLG_EXPLICIT,
322 .tag = 0,
323 .offset = offsetof(PKCS12_SAFEBAG, value.shkeybag),
324 .field_name = "value.shkeybag",
325 .item = &X509_SIG_it,
326 },
327
328 },
329 {
330 .value = NID_safeContentsBag,
331 .tt = {
332 .flags = ASN1_TFLG_EXPLICIT | ASN1_TFLG_SEQUENCE_OF,
333 .tag = 0,
334 .offset = offsetof(PKCS12_SAFEBAG, value.safes),
335 .field_name = "value.safes",
336 .item = &PKCS12_SAFEBAG_it,
337 },
338 },
339 {
340 .value = NID_certBag,
341 .tt = {
342 .flags = ASN1_TFLG_EXPLICIT,
343 .tag = 0,
344 .offset = offsetof(PKCS12_SAFEBAG, value.bag),
345 .field_name = "value.bag",
346 .item = &PKCS12_BAGS_it,
347 },
348
349 },
350 {
351 .value = NID_crlBag,
352 .tt = {
353 .flags = ASN1_TFLG_EXPLICIT,
354 .tag = 0,
355 .offset = offsetof(PKCS12_SAFEBAG, value.bag),
356 .field_name = "value.bag",
357 .item = &PKCS12_BAGS_it,
358 },
359
360 },
361 {
362 .value = NID_secretBag,
363 .tt = {
364 .flags = ASN1_TFLG_EXPLICIT,
365 .tag = 0,
366 .offset = offsetof(PKCS12_SAFEBAG, value.bag),
367 .field_name = "value.bag",
368 .item = &PKCS12_BAGS_it,
369 },
370
371 },
372 };
373
374 static const ASN1_ADB PKCS12_SAFEBAG_adb = {
375 .flags = 0,
376 .offset = offsetof(PKCS12_SAFEBAG, type),
377 .tbl = PKCS12_SAFEBAG_adbtbl,
378 .tblcount = sizeof(PKCS12_SAFEBAG_adbtbl) / sizeof(ASN1_ADB_TABLE),
379 .default_tt = &safebag_default_tt,
380 .null_tt = NULL,
381 };
382
383 static const ASN1_TEMPLATE PKCS12_SAFEBAG_seq_tt[] = {
384 {
385 .flags = 0,
386 .tag = 0,
387 .offset = offsetof(PKCS12_SAFEBAG, type),
388 .field_name = "type",
389 .item = &ASN1_OBJECT_it,
390 },
391 {
392 .flags = ASN1_TFLG_ADB_OID,
393 .tag = -1,
394 .offset = 0,
395 .field_name = "PKCS12_SAFEBAG",
396 .item = (const ASN1_ITEM *)&PKCS12_SAFEBAG_adb,
397 },
398 {
399 .flags = ASN1_TFLG_SET_OF | ASN1_TFLG_OPTIONAL,
400 .tag = 0,
401 .offset = offsetof(PKCS12_SAFEBAG, attrib),
402 .field_name = "attrib",
403 .item = &X509_ATTRIBUTE_it,
404 },
405 };
406
407 const ASN1_ITEM PKCS12_SAFEBAG_it = {
408 .itype = ASN1_ITYPE_SEQUENCE,
409 .utype = V_ASN1_SEQUENCE,
410 .templates = PKCS12_SAFEBAG_seq_tt,
411 .tcount = sizeof(PKCS12_SAFEBAG_seq_tt) / sizeof(ASN1_TEMPLATE),
412 .funcs = NULL,
413 .size = sizeof(PKCS12_SAFEBAG),
414 .sname = "PKCS12_SAFEBAG",
415 };
416
417
418 PKCS12_SAFEBAG *
d2i_PKCS12_SAFEBAG(PKCS12_SAFEBAG ** a,const unsigned char ** in,long len)419 d2i_PKCS12_SAFEBAG(PKCS12_SAFEBAG **a, const unsigned char **in, long len)
420 {
421 return (PKCS12_SAFEBAG *)ASN1_item_d2i((ASN1_VALUE **)a, in, len,
422 &PKCS12_SAFEBAG_it);
423 }
424 LCRYPTO_ALIAS(d2i_PKCS12_SAFEBAG);
425
426 int
i2d_PKCS12_SAFEBAG(PKCS12_SAFEBAG * a,unsigned char ** out)427 i2d_PKCS12_SAFEBAG(PKCS12_SAFEBAG *a, unsigned char **out)
428 {
429 return ASN1_item_i2d((ASN1_VALUE *)a, out, &PKCS12_SAFEBAG_it);
430 }
431 LCRYPTO_ALIAS(i2d_PKCS12_SAFEBAG);
432
433 PKCS12_SAFEBAG *
PKCS12_SAFEBAG_new(void)434 PKCS12_SAFEBAG_new(void)
435 {
436 return (PKCS12_SAFEBAG *)ASN1_item_new(&PKCS12_SAFEBAG_it);
437 }
438 LCRYPTO_ALIAS(PKCS12_SAFEBAG_new);
439
440 void
PKCS12_SAFEBAG_free(PKCS12_SAFEBAG * a)441 PKCS12_SAFEBAG_free(PKCS12_SAFEBAG *a)
442 {
443 ASN1_item_free((ASN1_VALUE *)a, &PKCS12_SAFEBAG_it);
444 }
445 LCRYPTO_ALIAS(PKCS12_SAFEBAG_free);
446
447 /* SEQUENCE OF SafeBag */
448 static const ASN1_TEMPLATE PKCS12_SAFEBAGS_item_tt = {
449 .flags = ASN1_TFLG_SEQUENCE_OF,
450 .tag = 0,
451 .offset = 0,
452 .field_name = "PKCS12_SAFEBAGS",
453 .item = &PKCS12_SAFEBAG_it,
454 };
455
456 const ASN1_ITEM PKCS12_SAFEBAGS_it = {
457 .itype = ASN1_ITYPE_PRIMITIVE,
458 .utype = -1,
459 .templates = &PKCS12_SAFEBAGS_item_tt,
460 .tcount = 0,
461 .funcs = NULL,
462 .size = 0,
463 .sname = "PKCS12_SAFEBAGS",
464 };
465
466 /* Authsafes: SEQUENCE OF PKCS7 */
467 static const ASN1_TEMPLATE PKCS12_AUTHSAFES_item_tt = {
468 .flags = ASN1_TFLG_SEQUENCE_OF,
469 .tag = 0,
470 .offset = 0,
471 .field_name = "PKCS12_AUTHSAFES",
472 .item = &PKCS7_it,
473 };
474
475 const ASN1_ITEM PKCS12_AUTHSAFES_it = {
476 .itype = ASN1_ITYPE_PRIMITIVE,
477 .utype = -1,
478 .templates = &PKCS12_AUTHSAFES_item_tt,
479 .tcount = 0,
480 .funcs = NULL,
481 .size = 0,
482 .sname = "PKCS12_AUTHSAFES",
483 };
484