1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 * 21 * 22 * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 /* 27 * This file implements the sign CSR operation for this tool. 28 */ 29 30 #include <stdio.h> 31 #include <errno.h> 32 #include <string.h> 33 #include <cryptoutil.h> 34 #include <security/cryptoki.h> 35 #include "common.h" 36 37 #include <kmfapi.h> 38 #include <kmfapiP.h> 39 40 #define SET_VALUE(f, s) \ 41 rv = f; \ 42 if (rv != KMF_OK) { \ 43 cryptoerror(LOG_STDERR, \ 44 gettext("Failed to set %s: 0x%02x\n"), s, rv); \ 45 goto cleanup; \ 46 } 47 48 49 static int 50 read_csrdata(KMF_HANDLE_T handle, char *csrfile, KMF_CSR_DATA *csrdata) 51 { 52 KMF_RETURN rv = KMF_OK; 53 KMF_ENCODE_FORMAT csrfmt; 54 KMF_DATA csrfiledata = {NULL, 0}; 55 KMF_DATA rawcsr = {NULL, 0}; 56 57 rv = kmf_get_file_format(csrfile, &csrfmt); 58 if (rv != KMF_OK) 59 return (rv); 60 61 rv = kmf_read_input_file(handle, csrfile, &csrfiledata); 62 if (rv != KMF_OK) 63 return (rv); 64 65 if (csrfmt == KMF_FORMAT_PEM) { 66 rv = kmf_pem_to_der(csrfiledata.Data, csrfiledata.Length, 67 &rawcsr.Data, (int *)&rawcsr.Length); 68 if (rv != KMF_OK) 69 return (rv); 70 71 kmf_free_data(&csrfiledata); 72 } else { 73 rawcsr.Data = csrfiledata.Data; 74 rawcsr.Length = csrfiledata.Length; 75 } 76 77 rv = kmf_decode_csr(handle, &rawcsr, csrdata); 78 kmf_free_data(&rawcsr); 79 80 return (rv); 81 } 82 83 static KMF_RETURN 84 find_csr_extn(KMF_X509_EXTENSIONS *extnlist, KMF_OID *extoid, 85 KMF_X509_EXTENSION *outextn) 86 { 87 int i, found = 0; 88 KMF_X509_EXTENSION *eptr; 89 KMF_RETURN rv = KMF_OK; 90 91 (void) memset(outextn, 0, sizeof (KMF_X509_EXTENSION)); 92 for (i = 0; !found && i < extnlist->numberOfExtensions; i++) { 93 eptr = &extnlist->extensions[i]; 94 if (IsEqualOid(extoid, &eptr->extnId)) { 95 rv = copy_extension_data(outextn, eptr); 96 found++; 97 } 98 } 99 if (found == 0 || rv != KMF_OK) 100 return (1); 101 else 102 return (rv); 103 } 104 105 static int 106 build_cert_from_csr(KMF_CSR_DATA *csrdata, 107 KMF_X509_CERTIFICATE *signedCert, 108 KMF_BIGINT *serial, 109 uint32_t ltime, 110 char *issuer, char *subject, 111 char *altname, 112 KMF_GENERALNAMECHOICES alttype, 113 int altcrit, 114 uint16_t kubits, 115 int kucrit, 116 EKU_LIST *ekulist) 117 { 118 KMF_RETURN rv = KMF_OK; 119 KMF_X509_NAME issuerDN, subjectDN; 120 121 /* 122 * If the CSR is ok, now we can generate the final certificate. 123 */ 124 (void) memset(signedCert, 0, sizeof (KMF_X509_CERTIFICATE)); 125 (void) memset(&issuerDN, 0, sizeof (issuerDN)); 126 (void) memset(&subjectDN, 0, sizeof (subjectDN)); 127 128 SET_VALUE(kmf_set_cert_version(signedCert, 2), "version number"); 129 130 SET_VALUE(kmf_set_cert_serial(signedCert, serial), "serial number"); 131 132 SET_VALUE(kmf_set_cert_validity(signedCert, NULL, ltime), 133 "validity time"); 134 135 if (issuer) { 136 if (kmf_dn_parser(issuer, &issuerDN) != KMF_OK) { 137 cryptoerror(LOG_STDERR, 138 gettext("Issuer name cannot be parsed\n")); 139 return (PK_ERR_USAGE); 140 } 141 SET_VALUE(kmf_set_cert_issuer(signedCert, &issuerDN), 142 "Issuer Name"); 143 } 144 if (subject) { 145 if (kmf_dn_parser(subject, &subjectDN) != KMF_OK) { 146 cryptoerror(LOG_STDERR, 147 gettext("Subject name cannot be parsed\n")); 148 return (PK_ERR_USAGE); 149 } 150 SET_VALUE(kmf_set_cert_subject(signedCert, &subjectDN), 151 "Subject Name"); 152 } else { 153 signedCert->certificate.subject = csrdata->csr.subject; 154 } 155 156 signedCert->certificate.subjectPublicKeyInfo = 157 csrdata->csr.subjectPublicKeyInfo; 158 159 signedCert->certificate.extensions = csrdata->csr.extensions; 160 161 signedCert->certificate.signature = 162 csrdata->signature.algorithmIdentifier; 163 164 if (kubits != 0) { 165 KMF_X509_EXTENSION extn; 166 uint16_t oldbits; 167 /* 168 * If the CSR already has KU, merge them. 169 */ 170 rv = find_csr_extn(&csrdata->csr.extensions, 171 (KMF_OID *)&KMFOID_KeyUsage, &extn); 172 if (rv == KMF_OK) { 173 extn.critical |= kucrit; 174 if (extn.value.tagAndValue->value.Length > 1) { 175 oldbits = 176 extn.value.tagAndValue->value.Data[1] << 8; 177 } else { 178 oldbits = 179 extn.value.tagAndValue->value.Data[0]; 180 } 181 oldbits |= kubits; 182 } else { 183 SET_VALUE(kmf_set_cert_ku(signedCert, kucrit, kubits), 184 "KeyUsage"); 185 } 186 } 187 if (altname != NULL) { 188 SET_VALUE(kmf_set_cert_subject_altname(signedCert, 189 altcrit, alttype, altname), "subjectAltName"); 190 } 191 if (ekulist != NULL) { 192 int i; 193 for (i = 0; rv == KMF_OK && i < ekulist->eku_count; i++) { 194 SET_VALUE(kmf_add_cert_eku(signedCert, 195 &ekulist->ekulist[i], 196 ekulist->critlist[i]), "Extended Key Usage"); 197 } 198 } 199 cleanup: 200 if (issuer != NULL) 201 kmf_free_dn(&issuerDN); 202 if (subject != NULL) 203 kmf_free_dn(&subjectDN); 204 205 return (rv); 206 } 207 208 static int 209 pk_sign_cert(KMF_HANDLE_T handle, KMF_X509_CERTIFICATE *cert, 210 KMF_KEY_HANDLE *key, KMF_DATA *outdata) 211 { 212 KMF_RETURN rv; 213 int numattr; 214 KMF_ATTRIBUTE attrlist[4]; 215 216 numattr = 0; 217 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYSTORE_TYPE_ATTR, 218 &key->kstype, sizeof (KMF_KEYSTORE_TYPE)); 219 numattr++; 220 221 kmf_set_attr_at_index(attrlist, numattr, KMF_KEY_HANDLE_ATTR, 222 key, sizeof (KMF_KEY_HANDLE_ATTR)); 223 numattr++; 224 225 /* cert data that is to be signed */ 226 kmf_set_attr_at_index(attrlist, numattr, KMF_X509_CERTIFICATE_ATTR, 227 cert, sizeof (KMF_X509_CERTIFICATE)); 228 numattr++; 229 230 /* output buffer for the signed cert */ 231 kmf_set_attr_at_index(attrlist, numattr, KMF_CERT_DATA_ATTR, 232 outdata, sizeof (KMF_DATA)); 233 numattr++; 234 235 if ((rv = kmf_sign_cert(handle, numattr, attrlist)) != KMF_OK) { 236 cryptoerror(LOG_STDERR, 237 gettext("Failed to sign certificate.\n")); 238 return (rv); 239 } 240 241 return (rv); 242 } 243 244 static int 245 pk_signcsr_files(KMF_HANDLE_T handle, 246 char *signkey, 247 char *csrfile, 248 KMF_BIGINT *serial, 249 char *certfile, 250 char *issuer, 251 char *subject, 252 char *altname, 253 KMF_GENERALNAMECHOICES alttype, 254 int altcrit, 255 uint16_t kubits, 256 int kucrit, 257 EKU_LIST *ekulist, 258 uint32_t ltime, 259 KMF_ENCODE_FORMAT fmt) 260 { 261 KMF_RETURN rv = KMF_OK; 262 KMF_CSR_DATA csrdata; 263 KMF_ATTRIBUTE attrlist[16]; 264 KMF_X509_CERTIFICATE signedCert; 265 KMF_KEYSTORE_TYPE kstype = KMF_KEYSTORE_OPENSSL; 266 KMF_KEY_CLASS keyclass = KMF_ASYM_PRI; 267 KMF_KEY_HANDLE cakey; 268 KMF_DATA certdata = {NULL, 0}; 269 int numattr, count; 270 271 rv = read_csrdata(handle, csrfile, &csrdata); 272 if (rv != KMF_OK) { 273 cryptoerror(LOG_STDERR, 274 gettext("Error reading CSR data\n")); 275 return (rv); 276 } 277 278 /* verify the signature first */ 279 numattr = 0; 280 kmf_set_attr_at_index(attrlist, numattr, KMF_CSR_DATA_ATTR, 281 &csrdata, sizeof (csrdata)); 282 numattr++; 283 284 rv = kmf_verify_csr(handle, numattr, attrlist); 285 if (rv != KMF_OK) { 286 cryptoerror(LOG_STDERR, gettext("CSR signature " 287 "verification failed.\n")); 288 goto cleanup; 289 } 290 291 rv = build_cert_from_csr(&csrdata, &signedCert, serial, ltime, 292 issuer, subject, altname, alttype, altcrit, kubits, 293 kucrit, ekulist); 294 295 if (rv != KMF_OK) 296 goto cleanup; 297 298 /* 299 * Find the signing key. 300 */ 301 (void) memset(&cakey, 0, sizeof (cakey)); 302 303 numattr = 0; 304 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYSTORE_TYPE_ATTR, 305 &kstype, sizeof (kstype)); 306 numattr++; 307 308 kmf_set_attr_at_index(attrlist, numattr, KMF_KEY_FILENAME_ATTR, 309 signkey, strlen(signkey)); 310 numattr++; 311 312 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYCLASS_ATTR, 313 &keyclass, sizeof (keyclass)); 314 numattr++; 315 316 kmf_set_attr_at_index(attrlist, numattr, KMF_KEY_HANDLE_ATTR, 317 &cakey, sizeof (cakey)); 318 numattr++; 319 320 count = 1; 321 kmf_set_attr_at_index(attrlist, numattr, KMF_COUNT_ATTR, 322 &count, sizeof (count)); 323 numattr++; 324 325 rv = kmf_find_key(handle, numattr, attrlist); 326 if (rv != KMF_OK) { 327 cryptoerror(LOG_STDERR, gettext( 328 "Error finding CA signing key\n")); 329 goto cleanup; 330 } 331 332 rv = pk_sign_cert(handle, &signedCert, &cakey, &certdata); 333 if (rv != KMF_OK) { 334 cryptoerror(LOG_STDERR, gettext( 335 "Error signing certificate.\n")); 336 goto cleanup; 337 } 338 339 rv = kmf_create_cert_file(&certdata, fmt, certfile); 340 341 cleanup: 342 kmf_free_signed_csr(&csrdata); 343 kmf_free_data(&certdata); 344 kmf_free_kmf_key(handle, &cakey); 345 return (rv); 346 } 347 348 static int 349 pk_signcsr_pk11_nss(KMF_HANDLE_T handle, 350 KMF_KEYSTORE_TYPE kstype, 351 char *dir, char *prefix, 352 char *token, KMF_CREDENTIAL *cred, 353 char *signkey, char *csrfile, 354 KMF_BIGINT *serial, char *certfile, char *issuer, char *subject, 355 char *altname, KMF_GENERALNAMECHOICES alttype, int altcrit, 356 uint16_t kubits, int kucrit, 357 EKU_LIST *ekulist, uint32_t ltime, 358 KMF_ENCODE_FORMAT fmt, int store, char *outlabel) 359 { 360 KMF_RETURN rv = KMF_OK; 361 KMF_DATA outcert = {NULL, 0}; 362 KMF_CSR_DATA csrdata; 363 KMF_KEY_HANDLE casignkey; 364 KMF_KEY_CLASS keyclass = KMF_ASYM_PRI; 365 int numattr = 0; 366 int keys = 1; 367 KMF_ATTRIBUTE attrlist[16]; 368 KMF_X509_CERTIFICATE signedCert; 369 boolean_t token_bool = B_TRUE; 370 boolean_t private_bool = B_TRUE; 371 372 (void) memset(&casignkey, 0, sizeof (KMF_KEY_HANDLE)); 373 374 rv = read_csrdata(handle, csrfile, &csrdata); 375 if (rv != KMF_OK) { 376 cryptoerror(LOG_STDERR, 377 gettext("Error reading CSR data\n")); 378 return (rv); 379 } 380 381 if (kstype == KMF_KEYSTORE_PK11TOKEN) { 382 rv = select_token(handle, token, FALSE); 383 } else if (kstype == KMF_KEYSTORE_NSS) { 384 rv = configure_nss(handle, dir, prefix); 385 } 386 387 /* verify the signature first */ 388 kmf_set_attr_at_index(attrlist, numattr, KMF_CSR_DATA_ATTR, 389 &csrdata, sizeof (csrdata)); 390 numattr++; 391 392 rv = kmf_verify_csr(handle, numattr, attrlist); 393 if (rv != KMF_OK) { 394 cryptoerror(LOG_STDERR, gettext("CSR signature " 395 "verification failed.\n")); 396 goto cleanup; 397 } 398 399 rv = build_cert_from_csr(&csrdata, 400 &signedCert, serial, ltime, 401 issuer, subject, altname, 402 alttype, altcrit, kubits, 403 kucrit, ekulist); 404 405 if (rv != KMF_OK) 406 goto cleanup; 407 408 /* 409 * Find the signing key. 410 */ 411 numattr = 0; 412 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYSTORE_TYPE_ATTR, 413 &kstype, sizeof (kstype)); 414 numattr++; 415 if (kstype == KMF_KEYSTORE_NSS) { 416 kmf_set_attr_at_index(attrlist, numattr, KMF_TOKEN_LABEL_ATTR, 417 token, strlen(token)); 418 numattr++; 419 } 420 421 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYLABEL_ATTR, signkey, 422 strlen(signkey)); 423 numattr++; 424 425 kmf_set_attr_at_index(attrlist, numattr, KMF_PRIVATE_BOOL_ATTR, 426 &private_bool, sizeof (private_bool)); 427 numattr++; 428 429 kmf_set_attr_at_index(attrlist, numattr, KMF_TOKEN_BOOL_ATTR, 430 &token_bool, sizeof (token_bool)); 431 numattr++; 432 433 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYCLASS_ATTR, 434 &keyclass, sizeof (keyclass)); 435 numattr++; 436 437 kmf_set_attr_at_index(attrlist, numattr, KMF_CREDENTIAL_ATTR, 438 cred, sizeof (KMF_CREDENTIAL_ATTR)); 439 numattr++; 440 441 kmf_set_attr_at_index(attrlist, numattr, KMF_COUNT_ATTR, 442 &keys, sizeof (keys)); 443 numattr++; 444 445 kmf_set_attr_at_index(attrlist, numattr, KMF_KEY_HANDLE_ATTR, 446 &casignkey, sizeof (casignkey)); 447 numattr++; 448 449 rv = kmf_find_key(handle, numattr, attrlist); 450 if (rv != KMF_OK) { 451 cryptoerror(LOG_STDERR, 452 gettext("Failed to find signing key\n")); 453 goto cleanup; 454 } 455 456 /* 457 * If we found the key, now we can sign the cert. 458 */ 459 rv = pk_sign_cert(handle, &signedCert, &casignkey, &outcert); 460 if (rv != KMF_OK) { 461 cryptoerror(LOG_STDERR, gettext( 462 "Error signing certificate.\n")); 463 goto cleanup; 464 } 465 466 /* 467 * Store it on the token if the user asked for it. 468 */ 469 if (store) { 470 numattr = 0; 471 kmf_set_attr_at_index(attrlist, numattr, KMF_KEYSTORE_TYPE_ATTR, 472 &kstype, sizeof (kstype)); 473 numattr++; 474 475 kmf_set_attr_at_index(attrlist, numattr, KMF_CERT_DATA_ATTR, 476 &outcert, sizeof (KMF_DATA)); 477 numattr++; 478 479 if (outlabel != NULL) { 480 kmf_set_attr_at_index(attrlist, numattr, 481 KMF_CERT_LABEL_ATTR, 482 outlabel, strlen(outlabel)); 483 numattr++; 484 } 485 486 if (kstype == KMF_KEYSTORE_NSS) { 487 if (token != NULL) 488 kmf_set_attr_at_index(attrlist, numattr, 489 KMF_TOKEN_LABEL_ATTR, 490 token, strlen(token)); 491 numattr++; 492 } 493 494 rv = kmf_store_cert(handle, numattr, attrlist); 495 if (rv != KMF_OK) { 496 display_error(handle, rv, 497 gettext("Failed to store cert " 498 "on PKCS#11 token.\n")); 499 rv = KMF_OK; 500 /* Not fatal, we can still write it to a file. */ 501 } 502 } 503 rv = kmf_create_cert_file(&outcert, fmt, certfile); 504 505 cleanup: 506 kmf_free_signed_csr(&csrdata); 507 kmf_free_data(&outcert); 508 kmf_free_kmf_key(handle, &casignkey); 509 510 return (rv); 511 } 512 513 /* 514 * sign a CSR and generate an x509v3 certificate file. 515 */ 516 int 517 pk_signcsr(int argc, char *argv[]) 518 { 519 int opt; 520 extern int optind_av; 521 extern char *optarg_av; 522 char *token_spec = NULL; 523 char *subject = NULL; 524 char *issuer = NULL; 525 char *dir = NULL; 526 char *prefix = NULL; 527 char *csrfile = NULL; 528 char *serstr = NULL; 529 char *ekustr = NULL; 530 char *kustr = NULL; 531 char *format = NULL; 532 char *storestr = NULL; 533 char *altname = NULL; 534 char *certfile = NULL; 535 char *lifetime = NULL; 536 char *signkey = NULL; 537 char *outlabel = NULL; 538 uint32_t ltime = 365 * 24 * 60 * 60; /* 1 Year */ 539 int store = 0; 540 uint16_t kubits = 0; 541 int altcrit = 0, kucrit = 0; 542 KMF_BIGINT serial = { NULL, 0 }; 543 EKU_LIST *ekulist = NULL; 544 KMF_KEYSTORE_TYPE kstype = 0; 545 KMF_RETURN rv = KMF_OK; 546 KMF_HANDLE_T kmfhandle = NULL; 547 KMF_CREDENTIAL tokencred = {NULL, 0}; 548 KMF_GENERALNAMECHOICES alttype = 0; 549 KMF_ENCODE_FORMAT fmt = KMF_FORMAT_PEM; 550 551 /* Parse command line options. Do NOT i18n/l10n. */ 552 while ((opt = getopt_av(argc, argv, 553 "k:(keystore)c:(csr)T:(token)d:(dir)" 554 "p:(prefix)S:(serial)s:(subject)a:(altname)" 555 "t:(store)F:(format)K:(keyusage)l:(signkey)" 556 "L:(lifetime)e:(eku)i:(issuer)" 557 "n:(outlabel)o:(outcert)")) != EOF) { 558 if (EMPTYSTRING(optarg_av)) 559 return (PK_ERR_USAGE); 560 switch (opt) { 561 case 'k': 562 if (kstype != 0) 563 return (PK_ERR_USAGE); 564 kstype = KS2Int(optarg_av); 565 if (kstype == 0) 566 return (PK_ERR_USAGE); 567 break; 568 case 't': 569 if (storestr != NULL) 570 return (PK_ERR_USAGE); 571 storestr = optarg_av; 572 store = yn_to_int(optarg_av); 573 if (store == -1) 574 return (PK_ERR_USAGE); 575 break; 576 case 'a': 577 if (altname) 578 return (PK_ERR_USAGE); 579 altname = optarg_av; 580 break; 581 case 's': 582 if (subject) 583 return (PK_ERR_USAGE); 584 subject = optarg_av; 585 break; 586 case 'i': 587 if (issuer) 588 return (PK_ERR_USAGE); 589 issuer = optarg_av; 590 break; 591 case 'd': 592 if (dir) 593 return (PK_ERR_USAGE); 594 dir = optarg_av; 595 break; 596 case 'p': 597 if (prefix) 598 return (PK_ERR_USAGE); 599 prefix = optarg_av; 600 break; 601 case 'S': 602 if (serstr != NULL) 603 return (PK_ERR_USAGE); 604 serstr = optarg_av; 605 break; 606 case 'c': 607 if (csrfile) 608 return (PK_ERR_USAGE); 609 csrfile = optarg_av; 610 break; 611 case 'T': /* token specifier */ 612 if (token_spec) 613 return (PK_ERR_USAGE); 614 token_spec = optarg_av; 615 break; 616 case 'l': /* object with specific label */ 617 if (signkey) 618 return (PK_ERR_USAGE); 619 signkey = optarg_av; 620 break; 621 case 'e': 622 if (ekustr != NULL) 623 return (PK_ERR_USAGE); 624 ekustr = optarg_av; 625 break; 626 case 'K': 627 if (kustr != NULL) 628 return (PK_ERR_USAGE); 629 kustr = optarg_av; 630 break; 631 case 'F': 632 if (format != NULL) 633 return (PK_ERR_USAGE); 634 format = optarg_av; 635 break; 636 case 'o': 637 if (certfile != NULL) 638 return (PK_ERR_USAGE); 639 certfile = optarg_av; 640 break; 641 case 'L': 642 if (lifetime != NULL) 643 return (PK_ERR_USAGE); 644 lifetime = optarg_av; 645 break; 646 case 'n': 647 if (outlabel != NULL) 648 return (PK_ERR_USAGE); 649 outlabel = optarg_av; 650 break; 651 default: 652 return (PK_ERR_USAGE); 653 } 654 } 655 /* No additional args allowed. */ 656 argc -= optind_av; 657 argv += optind_av; 658 if (argc) 659 return (PK_ERR_USAGE); 660 661 662 /* Assume keystore = PKCS#11 if not specified. */ 663 if (kstype == 0) 664 kstype = KMF_KEYSTORE_PK11TOKEN; 665 666 DIR_OPTION_CHECK(kstype, dir); 667 668 if (signkey == NULL) { 669 (void) fprintf(stderr, gettext("The signing key label " 670 "or filename was not specified\n")); 671 return (PK_ERR_USAGE); 672 } 673 if (csrfile == NULL) { 674 (void) fprintf(stderr, gettext("The CSR filename was not" 675 " specified\n")); 676 return (PK_ERR_USAGE); 677 } 678 if (certfile == NULL) { 679 (void) fprintf(stderr, gettext("The output certificate file " 680 "was not specified\n")); 681 return (PK_ERR_USAGE); 682 } 683 if (issuer == NULL) { 684 (void) fprintf(stderr, gettext("The issuer DN " 685 "was not specified\n")); 686 return (PK_ERR_USAGE); 687 } 688 if (lifetime != NULL) { 689 if (Str2Lifetime(lifetime, <ime) != 0) { 690 cryptoerror(LOG_STDERR, 691 gettext("Error parsing lifetime string\n")); 692 return (PK_ERR_USAGE); 693 } 694 } 695 if (kstype == KMF_KEYSTORE_PK11TOKEN && EMPTYSTRING(token_spec)) { 696 token_spec = PK_DEFAULT_PK11TOKEN; 697 } else if (kstype == KMF_KEYSTORE_NSS && EMPTYSTRING(token_spec)) { 698 token_spec = DEFAULT_NSS_TOKEN; 699 } 700 701 if (serstr != NULL) { 702 uchar_t *bytes = NULL; 703 size_t bytelen; 704 705 rv = kmf_hexstr_to_bytes((uchar_t *)serstr, &bytes, &bytelen); 706 if (rv != KMF_OK || bytes == NULL) { 707 (void) fprintf(stderr, gettext("Serial number " 708 "must be specified as a hex number " 709 "(ex: 0x0102030405ffeeddee)\n")); 710 return (PK_ERR_USAGE); 711 } 712 serial.val = bytes; 713 serial.len = bytelen; 714 } else { 715 (void) fprintf(stderr, gettext("The serial number was not" 716 " specified\n")); 717 return (PK_ERR_USAGE); 718 } 719 720 if ((kstype == KMF_KEYSTORE_PK11TOKEN || 721 kstype == KMF_KEYSTORE_NSS)) { 722 /* Need to get password for private key access */ 723 (void) get_token_password(kstype, token_spec, 724 &tokencred); 725 } 726 if (kustr != NULL) { 727 rv = verify_keyusage(kustr, &kubits, &kucrit); 728 if (rv != KMF_OK) { 729 (void) fprintf(stderr, gettext("KeyUsage " 730 "must be specified as a comma-separated list. " 731 "See the man page for details.\n")); 732 rv = PK_ERR_USAGE; 733 goto end; 734 } 735 } 736 if (ekustr != NULL) { 737 rv = verify_ekunames(ekustr, &ekulist); 738 if (rv != KMF_OK) { 739 (void) fprintf(stderr, gettext("EKUs must " 740 "be specified as a comma-separated list. " 741 "See the man page for details.\n")); 742 rv = PK_ERR_USAGE; 743 goto end; 744 } 745 } 746 if (altname != NULL) { 747 char *p; 748 rv = verify_altname(altname, &alttype, &altcrit); 749 if (rv != KMF_OK) { 750 (void) fprintf(stderr, gettext("Subject AltName " 751 "must be specified as a name=value pair. " 752 "See the man page for details.\n")); 753 rv = PK_ERR_USAGE; 754 goto end; 755 } 756 /* advance the altname past the '=' sign */ 757 p = strchr(altname, '='); 758 if (p != NULL) 759 altname = p + 1; 760 } 761 if (format && (fmt = Str2Format(format)) == KMF_FORMAT_UNDEF) { 762 cryptoerror(LOG_STDERR, 763 gettext("Error parsing format string (%s).\n"), 764 format); 765 return (PK_ERR_USAGE); 766 } 767 768 if ((rv = kmf_initialize(&kmfhandle, NULL, NULL)) != KMF_OK) { 769 return (rv); 770 } 771 772 if (kstype == KMF_KEYSTORE_PK11TOKEN) { 773 rv = pk_signcsr_pk11_nss(kmfhandle, 774 kstype, dir, prefix, token_spec, &tokencred, 775 signkey, csrfile, &serial, certfile, issuer, subject, 776 altname, alttype, altcrit, kubits, kucrit, 777 ekulist, ltime, fmt, store, outlabel); 778 779 } else if (kstype == KMF_KEYSTORE_NSS) { 780 if (dir == NULL) 781 dir = PK_DEFAULT_DIRECTORY; 782 783 rv = pk_signcsr_pk11_nss(kmfhandle, 784 kstype, dir, prefix, token_spec, &tokencred, 785 signkey, csrfile, &serial, certfile, issuer, subject, 786 altname, alttype, altcrit, kubits, kucrit, 787 ekulist, ltime, fmt, store, outlabel); 788 789 } else if (kstype == KMF_KEYSTORE_OPENSSL) { 790 rv = pk_signcsr_files(kmfhandle, 791 signkey, csrfile, &serial, certfile, issuer, subject, 792 altname, alttype, altcrit, kubits, kucrit, 793 ekulist, ltime, fmt); 794 } 795 796 end: 797 if (rv != KMF_OK) { 798 display_error(kmfhandle, rv, 799 gettext("Error listing objects")); 800 } 801 802 if (serial.val != NULL) 803 free(serial.val); 804 805 if (tokencred.cred != NULL) 806 free(tokencred.cred); 807 808 free_eku_list(ekulist); 809 810 (void) kmf_finalize(kmfhandle); 811 return (rv); 812 } 813