1*de0e0e4dSAntonio Huete Jimenez /* $OpenBSD: x509_vpm.c,v 1.30 2022/07/04 12:17:32 tb Exp $ */
2f5b1c8a1SJohn Marino /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
3f5b1c8a1SJohn Marino  * project 2004.
4f5b1c8a1SJohn Marino  */
5f5b1c8a1SJohn Marino /* ====================================================================
6f5b1c8a1SJohn Marino  * Copyright (c) 2004 The OpenSSL Project.  All rights reserved.
7f5b1c8a1SJohn Marino  *
8f5b1c8a1SJohn Marino  * Redistribution and use in source and binary forms, with or without
9f5b1c8a1SJohn Marino  * modification, are permitted provided that the following conditions
10f5b1c8a1SJohn Marino  * are met:
11f5b1c8a1SJohn Marino  *
12f5b1c8a1SJohn Marino  * 1. Redistributions of source code must retain the above copyright
13f5b1c8a1SJohn Marino  *    notice, this list of conditions and the following disclaimer.
14f5b1c8a1SJohn Marino  *
15f5b1c8a1SJohn Marino  * 2. Redistributions in binary form must reproduce the above copyright
16f5b1c8a1SJohn Marino  *    notice, this list of conditions and the following disclaimer in
17f5b1c8a1SJohn Marino  *    the documentation and/or other materials provided with the
18f5b1c8a1SJohn Marino  *    distribution.
19f5b1c8a1SJohn Marino  *
20f5b1c8a1SJohn Marino  * 3. All advertising materials mentioning features or use of this
21f5b1c8a1SJohn Marino  *    software must display the following acknowledgment:
22f5b1c8a1SJohn Marino  *    "This product includes software developed by the OpenSSL Project
23f5b1c8a1SJohn Marino  *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
24f5b1c8a1SJohn Marino  *
25f5b1c8a1SJohn Marino  * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
26f5b1c8a1SJohn Marino  *    endorse or promote products derived from this software without
27f5b1c8a1SJohn Marino  *    prior written permission. For written permission, please contact
28f5b1c8a1SJohn Marino  *    licensing@OpenSSL.org.
29f5b1c8a1SJohn Marino  *
30f5b1c8a1SJohn Marino  * 5. Products derived from this software may not be called "OpenSSL"
31f5b1c8a1SJohn Marino  *    nor may "OpenSSL" appear in their names without prior written
32f5b1c8a1SJohn Marino  *    permission of the OpenSSL Project.
33f5b1c8a1SJohn Marino  *
34f5b1c8a1SJohn Marino  * 6. Redistributions of any form whatsoever must retain the following
35f5b1c8a1SJohn Marino  *    acknowledgment:
36f5b1c8a1SJohn Marino  *    "This product includes software developed by the OpenSSL Project
37f5b1c8a1SJohn Marino  *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
38f5b1c8a1SJohn Marino  *
39f5b1c8a1SJohn Marino  * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
40f5b1c8a1SJohn Marino  * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
41f5b1c8a1SJohn Marino  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
42f5b1c8a1SJohn Marino  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
43f5b1c8a1SJohn Marino  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
44f5b1c8a1SJohn Marino  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
45f5b1c8a1SJohn Marino  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
46f5b1c8a1SJohn Marino  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
47f5b1c8a1SJohn Marino  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
48f5b1c8a1SJohn Marino  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
49f5b1c8a1SJohn Marino  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
50f5b1c8a1SJohn Marino  * OF THE POSSIBILITY OF SUCH DAMAGE.
51f5b1c8a1SJohn Marino  * ====================================================================
52f5b1c8a1SJohn Marino  *
53f5b1c8a1SJohn Marino  * This product includes cryptographic software written by Eric Young
54f5b1c8a1SJohn Marino  * (eay@cryptsoft.com).  This product includes software written by Tim
55f5b1c8a1SJohn Marino  * Hudson (tjh@cryptsoft.com).
56f5b1c8a1SJohn Marino  *
57f5b1c8a1SJohn Marino  */
58f5b1c8a1SJohn Marino 
59f5b1c8a1SJohn Marino #include <stdio.h>
60f5b1c8a1SJohn Marino #include <string.h>
61f5b1c8a1SJohn Marino 
62f5b1c8a1SJohn Marino #include <openssl/buffer.h>
63f5b1c8a1SJohn Marino #include <openssl/crypto.h>
64f5b1c8a1SJohn Marino #include <openssl/lhash.h>
6572c33676SMaxim Ag #include <openssl/stack.h>
66f5b1c8a1SJohn Marino #include <openssl/x509.h>
67f5b1c8a1SJohn Marino #include <openssl/x509v3.h>
68f5b1c8a1SJohn Marino 
6972c33676SMaxim Ag #include "vpm_int.h"
70*de0e0e4dSAntonio Huete Jimenez #include "x509_lcl.h"
7172c33676SMaxim Ag 
72f5b1c8a1SJohn Marino /* X509_VERIFY_PARAM functions */
73f5b1c8a1SJohn Marino 
7472c33676SMaxim Ag int X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM *param, const char *email,
7572c33676SMaxim Ag     size_t emaillen);
7672c33676SMaxim Ag int X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM *param, const unsigned char *ip,
7772c33676SMaxim Ag     size_t iplen);
7872c33676SMaxim Ag 
7972c33676SMaxim Ag #define SET_HOST 0
8072c33676SMaxim Ag #define ADD_HOST 1
8172c33676SMaxim Ag 
8272c33676SMaxim Ag static void
str_free(char * s)8372c33676SMaxim Ag str_free(char *s)
8472c33676SMaxim Ag {
8572c33676SMaxim Ag     free(s);
8672c33676SMaxim Ag }
8772c33676SMaxim Ag 
8872c33676SMaxim Ag #define string_stack_free(sk) sk_OPENSSL_STRING_pop_free(sk, str_free)
8972c33676SMaxim Ag 
9072c33676SMaxim Ag 
9172c33676SMaxim Ag /*
9272c33676SMaxim Ag  * Post 1.0.1 sk function "deep_copy".  For the moment we simply make
9372c33676SMaxim Ag  * these take void * and use them directly without a glorious blob of
9472c33676SMaxim Ag  * obfuscating macros of dubious value in front of them. All this in
9572c33676SMaxim Ag  * preparation for a rototilling of safestack.h (likely inspired by
9672c33676SMaxim Ag  * this).
9772c33676SMaxim Ag  */
9872c33676SMaxim Ag static void *
sk_deep_copy(void * sk_void,void * copy_func_void,void * free_func_void)9972c33676SMaxim Ag sk_deep_copy(void *sk_void, void *copy_func_void, void *free_func_void)
10072c33676SMaxim Ag {
10172c33676SMaxim Ag 	_STACK *sk = sk_void;
10272c33676SMaxim Ag 	void *(*copy_func)(void *) = copy_func_void;
10372c33676SMaxim Ag 	void (*free_func)(void *) = free_func_void;
10472c33676SMaxim Ag 	_STACK *ret = sk_dup(sk);
10572c33676SMaxim Ag 	size_t i;
10672c33676SMaxim Ag 
10772c33676SMaxim Ag 	if (ret == NULL)
10872c33676SMaxim Ag 		return NULL;
10972c33676SMaxim Ag 
11072c33676SMaxim Ag 	for (i = 0; i < ret->num; i++) {
11172c33676SMaxim Ag 		if (ret->data[i] == NULL)
11272c33676SMaxim Ag 			continue;
11372c33676SMaxim Ag 		ret->data[i] = copy_func(ret->data[i]);
11472c33676SMaxim Ag 		if (ret->data[i] == NULL) {
11572c33676SMaxim Ag 			size_t j;
11672c33676SMaxim Ag 			for (j = 0; j < i; j++) {
11772c33676SMaxim Ag 				if (ret->data[j] != NULL)
11872c33676SMaxim Ag 					free_func(ret->data[j]);
11972c33676SMaxim Ag 			}
12072c33676SMaxim Ag 			sk_free(ret);
12172c33676SMaxim Ag 			return NULL;
12272c33676SMaxim Ag 		}
12372c33676SMaxim Ag 	}
12472c33676SMaxim Ag 
12572c33676SMaxim Ag 	return ret;
12672c33676SMaxim Ag }
12772c33676SMaxim Ag 
12872c33676SMaxim Ag static int
x509_param_set_hosts_internal(X509_VERIFY_PARAM_ID * id,int mode,const char * name,size_t namelen)12972c33676SMaxim Ag x509_param_set_hosts_internal(X509_VERIFY_PARAM_ID *id, int mode,
13072c33676SMaxim Ag     const char *name, size_t namelen)
13172c33676SMaxim Ag {
13272c33676SMaxim Ag 	char *copy;
13372c33676SMaxim Ag 
13472c33676SMaxim Ag 	if (name != NULL && namelen == 0)
13572c33676SMaxim Ag 		namelen = strlen(name);
13672c33676SMaxim Ag 	/*
13772c33676SMaxim Ag 	 * Refuse names with embedded NUL bytes.
13872c33676SMaxim Ag 	 */
13972c33676SMaxim Ag 	if (name && memchr(name, '\0', namelen))
14072c33676SMaxim Ag 		return 0;
14172c33676SMaxim Ag 
14272c33676SMaxim Ag 	if (mode == SET_HOST && id->hosts) {
14372c33676SMaxim Ag 		string_stack_free(id->hosts);
14472c33676SMaxim Ag 		id->hosts = NULL;
14572c33676SMaxim Ag 	}
14672c33676SMaxim Ag 	if (name == NULL || namelen == 0)
14772c33676SMaxim Ag 		return 1;
14872c33676SMaxim Ag 	copy = strndup(name, namelen);
14972c33676SMaxim Ag 	if (copy == NULL)
15072c33676SMaxim Ag 		return 0;
15172c33676SMaxim Ag 
15272c33676SMaxim Ag 	if (id->hosts == NULL &&
15372c33676SMaxim Ag 	    (id->hosts = sk_OPENSSL_STRING_new_null()) == NULL) {
15472c33676SMaxim Ag 		free(copy);
15572c33676SMaxim Ag 		return 0;
15672c33676SMaxim Ag 	}
15772c33676SMaxim Ag 
15872c33676SMaxim Ag 	if (!sk_OPENSSL_STRING_push(id->hosts, copy)) {
15972c33676SMaxim Ag 		free(copy);
16072c33676SMaxim Ag 		if (sk_OPENSSL_STRING_num(id->hosts) == 0) {
16172c33676SMaxim Ag 			sk_OPENSSL_STRING_free(id->hosts);
16272c33676SMaxim Ag 			id->hosts = NULL;
16372c33676SMaxim Ag 		}
16472c33676SMaxim Ag 		return 0;
16572c33676SMaxim Ag 	}
16672c33676SMaxim Ag 
16772c33676SMaxim Ag 	return 1;
16872c33676SMaxim Ag }
16972c33676SMaxim Ag 
170f5b1c8a1SJohn Marino static void
x509_verify_param_zero(X509_VERIFY_PARAM * param)171f5b1c8a1SJohn Marino x509_verify_param_zero(X509_VERIFY_PARAM *param)
172f5b1c8a1SJohn Marino {
17372c33676SMaxim Ag 	X509_VERIFY_PARAM_ID *paramid;
174f5b1c8a1SJohn Marino 	if (!param)
175f5b1c8a1SJohn Marino 		return;
176*de0e0e4dSAntonio Huete Jimenez 	free(param->name);
177f5b1c8a1SJohn Marino 	param->name = NULL;
178f5b1c8a1SJohn Marino 	param->purpose = 0;
179f5b1c8a1SJohn Marino 	param->trust = 0;
180f5b1c8a1SJohn Marino 	/*param->inh_flags = X509_VP_FLAG_DEFAULT;*/
181f5b1c8a1SJohn Marino 	param->inh_flags = 0;
182*de0e0e4dSAntonio Huete Jimenez 	param->flags = 0;
183f5b1c8a1SJohn Marino 	param->depth = -1;
184f5b1c8a1SJohn Marino 	if (param->policies) {
185f5b1c8a1SJohn Marino 		sk_ASN1_OBJECT_pop_free(param->policies, ASN1_OBJECT_free);
186f5b1c8a1SJohn Marino 		param->policies = NULL;
187f5b1c8a1SJohn Marino 	}
18872c33676SMaxim Ag 	paramid = param->id;
18972c33676SMaxim Ag 	if (paramid->hosts) {
19072c33676SMaxim Ag 		string_stack_free(paramid->hosts);
19172c33676SMaxim Ag 		paramid->hosts = NULL;
19272c33676SMaxim Ag 	}
19372c33676SMaxim Ag 	free(paramid->peername);
19472c33676SMaxim Ag 	paramid->peername = NULL;
19572c33676SMaxim Ag 	free(paramid->email);
19672c33676SMaxim Ag 	paramid->email = NULL;
19772c33676SMaxim Ag 	paramid->emaillen = 0;
19872c33676SMaxim Ag 	free(paramid->ip);
19972c33676SMaxim Ag 	paramid->ip = NULL;
20072c33676SMaxim Ag 	paramid->iplen = 0;
20172c33676SMaxim Ag 	paramid->poisoned = 0;
202f5b1c8a1SJohn Marino }
203f5b1c8a1SJohn Marino 
204f5b1c8a1SJohn Marino X509_VERIFY_PARAM *
X509_VERIFY_PARAM_new(void)205f5b1c8a1SJohn Marino X509_VERIFY_PARAM_new(void)
206f5b1c8a1SJohn Marino {
207f5b1c8a1SJohn Marino 	X509_VERIFY_PARAM *param;
20872c33676SMaxim Ag 	X509_VERIFY_PARAM_ID *paramid;
209f5b1c8a1SJohn Marino 	param = calloc(1, sizeof(X509_VERIFY_PARAM));
21072c33676SMaxim Ag 	if (param == NULL)
21172c33676SMaxim Ag 		return NULL;
21272c33676SMaxim Ag 	paramid = calloc(1, sizeof(X509_VERIFY_PARAM_ID));
21372c33676SMaxim Ag 	if (paramid == NULL) {
21472c33676SMaxim Ag 		free(param);
21572c33676SMaxim Ag 		return NULL;
21672c33676SMaxim Ag 	}
21772c33676SMaxim Ag 	param->id = paramid;
218f5b1c8a1SJohn Marino 	x509_verify_param_zero(param);
219f5b1c8a1SJohn Marino 	return param;
220f5b1c8a1SJohn Marino }
221f5b1c8a1SJohn Marino 
222f5b1c8a1SJohn Marino void
X509_VERIFY_PARAM_free(X509_VERIFY_PARAM * param)223f5b1c8a1SJohn Marino X509_VERIFY_PARAM_free(X509_VERIFY_PARAM *param)
224f5b1c8a1SJohn Marino {
22572c33676SMaxim Ag 	if (param == NULL)
22672c33676SMaxim Ag 		return;
227f5b1c8a1SJohn Marino 	x509_verify_param_zero(param);
22872c33676SMaxim Ag 	free(param->id);
229f5b1c8a1SJohn Marino 	free(param);
230f5b1c8a1SJohn Marino }
231f5b1c8a1SJohn Marino 
232*de0e0e4dSAntonio Huete Jimenez /*
233*de0e0e4dSAntonio Huete Jimenez  * This function determines how parameters are "inherited" from one structure
234f5b1c8a1SJohn Marino  * to another. There are several different ways this can happen.
235f5b1c8a1SJohn Marino  *
236f5b1c8a1SJohn Marino  * 1. If a child structure needs to have its values initialized from a parent
237f5b1c8a1SJohn Marino  *    they are simply copied across. For example SSL_CTX copied to SSL.
238f5b1c8a1SJohn Marino  * 2. If the structure should take on values only if they are currently unset.
239f5b1c8a1SJohn Marino  *    For example the values in an SSL structure will take appropriate value
240f5b1c8a1SJohn Marino  *    for SSL servers or clients but only if the application has not set new
241f5b1c8a1SJohn Marino  *    ones.
242f5b1c8a1SJohn Marino  *
243f5b1c8a1SJohn Marino  * The "inh_flags" field determines how this function behaves.
244f5b1c8a1SJohn Marino  *
245f5b1c8a1SJohn Marino  * Normally any values which are set in the default are not copied from the
246f5b1c8a1SJohn Marino  * destination and verify flags are ORed together.
247f5b1c8a1SJohn Marino  *
248f5b1c8a1SJohn Marino  * If X509_VP_FLAG_DEFAULT is set then anything set in the source is copied
249f5b1c8a1SJohn Marino  * to the destination. Effectively the values in "to" become default values
250f5b1c8a1SJohn Marino  * which will be used only if nothing new is set in "from".
251f5b1c8a1SJohn Marino  *
252f5b1c8a1SJohn Marino  * If X509_VP_FLAG_OVERWRITE is set then all value are copied across whether
253f5b1c8a1SJohn Marino  * they are set or not. Flags is still Ored though.
254f5b1c8a1SJohn Marino  *
255f5b1c8a1SJohn Marino  * If X509_VP_FLAG_RESET_FLAGS is set then the flags value is copied instead
256f5b1c8a1SJohn Marino  * of ORed.
257f5b1c8a1SJohn Marino  *
258f5b1c8a1SJohn Marino  * If X509_VP_FLAG_LOCKED is set then no values are copied.
259f5b1c8a1SJohn Marino  *
260f5b1c8a1SJohn Marino  * If X509_VP_FLAG_ONCE is set then the current inh_flags setting is zeroed
261f5b1c8a1SJohn Marino  * after the next call.
262f5b1c8a1SJohn Marino  */
263f5b1c8a1SJohn Marino 
264f5b1c8a1SJohn Marino /* Macro to test if a field should be copied from src to dest */
265f5b1c8a1SJohn Marino 
266f5b1c8a1SJohn Marino #define test_x509_verify_param_copy(field, def) \
267f5b1c8a1SJohn Marino 	(to_overwrite || \
268f5b1c8a1SJohn Marino 		((src->field != def) && (to_default || (dest->field == def))))
269f5b1c8a1SJohn Marino 
27072c33676SMaxim Ag /* As above but for ID fields */
27172c33676SMaxim Ag 
27272c33676SMaxim Ag #define test_x509_verify_param_copy_id(idf, def) \
27372c33676SMaxim Ag 	test_x509_verify_param_copy(id->idf, def)
27472c33676SMaxim Ag 
275f5b1c8a1SJohn Marino /* Macro to test and copy a field if necessary */
276f5b1c8a1SJohn Marino 
277f5b1c8a1SJohn Marino #define x509_verify_param_copy(field, def) \
278f5b1c8a1SJohn Marino 	if (test_x509_verify_param_copy(field, def)) \
279f5b1c8a1SJohn Marino 		dest->field = src->field
280f5b1c8a1SJohn Marino 
281f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_inherit(X509_VERIFY_PARAM * dest,const X509_VERIFY_PARAM * src)282f5b1c8a1SJohn Marino X509_VERIFY_PARAM_inherit(X509_VERIFY_PARAM *dest, const X509_VERIFY_PARAM *src)
283f5b1c8a1SJohn Marino {
284f5b1c8a1SJohn Marino 	unsigned long inh_flags;
285f5b1c8a1SJohn Marino 	int to_default, to_overwrite;
28672c33676SMaxim Ag 	X509_VERIFY_PARAM_ID *id;
287f5b1c8a1SJohn Marino 
288f5b1c8a1SJohn Marino 	if (!src)
289f5b1c8a1SJohn Marino 		return 1;
29072c33676SMaxim Ag 	id = src->id;
291f5b1c8a1SJohn Marino 	inh_flags = dest->inh_flags | src->inh_flags;
292f5b1c8a1SJohn Marino 
293f5b1c8a1SJohn Marino 	if (inh_flags & X509_VP_FLAG_ONCE)
294f5b1c8a1SJohn Marino 		dest->inh_flags = 0;
295f5b1c8a1SJohn Marino 
296f5b1c8a1SJohn Marino 	if (inh_flags & X509_VP_FLAG_LOCKED)
297f5b1c8a1SJohn Marino 		return 1;
298f5b1c8a1SJohn Marino 
299f5b1c8a1SJohn Marino 	if (inh_flags & X509_VP_FLAG_DEFAULT)
300f5b1c8a1SJohn Marino 		to_default = 1;
301f5b1c8a1SJohn Marino 	else
302f5b1c8a1SJohn Marino 		to_default = 0;
303f5b1c8a1SJohn Marino 
304f5b1c8a1SJohn Marino 	if (inh_flags & X509_VP_FLAG_OVERWRITE)
305f5b1c8a1SJohn Marino 		to_overwrite = 1;
306f5b1c8a1SJohn Marino 	else
307f5b1c8a1SJohn Marino 		to_overwrite = 0;
308f5b1c8a1SJohn Marino 
309f5b1c8a1SJohn Marino 	x509_verify_param_copy(purpose, 0);
310f5b1c8a1SJohn Marino 	x509_verify_param_copy(trust, 0);
311f5b1c8a1SJohn Marino 	x509_verify_param_copy(depth, -1);
312f5b1c8a1SJohn Marino 
313f5b1c8a1SJohn Marino 	/* If overwrite or check time not set, copy across */
314f5b1c8a1SJohn Marino 
315f5b1c8a1SJohn Marino 	if (to_overwrite || !(dest->flags & X509_V_FLAG_USE_CHECK_TIME)) {
316f5b1c8a1SJohn Marino 		dest->check_time = src->check_time;
317f5b1c8a1SJohn Marino 		dest->flags &= ~X509_V_FLAG_USE_CHECK_TIME;
318f5b1c8a1SJohn Marino 		/* Don't need to copy flag: that is done below */
319f5b1c8a1SJohn Marino 	}
320f5b1c8a1SJohn Marino 
321f5b1c8a1SJohn Marino 	if (inh_flags & X509_VP_FLAG_RESET_FLAGS)
322f5b1c8a1SJohn Marino 		dest->flags = 0;
323f5b1c8a1SJohn Marino 
324f5b1c8a1SJohn Marino 	dest->flags |= src->flags;
325f5b1c8a1SJohn Marino 
326f5b1c8a1SJohn Marino 	if (test_x509_verify_param_copy(policies, NULL)) {
327f5b1c8a1SJohn Marino 		if (!X509_VERIFY_PARAM_set1_policies(dest, src->policies))
328f5b1c8a1SJohn Marino 			return 0;
329f5b1c8a1SJohn Marino 	}
330f5b1c8a1SJohn Marino 
33172c33676SMaxim Ag 	/* Copy the host flags if and only if we're copying the host list */
33272c33676SMaxim Ag 	if (test_x509_verify_param_copy_id(hosts, NULL)) {
33372c33676SMaxim Ag 		if (dest->id->hosts) {
33472c33676SMaxim Ag 			string_stack_free(dest->id->hosts);
33572c33676SMaxim Ag 			dest->id->hosts = NULL;
33672c33676SMaxim Ag 		}
33772c33676SMaxim Ag 		if (id->hosts) {
33872c33676SMaxim Ag 			dest->id->hosts =
33972c33676SMaxim Ag 			    sk_deep_copy(id->hosts, strdup, str_free);
34072c33676SMaxim Ag 			if (dest->id->hosts == NULL)
34172c33676SMaxim Ag 				return 0;
34272c33676SMaxim Ag 			dest->id->hostflags = id->hostflags;
34372c33676SMaxim Ag 		}
34472c33676SMaxim Ag 	}
34572c33676SMaxim Ag 
34672c33676SMaxim Ag 	if (test_x509_verify_param_copy_id(email, NULL)) {
34772c33676SMaxim Ag 		if (!X509_VERIFY_PARAM_set1_email(dest, id->email,
34872c33676SMaxim Ag 		    id->emaillen))
34972c33676SMaxim Ag 			return 0;
35072c33676SMaxim Ag 	}
35172c33676SMaxim Ag 
35272c33676SMaxim Ag 	if (test_x509_verify_param_copy_id(ip, NULL)) {
35372c33676SMaxim Ag 		if (!X509_VERIFY_PARAM_set1_ip(dest, id->ip, id->iplen))
35472c33676SMaxim Ag 			return 0;
35572c33676SMaxim Ag 	}
35672c33676SMaxim Ag 
357f5b1c8a1SJohn Marino 	return 1;
358f5b1c8a1SJohn Marino }
359f5b1c8a1SJohn Marino 
360f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set1(X509_VERIFY_PARAM * to,const X509_VERIFY_PARAM * from)361f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set1(X509_VERIFY_PARAM *to, const X509_VERIFY_PARAM *from)
362f5b1c8a1SJohn Marino {
363f5b1c8a1SJohn Marino 	unsigned long save_flags = to->inh_flags;
364f5b1c8a1SJohn Marino 	int ret;
365f5b1c8a1SJohn Marino 
366f5b1c8a1SJohn Marino 	to->inh_flags |= X509_VP_FLAG_DEFAULT;
367f5b1c8a1SJohn Marino 	ret = X509_VERIFY_PARAM_inherit(to, from);
368f5b1c8a1SJohn Marino 	to->inh_flags = save_flags;
369f5b1c8a1SJohn Marino 	return ret;
370f5b1c8a1SJohn Marino }
371f5b1c8a1SJohn Marino 
37272c33676SMaxim Ag static int
x509_param_set1_internal(char ** pdest,size_t * pdestlen,const char * src,size_t srclen,int nonul)37372c33676SMaxim Ag x509_param_set1_internal(char **pdest, size_t *pdestlen,  const char *src,
37472c33676SMaxim Ag     size_t srclen, int nonul)
37572c33676SMaxim Ag {
37672c33676SMaxim Ag 	char *tmp;
37772c33676SMaxim Ag 
37872c33676SMaxim Ag 	if (src == NULL)
37972c33676SMaxim Ag 		return 0;
38072c33676SMaxim Ag 
38172c33676SMaxim Ag 	if (srclen == 0) {
38272c33676SMaxim Ag 		srclen = strlen(src);
38372c33676SMaxim Ag 		if (srclen == 0)
38472c33676SMaxim Ag 			return 0;
38572c33676SMaxim Ag 		if ((tmp = strdup(src)) == NULL)
38672c33676SMaxim Ag 			return 0;
38772c33676SMaxim Ag 	} else {
38872c33676SMaxim Ag 		if (nonul && memchr(src, '\0', srclen))
38972c33676SMaxim Ag 			return 0;
39072c33676SMaxim Ag 		if ((tmp = malloc(srclen)) == NULL)
39172c33676SMaxim Ag 			return 0;
39272c33676SMaxim Ag 		memcpy(tmp, src, srclen);
39372c33676SMaxim Ag 	}
39472c33676SMaxim Ag 
39572c33676SMaxim Ag 	if (*pdest)
39672c33676SMaxim Ag 		free(*pdest);
39772c33676SMaxim Ag 	*pdest = tmp;
39872c33676SMaxim Ag 	if (pdestlen)
39972c33676SMaxim Ag 		*pdestlen = srclen;
40072c33676SMaxim Ag 	return 1;
40172c33676SMaxim Ag }
40272c33676SMaxim Ag 
403f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set1_name(X509_VERIFY_PARAM * param,const char * name)404f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set1_name(X509_VERIFY_PARAM *param, const char *name)
405f5b1c8a1SJohn Marino {
406f5b1c8a1SJohn Marino 	free(param->name);
407f5b1c8a1SJohn Marino 	param->name = NULL;
408f5b1c8a1SJohn Marino 	if (name == NULL)
409f5b1c8a1SJohn Marino 		return 1;
410f5b1c8a1SJohn Marino 	param->name = strdup(name);
411f5b1c8a1SJohn Marino 	if (param->name)
412f5b1c8a1SJohn Marino 		return 1;
413f5b1c8a1SJohn Marino 	return 0;
414f5b1c8a1SJohn Marino }
415f5b1c8a1SJohn Marino 
416f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set_flags(X509_VERIFY_PARAM * param,unsigned long flags)417f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set_flags(X509_VERIFY_PARAM *param, unsigned long flags)
418f5b1c8a1SJohn Marino {
419f5b1c8a1SJohn Marino 	param->flags |= flags;
420f5b1c8a1SJohn Marino 	if (flags & X509_V_FLAG_POLICY_MASK)
421f5b1c8a1SJohn Marino 		param->flags |= X509_V_FLAG_POLICY_CHECK;
422f5b1c8a1SJohn Marino 	return 1;
423f5b1c8a1SJohn Marino }
424f5b1c8a1SJohn Marino 
425f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_clear_flags(X509_VERIFY_PARAM * param,unsigned long flags)426f5b1c8a1SJohn Marino X509_VERIFY_PARAM_clear_flags(X509_VERIFY_PARAM *param, unsigned long flags)
427f5b1c8a1SJohn Marino {
428f5b1c8a1SJohn Marino 	param->flags &= ~flags;
429f5b1c8a1SJohn Marino 	return 1;
430f5b1c8a1SJohn Marino }
431f5b1c8a1SJohn Marino 
432f5b1c8a1SJohn Marino unsigned long
X509_VERIFY_PARAM_get_flags(X509_VERIFY_PARAM * param)433f5b1c8a1SJohn Marino X509_VERIFY_PARAM_get_flags(X509_VERIFY_PARAM *param)
434f5b1c8a1SJohn Marino {
435f5b1c8a1SJohn Marino 	return param->flags;
436f5b1c8a1SJohn Marino }
437f5b1c8a1SJohn Marino 
438f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set_purpose(X509_VERIFY_PARAM * param,int purpose)439f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set_purpose(X509_VERIFY_PARAM *param, int purpose)
440f5b1c8a1SJohn Marino {
441f5b1c8a1SJohn Marino 	return X509_PURPOSE_set(&param->purpose, purpose);
442f5b1c8a1SJohn Marino }
443f5b1c8a1SJohn Marino 
444f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set_trust(X509_VERIFY_PARAM * param,int trust)445f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set_trust(X509_VERIFY_PARAM *param, int trust)
446f5b1c8a1SJohn Marino {
447f5b1c8a1SJohn Marino 	return X509_TRUST_set(&param->trust, trust);
448f5b1c8a1SJohn Marino }
449f5b1c8a1SJohn Marino 
450f5b1c8a1SJohn Marino void
X509_VERIFY_PARAM_set_depth(X509_VERIFY_PARAM * param,int depth)451f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set_depth(X509_VERIFY_PARAM *param, int depth)
452f5b1c8a1SJohn Marino {
453f5b1c8a1SJohn Marino 	param->depth = depth;
454f5b1c8a1SJohn Marino }
455f5b1c8a1SJohn Marino 
456f5b1c8a1SJohn Marino void
X509_VERIFY_PARAM_set_auth_level(X509_VERIFY_PARAM * param,int auth_level)457*de0e0e4dSAntonio Huete Jimenez X509_VERIFY_PARAM_set_auth_level(X509_VERIFY_PARAM *param, int auth_level)
458*de0e0e4dSAntonio Huete Jimenez {
459*de0e0e4dSAntonio Huete Jimenez 	param->security_level = auth_level;
460*de0e0e4dSAntonio Huete Jimenez }
461*de0e0e4dSAntonio Huete Jimenez 
462*de0e0e4dSAntonio Huete Jimenez time_t
X509_VERIFY_PARAM_get_time(const X509_VERIFY_PARAM * param)463*de0e0e4dSAntonio Huete Jimenez X509_VERIFY_PARAM_get_time(const X509_VERIFY_PARAM *param)
464*de0e0e4dSAntonio Huete Jimenez {
465*de0e0e4dSAntonio Huete Jimenez 	return param->check_time;
466*de0e0e4dSAntonio Huete Jimenez }
467*de0e0e4dSAntonio Huete Jimenez 
468*de0e0e4dSAntonio Huete Jimenez void
X509_VERIFY_PARAM_set_time(X509_VERIFY_PARAM * param,time_t t)469f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set_time(X509_VERIFY_PARAM *param, time_t t)
470f5b1c8a1SJohn Marino {
471f5b1c8a1SJohn Marino 	param->check_time = t;
472f5b1c8a1SJohn Marino 	param->flags |= X509_V_FLAG_USE_CHECK_TIME;
473f5b1c8a1SJohn Marino }
474f5b1c8a1SJohn Marino 
475f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_add0_policy(X509_VERIFY_PARAM * param,ASN1_OBJECT * policy)476f5b1c8a1SJohn Marino X509_VERIFY_PARAM_add0_policy(X509_VERIFY_PARAM *param, ASN1_OBJECT *policy)
477f5b1c8a1SJohn Marino {
478f5b1c8a1SJohn Marino 	if (!param->policies) {
479f5b1c8a1SJohn Marino 		param->policies = sk_ASN1_OBJECT_new_null();
480f5b1c8a1SJohn Marino 		if (!param->policies)
481f5b1c8a1SJohn Marino 			return 0;
482f5b1c8a1SJohn Marino 	}
483f5b1c8a1SJohn Marino 	if (!sk_ASN1_OBJECT_push(param->policies, policy))
484f5b1c8a1SJohn Marino 		return 0;
485f5b1c8a1SJohn Marino 	return 1;
486f5b1c8a1SJohn Marino }
487f5b1c8a1SJohn Marino 
488f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set1_policies(X509_VERIFY_PARAM * param,STACK_OF (ASN1_OBJECT)* policies)489f5b1c8a1SJohn Marino X509_VERIFY_PARAM_set1_policies(X509_VERIFY_PARAM *param,
490f5b1c8a1SJohn Marino     STACK_OF(ASN1_OBJECT) *policies)
491f5b1c8a1SJohn Marino {
492f5b1c8a1SJohn Marino 	int i;
493f5b1c8a1SJohn Marino 	ASN1_OBJECT *oid, *doid;
494f5b1c8a1SJohn Marino 
495f5b1c8a1SJohn Marino 	if (!param)
496f5b1c8a1SJohn Marino 		return 0;
497f5b1c8a1SJohn Marino 	if (param->policies)
498f5b1c8a1SJohn Marino 		sk_ASN1_OBJECT_pop_free(param->policies, ASN1_OBJECT_free);
499f5b1c8a1SJohn Marino 
500f5b1c8a1SJohn Marino 	if (!policies) {
501f5b1c8a1SJohn Marino 		param->policies = NULL;
502f5b1c8a1SJohn Marino 		return 1;
503f5b1c8a1SJohn Marino 	}
504f5b1c8a1SJohn Marino 
505f5b1c8a1SJohn Marino 	param->policies = sk_ASN1_OBJECT_new_null();
506f5b1c8a1SJohn Marino 	if (!param->policies)
507f5b1c8a1SJohn Marino 		return 0;
508f5b1c8a1SJohn Marino 
509f5b1c8a1SJohn Marino 	for (i = 0; i < sk_ASN1_OBJECT_num(policies); i++) {
510f5b1c8a1SJohn Marino 		oid = sk_ASN1_OBJECT_value(policies, i);
511f5b1c8a1SJohn Marino 		doid = OBJ_dup(oid);
512f5b1c8a1SJohn Marino 		if (!doid)
513f5b1c8a1SJohn Marino 			return 0;
514f5b1c8a1SJohn Marino 		if (!sk_ASN1_OBJECT_push(param->policies, doid)) {
515f5b1c8a1SJohn Marino 			ASN1_OBJECT_free(doid);
516f5b1c8a1SJohn Marino 			return 0;
517f5b1c8a1SJohn Marino 		}
518f5b1c8a1SJohn Marino 	}
519f5b1c8a1SJohn Marino 	param->flags |= X509_V_FLAG_POLICY_CHECK;
520f5b1c8a1SJohn Marino 	return 1;
521f5b1c8a1SJohn Marino }
522f5b1c8a1SJohn Marino 
523f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_set1_host(X509_VERIFY_PARAM * param,const char * name,size_t namelen)52472c33676SMaxim Ag X509_VERIFY_PARAM_set1_host(X509_VERIFY_PARAM *param,
52572c33676SMaxim Ag     const char *name, size_t namelen)
52672c33676SMaxim Ag {
52772c33676SMaxim Ag 	if (x509_param_set_hosts_internal(param->id, SET_HOST, name, namelen))
52872c33676SMaxim Ag 		return 1;
52972c33676SMaxim Ag 	param->id->poisoned = 1;
53072c33676SMaxim Ag 	return 0;
53172c33676SMaxim Ag }
53272c33676SMaxim Ag 
53372c33676SMaxim Ag int
X509_VERIFY_PARAM_add1_host(X509_VERIFY_PARAM * param,const char * name,size_t namelen)53472c33676SMaxim Ag X509_VERIFY_PARAM_add1_host(X509_VERIFY_PARAM *param,
53572c33676SMaxim Ag     const char *name, size_t namelen)
53672c33676SMaxim Ag {
53772c33676SMaxim Ag 	if (x509_param_set_hosts_internal(param->id, ADD_HOST, name, namelen))
53872c33676SMaxim Ag 		return 1;
53972c33676SMaxim Ag 	param->id->poisoned = 1;
54072c33676SMaxim Ag 	return 0;
54172c33676SMaxim Ag }
54272c33676SMaxim Ag 
54372c33676SMaxim Ag void
X509_VERIFY_PARAM_set_hostflags(X509_VERIFY_PARAM * param,unsigned int flags)54472c33676SMaxim Ag X509_VERIFY_PARAM_set_hostflags(X509_VERIFY_PARAM *param, unsigned int flags)
54572c33676SMaxim Ag {
54672c33676SMaxim Ag 	param->id->hostflags = flags;
54772c33676SMaxim Ag }
54872c33676SMaxim Ag 
54972c33676SMaxim Ag char *
X509_VERIFY_PARAM_get0_peername(X509_VERIFY_PARAM * param)55072c33676SMaxim Ag X509_VERIFY_PARAM_get0_peername(X509_VERIFY_PARAM *param)
55172c33676SMaxim Ag {
55272c33676SMaxim Ag 	return param->id->peername;
55372c33676SMaxim Ag }
55472c33676SMaxim Ag 
55572c33676SMaxim Ag int
X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM * param,const char * email,size_t emaillen)55672c33676SMaxim Ag X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM *param,  const char *email,
55772c33676SMaxim Ag     size_t emaillen)
55872c33676SMaxim Ag {
55972c33676SMaxim Ag 	if (x509_param_set1_internal(&param->id->email, &param->id->emaillen,
56072c33676SMaxim Ag 	    email, emaillen, 1))
56172c33676SMaxim Ag 		return 1;
56272c33676SMaxim Ag 	param->id->poisoned = 1;
56372c33676SMaxim Ag 	return 0;
56472c33676SMaxim Ag }
56572c33676SMaxim Ag 
56672c33676SMaxim Ag int
X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM * param,const unsigned char * ip,size_t iplen)56772c33676SMaxim Ag X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM *param, const unsigned char *ip,
56872c33676SMaxim Ag     size_t iplen)
56972c33676SMaxim Ag {
57072c33676SMaxim Ag 	if (iplen != 4 && iplen != 16)
57172c33676SMaxim Ag 		goto err;
57272c33676SMaxim Ag 	if (x509_param_set1_internal((char **)&param->id->ip, &param->id->iplen,
57372c33676SMaxim Ag 		(char *)ip, iplen, 0))
57472c33676SMaxim Ag 		return 1;
57572c33676SMaxim Ag  err:
57672c33676SMaxim Ag 	param->id->poisoned = 1;
57772c33676SMaxim Ag 	return 0;
57872c33676SMaxim Ag }
57972c33676SMaxim Ag 
58072c33676SMaxim Ag int
X509_VERIFY_PARAM_set1_ip_asc(X509_VERIFY_PARAM * param,const char * ipasc)58172c33676SMaxim Ag X509_VERIFY_PARAM_set1_ip_asc(X509_VERIFY_PARAM *param, const char *ipasc)
58272c33676SMaxim Ag {
58372c33676SMaxim Ag 	unsigned char ipout[16];
58472c33676SMaxim Ag 	size_t iplen;
58572c33676SMaxim Ag 
58672c33676SMaxim Ag 	iplen = (size_t)a2i_ipadd(ipout, ipasc);
58772c33676SMaxim Ag 	return X509_VERIFY_PARAM_set1_ip(param, ipout, iplen);
58872c33676SMaxim Ag }
58972c33676SMaxim Ag 
59072c33676SMaxim Ag int
X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM * param)591f5b1c8a1SJohn Marino X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM *param)
592f5b1c8a1SJohn Marino {
593f5b1c8a1SJohn Marino 	return param->depth;
594f5b1c8a1SJohn Marino }
595f5b1c8a1SJohn Marino 
59672c33676SMaxim Ag const char *
X509_VERIFY_PARAM_get0_name(const X509_VERIFY_PARAM * param)59772c33676SMaxim Ag X509_VERIFY_PARAM_get0_name(const X509_VERIFY_PARAM *param)
59872c33676SMaxim Ag {
59972c33676SMaxim Ag 	return param->name;
60072c33676SMaxim Ag }
60172c33676SMaxim Ag 
60272c33676SMaxim Ag static const X509_VERIFY_PARAM_ID _empty_id = { NULL };
60372c33676SMaxim Ag 
60472c33676SMaxim Ag #define vpm_empty_id (X509_VERIFY_PARAM_ID *)&_empty_id
60572c33676SMaxim Ag 
60672c33676SMaxim Ag /*
60772c33676SMaxim Ag  * Default verify parameters: these are used for various applications and can
60872c33676SMaxim Ag  * be overridden by the user specified table.
609f5b1c8a1SJohn Marino  */
610f5b1c8a1SJohn Marino 
611f5b1c8a1SJohn Marino static const X509_VERIFY_PARAM default_table[] = {
612f5b1c8a1SJohn Marino 	{
61372c33676SMaxim Ag 		.name = "default",
614*de0e0e4dSAntonio Huete Jimenez 		.flags = X509_V_FLAG_TRUSTED_FIRST,
61572c33676SMaxim Ag 		.depth = 100,
61672c33676SMaxim Ag 		.trust = 0,  /* XXX This is not the default trust value */
61772c33676SMaxim Ag 		.id = vpm_empty_id
618f5b1c8a1SJohn Marino 	},
619f5b1c8a1SJohn Marino 	{
62072c33676SMaxim Ag 		.name = "pkcs7",
62172c33676SMaxim Ag 		.purpose = X509_PURPOSE_SMIME_SIGN,
62272c33676SMaxim Ag 		.trust = X509_TRUST_EMAIL,
62372c33676SMaxim Ag 		.depth = -1,
62472c33676SMaxim Ag 		.id = vpm_empty_id
625f5b1c8a1SJohn Marino 	},
626f5b1c8a1SJohn Marino 	{
62772c33676SMaxim Ag 		.name = "smime_sign",
62872c33676SMaxim Ag 		.purpose = X509_PURPOSE_SMIME_SIGN,
62972c33676SMaxim Ag 		.trust = X509_TRUST_EMAIL,
63072c33676SMaxim Ag 		.depth =  -1,
63172c33676SMaxim Ag 		.id = vpm_empty_id
632f5b1c8a1SJohn Marino 	},
633f5b1c8a1SJohn Marino 	{
63472c33676SMaxim Ag 		.name = "ssl_client",
63572c33676SMaxim Ag 		.purpose = X509_PURPOSE_SSL_CLIENT,
63672c33676SMaxim Ag 		.trust = X509_TRUST_SSL_CLIENT,
63772c33676SMaxim Ag 		.depth = -1,
63872c33676SMaxim Ag 		.id = vpm_empty_id
639f5b1c8a1SJohn Marino 	},
640f5b1c8a1SJohn Marino 	{
64172c33676SMaxim Ag 		.name = "ssl_server",
64272c33676SMaxim Ag 		.purpose = X509_PURPOSE_SSL_SERVER,
64372c33676SMaxim Ag 		.trust = X509_TRUST_SSL_SERVER,
64472c33676SMaxim Ag 		.depth = -1,
64572c33676SMaxim Ag 		.id = vpm_empty_id
646f5b1c8a1SJohn Marino 	}
647f5b1c8a1SJohn Marino };
648f5b1c8a1SJohn Marino 
649f5b1c8a1SJohn Marino static STACK_OF(X509_VERIFY_PARAM) *param_table = NULL;
650f5b1c8a1SJohn Marino 
651f5b1c8a1SJohn Marino static int
param_cmp(const X509_VERIFY_PARAM * const * a,const X509_VERIFY_PARAM * const * b)652f5b1c8a1SJohn Marino param_cmp(const X509_VERIFY_PARAM * const *a,
653f5b1c8a1SJohn Marino     const X509_VERIFY_PARAM * const *b)
654f5b1c8a1SJohn Marino {
655f5b1c8a1SJohn Marino 	return strcmp((*a)->name, (*b)->name);
656f5b1c8a1SJohn Marino }
657f5b1c8a1SJohn Marino 
658f5b1c8a1SJohn Marino int
X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM * param)659f5b1c8a1SJohn Marino X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param)
660f5b1c8a1SJohn Marino {
661f5b1c8a1SJohn Marino 	X509_VERIFY_PARAM *ptmp;
662f5b1c8a1SJohn Marino 	if (!param_table) {
663f5b1c8a1SJohn Marino 		param_table = sk_X509_VERIFY_PARAM_new(param_cmp);
664f5b1c8a1SJohn Marino 		if (!param_table)
665f5b1c8a1SJohn Marino 			return 0;
666f5b1c8a1SJohn Marino 	} else {
66772c33676SMaxim Ag 		size_t idx;
66872c33676SMaxim Ag 
66972c33676SMaxim Ag 		if ((idx = sk_X509_VERIFY_PARAM_find(param_table, param))
67072c33676SMaxim Ag 		    != -1) {
67172c33676SMaxim Ag 			ptmp = sk_X509_VERIFY_PARAM_value(param_table,
67272c33676SMaxim Ag 			    idx);
673f5b1c8a1SJohn Marino 			X509_VERIFY_PARAM_free(ptmp);
67472c33676SMaxim Ag 			(void)sk_X509_VERIFY_PARAM_delete(param_table,
67572c33676SMaxim Ag 			    idx);
676f5b1c8a1SJohn Marino 		}
677f5b1c8a1SJohn Marino 	}
678f5b1c8a1SJohn Marino 	if (!sk_X509_VERIFY_PARAM_push(param_table, param))
679f5b1c8a1SJohn Marino 		return 0;
680f5b1c8a1SJohn Marino 	return 1;
681f5b1c8a1SJohn Marino }
682f5b1c8a1SJohn Marino 
68372c33676SMaxim Ag int
X509_VERIFY_PARAM_get_count(void)68472c33676SMaxim Ag X509_VERIFY_PARAM_get_count(void)
685f5b1c8a1SJohn Marino {
68672c33676SMaxim Ag 	int num = sizeof(default_table) / sizeof(X509_VERIFY_PARAM);
68772c33676SMaxim Ag 	if (param_table)
68872c33676SMaxim Ag 		num += sk_X509_VERIFY_PARAM_num(param_table);
68972c33676SMaxim Ag 	return num;
69072c33676SMaxim Ag }
69172c33676SMaxim Ag 
692*de0e0e4dSAntonio Huete Jimenez const X509_VERIFY_PARAM *
X509_VERIFY_PARAM_get0(int id)693*de0e0e4dSAntonio Huete Jimenez X509_VERIFY_PARAM_get0(int id)
69472c33676SMaxim Ag {
69572c33676SMaxim Ag 	int num = sizeof(default_table) / sizeof(X509_VERIFY_PARAM);
69672c33676SMaxim Ag 	if (id < num)
69772c33676SMaxim Ag 		return default_table + id;
69872c33676SMaxim Ag 	return sk_X509_VERIFY_PARAM_value(param_table, id - num);
69972c33676SMaxim Ag }
70072c33676SMaxim Ag 
701*de0e0e4dSAntonio Huete Jimenez const X509_VERIFY_PARAM *
X509_VERIFY_PARAM_lookup(const char * name)702*de0e0e4dSAntonio Huete Jimenez X509_VERIFY_PARAM_lookup(const char *name)
70372c33676SMaxim Ag {
704f5b1c8a1SJohn Marino 	X509_VERIFY_PARAM pm;
70572c33676SMaxim Ag 	unsigned int i, limit;
706f5b1c8a1SJohn Marino 
707f5b1c8a1SJohn Marino 	pm.name = (char *)name;
708f5b1c8a1SJohn Marino 	if (param_table) {
70972c33676SMaxim Ag 		size_t idx;
71072c33676SMaxim Ag 		if ((idx = sk_X509_VERIFY_PARAM_find(param_table, &pm)) != -1)
711f5b1c8a1SJohn Marino 			return sk_X509_VERIFY_PARAM_value(param_table, idx);
712f5b1c8a1SJohn Marino 	}
71372c33676SMaxim Ag 
71472c33676SMaxim Ag 	limit = sizeof(default_table) / sizeof(X509_VERIFY_PARAM);
71572c33676SMaxim Ag 	for (i = 0; i < limit; i++) {
71672c33676SMaxim Ag 		if (strcmp(default_table[i].name, name) == 0) {
71772c33676SMaxim Ag 			return &default_table[i];
71872c33676SMaxim Ag 		}
71972c33676SMaxim Ag 	}
72072c33676SMaxim Ag 	return NULL;
721f5b1c8a1SJohn Marino }
722f5b1c8a1SJohn Marino 
723f5b1c8a1SJohn Marino void
X509_VERIFY_PARAM_table_cleanup(void)724f5b1c8a1SJohn Marino X509_VERIFY_PARAM_table_cleanup(void)
725f5b1c8a1SJohn Marino {
726f5b1c8a1SJohn Marino 	if (param_table)
727f5b1c8a1SJohn Marino 		sk_X509_VERIFY_PARAM_pop_free(param_table,
728f5b1c8a1SJohn Marino 		    X509_VERIFY_PARAM_free);
729f5b1c8a1SJohn Marino 	param_table = NULL;
730f5b1c8a1SJohn Marino }
731