diff options
| author | beck <> | 2016-11-05 20:14:59 +0000 |
|---|---|---|
| committer | beck <> | 2016-11-05 20:14:59 +0000 |
| commit | 006b3edc4e8b27fc4eac3f0cfb5e5493ea4beb93 (patch) | |
| tree | 53bfe8b60583155aa7efbd2eec5361c8d3415475 /src | |
| parent | ae7c4d6707d71c0b28088f305ce5e4d6cb960032 (diff) | |
| download | openbsd-006b3edc4e8b27fc4eac3f0cfb5e5493ea4beb93.tar.gz openbsd-006b3edc4e8b27fc4eac3f0cfb5e5493ea4beb93.tar.bz2 openbsd-006b3edc4e8b27fc4eac3f0cfb5e5493ea4beb93.zip | |
Part one of the alt chains changes, bring in newer modifications to
VERIFY_PARAMS - based on boringssl.
ok jsing@ miod@
Diffstat (limited to 'src')
| -rw-r--r-- | src/lib/libcrypto/x509/vpm_int.h | 70 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_vfy.h | 34 | ||||
| -rw-r--r-- | src/lib/libcrypto/x509/x509_vpm.c | 380 |
3 files changed, 411 insertions, 73 deletions
diff --git a/src/lib/libcrypto/x509/vpm_int.h b/src/lib/libcrypto/x509/vpm_int.h index e69de29bb2..3bd357bddd 100644 --- a/src/lib/libcrypto/x509/vpm_int.h +++ b/src/lib/libcrypto/x509/vpm_int.h | |||
| @@ -0,0 +1,70 @@ | |||
| 1 | /* $OpenBSD: vpm_int.h,v 1.2 2016/11/05 20:14:59 beck Exp $ */ | ||
| 2 | /* | ||
| 3 | * Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL project | ||
| 4 | * 2013. | ||
| 5 | */ | ||
| 6 | /* ==================================================================== | ||
| 7 | * Copyright (c) 2013 The OpenSSL Project. All rights reserved. | ||
| 8 | * | ||
| 9 | * Redistribution and use in source and binary forms, with or without | ||
| 10 | * modification, are permitted provided that the following conditions | ||
| 11 | * are met: | ||
| 12 | * | ||
| 13 | * 1. Redistributions of source code must retain the above copyright | ||
| 14 | * notice, this list of conditions and the following disclaimer. | ||
| 15 | * | ||
| 16 | * 2. Redistributions in binary form must reproduce the above copyright | ||
| 17 | * notice, this list of conditions and the following disclaimer in | ||
| 18 | * the documentation and/or other materials provided with the | ||
| 19 | * distribution. | ||
| 20 | * | ||
| 21 | * 3. All advertising materials mentioning features or use of this | ||
| 22 | * software must display the following acknowledgment: | ||
| 23 | * "This product includes software developed by the OpenSSL Project | ||
| 24 | * for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)" | ||
| 25 | * | ||
| 26 | * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to | ||
| 27 | * endorse or promote products derived from this software without | ||
| 28 | * prior written permission. For written permission, please contact | ||
| 29 | * licensing@OpenSSL.org. | ||
| 30 | * | ||
| 31 | * 5. Products derived from this software may not be called "OpenSSL" | ||
| 32 | * nor may "OpenSSL" appear in their names without prior written | ||
| 33 | * permission of the OpenSSL Project. | ||
| 34 | * | ||
| 35 | * 6. Redistributions of any form whatsoever must retain the following | ||
| 36 | * acknowledgment: | ||
| 37 | * "This product includes software developed by the OpenSSL Project | ||
| 38 | * for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)" | ||
| 39 | * | ||
| 40 | * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY | ||
| 41 | * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||
| 42 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR | ||
| 43 | * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR | ||
| 44 | * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, | ||
| 45 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT | ||
| 46 | * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | ||
| 47 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
| 48 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, | ||
| 49 | * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) | ||
| 50 | * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED | ||
| 51 | * OF THE POSSIBILITY OF SUCH DAMAGE. | ||
| 52 | * ==================================================================== | ||
| 53 | * | ||
| 54 | * This product includes cryptographic software written by Eric Young | ||
| 55 | * (eay@cryptsoft.com). This product includes software written by Tim | ||
| 56 | * Hudson (tjh@cryptsoft.com). | ||
| 57 | * | ||
| 58 | */ | ||
| 59 | |||
| 60 | /* internal only structure to hold additional X509_VERIFY_PARAM data */ | ||
| 61 | |||
| 62 | struct X509_VERIFY_PARAM_ID_st { | ||
| 63 | STACK_OF(OPENSSL_STRING) *hosts; /* Set of acceptable names */ | ||
| 64 | unsigned int hostflags; /* Flags to control matching features */ | ||
| 65 | char *peername; /* Matching hostname in peer certificate */ | ||
| 66 | char *email; /* If not NULL email address to match */ | ||
| 67 | size_t emaillen; | ||
| 68 | unsigned char *ip; /* If not NULL IP address to match */ | ||
| 69 | size_t iplen; /* Length of IP address */ | ||
| 70 | }; | ||
diff --git a/src/lib/libcrypto/x509/x509_vfy.h b/src/lib/libcrypto/x509/x509_vfy.h index e3a1db2407..4b81e8a2cd 100644 --- a/src/lib/libcrypto/x509/x509_vfy.h +++ b/src/lib/libcrypto/x509/x509_vfy.h | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: x509_vfy.h,v 1.16 2015/09/14 16:13:39 jsing Exp $ */ | 1 | /* $OpenBSD: x509_vfy.h,v 1.17 2016/11/05 20:14:59 beck Exp $ */ |
| 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
| 3 | * All rights reserved. | 3 | * All rights reserved. |
| 4 | * | 4 | * |
| @@ -147,6 +147,8 @@ typedef struct x509_lookup_method_st | |||
| 147 | X509_OBJECT *ret); | 147 | X509_OBJECT *ret); |
| 148 | } X509_LOOKUP_METHOD; | 148 | } X509_LOOKUP_METHOD; |
| 149 | 149 | ||
| 150 | typedef struct X509_VERIFY_PARAM_ID_st X509_VERIFY_PARAM_ID; | ||
| 151 | |||
| 150 | /* This structure hold all parameters associated with a verify operation | 152 | /* This structure hold all parameters associated with a verify operation |
| 151 | * by including an X509_VERIFY_PARAM structure in related structures the | 153 | * by including an X509_VERIFY_PARAM structure in related structures the |
| 152 | * parameters used can be customized | 154 | * parameters used can be customized |
| @@ -162,7 +164,8 @@ typedef struct X509_VERIFY_PARAM_st | |||
| 162 | int trust; /* trust setting to check */ | 164 | int trust; /* trust setting to check */ |
| 163 | int depth; /* Verify depth */ | 165 | int depth; /* Verify depth */ |
| 164 | STACK_OF(ASN1_OBJECT) *policies; /* Permissible policies */ | 166 | STACK_OF(ASN1_OBJECT) *policies; /* Permissible policies */ |
| 165 | } X509_VERIFY_PARAM; | 167 | X509_VERIFY_PARAM_ID *id; /* opaque ID data */ |
| 168 | } X509_VERIFY_PARAM; | ||
| 166 | 169 | ||
| 167 | DECLARE_STACK_OF(X509_VERIFY_PARAM) | 170 | DECLARE_STACK_OF(X509_VERIFY_PARAM) |
| 168 | 171 | ||
| @@ -288,8 +291,7 @@ void X509_STORE_CTX_set_depth(X509_STORE_CTX *ctx, int depth); | |||
| 288 | (long)(type),NULL) | 291 | (long)(type),NULL) |
| 289 | 292 | ||
| 290 | #define X509_V_OK 0 | 293 | #define X509_V_OK 0 |
| 291 | /* illegal error (for uninitialized values, to avoid X509_V_OK): 1 */ | 294 | #define X509_V_ERR_UNSPECIFIED 1 |
| 292 | |||
| 293 | #define X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT 2 | 295 | #define X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT 2 |
| 294 | #define X509_V_ERR_UNABLE_TO_GET_CRL 3 | 296 | #define X509_V_ERR_UNABLE_TO_GET_CRL 3 |
| 295 | #define X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE 4 | 297 | #define X509_V_ERR_UNABLE_TO_DECRYPT_CERT_SIGNATURE 4 |
| @@ -351,6 +353,16 @@ void X509_STORE_CTX_set_depth(X509_STORE_CTX *ctx, int depth); | |||
| 351 | /* The application is not happy */ | 353 | /* The application is not happy */ |
| 352 | #define X509_V_ERR_APPLICATION_VERIFICATION 50 | 354 | #define X509_V_ERR_APPLICATION_VERIFICATION 50 |
| 353 | 355 | ||
| 356 | /* Host, email and IP check errors */ | ||
| 357 | #define X509_V_ERR_HOSTNAME_MISMATCH 62 | ||
| 358 | #define X509_V_ERR_EMAIL_MISMATCH 63 | ||
| 359 | #define X509_V_ERR_IP_ADDRESS_MISMATCH 64 | ||
| 360 | |||
| 361 | /* Caller error */ | ||
| 362 | #define X509_V_ERR_INVALID_CALL 65 | ||
| 363 | /* Issuer lookup error */ | ||
| 364 | #define X509_V_ERR_STORE_LOOKUP 66 | ||
| 365 | |||
| 354 | /* Certificate verify flags */ | 366 | /* Certificate verify flags */ |
| 355 | 367 | ||
| 356 | /* Send issuer+subject checks to verify_cb */ | 368 | /* Send issuer+subject checks to verify_cb */ |
| @@ -383,6 +395,16 @@ void X509_STORE_CTX_set_depth(X509_STORE_CTX *ctx, int depth); | |||
| 383 | #define X509_V_FLAG_USE_DELTAS 0x2000 | 395 | #define X509_V_FLAG_USE_DELTAS 0x2000 |
| 384 | /* Check selfsigned CA signature */ | 396 | /* Check selfsigned CA signature */ |
| 385 | #define X509_V_FLAG_CHECK_SS_SIGNATURE 0x4000 | 397 | #define X509_V_FLAG_CHECK_SS_SIGNATURE 0x4000 |
| 398 | /* Use trusted store first */ | ||
| 399 | #define X509_V_FLAG_TRUSTED_FIRST 0x8000 | ||
| 400 | /* Allow partial chains if at least one certificate is in trusted store */ | ||
| 401 | #define X509_V_FLAG_PARTIAL_CHAIN 0x80000 | ||
| 402 | |||
| 403 | /* If the initial chain is not trusted, do not attempt to build an alternative | ||
| 404 | * chain. Alternate chain checking was introduced in 1.0.2b. Setting this flag | ||
| 405 | * will force the behaviour to match that of previous versions. */ | ||
| 406 | #define X509_V_FLAG_NO_ALT_CHAINS 0x100000 | ||
| 407 | |||
| 386 | /* Do not check certificate or CRL validity against current time. */ | 408 | /* Do not check certificate or CRL validity against current time. */ |
| 387 | #define X509_V_FLAG_NO_CHECK_TIME 0x200000 | 409 | #define X509_V_FLAG_NO_CHECK_TIME 0x200000 |
| 388 | 410 | ||
| @@ -519,6 +541,10 @@ int X509_VERIFY_PARAM_add0_policy(X509_VERIFY_PARAM *param, | |||
| 519 | ASN1_OBJECT *policy); | 541 | ASN1_OBJECT *policy); |
| 520 | int X509_VERIFY_PARAM_set1_policies(X509_VERIFY_PARAM *param, | 542 | int X509_VERIFY_PARAM_set1_policies(X509_VERIFY_PARAM *param, |
| 521 | STACK_OF(ASN1_OBJECT) *policies); | 543 | STACK_OF(ASN1_OBJECT) *policies); |
| 544 | int X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM *param, const char *email, | ||
| 545 | size_t emaillen); | ||
| 546 | int X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM *param, const unsigned char *ip, | ||
| 547 | size_t iplen); | ||
| 522 | int X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM *param); | 548 | int X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM *param); |
| 523 | 549 | ||
| 524 | int X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param); | 550 | int X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param); |
diff --git a/src/lib/libcrypto/x509/x509_vpm.c b/src/lib/libcrypto/x509/x509_vpm.c index 8ec972050d..46375d798b 100644 --- a/src/lib/libcrypto/x509/x509_vpm.c +++ b/src/lib/libcrypto/x509/x509_vpm.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: x509_vpm.c,v 1.11 2014/09/29 04:16:49 miod Exp $ */ | 1 | /* $OpenBSD: x509_vpm.c,v 1.12 2016/11/05 20:14:59 beck Exp $ */ |
| 2 | /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL | 2 | /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL |
| 3 | * project 2004. | 3 | * project 2004. |
| 4 | */ | 4 | */ |
| @@ -62,14 +62,108 @@ | |||
| 62 | #include <openssl/buffer.h> | 62 | #include <openssl/buffer.h> |
| 63 | #include <openssl/crypto.h> | 63 | #include <openssl/crypto.h> |
| 64 | #include <openssl/lhash.h> | 64 | #include <openssl/lhash.h> |
| 65 | #include <openssl/stack.h> | ||
| 65 | #include <openssl/x509.h> | 66 | #include <openssl/x509.h> |
| 66 | #include <openssl/x509v3.h> | 67 | #include <openssl/x509v3.h> |
| 67 | 68 | ||
| 69 | #include "vpm_int.h" | ||
| 70 | |||
| 68 | /* X509_VERIFY_PARAM functions */ | 71 | /* X509_VERIFY_PARAM functions */ |
| 69 | 72 | ||
| 73 | #define SET_HOST 0 | ||
| 74 | #define ADD_HOST 1 | ||
| 75 | |||
| 76 | static void | ||
| 77 | str_free(char *s) | ||
| 78 | { | ||
| 79 | free(s); | ||
| 80 | } | ||
| 81 | |||
| 82 | #define string_stack_free(sk) sk_OPENSSL_STRING_pop_free(sk, str_free) | ||
| 83 | |||
| 84 | |||
| 85 | /* | ||
| 86 | * Post 1.0.1 sk function "deep_copy". For the moment we simply make | ||
| 87 | * these take void * and use them directly without a glorious blob of | ||
| 88 | * obfuscating macros of dubious value in front of them. All this in | ||
| 89 | * preparation for a rototilling of safestack.h (likely inspired by | ||
| 90 | * this). | ||
| 91 | */ | ||
| 92 | static void * | ||
| 93 | sk_deep_copy(void *sk_void, void *copy_func_void, void *free_func_void) | ||
| 94 | { | ||
| 95 | _STACK *sk = sk_void; | ||
| 96 | void *(*copy_func)(void *) = copy_func_void; | ||
| 97 | void (*free_func)(void *) = copy_func_void; | ||
| 98 | _STACK *ret = sk_dup(sk); | ||
| 99 | |||
| 100 | if (ret == NULL) | ||
| 101 | return NULL; | ||
| 102 | |||
| 103 | size_t i; | ||
| 104 | for (i = 0; i < ret->num; i++) { | ||
| 105 | if (ret->data[i] == NULL) | ||
| 106 | continue; | ||
| 107 | ret->data[i] = copy_func(ret->data[i]); | ||
| 108 | if (ret->data[i] == NULL) { | ||
| 109 | size_t j; | ||
| 110 | for (j = 0; j < i; j++) { | ||
| 111 | if (ret->data[j] != NULL) | ||
| 112 | free_func(ret->data[j]); | ||
| 113 | } | ||
| 114 | sk_free(ret); | ||
| 115 | return NULL; | ||
| 116 | } | ||
| 117 | } | ||
| 118 | |||
| 119 | return ret; | ||
| 120 | } | ||
| 121 | |||
| 122 | static int | ||
| 123 | int_x509_param_set_hosts(X509_VERIFY_PARAM_ID *id, int mode, | ||
| 124 | const char *name, size_t namelen) | ||
| 125 | { | ||
| 126 | char *copy; | ||
| 127 | |||
| 128 | /* | ||
| 129 | * Refuse names with embedded NUL bytes. | ||
| 130 | * XXX: Do we need to push an error onto the error stack? | ||
| 131 | */ | ||
| 132 | if (name && memchr(name, '\0', namelen)) | ||
| 133 | return 0; | ||
| 134 | |||
| 135 | if (mode == SET_HOST && id->hosts) { | ||
| 136 | string_stack_free(id->hosts); | ||
| 137 | id->hosts = NULL; | ||
| 138 | } | ||
| 139 | if (name == NULL || namelen == 0) | ||
| 140 | return 1; | ||
| 141 | copy = strndup(name, namelen); | ||
| 142 | if (copy == NULL) | ||
| 143 | return 0; | ||
| 144 | |||
| 145 | if (id->hosts == NULL && | ||
| 146 | (id->hosts = sk_OPENSSL_STRING_new_null()) == NULL) { | ||
| 147 | free(copy); | ||
| 148 | return 0; | ||
| 149 | } | ||
| 150 | |||
| 151 | if (!sk_OPENSSL_STRING_push(id->hosts, copy)) { | ||
| 152 | free(copy); | ||
| 153 | if (sk_OPENSSL_STRING_num(id->hosts) == 0) { | ||
| 154 | sk_OPENSSL_STRING_free(id->hosts); | ||
| 155 | id->hosts = NULL; | ||
| 156 | } | ||
| 157 | return 0; | ||
| 158 | } | ||
| 159 | |||
| 160 | return 1; | ||
| 161 | } | ||
| 162 | |||
| 70 | static void | 163 | static void |
| 71 | x509_verify_param_zero(X509_VERIFY_PARAM *param) | 164 | x509_verify_param_zero(X509_VERIFY_PARAM *param) |
| 72 | { | 165 | { |
| 166 | X509_VERIFY_PARAM_ID *paramid; | ||
| 73 | if (!param) | 167 | if (!param) |
| 74 | return; | 168 | return; |
| 75 | param->name = NULL; | 169 | param->name = NULL; |
| @@ -83,14 +177,35 @@ x509_verify_param_zero(X509_VERIFY_PARAM *param) | |||
| 83 | sk_ASN1_OBJECT_pop_free(param->policies, ASN1_OBJECT_free); | 177 | sk_ASN1_OBJECT_pop_free(param->policies, ASN1_OBJECT_free); |
| 84 | param->policies = NULL; | 178 | param->policies = NULL; |
| 85 | } | 179 | } |
| 180 | paramid = param->id; | ||
| 181 | if (paramid->hosts) { | ||
| 182 | string_stack_free(paramid->hosts); | ||
| 183 | paramid->hosts = NULL; | ||
| 184 | } | ||
| 185 | free(paramid->peername); | ||
| 186 | paramid->peername = NULL; | ||
| 187 | free(paramid->email); | ||
| 188 | paramid->email = NULL; | ||
| 189 | paramid->emaillen = 0; | ||
| 190 | free(paramid->ip); | ||
| 191 | paramid->ip = NULL; | ||
| 192 | paramid->iplen = 0; | ||
| 86 | } | 193 | } |
| 87 | 194 | ||
| 88 | X509_VERIFY_PARAM * | 195 | X509_VERIFY_PARAM * |
| 89 | X509_VERIFY_PARAM_new(void) | 196 | X509_VERIFY_PARAM_new(void) |
| 90 | { | 197 | { |
| 91 | X509_VERIFY_PARAM *param; | 198 | X509_VERIFY_PARAM *param; |
| 92 | 199 | X509_VERIFY_PARAM_ID *paramid; | |
| 93 | param = calloc(1, sizeof(X509_VERIFY_PARAM)); | 200 | param = calloc(1, sizeof(X509_VERIFY_PARAM)); |
| 201 | if (param == NULL) | ||
| 202 | return NULL; | ||
| 203 | paramid = calloc (1, sizeof(X509_VERIFY_PARAM_ID)); | ||
| 204 | if (paramid == NULL) { | ||
| 205 | free(param); | ||
| 206 | return NULL; | ||
| 207 | } | ||
| 208 | param->id = paramid; | ||
| 94 | x509_verify_param_zero(param); | 209 | x509_verify_param_zero(param); |
| 95 | return param; | 210 | return param; |
| 96 | } | 211 | } |
| @@ -98,7 +213,10 @@ X509_VERIFY_PARAM_new(void) | |||
| 98 | void | 213 | void |
| 99 | X509_VERIFY_PARAM_free(X509_VERIFY_PARAM *param) | 214 | X509_VERIFY_PARAM_free(X509_VERIFY_PARAM *param) |
| 100 | { | 215 | { |
| 216 | if (param == NULL) | ||
| 217 | return; | ||
| 101 | x509_verify_param_zero(param); | 218 | x509_verify_param_zero(param); |
| 219 | free(param->id); | ||
| 102 | free(param); | 220 | free(param); |
| 103 | } | 221 | } |
| 104 | 222 | ||
| @@ -139,21 +257,27 @@ X509_VERIFY_PARAM_free(X509_VERIFY_PARAM *param) | |||
| 139 | (to_overwrite || \ | 257 | (to_overwrite || \ |
| 140 | ((src->field != def) && (to_default || (dest->field == def)))) | 258 | ((src->field != def) && (to_default || (dest->field == def)))) |
| 141 | 259 | ||
| 260 | /* As above but for ID fields */ | ||
| 261 | |||
| 262 | #define test_x509_verify_param_copy_id(idf, def) \ | ||
| 263 | test_x509_verify_param_copy(id->idf, def) | ||
| 264 | |||
| 142 | /* Macro to test and copy a field if necessary */ | 265 | /* Macro to test and copy a field if necessary */ |
| 143 | 266 | ||
| 144 | #define x509_verify_param_copy(field, def) \ | 267 | #define x509_verify_param_copy(field, def) \ |
| 145 | if (test_x509_verify_param_copy(field, def)) \ | 268 | if (test_x509_verify_param_copy(field, def)) \ |
| 146 | dest->field = src->field | 269 | dest->field = src->field |
| 147 | 270 | ||
| 148 | |||
| 149 | int | 271 | int |
| 150 | X509_VERIFY_PARAM_inherit(X509_VERIFY_PARAM *dest, const X509_VERIFY_PARAM *src) | 272 | X509_VERIFY_PARAM_inherit(X509_VERIFY_PARAM *dest, const X509_VERIFY_PARAM *src) |
| 151 | { | 273 | { |
| 152 | unsigned long inh_flags; | 274 | unsigned long inh_flags; |
| 153 | int to_default, to_overwrite; | 275 | int to_default, to_overwrite; |
| 276 | X509_VERIFY_PARAM_ID *id; | ||
| 154 | 277 | ||
| 155 | if (!src) | 278 | if (!src) |
| 156 | return 1; | 279 | return 1; |
| 280 | id = src->id; | ||
| 157 | inh_flags = dest->inh_flags | src->inh_flags; | 281 | inh_flags = dest->inh_flags | src->inh_flags; |
| 158 | 282 | ||
| 159 | if (inh_flags & X509_VP_FLAG_ONCE) | 283 | if (inh_flags & X509_VP_FLAG_ONCE) |
| @@ -194,6 +318,32 @@ X509_VERIFY_PARAM_inherit(X509_VERIFY_PARAM *dest, const X509_VERIFY_PARAM *src) | |||
| 194 | return 0; | 318 | return 0; |
| 195 | } | 319 | } |
| 196 | 320 | ||
| 321 | /* Copy the host flags if and only if we're copying the host list */ | ||
| 322 | if (test_x509_verify_param_copy_id(hosts, NULL)) { | ||
| 323 | if (dest->id->hosts) { | ||
| 324 | string_stack_free(dest->id->hosts); | ||
| 325 | dest->id->hosts = NULL; | ||
| 326 | } | ||
| 327 | if (id->hosts) { | ||
| 328 | dest->id->hosts = | ||
| 329 | sk_deep_copy(id->hosts, strdup, str_free); | ||
| 330 | if (dest->id->hosts == NULL) | ||
| 331 | return 0; | ||
| 332 | dest->id->hostflags = id->hostflags; | ||
| 333 | } | ||
| 334 | } | ||
| 335 | |||
| 336 | if (test_x509_verify_param_copy_id(email, NULL)) { | ||
| 337 | if (!X509_VERIFY_PARAM_set1_email(dest, id->email, | ||
| 338 | id->emaillen)) | ||
| 339 | return 0; | ||
| 340 | } | ||
| 341 | |||
| 342 | if (test_x509_verify_param_copy_id(ip, NULL)) { | ||
| 343 | if (!X509_VERIFY_PARAM_set1_ip(dest, id->ip, id->iplen)) | ||
| 344 | return 0; | ||
| 345 | } | ||
| 346 | |||
| 197 | return 1; | 347 | return 1; |
| 198 | } | 348 | } |
| 199 | 349 | ||
| @@ -209,6 +359,33 @@ X509_VERIFY_PARAM_set1(X509_VERIFY_PARAM *to, const X509_VERIFY_PARAM *from) | |||
| 209 | return ret; | 359 | return ret; |
| 210 | } | 360 | } |
| 211 | 361 | ||
| 362 | static int | ||
| 363 | int_x509_param_set1(char **pdest, size_t *pdestlen, const char *src, | ||
| 364 | size_t srclen) | ||
| 365 | { | ||
| 366 | char *tmp; | ||
| 367 | if (src) { | ||
| 368 | if (srclen == 0) { | ||
| 369 | if ((tmp = strdup(src)) == NULL) | ||
| 370 | return 0; | ||
| 371 | srclen = strlen(src); | ||
| 372 | } else { | ||
| 373 | if ((tmp = malloc(srclen)) == NULL) | ||
| 374 | return 0; | ||
| 375 | memcpy(tmp, src, srclen); | ||
| 376 | } | ||
| 377 | } else { | ||
| 378 | tmp = NULL; | ||
| 379 | srclen = 0; | ||
| 380 | } | ||
| 381 | if (*pdest) | ||
| 382 | free(*pdest); | ||
| 383 | *pdest = tmp; | ||
| 384 | if (pdestlen) | ||
| 385 | *pdestlen = srclen; | ||
| 386 | return 1; | ||
| 387 | } | ||
| 388 | |||
| 212 | int | 389 | int |
| 213 | X509_VERIFY_PARAM_set1_name(X509_VERIFY_PARAM *param, const char *name) | 390 | X509_VERIFY_PARAM_set1_name(X509_VERIFY_PARAM *param, const char *name) |
| 214 | { | 391 | { |
| @@ -318,82 +495,121 @@ X509_VERIFY_PARAM_set1_policies(X509_VERIFY_PARAM *param, | |||
| 318 | } | 495 | } |
| 319 | 496 | ||
| 320 | int | 497 | int |
| 498 | X509_VERIFY_PARAM_set1_host(X509_VERIFY_PARAM *param, | ||
| 499 | const char *name, size_t namelen) | ||
| 500 | { | ||
| 501 | return int_x509_param_set_hosts(param->id, SET_HOST, name, namelen); | ||
| 502 | } | ||
| 503 | |||
| 504 | int | ||
| 505 | X509_VERIFY_PARAM_add1_host(X509_VERIFY_PARAM *param, | ||
| 506 | const char *name, size_t namelen) | ||
| 507 | { | ||
| 508 | return int_x509_param_set_hosts(param->id, ADD_HOST, name, namelen); | ||
| 509 | } | ||
| 510 | |||
| 511 | void | ||
| 512 | X509_VERIFY_PARAM_set_hostflags(X509_VERIFY_PARAM *param, unsigned int flags) | ||
| 513 | { | ||
| 514 | param->id->hostflags = flags; | ||
| 515 | } | ||
| 516 | |||
| 517 | char * | ||
| 518 | X509_VERIFY_PARAM_get0_peername(X509_VERIFY_PARAM *param) | ||
| 519 | { | ||
| 520 | return param->id->peername; | ||
| 521 | } | ||
| 522 | |||
| 523 | int | ||
| 524 | X509_VERIFY_PARAM_set1_email(X509_VERIFY_PARAM *param, const char *email, | ||
| 525 | size_t emaillen) | ||
| 526 | { | ||
| 527 | return int_x509_param_set1(¶m->id->email, ¶m->id->emaillen, | ||
| 528 | email, emaillen); | ||
| 529 | } | ||
| 530 | |||
| 531 | int | ||
| 532 | X509_VERIFY_PARAM_set1_ip(X509_VERIFY_PARAM *param, const unsigned char *ip, | ||
| 533 | size_t iplen) | ||
| 534 | { | ||
| 535 | if (iplen != 0 && iplen != 4 && iplen != 16) | ||
| 536 | return 0; | ||
| 537 | return int_x509_param_set1((char **)¶m->id->ip, ¶m->id->iplen, | ||
| 538 | (char *)ip, iplen); | ||
| 539 | } | ||
| 540 | |||
| 541 | int | ||
| 542 | X509_VERIFY_PARAM_set1_ip_asc(X509_VERIFY_PARAM *param, const char *ipasc) | ||
| 543 | { | ||
| 544 | unsigned char ipout[16]; | ||
| 545 | size_t iplen; | ||
| 546 | |||
| 547 | iplen = (size_t)a2i_ipadd(ipout, ipasc); | ||
| 548 | if (iplen == 0) | ||
| 549 | return 0; | ||
| 550 | return X509_VERIFY_PARAM_set1_ip(param, ipout, iplen); | ||
| 551 | } | ||
| 552 | |||
| 553 | int | ||
| 321 | X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM *param) | 554 | X509_VERIFY_PARAM_get_depth(const X509_VERIFY_PARAM *param) |
| 322 | { | 555 | { |
| 323 | return param->depth; | 556 | return param->depth; |
| 324 | } | 557 | } |
| 325 | 558 | ||
| 326 | /* Default verify parameters: these are used for various | 559 | const char * |
| 327 | * applications and can be overridden by the user specified table. | 560 | X509_VERIFY_PARAM_get0_name(const X509_VERIFY_PARAM *param) |
| 328 | * NB: the 'name' field *must* be in alphabetical order because it | 561 | { |
| 329 | * will be searched using OBJ_search. | 562 | return param->name; |
| 563 | } | ||
| 564 | |||
| 565 | static const X509_VERIFY_PARAM_ID _empty_id = { NULL }; | ||
| 566 | |||
| 567 | #define vpm_empty_id (X509_VERIFY_PARAM_ID *)&_empty_id | ||
| 568 | |||
| 569 | /* | ||
| 570 | * Default verify parameters: these are used for various applications and can | ||
| 571 | * be overridden by the user specified table. | ||
| 330 | */ | 572 | */ |
| 331 | 573 | ||
| 332 | static const X509_VERIFY_PARAM default_table[] = { | 574 | static const X509_VERIFY_PARAM default_table[] = { |
| 333 | { | 575 | { |
| 334 | "default", /* X509 default parameters */ | 576 | .name = "default", |
| 335 | 0, /* Check time */ | 577 | .depth = 100, |
| 336 | 0, /* internal flags */ | 578 | .id = vpm_empty_id |
| 337 | 0, /* flags */ | ||
| 338 | 0, /* purpose */ | ||
| 339 | 0, /* trust */ | ||
| 340 | 100, /* depth */ | ||
| 341 | NULL /* policies */ | ||
| 342 | }, | 579 | }, |
| 343 | { | 580 | { |
| 344 | "pkcs7", /* S/MIME sign parameters */ | 581 | .name = "pkcs7", |
| 345 | 0, /* Check time */ | 582 | .purpose = X509_PURPOSE_SMIME_SIGN, |
| 346 | 0, /* internal flags */ | 583 | .trust = X509_TRUST_EMAIL, |
| 347 | 0, /* flags */ | 584 | .depth = -1, |
| 348 | X509_PURPOSE_SMIME_SIGN, /* purpose */ | 585 | .id = vpm_empty_id |
| 349 | X509_TRUST_EMAIL, /* trust */ | ||
| 350 | -1, /* depth */ | ||
| 351 | NULL /* policies */ | ||
| 352 | }, | 586 | }, |
| 353 | { | 587 | { |
| 354 | "smime_sign", /* S/MIME sign parameters */ | 588 | .name = "smime_sign", |
| 355 | 0, /* Check time */ | 589 | .purpose = X509_PURPOSE_SMIME_SIGN, |
| 356 | 0, /* internal flags */ | 590 | .trust = X509_TRUST_EMAIL, |
| 357 | 0, /* flags */ | 591 | .depth = -1, |
| 358 | X509_PURPOSE_SMIME_SIGN, /* purpose */ | 592 | .id = vpm_empty_id |
| 359 | X509_TRUST_EMAIL, /* trust */ | ||
| 360 | -1, /* depth */ | ||
| 361 | NULL /* policies */ | ||
| 362 | }, | 593 | }, |
| 363 | { | 594 | { |
| 364 | "ssl_client", /* SSL/TLS client parameters */ | 595 | .name = "ssl_client", |
| 365 | 0, /* Check time */ | 596 | .purpose = X509_PURPOSE_SSL_CLIENT, |
| 366 | 0, /* internal flags */ | 597 | .trust = X509_TRUST_SSL_CLIENT, |
| 367 | 0, /* flags */ | 598 | .depth = -1, |
| 368 | X509_PURPOSE_SSL_CLIENT, /* purpose */ | 599 | .id = vpm_empty_id |
| 369 | X509_TRUST_SSL_CLIENT, /* trust */ | ||
| 370 | -1, /* depth */ | ||
| 371 | NULL /* policies */ | ||
| 372 | }, | 600 | }, |
| 373 | { | 601 | { |
| 374 | "ssl_server", /* SSL/TLS server parameters */ | 602 | .name = "ssl_server", |
| 375 | 0, /* Check time */ | 603 | .purpose = X509_PURPOSE_SSL_SERVER, |
| 376 | 0, /* internal flags */ | 604 | .trust = X509_TRUST_SSL_SERVER, |
| 377 | 0, /* flags */ | 605 | .depth = -1, |
| 378 | X509_PURPOSE_SSL_SERVER, /* purpose */ | 606 | .id = vpm_empty_id |
| 379 | X509_TRUST_SSL_SERVER, /* trust */ | ||
| 380 | -1, /* depth */ | ||
| 381 | NULL /* policies */ | ||
| 382 | } | 607 | } |
| 383 | }; | 608 | }; |
| 384 | 609 | ||
| 385 | static STACK_OF(X509_VERIFY_PARAM) *param_table = NULL; | 610 | static STACK_OF(X509_VERIFY_PARAM) *param_table = NULL; |
| 386 | 611 | ||
| 387 | static int | 612 | static int |
| 388 | table_cmp(const X509_VERIFY_PARAM *a, const X509_VERIFY_PARAM *b) | ||
| 389 | { | ||
| 390 | return strcmp(a->name, b->name); | ||
| 391 | } | ||
| 392 | |||
| 393 | DECLARE_OBJ_BSEARCH_CMP_FN(X509_VERIFY_PARAM, X509_VERIFY_PARAM, table); | ||
| 394 | IMPLEMENT_OBJ_BSEARCH_CMP_FN(X509_VERIFY_PARAM, X509_VERIFY_PARAM, table); | ||
| 395 | |||
| 396 | static int | ||
| 397 | param_cmp(const X509_VERIFY_PARAM * const *a, | 613 | param_cmp(const X509_VERIFY_PARAM * const *a, |
| 398 | const X509_VERIFY_PARAM * const *b) | 614 | const X509_VERIFY_PARAM * const *b) |
| 399 | { | 615 | { |
| @@ -403,19 +619,21 @@ param_cmp(const X509_VERIFY_PARAM * const *a, | |||
| 403 | int | 619 | int |
| 404 | X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param) | 620 | X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param) |
| 405 | { | 621 | { |
| 406 | int idx; | ||
| 407 | X509_VERIFY_PARAM *ptmp; | 622 | X509_VERIFY_PARAM *ptmp; |
| 408 | |||
| 409 | if (!param_table) { | 623 | if (!param_table) { |
| 410 | param_table = sk_X509_VERIFY_PARAM_new(param_cmp); | 624 | param_table = sk_X509_VERIFY_PARAM_new(param_cmp); |
| 411 | if (!param_table) | 625 | if (!param_table) |
| 412 | return 0; | 626 | return 0; |
| 413 | } else { | 627 | } else { |
| 414 | idx = sk_X509_VERIFY_PARAM_find(param_table, param); | 628 | size_t idx; |
| 415 | if (idx != -1) { | 629 | |
| 416 | ptmp = sk_X509_VERIFY_PARAM_value(param_table, idx); | 630 | if ((idx = sk_X509_VERIFY_PARAM_find(param_table, param)) |
| 631 | != -1) { | ||
| 632 | ptmp = sk_X509_VERIFY_PARAM_value(param_table, | ||
| 633 | idx); | ||
| 417 | X509_VERIFY_PARAM_free(ptmp); | 634 | X509_VERIFY_PARAM_free(ptmp); |
| 418 | (void)sk_X509_VERIFY_PARAM_delete(param_table, idx); | 635 | (void)sk_X509_VERIFY_PARAM_delete(param_table, |
| 636 | idx); | ||
| 419 | } | 637 | } |
| 420 | } | 638 | } |
| 421 | if (!sk_X509_VERIFY_PARAM_push(param_table, param)) | 639 | if (!sk_X509_VERIFY_PARAM_push(param_table, param)) |
| @@ -423,20 +641,44 @@ X509_VERIFY_PARAM_add0_table(X509_VERIFY_PARAM *param) | |||
| 423 | return 1; | 641 | return 1; |
| 424 | } | 642 | } |
| 425 | 643 | ||
| 426 | const X509_VERIFY_PARAM * | 644 | int |
| 427 | X509_VERIFY_PARAM_lookup(const char *name) | 645 | X509_VERIFY_PARAM_get_count(void) |
| 646 | { | ||
| 647 | int num = sizeof(default_table) / sizeof(X509_VERIFY_PARAM); | ||
| 648 | if (param_table) | ||
| 649 | num += sk_X509_VERIFY_PARAM_num(param_table); | ||
| 650 | return num; | ||
| 651 | } | ||
| 652 | |||
| 653 | const | ||
| 654 | X509_VERIFY_PARAM *X509_VERIFY_PARAM_get0(int id) | ||
| 655 | { | ||
| 656 | int num = sizeof(default_table) / sizeof(X509_VERIFY_PARAM); | ||
| 657 | if (id < num) | ||
| 658 | return default_table + id; | ||
| 659 | return sk_X509_VERIFY_PARAM_value(param_table, id - num); | ||
| 660 | } | ||
| 661 | |||
| 662 | const | ||
| 663 | X509_VERIFY_PARAM *X509_VERIFY_PARAM_lookup(const char *name) | ||
| 428 | { | 664 | { |
| 429 | int idx; | ||
| 430 | X509_VERIFY_PARAM pm; | 665 | X509_VERIFY_PARAM pm; |
| 666 | unsigned int i, limit; | ||
| 431 | 667 | ||
| 432 | pm.name = (char *)name; | 668 | pm.name = (char *)name; |
| 433 | if (param_table) { | 669 | if (param_table) { |
| 434 | idx = sk_X509_VERIFY_PARAM_find(param_table, &pm); | 670 | size_t idx; |
| 435 | if (idx != -1) | 671 | if ((idx = sk_X509_VERIFY_PARAM_find(param_table, &pm)) != -1) |
| 436 | return sk_X509_VERIFY_PARAM_value(param_table, idx); | 672 | return sk_X509_VERIFY_PARAM_value(param_table, idx); |
| 437 | } | 673 | } |
| 438 | return OBJ_bsearch_table(&pm, default_table, | 674 | |
| 439 | sizeof(default_table)/sizeof(X509_VERIFY_PARAM)); | 675 | limit = sizeof(default_table) / sizeof(X509_VERIFY_PARAM); |
| 676 | for (i = 0; i < limit; i++) { | ||
| 677 | if (strcmp(default_table[i].name, name) == 0) { | ||
| 678 | return &default_table[i]; | ||
| 679 | } | ||
| 680 | } | ||
| 681 | return NULL; | ||
| 440 | } | 682 | } |
| 441 | 683 | ||
| 442 | void | 684 | void |
