1 /* $OpenBSD: ssl_rsa.c,v 1.16 2014/07/12 16:03:37 miod Exp $ */ 2 /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) 3 * All rights reserved. 4 * 5 * This package is an SSL implementation written 6 * by Eric Young (eay@cryptsoft.com). 7 * The implementation was written so as to conform with Netscapes SSL. 8 * 9 * This library is free for commercial and non-commercial use as long as 10 * the following conditions are aheared to. The following conditions 11 * apply to all code found in this distribution, be it the RC4, RSA, 12 * lhash, DES, etc., code; not just the SSL code. The SSL documentation 13 * included with this distribution is covered by the same copyright terms 14 * except that the holder is Tim Hudson (tjh@cryptsoft.com). 15 * 16 * Copyright remains Eric Young's, and as such any Copyright notices in 17 * the code are not to be removed. 18 * If this package is used in a product, Eric Young should be given attribution 19 * as the author of the parts of the library used. 20 * This can be in the form of a textual message at program startup or 21 * in documentation (online or textual) provided with the package. 22 * 23 * Redistribution and use in source and binary forms, with or without 24 * modification, are permitted provided that the following conditions 25 * are met: 26 * 1. Redistributions of source code must retain the copyright 27 * notice, this list of conditions and the following disclaimer. 28 * 2. Redistributions in binary form must reproduce the above copyright 29 * notice, this list of conditions and the following disclaimer in the 30 * documentation and/or other materials provided with the distribution. 31 * 3. All advertising materials mentioning features or use of this software 32 * must display the following acknowledgement: 33 * "This product includes cryptographic software written by 34 * Eric Young (eay@cryptsoft.com)" 35 * The word 'cryptographic' can be left out if the rouines from the library 36 * being used are not cryptographic related :-). 37 * 4. If you include any Windows specific code (or a derivative thereof) from 38 * the apps directory (application code) you must include an acknowledgement: 39 * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)" 40 * 41 * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND 42 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 43 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 44 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 45 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 46 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 47 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 48 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 49 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 50 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 51 * SUCH DAMAGE. 52 * 53 * The licence and distribution terms for any publically available version or 54 * derivative of this code cannot be changed. i.e. this code cannot simply be 55 * copied and put under another distribution licence 56 * [including the GNU Public Licence.] 57 */ 58 59 #include <stdio.h> 60 #include "ssl_locl.h" 61 #include <openssl/bio.h> 62 #include <openssl/objects.h> 63 #include <openssl/evp.h> 64 #include <openssl/x509.h> 65 #include <openssl/pem.h> 66 67 static int ssl_set_cert(CERT *c, X509 *x509); 68 static int ssl_set_pkey(CERT *c, EVP_PKEY *pkey); 69 int 70 SSL_use_certificate(SSL *ssl, X509 *x) 71 { 72 if (x == NULL) { 73 SSLerr(SSL_F_SSL_USE_CERTIFICATE, ERR_R_PASSED_NULL_PARAMETER); 74 return (0); 75 } 76 if (!ssl_cert_inst(&ssl->cert)) { 77 SSLerr(SSL_F_SSL_USE_CERTIFICATE, ERR_R_MALLOC_FAILURE); 78 return (0); 79 } 80 return (ssl_set_cert(ssl->cert, x)); 81 } 82 83 int 84 SSL_use_certificate_file(SSL *ssl, const char *file, int type) 85 { 86 int j; 87 BIO *in; 88 int ret = 0; 89 X509 *x = NULL; 90 91 in = BIO_new(BIO_s_file_internal()); 92 if (in == NULL) { 93 SSLerr(SSL_F_SSL_USE_CERTIFICATE_FILE, ERR_R_BUF_LIB); 94 goto end; 95 } 96 97 if (BIO_read_filename(in, file) <= 0) { 98 SSLerr(SSL_F_SSL_USE_CERTIFICATE_FILE, ERR_R_SYS_LIB); 99 goto end; 100 } 101 if (type == SSL_FILETYPE_ASN1) { 102 j = ERR_R_ASN1_LIB; 103 x = d2i_X509_bio(in, NULL); 104 } else if (type == SSL_FILETYPE_PEM) { 105 j = ERR_R_PEM_LIB; 106 x = PEM_read_bio_X509(in, NULL, 107 ssl->ctx->default_passwd_callback, 108 ssl->ctx->default_passwd_callback_userdata); 109 } else { 110 SSLerr(SSL_F_SSL_USE_CERTIFICATE_FILE, SSL_R_BAD_SSL_FILETYPE); 111 goto end; 112 } 113 114 if (x == NULL) { 115 SSLerr(SSL_F_SSL_USE_CERTIFICATE_FILE, j); 116 goto end; 117 } 118 119 ret = SSL_use_certificate(ssl, x); 120 end: 121 if (x != NULL) 122 X509_free(x); 123 BIO_free(in); 124 return (ret); 125 } 126 127 int 128 SSL_use_certificate_ASN1(SSL *ssl, const unsigned char *d, int len) 129 { 130 X509 *x; 131 int ret; 132 133 x = d2i_X509(NULL, &d,(long)len); 134 if (x == NULL) { 135 SSLerr(SSL_F_SSL_USE_CERTIFICATE_ASN1, ERR_R_ASN1_LIB); 136 return (0); 137 } 138 139 ret = SSL_use_certificate(ssl, x); 140 X509_free(x); 141 return (ret); 142 } 143 144 int 145 SSL_use_RSAPrivateKey(SSL *ssl, RSA *rsa) 146 { 147 EVP_PKEY *pkey; 148 int ret; 149 150 if (rsa == NULL) { 151 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY, ERR_R_PASSED_NULL_PARAMETER); 152 return (0); 153 } 154 if (!ssl_cert_inst(&ssl->cert)) { 155 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY, ERR_R_MALLOC_FAILURE); 156 return (0); 157 } 158 if ((pkey = EVP_PKEY_new()) == NULL) { 159 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY, ERR_R_EVP_LIB); 160 return (0); 161 } 162 163 RSA_up_ref(rsa); 164 EVP_PKEY_assign_RSA(pkey, rsa); 165 166 ret = ssl_set_pkey(ssl->cert, pkey); 167 EVP_PKEY_free(pkey); 168 return (ret); 169 } 170 171 static int 172 ssl_set_pkey(CERT *c, EVP_PKEY *pkey) 173 { 174 int i; 175 176 i = ssl_cert_type(NULL, pkey); 177 if (i < 0) { 178 SSLerr(SSL_F_SSL_SET_PKEY, SSL_R_UNKNOWN_CERTIFICATE_TYPE); 179 return (0); 180 } 181 182 if (c->pkeys[i].x509 != NULL) { 183 EVP_PKEY *pktmp; 184 pktmp = X509_get_pubkey(c->pkeys[i].x509); 185 EVP_PKEY_copy_parameters(pktmp, pkey); 186 EVP_PKEY_free(pktmp); 187 ERR_clear_error(); 188 189 /* 190 * Don't check the public/private key, this is mostly 191 * for smart cards. 192 */ 193 if ((pkey->type == EVP_PKEY_RSA) && 194 (RSA_flags(pkey->pkey.rsa) & RSA_METHOD_FLAG_NO_CHECK)) 195 ; 196 else 197 if (!X509_check_private_key(c->pkeys[i].x509, pkey)) { 198 X509_free(c->pkeys[i].x509); 199 c->pkeys[i].x509 = NULL; 200 return 0; 201 } 202 } 203 204 EVP_PKEY_free(c->pkeys[i].privatekey); 205 CRYPTO_add(&pkey->references, 1, CRYPTO_LOCK_EVP_PKEY); 206 c->pkeys[i].privatekey = pkey; 207 c->key = &(c->pkeys[i]); 208 209 c->valid = 0; 210 return (1); 211 } 212 213 int 214 SSL_use_RSAPrivateKey_file(SSL *ssl, const char *file, int type) 215 { 216 int j, ret = 0; 217 BIO *in; 218 RSA *rsa = NULL; 219 220 in = BIO_new(BIO_s_file_internal()); 221 if (in == NULL) { 222 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY_FILE, ERR_R_BUF_LIB); 223 goto end; 224 } 225 226 if (BIO_read_filename(in, file) <= 0) { 227 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY_FILE, ERR_R_SYS_LIB); 228 goto end; 229 } 230 if (type == SSL_FILETYPE_ASN1) { 231 j = ERR_R_ASN1_LIB; 232 rsa = d2i_RSAPrivateKey_bio(in, NULL); 233 } else if (type == SSL_FILETYPE_PEM) { 234 j = ERR_R_PEM_LIB; 235 rsa = PEM_read_bio_RSAPrivateKey(in, NULL, 236 ssl->ctx->default_passwd_callback, 237 ssl->ctx->default_passwd_callback_userdata); 238 } else { 239 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY_FILE, SSL_R_BAD_SSL_FILETYPE); 240 goto end; 241 } 242 if (rsa == NULL) { 243 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY_FILE, j); 244 goto end; 245 } 246 ret = SSL_use_RSAPrivateKey(ssl, rsa); 247 RSA_free(rsa); 248 end: 249 BIO_free(in); 250 return (ret); 251 } 252 253 int 254 SSL_use_RSAPrivateKey_ASN1(SSL *ssl, unsigned char *d, long len) 255 { 256 int ret; 257 const unsigned char *p; 258 RSA *rsa; 259 260 p = d; 261 if ((rsa = d2i_RSAPrivateKey(NULL, &p,(long)len)) == NULL) { 262 SSLerr(SSL_F_SSL_USE_RSAPRIVATEKEY_ASN1, ERR_R_ASN1_LIB); 263 return (0); 264 } 265 266 ret = SSL_use_RSAPrivateKey(ssl, rsa); 267 RSA_free(rsa); 268 return (ret); 269 } 270 271 int 272 SSL_use_PrivateKey(SSL *ssl, EVP_PKEY *pkey) 273 { 274 int ret; 275 276 if (pkey == NULL) { 277 SSLerr(SSL_F_SSL_USE_PRIVATEKEY, ERR_R_PASSED_NULL_PARAMETER); 278 return (0); 279 } 280 if (!ssl_cert_inst(&ssl->cert)) { 281 SSLerr(SSL_F_SSL_USE_PRIVATEKEY, ERR_R_MALLOC_FAILURE); 282 return (0); 283 } 284 ret = ssl_set_pkey(ssl->cert, pkey); 285 return (ret); 286 } 287 288 int 289 SSL_use_PrivateKey_file(SSL *ssl, const char *file, int type) 290 { 291 int j, ret = 0; 292 BIO *in; 293 EVP_PKEY *pkey = NULL; 294 295 in = BIO_new(BIO_s_file_internal()); 296 if (in == NULL) { 297 SSLerr(SSL_F_SSL_USE_PRIVATEKEY_FILE, ERR_R_BUF_LIB); 298 goto end; 299 } 300 301 if (BIO_read_filename(in, file) <= 0) { 302 SSLerr(SSL_F_SSL_USE_PRIVATEKEY_FILE, ERR_R_SYS_LIB); 303 goto end; 304 } 305 if (type == SSL_FILETYPE_PEM) { 306 j = ERR_R_PEM_LIB; 307 pkey = PEM_read_bio_PrivateKey(in, NULL, 308 ssl->ctx->default_passwd_callback, 309 ssl->ctx->default_passwd_callback_userdata); 310 } else if (type == SSL_FILETYPE_ASN1) { 311 j = ERR_R_ASN1_LIB; 312 pkey = d2i_PrivateKey_bio(in, NULL); 313 } else { 314 SSLerr(SSL_F_SSL_USE_PRIVATEKEY_FILE, SSL_R_BAD_SSL_FILETYPE); 315 goto end; 316 } 317 if (pkey == NULL) { 318 SSLerr(SSL_F_SSL_USE_PRIVATEKEY_FILE, j); 319 goto end; 320 } 321 ret = SSL_use_PrivateKey(ssl, pkey); 322 EVP_PKEY_free(pkey); 323 end: 324 BIO_free(in); 325 return (ret); 326 } 327 328 int 329 SSL_use_PrivateKey_ASN1(int type, SSL *ssl, const unsigned char *d, long len) 330 { 331 int ret; 332 const unsigned char *p; 333 EVP_PKEY *pkey; 334 335 p = d; 336 if ((pkey = d2i_PrivateKey(type, NULL, &p,(long)len)) == NULL) { 337 SSLerr(SSL_F_SSL_USE_PRIVATEKEY_ASN1, ERR_R_ASN1_LIB); 338 return (0); 339 } 340 341 ret = SSL_use_PrivateKey(ssl, pkey); 342 EVP_PKEY_free(pkey); 343 return (ret); 344 } 345 346 int 347 SSL_CTX_use_certificate(SSL_CTX *ctx, X509 *x) 348 { 349 if (x == NULL) { 350 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE, ERR_R_PASSED_NULL_PARAMETER); 351 return (0); 352 } 353 if (!ssl_cert_inst(&ctx->cert)) { 354 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE, ERR_R_MALLOC_FAILURE); 355 return (0); 356 } 357 return (ssl_set_cert(ctx->cert, x)); 358 } 359 360 static int 361 ssl_set_cert(CERT *c, X509 *x) 362 { 363 EVP_PKEY *pkey; 364 int i; 365 366 pkey = X509_get_pubkey(x); 367 if (pkey == NULL) { 368 SSLerr(SSL_F_SSL_SET_CERT, SSL_R_X509_LIB); 369 return (0); 370 } 371 372 i = ssl_cert_type(x, pkey); 373 if (i < 0) { 374 SSLerr(SSL_F_SSL_SET_CERT, SSL_R_UNKNOWN_CERTIFICATE_TYPE); 375 EVP_PKEY_free(pkey); 376 return (0); 377 } 378 379 if (c->pkeys[i].privatekey != NULL) { 380 EVP_PKEY_copy_parameters(pkey, c->pkeys[i].privatekey); 381 ERR_clear_error(); 382 383 /* 384 * Don't check the public/private key, this is mostly 385 * for smart cards. 386 */ 387 if ((c->pkeys[i].privatekey->type == EVP_PKEY_RSA) && 388 (RSA_flags(c->pkeys[i].privatekey->pkey.rsa) & 389 RSA_METHOD_FLAG_NO_CHECK)) 390 ; 391 else 392 if (!X509_check_private_key(x, c->pkeys[i].privatekey)) { 393 /* 394 * don't fail for a cert/key mismatch, just free 395 * current private key (when switching to a different 396 * cert & key, first this function should be used, 397 * then ssl_set_pkey 398 */ 399 EVP_PKEY_free(c->pkeys[i].privatekey); 400 c->pkeys[i].privatekey = NULL; 401 /* clear error queue */ 402 ERR_clear_error(); 403 } 404 } 405 406 EVP_PKEY_free(pkey); 407 408 if (c->pkeys[i].x509 != NULL) 409 X509_free(c->pkeys[i].x509); 410 CRYPTO_add(&x->references, 1, CRYPTO_LOCK_X509); 411 c->pkeys[i].x509 = x; 412 c->key = &(c->pkeys[i]); 413 414 c->valid = 0; 415 return (1); 416 } 417 418 int 419 SSL_CTX_use_certificate_file(SSL_CTX *ctx, const char *file, int type) 420 { 421 int j; 422 BIO *in; 423 int ret = 0; 424 X509 *x = NULL; 425 426 in = BIO_new(BIO_s_file_internal()); 427 if (in == NULL) { 428 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_FILE, ERR_R_BUF_LIB); 429 goto end; 430 } 431 432 if (BIO_read_filename(in, file) <= 0) { 433 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_FILE, ERR_R_SYS_LIB); 434 goto end; 435 } 436 if (type == SSL_FILETYPE_ASN1) { 437 j = ERR_R_ASN1_LIB; 438 x = d2i_X509_bio(in, NULL); 439 } else if (type == SSL_FILETYPE_PEM) { 440 j = ERR_R_PEM_LIB; 441 x = PEM_read_bio_X509(in, NULL, ctx->default_passwd_callback, 442 ctx->default_passwd_callback_userdata); 443 } else { 444 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_FILE, SSL_R_BAD_SSL_FILETYPE); 445 goto end; 446 } 447 448 if (x == NULL) { 449 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_FILE, j); 450 goto end; 451 } 452 453 ret = SSL_CTX_use_certificate(ctx, x); 454 end: 455 if (x != NULL) 456 X509_free(x); 457 BIO_free(in); 458 return (ret); 459 } 460 461 int 462 SSL_CTX_use_certificate_ASN1(SSL_CTX *ctx, int len, const unsigned char *d) 463 { 464 X509 *x; 465 int ret; 466 467 x = d2i_X509(NULL, &d,(long)len); 468 if (x == NULL) { 469 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_ASN1, ERR_R_ASN1_LIB); 470 return (0); 471 } 472 473 ret = SSL_CTX_use_certificate(ctx, x); 474 X509_free(x); 475 return (ret); 476 } 477 478 int 479 SSL_CTX_use_RSAPrivateKey(SSL_CTX *ctx, RSA *rsa) 480 { 481 int ret; 482 EVP_PKEY *pkey; 483 484 if (rsa == NULL) { 485 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY, ERR_R_PASSED_NULL_PARAMETER); 486 return (0); 487 } 488 if (!ssl_cert_inst(&ctx->cert)) { 489 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY, ERR_R_MALLOC_FAILURE); 490 return (0); 491 } 492 if ((pkey = EVP_PKEY_new()) == NULL) { 493 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY, ERR_R_EVP_LIB); 494 return (0); 495 } 496 497 RSA_up_ref(rsa); 498 EVP_PKEY_assign_RSA(pkey, rsa); 499 500 ret = ssl_set_pkey(ctx->cert, pkey); 501 EVP_PKEY_free(pkey); 502 return (ret); 503 } 504 505 int 506 SSL_CTX_use_RSAPrivateKey_file(SSL_CTX *ctx, const char *file, int type) 507 { 508 int j, ret = 0; 509 BIO *in; 510 RSA *rsa = NULL; 511 512 in = BIO_new(BIO_s_file_internal()); 513 if (in == NULL) { 514 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_FILE, ERR_R_BUF_LIB); 515 goto end; 516 } 517 518 if (BIO_read_filename(in, file) <= 0) { 519 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_FILE, ERR_R_SYS_LIB); 520 goto end; 521 } 522 if (type == SSL_FILETYPE_ASN1) { 523 j = ERR_R_ASN1_LIB; 524 rsa = d2i_RSAPrivateKey_bio(in, NULL); 525 } else if (type == SSL_FILETYPE_PEM) { 526 j = ERR_R_PEM_LIB; 527 rsa = PEM_read_bio_RSAPrivateKey(in, NULL, 528 ctx->default_passwd_callback, 529 ctx->default_passwd_callback_userdata); 530 } else { 531 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_FILE, SSL_R_BAD_SSL_FILETYPE); 532 goto end; 533 } 534 if (rsa == NULL) { 535 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_FILE, j); 536 goto end; 537 } 538 ret = SSL_CTX_use_RSAPrivateKey(ctx, rsa); 539 RSA_free(rsa); 540 end: 541 BIO_free(in); 542 return (ret); 543 } 544 545 int 546 SSL_CTX_use_RSAPrivateKey_ASN1(SSL_CTX *ctx, const unsigned char *d, long len) 547 { 548 int ret; 549 const unsigned char *p; 550 RSA *rsa; 551 552 p = d; 553 if ((rsa = d2i_RSAPrivateKey(NULL, &p,(long)len)) == NULL) { 554 SSLerr(SSL_F_SSL_CTX_USE_RSAPRIVATEKEY_ASN1, ERR_R_ASN1_LIB); 555 return (0); 556 } 557 558 ret = SSL_CTX_use_RSAPrivateKey(ctx, rsa); 559 RSA_free(rsa); 560 return (ret); 561 } 562 563 int 564 SSL_CTX_use_PrivateKey(SSL_CTX *ctx, EVP_PKEY *pkey) 565 { 566 if (pkey == NULL) { 567 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY, 568 ERR_R_PASSED_NULL_PARAMETER); 569 return (0); 570 } 571 if (!ssl_cert_inst(&ctx->cert)) { 572 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY, ERR_R_MALLOC_FAILURE); 573 return (0); 574 } 575 return (ssl_set_pkey(ctx->cert, pkey)); 576 } 577 578 int 579 SSL_CTX_use_PrivateKey_file(SSL_CTX *ctx, const char *file, int type) 580 { 581 int j, ret = 0; 582 BIO *in; 583 EVP_PKEY *pkey = NULL; 584 585 in = BIO_new(BIO_s_file_internal()); 586 if (in == NULL) { 587 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_BUF_LIB); 588 goto end; 589 } 590 591 if (BIO_read_filename(in, file) <= 0) { 592 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, ERR_R_SYS_LIB); 593 goto end; 594 } 595 if (type == SSL_FILETYPE_PEM) { 596 j = ERR_R_PEM_LIB; 597 pkey = PEM_read_bio_PrivateKey(in, NULL, 598 ctx->default_passwd_callback, 599 ctx->default_passwd_callback_userdata); 600 } else if (type == SSL_FILETYPE_ASN1) { 601 j = ERR_R_ASN1_LIB; 602 pkey = d2i_PrivateKey_bio(in, NULL); 603 } else { 604 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, 605 SSL_R_BAD_SSL_FILETYPE); 606 goto end; 607 } 608 if (pkey == NULL) { 609 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_FILE, j); 610 goto end; 611 } 612 ret = SSL_CTX_use_PrivateKey(ctx, pkey); 613 EVP_PKEY_free(pkey); 614 end: 615 BIO_free(in); 616 return (ret); 617 } 618 619 int 620 SSL_CTX_use_PrivateKey_ASN1(int type, SSL_CTX *ctx, const unsigned char *d, 621 long len) 622 { 623 int ret; 624 const unsigned char *p; 625 EVP_PKEY *pkey; 626 627 p = d; 628 if ((pkey = d2i_PrivateKey(type, NULL, &p,(long)len)) == NULL) { 629 SSLerr(SSL_F_SSL_CTX_USE_PRIVATEKEY_ASN1, ERR_R_ASN1_LIB); 630 return (0); 631 } 632 633 ret = SSL_CTX_use_PrivateKey(ctx, pkey); 634 EVP_PKEY_free(pkey); 635 return (ret); 636 } 637 638 639 /* 640 * Read a file that contains our certificate in "PEM" format, 641 * possibly followed by a sequence of CA certificates that should be 642 * sent to the peer in the Certificate message. 643 */ 644 int 645 SSL_CTX_use_certificate_chain_file(SSL_CTX *ctx, const char *file) 646 { 647 BIO *in; 648 int ret = 0; 649 X509 *x = NULL; 650 651 ERR_clear_error(); /* clear error stack for SSL_CTX_use_certificate() */ 652 653 in = BIO_new(BIO_s_file_internal()); 654 if (in == NULL) { 655 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_BUF_LIB); 656 goto end; 657 } 658 659 if (BIO_read_filename(in, file) <= 0) { 660 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_SYS_LIB); 661 goto end; 662 } 663 664 x = PEM_read_bio_X509_AUX(in, NULL, ctx->default_passwd_callback, 665 ctx->default_passwd_callback_userdata); 666 if (x == NULL) { 667 SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_PEM_LIB); 668 goto end; 669 } 670 671 ret = SSL_CTX_use_certificate(ctx, x); 672 673 if (ERR_peek_error() != 0) 674 ret = 0; 675 /* Key/certificate mismatch doesn't imply ret==0 ... */ 676 if (ret) { 677 /* 678 * If we could set up our certificate, now proceed to 679 * the CA certificates. 680 */ 681 X509 *ca; 682 int r; 683 unsigned long err; 684 685 if (ctx->extra_certs != NULL) { 686 sk_X509_pop_free(ctx->extra_certs, X509_free); 687 ctx->extra_certs = NULL; 688 } 689 690 while ((ca = PEM_read_bio_X509(in, NULL, 691 ctx->default_passwd_callback, 692 ctx->default_passwd_callback_userdata)) != NULL) { 693 r = SSL_CTX_add_extra_chain_cert(ctx, ca); 694 if (!r) { 695 X509_free(ca); 696 ret = 0; 697 goto end; 698 } 699 /* 700 * Note that we must not free r if it was successfully 701 * added to the chain (while we must free the main 702 * certificate, since its reference count is increased 703 * by SSL_CTX_use_certificate). 704 */ 705 } 706 707 /* When the while loop ends, it's usually just EOF. */ 708 err = ERR_peek_last_error(); 709 if (ERR_GET_LIB(err) == ERR_LIB_PEM && 710 ERR_GET_REASON(err) == PEM_R_NO_START_LINE) 711 ERR_clear_error(); 712 else 713 ret = 0; /* some real error */ 714 } 715 716 end: 717 if (x != NULL) 718 X509_free(x); 719 BIO_free(in); 720 return (ret); 721 } 722