apps.c revision 291721
1/* apps/apps.c */ 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 * Copyright (c) 1998-2001 The OpenSSL Project. All rights reserved. 60 * 61 * Redistribution and use in source and binary forms, with or without 62 * modification, are permitted provided that the following conditions 63 * are met: 64 * 65 * 1. Redistributions of source code must retain the above copyright 66 * notice, this list of conditions and the following disclaimer. 67 * 68 * 2. Redistributions in binary form must reproduce the above copyright 69 * notice, this list of conditions and the following disclaimer in 70 * the documentation and/or other materials provided with the 71 * distribution. 72 * 73 * 3. All advertising materials mentioning features or use of this 74 * software must display the following acknowledgment: 75 * "This product includes software developed by the OpenSSL Project 76 * for use in the OpenSSL Toolkit. (http://www.openssl.org/)" 77 * 78 * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to 79 * endorse or promote products derived from this software without 80 * prior written permission. For written permission, please contact 81 * openssl-core@openssl.org. 82 * 83 * 5. Products derived from this software may not be called "OpenSSL" 84 * nor may "OpenSSL" appear in their names without prior written 85 * permission of the OpenSSL Project. 86 * 87 * 6. Redistributions of any form whatsoever must retain the following 88 * acknowledgment: 89 * "This product includes software developed by the OpenSSL Project 90 * for use in the OpenSSL Toolkit (http://www.openssl.org/)" 91 * 92 * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY 93 * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 94 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 95 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR 96 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 97 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 98 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 99 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 100 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 101 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 102 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED 103 * OF THE POSSIBILITY OF SUCH DAMAGE. 104 * ==================================================================== 105 * 106 * This product includes cryptographic software written by Eric Young 107 * (eay@cryptsoft.com). This product includes software written by Tim 108 * Hudson (tjh@cryptsoft.com). 109 * 110 */ 111 112#if !defined(_POSIX_C_SOURCE) && defined(OPENSSL_SYS_VMS) 113/* 114 * On VMS, you need to define this to get the declaration of fileno(). The 115 * value 2 is to make sure no function defined in POSIX-2 is left undefined. 116 */ 117# define _POSIX_C_SOURCE 2 118#endif 119#include <stdio.h> 120#include <stdlib.h> 121#include <string.h> 122#include <sys/types.h> 123#include <ctype.h> 124#include <errno.h> 125#include <assert.h> 126#include <openssl/err.h> 127#include <openssl/x509.h> 128#include <openssl/x509v3.h> 129#include <openssl/pem.h> 130#include <openssl/pkcs12.h> 131#include <openssl/ui.h> 132#include <openssl/safestack.h> 133#ifndef OPENSSL_NO_ENGINE 134# include <openssl/engine.h> 135#endif 136#ifndef OPENSSL_NO_RSA 137# include <openssl/rsa.h> 138#endif 139#include <openssl/bn.h> 140#ifndef OPENSSL_NO_JPAKE 141# include <openssl/jpake.h> 142#endif 143 144#define NON_MAIN 145#include "apps.h" 146#undef NON_MAIN 147 148#ifdef _WIN32 149static int WIN32_rename(const char *from, const char *to); 150# define rename(from,to) WIN32_rename((from),(to)) 151#endif 152 153typedef struct { 154 const char *name; 155 unsigned long flag; 156 unsigned long mask; 157} NAME_EX_TBL; 158 159static UI_METHOD *ui_method = NULL; 160 161static int set_table_opts(unsigned long *flags, const char *arg, 162 const NAME_EX_TBL * in_tbl); 163static int set_multi_opts(unsigned long *flags, const char *arg, 164 const NAME_EX_TBL * in_tbl); 165 166#if !defined(OPENSSL_NO_RC4) && !defined(OPENSSL_NO_RSA) 167/* Looks like this stuff is worth moving into separate function */ 168static EVP_PKEY *load_netscape_key(BIO *err, BIO *key, const char *file, 169 const char *key_descrip, int format); 170#endif 171 172int app_init(long mesgwin); 173#ifdef undef /* never finished - probably never will be 174 * :-) */ 175int args_from_file(char *file, int *argc, char **argv[]) 176{ 177 FILE *fp; 178 int num, i; 179 unsigned int len; 180 static char *buf = NULL; 181 static char **arg = NULL; 182 char *p; 183 184 fp = fopen(file, "r"); 185 if (fp == NULL) 186 return (0); 187 188 if (fseek(fp, 0, SEEK_END) == 0) 189 len = ftell(fp), rewind(fp); 190 else 191 len = -1; 192 if (len <= 0) { 193 fclose(fp); 194 return (0); 195 } 196 197 *argc = 0; 198 *argv = NULL; 199 200 if (buf != NULL) 201 OPENSSL_free(buf); 202 buf = (char *)OPENSSL_malloc(len + 1); 203 if (buf == NULL) 204 return (0); 205 206 len = fread(buf, 1, len, fp); 207 if (len <= 1) 208 return (0); 209 buf[len] = '\0'; 210 211 i = 0; 212 for (p = buf; *p; p++) 213 if (*p == '\n') 214 i++; 215 if (arg != NULL) 216 OPENSSL_free(arg); 217 arg = (char **)OPENSSL_malloc(sizeof(char *) * (i * 2)); 218 219 *argv = arg; 220 num = 0; 221 p = buf; 222 for (;;) { 223 if (!*p) 224 break; 225 if (*p == '#') { /* comment line */ 226 while (*p && (*p != '\n')) 227 p++; 228 continue; 229 } 230 /* else we have a line */ 231 *(arg++) = p; 232 num++; 233 while (*p && ((*p != ' ') && (*p != '\t') && (*p != '\n'))) 234 p++; 235 if (!*p) 236 break; 237 if (*p == '\n') { 238 *(p++) = '\0'; 239 continue; 240 } 241 /* else it is a tab or space */ 242 p++; 243 while (*p && ((*p == ' ') || (*p == '\t') || (*p == '\n'))) 244 p++; 245 if (!*p) 246 break; 247 if (*p == '\n') { 248 p++; 249 continue; 250 } 251 *(arg++) = p++; 252 num++; 253 while (*p && (*p != '\n')) 254 p++; 255 if (!*p) 256 break; 257 /* else *p == '\n' */ 258 *(p++) = '\0'; 259 } 260 *argc = num; 261 return (1); 262} 263#endif 264 265int str2fmt(char *s) 266{ 267 if (s == NULL) 268 return FORMAT_UNDEF; 269 if ((*s == 'D') || (*s == 'd')) 270 return (FORMAT_ASN1); 271 else if ((*s == 'T') || (*s == 't')) 272 return (FORMAT_TEXT); 273 else if ((*s == 'N') || (*s == 'n')) 274 return (FORMAT_NETSCAPE); 275 else if ((*s == 'S') || (*s == 's')) 276 return (FORMAT_SMIME); 277 else if ((*s == 'M') || (*s == 'm')) 278 return (FORMAT_MSBLOB); 279 else if ((*s == '1') 280 || (strcmp(s, "PKCS12") == 0) || (strcmp(s, "pkcs12") == 0) 281 || (strcmp(s, "P12") == 0) || (strcmp(s, "p12") == 0)) 282 return (FORMAT_PKCS12); 283 else if ((*s == 'E') || (*s == 'e')) 284 return (FORMAT_ENGINE); 285 else if ((*s == 'P') || (*s == 'p')) { 286 if (s[1] == 'V' || s[1] == 'v') 287 return FORMAT_PVK; 288 else 289 return (FORMAT_PEM); 290 } else 291 return (FORMAT_UNDEF); 292} 293 294#if defined(OPENSSL_SYS_MSDOS) || defined(OPENSSL_SYS_WIN32) || defined(OPENSSL_SYS_WIN16) || defined(OPENSSL_SYS_NETWARE) 295void program_name(char *in, char *out, int size) 296{ 297 int i, n; 298 char *p = NULL; 299 300 n = strlen(in); 301 /* find the last '/', '\' or ':' */ 302 for (i = n - 1; i > 0; i--) { 303 if ((in[i] == '/') || (in[i] == '\\') || (in[i] == ':')) { 304 p = &(in[i + 1]); 305 break; 306 } 307 } 308 if (p == NULL) 309 p = in; 310 n = strlen(p); 311 312# if defined(OPENSSL_SYS_NETWARE) 313 /* strip off trailing .nlm if present. */ 314 if ((n > 4) && (p[n - 4] == '.') && 315 ((p[n - 3] == 'n') || (p[n - 3] == 'N')) && 316 ((p[n - 2] == 'l') || (p[n - 2] == 'L')) && 317 ((p[n - 1] == 'm') || (p[n - 1] == 'M'))) 318 n -= 4; 319# else 320 /* strip off trailing .exe if present. */ 321 if ((n > 4) && (p[n - 4] == '.') && 322 ((p[n - 3] == 'e') || (p[n - 3] == 'E')) && 323 ((p[n - 2] == 'x') || (p[n - 2] == 'X')) && 324 ((p[n - 1] == 'e') || (p[n - 1] == 'E'))) 325 n -= 4; 326# endif 327 328 if (n > size - 1) 329 n = size - 1; 330 331 for (i = 0; i < n; i++) { 332 if ((p[i] >= 'A') && (p[i] <= 'Z')) 333 out[i] = p[i] - 'A' + 'a'; 334 else 335 out[i] = p[i]; 336 } 337 out[n] = '\0'; 338} 339#else 340# ifdef OPENSSL_SYS_VMS 341void program_name(char *in, char *out, int size) 342{ 343 char *p = in, *q; 344 char *chars = ":]>"; 345 346 while (*chars != '\0') { 347 q = strrchr(p, *chars); 348 if (q > p) 349 p = q + 1; 350 chars++; 351 } 352 353 q = strrchr(p, '.'); 354 if (q == NULL) 355 q = p + strlen(p); 356 strncpy(out, p, size - 1); 357 if (q - p >= size) { 358 out[size - 1] = '\0'; 359 } else { 360 out[q - p] = '\0'; 361 } 362} 363# else 364void program_name(char *in, char *out, int size) 365{ 366 char *p; 367 368 p = strrchr(in, '/'); 369 if (p != NULL) 370 p++; 371 else 372 p = in; 373 BUF_strlcpy(out, p, size); 374} 375# endif 376#endif 377 378int chopup_args(ARGS *arg, char *buf, int *argc, char **argv[]) 379{ 380 int num, i; 381 char *p; 382 383 *argc = 0; 384 *argv = NULL; 385 386 i = 0; 387 if (arg->count == 0) { 388 arg->count = 20; 389 arg->data = (char **)OPENSSL_malloc(sizeof(char *) * arg->count); 390 if (arg->data == NULL) 391 return 0; 392 } 393 for (i = 0; i < arg->count; i++) 394 arg->data[i] = NULL; 395 396 num = 0; 397 p = buf; 398 for (;;) { 399 /* first scan over white space */ 400 if (!*p) 401 break; 402 while (*p && ((*p == ' ') || (*p == '\t') || (*p == '\n'))) 403 p++; 404 if (!*p) 405 break; 406 407 /* The start of something good :-) */ 408 if (num >= arg->count) { 409 char **tmp_p; 410 int tlen = arg->count + 20; 411 tmp_p = (char **)OPENSSL_realloc(arg->data, 412 sizeof(char *) * tlen); 413 if (tmp_p == NULL) 414 return 0; 415 arg->data = tmp_p; 416 arg->count = tlen; 417 /* initialize newly allocated data */ 418 for (i = num; i < arg->count; i++) 419 arg->data[i] = NULL; 420 } 421 arg->data[num++] = p; 422 423 /* now look for the end of this */ 424 if ((*p == '\'') || (*p == '\"')) { /* scan for closing quote */ 425 i = *(p++); 426 arg->data[num - 1]++; /* jump over quote */ 427 while (*p && (*p != i)) 428 p++; 429 *p = '\0'; 430 } else { 431 while (*p && ((*p != ' ') && (*p != '\t') && (*p != '\n'))) 432 p++; 433 434 if (*p == '\0') 435 p--; 436 else 437 *p = '\0'; 438 } 439 p++; 440 } 441 *argc = num; 442 *argv = arg->data; 443 return (1); 444} 445 446#ifndef APP_INIT 447int app_init(long mesgwin) 448{ 449 return (1); 450} 451#endif 452 453int dump_cert_text(BIO *out, X509 *x) 454{ 455 char *p; 456 457 p = X509_NAME_oneline(X509_get_subject_name(x), NULL, 0); 458 BIO_puts(out, "subject="); 459 BIO_puts(out, p); 460 OPENSSL_free(p); 461 462 p = X509_NAME_oneline(X509_get_issuer_name(x), NULL, 0); 463 BIO_puts(out, "\nissuer="); 464 BIO_puts(out, p); 465 BIO_puts(out, "\n"); 466 OPENSSL_free(p); 467 468 return 0; 469} 470 471static int ui_open(UI *ui) 472{ 473 return UI_method_get_opener(UI_OpenSSL())(ui); 474} 475 476static int ui_read(UI *ui, UI_STRING *uis) 477{ 478 if (UI_get_input_flags(uis) & UI_INPUT_FLAG_DEFAULT_PWD 479 && UI_get0_user_data(ui)) { 480 switch (UI_get_string_type(uis)) { 481 case UIT_PROMPT: 482 case UIT_VERIFY: 483 { 484 const char *password = 485 ((PW_CB_DATA *)UI_get0_user_data(ui))->password; 486 if (password && password[0] != '\0') { 487 UI_set_result(ui, uis, password); 488 return 1; 489 } 490 } 491 default: 492 break; 493 } 494 } 495 return UI_method_get_reader(UI_OpenSSL())(ui, uis); 496} 497 498static int ui_write(UI *ui, UI_STRING *uis) 499{ 500 if (UI_get_input_flags(uis) & UI_INPUT_FLAG_DEFAULT_PWD 501 && UI_get0_user_data(ui)) { 502 switch (UI_get_string_type(uis)) { 503 case UIT_PROMPT: 504 case UIT_VERIFY: 505 { 506 const char *password = 507 ((PW_CB_DATA *)UI_get0_user_data(ui))->password; 508 if (password && password[0] != '\0') 509 return 1; 510 } 511 default: 512 break; 513 } 514 } 515 return UI_method_get_writer(UI_OpenSSL())(ui, uis); 516} 517 518static int ui_close(UI *ui) 519{ 520 return UI_method_get_closer(UI_OpenSSL())(ui); 521} 522 523int setup_ui_method(void) 524{ 525 ui_method = UI_create_method("OpenSSL application user interface"); 526 UI_method_set_opener(ui_method, ui_open); 527 UI_method_set_reader(ui_method, ui_read); 528 UI_method_set_writer(ui_method, ui_write); 529 UI_method_set_closer(ui_method, ui_close); 530 return 0; 531} 532 533void destroy_ui_method(void) 534{ 535 if (ui_method) { 536 UI_destroy_method(ui_method); 537 ui_method = NULL; 538 } 539} 540 541int password_callback(char *buf, int bufsiz, int verify, PW_CB_DATA *cb_tmp) 542{ 543 UI *ui = NULL; 544 int res = 0; 545 const char *prompt_info = NULL; 546 const char *password = NULL; 547 PW_CB_DATA *cb_data = (PW_CB_DATA *)cb_tmp; 548 549 if (cb_data) { 550 if (cb_data->password) 551 password = cb_data->password; 552 if (cb_data->prompt_info) 553 prompt_info = cb_data->prompt_info; 554 } 555 556 if (password) { 557 res = strlen(password); 558 if (res > bufsiz) 559 res = bufsiz; 560 memcpy(buf, password, res); 561 return res; 562 } 563 564 ui = UI_new_method(ui_method); 565 if (ui) { 566 int ok = 0; 567 char *buff = NULL; 568 int ui_flags = 0; 569 char *prompt = NULL; 570 571 prompt = UI_construct_prompt(ui, "pass phrase", prompt_info); 572 if (!prompt) { 573 BIO_printf(bio_err, "Out of memory\n"); 574 UI_free(ui); 575 return 0; 576 } 577 578 ui_flags |= UI_INPUT_FLAG_DEFAULT_PWD; 579 UI_ctrl(ui, UI_CTRL_PRINT_ERRORS, 1, 0, 0); 580 581 if (ok >= 0) 582 ok = UI_add_input_string(ui, prompt, ui_flags, buf, 583 PW_MIN_LENGTH, bufsiz - 1); 584 if (ok >= 0 && verify) { 585 buff = (char *)OPENSSL_malloc(bufsiz); 586 if (!buff) { 587 BIO_printf(bio_err, "Out of memory\n"); 588 UI_free(ui); 589 OPENSSL_free(prompt); 590 return 0; 591 } 592 ok = UI_add_verify_string(ui, prompt, ui_flags, buff, 593 PW_MIN_LENGTH, bufsiz - 1, buf); 594 } 595 if (ok >= 0) 596 do { 597 ok = UI_process(ui); 598 } 599 while (ok < 0 && UI_ctrl(ui, UI_CTRL_IS_REDOABLE, 0, 0, 0)); 600 601 if (buff) { 602 OPENSSL_cleanse(buff, (unsigned int)bufsiz); 603 OPENSSL_free(buff); 604 } 605 606 if (ok >= 0) 607 res = strlen(buf); 608 if (ok == -1) { 609 BIO_printf(bio_err, "User interface error\n"); 610 ERR_print_errors(bio_err); 611 OPENSSL_cleanse(buf, (unsigned int)bufsiz); 612 res = 0; 613 } 614 if (ok == -2) { 615 BIO_printf(bio_err, "aborted!\n"); 616 OPENSSL_cleanse(buf, (unsigned int)bufsiz); 617 res = 0; 618 } 619 UI_free(ui); 620 OPENSSL_free(prompt); 621 } 622 return res; 623} 624 625static char *app_get_pass(BIO *err, char *arg, int keepbio); 626 627int app_passwd(BIO *err, char *arg1, char *arg2, char **pass1, char **pass2) 628{ 629 int same; 630 if (!arg2 || !arg1 || strcmp(arg1, arg2)) 631 same = 0; 632 else 633 same = 1; 634 if (arg1) { 635 *pass1 = app_get_pass(err, arg1, same); 636 if (!*pass1) 637 return 0; 638 } else if (pass1) 639 *pass1 = NULL; 640 if (arg2) { 641 *pass2 = app_get_pass(err, arg2, same ? 2 : 0); 642 if (!*pass2) 643 return 0; 644 } else if (pass2) 645 *pass2 = NULL; 646 return 1; 647} 648 649static char *app_get_pass(BIO *err, char *arg, int keepbio) 650{ 651 char *tmp, tpass[APP_PASS_LEN]; 652 static BIO *pwdbio = NULL; 653 int i; 654 if (!strncmp(arg, "pass:", 5)) 655 return BUF_strdup(arg + 5); 656 if (!strncmp(arg, "env:", 4)) { 657 tmp = getenv(arg + 4); 658 if (!tmp) { 659 BIO_printf(err, "Can't read environment variable %s\n", arg + 4); 660 return NULL; 661 } 662 return BUF_strdup(tmp); 663 } 664 if (!keepbio || !pwdbio) { 665 if (!strncmp(arg, "file:", 5)) { 666 pwdbio = BIO_new_file(arg + 5, "r"); 667 if (!pwdbio) { 668 BIO_printf(err, "Can't open file %s\n", arg + 5); 669 return NULL; 670 } 671#if !defined(_WIN32) 672 /* 673 * Under _WIN32, which covers even Win64 and CE, file 674 * descriptors referenced by BIO_s_fd are not inherited 675 * by child process and therefore below is not an option. 676 * It could have been an option if bss_fd.c was operating 677 * on real Windows descriptors, such as those obtained 678 * with CreateFile. 679 */ 680 } else if (!strncmp(arg, "fd:", 3)) { 681 BIO *btmp; 682 i = atoi(arg + 3); 683 if (i >= 0) 684 pwdbio = BIO_new_fd(i, BIO_NOCLOSE); 685 if ((i < 0) || !pwdbio) { 686 BIO_printf(err, "Can't access file descriptor %s\n", arg + 3); 687 return NULL; 688 } 689 /* 690 * Can't do BIO_gets on an fd BIO so add a buffering BIO 691 */ 692 btmp = BIO_new(BIO_f_buffer()); 693 pwdbio = BIO_push(btmp, pwdbio); 694#endif 695 } else if (!strcmp(arg, "stdin")) { 696 pwdbio = BIO_new_fp(stdin, BIO_NOCLOSE); 697 if (!pwdbio) { 698 BIO_printf(err, "Can't open BIO for stdin\n"); 699 return NULL; 700 } 701 } else { 702 BIO_printf(err, "Invalid password argument \"%s\"\n", arg); 703 return NULL; 704 } 705 } 706 i = BIO_gets(pwdbio, tpass, APP_PASS_LEN); 707 if (keepbio != 1) { 708 BIO_free_all(pwdbio); 709 pwdbio = NULL; 710 } 711 if (i <= 0) { 712 BIO_printf(err, "Error reading password from BIO\n"); 713 return NULL; 714 } 715 tmp = strchr(tpass, '\n'); 716 if (tmp) 717 *tmp = 0; 718 return BUF_strdup(tpass); 719} 720 721int add_oid_section(BIO *err, CONF *conf) 722{ 723 char *p; 724 STACK_OF(CONF_VALUE) *sktmp; 725 CONF_VALUE *cnf; 726 int i; 727 if (!(p = NCONF_get_string(conf, NULL, "oid_section"))) { 728 ERR_clear_error(); 729 return 1; 730 } 731 if (!(sktmp = NCONF_get_section(conf, p))) { 732 BIO_printf(err, "problem loading oid section %s\n", p); 733 return 0; 734 } 735 for (i = 0; i < sk_CONF_VALUE_num(sktmp); i++) { 736 cnf = sk_CONF_VALUE_value(sktmp, i); 737 if (OBJ_create(cnf->value, cnf->name, cnf->name) == NID_undef) { 738 BIO_printf(err, "problem creating object %s=%s\n", 739 cnf->name, cnf->value); 740 return 0; 741 } 742 } 743 return 1; 744} 745 746static int load_pkcs12(BIO *err, BIO *in, const char *desc, 747 pem_password_cb *pem_cb, void *cb_data, 748 EVP_PKEY **pkey, X509 **cert, STACK_OF(X509) **ca) 749{ 750 const char *pass; 751 char tpass[PEM_BUFSIZE]; 752 int len, ret = 0; 753 PKCS12 *p12; 754 p12 = d2i_PKCS12_bio(in, NULL); 755 if (p12 == NULL) { 756 BIO_printf(err, "Error loading PKCS12 file for %s\n", desc); 757 goto die; 758 } 759 /* See if an empty password will do */ 760 if (PKCS12_verify_mac(p12, "", 0) || PKCS12_verify_mac(p12, NULL, 0)) 761 pass = ""; 762 else { 763 if (!pem_cb) 764 pem_cb = (pem_password_cb *)password_callback; 765 len = pem_cb(tpass, PEM_BUFSIZE, 0, cb_data); 766 if (len < 0) { 767 BIO_printf(err, "Passpharse callback error for %s\n", desc); 768 goto die; 769 } 770 if (len < PEM_BUFSIZE) 771 tpass[len] = 0; 772 if (!PKCS12_verify_mac(p12, tpass, len)) { 773 BIO_printf(err, 774 "Mac verify error (wrong password?) in PKCS12 file for %s\n", 775 desc); 776 goto die; 777 } 778 pass = tpass; 779 } 780 ret = PKCS12_parse(p12, pass, pkey, cert, ca); 781 die: 782 if (p12) 783 PKCS12_free(p12); 784 return ret; 785} 786 787X509 *load_cert(BIO *err, const char *file, int format, 788 const char *pass, ENGINE *e, const char *cert_descrip) 789{ 790 X509 *x = NULL; 791 BIO *cert; 792 793 if ((cert = BIO_new(BIO_s_file())) == NULL) { 794 ERR_print_errors(err); 795 goto end; 796 } 797 798 if (file == NULL) { 799#ifdef _IONBF 800# ifndef OPENSSL_NO_SETVBUF_IONBF 801 setvbuf(stdin, NULL, _IONBF, 0); 802# endif /* ndef OPENSSL_NO_SETVBUF_IONBF */ 803#endif 804 BIO_set_fp(cert, stdin, BIO_NOCLOSE); 805 } else { 806 if (BIO_read_filename(cert, file) <= 0) { 807 BIO_printf(err, "Error opening %s %s\n", cert_descrip, file); 808 ERR_print_errors(err); 809 goto end; 810 } 811 } 812 813 if (format == FORMAT_ASN1) 814 x = d2i_X509_bio(cert, NULL); 815 else if (format == FORMAT_NETSCAPE) { 816 NETSCAPE_X509 *nx; 817 nx = ASN1_item_d2i_bio(ASN1_ITEM_rptr(NETSCAPE_X509), cert, NULL); 818 if (nx == NULL) 819 goto end; 820 821 if ((strncmp(NETSCAPE_CERT_HDR, (char *)nx->header->data, 822 nx->header->length) != 0)) { 823 NETSCAPE_X509_free(nx); 824 BIO_printf(err, "Error reading header on certificate\n"); 825 goto end; 826 } 827 x = nx->cert; 828 nx->cert = NULL; 829 NETSCAPE_X509_free(nx); 830 } else if (format == FORMAT_PEM) 831 x = PEM_read_bio_X509_AUX(cert, NULL, 832 (pem_password_cb *)password_callback, NULL); 833 else if (format == FORMAT_PKCS12) { 834 if (!load_pkcs12(err, cert, cert_descrip, NULL, NULL, NULL, &x, NULL)) 835 goto end; 836 } else { 837 BIO_printf(err, "bad input format specified for %s\n", cert_descrip); 838 goto end; 839 } 840 end: 841 if (x == NULL) { 842 BIO_printf(err, "unable to load certificate\n"); 843 ERR_print_errors(err); 844 } 845 if (cert != NULL) 846 BIO_free(cert); 847 return (x); 848} 849 850EVP_PKEY *load_key(BIO *err, const char *file, int format, int maybe_stdin, 851 const char *pass, ENGINE *e, const char *key_descrip) 852{ 853 BIO *key = NULL; 854 EVP_PKEY *pkey = NULL; 855 PW_CB_DATA cb_data; 856 857 cb_data.password = pass; 858 cb_data.prompt_info = file; 859 860 if (file == NULL && (!maybe_stdin || format == FORMAT_ENGINE)) { 861 BIO_printf(err, "no keyfile specified\n"); 862 goto end; 863 } 864#ifndef OPENSSL_NO_ENGINE 865 if (format == FORMAT_ENGINE) { 866 if (!e) 867 BIO_printf(err, "no engine specified\n"); 868 else { 869 pkey = ENGINE_load_private_key(e, file, ui_method, &cb_data); 870 if (!pkey) { 871 BIO_printf(err, "cannot load %s from engine\n", key_descrip); 872 ERR_print_errors(err); 873 } 874 } 875 goto end; 876 } 877#endif 878 key = BIO_new(BIO_s_file()); 879 if (key == NULL) { 880 ERR_print_errors(err); 881 goto end; 882 } 883 if (file == NULL && maybe_stdin) { 884#ifdef _IONBF 885# ifndef OPENSSL_NO_SETVBUF_IONBF 886 setvbuf(stdin, NULL, _IONBF, 0); 887# endif /* ndef OPENSSL_NO_SETVBUF_IONBF */ 888#endif 889 BIO_set_fp(key, stdin, BIO_NOCLOSE); 890 } else if (BIO_read_filename(key, file) <= 0) { 891 BIO_printf(err, "Error opening %s %s\n", key_descrip, file); 892 ERR_print_errors(err); 893 goto end; 894 } 895 if (format == FORMAT_ASN1) { 896 pkey = d2i_PrivateKey_bio(key, NULL); 897 } else if (format == FORMAT_PEM) { 898 pkey = PEM_read_bio_PrivateKey(key, NULL, 899 (pem_password_cb *)password_callback, 900 &cb_data); 901 } 902#if !defined(OPENSSL_NO_RC4) && !defined(OPENSSL_NO_RSA) 903 else if (format == FORMAT_NETSCAPE || format == FORMAT_IISSGC) 904 pkey = load_netscape_key(err, key, file, key_descrip, format); 905#endif 906 else if (format == FORMAT_PKCS12) { 907 if (!load_pkcs12(err, key, key_descrip, 908 (pem_password_cb *)password_callback, &cb_data, 909 &pkey, NULL, NULL)) 910 goto end; 911 } 912#if !defined(OPENSSL_NO_RSA) && !defined(OPENSSL_NO_DSA) && !defined (OPENSSL_NO_RC4) 913 else if (format == FORMAT_MSBLOB) 914 pkey = b2i_PrivateKey_bio(key); 915 else if (format == FORMAT_PVK) 916 pkey = b2i_PVK_bio(key, (pem_password_cb *)password_callback, 917 &cb_data); 918#endif 919 else { 920 BIO_printf(err, "bad input format specified for key file\n"); 921 goto end; 922 } 923 end: 924 if (key != NULL) 925 BIO_free(key); 926 if (pkey == NULL) { 927 BIO_printf(err, "unable to load %s\n", key_descrip); 928 ERR_print_errors(err); 929 } 930 return (pkey); 931} 932 933EVP_PKEY *load_pubkey(BIO *err, const char *file, int format, int maybe_stdin, 934 const char *pass, ENGINE *e, const char *key_descrip) 935{ 936 BIO *key = NULL; 937 EVP_PKEY *pkey = NULL; 938 PW_CB_DATA cb_data; 939 940 cb_data.password = pass; 941 cb_data.prompt_info = file; 942 943 if (file == NULL && (!maybe_stdin || format == FORMAT_ENGINE)) { 944 BIO_printf(err, "no keyfile specified\n"); 945 goto end; 946 } 947#ifndef OPENSSL_NO_ENGINE 948 if (format == FORMAT_ENGINE) { 949 if (!e) 950 BIO_printf(bio_err, "no engine specified\n"); 951 else 952 pkey = ENGINE_load_public_key(e, file, ui_method, &cb_data); 953 goto end; 954 } 955#endif 956 key = BIO_new(BIO_s_file()); 957 if (key == NULL) { 958 ERR_print_errors(err); 959 goto end; 960 } 961 if (file == NULL && maybe_stdin) { 962#ifdef _IONBF 963# ifndef OPENSSL_NO_SETVBUF_IONBF 964 setvbuf(stdin, NULL, _IONBF, 0); 965# endif /* ndef OPENSSL_NO_SETVBUF_IONBF */ 966#endif 967 BIO_set_fp(key, stdin, BIO_NOCLOSE); 968 } else if (BIO_read_filename(key, file) <= 0) { 969 BIO_printf(err, "Error opening %s %s\n", key_descrip, file); 970 ERR_print_errors(err); 971 goto end; 972 } 973 if (format == FORMAT_ASN1) { 974 pkey = d2i_PUBKEY_bio(key, NULL); 975 } 976#ifndef OPENSSL_NO_RSA 977 else if (format == FORMAT_ASN1RSA) { 978 RSA *rsa; 979 rsa = d2i_RSAPublicKey_bio(key, NULL); 980 if (rsa) { 981 pkey = EVP_PKEY_new(); 982 if (pkey) 983 EVP_PKEY_set1_RSA(pkey, rsa); 984 RSA_free(rsa); 985 } else 986 pkey = NULL; 987 } else if (format == FORMAT_PEMRSA) { 988 RSA *rsa; 989 rsa = PEM_read_bio_RSAPublicKey(key, NULL, 990 (pem_password_cb *)password_callback, 991 &cb_data); 992 if (rsa) { 993 pkey = EVP_PKEY_new(); 994 if (pkey) 995 EVP_PKEY_set1_RSA(pkey, rsa); 996 RSA_free(rsa); 997 } else 998 pkey = NULL; 999 } 1000#endif 1001 else if (format == FORMAT_PEM) { 1002 pkey = PEM_read_bio_PUBKEY(key, NULL, 1003 (pem_password_cb *)password_callback, 1004 &cb_data); 1005 } 1006#if !defined(OPENSSL_NO_RC4) && !defined(OPENSSL_NO_RSA) 1007 else if (format == FORMAT_NETSCAPE || format == FORMAT_IISSGC) 1008 pkey = load_netscape_key(err, key, file, key_descrip, format); 1009#endif 1010#if !defined(OPENSSL_NO_RSA) && !defined(OPENSSL_NO_DSA) 1011 else if (format == FORMAT_MSBLOB) 1012 pkey = b2i_PublicKey_bio(key); 1013#endif 1014 else { 1015 BIO_printf(err, "bad input format specified for key file\n"); 1016 goto end; 1017 } 1018 end: 1019 if (key != NULL) 1020 BIO_free(key); 1021 if (pkey == NULL) 1022 BIO_printf(err, "unable to load %s\n", key_descrip); 1023 return (pkey); 1024} 1025 1026#if !defined(OPENSSL_NO_RC4) && !defined(OPENSSL_NO_RSA) 1027static EVP_PKEY *load_netscape_key(BIO *err, BIO *key, const char *file, 1028 const char *key_descrip, int format) 1029{ 1030 EVP_PKEY *pkey; 1031 BUF_MEM *buf; 1032 RSA *rsa; 1033 const unsigned char *p; 1034 int size, i; 1035 1036 buf = BUF_MEM_new(); 1037 pkey = EVP_PKEY_new(); 1038 size = 0; 1039 if (buf == NULL || pkey == NULL) 1040 goto error; 1041 for (;;) { 1042 if (!BUF_MEM_grow_clean(buf, size + 1024 * 10)) 1043 goto error; 1044 i = BIO_read(key, &(buf->data[size]), 1024 * 10); 1045 size += i; 1046 if (i == 0) 1047 break; 1048 if (i < 0) { 1049 BIO_printf(err, "Error reading %s %s", key_descrip, file); 1050 goto error; 1051 } 1052 } 1053 p = (unsigned char *)buf->data; 1054 rsa = d2i_RSA_NET(NULL, &p, (long)size, NULL, 1055 (format == FORMAT_IISSGC ? 1 : 0)); 1056 if (rsa == NULL) 1057 goto error; 1058 BUF_MEM_free(buf); 1059 EVP_PKEY_set1_RSA(pkey, rsa); 1060 return pkey; 1061 error: 1062 BUF_MEM_free(buf); 1063 EVP_PKEY_free(pkey); 1064 return NULL; 1065} 1066#endif /* ndef OPENSSL_NO_RC4 */ 1067 1068static int load_certs_crls(BIO *err, const char *file, int format, 1069 const char *pass, ENGINE *e, const char *desc, 1070 STACK_OF(X509) **pcerts, 1071 STACK_OF(X509_CRL) **pcrls) 1072{ 1073 int i; 1074 BIO *bio; 1075 STACK_OF(X509_INFO) *xis = NULL; 1076 X509_INFO *xi; 1077 PW_CB_DATA cb_data; 1078 int rv = 0; 1079 1080 cb_data.password = pass; 1081 cb_data.prompt_info = file; 1082 1083 if (format != FORMAT_PEM) { 1084 BIO_printf(err, "bad input format specified for %s\n", desc); 1085 return 0; 1086 } 1087 1088 if (file == NULL) 1089 bio = BIO_new_fp(stdin, BIO_NOCLOSE); 1090 else 1091 bio = BIO_new_file(file, "r"); 1092 1093 if (bio == NULL) { 1094 BIO_printf(err, "Error opening %s %s\n", desc, file ? file : "stdin"); 1095 ERR_print_errors(err); 1096 return 0; 1097 } 1098 1099 xis = PEM_X509_INFO_read_bio(bio, NULL, 1100 (pem_password_cb *)password_callback, 1101 &cb_data); 1102 1103 BIO_free(bio); 1104 1105 if (pcerts) { 1106 *pcerts = sk_X509_new_null(); 1107 if (!*pcerts) 1108 goto end; 1109 } 1110 1111 if (pcrls) { 1112 *pcrls = sk_X509_CRL_new_null(); 1113 if (!*pcrls) 1114 goto end; 1115 } 1116 1117 for (i = 0; i < sk_X509_INFO_num(xis); i++) { 1118 xi = sk_X509_INFO_value(xis, i); 1119 if (xi->x509 && pcerts) { 1120 if (!sk_X509_push(*pcerts, xi->x509)) 1121 goto end; 1122 xi->x509 = NULL; 1123 } 1124 if (xi->crl && pcrls) { 1125 if (!sk_X509_CRL_push(*pcrls, xi->crl)) 1126 goto end; 1127 xi->crl = NULL; 1128 } 1129 } 1130 1131 if (pcerts && sk_X509_num(*pcerts) > 0) 1132 rv = 1; 1133 1134 if (pcrls && sk_X509_CRL_num(*pcrls) > 0) 1135 rv = 1; 1136 1137 end: 1138 1139 if (xis) 1140 sk_X509_INFO_pop_free(xis, X509_INFO_free); 1141 1142 if (rv == 0) { 1143 if (pcerts) { 1144 sk_X509_pop_free(*pcerts, X509_free); 1145 *pcerts = NULL; 1146 } 1147 if (pcrls) { 1148 sk_X509_CRL_pop_free(*pcrls, X509_CRL_free); 1149 *pcrls = NULL; 1150 } 1151 BIO_printf(err, "unable to load %s\n", 1152 pcerts ? "certificates" : "CRLs"); 1153 ERR_print_errors(err); 1154 } 1155 return rv; 1156} 1157 1158STACK_OF(X509) *load_certs(BIO *err, const char *file, int format, 1159 const char *pass, ENGINE *e, const char *desc) 1160{ 1161 STACK_OF(X509) *certs; 1162 if (!load_certs_crls(err, file, format, pass, e, desc, &certs, NULL)) 1163 return NULL; 1164 return certs; 1165} 1166 1167STACK_OF(X509_CRL) *load_crls(BIO *err, const char *file, int format, 1168 const char *pass, ENGINE *e, const char *desc) 1169{ 1170 STACK_OF(X509_CRL) *crls; 1171 if (!load_certs_crls(err, file, format, pass, e, desc, NULL, &crls)) 1172 return NULL; 1173 return crls; 1174} 1175 1176#define X509V3_EXT_UNKNOWN_MASK (0xfL << 16) 1177/* Return error for unknown extensions */ 1178#define X509V3_EXT_DEFAULT 0 1179/* Print error for unknown extensions */ 1180#define X509V3_EXT_ERROR_UNKNOWN (1L << 16) 1181/* ASN1 parse unknown extensions */ 1182#define X509V3_EXT_PARSE_UNKNOWN (2L << 16) 1183/* BIO_dump unknown extensions */ 1184#define X509V3_EXT_DUMP_UNKNOWN (3L << 16) 1185 1186#define X509_FLAG_CA (X509_FLAG_NO_ISSUER | X509_FLAG_NO_PUBKEY | \ 1187 X509_FLAG_NO_HEADER | X509_FLAG_NO_VERSION) 1188 1189int set_cert_ex(unsigned long *flags, const char *arg) 1190{ 1191 static const NAME_EX_TBL cert_tbl[] = { 1192 {"compatible", X509_FLAG_COMPAT, 0xffffffffl}, 1193 {"ca_default", X509_FLAG_CA, 0xffffffffl}, 1194 {"no_header", X509_FLAG_NO_HEADER, 0}, 1195 {"no_version", X509_FLAG_NO_VERSION, 0}, 1196 {"no_serial", X509_FLAG_NO_SERIAL, 0}, 1197 {"no_signame", X509_FLAG_NO_SIGNAME, 0}, 1198 {"no_validity", X509_FLAG_NO_VALIDITY, 0}, 1199 {"no_subject", X509_FLAG_NO_SUBJECT, 0}, 1200 {"no_issuer", X509_FLAG_NO_ISSUER, 0}, 1201 {"no_pubkey", X509_FLAG_NO_PUBKEY, 0}, 1202 {"no_extensions", X509_FLAG_NO_EXTENSIONS, 0}, 1203 {"no_sigdump", X509_FLAG_NO_SIGDUMP, 0}, 1204 {"no_aux", X509_FLAG_NO_AUX, 0}, 1205 {"no_attributes", X509_FLAG_NO_ATTRIBUTES, 0}, 1206 {"ext_default", X509V3_EXT_DEFAULT, X509V3_EXT_UNKNOWN_MASK}, 1207 {"ext_error", X509V3_EXT_ERROR_UNKNOWN, X509V3_EXT_UNKNOWN_MASK}, 1208 {"ext_parse", X509V3_EXT_PARSE_UNKNOWN, X509V3_EXT_UNKNOWN_MASK}, 1209 {"ext_dump", X509V3_EXT_DUMP_UNKNOWN, X509V3_EXT_UNKNOWN_MASK}, 1210 {NULL, 0, 0} 1211 }; 1212 return set_multi_opts(flags, arg, cert_tbl); 1213} 1214 1215int set_name_ex(unsigned long *flags, const char *arg) 1216{ 1217 static const NAME_EX_TBL ex_tbl[] = { 1218 {"esc_2253", ASN1_STRFLGS_ESC_2253, 0}, 1219 {"esc_ctrl", ASN1_STRFLGS_ESC_CTRL, 0}, 1220 {"esc_msb", ASN1_STRFLGS_ESC_MSB, 0}, 1221 {"use_quote", ASN1_STRFLGS_ESC_QUOTE, 0}, 1222 {"utf8", ASN1_STRFLGS_UTF8_CONVERT, 0}, 1223 {"ignore_type", ASN1_STRFLGS_IGNORE_TYPE, 0}, 1224 {"show_type", ASN1_STRFLGS_SHOW_TYPE, 0}, 1225 {"dump_all", ASN1_STRFLGS_DUMP_ALL, 0}, 1226 {"dump_nostr", ASN1_STRFLGS_DUMP_UNKNOWN, 0}, 1227 {"dump_der", ASN1_STRFLGS_DUMP_DER, 0}, 1228 {"compat", XN_FLAG_COMPAT, 0xffffffffL}, 1229 {"sep_comma_plus", XN_FLAG_SEP_COMMA_PLUS, XN_FLAG_SEP_MASK}, 1230 {"sep_comma_plus_space", XN_FLAG_SEP_CPLUS_SPC, XN_FLAG_SEP_MASK}, 1231 {"sep_semi_plus_space", XN_FLAG_SEP_SPLUS_SPC, XN_FLAG_SEP_MASK}, 1232 {"sep_multiline", XN_FLAG_SEP_MULTILINE, XN_FLAG_SEP_MASK}, 1233 {"dn_rev", XN_FLAG_DN_REV, 0}, 1234 {"nofname", XN_FLAG_FN_NONE, XN_FLAG_FN_MASK}, 1235 {"sname", XN_FLAG_FN_SN, XN_FLAG_FN_MASK}, 1236 {"lname", XN_FLAG_FN_LN, XN_FLAG_FN_MASK}, 1237 {"align", XN_FLAG_FN_ALIGN, 0}, 1238 {"oid", XN_FLAG_FN_OID, XN_FLAG_FN_MASK}, 1239 {"space_eq", XN_FLAG_SPC_EQ, 0}, 1240 {"dump_unknown", XN_FLAG_DUMP_UNKNOWN_FIELDS, 0}, 1241 {"RFC2253", XN_FLAG_RFC2253, 0xffffffffL}, 1242 {"oneline", XN_FLAG_ONELINE, 0xffffffffL}, 1243 {"multiline", XN_FLAG_MULTILINE, 0xffffffffL}, 1244 {"ca_default", XN_FLAG_MULTILINE, 0xffffffffL}, 1245 {NULL, 0, 0} 1246 }; 1247 if (set_multi_opts(flags, arg, ex_tbl) == 0) 1248 return 0; 1249 if ((*flags & XN_FLAG_SEP_MASK) == 0) 1250 *flags |= XN_FLAG_SEP_CPLUS_SPC; 1251 return 1; 1252} 1253 1254int set_ext_copy(int *copy_type, const char *arg) 1255{ 1256 if (!strcasecmp(arg, "none")) 1257 *copy_type = EXT_COPY_NONE; 1258 else if (!strcasecmp(arg, "copy")) 1259 *copy_type = EXT_COPY_ADD; 1260 else if (!strcasecmp(arg, "copyall")) 1261 *copy_type = EXT_COPY_ALL; 1262 else 1263 return 0; 1264 return 1; 1265} 1266 1267int copy_extensions(X509 *x, X509_REQ *req, int copy_type) 1268{ 1269 STACK_OF(X509_EXTENSION) *exts = NULL; 1270 X509_EXTENSION *ext, *tmpext; 1271 ASN1_OBJECT *obj; 1272 int i, idx, ret = 0; 1273 if (!x || !req || (copy_type == EXT_COPY_NONE)) 1274 return 1; 1275 exts = X509_REQ_get_extensions(req); 1276 1277 for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) { 1278 ext = sk_X509_EXTENSION_value(exts, i); 1279 obj = X509_EXTENSION_get_object(ext); 1280 idx = X509_get_ext_by_OBJ(x, obj, -1); 1281 /* Does extension exist? */ 1282 if (idx != -1) { 1283 /* If normal copy don't override existing extension */ 1284 if (copy_type == EXT_COPY_ADD) 1285 continue; 1286 /* Delete all extensions of same type */ 1287 do { 1288 tmpext = X509_get_ext(x, idx); 1289 X509_delete_ext(x, idx); 1290 X509_EXTENSION_free(tmpext); 1291 idx = X509_get_ext_by_OBJ(x, obj, -1); 1292 } while (idx != -1); 1293 } 1294 if (!X509_add_ext(x, ext, -1)) 1295 goto end; 1296 } 1297 1298 ret = 1; 1299 1300 end: 1301 1302 sk_X509_EXTENSION_pop_free(exts, X509_EXTENSION_free); 1303 1304 return ret; 1305} 1306 1307static int set_multi_opts(unsigned long *flags, const char *arg, 1308 const NAME_EX_TBL * in_tbl) 1309{ 1310 STACK_OF(CONF_VALUE) *vals; 1311 CONF_VALUE *val; 1312 int i, ret = 1; 1313 if (!arg) 1314 return 0; 1315 vals = X509V3_parse_list(arg); 1316 for (i = 0; i < sk_CONF_VALUE_num(vals); i++) { 1317 val = sk_CONF_VALUE_value(vals, i); 1318 if (!set_table_opts(flags, val->name, in_tbl)) 1319 ret = 0; 1320 } 1321 sk_CONF_VALUE_pop_free(vals, X509V3_conf_free); 1322 return ret; 1323} 1324 1325static int set_table_opts(unsigned long *flags, const char *arg, 1326 const NAME_EX_TBL * in_tbl) 1327{ 1328 char c; 1329 const NAME_EX_TBL *ptbl; 1330 c = arg[0]; 1331 1332 if (c == '-') { 1333 c = 0; 1334 arg++; 1335 } else if (c == '+') { 1336 c = 1; 1337 arg++; 1338 } else 1339 c = 1; 1340 1341 for (ptbl = in_tbl; ptbl->name; ptbl++) { 1342 if (!strcasecmp(arg, ptbl->name)) { 1343 *flags &= ~ptbl->mask; 1344 if (c) 1345 *flags |= ptbl->flag; 1346 else 1347 *flags &= ~ptbl->flag; 1348 return 1; 1349 } 1350 } 1351 return 0; 1352} 1353 1354void print_name(BIO *out, const char *title, X509_NAME *nm, 1355 unsigned long lflags) 1356{ 1357 char *buf; 1358 char mline = 0; 1359 int indent = 0; 1360 1361 if (title) 1362 BIO_puts(out, title); 1363 if ((lflags & XN_FLAG_SEP_MASK) == XN_FLAG_SEP_MULTILINE) { 1364 mline = 1; 1365 indent = 4; 1366 } 1367 if (lflags == XN_FLAG_COMPAT) { 1368 buf = X509_NAME_oneline(nm, 0, 0); 1369 BIO_puts(out, buf); 1370 BIO_puts(out, "\n"); 1371 OPENSSL_free(buf); 1372 } else { 1373 if (mline) 1374 BIO_puts(out, "\n"); 1375 X509_NAME_print_ex(out, nm, indent, lflags); 1376 BIO_puts(out, "\n"); 1377 } 1378} 1379 1380X509_STORE *setup_verify(BIO *bp, char *CAfile, char *CApath) 1381{ 1382 X509_STORE *store; 1383 X509_LOOKUP *lookup; 1384 if (!(store = X509_STORE_new())) 1385 goto end; 1386 lookup = X509_STORE_add_lookup(store, X509_LOOKUP_file()); 1387 if (lookup == NULL) 1388 goto end; 1389 if (CAfile) { 1390 if (!X509_LOOKUP_load_file(lookup, CAfile, X509_FILETYPE_PEM)) { 1391 BIO_printf(bp, "Error loading file %s\n", CAfile); 1392 goto end; 1393 } 1394 } else 1395 X509_LOOKUP_load_file(lookup, NULL, X509_FILETYPE_DEFAULT); 1396 1397 lookup = X509_STORE_add_lookup(store, X509_LOOKUP_hash_dir()); 1398 if (lookup == NULL) 1399 goto end; 1400 if (CApath) { 1401 if (!X509_LOOKUP_add_dir(lookup, CApath, X509_FILETYPE_PEM)) { 1402 BIO_printf(bp, "Error loading directory %s\n", CApath); 1403 goto end; 1404 } 1405 } else 1406 X509_LOOKUP_add_dir(lookup, NULL, X509_FILETYPE_DEFAULT); 1407 1408 ERR_clear_error(); 1409 return store; 1410 end: 1411 X509_STORE_free(store); 1412 return NULL; 1413} 1414 1415#ifndef OPENSSL_NO_ENGINE 1416/* Try to load an engine in a shareable library */ 1417static ENGINE *try_load_engine(BIO *err, const char *engine, int debug) 1418{ 1419 ENGINE *e = ENGINE_by_id("dynamic"); 1420 if (e) { 1421 if (!ENGINE_ctrl_cmd_string(e, "SO_PATH", engine, 0) 1422 || !ENGINE_ctrl_cmd_string(e, "LOAD", NULL, 0)) { 1423 ENGINE_free(e); 1424 e = NULL; 1425 } 1426 } 1427 return e; 1428} 1429 1430ENGINE *setup_engine(BIO *err, const char *engine, int debug) 1431{ 1432 ENGINE *e = NULL; 1433 1434 if (engine) { 1435 if (strcmp(engine, "auto") == 0) { 1436 BIO_printf(err, "enabling auto ENGINE support\n"); 1437 ENGINE_register_all_complete(); 1438 return NULL; 1439 } 1440 if ((e = ENGINE_by_id(engine)) == NULL 1441 && (e = try_load_engine(err, engine, debug)) == NULL) { 1442 BIO_printf(err, "invalid engine \"%s\"\n", engine); 1443 ERR_print_errors(err); 1444 return NULL; 1445 } 1446 if (debug) { 1447 ENGINE_ctrl(e, ENGINE_CTRL_SET_LOGSTREAM, 0, err, 0); 1448 } 1449 ENGINE_ctrl_cmd(e, "SET_USER_INTERFACE", 0, ui_method, 0, 1); 1450 if (!ENGINE_set_default(e, ENGINE_METHOD_ALL)) { 1451 BIO_printf(err, "can't use that engine\n"); 1452 ERR_print_errors(err); 1453 ENGINE_free(e); 1454 return NULL; 1455 } 1456 1457 BIO_printf(err, "engine \"%s\" set.\n", ENGINE_get_id(e)); 1458 1459 /* Free our "structural" reference. */ 1460 ENGINE_free(e); 1461 } 1462 return e; 1463} 1464#endif 1465 1466int load_config(BIO *err, CONF *cnf) 1467{ 1468 static int load_config_called = 0; 1469 if (load_config_called) 1470 return 1; 1471 load_config_called = 1; 1472 if (!cnf) 1473 cnf = config; 1474 if (!cnf) 1475 return 1; 1476 1477 OPENSSL_load_builtin_modules(); 1478 1479 if (CONF_modules_load(cnf, NULL, 0) <= 0) { 1480 BIO_printf(err, "Error configuring OpenSSL\n"); 1481 ERR_print_errors(err); 1482 return 0; 1483 } 1484 return 1; 1485} 1486 1487char *make_config_name() 1488{ 1489 const char *t = X509_get_default_cert_area(); 1490 size_t len; 1491 char *p; 1492 1493 len = strlen(t) + strlen(OPENSSL_CONF) + 2; 1494 p = OPENSSL_malloc(len); 1495 if (p == NULL) 1496 return NULL; 1497 BUF_strlcpy(p, t, len); 1498#ifndef OPENSSL_SYS_VMS 1499 BUF_strlcat(p, "/", len); 1500#endif 1501 BUF_strlcat(p, OPENSSL_CONF, len); 1502 1503 return p; 1504} 1505 1506static unsigned long index_serial_hash(const OPENSSL_CSTRING *a) 1507{ 1508 const char *n; 1509 1510 n = a[DB_serial]; 1511 while (*n == '0') 1512 n++; 1513 return (lh_strhash(n)); 1514} 1515 1516static int index_serial_cmp(const OPENSSL_CSTRING *a, 1517 const OPENSSL_CSTRING *b) 1518{ 1519 const char *aa, *bb; 1520 1521 for (aa = a[DB_serial]; *aa == '0'; aa++) ; 1522 for (bb = b[DB_serial]; *bb == '0'; bb++) ; 1523 return (strcmp(aa, bb)); 1524} 1525 1526static int index_name_qual(char **a) 1527{ 1528 return (a[0][0] == 'V'); 1529} 1530 1531static unsigned long index_name_hash(const OPENSSL_CSTRING *a) 1532{ 1533 return (lh_strhash(a[DB_name])); 1534} 1535 1536int index_name_cmp(const OPENSSL_CSTRING *a, const OPENSSL_CSTRING *b) 1537{ 1538 return (strcmp(a[DB_name], b[DB_name])); 1539} 1540 1541static IMPLEMENT_LHASH_HASH_FN(index_serial, OPENSSL_CSTRING) 1542static IMPLEMENT_LHASH_COMP_FN(index_serial, OPENSSL_CSTRING) 1543static IMPLEMENT_LHASH_HASH_FN(index_name, OPENSSL_CSTRING) 1544static IMPLEMENT_LHASH_COMP_FN(index_name, OPENSSL_CSTRING) 1545#undef BSIZE 1546#define BSIZE 256 1547BIGNUM *load_serial(char *serialfile, int create, ASN1_INTEGER **retai) 1548{ 1549 BIO *in = NULL; 1550 BIGNUM *ret = NULL; 1551 MS_STATIC char buf[1024]; 1552 ASN1_INTEGER *ai = NULL; 1553 1554 ai = ASN1_INTEGER_new(); 1555 if (ai == NULL) 1556 goto err; 1557 1558 if ((in = BIO_new(BIO_s_file())) == NULL) { 1559 ERR_print_errors(bio_err); 1560 goto err; 1561 } 1562 1563 if (BIO_read_filename(in, serialfile) <= 0) { 1564 if (!create) { 1565 perror(serialfile); 1566 goto err; 1567 } else { 1568 ret = BN_new(); 1569 if (ret == NULL || !rand_serial(ret, ai)) 1570 BIO_printf(bio_err, "Out of memory\n"); 1571 } 1572 } else { 1573 if (!a2i_ASN1_INTEGER(in, ai, buf, 1024)) { 1574 BIO_printf(bio_err, "unable to load number from %s\n", 1575 serialfile); 1576 goto err; 1577 } 1578 ret = ASN1_INTEGER_to_BN(ai, NULL); 1579 if (ret == NULL) { 1580 BIO_printf(bio_err, 1581 "error converting number from bin to BIGNUM\n"); 1582 goto err; 1583 } 1584 } 1585 1586 if (ret && retai) { 1587 *retai = ai; 1588 ai = NULL; 1589 } 1590 err: 1591 if (in != NULL) 1592 BIO_free(in); 1593 if (ai != NULL) 1594 ASN1_INTEGER_free(ai); 1595 return (ret); 1596} 1597 1598int save_serial(char *serialfile, char *suffix, BIGNUM *serial, 1599 ASN1_INTEGER **retai) 1600{ 1601 char buf[1][BSIZE]; 1602 BIO *out = NULL; 1603 int ret = 0; 1604 ASN1_INTEGER *ai = NULL; 1605 int j; 1606 1607 if (suffix == NULL) 1608 j = strlen(serialfile); 1609 else 1610 j = strlen(serialfile) + strlen(suffix) + 1; 1611 if (j >= BSIZE) { 1612 BIO_printf(bio_err, "file name too long\n"); 1613 goto err; 1614 } 1615 1616 if (suffix == NULL) 1617 BUF_strlcpy(buf[0], serialfile, BSIZE); 1618 else { 1619#ifndef OPENSSL_SYS_VMS 1620 j = BIO_snprintf(buf[0], sizeof buf[0], "%s.%s", serialfile, suffix); 1621#else 1622 j = BIO_snprintf(buf[0], sizeof buf[0], "%s-%s", serialfile, suffix); 1623#endif 1624 } 1625#ifdef RL_DEBUG 1626 BIO_printf(bio_err, "DEBUG: writing \"%s\"\n", buf[0]); 1627#endif 1628 out = BIO_new(BIO_s_file()); 1629 if (out == NULL) { 1630 ERR_print_errors(bio_err); 1631 goto err; 1632 } 1633 if (BIO_write_filename(out, buf[0]) <= 0) { 1634 perror(serialfile); 1635 goto err; 1636 } 1637 1638 if ((ai = BN_to_ASN1_INTEGER(serial, NULL)) == NULL) { 1639 BIO_printf(bio_err, "error converting serial to ASN.1 format\n"); 1640 goto err; 1641 } 1642 i2a_ASN1_INTEGER(out, ai); 1643 BIO_puts(out, "\n"); 1644 ret = 1; 1645 if (retai) { 1646 *retai = ai; 1647 ai = NULL; 1648 } 1649 err: 1650 if (out != NULL) 1651 BIO_free_all(out); 1652 if (ai != NULL) 1653 ASN1_INTEGER_free(ai); 1654 return (ret); 1655} 1656 1657int rotate_serial(char *serialfile, char *new_suffix, char *old_suffix) 1658{ 1659 char buf[5][BSIZE]; 1660 int i, j; 1661 1662 i = strlen(serialfile) + strlen(old_suffix); 1663 j = strlen(serialfile) + strlen(new_suffix); 1664 if (i > j) 1665 j = i; 1666 if (j + 1 >= BSIZE) { 1667 BIO_printf(bio_err, "file name too long\n"); 1668 goto err; 1669 } 1670#ifndef OPENSSL_SYS_VMS 1671 j = BIO_snprintf(buf[0], sizeof buf[0], "%s.%s", serialfile, new_suffix); 1672#else 1673 j = BIO_snprintf(buf[0], sizeof buf[0], "%s-%s", serialfile, new_suffix); 1674#endif 1675#ifndef OPENSSL_SYS_VMS 1676 j = BIO_snprintf(buf[1], sizeof buf[1], "%s.%s", serialfile, old_suffix); 1677#else 1678 j = BIO_snprintf(buf[1], sizeof buf[1], "%s-%s", serialfile, old_suffix); 1679#endif 1680#ifdef RL_DEBUG 1681 BIO_printf(bio_err, "DEBUG: renaming \"%s\" to \"%s\"\n", 1682 serialfile, buf[1]); 1683#endif 1684 if (rename(serialfile, buf[1]) < 0 && errno != ENOENT 1685#ifdef ENOTDIR 1686 && errno != ENOTDIR 1687#endif 1688 ) { 1689 BIO_printf(bio_err, 1690 "unable to rename %s to %s\n", serialfile, buf[1]); 1691 perror("reason"); 1692 goto err; 1693 } 1694#ifdef RL_DEBUG 1695 BIO_printf(bio_err, "DEBUG: renaming \"%s\" to \"%s\"\n", 1696 buf[0], serialfile); 1697#endif 1698 if (rename(buf[0], serialfile) < 0) { 1699 BIO_printf(bio_err, 1700 "unable to rename %s to %s\n", buf[0], serialfile); 1701 perror("reason"); 1702 rename(buf[1], serialfile); 1703 goto err; 1704 } 1705 return 1; 1706 err: 1707 return 0; 1708} 1709 1710int rand_serial(BIGNUM *b, ASN1_INTEGER *ai) 1711{ 1712 BIGNUM *btmp; 1713 int ret = 0; 1714 if (b) 1715 btmp = b; 1716 else 1717 btmp = BN_new(); 1718 1719 if (!btmp) 1720 return 0; 1721 1722 if (!BN_pseudo_rand(btmp, SERIAL_RAND_BITS, 0, 0)) 1723 goto error; 1724 if (ai && !BN_to_ASN1_INTEGER(btmp, ai)) 1725 goto error; 1726 1727 ret = 1; 1728 1729 error: 1730 1731 if (!b) 1732 BN_free(btmp); 1733 1734 return ret; 1735} 1736 1737CA_DB *load_index(char *dbfile, DB_ATTR *db_attr) 1738{ 1739 CA_DB *retdb = NULL; 1740 TXT_DB *tmpdb = NULL; 1741 BIO *in = BIO_new(BIO_s_file()); 1742 CONF *dbattr_conf = NULL; 1743 char buf[1][BSIZE]; 1744 long errorline = -1; 1745 1746 if (in == NULL) { 1747 ERR_print_errors(bio_err); 1748 goto err; 1749 } 1750 if (BIO_read_filename(in, dbfile) <= 0) { 1751 perror(dbfile); 1752 BIO_printf(bio_err, "unable to open '%s'\n", dbfile); 1753 goto err; 1754 } 1755 if ((tmpdb = TXT_DB_read(in, DB_NUMBER)) == NULL) 1756 goto err; 1757 1758#ifndef OPENSSL_SYS_VMS 1759 BIO_snprintf(buf[0], sizeof buf[0], "%s.attr", dbfile); 1760#else 1761 BIO_snprintf(buf[0], sizeof buf[0], "%s-attr", dbfile); 1762#endif 1763 dbattr_conf = NCONF_new(NULL); 1764 if (NCONF_load(dbattr_conf, buf[0], &errorline) <= 0) { 1765 if (errorline > 0) { 1766 BIO_printf(bio_err, 1767 "error on line %ld of db attribute file '%s'\n", 1768 errorline, buf[0]); 1769 goto err; 1770 } else { 1771 NCONF_free(dbattr_conf); 1772 dbattr_conf = NULL; 1773 } 1774 } 1775 1776 if ((retdb = OPENSSL_malloc(sizeof(CA_DB))) == NULL) { 1777 fprintf(stderr, "Out of memory\n"); 1778 goto err; 1779 } 1780 1781 retdb->db = tmpdb; 1782 tmpdb = NULL; 1783 if (db_attr) 1784 retdb->attributes = *db_attr; 1785 else { 1786 retdb->attributes.unique_subject = 1; 1787 } 1788 1789 if (dbattr_conf) { 1790 char *p = NCONF_get_string(dbattr_conf, NULL, "unique_subject"); 1791 if (p) { 1792#ifdef RL_DEBUG 1793 BIO_printf(bio_err, 1794 "DEBUG[load_index]: unique_subject = \"%s\"\n", p); 1795#endif 1796 retdb->attributes.unique_subject = parse_yesno(p, 1); 1797 } 1798 } 1799 1800 err: 1801 if (dbattr_conf) 1802 NCONF_free(dbattr_conf); 1803 if (tmpdb) 1804 TXT_DB_free(tmpdb); 1805 if (in) 1806 BIO_free_all(in); 1807 return retdb; 1808} 1809 1810int index_index(CA_DB *db) 1811{ 1812 if (!TXT_DB_create_index(db->db, DB_serial, NULL, 1813 LHASH_HASH_FN(index_serial), 1814 LHASH_COMP_FN(index_serial))) { 1815 BIO_printf(bio_err, 1816 "error creating serial number index:(%ld,%ld,%ld)\n", 1817 db->db->error, db->db->arg1, db->db->arg2); 1818 return 0; 1819 } 1820 1821 if (db->attributes.unique_subject 1822 && !TXT_DB_create_index(db->db, DB_name, index_name_qual, 1823 LHASH_HASH_FN(index_name), 1824 LHASH_COMP_FN(index_name))) { 1825 BIO_printf(bio_err, "error creating name index:(%ld,%ld,%ld)\n", 1826 db->db->error, db->db->arg1, db->db->arg2); 1827 return 0; 1828 } 1829 return 1; 1830} 1831 1832int save_index(const char *dbfile, const char *suffix, CA_DB *db) 1833{ 1834 char buf[3][BSIZE]; 1835 BIO *out = BIO_new(BIO_s_file()); 1836 int j; 1837 1838 if (out == NULL) { 1839 ERR_print_errors(bio_err); 1840 goto err; 1841 } 1842 1843 j = strlen(dbfile) + strlen(suffix); 1844 if (j + 6 >= BSIZE) { 1845 BIO_printf(bio_err, "file name too long\n"); 1846 goto err; 1847 } 1848#ifndef OPENSSL_SYS_VMS 1849 j = BIO_snprintf(buf[2], sizeof buf[2], "%s.attr", dbfile); 1850#else 1851 j = BIO_snprintf(buf[2], sizeof buf[2], "%s-attr", dbfile); 1852#endif 1853#ifndef OPENSSL_SYS_VMS 1854 j = BIO_snprintf(buf[1], sizeof buf[1], "%s.attr.%s", dbfile, suffix); 1855#else 1856 j = BIO_snprintf(buf[1], sizeof buf[1], "%s-attr-%s", dbfile, suffix); 1857#endif 1858#ifndef OPENSSL_SYS_VMS 1859 j = BIO_snprintf(buf[0], sizeof buf[0], "%s.%s", dbfile, suffix); 1860#else 1861 j = BIO_snprintf(buf[0], sizeof buf[0], "%s-%s", dbfile, suffix); 1862#endif 1863#ifdef RL_DEBUG 1864 BIO_printf(bio_err, "DEBUG: writing \"%s\"\n", buf[0]); 1865#endif 1866 if (BIO_write_filename(out, buf[0]) <= 0) { 1867 perror(dbfile); 1868 BIO_printf(bio_err, "unable to open '%s'\n", dbfile); 1869 goto err; 1870 } 1871 j = TXT_DB_write(out, db->db); 1872 if (j <= 0) 1873 goto err; 1874 1875 BIO_free(out); 1876 1877 out = BIO_new(BIO_s_file()); 1878#ifdef RL_DEBUG 1879 BIO_printf(bio_err, "DEBUG: writing \"%s\"\n", buf[1]); 1880#endif 1881 if (BIO_write_filename(out, buf[1]) <= 0) { 1882 perror(buf[2]); 1883 BIO_printf(bio_err, "unable to open '%s'\n", buf[2]); 1884 goto err; 1885 } 1886 BIO_printf(out, "unique_subject = %s\n", 1887 db->attributes.unique_subject ? "yes" : "no"); 1888 BIO_free(out); 1889 1890 return 1; 1891 err: 1892 return 0; 1893} 1894 1895int rotate_index(const char *dbfile, const char *new_suffix, 1896 const char *old_suffix) 1897{ 1898 char buf[5][BSIZE]; 1899 int i, j; 1900 1901 i = strlen(dbfile) + strlen(old_suffix); 1902 j = strlen(dbfile) + strlen(new_suffix); 1903 if (i > j) 1904 j = i; 1905 if (j + 6 >= BSIZE) { 1906 BIO_printf(bio_err, "file name too long\n"); 1907 goto err; 1908 } 1909#ifndef OPENSSL_SYS_VMS 1910 j = BIO_snprintf(buf[4], sizeof buf[4], "%s.attr", dbfile); 1911#else 1912 j = BIO_snprintf(buf[4], sizeof buf[4], "%s-attr", dbfile); 1913#endif 1914#ifndef OPENSSL_SYS_VMS 1915 j = BIO_snprintf(buf[2], sizeof buf[2], "%s.attr.%s", dbfile, new_suffix); 1916#else 1917 j = BIO_snprintf(buf[2], sizeof buf[2], "%s-attr-%s", dbfile, new_suffix); 1918#endif 1919#ifndef OPENSSL_SYS_VMS 1920 j = BIO_snprintf(buf[0], sizeof buf[0], "%s.%s", dbfile, new_suffix); 1921#else 1922 j = BIO_snprintf(buf[0], sizeof buf[0], "%s-%s", dbfile, new_suffix); 1923#endif 1924#ifndef OPENSSL_SYS_VMS 1925 j = BIO_snprintf(buf[1], sizeof buf[1], "%s.%s", dbfile, old_suffix); 1926#else 1927 j = BIO_snprintf(buf[1], sizeof buf[1], "%s-%s", dbfile, old_suffix); 1928#endif 1929#ifndef OPENSSL_SYS_VMS 1930 j = BIO_snprintf(buf[3], sizeof buf[3], "%s.attr.%s", dbfile, old_suffix); 1931#else 1932 j = BIO_snprintf(buf[3], sizeof buf[3], "%s-attr-%s", dbfile, old_suffix); 1933#endif 1934#ifdef RL_DEBUG 1935 BIO_printf(bio_err, "DEBUG: renaming \"%s\" to \"%s\"\n", dbfile, buf[1]); 1936#endif 1937 if (rename(dbfile, buf[1]) < 0 && errno != ENOENT 1938#ifdef ENOTDIR 1939 && errno != ENOTDIR 1940#endif 1941 ) { 1942 BIO_printf(bio_err, "unable to rename %s to %s\n", dbfile, buf[1]); 1943 perror("reason"); 1944 goto err; 1945 } 1946#ifdef RL_DEBUG 1947 BIO_printf(bio_err, "DEBUG: renaming \"%s\" to \"%s\"\n", buf[0], dbfile); 1948#endif 1949 if (rename(buf[0], dbfile) < 0) { 1950 BIO_printf(bio_err, "unable to rename %s to %s\n", buf[0], dbfile); 1951 perror("reason"); 1952 rename(buf[1], dbfile); 1953 goto err; 1954 } 1955#ifdef RL_DEBUG 1956 BIO_printf(bio_err, "DEBUG: renaming \"%s\" to \"%s\"\n", buf[4], buf[3]); 1957#endif 1958 if (rename(buf[4], buf[3]) < 0 && errno != ENOENT 1959#ifdef ENOTDIR 1960 && errno != ENOTDIR 1961#endif 1962 ) { 1963 BIO_printf(bio_err, "unable to rename %s to %s\n", buf[4], buf[3]); 1964 perror("reason"); 1965 rename(dbfile, buf[0]); 1966 rename(buf[1], dbfile); 1967 goto err; 1968 } 1969#ifdef RL_DEBUG 1970 BIO_printf(bio_err, "DEBUG: renaming \"%s\" to \"%s\"\n", buf[2], buf[4]); 1971#endif 1972 if (rename(buf[2], buf[4]) < 0) { 1973 BIO_printf(bio_err, "unable to rename %s to %s\n", buf[2], buf[4]); 1974 perror("reason"); 1975 rename(buf[3], buf[4]); 1976 rename(dbfile, buf[0]); 1977 rename(buf[1], dbfile); 1978 goto err; 1979 } 1980 return 1; 1981 err: 1982 return 0; 1983} 1984 1985void free_index(CA_DB *db) 1986{ 1987 if (db) { 1988 if (db->db) 1989 TXT_DB_free(db->db); 1990 OPENSSL_free(db); 1991 } 1992} 1993 1994int parse_yesno(const char *str, int def) 1995{ 1996 int ret = def; 1997 if (str) { 1998 switch (*str) { 1999 case 'f': /* false */ 2000 case 'F': /* FALSE */ 2001 case 'n': /* no */ 2002 case 'N': /* NO */ 2003 case '0': /* 0 */ 2004 ret = 0; 2005 break; 2006 case 't': /* true */ 2007 case 'T': /* TRUE */ 2008 case 'y': /* yes */ 2009 case 'Y': /* YES */ 2010 case '1': /* 1 */ 2011 ret = 1; 2012 break; 2013 default: 2014 ret = def; 2015 break; 2016 } 2017 } 2018 return ret; 2019} 2020 2021/* 2022 * subject is expected to be in the format /type0=value0/type1=value1/type2=... 2023 * where characters may be escaped by \ 2024 */ 2025X509_NAME *parse_name(char *subject, long chtype, int multirdn) 2026{ 2027 size_t buflen = strlen(subject) + 1; /* to copy the types and values 2028 * into. due to escaping, the copy 2029 * can only become shorter */ 2030 char *buf = OPENSSL_malloc(buflen); 2031 size_t max_ne = buflen / 2 + 1; /* maximum number of name elements */ 2032 char **ne_types = OPENSSL_malloc(max_ne * sizeof(char *)); 2033 char **ne_values = OPENSSL_malloc(max_ne * sizeof(char *)); 2034 int *mval = OPENSSL_malloc(max_ne * sizeof(int)); 2035 2036 char *sp = subject, *bp = buf; 2037 int i, ne_num = 0; 2038 2039 X509_NAME *n = NULL; 2040 int nid; 2041 2042 if (!buf || !ne_types || !ne_values || !mval) { 2043 BIO_printf(bio_err, "malloc error\n"); 2044 goto error; 2045 } 2046 2047 if (*subject != '/') { 2048 BIO_printf(bio_err, "Subject does not start with '/'.\n"); 2049 goto error; 2050 } 2051 sp++; /* skip leading / */ 2052 2053 /* no multivalued RDN by default */ 2054 mval[ne_num] = 0; 2055 2056 while (*sp) { 2057 /* collect type */ 2058 ne_types[ne_num] = bp; 2059 while (*sp) { 2060 if (*sp == '\\') { /* is there anything to escape in the 2061 * type...? */ 2062 if (*++sp) 2063 *bp++ = *sp++; 2064 else { 2065 BIO_printf(bio_err, 2066 "escape character at end of string\n"); 2067 goto error; 2068 } 2069 } else if (*sp == '=') { 2070 sp++; 2071 *bp++ = '\0'; 2072 break; 2073 } else 2074 *bp++ = *sp++; 2075 } 2076 if (!*sp) { 2077 BIO_printf(bio_err, 2078 "end of string encountered while processing type of subject name element #%d\n", 2079 ne_num); 2080 goto error; 2081 } 2082 ne_values[ne_num] = bp; 2083 while (*sp) { 2084 if (*sp == '\\') { 2085 if (*++sp) 2086 *bp++ = *sp++; 2087 else { 2088 BIO_printf(bio_err, 2089 "escape character at end of string\n"); 2090 goto error; 2091 } 2092 } else if (*sp == '/') { 2093 sp++; 2094 /* no multivalued RDN by default */ 2095 mval[ne_num + 1] = 0; 2096 break; 2097 } else if (*sp == '+' && multirdn) { 2098 /* 2099 * a not escaped + signals a mutlivalued RDN 2100 */ 2101 sp++; 2102 mval[ne_num + 1] = -1; 2103 break; 2104 } else 2105 *bp++ = *sp++; 2106 } 2107 *bp++ = '\0'; 2108 ne_num++; 2109 } 2110 2111 if (!(n = X509_NAME_new())) 2112 goto error; 2113 2114 for (i = 0; i < ne_num; i++) { 2115 if ((nid = OBJ_txt2nid(ne_types[i])) == NID_undef) { 2116 BIO_printf(bio_err, 2117 "Subject Attribute %s has no known NID, skipped\n", 2118 ne_types[i]); 2119 continue; 2120 } 2121 2122 if (!*ne_values[i]) { 2123 BIO_printf(bio_err, 2124 "No value provided for Subject Attribute %s, skipped\n", 2125 ne_types[i]); 2126 continue; 2127 } 2128 2129 if (!X509_NAME_add_entry_by_NID 2130 (n, nid, chtype, (unsigned char *)ne_values[i], -1, -1, mval[i])) 2131 goto error; 2132 } 2133 2134 OPENSSL_free(ne_values); 2135 OPENSSL_free(ne_types); 2136 OPENSSL_free(buf); 2137 OPENSSL_free(mval); 2138 return n; 2139 2140 error: 2141 X509_NAME_free(n); 2142 if (ne_values) 2143 OPENSSL_free(ne_values); 2144 if (ne_types) 2145 OPENSSL_free(ne_types); 2146 if (mval) 2147 OPENSSL_free(mval); 2148 if (buf) 2149 OPENSSL_free(buf); 2150 return NULL; 2151} 2152 2153int args_verify(char ***pargs, int *pargc, 2154 int *badarg, BIO *err, X509_VERIFY_PARAM **pm) 2155{ 2156 ASN1_OBJECT *otmp = NULL; 2157 unsigned long flags = 0; 2158 int i; 2159 int purpose = 0, depth = -1; 2160 char **oldargs = *pargs; 2161 char *arg = **pargs, *argn = (*pargs)[1]; 2162 time_t at_time = 0; 2163 if (!strcmp(arg, "-policy")) { 2164 if (!argn) 2165 *badarg = 1; 2166 else { 2167 otmp = OBJ_txt2obj(argn, 0); 2168 if (!otmp) { 2169 BIO_printf(err, "Invalid Policy \"%s\"\n", argn); 2170 *badarg = 1; 2171 } 2172 } 2173 (*pargs)++; 2174 } else if (strcmp(arg, "-purpose") == 0) { 2175 X509_PURPOSE *xptmp; 2176 if (!argn) 2177 *badarg = 1; 2178 else { 2179 i = X509_PURPOSE_get_by_sname(argn); 2180 if (i < 0) { 2181 BIO_printf(err, "unrecognized purpose\n"); 2182 *badarg = 1; 2183 } else { 2184 xptmp = X509_PURPOSE_get0(i); 2185 purpose = X509_PURPOSE_get_id(xptmp); 2186 } 2187 } 2188 (*pargs)++; 2189 } else if (strcmp(arg, "-verify_depth") == 0) { 2190 if (!argn) 2191 *badarg = 1; 2192 else { 2193 depth = atoi(argn); 2194 if (depth < 0) { 2195 BIO_printf(err, "invalid depth\n"); 2196 *badarg = 1; 2197 } 2198 } 2199 (*pargs)++; 2200 } else if (strcmp(arg, "-attime") == 0) { 2201 if (!argn) 2202 *badarg = 1; 2203 else { 2204 long timestamp; 2205 /* 2206 * interpret the -attime argument as seconds since Epoch 2207 */ 2208 if (sscanf(argn, "%li", ×tamp) != 1) { 2209 BIO_printf(bio_err, "Error parsing timestamp %s\n", argn); 2210 *badarg = 1; 2211 } 2212 /* on some platforms time_t may be a float */ 2213 at_time = (time_t)timestamp; 2214 } 2215 (*pargs)++; 2216 } else if (!strcmp(arg, "-ignore_critical")) 2217 flags |= X509_V_FLAG_IGNORE_CRITICAL; 2218 else if (!strcmp(arg, "-issuer_checks")) 2219 flags |= X509_V_FLAG_CB_ISSUER_CHECK; 2220 else if (!strcmp(arg, "-crl_check")) 2221 flags |= X509_V_FLAG_CRL_CHECK; 2222 else if (!strcmp(arg, "-crl_check_all")) 2223 flags |= X509_V_FLAG_CRL_CHECK | X509_V_FLAG_CRL_CHECK_ALL; 2224 else if (!strcmp(arg, "-policy_check")) 2225 flags |= X509_V_FLAG_POLICY_CHECK; 2226 else if (!strcmp(arg, "-explicit_policy")) 2227 flags |= X509_V_FLAG_EXPLICIT_POLICY; 2228 else if (!strcmp(arg, "-inhibit_any")) 2229 flags |= X509_V_FLAG_INHIBIT_ANY; 2230 else if (!strcmp(arg, "-inhibit_map")) 2231 flags |= X509_V_FLAG_INHIBIT_MAP; 2232 else if (!strcmp(arg, "-x509_strict")) 2233 flags |= X509_V_FLAG_X509_STRICT; 2234 else if (!strcmp(arg, "-extended_crl")) 2235 flags |= X509_V_FLAG_EXTENDED_CRL_SUPPORT; 2236 else if (!strcmp(arg, "-use_deltas")) 2237 flags |= X509_V_FLAG_USE_DELTAS; 2238 else if (!strcmp(arg, "-policy_print")) 2239 flags |= X509_V_FLAG_NOTIFY_POLICY; 2240 else if (!strcmp(arg, "-check_ss_sig")) 2241 flags |= X509_V_FLAG_CHECK_SS_SIGNATURE; 2242 else if (!strcmp(arg, "-no_alt_chains")) 2243 flags |= X509_V_FLAG_NO_ALT_CHAINS; 2244 else 2245 return 0; 2246 2247 if (*badarg) { 2248 if (*pm) 2249 X509_VERIFY_PARAM_free(*pm); 2250 *pm = NULL; 2251 goto end; 2252 } 2253 2254 if (!*pm && !(*pm = X509_VERIFY_PARAM_new())) { 2255 *badarg = 1; 2256 goto end; 2257 } 2258 2259 if (otmp) 2260 X509_VERIFY_PARAM_add0_policy(*pm, otmp); 2261 if (flags) 2262 X509_VERIFY_PARAM_set_flags(*pm, flags); 2263 2264 if (purpose) 2265 X509_VERIFY_PARAM_set_purpose(*pm, purpose); 2266 2267 if (depth >= 0) 2268 X509_VERIFY_PARAM_set_depth(*pm, depth); 2269 2270 if (at_time) 2271 X509_VERIFY_PARAM_set_time(*pm, at_time); 2272 2273 end: 2274 2275 (*pargs)++; 2276 2277 if (pargc) 2278 *pargc -= *pargs - oldargs; 2279 2280 return 1; 2281 2282} 2283 2284/* 2285 * Read whole contents of a BIO into an allocated memory buffer and return 2286 * it. 2287 */ 2288 2289int bio_to_mem(unsigned char **out, int maxlen, BIO *in) 2290{ 2291 BIO *mem; 2292 int len, ret; 2293 unsigned char tbuf[1024]; 2294 mem = BIO_new(BIO_s_mem()); 2295 if (!mem) 2296 return -1; 2297 for (;;) { 2298 if ((maxlen != -1) && maxlen < 1024) 2299 len = maxlen; 2300 else 2301 len = 1024; 2302 len = BIO_read(in, tbuf, len); 2303 if (len <= 0) 2304 break; 2305 if (BIO_write(mem, tbuf, len) != len) { 2306 BIO_free(mem); 2307 return -1; 2308 } 2309 maxlen -= len; 2310 2311 if (maxlen == 0) 2312 break; 2313 } 2314 ret = BIO_get_mem_data(mem, (char **)out); 2315 BIO_set_flags(mem, BIO_FLAGS_MEM_RDONLY); 2316 BIO_free(mem); 2317 return ret; 2318} 2319 2320int pkey_ctrl_string(EVP_PKEY_CTX *ctx, char *value) 2321{ 2322 int rv; 2323 char *stmp, *vtmp = NULL; 2324 stmp = BUF_strdup(value); 2325 if (!stmp) 2326 return -1; 2327 vtmp = strchr(stmp, ':'); 2328 if (vtmp) { 2329 *vtmp = 0; 2330 vtmp++; 2331 } 2332 rv = EVP_PKEY_CTX_ctrl_str(ctx, stmp, vtmp); 2333 OPENSSL_free(stmp); 2334 return rv; 2335} 2336 2337static void nodes_print(BIO *out, const char *name, 2338 STACK_OF(X509_POLICY_NODE) *nodes) 2339{ 2340 X509_POLICY_NODE *node; 2341 int i; 2342 BIO_printf(out, "%s Policies:", name); 2343 if (nodes) { 2344 BIO_puts(out, "\n"); 2345 for (i = 0; i < sk_X509_POLICY_NODE_num(nodes); i++) { 2346 node = sk_X509_POLICY_NODE_value(nodes, i); 2347 X509_POLICY_NODE_print(out, node, 2); 2348 } 2349 } else 2350 BIO_puts(out, " <empty>\n"); 2351} 2352 2353void policies_print(BIO *out, X509_STORE_CTX *ctx) 2354{ 2355 X509_POLICY_TREE *tree; 2356 int explicit_policy; 2357 int free_out = 0; 2358 if (out == NULL) { 2359 out = BIO_new_fp(stderr, BIO_NOCLOSE); 2360 free_out = 1; 2361 } 2362 tree = X509_STORE_CTX_get0_policy_tree(ctx); 2363 explicit_policy = X509_STORE_CTX_get_explicit_policy(ctx); 2364 2365 BIO_printf(out, "Require explicit Policy: %s\n", 2366 explicit_policy ? "True" : "False"); 2367 2368 nodes_print(out, "Authority", X509_policy_tree_get0_policies(tree)); 2369 nodes_print(out, "User", X509_policy_tree_get0_user_policies(tree)); 2370 if (free_out) 2371 BIO_free(out); 2372} 2373 2374#if !defined(OPENSSL_NO_JPAKE) && !defined(OPENSSL_NO_PSK) 2375 2376static JPAKE_CTX *jpake_init(const char *us, const char *them, 2377 const char *secret) 2378{ 2379 BIGNUM *p = NULL; 2380 BIGNUM *g = NULL; 2381 BIGNUM *q = NULL; 2382 BIGNUM *bnsecret = BN_new(); 2383 JPAKE_CTX *ctx; 2384 2385 /* Use a safe prime for p (that we found earlier) */ 2386 BN_hex2bn(&p, 2387 "F9E5B365665EA7A05A9C534502780FEE6F1AB5BD4F49947FD036DBD7E905269AF46EF28B0FC07487EE4F5D20FB3C0AF8E700F3A2FA3414970CBED44FEDFF80CE78D800F184BB82435D137AADA2C6C16523247930A63B85661D1FC817A51ACD96168E95898A1F83A79FFB529368AA7833ABD1B0C3AEDDB14D2E1A2F71D99F763F"); 2388 g = BN_new(); 2389 BN_set_word(g, 2); 2390 q = BN_new(); 2391 BN_rshift1(q, p); 2392 2393 BN_bin2bn((const unsigned char *)secret, strlen(secret), bnsecret); 2394 2395 ctx = JPAKE_CTX_new(us, them, p, g, q, bnsecret); 2396 BN_free(bnsecret); 2397 BN_free(q); 2398 BN_free(g); 2399 BN_free(p); 2400 2401 return ctx; 2402} 2403 2404static void jpake_send_part(BIO *conn, const JPAKE_STEP_PART *p) 2405{ 2406 BN_print(conn, p->gx); 2407 BIO_puts(conn, "\n"); 2408 BN_print(conn, p->zkpx.gr); 2409 BIO_puts(conn, "\n"); 2410 BN_print(conn, p->zkpx.b); 2411 BIO_puts(conn, "\n"); 2412} 2413 2414static void jpake_send_step1(BIO *bconn, JPAKE_CTX *ctx) 2415{ 2416 JPAKE_STEP1 s1; 2417 2418 JPAKE_STEP1_init(&s1); 2419 JPAKE_STEP1_generate(&s1, ctx); 2420 jpake_send_part(bconn, &s1.p1); 2421 jpake_send_part(bconn, &s1.p2); 2422 (void)BIO_flush(bconn); 2423 JPAKE_STEP1_release(&s1); 2424} 2425 2426static void jpake_send_step2(BIO *bconn, JPAKE_CTX *ctx) 2427{ 2428 JPAKE_STEP2 s2; 2429 2430 JPAKE_STEP2_init(&s2); 2431 JPAKE_STEP2_generate(&s2, ctx); 2432 jpake_send_part(bconn, &s2); 2433 (void)BIO_flush(bconn); 2434 JPAKE_STEP2_release(&s2); 2435} 2436 2437static void jpake_send_step3a(BIO *bconn, JPAKE_CTX *ctx) 2438{ 2439 JPAKE_STEP3A s3a; 2440 2441 JPAKE_STEP3A_init(&s3a); 2442 JPAKE_STEP3A_generate(&s3a, ctx); 2443 BIO_write(bconn, s3a.hhk, sizeof s3a.hhk); 2444 (void)BIO_flush(bconn); 2445 JPAKE_STEP3A_release(&s3a); 2446} 2447 2448static void jpake_send_step3b(BIO *bconn, JPAKE_CTX *ctx) 2449{ 2450 JPAKE_STEP3B s3b; 2451 2452 JPAKE_STEP3B_init(&s3b); 2453 JPAKE_STEP3B_generate(&s3b, ctx); 2454 BIO_write(bconn, s3b.hk, sizeof s3b.hk); 2455 (void)BIO_flush(bconn); 2456 JPAKE_STEP3B_release(&s3b); 2457} 2458 2459static void readbn(BIGNUM **bn, BIO *bconn) 2460{ 2461 char buf[10240]; 2462 int l; 2463 2464 l = BIO_gets(bconn, buf, sizeof buf); 2465 assert(l > 0); 2466 assert(buf[l - 1] == '\n'); 2467 buf[l - 1] = '\0'; 2468 BN_hex2bn(bn, buf); 2469} 2470 2471static void jpake_receive_part(JPAKE_STEP_PART *p, BIO *bconn) 2472{ 2473 readbn(&p->gx, bconn); 2474 readbn(&p->zkpx.gr, bconn); 2475 readbn(&p->zkpx.b, bconn); 2476} 2477 2478static void jpake_receive_step1(JPAKE_CTX *ctx, BIO *bconn) 2479{ 2480 JPAKE_STEP1 s1; 2481 2482 JPAKE_STEP1_init(&s1); 2483 jpake_receive_part(&s1.p1, bconn); 2484 jpake_receive_part(&s1.p2, bconn); 2485 if (!JPAKE_STEP1_process(ctx, &s1)) { 2486 ERR_print_errors(bio_err); 2487 exit(1); 2488 } 2489 JPAKE_STEP1_release(&s1); 2490} 2491 2492static void jpake_receive_step2(JPAKE_CTX *ctx, BIO *bconn) 2493{ 2494 JPAKE_STEP2 s2; 2495 2496 JPAKE_STEP2_init(&s2); 2497 jpake_receive_part(&s2, bconn); 2498 if (!JPAKE_STEP2_process(ctx, &s2)) { 2499 ERR_print_errors(bio_err); 2500 exit(1); 2501 } 2502 JPAKE_STEP2_release(&s2); 2503} 2504 2505static void jpake_receive_step3a(JPAKE_CTX *ctx, BIO *bconn) 2506{ 2507 JPAKE_STEP3A s3a; 2508 int l; 2509 2510 JPAKE_STEP3A_init(&s3a); 2511 l = BIO_read(bconn, s3a.hhk, sizeof s3a.hhk); 2512 assert(l == sizeof s3a.hhk); 2513 if (!JPAKE_STEP3A_process(ctx, &s3a)) { 2514 ERR_print_errors(bio_err); 2515 exit(1); 2516 } 2517 JPAKE_STEP3A_release(&s3a); 2518} 2519 2520static void jpake_receive_step3b(JPAKE_CTX *ctx, BIO *bconn) 2521{ 2522 JPAKE_STEP3B s3b; 2523 int l; 2524 2525 JPAKE_STEP3B_init(&s3b); 2526 l = BIO_read(bconn, s3b.hk, sizeof s3b.hk); 2527 assert(l == sizeof s3b.hk); 2528 if (!JPAKE_STEP3B_process(ctx, &s3b)) { 2529 ERR_print_errors(bio_err); 2530 exit(1); 2531 } 2532 JPAKE_STEP3B_release(&s3b); 2533} 2534 2535void jpake_client_auth(BIO *out, BIO *conn, const char *secret) 2536{ 2537 JPAKE_CTX *ctx; 2538 BIO *bconn; 2539 2540 BIO_puts(out, "Authenticating with JPAKE\n"); 2541 2542 ctx = jpake_init("client", "server", secret); 2543 2544 bconn = BIO_new(BIO_f_buffer()); 2545 BIO_push(bconn, conn); 2546 2547 jpake_send_step1(bconn, ctx); 2548 jpake_receive_step1(ctx, bconn); 2549 jpake_send_step2(bconn, ctx); 2550 jpake_receive_step2(ctx, bconn); 2551 jpake_send_step3a(bconn, ctx); 2552 jpake_receive_step3b(ctx, bconn); 2553 2554 BIO_puts(out, "JPAKE authentication succeeded, setting PSK\n"); 2555 2556 psk_key = BN_bn2hex(JPAKE_get_shared_key(ctx)); 2557 2558 BIO_pop(bconn); 2559 BIO_free(bconn); 2560 2561 JPAKE_CTX_free(ctx); 2562} 2563 2564void jpake_server_auth(BIO *out, BIO *conn, const char *secret) 2565{ 2566 JPAKE_CTX *ctx; 2567 BIO *bconn; 2568 2569 BIO_puts(out, "Authenticating with JPAKE\n"); 2570 2571 ctx = jpake_init("server", "client", secret); 2572 2573 bconn = BIO_new(BIO_f_buffer()); 2574 BIO_push(bconn, conn); 2575 2576 jpake_receive_step1(ctx, bconn); 2577 jpake_send_step1(bconn, ctx); 2578 jpake_receive_step2(ctx, bconn); 2579 jpake_send_step2(bconn, ctx); 2580 jpake_receive_step3a(ctx, bconn); 2581 jpake_send_step3b(bconn, ctx); 2582 2583 BIO_puts(out, "JPAKE authentication succeeded, setting PSK\n"); 2584 2585 psk_key = BN_bn2hex(JPAKE_get_shared_key(ctx)); 2586 2587 BIO_pop(bconn); 2588 BIO_free(bconn); 2589 2590 JPAKE_CTX_free(ctx); 2591} 2592 2593#endif 2594 2595#if !defined(OPENSSL_NO_TLSEXT) && !defined(OPENSSL_NO_NEXTPROTONEG) 2596/*- 2597 * next_protos_parse parses a comma separated list of strings into a string 2598 * in a format suitable for passing to SSL_CTX_set_next_protos_advertised. 2599 * outlen: (output) set to the length of the resulting buffer on success. 2600 * err: (maybe NULL) on failure, an error message line is written to this BIO. 2601 * in: a NUL termianted string like "abc,def,ghi" 2602 * 2603 * returns: a malloced buffer or NULL on failure. 2604 */ 2605unsigned char *next_protos_parse(unsigned short *outlen, const char *in) 2606{ 2607 size_t len; 2608 unsigned char *out; 2609 size_t i, start = 0; 2610 2611 len = strlen(in); 2612 if (len >= 65535) 2613 return NULL; 2614 2615 out = OPENSSL_malloc(strlen(in) + 1); 2616 if (!out) 2617 return NULL; 2618 2619 for (i = 0; i <= len; ++i) { 2620 if (i == len || in[i] == ',') { 2621 if (i - start > 255) { 2622 OPENSSL_free(out); 2623 return NULL; 2624 } 2625 out[start] = i - start; 2626 start = i + 1; 2627 } else 2628 out[i + 1] = in[i]; 2629 } 2630 2631 *outlen = len + 1; 2632 return out; 2633} 2634#endif /* !OPENSSL_NO_TLSEXT && 2635 * !OPENSSL_NO_NEXTPROTONEG */ 2636 2637/* 2638 * Platform-specific sections 2639 */ 2640#if defined(_WIN32) 2641# ifdef fileno 2642# undef fileno 2643# define fileno(a) (int)_fileno(a) 2644# endif 2645 2646# include <windows.h> 2647# include <tchar.h> 2648 2649static int WIN32_rename(const char *from, const char *to) 2650{ 2651 TCHAR *tfrom = NULL, *tto; 2652 DWORD err; 2653 int ret = 0; 2654 2655 if (sizeof(TCHAR) == 1) { 2656 tfrom = (TCHAR *)from; 2657 tto = (TCHAR *)to; 2658 } else { /* UNICODE path */ 2659 2660 size_t i, flen = strlen(from) + 1, tlen = strlen(to) + 1; 2661 tfrom = (TCHAR *)malloc(sizeof(TCHAR) * (flen + tlen)); 2662 if (tfrom == NULL) 2663 goto err; 2664 tto = tfrom + flen; 2665# if !defined(_WIN32_WCE) || _WIN32_WCE>=101 2666 if (!MultiByteToWideChar(CP_ACP, 0, from, flen, (WCHAR *)tfrom, flen)) 2667# endif 2668 for (i = 0; i < flen; i++) 2669 tfrom[i] = (TCHAR)from[i]; 2670# if !defined(_WIN32_WCE) || _WIN32_WCE>=101 2671 if (!MultiByteToWideChar(CP_ACP, 0, to, tlen, (WCHAR *)tto, tlen)) 2672# endif 2673 for (i = 0; i < tlen; i++) 2674 tto[i] = (TCHAR)to[i]; 2675 } 2676 2677 if (MoveFile(tfrom, tto)) 2678 goto ok; 2679 err = GetLastError(); 2680 if (err == ERROR_ALREADY_EXISTS || err == ERROR_FILE_EXISTS) { 2681 if (DeleteFile(tto) && MoveFile(tfrom, tto)) 2682 goto ok; 2683 err = GetLastError(); 2684 } 2685 if (err == ERROR_FILE_NOT_FOUND || err == ERROR_PATH_NOT_FOUND) 2686 errno = ENOENT; 2687 else if (err == ERROR_ACCESS_DENIED) 2688 errno = EACCES; 2689 else 2690 errno = EINVAL; /* we could map more codes... */ 2691 err: 2692 ret = -1; 2693 ok: 2694 if (tfrom != NULL && tfrom != (TCHAR *)from) 2695 free(tfrom); 2696 return ret; 2697} 2698#endif 2699 2700/* app_tminterval section */ 2701#if defined(_WIN32) 2702double app_tminterval(int stop, int usertime) 2703{ 2704 FILETIME now; 2705 double ret = 0; 2706 static ULARGE_INTEGER tmstart; 2707 static int warning = 1; 2708# ifdef _WIN32_WINNT 2709 static HANDLE proc = NULL; 2710 2711 if (proc == NULL) { 2712 if (check_winnt()) 2713 proc = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, 2714 GetCurrentProcessId()); 2715 if (proc == NULL) 2716 proc = (HANDLE) - 1; 2717 } 2718 2719 if (usertime && proc != (HANDLE) - 1) { 2720 FILETIME junk; 2721 GetProcessTimes(proc, &junk, &junk, &junk, &now); 2722 } else 2723# endif 2724 { 2725 SYSTEMTIME systime; 2726 2727 if (usertime && warning) { 2728 BIO_printf(bio_err, "To get meaningful results, run " 2729 "this program on idle system.\n"); 2730 warning = 0; 2731 } 2732 GetSystemTime(&systime); 2733 SystemTimeToFileTime(&systime, &now); 2734 } 2735 2736 if (stop == TM_START) { 2737 tmstart.u.LowPart = now.dwLowDateTime; 2738 tmstart.u.HighPart = now.dwHighDateTime; 2739 } else { 2740 ULARGE_INTEGER tmstop; 2741 2742 tmstop.u.LowPart = now.dwLowDateTime; 2743 tmstop.u.HighPart = now.dwHighDateTime; 2744 2745 ret = (__int64)(tmstop.QuadPart - tmstart.QuadPart) * 1e-7; 2746 } 2747 2748 return (ret); 2749} 2750 2751#elif defined(OPENSSL_SYS_NETWARE) 2752# include <time.h> 2753 2754double app_tminterval(int stop, int usertime) 2755{ 2756 double ret = 0; 2757 static clock_t tmstart; 2758 static int warning = 1; 2759 2760 if (usertime && warning) { 2761 BIO_printf(bio_err, "To get meaningful results, run " 2762 "this program on idle system.\n"); 2763 warning = 0; 2764 } 2765 2766 if (stop == TM_START) 2767 tmstart = clock(); 2768 else 2769 ret = (clock() - tmstart) / (double)CLOCKS_PER_SEC; 2770 2771 return (ret); 2772} 2773 2774#elif defined(OPENSSL_SYSTEM_VXWORKS) 2775# include <time.h> 2776 2777double app_tminterval(int stop, int usertime) 2778{ 2779 double ret = 0; 2780# ifdef CLOCK_REALTIME 2781 static struct timespec tmstart; 2782 struct timespec now; 2783# else 2784 static unsigned long tmstart; 2785 unsigned long now; 2786# endif 2787 static int warning = 1; 2788 2789 if (usertime && warning) { 2790 BIO_printf(bio_err, "To get meaningful results, run " 2791 "this program on idle system.\n"); 2792 warning = 0; 2793 } 2794# ifdef CLOCK_REALTIME 2795 clock_gettime(CLOCK_REALTIME, &now); 2796 if (stop == TM_START) 2797 tmstart = now; 2798 else 2799 ret = ((now.tv_sec + now.tv_nsec * 1e-9) 2800 - (tmstart.tv_sec + tmstart.tv_nsec * 1e-9)); 2801# else 2802 now = tickGet(); 2803 if (stop == TM_START) 2804 tmstart = now; 2805 else 2806 ret = (now - tmstart) / (double)sysClkRateGet(); 2807# endif 2808 return (ret); 2809} 2810 2811#elif defined(OPENSSL_SYSTEM_VMS) 2812# include <time.h> 2813# include <times.h> 2814 2815double app_tminterval(int stop, int usertime) 2816{ 2817 static clock_t tmstart; 2818 double ret = 0; 2819 clock_t now; 2820# ifdef __TMS 2821 struct tms rus; 2822 2823 now = times(&rus); 2824 if (usertime) 2825 now = rus.tms_utime; 2826# else 2827 if (usertime) 2828 now = clock(); /* sum of user and kernel times */ 2829 else { 2830 struct timeval tv; 2831 gettimeofday(&tv, NULL); 2832 now = (clock_t)((unsigned long long)tv.tv_sec * CLK_TCK + 2833 (unsigned long long)tv.tv_usec * (1000000 / CLK_TCK) 2834 ); 2835 } 2836# endif 2837 if (stop == TM_START) 2838 tmstart = now; 2839 else 2840 ret = (now - tmstart) / (double)(CLK_TCK); 2841 2842 return (ret); 2843} 2844 2845#elif defined(_SC_CLK_TCK) /* by means of unistd.h */ 2846# include <sys/times.h> 2847 2848double app_tminterval(int stop, int usertime) 2849{ 2850 double ret = 0; 2851 struct tms rus; 2852 clock_t now = times(&rus); 2853 static clock_t tmstart; 2854 2855 if (usertime) 2856 now = rus.tms_utime; 2857 2858 if (stop == TM_START) 2859 tmstart = now; 2860 else { 2861 long int tck = sysconf(_SC_CLK_TCK); 2862 ret = (now - tmstart) / (double)tck; 2863 } 2864 2865 return (ret); 2866} 2867 2868#else 2869# include <sys/time.h> 2870# include <sys/resource.h> 2871 2872double app_tminterval(int stop, int usertime) 2873{ 2874 double ret = 0; 2875 struct rusage rus; 2876 struct timeval now; 2877 static struct timeval tmstart; 2878 2879 if (usertime) 2880 getrusage(RUSAGE_SELF, &rus), now = rus.ru_utime; 2881 else 2882 gettimeofday(&now, NULL); 2883 2884 if (stop == TM_START) 2885 tmstart = now; 2886 else 2887 ret = ((now.tv_sec + now.tv_usec * 1e-6) 2888 - (tmstart.tv_sec + tmstart.tv_usec * 1e-6)); 2889 2890 return ret; 2891} 2892#endif 2893 2894/* app_isdir section */ 2895#ifdef _WIN32 2896int app_isdir(const char *name) 2897{ 2898 HANDLE hList; 2899 WIN32_FIND_DATA FileData; 2900# if defined(UNICODE) || defined(_UNICODE) 2901 size_t i, len_0 = strlen(name) + 1; 2902 2903 if (len_0 > sizeof(FileData.cFileName) / sizeof(FileData.cFileName[0])) 2904 return -1; 2905 2906# if !defined(_WIN32_WCE) || _WIN32_WCE>=101 2907 if (!MultiByteToWideChar 2908 (CP_ACP, 0, name, len_0, FileData.cFileName, len_0)) 2909# endif 2910 for (i = 0; i < len_0; i++) 2911 FileData.cFileName[i] = (WCHAR)name[i]; 2912 2913 hList = FindFirstFile(FileData.cFileName, &FileData); 2914# else 2915 hList = FindFirstFile(name, &FileData); 2916# endif 2917 if (hList == INVALID_HANDLE_VALUE) 2918 return -1; 2919 FindClose(hList); 2920 return ((FileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0); 2921} 2922#else 2923# include <sys/stat.h> 2924# ifndef S_ISDIR 2925# if defined(_S_IFMT) && defined(_S_IFDIR) 2926# define S_ISDIR(a) (((a) & _S_IFMT) == _S_IFDIR) 2927# else 2928# define S_ISDIR(a) (((a) & S_IFMT) == S_IFDIR) 2929# endif 2930# endif 2931 2932int app_isdir(const char *name) 2933{ 2934# if defined(S_ISDIR) 2935 struct stat st; 2936 2937 if (stat(name, &st) == 0) 2938 return S_ISDIR(st.st_mode); 2939 else 2940 return -1; 2941# else 2942 return -1; 2943# endif 2944} 2945#endif 2946 2947/* raw_read|write section */ 2948#if defined(_WIN32) && defined(STD_INPUT_HANDLE) 2949int raw_read_stdin(void *buf, int siz) 2950{ 2951 DWORD n; 2952 if (ReadFile(GetStdHandle(STD_INPUT_HANDLE), buf, siz, &n, NULL)) 2953 return (n); 2954 else 2955 return (-1); 2956} 2957#else 2958int raw_read_stdin(void *buf, int siz) 2959{ 2960 return read(fileno(stdin), buf, siz); 2961} 2962#endif 2963 2964#if defined(_WIN32) && defined(STD_OUTPUT_HANDLE) 2965int raw_write_stdout(const void *buf, int siz) 2966{ 2967 DWORD n; 2968 if (WriteFile(GetStdHandle(STD_OUTPUT_HANDLE), buf, siz, &n, NULL)) 2969 return (n); 2970 else 2971 return (-1); 2972} 2973#else 2974int raw_write_stdout(const void *buf, int siz) 2975{ 2976 return write(fileno(stdout), buf, siz); 2977} 2978#endif 2979