Merge branch vendor/AWK into master.
[dragonfly.git] / crypto / libressl / crypto / x509 / x509_vpm.c
1 /* $OpenBSD: x509_vpm.c,v 1.18 2018/04/06 07:08:20 beck Exp $ */
2 /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
3  * project 2004.
4  */
5 /* ====================================================================
6  * Copyright (c) 2004 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 #include <string.h>
61
62 #include <openssl/buffer.h>
63 #include <openssl/crypto.h>
64 #include <openssl/lhash.h>
65 #include <openssl/stack.h>
66 #include <openssl/x509.h>
67 #include <openssl/x509v3.h>
68
69 #include "vpm_int.h"
70
71 /* X509_VERIFY_PARAM functions */
72
73 int X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM *param, const char *email,
74     size_t emaillen);
75 int X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM *param, const unsigned char *ip,
76     size_t iplen);
77
78 #define SET_HOST 0
79 #define ADD_HOST 1
80
81 static void
82 str_free(char *s)
83 {
84     free(s);
85 }
86
87 #define string_stack_free(sk) sk_OPENSSL_STRING_pop_free(sk, str_free)
88
89
90 /*
91  * Post 1.0.1 sk function "deep_copy".  For the moment we simply make
92  * these take void * and use them directly without a glorious blob of
93  * obfuscating macros of dubious value in front of them. All this in
94  * preparation for a rototilling of safestack.h (likely inspired by
95  * this).
96  */
97 static void *
98 sk_deep_copy(void *sk_void, void *copy_func_void, void *free_func_void)
99 {
100         _STACK *sk = sk_void;
101         void *(*copy_func)(void *) = copy_func_void;
102         void (*free_func)(void *) = free_func_void;
103         _STACK *ret = sk_dup(sk);
104         size_t i;
105
106         if (ret == NULL)
107                 return NULL;
108
109         for (i = 0; i < ret->num; i++) {
110                 if (ret->data[i] == NULL)
111                         continue;
112                 ret->data[i] = copy_func(ret->data[i]);
113                 if (ret->data[i] == NULL) {
114                         size_t j;
115                         for (j = 0; j < i; j++) {
116                                 if (ret->data[j] != NULL)
117                                         free_func(ret->data[j]);
118                         }
119                         sk_free(ret);
120                         return NULL;
121                 }
122         }
123
124         return ret;
125 }
126
127 static int
128 x509_param_set_hosts_internal(X509_VERIFY_PARAM_ID *id, int mode,
129     const char *name, size_t namelen)
130 {
131         char *copy;
132
133         if (name != NULL && namelen == 0)
134                 namelen = strlen(name);
135         /*
136          * Refuse names with embedded NUL bytes.
137          */
138         if (name && memchr(name, '\0', namelen))
139                 return 0;
140
141         if (mode == SET_HOST && id->hosts) {
142                 string_stack_free(id->hosts);
143                 id->hosts = NULL;
144         }
145         if (name == NULL || namelen == 0)
146                 return 1;
147         copy = strndup(name, namelen);
148         if (copy == NULL)
149                 return 0;
150
151         if (id->hosts == NULL &&
152             (id->hosts = sk_OPENSSL_STRING_new_null()) == NULL) {
153                 free(copy);
154                 return 0;
155         }
156
157         if (!sk_OPENSSL_STRING_push(id->hosts, copy)) {
158                 free(copy);
159                 if (sk_OPENSSL_STRING_num(id->hosts) == 0) {
160                         sk_OPENSSL_STRING_free(id->hosts);
161                         id->hosts = NULL;
162                 }
163                 return 0;
164         }
165
166         return 1;
167 }
168
169 static void
170 x509_verify_param_zero(X509_VERIFY_PARAM *param)
171 {
172         X509_VERIFY_PARAM_ID *paramid;
173         if (!param)
174                 return;
175         param->name = NULL;
176         param->purpose = 0;
177         param->trust = 0;
178         /*param->inh_flags = X509_VP_FLAG_DEFAULT;*/
179         param->inh_flags = 0;
180         param->flags = 0;
181         param->depth = -1;
182         if (param->policies) {
183                 sk_ASN1_OBJECT_pop_free(param->policies, ASN1_OBJECT_free);
184                 param->policies = NULL;
185         }
186         paramid = param->id;
187         if (paramid->hosts) {
188                 string_stack_free(paramid->hosts);
189                 paramid->hosts = NULL;
190         }
191         free(paramid->peername);
192         paramid->peername = NULL;
193         free(paramid->email);
194         paramid->email = NULL;
195         paramid->emaillen = 0;
196         free(paramid->ip);
197         paramid->ip = NULL;
198         paramid->iplen = 0;
199         paramid->poisoned = 0;
200 }
201
202 X509_VERIFY_PARAM *
203 X509_VERIFY_PARAM_new(void)
204 {
205         X509_VERIFY_PARAM *param;
206         X509_VERIFY_PARAM_ID *paramid;
207         param = calloc(1, sizeof(X509_VERIFY_PARAM));
208         if (param == NULL)
209                 return NULL;
210         paramid = calloc (1, sizeof(X509_VERIFY_PARAM_ID));
211         if (paramid == NULL) {
212                 free(param);
213                 return NULL;
214         }
215         param->id = paramid;
216         x509_verify_param_zero(param);
217         return param;
218 }
219
220 void
221 X509_VERIFY_PARAM_free(X509_VERIFY_PARAM *param)
222 {
223         if (param == NULL)
224                 return;
225         x509_verify_param_zero(param);
226         free(param->id);
227         free(param);
228 }
229
230 /* This function determines how parameters are "inherited" from one structure
231  * to another. There are several different ways this can happen.
232  *
233  * 1. If a child structure needs to have its values initialized from a parent
234  *    they are simply copied across. For example SSL_CTX copied to SSL.
235  * 2. If the structure should take on values only if they are currently unset.
236  *    For example the values in an SSL structure will take appropriate value
237  *    for SSL servers or clients but only if the application has not set new
238  *    ones.
239  *
240  * The "inh_flags" field determines how this function behaves.
241  *
242  * Normally any values which are set in the default are not copied from the
243  * destination and verify flags are ORed together.
244  *
245  * If X509_VP_FLAG_DEFAULT is set then anything set in the source is copied
246  * to the destination. Effectively the values in "to" become default values
247  * which will be used only if nothing new is set in "from".
248  *
249  * If X509_VP_FLAG_OVERWRITE is set then all value are copied across whether
250  * they are set or not. Flags is still Ored though.
251  *
252  * If X509_VP_FLAG_RESET_FLAGS is set then the flags value is copied instead
253  * of ORed.
254  *
255  * If X509_VP_FLAG_LOCKED is set then no values are copied.
256  *
257  * If X509_VP_FLAG_ONCE is set then the current inh_flags setting is zeroed
258  * after the next call.
259  */
260
261 /* Macro to test if a field should be copied from src to dest */
262
263 #define test_x509_verify_param_copy(field, def) \
264         (to_overwrite || \
265                 ((src->field != def) && (to_default || (dest->field == def))))
266
267 /* As above but for ID fields */
268
269 #define test_x509_verify_param_copy_id(idf, def) \
270         test_x509_verify_param_copy(id->idf, def)
271
272 /* Macro to test and copy a field if necessary */
273
274 #define x509_verify_param_copy(field, def) \
275         if (test_x509_verify_param_copy(field, def)) \
276                 dest->field = src->field
277
278 int
279 X509_VERIFY_PARAM_inherit(X509_VERIFY_PARAM *dest, const X509_VERIFY_PARAM *src)
280 {
281         unsigned long inh_flags;
282         int to_default, to_overwrite;
283         X509_VERIFY_PARAM_ID *id;
284
285         if (!src)
286                 return 1;
287         id = src->id;
288         inh_flags = dest->inh_flags | src->inh_flags;
289
290         if (inh_flags & X509_VP_FLAG_ONCE)
291                 dest->inh_flags = 0;
292
293         if (inh_flags & X509_VP_FLAG_LOCKED)
294                 return 1;
295
296         if (inh_flags & X509_VP_FLAG_DEFAULT)
297                 to_default = 1;
298         else
299                 to_default = 0;
300
301         if (inh_flags & X509_VP_FLAG_OVERWRITE)
302                 to_overwrite = 1;
303         else
304                 to_overwrite = 0;
305
306         x509_verify_param_copy(purpose, 0);
307         x509_verify_param_copy(trust, 0);
308         x509_verify_param_copy(depth, -1);
309
310         /* If overwrite or check time not set, copy across */
311
312         if (to_overwrite || !(dest->flags & X509_V_FLAG_USE_CHECK_TIME)) {
313                 dest->check_time = src->check_time;
314                 dest->flags &= ~X509_V_FLAG_USE_CHECK_TIME;
315                 /* Don't need to copy flag: that is done below */
316         }
317
318         if (inh_flags & X509_VP_FLAG_RESET_FLAGS)
319                 dest->flags = 0;
320
321         dest->flags |= src->flags;
322
323         if (test_x509_verify_param_copy(policies, NULL)) {
324                 if (!X509_VERIFY_PARAM_set1_policies(dest, src->policies))
325                         return 0;
326         }
327
328         /* Copy the host flags if and only if we're copying the host list */
329         if (test_x509_verify_param_copy_id(hosts, NULL)) {
330                 if (dest->id->hosts) {
331                         string_stack_free(dest->id->hosts);
332                         dest->id->hosts = NULL;
333                 }
334                 if (id->hosts) {
335                         dest->id->hosts =
336                             sk_deep_copy(id->hosts, strdup, str_free);
337                         if (dest->id->hosts == NULL)
338                                 return 0;
339                         dest->id->hostflags = id->hostflags;
340                 }
341         }
342
343         if (test_x509_verify_param_copy_id(email, NULL)) {
344                 if (!X509_VERIFY_PARAM_set1_email(dest, id->email,
345                     id->emaillen))
346                         return 0;
347         }
348
349         if (test_x509_verify_param_copy_id(ip, NULL)) {
350                 if (!X509_VERIFY_PARAM_set1_ip(dest, id->ip, id->iplen))
351                         return 0;
352         }
353
354         return 1;
355 }
356
357 int
358 X509_VERIFY_PARAM_set1(X509_VERIFY_PARAM *to, const X509_VERIFY_PARAM *from)
359 {
360         unsigned long save_flags = to->inh_flags;
361         int ret;
362
363         to->inh_flags |= X509_VP_FLAG_DEFAULT;
364         ret = X509_VERIFY_PARAM_inherit(to, from);
365         to->inh_flags = save_flags;
366         return ret;
367 }
368
369 static int
370 x509_param_set1_internal(char **pdest, size_t *pdestlen,  const char *src,
371     size_t srclen, int nonul)
372 {
373         char *tmp;
374
375         if (src == NULL)
376                 return 0;
377
378         if (srclen == 0) {
379                 srclen = strlen(src);
380                 if (srclen == 0)
381                         return 0;
382                 if ((tmp = strdup(src)) == NULL)
383                         return 0;
384         } else {
385                 if (nonul && memchr(src, '\0', srclen))
386                         return 0;
387                 if ((tmp = malloc(srclen)) == NULL)
388                         return 0;
389                 memcpy(tmp, src, srclen);
390         }
391
392         if (*pdest)
393                 free(*pdest);
394         *pdest = tmp;
395         if (pdestlen)
396                 *pdestlen = srclen;
397         return 1;
398 }
399
400 int
401 X509_VERIFY_PARAM_set1_name(X509_VERIFY_PARAM *param, const char *name)
402 {
403         free(param->name);
404         param->name = NULL;
405         if (name == NULL)
406                 return 1;
407         param->name = strdup(name);
408         if (param->name)
409                 return 1;
410         return 0;
411 }
412
413 int
414 X509_VERIFY_PARAM_set_flags(X509_VERIFY_PARAM *param, unsigned long flags)
415 {
416         param->flags |= flags;
417         if (flags & X509_V_FLAG_POLICY_MASK)
418                 param->flags |= X509_V_FLAG_POLICY_CHECK;
419         return 1;
420 }
421
422 int
423 X509_VERIFY_PARAM_clear_flags(X509_VERIFY_PARAM *param, unsigned long flags)
424 {
425         param->flags &= ~flags;
426         return 1;
427 }
428
429 unsigned long
430 X509_VERIFY_PARAM_get_flags(X509_VERIFY_PARAM *param)
431 {
432         return param->flags;
433 }
434
435 int
436 X509_VERIFY_PARAM_set_purpose(X509_VERIFY_PARAM *param, int purpose)
437 {
438         return X509_PURPOSE_set(&param->purpose, purpose);
439 }
440
441 int
442 X509_VERIFY_PARAM_set_trust(X509_VERIFY_PARAM *param, int trust)
443 {
444         return X509_TRUST_set(&param->trust, trust);
445 }
446
447 void
448 X509_VERIFY_PARAM_set_depth(X509_VERIFY_PARAM *param, int depth)
449 {
450         param->depth = depth;
451 }
452
453 void
454 X509_VERIFY_PARAM_set_time(X509_VERIFY_PARAM *param, time_t t)
455 {
456         param->check_time = t;
457         param->flags |= X509_V_FLAG_USE_CHECK_TIME;
458 }
459
460 int
461 X509_VERIFY_PARAM_add0_policy(X509_VERIFY_PARAM *param, ASN1_OBJECT *policy)
462 {
463         if (!param->policies) {
464                 param->policies = sk_ASN1_OBJECT_new_null();
465                 if (!param->policies)
466                         return 0;
467         }
468         if (!sk_ASN1_OBJECT_push(param->policies, policy))
469                 return 0;
470         return 1;
471 }
472
473 int
474 X509_VERIFY_PARAM_set1_policies(X509_VERIFY_PARAM *param,
475     STACK_OF(ASN1_OBJECT) *policies)
476 {
477         int i;
478         ASN1_OBJECT *oid, *doid;
479
480         if (!param)
481                 return 0;
482         if (param->policies)
483                 sk_ASN1_OBJECT_pop_free(param->policies, ASN1_OBJECT_free);
484
485         if (!policies) {
486                 param->policies = NULL;
487                 return 1;
488         }
489
490         param->policies = sk_ASN1_OBJECT_new_null();
491         if (!param->policies)
492                 return 0;
493
494         for (i = 0; i < sk_ASN1_OBJECT_num(policies); i++) {
495                 oid = sk_ASN1_OBJECT_value(policies, i);
496                 doid = OBJ_dup(oid);
497                 if (!doid)
498                         return 0;
499                 if (!sk_ASN1_OBJECT_push(param->policies, doid)) {
500                         ASN1_OBJECT_free(doid);
501                         return 0;
502                 }
503         }
504         param->flags |= X509_V_FLAG_POLICY_CHECK;
505         return 1;
506 }
507
508 int
509 X509_VERIFY_PARAM_set1_host(X509_VERIFY_PARAM *param,
510     const char *name, size_t namelen)
511 {
512         if (x509_param_set_hosts_internal(param->id, SET_HOST, name, namelen))
513                 return 1;
514         param->id->poisoned = 1;
515         return 0;
516 }
517
518 int
519 X509_VERIFY_PARAM_add1_host(X509_VERIFY_PARAM *param,
520     const char *name, size_t namelen)
521 {
522         if (x509_param_set_hosts_internal(param->id, ADD_HOST, name, namelen))
523                 return 1;
524         param->id->poisoned = 1;
525         return 0;
526 }
527
528 void
529 X509_VERIFY_PARAM_set_hostflags(X509_VERIFY_PARAM *param, unsigned int flags)
530 {
531         param->id->hostflags = flags;
532 }
533
534 char *
535 X509_VERIFY_PARAM_get0_peername(X509_VERIFY_PARAM *param)
536 {
537         return param->id->peername;
538 }
539
540 int
541 X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM *param,  const char *email,
542     size_t emaillen)
543 {
544         if (x509_param_set1_internal(&param->id->email, &param->id->emaillen,
545             email, emaillen, 1))
546                 return 1;
547         param->id->poisoned = 1;
548         return 0;
549 }
550
551 int
552 X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM *param, const unsigned char *ip,
553     size_t iplen)
554 {
555         if (iplen != 4 && iplen != 16)
556                 goto err;
557         if (x509_param_set1_internal((char **)&param->id->ip, &param->id->iplen,
558                 (char *)ip, iplen, 0))
559                 return 1;
560  err:
561         param->id->poisoned = 1;
562         return 0;
563 }
564
565 int
566 X509_VERIFY_PARAM_set1_ip_asc(X509_VERIFY_PARAM *param, const char *ipasc)
567 {
568         unsigned char ipout[16];
569         size_t iplen;
570
571         iplen = (size_t)a2i_ipadd(ipout, ipasc);
572         return X509_VERIFY_PARAM_set1_ip(param, ipout, iplen);
573 }
574
575 int
576 X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM *param)
577 {
578         return param->depth;
579 }
580
581 const char *
582 X509_VERIFY_PARAM_get0_name(const X509_VERIFY_PARAM *param)
583 {
584         return param->name;
585 }
586
587 static const X509_VERIFY_PARAM_ID _empty_id = { NULL };
588
589 #define vpm_empty_id (X509_VERIFY_PARAM_ID *)&_empty_id
590
591 /*
592  * Default verify parameters: these are used for various applications and can
593  * be overridden by the user specified table.
594  */
595
596 static const X509_VERIFY_PARAM default_table[] = {
597         {
598                 .name = "default",
599                 .depth = 100,
600                 .trust = 0,  /* XXX This is not the default trust value */
601                 .id = vpm_empty_id
602         },
603         {
604                 .name = "pkcs7",
605                 .purpose = X509_PURPOSE_SMIME_SIGN,
606                 .trust = X509_TRUST_EMAIL,
607                 .depth = -1,
608                 .id = vpm_empty_id
609         },
610         {
611                 .name = "smime_sign",
612                 .purpose = X509_PURPOSE_SMIME_SIGN,
613                 .trust = X509_TRUST_EMAIL,
614                 .depth =  -1,
615                 .id = vpm_empty_id
616         },
617         {
618                 .name = "ssl_client",
619                 .purpose = X509_PURPOSE_SSL_CLIENT,
620                 .trust = X509_TRUST_SSL_CLIENT,
621                 .depth = -1,
622                 .id = vpm_empty_id
623         },
624         {
625                 .name = "ssl_server",
626                 .purpose = X509_PURPOSE_SSL_SERVER,
627                 .trust = X509_TRUST_SSL_SERVER,
628                 .depth = -1,
629                 .id = vpm_empty_id
630         }
631 };
632
633 static STACK_OF(X509_VERIFY_PARAM) *param_table = NULL;
634
635 static int
636 param_cmp(const X509_VERIFY_PARAM * const *a,
637     const X509_VERIFY_PARAM * const *b)
638 {
639         return strcmp((*a)->name, (*b)->name);
640 }
641
642 int
643 X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param)
644 {
645         X509_VERIFY_PARAM *ptmp;
646         if (!param_table) {
647                 param_table = sk_X509_VERIFY_PARAM_new(param_cmp);
648                 if (!param_table)
649                         return 0;
650         } else {
651                 size_t idx;
652
653                 if ((idx = sk_X509_VERIFY_PARAM_find(param_table, param))
654                     != -1) {
655                         ptmp = sk_X509_VERIFY_PARAM_value(param_table,
656                             idx);
657                         X509_VERIFY_PARAM_free(ptmp);
658                         (void)sk_X509_VERIFY_PARAM_delete(param_table,
659                             idx);
660                 }
661         }
662         if (!sk_X509_VERIFY_PARAM_push(param_table, param))
663                 return 0;
664         return 1;
665 }
666
667 int
668 X509_VERIFY_PARAM_get_count(void)
669 {
670         int num = sizeof(default_table) / sizeof(X509_VERIFY_PARAM);
671         if (param_table)
672                 num += sk_X509_VERIFY_PARAM_num(param_table);
673         return num;
674 }
675
676 const
677 X509_VERIFY_PARAM *X509_VERIFY_PARAM_get0(int id)
678 {
679         int num = sizeof(default_table) / sizeof(X509_VERIFY_PARAM);
680         if (id < num)
681                 return default_table + id;
682         return sk_X509_VERIFY_PARAM_value(param_table, id - num);
683 }
684
685 const
686 X509_VERIFY_PARAM *X509_VERIFY_PARAM_lookup(const char *name)
687 {
688         X509_VERIFY_PARAM pm;
689         unsigned int i, limit;
690
691         pm.name = (char *)name;
692         if (param_table) {
693                 size_t idx;
694                 if ((idx = sk_X509_VERIFY_PARAM_find(param_table, &pm)) != -1)
695                         return sk_X509_VERIFY_PARAM_value(param_table, idx);
696         }
697
698         limit = sizeof(default_table) / sizeof(X509_VERIFY_PARAM);
699         for (i = 0; i < limit; i++) {
700                 if (strcmp(default_table[i].name, name) == 0) {
701                         return &default_table[i];
702                 }
703         }
704         return NULL;
705 }
706
707 void
708 X509_VERIFY_PARAM_table_cleanup(void)
709 {
710         if (param_table)
711                 sk_X509_VERIFY_PARAM_pop_free(param_table,
712                     X509_VERIFY_PARAM_free);
713         param_table = NULL;
714 }