1 /* 2 * Copyright 1995-2025 The OpenSSL Project Authors. All Rights Reserved. 3 * 4 * Licensed under the Apache License 2.0 (the "License"). You may not use 5 * this file except in compliance with the License. You can obtain a copy 6 * in the file LICENSE in the source distribution or at 7 * https://www.openssl.org/source/license.html 8 */ 9 10 #include <stdio.h> 11 #include "internal/cryptlib.h" 12 #include "internal/refcount.h" 13 #include <openssl/x509.h> 14 #include "crypto/x509.h" 15 #include <openssl/x509v3.h> 16 #include "x509_local.h" 17 18 X509_LOOKUP *X509_LOOKUP_new(X509_LOOKUP_METHOD *method) 19 { 20 X509_LOOKUP *ret = OPENSSL_zalloc(sizeof(*ret)); 21 22 if (ret == NULL) 23 return NULL; 24 25 ret->method = method; 26 if (method->new_item != NULL && method->new_item(ret) == 0) { 27 OPENSSL_free(ret); 28 return NULL; 29 } 30 return ret; 31 } 32 33 void X509_LOOKUP_free(X509_LOOKUP *ctx) 34 { 35 if (ctx == NULL) 36 return; 37 if ((ctx->method != NULL) && (ctx->method->free != NULL)) 38 (*ctx->method->free)(ctx); 39 OPENSSL_free(ctx); 40 } 41 42 int X509_STORE_lock(X509_STORE *xs) 43 { 44 return CRYPTO_THREAD_write_lock(xs->lock); 45 } 46 47 int ossl_x509_store_read_lock(X509_STORE *xs) 48 { 49 return CRYPTO_THREAD_read_lock(xs->lock); 50 } 51 52 int X509_STORE_unlock(X509_STORE *xs) 53 { 54 return CRYPTO_THREAD_unlock(xs->lock); 55 } 56 57 int X509_LOOKUP_init(X509_LOOKUP *ctx) 58 { 59 if (ctx->method == NULL) 60 return 0; 61 if (ctx->method->init != NULL) 62 return ctx->method->init(ctx); 63 else 64 return 1; 65 } 66 67 int X509_LOOKUP_shutdown(X509_LOOKUP *ctx) 68 { 69 if (ctx->method == NULL) 70 return 0; 71 if (ctx->method->shutdown != NULL) 72 return ctx->method->shutdown(ctx); 73 else 74 return 1; 75 } 76 77 int X509_LOOKUP_ctrl_ex(X509_LOOKUP *ctx, int cmd, const char *argc, long argl, 78 char **ret, OSSL_LIB_CTX *libctx, const char *propq) 79 { 80 if (ctx->method == NULL) 81 return -1; 82 if (ctx->method->ctrl_ex != NULL) 83 return ctx->method->ctrl_ex(ctx, cmd, argc, argl, ret, libctx, propq); 84 if (ctx->method->ctrl != NULL) 85 return ctx->method->ctrl(ctx, cmd, argc, argl, ret); 86 return 1; 87 } 88 89 int X509_LOOKUP_ctrl(X509_LOOKUP *ctx, int cmd, const char *argc, long argl, 90 char **ret) 91 { 92 return X509_LOOKUP_ctrl_ex(ctx, cmd, argc, argl, ret, NULL, NULL); 93 } 94 95 int X509_LOOKUP_by_subject_ex(X509_LOOKUP *ctx, X509_LOOKUP_TYPE type, 96 const X509_NAME *name, X509_OBJECT *ret, 97 OSSL_LIB_CTX *libctx, const char *propq) 98 { 99 if (ctx->skip 100 || ctx->method == NULL 101 || (ctx->method->get_by_subject == NULL 102 && ctx->method->get_by_subject_ex == NULL)) 103 return 0; 104 if (ctx->method->get_by_subject_ex != NULL) 105 return ctx->method->get_by_subject_ex(ctx, type, name, ret, libctx, 106 propq); 107 else 108 return ctx->method->get_by_subject(ctx, type, name, ret); 109 } 110 111 int X509_LOOKUP_by_subject(X509_LOOKUP *ctx, X509_LOOKUP_TYPE type, 112 const X509_NAME *name, X509_OBJECT *ret) 113 { 114 return X509_LOOKUP_by_subject_ex(ctx, type, name, ret, NULL, NULL); 115 } 116 117 int X509_LOOKUP_by_issuer_serial(X509_LOOKUP *ctx, X509_LOOKUP_TYPE type, 118 const X509_NAME *name, 119 const ASN1_INTEGER *serial, 120 X509_OBJECT *ret) 121 { 122 if ((ctx->method == NULL) || (ctx->method->get_by_issuer_serial == NULL)) 123 return 0; 124 return ctx->method->get_by_issuer_serial(ctx, type, name, serial, ret); 125 } 126 127 int X509_LOOKUP_by_fingerprint(X509_LOOKUP *ctx, X509_LOOKUP_TYPE type, 128 const unsigned char *bytes, int len, 129 X509_OBJECT *ret) 130 { 131 if ((ctx->method == NULL) || (ctx->method->get_by_fingerprint == NULL)) 132 return 0; 133 return ctx->method->get_by_fingerprint(ctx, type, bytes, len, ret); 134 } 135 136 int X509_LOOKUP_by_alias(X509_LOOKUP *ctx, X509_LOOKUP_TYPE type, 137 const char *str, int len, X509_OBJECT *ret) 138 { 139 if ((ctx->method == NULL) || (ctx->method->get_by_alias == NULL)) 140 return 0; 141 return ctx->method->get_by_alias(ctx, type, str, len, ret); 142 } 143 144 int X509_LOOKUP_set_method_data(X509_LOOKUP *ctx, void *data) 145 { 146 ctx->method_data = data; 147 return 1; 148 } 149 150 void *X509_LOOKUP_get_method_data(const X509_LOOKUP *ctx) 151 { 152 return ctx->method_data; 153 } 154 155 X509_STORE *X509_LOOKUP_get_store(const X509_LOOKUP *ctx) 156 { 157 return ctx->store_ctx; 158 } 159 160 static int x509_object_cmp(const X509_OBJECT *const *a, 161 const X509_OBJECT *const *b) 162 { 163 int ret; 164 165 ret = ((*a)->type - (*b)->type); 166 if (ret) 167 return ret; 168 switch ((*a)->type) { 169 case X509_LU_X509: 170 ret = X509_subject_name_cmp((*a)->data.x509, (*b)->data.x509); 171 break; 172 case X509_LU_CRL: 173 ret = X509_CRL_cmp((*a)->data.crl, (*b)->data.crl); 174 break; 175 case X509_LU_NONE: 176 /* abort(); */ 177 return 0; 178 } 179 return ret; 180 } 181 182 X509_STORE *X509_STORE_new(void) 183 { 184 X509_STORE *ret = OPENSSL_zalloc(sizeof(*ret)); 185 186 if (ret == NULL) 187 return NULL; 188 if ((ret->objs = sk_X509_OBJECT_new(x509_object_cmp)) == NULL) { 189 ERR_raise(ERR_LIB_X509, ERR_R_CRYPTO_LIB); 190 goto err; 191 } 192 ret->cache = 1; 193 if ((ret->get_cert_methods = sk_X509_LOOKUP_new_null()) == NULL) { 194 ERR_raise(ERR_LIB_X509, ERR_R_CRYPTO_LIB); 195 goto err; 196 } 197 198 if ((ret->param = X509_VERIFY_PARAM_new()) == NULL) { 199 ERR_raise(ERR_LIB_X509, ERR_R_X509_LIB); 200 goto err; 201 } 202 if (!CRYPTO_new_ex_data(CRYPTO_EX_INDEX_X509_STORE, ret, &ret->ex_data)) { 203 ERR_raise(ERR_LIB_X509, ERR_R_CRYPTO_LIB); 204 goto err; 205 } 206 207 ret->lock = CRYPTO_THREAD_lock_new(); 208 if (ret->lock == NULL) { 209 ERR_raise(ERR_LIB_X509, ERR_R_CRYPTO_LIB); 210 goto err; 211 } 212 213 if (!CRYPTO_NEW_REF(&ret->references, 1)) 214 goto err; 215 return ret; 216 217 err: 218 X509_VERIFY_PARAM_free(ret->param); 219 sk_X509_OBJECT_free(ret->objs); 220 sk_X509_LOOKUP_free(ret->get_cert_methods); 221 CRYPTO_THREAD_lock_free(ret->lock); 222 OPENSSL_free(ret); 223 return NULL; 224 } 225 226 void X509_STORE_free(X509_STORE *xs) 227 { 228 int i; 229 STACK_OF(X509_LOOKUP) *sk; 230 X509_LOOKUP *lu; 231 232 if (xs == NULL) 233 return; 234 CRYPTO_DOWN_REF(&xs->references, &i); 235 REF_PRINT_COUNT("X509_STORE", i, xs); 236 if (i > 0) 237 return; 238 REF_ASSERT_ISNT(i < 0); 239 240 sk = xs->get_cert_methods; 241 for (i = 0; i < sk_X509_LOOKUP_num(sk); i++) { 242 lu = sk_X509_LOOKUP_value(sk, i); 243 X509_LOOKUP_shutdown(lu); 244 X509_LOOKUP_free(lu); 245 } 246 sk_X509_LOOKUP_free(sk); 247 sk_X509_OBJECT_pop_free(xs->objs, X509_OBJECT_free); 248 249 CRYPTO_free_ex_data(CRYPTO_EX_INDEX_X509_STORE, xs, &xs->ex_data); 250 X509_VERIFY_PARAM_free(xs->param); 251 CRYPTO_THREAD_lock_free(xs->lock); 252 CRYPTO_FREE_REF(&xs->references); 253 OPENSSL_free(xs); 254 } 255 256 int X509_STORE_up_ref(X509_STORE *xs) 257 { 258 int i; 259 260 if (CRYPTO_UP_REF(&xs->references, &i) <= 0) 261 return 0; 262 263 REF_PRINT_COUNT("X509_STORE", i, xs); 264 REF_ASSERT_ISNT(i < 2); 265 return i > 1 ? 1 : 0; 266 } 267 268 X509_LOOKUP *X509_STORE_add_lookup(X509_STORE *xs, X509_LOOKUP_METHOD *m) 269 { 270 int i; 271 STACK_OF(X509_LOOKUP) *sk; 272 X509_LOOKUP *lu; 273 274 sk = xs->get_cert_methods; 275 for (i = 0; i < sk_X509_LOOKUP_num(sk); i++) { 276 lu = sk_X509_LOOKUP_value(sk, i); 277 if (m == lu->method) { 278 return lu; 279 } 280 } 281 /* a new one */ 282 lu = X509_LOOKUP_new(m); 283 if (lu == NULL) { 284 ERR_raise(ERR_LIB_X509, ERR_R_X509_LIB); 285 return NULL; 286 } 287 288 lu->store_ctx = xs; 289 if (sk_X509_LOOKUP_push(xs->get_cert_methods, lu)) 290 return lu; 291 /* sk_X509_LOOKUP_push() failed */ 292 ERR_raise(ERR_LIB_X509, ERR_R_CRYPTO_LIB); 293 X509_LOOKUP_free(lu); 294 return NULL; 295 } 296 297 /* Also fill the cache (ctx->store->objs) with all matching certificates. */ 298 X509_OBJECT *X509_STORE_CTX_get_obj_by_subject(X509_STORE_CTX *ctx, 299 X509_LOOKUP_TYPE type, 300 const X509_NAME *name) 301 { 302 X509_OBJECT *ret = X509_OBJECT_new(); 303 304 if (ret == NULL) 305 return NULL; 306 if (!X509_STORE_CTX_get_by_subject(ctx, type, name, ret)) { 307 X509_OBJECT_free(ret); 308 return NULL; 309 } 310 return ret; 311 } 312 313 /* 314 * May be called with |ret| == NULL just for the side effect of 315 * caching all certs matching the given subject DN in |ctx->store->objs|. 316 * Returns 1 if successful, 317 * 0 if not found or X509_LOOKUP_by_subject_ex() returns an error, 318 * -1 on failure 319 */ 320 int ossl_x509_store_ctx_get_by_subject(const X509_STORE_CTX *ctx, X509_LOOKUP_TYPE type, 321 const X509_NAME *name, X509_OBJECT *ret) 322 { 323 X509_STORE *store = ctx->store; 324 X509_LOOKUP *lu; 325 X509_OBJECT stmp, *tmp; 326 int i, j; 327 328 if (store == NULL) 329 return 0; 330 331 stmp.type = X509_LU_NONE; 332 stmp.data.x509 = NULL; 333 334 if (!ossl_x509_store_read_lock(store)) 335 return 0; 336 /* Should already be sorted...but just in case */ 337 if (!sk_X509_OBJECT_is_sorted(store->objs)) { 338 X509_STORE_unlock(store); 339 /* Take a write lock instead of a read lock */ 340 if (!X509_STORE_lock(store)) 341 return 0; 342 /* 343 * Another thread might have sorted it in the meantime. But if so, 344 * sk_X509_OBJECT_sort() exits early. 345 */ 346 sk_X509_OBJECT_sort(store->objs); 347 } 348 tmp = X509_OBJECT_retrieve_by_subject(store->objs, type, name); 349 X509_STORE_unlock(store); 350 351 if (tmp == NULL || type == X509_LU_CRL) { 352 for (i = 0; i < sk_X509_LOOKUP_num(store->get_cert_methods); i++) { 353 lu = sk_X509_LOOKUP_value(store->get_cert_methods, i); 354 if (lu->skip) 355 continue; 356 if (lu->method == NULL) 357 return -1; 358 j = X509_LOOKUP_by_subject_ex(lu, type, name, &stmp, 359 ctx->libctx, ctx->propq); 360 if (j != 0) { /* non-zero value is considered success here */ 361 tmp = &stmp; 362 break; 363 } 364 } 365 if (tmp == NULL) 366 return 0; 367 } 368 369 if (ret != NULL) { 370 if (!X509_OBJECT_up_ref_count(tmp)) 371 return -1; 372 ret->type = tmp->type; 373 ret->data = tmp->data; 374 } 375 return 1; 376 } 377 378 /* Also fill the cache |ctx->store->objs| with all matching certificates. */ 379 int X509_STORE_CTX_get_by_subject(const X509_STORE_CTX *ctx, 380 X509_LOOKUP_TYPE type, 381 const X509_NAME *name, X509_OBJECT *ret) 382 { 383 return ossl_x509_store_ctx_get_by_subject(ctx, type, name, ret) > 0; 384 } 385 386 static int x509_store_add(X509_STORE *store, void *x, int crl) 387 { 388 X509_OBJECT *obj; 389 int ret = 0, added = 0; 390 391 if (x == NULL) 392 return 0; 393 obj = X509_OBJECT_new(); 394 if (obj == NULL) 395 return 0; 396 397 if (crl) { 398 obj->type = X509_LU_CRL; 399 obj->data.crl = (X509_CRL *)x; 400 } else { 401 obj->type = X509_LU_X509; 402 obj->data.x509 = (X509 *)x; 403 } 404 if (!X509_OBJECT_up_ref_count(obj)) { 405 obj->type = X509_LU_NONE; 406 X509_OBJECT_free(obj); 407 return 0; 408 } 409 410 if (!X509_STORE_lock(store)) { 411 X509_OBJECT_free(obj); 412 return 0; 413 } 414 415 if (X509_OBJECT_retrieve_match(store->objs, obj)) { 416 ret = 1; 417 } else { 418 added = sk_X509_OBJECT_push(store->objs, obj); 419 ret = added != 0; 420 } 421 X509_STORE_unlock(store); 422 423 if (added == 0) /* obj not pushed */ 424 X509_OBJECT_free(obj); 425 426 return ret; 427 } 428 429 int X509_STORE_add_cert(X509_STORE *xs, X509 *x) 430 { 431 if (!x509_store_add(xs, x, 0)) { 432 ERR_raise(ERR_LIB_X509, ERR_R_X509_LIB); 433 return 0; 434 } 435 return 1; 436 } 437 438 int X509_STORE_add_crl(X509_STORE *xs, X509_CRL *x) 439 { 440 if (!x509_store_add(xs, x, 1)) { 441 ERR_raise(ERR_LIB_X509, ERR_R_X509_LIB); 442 return 0; 443 } 444 return 1; 445 } 446 447 int X509_OBJECT_up_ref_count(X509_OBJECT *a) 448 { 449 switch (a->type) { 450 case X509_LU_NONE: 451 break; 452 case X509_LU_X509: 453 return X509_up_ref(a->data.x509); 454 case X509_LU_CRL: 455 return X509_CRL_up_ref(a->data.crl); 456 } 457 return 1; 458 } 459 460 X509 *X509_OBJECT_get0_X509(const X509_OBJECT *a) 461 { 462 if (a == NULL || a->type != X509_LU_X509) 463 return NULL; 464 return a->data.x509; 465 } 466 467 X509_CRL *X509_OBJECT_get0_X509_CRL(const X509_OBJECT *a) 468 { 469 if (a == NULL || a->type != X509_LU_CRL) 470 return NULL; 471 return a->data.crl; 472 } 473 474 X509_LOOKUP_TYPE X509_OBJECT_get_type(const X509_OBJECT *a) 475 { 476 return a->type; 477 } 478 479 X509_OBJECT *X509_OBJECT_new(void) 480 { 481 X509_OBJECT *ret = OPENSSL_zalloc(sizeof(*ret)); 482 483 if (ret == NULL) 484 return NULL; 485 ret->type = X509_LU_NONE; 486 return ret; 487 } 488 489 static void x509_object_free_internal(X509_OBJECT *a) 490 { 491 if (a == NULL) 492 return; 493 switch (a->type) { 494 case X509_LU_NONE: 495 break; 496 case X509_LU_X509: 497 X509_free(a->data.x509); 498 break; 499 case X509_LU_CRL: 500 X509_CRL_free(a->data.crl); 501 break; 502 } 503 } 504 505 int X509_OBJECT_set1_X509(X509_OBJECT *a, X509 *obj) 506 { 507 if (a == NULL || !X509_up_ref(obj)) 508 return 0; 509 510 x509_object_free_internal(a); 511 a->type = X509_LU_X509; 512 a->data.x509 = obj; 513 return 1; 514 } 515 516 int X509_OBJECT_set1_X509_CRL(X509_OBJECT *a, X509_CRL *obj) 517 { 518 if (a == NULL || !X509_CRL_up_ref(obj)) 519 return 0; 520 521 x509_object_free_internal(a); 522 a->type = X509_LU_CRL; 523 a->data.crl = obj; 524 return 1; 525 } 526 527 void X509_OBJECT_free(X509_OBJECT *a) 528 { 529 x509_object_free_internal(a); 530 OPENSSL_free(a); 531 } 532 533 /* Returns -1 if not found, but also on error */ 534 static int x509_object_idx_cnt(STACK_OF(X509_OBJECT) *h, X509_LOOKUP_TYPE type, 535 const X509_NAME *name, int *pnmatch) 536 { 537 X509_OBJECT stmp; 538 X509 x509_s; 539 X509_CRL crl_s; 540 541 stmp.type = type; 542 switch (type) { 543 case X509_LU_X509: 544 stmp.data.x509 = &x509_s; 545 x509_s.cert_info.subject = (X509_NAME *)name; /* won't modify it */ 546 break; 547 case X509_LU_CRL: 548 stmp.data.crl = &crl_s; 549 crl_s.crl.issuer = (X509_NAME *)name; /* won't modify it */ 550 break; 551 case X509_LU_NONE: 552 default: 553 /* abort(); */ 554 return -1; 555 } 556 557 /* Assumes h is locked for read if applicable */ 558 return sk_X509_OBJECT_find_all(h, &stmp, pnmatch); 559 } 560 561 /* Assumes h is locked for read if applicable */ 562 int X509_OBJECT_idx_by_subject(STACK_OF(X509_OBJECT) *h, X509_LOOKUP_TYPE type, 563 const X509_NAME *name) 564 { 565 return x509_object_idx_cnt(h, type, name, NULL); 566 } 567 568 /* Assumes h is locked for read if applicable */ 569 X509_OBJECT *X509_OBJECT_retrieve_by_subject(STACK_OF(X509_OBJECT) *h, 570 X509_LOOKUP_TYPE type, 571 const X509_NAME *name) 572 { 573 int idx = X509_OBJECT_idx_by_subject(h, type, name); 574 575 if (idx == -1) 576 return NULL; 577 return sk_X509_OBJECT_value(h, idx); 578 } 579 580 STACK_OF(X509_OBJECT) *X509_STORE_get0_objects(const X509_STORE *xs) 581 { 582 return xs->objs; 583 } 584 585 static X509_OBJECT *x509_object_dup(const X509_OBJECT *obj) 586 { 587 X509_OBJECT *ret = X509_OBJECT_new(); 588 if (ret == NULL) 589 return NULL; 590 591 ret->type = obj->type; 592 ret->data = obj->data; 593 X509_OBJECT_up_ref_count(ret); 594 return ret; 595 } 596 597 STACK_OF(X509_OBJECT) *X509_STORE_get1_objects(X509_STORE *store) 598 { 599 STACK_OF(X509_OBJECT) *objs; 600 601 if (store == NULL) { 602 ERR_raise(ERR_LIB_X509, ERR_R_PASSED_NULL_PARAMETER); 603 return NULL; 604 } 605 606 if (!ossl_x509_store_read_lock(store)) 607 return NULL; 608 609 objs = sk_X509_OBJECT_deep_copy(store->objs, x509_object_dup, 610 X509_OBJECT_free); 611 X509_STORE_unlock(store); 612 return objs; 613 } 614 615 STACK_OF(X509) *X509_STORE_get1_all_certs(X509_STORE *store) 616 { 617 STACK_OF(X509) *sk; 618 STACK_OF(X509_OBJECT) *objs; 619 int i; 620 621 if (store == NULL) { 622 ERR_raise(ERR_LIB_X509, ERR_R_PASSED_NULL_PARAMETER); 623 return NULL; 624 } 625 if ((sk = sk_X509_new_null()) == NULL) 626 return NULL; 627 if (!X509_STORE_lock(store)) 628 goto out_free; 629 630 sk_X509_OBJECT_sort(store->objs); 631 objs = X509_STORE_get0_objects(store); 632 for (i = 0; i < sk_X509_OBJECT_num(objs); i++) { 633 X509 *cert = X509_OBJECT_get0_X509(sk_X509_OBJECT_value(objs, i)); 634 635 if (cert != NULL 636 && !X509_add_cert(sk, cert, X509_ADD_FLAG_UP_REF)) 637 goto err; 638 } 639 X509_STORE_unlock(store); 640 return sk; 641 642 err: 643 X509_STORE_unlock(store); 644 out_free: 645 OSSL_STACK_OF_X509_free(sk); 646 return NULL; 647 } 648 649 /*- 650 * Collect from |ctx->store| all certs with subject matching |nm|. 651 * Returns NULL on internal/fatal error, empty stack if not found. 652 */ 653 STACK_OF(X509) *X509_STORE_CTX_get1_certs(X509_STORE_CTX *ctx, 654 const X509_NAME *nm) 655 { 656 int i, idx, cnt; 657 STACK_OF(X509) *sk = NULL; 658 X509 *x; 659 X509_OBJECT *obj; 660 X509_STORE *store = ctx->store; 661 662 if (store == NULL) 663 return sk_X509_new_null(); 664 665 if (!X509_STORE_lock(store)) 666 return NULL; 667 668 sk_X509_OBJECT_sort(store->objs); 669 idx = x509_object_idx_cnt(store->objs, X509_LU_X509, nm, &cnt); 670 if (idx < 0) { 671 /* 672 * Nothing found in cache: do lookup to possibly add new objects to 673 * cache 674 */ 675 X509_STORE_unlock(store); 676 i = ossl_x509_store_ctx_get_by_subject(ctx, X509_LU_X509, nm, NULL); 677 if (i <= 0) 678 return i < 0 ? NULL : sk_X509_new_null(); 679 if (!X509_STORE_lock(store)) 680 return NULL; 681 sk_X509_OBJECT_sort(store->objs); 682 idx = x509_object_idx_cnt(store->objs, X509_LU_X509, nm, &cnt); 683 } 684 685 sk = sk_X509_new_null(); 686 if (idx < 0 || sk == NULL) 687 goto end; 688 for (i = 0; i < cnt; i++, idx++) { 689 obj = sk_X509_OBJECT_value(store->objs, idx); 690 x = obj->data.x509; 691 if (!X509_add_cert(sk, x, X509_ADD_FLAG_UP_REF)) { 692 X509_STORE_unlock(store); 693 OSSL_STACK_OF_X509_free(sk); 694 return NULL; 695 } 696 } 697 end: 698 X509_STORE_unlock(store); 699 return sk; 700 } 701 702 /* Returns NULL on internal/fatal error, empty stack if not found */ 703 STACK_OF(X509_CRL) *X509_STORE_CTX_get1_crls(const X509_STORE_CTX *ctx, 704 const X509_NAME *nm) 705 { 706 int i = 1, idx, cnt; 707 STACK_OF(X509_CRL) *sk; 708 X509_CRL *x; 709 X509_OBJECT *obj; 710 X509_STORE *store = ctx->store; 711 712 /* Always do lookup to possibly add new CRLs to cache */ 713 i = ossl_x509_store_ctx_get_by_subject(ctx, X509_LU_CRL, nm, NULL); 714 if (i < 0) 715 return NULL; 716 sk = sk_X509_CRL_new_null(); 717 if (i == 0) 718 return sk; 719 if (!X509_STORE_lock(store)) { 720 sk_X509_CRL_free(sk); 721 return NULL; 722 } 723 sk_X509_OBJECT_sort(store->objs); 724 idx = x509_object_idx_cnt(store->objs, X509_LU_CRL, nm, &cnt); 725 if (idx < 0) { 726 X509_STORE_unlock(store); 727 return sk; 728 } 729 730 for (i = 0; i < cnt; i++, idx++) { 731 obj = sk_X509_OBJECT_value(store->objs, idx); 732 x = obj->data.crl; 733 if (!X509_CRL_up_ref(x)) { 734 X509_STORE_unlock(store); 735 sk_X509_CRL_pop_free(sk, X509_CRL_free); 736 return NULL; 737 } 738 if (!sk_X509_CRL_push(sk, x)) { 739 X509_STORE_unlock(store); 740 X509_CRL_free(x); 741 sk_X509_CRL_pop_free(sk, X509_CRL_free); 742 return NULL; 743 } 744 } 745 X509_STORE_unlock(store); 746 return sk; 747 } 748 749 X509_OBJECT *X509_OBJECT_retrieve_match(STACK_OF(X509_OBJECT) *h, 750 X509_OBJECT *x) 751 { 752 int idx, i, num; 753 X509_OBJECT *obj; 754 755 idx = sk_X509_OBJECT_find(h, x); 756 if (idx < 0) 757 return NULL; 758 if ((x->type != X509_LU_X509) && (x->type != X509_LU_CRL)) 759 return sk_X509_OBJECT_value(h, idx); 760 for (i = idx, num = sk_X509_OBJECT_num(h); i < num; i++) { 761 obj = sk_X509_OBJECT_value(h, i); 762 if (x509_object_cmp((const X509_OBJECT **)&obj, 763 (const X509_OBJECT **)&x)) 764 return NULL; 765 if (x->type == X509_LU_X509) { 766 if (!X509_cmp(obj->data.x509, x->data.x509)) 767 return obj; 768 } else if (x->type == X509_LU_CRL) { 769 if (X509_CRL_match(obj->data.crl, x->data.crl) == 0) 770 return obj; 771 } else { 772 return obj; 773 } 774 } 775 return NULL; 776 } 777 778 int X509_STORE_set_flags(X509_STORE *xs, unsigned long flags) 779 { 780 return X509_VERIFY_PARAM_set_flags(xs->param, flags); 781 } 782 783 int X509_STORE_set_depth(X509_STORE *xs, int depth) 784 { 785 X509_VERIFY_PARAM_set_depth(xs->param, depth); 786 return 1; 787 } 788 789 int X509_STORE_set_purpose(X509_STORE *xs, int purpose) 790 { 791 return X509_VERIFY_PARAM_set_purpose(xs->param, purpose); 792 } 793 794 int X509_STORE_set_trust(X509_STORE *xs, int trust) 795 { 796 return X509_VERIFY_PARAM_set_trust(xs->param, trust); 797 } 798 799 int X509_STORE_set1_param(X509_STORE *xs, const X509_VERIFY_PARAM *param) 800 { 801 return X509_VERIFY_PARAM_set1(xs->param, param); 802 } 803 804 X509_VERIFY_PARAM *X509_STORE_get0_param(const X509_STORE *xs) 805 { 806 return xs->param; 807 } 808 809 void X509_STORE_set_verify(X509_STORE *xs, X509_STORE_CTX_verify_fn verify) 810 { 811 xs->verify = verify; 812 } 813 814 X509_STORE_CTX_verify_fn X509_STORE_get_verify(const X509_STORE *xs) 815 { 816 return xs->verify; 817 } 818 819 void X509_STORE_set_verify_cb(X509_STORE *xs, 820 X509_STORE_CTX_verify_cb verify_cb) 821 { 822 xs->verify_cb = verify_cb; 823 } 824 825 X509_STORE_CTX_verify_cb X509_STORE_get_verify_cb(const X509_STORE *xs) 826 { 827 return xs->verify_cb; 828 } 829 830 void X509_STORE_set_get_issuer(X509_STORE *xs, 831 X509_STORE_CTX_get_issuer_fn get_issuer) 832 { 833 xs->get_issuer = get_issuer; 834 } 835 836 X509_STORE_CTX_get_issuer_fn X509_STORE_get_get_issuer(const X509_STORE *xs) 837 { 838 return xs->get_issuer; 839 } 840 841 void X509_STORE_set_check_issued(X509_STORE *xs, 842 X509_STORE_CTX_check_issued_fn check_issued) 843 { 844 xs->check_issued = check_issued; 845 } 846 847 X509_STORE_CTX_check_issued_fn X509_STORE_get_check_issued(const X509_STORE *xs) 848 { 849 return xs->check_issued; 850 } 851 852 void X509_STORE_set_check_revocation(X509_STORE *xs, 853 X509_STORE_CTX_check_revocation_fn cb) 854 { 855 xs->check_revocation = cb; 856 } 857 858 X509_STORE_CTX_check_revocation_fn X509_STORE_get_check_revocation(const X509_STORE *xs) 859 { 860 return xs->check_revocation; 861 } 862 863 void X509_STORE_set_get_crl(X509_STORE *xs, 864 X509_STORE_CTX_get_crl_fn get_crl) 865 { 866 xs->get_crl = get_crl; 867 } 868 869 X509_STORE_CTX_get_crl_fn X509_STORE_get_get_crl(const X509_STORE *xs) 870 { 871 return xs->get_crl; 872 } 873 874 void X509_STORE_set_check_crl(X509_STORE *xs, 875 X509_STORE_CTX_check_crl_fn check_crl) 876 { 877 xs->check_crl = check_crl; 878 } 879 880 X509_STORE_CTX_check_crl_fn X509_STORE_get_check_crl(const X509_STORE *xs) 881 { 882 return xs->check_crl; 883 } 884 885 void X509_STORE_set_cert_crl(X509_STORE *xs, 886 X509_STORE_CTX_cert_crl_fn cert_crl) 887 { 888 xs->cert_crl = cert_crl; 889 } 890 891 X509_STORE_CTX_cert_crl_fn X509_STORE_get_cert_crl(const X509_STORE *xs) 892 { 893 return xs->cert_crl; 894 } 895 896 void X509_STORE_set_check_policy(X509_STORE *xs, 897 X509_STORE_CTX_check_policy_fn check_policy) 898 { 899 xs->check_policy = check_policy; 900 } 901 902 X509_STORE_CTX_check_policy_fn X509_STORE_get_check_policy(const X509_STORE *xs) 903 { 904 return xs->check_policy; 905 } 906 907 void X509_STORE_set_lookup_certs(X509_STORE *xs, 908 X509_STORE_CTX_lookup_certs_fn lookup_certs) 909 { 910 xs->lookup_certs = lookup_certs; 911 } 912 913 X509_STORE_CTX_lookup_certs_fn X509_STORE_get_lookup_certs(const X509_STORE *xs) 914 { 915 return xs->lookup_certs; 916 } 917 918 void X509_STORE_set_lookup_crls(X509_STORE *xs, 919 X509_STORE_CTX_lookup_crls_fn lookup_crls) 920 { 921 xs->lookup_crls = lookup_crls; 922 } 923 924 X509_STORE_CTX_lookup_crls_fn X509_STORE_get_lookup_crls(const X509_STORE *xs) 925 { 926 return xs->lookup_crls; 927 } 928 929 void X509_STORE_set_cleanup(X509_STORE *xs, 930 X509_STORE_CTX_cleanup_fn cleanup) 931 { 932 xs->cleanup = cleanup; 933 } 934 935 X509_STORE_CTX_cleanup_fn X509_STORE_get_cleanup(const X509_STORE *xs) 936 { 937 return xs->cleanup; 938 } 939 940 int X509_STORE_set_ex_data(X509_STORE *xs, int idx, void *data) 941 { 942 return CRYPTO_set_ex_data(&xs->ex_data, idx, data); 943 } 944 945 void *X509_STORE_get_ex_data(const X509_STORE *xs, int idx) 946 { 947 return CRYPTO_get_ex_data(&xs->ex_data, idx); 948 } 949 950 X509_STORE *X509_STORE_CTX_get0_store(const X509_STORE_CTX *ctx) 951 { 952 return ctx->store; 953 } 954