1 /* 2 * The Initial Developer of the Original Code is International 3 * Business Machines Corporation. Portions created by IBM 4 * Corporation are Copyright (C) 2005 International Business 5 * Machines Corporation. All Rights Reserved. 6 * 7 * This program is free software; you can redistribute it and/or modify 8 * it under the terms of the Common Public License as published by 9 * IBM Corporation; either version 1 of the License, or (at your option) 10 * any later version. 11 * 12 * This program is distributed in the hope that it will be useful, 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 * Common Public License for more details. 16 * 17 * You should have received a copy of the Common Public License 18 * along with this program; if not, a copy can be viewed at 19 * http://www.opensource.org/licenses/cpl1.0.php. 20 */ 21 /* 22 * Copyright 2010 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 #include <pthread.h> 27 #include <string.h> 28 29 #include <sys/types.h> 30 #include <sys/stat.h> 31 #include <uuid/uuid.h> 32 #include <fcntl.h> 33 #include <errno.h> 34 #include <pwd.h> 35 #include <syslog.h> 36 37 #include <openssl/rsa.h> 38 39 #include <tss/platform.h> 40 #include <tss/tss_defines.h> 41 #include <tss/tss_typedef.h> 42 #include <tss/tss_structs.h> 43 #include <tss/tss_error.h> 44 #include <tss/tcs_error.h> 45 #include <tss/tspi.h> 46 #include <trousers/trousers.h> 47 48 #include "tpmtok_int.h" 49 #include "tpmtok_defs.h" 50 51 #define MAX_RSA_KEYLENGTH 512 52 53 extern void stlogit(char *fmt, ...); 54 55 CK_RV token_rng(TSS_HCONTEXT, CK_BYTE *, CK_ULONG); 56 int tok_slot2local(CK_SLOT_ID); 57 CK_RV token_specific_session(CK_SLOT_ID); 58 CK_RV token_specific_final(TSS_HCONTEXT); 59 60 CK_RV 61 token_specific_rsa_decrypt( 62 TSS_HCONTEXT, 63 CK_BYTE *, 64 CK_ULONG, 65 CK_BYTE *, 66 CK_ULONG *, 67 OBJECT *); 68 69 CK_RV 70 token_specific_rsa_encrypt( 71 TSS_HCONTEXT, 72 CK_BYTE *, 73 CK_ULONG, 74 CK_BYTE *, 75 CK_ULONG *, 76 OBJECT *); 77 78 CK_RV 79 token_specific_rsa_sign( 80 TSS_HCONTEXT, 81 CK_BYTE *, 82 CK_ULONG, 83 CK_BYTE *, 84 CK_ULONG *, 85 OBJECT *); 86 87 CK_RV 88 token_specific_rsa_verify(TSS_HCONTEXT, CK_BYTE *, 89 CK_ULONG, CK_BYTE *, CK_ULONG, OBJECT *); 90 91 CK_RV 92 token_specific_rsa_generate_keypair(TSS_HCONTEXT, 93 TEMPLATE *, 94 TEMPLATE *); 95 96 CK_RV 97 token_specific_sha_init(DIGEST_CONTEXT *); 98 99 CK_RV 100 token_specific_sha_update(DIGEST_CONTEXT *, 101 CK_BYTE *, 102 CK_ULONG); 103 104 CK_RV 105 token_specific_sha_final(DIGEST_CONTEXT *, 106 CK_BYTE *, 107 CK_ULONG *); 108 109 CK_RV token_specific_login(TSS_HCONTEXT, CK_USER_TYPE, CK_CHAR_PTR, CK_ULONG); 110 CK_RV token_specific_logout(TSS_HCONTEXT); 111 CK_RV token_specific_init_pin(TSS_HCONTEXT, CK_CHAR_PTR, CK_ULONG); 112 CK_RV token_specific_set_pin(ST_SESSION_HANDLE, CK_CHAR_PTR, 113 CK_ULONG, CK_CHAR_PTR, CK_ULONG); 114 CK_RV token_specific_verify_so_pin(TSS_HCONTEXT, CK_CHAR_PTR, CK_ULONG); 115 116 static CK_RV 117 token_specific_init(char *, CK_SLOT_ID, TSS_HCONTEXT *); 118 119 struct token_specific_struct token_specific = { 120 "TPM_Debug", 121 &token_specific_init, 122 NULL, 123 &token_rng, 124 &token_specific_session, 125 &token_specific_final, 126 &token_specific_rsa_decrypt, 127 &token_specific_rsa_encrypt, 128 &token_specific_rsa_sign, 129 &token_specific_rsa_verify, 130 &token_specific_rsa_generate_keypair, 131 NULL, 132 NULL, 133 NULL, 134 &token_specific_login, 135 &token_specific_logout, 136 &token_specific_init_pin, 137 &token_specific_set_pin, 138 &token_specific_verify_so_pin 139 }; 140 141 /* The context we'll use globally to connect to the TSP */ 142 143 /* TSP key handles */ 144 TSS_HKEY hPublicRootKey = NULL_HKEY; 145 TSS_HKEY hPublicLeafKey = NULL_HKEY; 146 TSS_HKEY hPrivateRootKey = NULL_HKEY; 147 TSS_HKEY hPrivateLeafKey = NULL_HKEY; 148 149 TSS_UUID publicRootKeyUUID; 150 TSS_UUID publicLeafKeyUUID; 151 TSS_UUID privateRootKeyUUID; 152 TSS_UUID privateLeafKeyUUID; 153 154 /* TSP policy handles */ 155 TSS_HPOLICY hDefaultPolicy = NULL_HPOLICY; 156 157 /* PKCS#11 key handles */ 158 int not_initialized = 0; 159 160 CK_BYTE current_user_pin_sha[SHA1_DIGEST_LENGTH]; 161 CK_BYTE current_so_pin_sha[SHA1_DIGEST_LENGTH]; 162 163 static TPM_CAP_VERSION_INFO tpmvinfo; 164 165 static CK_RV 166 verify_user_pin(TSS_HCONTEXT, CK_BYTE *); 167 168 static TSS_RESULT 169 tss_assign_secret_key_policy(TSS_HCONTEXT, TSS_FLAG, TSS_HKEY, CK_CHAR *); 170 171 static TSS_RESULT 172 set_legacy_key_params(TSS_HKEY); 173 174 static void 175 local_uuid_clear(TSS_UUID *uuid) 176 { 177 if (uuid == NULL) 178 return; 179 (void) memset(uuid, 0, sizeof (TSS_UUID)); 180 } 181 182 183 /* convert from TSS_UUID to uuid_t */ 184 static void 185 tss_uuid_convert_from(TSS_UUID *uu, uuid_t ptr) 186 { 187 uint_t tmp; 188 uchar_t *out = ptr; 189 190 tmp = ntohl(uu->ulTimeLow); 191 out[3] = (uchar_t)tmp; 192 tmp >>= 8; 193 out[2] = (uchar_t)tmp; 194 tmp >>= 8; 195 out[1] = (uchar_t)tmp; 196 tmp >>= 8; 197 out[0] = (uchar_t)tmp; 198 199 tmp = ntohs(uu->usTimeMid); 200 out[5] = (uchar_t)tmp; 201 tmp >>= 8; 202 out[4] = (uchar_t)tmp; 203 204 tmp = ntohs(uu->usTimeHigh); 205 out[7] = (uchar_t)tmp; 206 tmp >>= 8; 207 out[6] = (uchar_t)tmp; 208 209 tmp = uu->bClockSeqHigh; 210 out[8] = (uchar_t)tmp; 211 tmp = uu->bClockSeqLow; 212 out[9] = (uchar_t)tmp; 213 214 (void) memcpy(out+10, uu->rgbNode, 6); 215 } 216 217 /* convert from uuid_t to TSS_UUID */ 218 static void 219 tss_uuid_convert_to(TSS_UUID *uuid, uuid_t in) 220 { 221 uchar_t *ptr; 222 uint32_t ltmp; 223 uint16_t stmp; 224 225 ptr = in; 226 227 ltmp = *ptr++; 228 ltmp = (ltmp << 8) | *ptr++; 229 ltmp = (ltmp << 8) | *ptr++; 230 ltmp = (ltmp << 8) | *ptr++; 231 uuid->ulTimeLow = ntohl(ltmp); 232 233 stmp = *ptr++; 234 stmp = (stmp << 8) | *ptr++; 235 uuid->usTimeMid = ntohs(stmp); 236 237 stmp = *ptr++; 238 stmp = (stmp << 8) | *ptr++; 239 uuid->usTimeHigh = ntohs(stmp); 240 241 uuid->bClockSeqHigh = *ptr++; 242 243 uuid->bClockSeqLow = *ptr++; 244 245 (void) memcpy(uuid->rgbNode, ptr, 6); 246 } 247 248 static void 249 local_uuid_copy(TSS_UUID *dst, TSS_UUID *src) 250 { 251 uuid_t udst, usrc; 252 253 tss_uuid_convert_from(dst, udst); 254 tss_uuid_convert_from(src, usrc); 255 256 uuid_copy(udst, usrc); 257 258 tss_uuid_convert_to(dst, udst); 259 } 260 261 static void 262 local_uuid_generate(TSS_UUID *uu) 263 { 264 uuid_t newuuid; 265 266 uuid_generate(newuuid); 267 268 tss_uuid_convert_to(uu, newuuid); 269 } 270 271 static int 272 local_copy_file(char *dst, char *src) 273 { 274 FILE *fdest, *fsrc; 275 char line[BUFSIZ]; 276 277 fdest = fopen(dst, "w"); 278 if (fdest == NULL) 279 return (-1); 280 281 fsrc = fopen(src, "r"); 282 if (fsrc == NULL) { 283 (void) fclose(fdest); 284 return (-1); 285 } 286 287 while (fread(line, sizeof (line), 1, fsrc)) 288 (void) fprintf(fdest, "%s\n", line); 289 (void) fclose(fsrc); 290 (void) fclose(fdest); 291 return (0); 292 } 293 294 static int 295 remove_uuid(char *keyname) 296 { 297 int ret = 0; 298 FILE *fp, *newfp; 299 char fname[MAXPATHLEN]; 300 char line[BUFSIZ], key[BUFSIZ], idstr[BUFSIZ]; 301 char *tmpfname; 302 char *p = get_tpm_keystore_path(); 303 304 if (p == NULL) 305 return (-1); 306 307 (void) snprintf(fname, sizeof (fname), 308 "%s/%s", p, TPMTOK_UUID_INDEX_FILENAME); 309 310 fp = fopen(fname, "r"); 311 if (fp == NULL) { 312 return (-1); 313 } 314 315 tmpfname = tempnam("/tmp", "tpmtok"); 316 newfp = fopen(tmpfname, "w+"); 317 if (newfp == NULL) { 318 free(tmpfname); 319 (void) fclose(fp); 320 return (-1); 321 } 322 323 while (!feof(fp)) { 324 (void) fgets(line, sizeof (line), fp); 325 if (sscanf(line, "%1024s %1024s", key, idstr) == 2) { 326 if (strcmp(key, keyname)) 327 (void) fprintf(newfp, "%s\n", line); 328 } 329 } 330 331 (void) fclose(fp); 332 (void) fclose(newfp); 333 if (local_copy_file(fname, tmpfname) == 0) 334 (void) unlink(tmpfname); 335 336 free(tmpfname); 337 338 return (ret); 339 } 340 341 static int 342 find_uuid(char *keyname, TSS_UUID *uu) 343 { 344 int ret = 0, found = 0; 345 FILE *fp = NULL; 346 char fname[MAXPATHLEN]; 347 char line[BUFSIZ], key[BUFSIZ], idstr[BUFSIZ]; 348 uuid_t uuid; 349 char *p = get_tpm_keystore_path(); 350 351 if (p == NULL) 352 return (-1); 353 354 tss_uuid_convert_from(uu, uuid); 355 356 (void) snprintf(fname, sizeof (fname), 357 "%s/%s", p, TPMTOK_UUID_INDEX_FILENAME); 358 359 /* Open UUID Index file */ 360 fp = fopen(fname, "r"); 361 if (fp == NULL) { 362 if (errno == ENOENT) { 363 /* initialize the file */ 364 fp = fopen(fname, "w"); 365 if (fp != NULL) 366 (void) fclose(fp); 367 } 368 return (-1); 369 } 370 371 while (!feof(fp)) { 372 (void) fgets(line, sizeof (line), fp); 373 if (sscanf(line, "%1024s %1024s", key, idstr) == 2) { 374 if (strcmp(key, keyname) == 0) { 375 ret = uuid_parse(idstr, uuid); 376 if (ret == 0) { 377 found = 1; 378 tss_uuid_convert_to(uu, 379 uuid); 380 } 381 break; 382 } 383 } 384 } 385 (void) fclose(fp); 386 387 if (!found) 388 ret = -1; 389 return (ret); 390 } 391 392 static int 393 local_uuid_is_null(TSS_UUID *uu) 394 { 395 uuid_t uuid; 396 int nulluuid; 397 398 tss_uuid_convert_from(uu, uuid); 399 400 nulluuid = uuid_is_null(uuid); 401 return (nulluuid); 402 } 403 404 static int 405 add_uuid(char *keyname, TSS_UUID *uu) 406 { 407 FILE *fp = NULL; 408 char fname[MAXPATHLEN]; 409 char idstr[BUFSIZ]; 410 uuid_t uuid; 411 char *p = get_tpm_keystore_path(); 412 413 if (p == NULL) 414 return (-1); 415 416 tss_uuid_convert_from(uu, uuid); 417 418 if (uuid_is_null(uuid)) 419 return (-1); 420 421 uuid_unparse(uuid, idstr); 422 423 (void) snprintf(fname, sizeof (fname), 424 "%s/%s", p, TPMTOK_UUID_INDEX_FILENAME); 425 426 fp = fopen(fname, "a"); 427 if (fp == NULL) 428 return (-1); 429 430 (void) fprintf(fp, "%s %s\n", keyname, idstr); 431 (void) fclose(fp); 432 433 return (0); 434 } 435 436 437 static UINT32 438 util_get_keysize_flag(CK_ULONG size) 439 { 440 switch (size) { 441 case 512: 442 return (TSS_KEY_SIZE_512); 443 break; 444 case 1024: 445 return (TSS_KEY_SIZE_1024); 446 break; 447 case 2048: 448 return (TSS_KEY_SIZE_2048); 449 break; 450 default: 451 break; 452 } 453 454 return (0); 455 } 456 457 /* make sure the public exponent attribute is 65537 */ 458 static CK_ULONG 459 util_check_public_exponent(TEMPLATE *tmpl) 460 { 461 CK_BBOOL flag; 462 CK_ATTRIBUTE *publ_exp_attr; 463 CK_BYTE pubexp_bytes[] = { 1, 0, 1 }; 464 CK_ULONG publ_exp, rc = 1; 465 466 flag = template_attribute_find(tmpl, CKA_PUBLIC_EXPONENT, 467 &publ_exp_attr); 468 if (!flag) { 469 LogError1("Couldn't find public exponent attribute"); 470 return (CKR_TEMPLATE_INCOMPLETE); 471 } 472 473 switch (publ_exp_attr->ulValueLen) { 474 case 3: 475 rc = memcmp(pubexp_bytes, publ_exp_attr->pValue, 3); 476 break; 477 case sizeof (CK_ULONG): 478 publ_exp = *((CK_ULONG *)publ_exp_attr->pValue); 479 if (publ_exp == 65537) 480 rc = 0; 481 break; 482 default: 483 break; 484 } 485 486 return (rc); 487 } 488 489 TSS_RESULT 490 set_public_modulus(TSS_HCONTEXT hContext, TSS_HKEY hKey, 491 unsigned long size_n, unsigned char *n) 492 { 493 UINT64 offset; 494 UINT32 blob_size; 495 BYTE *blob, pub_blob[1024]; 496 TCPA_PUBKEY pub_key; 497 TSS_RESULT result; 498 499 /* Get the TCPA_PUBKEY blob from the key object. */ 500 result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_KEY_BLOB, 501 TSS_TSPATTRIB_KEYBLOB_PUBLIC_KEY, &blob_size, &blob); 502 if (result != TSS_SUCCESS) { 503 stlogit("Tspi_GetAttribData failed: rc=0x%0x - %s\n", 504 result, Trspi_Error_String(result)); 505 return (result); 506 } 507 508 offset = 0; 509 result = Trspi_UnloadBlob_PUBKEY(&offset, blob, &pub_key); 510 if (result != TSS_SUCCESS) { 511 stlogit("Trspi_UnloadBlob_PUBKEY failed: rc=0x%0x - %s\n", 512 result, Trspi_Error_String(result)); 513 return (result); 514 } 515 516 Tspi_Context_FreeMemory(hContext, blob); 517 /* Free the first dangling reference, putting 'n' in its place */ 518 free(pub_key.pubKey.key); 519 pub_key.pubKey.keyLength = size_n; 520 pub_key.pubKey.key = n; 521 522 offset = 0; 523 Trspi_LoadBlob_PUBKEY(&offset, pub_blob, &pub_key); 524 525 /* Free the second dangling reference */ 526 free(pub_key.algorithmParms.parms); 527 528 /* set the public key data in the TSS object */ 529 result = Tspi_SetAttribData(hKey, TSS_TSPATTRIB_KEY_BLOB, 530 TSS_TSPATTRIB_KEYBLOB_PUBLIC_KEY, (UINT32)offset, pub_blob); 531 if (result != TSS_SUCCESS) { 532 stlogit("Tspi_SetAttribData failed: rc=0x%0x - %s\n", 533 result, Trspi_Error_String(result)); 534 return (result); 535 } 536 537 return (result); 538 } 539 540 /* 541 * Get details about the TPM to put into the token_info structure. 542 */ 543 CK_RV 544 token_get_tpm_info(TSS_HCONTEXT hContext, TOKEN_DATA *td) 545 { 546 TSS_RESULT result; 547 TPM_CAPABILITY_AREA capArea = TSS_TPMCAP_VERSION_VAL; 548 UINT32 datalen; 549 BYTE *data; 550 TSS_HTPM hTPM; 551 552 if ((result = Tspi_Context_GetTpmObject(hContext, &hTPM))) { 553 stlogit("Tspi_Context_GetTpmObject: 0x%0x - %s", 554 result, Trspi_Error_String(result)); 555 return (CKR_FUNCTION_FAILED); 556 } 557 if ((result = Tspi_TPM_GetCapability(hTPM, 558 capArea, 0, NULL, &datalen, &data)) != 0 || datalen == 0 || 559 data == NULL) { 560 stlogit("Tspi_Context_GetCapability: 0x%0x - %s", 561 result, Trspi_Error_String(result)); 562 return (CKR_FUNCTION_FAILED); 563 } 564 if (datalen > sizeof (tpmvinfo)) { 565 Tspi_Context_FreeMemory(hContext, data); 566 return (CKR_FUNCTION_FAILED); 567 } 568 569 (void) memcpy(&tpmvinfo, (void *)data, datalen); 570 571 bzero(td->token_info.manufacturerID, 572 sizeof (td->token_info.manufacturerID)); 573 574 (void) memset(td->token_info.manufacturerID, ' ', 575 sizeof (td->token_info.manufacturerID) - 1); 576 577 (void) memcpy(td->token_info.manufacturerID, 578 tpmvinfo.tpmVendorID, sizeof (tpmvinfo.tpmVendorID)); 579 580 (void) memset(td->token_info.label, ' ', 581 sizeof (td->token_info.label) - 1); 582 583 (void) memcpy(td->token_info.label, "TPM", 3); 584 585 td->token_info.hardwareVersion.major = tpmvinfo.version.major; 586 td->token_info.hardwareVersion.minor = tpmvinfo.version.minor; 587 td->token_info.firmwareVersion.major = tpmvinfo.version.revMajor; 588 td->token_info.firmwareVersion.minor = tpmvinfo.version.revMinor; 589 590 Tspi_Context_FreeMemory(hContext, data); 591 return (CKR_OK); 592 } 593 594 /*ARGSUSED*/ 595 CK_RV 596 token_specific_session(CK_SLOT_ID slotid) 597 { 598 return (CKR_OK); 599 } 600 601 CK_RV 602 token_rng(TSS_HCONTEXT hContext, CK_BYTE *output, CK_ULONG bytes) 603 { 604 TSS_RESULT rc; 605 TSS_HTPM hTPM; 606 BYTE *random_bytes = NULL; 607 608 if ((rc = Tspi_Context_GetTpmObject(hContext, &hTPM))) { 609 stlogit("Tspi_Context_GetTpmObject: 0x%0x - %s", 610 rc, Trspi_Error_String(rc)); 611 return (CKR_FUNCTION_FAILED); 612 } 613 614 if ((rc = Tspi_TPM_GetRandom(hTPM, bytes, &random_bytes))) { 615 stlogit("Tspi_TPM_GetRandom: 0x%0x - %s", 616 rc, Trspi_Error_String(rc)); 617 return (CKR_FUNCTION_FAILED); 618 } 619 620 (void) memcpy(output, random_bytes, bytes); 621 Tspi_Context_FreeMemory(hContext, random_bytes); 622 623 return (CKR_OK); 624 } 625 626 TSS_RESULT 627 open_tss_context(TSS_HCONTEXT *pContext) 628 { 629 TSS_RESULT result; 630 631 if ((result = Tspi_Context_Create(pContext))) { 632 stlogit("Tspi_Context_Create: 0x%0x - %s", 633 result, Trspi_Error_String(result)); 634 return (CKR_FUNCTION_FAILED); 635 } 636 637 if ((result = Tspi_Context_Connect(*pContext, NULL))) { 638 stlogit("Tspi_Context_Connect: 0x%0x - %s", 639 result, Trspi_Error_String(result)); 640 Tspi_Context_Close(*pContext); 641 *pContext = 0; 642 return (CKR_FUNCTION_FAILED); 643 } 644 return (result); 645 } 646 647 /*ARGSUSED*/ 648 static CK_RV 649 token_specific_init(char *Correlator, CK_SLOT_ID SlotNumber, 650 TSS_HCONTEXT *hContext) 651 { 652 TSS_RESULT result; 653 654 result = open_tss_context(hContext); 655 if (result) 656 return (CKR_FUNCTION_FAILED); 657 658 if ((result = Tspi_Context_GetDefaultPolicy(*hContext, 659 &hDefaultPolicy))) { 660 stlogit("Tspi_Context_GetDefaultPolicy: 0x%0x - %s", 661 result, Trspi_Error_String(result)); 662 return (CKR_FUNCTION_FAILED); 663 } 664 665 local_uuid_clear(&publicRootKeyUUID); 666 local_uuid_clear(&privateRootKeyUUID); 667 local_uuid_clear(&publicLeafKeyUUID); 668 local_uuid_clear(&privateLeafKeyUUID); 669 670 result = token_get_tpm_info(*hContext, nv_token_data); 671 return (result); 672 } 673 674 /* 675 * Given a modulus and prime from an RSA key, create a TSS_HKEY object by 676 * wrapping the RSA key with a key from the TPM (SRK or other previously stored 677 * key). 678 */ 679 static CK_RV 680 token_wrap_sw_key( 681 TSS_HCONTEXT hContext, 682 int size_n, 683 unsigned char *n, 684 int size_p, 685 unsigned char *p, 686 TSS_HKEY hParentKey, 687 TSS_FLAG initFlags, 688 TSS_HKEY *phKey) 689 { 690 TSS_RESULT result; 691 UINT32 key_size; 692 693 key_size = util_get_keysize_flag(size_n * 8); 694 if (initFlags == 0) { 695 return (CKR_FUNCTION_FAILED); 696 } 697 698 /* create the TSS key object */ 699 result = Tspi_Context_CreateObject(hContext, TSS_OBJECT_TYPE_RSAKEY, 700 TSS_KEY_MIGRATABLE | initFlags | key_size, phKey); 701 if (result != TSS_SUCCESS) { 702 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 703 result, Trspi_Error_String(result)); 704 return (CKR_FUNCTION_FAILED); 705 } 706 707 result = set_public_modulus(hContext, *phKey, size_n, n); 708 if (result != TSS_SUCCESS) { 709 Tspi_Context_CloseObject(hContext, *phKey); 710 *phKey = NULL_HKEY; 711 return (CKR_FUNCTION_FAILED); 712 } 713 714 /* set the private key data in the TSS object */ 715 result = Tspi_SetAttribData(*phKey, TSS_TSPATTRIB_KEY_BLOB, 716 TSS_TSPATTRIB_KEYBLOB_PRIVATE_KEY, size_p, p); 717 if (result != TSS_SUCCESS) { 718 stlogit("Tspi_SetAttribData: 0x%x - %s", 719 result, Trspi_Error_String(result)); 720 Tspi_Context_CloseObject(hContext, *phKey); 721 *phKey = NULL_HKEY; 722 return (CKR_FUNCTION_FAILED); 723 } 724 725 result = tss_assign_secret_key_policy(hContext, TSS_POLICY_MIGRATION, 726 *phKey, NULL); 727 728 if (TPMTOK_TSS_KEY_TYPE(initFlags) == TSS_KEY_TYPE_LEGACY) { 729 if ((result = Tspi_SetAttribUint32(*phKey, 730 TSS_TSPATTRIB_KEY_INFO, TSS_TSPATTRIB_KEYINFO_ENCSCHEME, 731 TSS_ES_RSAESPKCSV15))) { 732 stlogit("Tspi_SetAttribUint32: 0x%0x - %s\n", 733 result, Trspi_Error_String(result)); 734 Tspi_Context_CloseObject(hContext, *phKey); 735 return (CKR_FUNCTION_FAILED); 736 } 737 738 if ((result = Tspi_SetAttribUint32(*phKey, 739 TSS_TSPATTRIB_KEY_INFO, TSS_TSPATTRIB_KEYINFO_SIGSCHEME, 740 TSS_SS_RSASSAPKCS1V15_DER))) { 741 stlogit("Tspi_SetAttribUint32: 0x%0x - %s\n", 742 result, Trspi_Error_String(result)); 743 Tspi_Context_CloseObject(hContext, *phKey); 744 return (CKR_FUNCTION_FAILED); 745 } 746 } 747 748 result = Tspi_Key_WrapKey(*phKey, hParentKey, NULL_HPCRS); 749 if (result != TSS_SUCCESS) { 750 stlogit("Tspi_Key_WrapKey: 0x%0x - %s", 751 result, Trspi_Error_String(result)); 752 Tspi_Context_CloseObject(hContext, *phKey); 753 *phKey = NULL_HKEY; 754 return (CKR_FUNCTION_FAILED); 755 } 756 757 return (CKR_OK); 758 } 759 760 /* 761 * Create a TPM key blob for an imported key. This function is only called when 762 * a key is in active use, so any failure should trickle through. 763 */ 764 static CK_RV 765 token_wrap_key_object(TSS_HCONTEXT hContext, 766 CK_OBJECT_HANDLE ckObject, 767 TSS_HKEY hParentKey, TSS_HKEY *phKey) 768 { 769 CK_RV rc = CKR_OK; 770 CK_ATTRIBUTE *attr = NULL, *new_attr, *prime_attr; 771 CK_ULONG class, key_type; 772 OBJECT *obj; 773 774 TSS_RESULT result; 775 TSS_FLAG initFlags = 0; 776 BYTE *rgbBlob; 777 UINT32 ulBlobLen; 778 779 if ((rc = object_mgr_find_in_map1(hContext, ckObject, &obj))) { 780 return (rc); 781 } 782 783 /* if the object isn't a key, fail */ 784 if (template_attribute_find(obj->template, CKA_KEY_TYPE, 785 &attr) == FALSE) { 786 return (CKR_TEMPLATE_INCOMPLETE); 787 } 788 789 key_type = *((CK_ULONG *)attr->pValue); 790 791 if (key_type != CKK_RSA) { 792 return (CKR_TEMPLATE_INCONSISTENT); 793 } 794 795 if (template_attribute_find(obj->template, CKA_CLASS, 796 &attr) == FALSE) { 797 return (CKR_TEMPLATE_INCOMPLETE); 798 } 799 800 class = *((CK_ULONG *)attr->pValue); 801 802 if (class == CKO_PRIVATE_KEY) { 803 /* 804 * In order to create a full TSS key blob using a PKCS#11 805 * private key object, we need one of the two primes, the 806 * modulus and the private exponent and we need the public 807 * exponent to be correct. 808 */ 809 810 /* 811 * Check the least likely attribute to exist first, the 812 * primes. 813 */ 814 if (template_attribute_find(obj->template, CKA_PRIME_1, 815 &prime_attr) == FALSE) { 816 if (template_attribute_find(obj->template, 817 CKA_PRIME_2, &prime_attr) == FALSE) { 818 return (CKR_TEMPLATE_INCOMPLETE); 819 } 820 } 821 822 /* Make sure the public exponent is usable */ 823 if ((rc = util_check_public_exponent(obj->template))) { 824 return (CKR_TEMPLATE_INCONSISTENT); 825 } 826 827 /* get the modulus */ 828 if (template_attribute_find(obj->template, CKA_MODULUS, 829 &attr) == FALSE) { 830 return (CKR_TEMPLATE_INCOMPLETE); 831 } 832 833 /* make sure the key size is usable */ 834 initFlags = util_get_keysize_flag(attr->ulValueLen * 8); 835 if (initFlags == 0) { 836 return (CKR_TEMPLATE_INCONSISTENT); 837 } 838 839 /* generate the software based key */ 840 if ((rc = token_wrap_sw_key(hContext, 841 (int)attr->ulValueLen, attr->pValue, 842 (int)prime_attr->ulValueLen, prime_attr->pValue, 843 hParentKey, TSS_KEY_TYPE_LEGACY | TSS_KEY_NO_AUTHORIZATION, 844 phKey))) { 845 return (rc); 846 } 847 } else if (class == CKO_PUBLIC_KEY) { 848 /* Make sure the public exponent is usable */ 849 if ((util_check_public_exponent(obj->template))) { 850 return (CKR_TEMPLATE_INCONSISTENT); 851 } 852 853 /* grab the modulus to put into the TSS key object */ 854 if (template_attribute_find(obj->template, 855 CKA_MODULUS, &attr) == FALSE) { 856 return (CKR_TEMPLATE_INCONSISTENT); 857 } 858 859 /* make sure the key size is usable */ 860 initFlags = util_get_keysize_flag(attr->ulValueLen * 8); 861 if (initFlags == 0) { 862 return (CKR_TEMPLATE_INCONSISTENT); 863 } 864 865 initFlags |= TSS_KEY_MIGRATABLE | TSS_KEY_NO_AUTHORIZATION | 866 TSS_KEY_TYPE_LEGACY; 867 868 if ((result = Tspi_Context_CreateObject(hContext, 869 TSS_OBJECT_TYPE_RSAKEY, initFlags, phKey))) { 870 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 871 result, Trspi_Error_String(result)); 872 return (result); 873 } 874 875 if ((result = set_public_modulus(hContext, *phKey, 876 attr->ulValueLen, attr->pValue))) { 877 Tspi_Context_CloseObject(hContext, *phKey); 878 *phKey = NULL_HKEY; 879 return (CKR_FUNCTION_FAILED); 880 } 881 result = tss_assign_secret_key_policy(hContext, 882 TSS_POLICY_MIGRATION, *phKey, NULL); 883 if (result) { 884 Tspi_Context_CloseObject(hContext, *phKey); 885 *phKey = NULL_HKEY; 886 return (CKR_FUNCTION_FAILED); 887 } 888 889 result = set_legacy_key_params(*phKey); 890 if (result) { 891 Tspi_Context_CloseObject(hContext, *phKey); 892 *phKey = NULL_HKEY; 893 return (CKR_FUNCTION_FAILED); 894 } 895 } else { 896 return (CKR_FUNCTION_FAILED); 897 } 898 899 /* grab the entire key blob to put into the PKCS#11 object */ 900 if ((result = Tspi_GetAttribData(*phKey, TSS_TSPATTRIB_KEY_BLOB, 901 TSS_TSPATTRIB_KEYBLOB_BLOB, &ulBlobLen, &rgbBlob))) { 902 stlogit("Tspi_GetAttribData: 0x%0x - %s", 903 result, Trspi_Error_String(result)); 904 return (CKR_FUNCTION_FAILED); 905 } 906 907 /* insert the key blob into the object */ 908 if ((rc = build_attribute(CKA_IBM_OPAQUE, rgbBlob, ulBlobLen, 909 &new_attr))) { 910 Tspi_Context_FreeMemory(hContext, rgbBlob); 911 return (rc); 912 } 913 (void) template_update_attribute(obj->template, new_attr); 914 Tspi_Context_FreeMemory(hContext, rgbBlob); 915 916 /* 917 * If this is a token object, save it with the new attribute 918 * so that we don't have to go down this path again. 919 */ 920 if (!object_is_session_object(obj)) { 921 rc = save_token_object(hContext, obj); 922 } 923 924 return (rc); 925 } 926 927 static TSS_RESULT 928 tss_assign_secret_key_policy(TSS_HCONTEXT hContext, TSS_FLAG policyType, 929 TSS_HKEY hKey, CK_CHAR *passHash) 930 { 931 TSS_RESULT result; 932 TSS_HPOLICY hPolicy; 933 934 if ((result = Tspi_Context_CreateObject(hContext, 935 TSS_OBJECT_TYPE_POLICY, policyType, &hPolicy))) { 936 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 937 result, Trspi_Error_String(result)); 938 return (result); 939 } 940 if ((result = Tspi_Policy_AssignToObject(hPolicy, hKey))) { 941 stlogit("Tspi_Policy_AssignToObject: 0x%0x - %s", 942 result, Trspi_Error_String(result)); 943 goto done; 944 } 945 if (passHash == NULL) { 946 result = Tspi_Policy_SetSecret(hPolicy, TSS_SECRET_MODE_NONE, 947 0, NULL); 948 } else { 949 result = Tspi_Policy_SetSecret(hPolicy, TSS_SECRET_MODE_SHA1, 950 SHA1_DIGEST_LENGTH, passHash); 951 } 952 if (result != TSS_SUCCESS) { 953 stlogit("Tspi_Policy_SetSecret: 0x%0x - %s", 954 result, Trspi_Error_String(result)); 955 goto done; 956 } 957 done: 958 if (result != TSS_SUCCESS) 959 Tspi_Context_CloseObject(hContext, hPolicy); 960 return (result); 961 } 962 963 /* 964 * Take a key from the TSS store (on-disk) and load it into the TPM, wrapped 965 * by an already TPM-resident key and protected with a PIN (optional). 966 */ 967 static CK_RV 968 token_load_key( 969 TSS_HCONTEXT hContext, 970 CK_OBJECT_HANDLE ckKey, 971 TSS_HKEY hParentKey, 972 CK_CHAR_PTR passHash, 973 TSS_HKEY *phKey) 974 { 975 TSS_RESULT result; 976 CK_RV rc; 977 978 /* 979 * The key blob wasn't found, load the parts of the key 980 * from the object DB and create a new key object that 981 * gets loaded into the TPM, wrapped with the parent key. 982 */ 983 if ((rc = token_wrap_key_object(hContext, ckKey, 984 hParentKey, phKey))) { 985 return (rc); 986 } 987 988 /* 989 * Assign the PIN hash (optional) to the newly loaded key object, 990 * if this PIN is incorrect, the TPM will not be able to decrypt 991 * the private key and use it. 992 */ 993 result = tss_assign_secret_key_policy(hContext, TSS_POLICY_USAGE, 994 *phKey, passHash); 995 996 return (result); 997 } 998 999 /* 1000 * Load the SRK into the TPM by referencing its well-known UUID and using the 1001 * default SRK PIN (20 bytes of 0x00). 1002 * 1003 * NOTE - if the SRK PIN is changed by an administrative tool, this code will 1004 * fail because it assumes that the well-known PIN is still being used. 1005 */ 1006 static TSS_RESULT 1007 token_load_srk(TSS_HCONTEXT hContext, TSS_HKEY *hSRK) 1008 { 1009 TSS_HPOLICY hPolicy; 1010 TSS_RESULT result; 1011 TSS_UUID SRK_UUID = TSS_UUID_SRK; 1012 BYTE wellKnown[] = TSS_WELL_KNOWN_SECRET; 1013 TSS_HTPM hTPM; 1014 1015 if ((result = Tspi_Context_GetTpmObject(hContext, &hTPM))) { 1016 stlogit("Tspi_Context_GetTpmObject: 0x%0x - %s", 1017 result, Trspi_Error_String(result)); 1018 return (CKR_FUNCTION_FAILED); 1019 } 1020 1021 /* load the SRK */ 1022 if ((result = Tspi_Context_LoadKeyByUUID(hContext, 1023 TSS_PS_TYPE_SYSTEM, SRK_UUID, hSRK))) { 1024 stlogit("Tspi_Context_LoadKeyByUUID: 0x%0x - %s", 1025 result, Trspi_Error_String(result)); 1026 goto done; 1027 } 1028 if ((result = Tspi_GetPolicyObject(*hSRK, TSS_POLICY_USAGE, 1029 &hPolicy))) { 1030 stlogit("Tspi_GetPolicyObject: 0x%0x - %s", 1031 result, Trspi_Error_String(result)); 1032 goto done; 1033 } 1034 if ((result = Tspi_Policy_SetSecret(hPolicy, TSS_SECRET_MODE_SHA1, 1035 sizeof (wellKnown), wellKnown))) { 1036 stlogit("Tspi_Policy_SetSecret: 0x%0x - %s", 1037 result, Trspi_Error_String(result)); 1038 goto done; 1039 } 1040 1041 done: 1042 return (result); 1043 } 1044 1045 static TSS_RESULT 1046 tss_find_and_load_key(TSS_HCONTEXT hContext, 1047 char *keyid, TSS_UUID *uuid, TSS_HKEY hParent, 1048 BYTE *hash, TSS_HKEY *hKey) 1049 { 1050 TSS_RESULT result; 1051 1052 if (local_uuid_is_null(uuid) && 1053 find_uuid(keyid, uuid)) { 1054 /* The UUID was not created or saved yet */ 1055 return (1); 1056 } 1057 result = Tspi_Context_GetKeyByUUID(hContext, 1058 TSS_PS_TYPE_USER, *uuid, hKey); 1059 if (result) { 1060 stlogit("Tspi_Context_GetKeyByUUID: 0x%0x - %s", 1061 result, Trspi_Error_String(result)); 1062 return (result); 1063 } 1064 1065 if (hash != NULL) { 1066 result = tss_assign_secret_key_policy(hContext, 1067 TSS_POLICY_USAGE, *hKey, (CK_BYTE *)hash); 1068 if (result) 1069 return (result); 1070 } 1071 1072 result = Tspi_Key_LoadKey(*hKey, hParent); 1073 if (result) 1074 stlogit("Tspi_Key_LoadKey: 0x%0x - %s", 1075 result, Trspi_Error_String(result)); 1076 1077 return (result); 1078 } 1079 1080 static TSS_RESULT 1081 token_load_public_root_key(TSS_HCONTEXT hContext) 1082 { 1083 TSS_RESULT result; 1084 TSS_HKEY hSRK; 1085 1086 if (hPublicRootKey != NULL_HKEY) 1087 return (TSS_SUCCESS); 1088 1089 if ((result = token_load_srk(hContext, &hSRK))) { 1090 return (result); 1091 } 1092 1093 result = tss_find_and_load_key(hContext, 1094 TPMTOK_PUBLIC_ROOT_KEY_ID, 1095 &publicRootKeyUUID, hSRK, NULL, &hPublicRootKey); 1096 if (result) 1097 return (result); 1098 1099 return (result); 1100 } 1101 1102 static TSS_RESULT 1103 set_legacy_key_params(TSS_HKEY hKey) 1104 { 1105 TSS_RESULT result; 1106 1107 if ((result = Tspi_SetAttribUint32(hKey, 1108 TSS_TSPATTRIB_KEY_INFO, 1109 TSS_TSPATTRIB_KEYINFO_ENCSCHEME, 1110 TSS_ES_RSAESPKCSV15))) { 1111 stlogit("Tspi_SetAttribUint32: 0x%0x - %s", 1112 result, Trspi_Error_String(result)); 1113 return (result); 1114 } 1115 1116 if ((result = Tspi_SetAttribUint32(hKey, 1117 TSS_TSPATTRIB_KEY_INFO, 1118 TSS_TSPATTRIB_KEYINFO_SIGSCHEME, 1119 TSS_SS_RSASSAPKCS1V15_DER))) { 1120 stlogit("Tspi_SetAttribUint32: 0x%0x - %s", 1121 result, Trspi_Error_String(result)); 1122 return (result); 1123 } 1124 1125 return (result); 1126 } 1127 1128 static TSS_RESULT 1129 tss_generate_key(TSS_HCONTEXT hContext, TSS_FLAG initFlags, BYTE *passHash, 1130 TSS_HKEY hParentKey, TSS_HKEY *phKey) 1131 { 1132 TSS_RESULT result; 1133 TSS_HPOLICY hMigPolicy; 1134 1135 if ((result = Tspi_Context_CreateObject(hContext, 1136 TSS_OBJECT_TYPE_RSAKEY, initFlags, phKey))) { 1137 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 1138 result, Trspi_Error_String(result)); 1139 return (result); 1140 } 1141 result = tss_assign_secret_key_policy(hContext, TSS_POLICY_USAGE, 1142 *phKey, passHash); 1143 1144 if (result) { 1145 Tspi_Context_CloseObject(hContext, *phKey); 1146 return (result); 1147 } 1148 1149 if (TPMTOK_TSS_KEY_MIG_TYPE(initFlags) == TSS_KEY_MIGRATABLE) { 1150 if ((result = Tspi_Context_CreateObject(hContext, 1151 TSS_OBJECT_TYPE_POLICY, TSS_POLICY_MIGRATION, 1152 &hMigPolicy))) { 1153 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 1154 result, Trspi_Error_String(result)); 1155 Tspi_Context_CloseObject(hContext, *phKey); 1156 return (result); 1157 } 1158 1159 if (passHash == NULL) { 1160 result = Tspi_Policy_SetSecret(hMigPolicy, 1161 TSS_SECRET_MODE_NONE, 0, NULL); 1162 } else { 1163 result = Tspi_Policy_SetSecret(hMigPolicy, 1164 TSS_SECRET_MODE_SHA1, 20, passHash); 1165 } 1166 1167 if (result != TSS_SUCCESS) { 1168 stlogit("Tspi_Policy_SetSecret: 0x%0x - %s", 1169 result, Trspi_Error_String(result)); 1170 Tspi_Context_CloseObject(hContext, *phKey); 1171 Tspi_Context_CloseObject(hContext, hMigPolicy); 1172 return (result); 1173 } 1174 1175 if ((result = Tspi_Policy_AssignToObject(hMigPolicy, *phKey))) { 1176 stlogit("Tspi_Policy_AssignToObject: 0x%0x - %s", 1177 result, Trspi_Error_String(result)); 1178 Tspi_Context_CloseObject(hContext, *phKey); 1179 Tspi_Context_CloseObject(hContext, hMigPolicy); 1180 return (result); 1181 } 1182 } 1183 1184 if (TPMTOK_TSS_KEY_TYPE(initFlags) == TSS_KEY_TYPE_LEGACY) { 1185 result = set_legacy_key_params(*phKey); 1186 if (result) { 1187 Tspi_Context_CloseObject(hContext, *phKey); 1188 Tspi_Context_CloseObject(hContext, hMigPolicy); 1189 return (result); 1190 } 1191 } 1192 1193 if ((result = Tspi_Key_CreateKey(*phKey, hParentKey, 0))) { 1194 stlogit("Tspi_Key_CreateKey: 0x%0x - %s", 1195 result, Trspi_Error_String(result)); 1196 Tspi_Context_CloseObject(hContext, *phKey); 1197 Tspi_Context_CloseObject(hContext, hMigPolicy); 1198 } 1199 1200 return (result); 1201 } 1202 1203 static TSS_RESULT 1204 tss_change_auth( 1205 TSS_HCONTEXT hContext, 1206 TSS_HKEY hObjectToChange, TSS_HKEY hParentObject, 1207 TSS_UUID objUUID, TSS_UUID parentUUID, 1208 CK_CHAR *passHash) 1209 { 1210 TSS_RESULT result; 1211 TSS_HPOLICY hPolicy; 1212 TSS_HKEY oldkey; 1213 1214 if ((result = Tspi_Context_CreateObject(hContext, 1215 TSS_OBJECT_TYPE_POLICY, TSS_POLICY_USAGE, &hPolicy))) { 1216 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 1217 result, Trspi_Error_String(result)); 1218 return (result); 1219 } 1220 1221 if ((result = Tspi_Policy_SetSecret(hPolicy, TSS_SECRET_MODE_SHA1, 1222 SHA1_DIGEST_LENGTH, passHash))) { 1223 stlogit("Tspi_Policy_SetSecret: 0x%0x - %s", 1224 result, Trspi_Error_String(result)); 1225 return (result); 1226 } 1227 1228 if ((result = Tspi_ChangeAuth(hObjectToChange, hParentObject, 1229 hPolicy))) { 1230 stlogit("Tspi_ChangeAuth: 0x%0x - %s", 1231 result, Trspi_Error_String(result)); 1232 } 1233 /* 1234 * Update the PS key by unregistering the key UUID and then 1235 * re-registering with the same UUID. This forces the updated 1236 * auth data associated with the key to be stored in PS so 1237 * the new PIN can be used next time. 1238 */ 1239 if ((result = Tspi_Context_UnregisterKey(hContext, 1240 TSS_PS_TYPE_USER, objUUID, &oldkey))) 1241 stlogit("Tspi_Context_UnregisterKey: 0x%0x - %s", 1242 result, Trspi_Error_String(result)); 1243 1244 if ((result = Tspi_Context_RegisterKey(hContext, hObjectToChange, 1245 TSS_PS_TYPE_USER, objUUID, TSS_PS_TYPE_USER, parentUUID))) 1246 stlogit("Tspi_Context_RegisterKey: 0x%0x - %s", 1247 result, Trspi_Error_String(result)); 1248 1249 return (result); 1250 } 1251 1252 static CK_RV 1253 token_generate_leaf_key(TSS_HCONTEXT hContext, 1254 int key_type, CK_CHAR_PTR passHash, TSS_HKEY *phKey) 1255 { 1256 CK_RV rc = CKR_FUNCTION_FAILED; 1257 TSS_RESULT result; 1258 TSS_HKEY hParentKey; 1259 TSS_UUID newuuid, parentUUID; 1260 char *keyid; 1261 TSS_FLAG initFlags = TSS_KEY_MIGRATABLE | 1262 TSS_KEY_TYPE_BIND | TSS_KEY_SIZE_2048 | TSS_KEY_AUTHORIZATION; 1263 1264 switch (key_type) { 1265 case TPMTOK_PUBLIC_LEAF_KEY: 1266 hParentKey = hPublicRootKey; 1267 keyid = TPMTOK_PUBLIC_LEAF_KEY_ID; 1268 local_uuid_copy(&parentUUID, &publicRootKeyUUID); 1269 break; 1270 case TPMTOK_PRIVATE_LEAF_KEY: 1271 hParentKey = hPrivateRootKey; 1272 keyid = TPMTOK_PRIVATE_LEAF_KEY_ID; 1273 local_uuid_copy(&parentUUID, &privateRootKeyUUID); 1274 break; 1275 default: 1276 stlogit("Unknown key type 0x%0x", key_type); 1277 goto done; 1278 break; 1279 } 1280 1281 if (result = tss_generate_key(hContext, initFlags, passHash, 1282 hParentKey, phKey)) { 1283 return (rc); 1284 } 1285 1286 /* 1287 * - generate newUUID 1288 * - Tspi_Context_RegisterKey(hContext, hPrivateRootKey, 1289 * USER, newUUID, USER, parentUUID); 1290 * - store newUUID 1291 */ 1292 (void) local_uuid_generate(&newuuid); 1293 1294 result = Tspi_Context_RegisterKey(hContext, *phKey, 1295 TSS_PS_TYPE_USER, newuuid, 1296 TSS_PS_TYPE_USER, parentUUID); 1297 if (result == TSS_SUCCESS) { 1298 int ret; 1299 /* 1300 * Add the UUID to the token UUID index. 1301 */ 1302 ret = add_uuid(keyid, &newuuid); 1303 1304 if (ret) 1305 result = Tspi_Context_UnregisterKey(hContext, 1306 TSS_PS_TYPE_USER, newuuid, phKey); 1307 else 1308 rc = CKR_OK; 1309 } 1310 1311 done: 1312 return (rc); 1313 } 1314 1315 /* 1316 * PINs are verified by attempting to bind/unbind random data using a 1317 * TPM resident key that has the PIN being tested assigned as its "secret". 1318 * If the PIN is incorrect, the unbind operation will fail. 1319 */ 1320 static CK_RV 1321 token_verify_pin(TSS_HCONTEXT hContext, TSS_HKEY hKey) 1322 { 1323 TSS_HENCDATA hEncData; 1324 UINT32 ulUnboundDataLen; 1325 BYTE *rgbUnboundData = NULL; 1326 BYTE rgbData[16]; 1327 TSS_RESULT result; 1328 CK_RV rc = CKR_FUNCTION_FAILED; 1329 1330 if ((result = Tspi_Context_CreateObject(hContext, 1331 TSS_OBJECT_TYPE_ENCDATA, TSS_ENCDATA_BIND, &hEncData))) { 1332 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 1333 result, Trspi_Error_String(result)); 1334 goto done; 1335 } 1336 1337 /* Use some random data */ 1338 rc = token_rng(hContext, rgbData, sizeof (rgbData)); 1339 if (rc) 1340 goto done; 1341 1342 if ((result = Tspi_Data_Bind(hEncData, hKey, 1343 sizeof (rgbData), rgbData))) { 1344 stlogit("Tspi_Data_Bind: 0x%0x - %s", 1345 result, Trspi_Error_String(result)); 1346 goto done; 1347 } 1348 1349 /* unbind the junk data to test the key's auth data */ 1350 result = Tspi_Data_Unbind(hEncData, hKey, &ulUnboundDataLen, 1351 &rgbUnboundData); 1352 if (result == TPM_E_AUTHFAIL) { 1353 rc = CKR_PIN_INCORRECT; 1354 stlogit("Tspi_Data_Unbind: 0x%0x - %s", 1355 result, Trspi_Error_String(result)); 1356 goto done; 1357 } else if (result != TSS_SUCCESS) { 1358 stlogit("Tspi_Data_Unbind: 0x%0x - %s", 1359 result, Trspi_Error_String(result)); 1360 rc = CKR_FUNCTION_FAILED; 1361 goto done; 1362 } 1363 1364 if (memcmp(rgbUnboundData, rgbData, ulUnboundDataLen)) 1365 rc = CKR_PIN_INCORRECT; 1366 else 1367 rc = CKR_OK; 1368 1369 done: 1370 if (rgbUnboundData != NULL) 1371 Tspi_Context_FreeMemory(hContext, rgbUnboundData); 1372 Tspi_Context_CloseObject(hContext, hEncData); 1373 return (rc); 1374 } 1375 1376 static CK_RV 1377 token_create_private_tree(TSS_HCONTEXT hContext, CK_BYTE *pinHash) 1378 { 1379 CK_RV rc; 1380 TSS_RESULT result; 1381 int ret; 1382 TSS_FLAG initFlags = TSS_KEY_SIZE_2048 | 1383 TSS_KEY_NO_AUTHORIZATION | TSS_KEY_TYPE_STORAGE; 1384 TSS_UUID SRK_UUID = TSS_UUID_SRK; 1385 TSS_HKEY hSRK; 1386 1387 if (token_load_srk(hContext, &hSRK)) 1388 return (CKR_FUNCTION_FAILED); 1389 1390 /* 1391 * - create UUID privateRootKeyUUID 1392 * - Tspi_Context_RegisterKey(hContext, hPrivateRootKey, 1393 * USER, privateRootKeyUUID, system, UUID_SRK); 1394 * - store privateRootKeyUUID in users private token space. 1395 */ 1396 if ((result = tss_generate_key(hContext, initFlags, NULL, hSRK, 1397 &hPrivateRootKey))) { 1398 return (result); 1399 } 1400 if (local_uuid_is_null(&privateRootKeyUUID)) 1401 local_uuid_generate(&privateRootKeyUUID); 1402 1403 result = Tspi_Context_RegisterKey(hContext, hPrivateRootKey, 1404 TSS_PS_TYPE_USER, privateRootKeyUUID, 1405 TSS_PS_TYPE_SYSTEM, SRK_UUID); 1406 1407 if (result) { 1408 local_uuid_clear(&privateRootKeyUUID); 1409 return (result); 1410 } 1411 1412 ret = add_uuid(TPMTOK_PRIVATE_ROOT_KEY_ID, &privateRootKeyUUID); 1413 if (ret) { 1414 result = Tspi_Context_UnregisterKey(hContext, 1415 TSS_PS_TYPE_USER, privateRootKeyUUID, 1416 &hPrivateRootKey); 1417 return (CKR_FUNCTION_FAILED); 1418 } 1419 1420 if ((result = Tspi_Key_LoadKey(hPrivateRootKey, hSRK))) { 1421 stlogit("Tspi_Key_LoadKey: 0x%0x - %s", 1422 result, Trspi_Error_String(result)); 1423 Tspi_Context_CloseObject(hContext, hPrivateRootKey); 1424 1425 (void) remove_uuid(TPMTOK_PRIVATE_ROOT_KEY_ID); 1426 local_uuid_clear(&privateRootKeyUUID); 1427 1428 hPrivateRootKey = NULL_HKEY; 1429 return (CKR_FUNCTION_FAILED); 1430 } 1431 1432 1433 /* generate the private leaf key */ 1434 if ((rc = token_generate_leaf_key(hContext, 1435 TPMTOK_PRIVATE_LEAF_KEY, 1436 pinHash, &hPrivateLeafKey))) { 1437 return (rc); 1438 } 1439 1440 if ((result = Tspi_Key_LoadKey(hPrivateLeafKey, hPrivateRootKey))) { 1441 stlogit("Tspi_Key_LoadKey: 0x%0x - %s", 1442 result, Trspi_Error_String(result)); 1443 1444 (void) Tspi_Context_UnregisterKey(hContext, 1445 TSS_PS_TYPE_USER, privateLeafKeyUUID, 1446 &hPrivateLeafKey); 1447 (void) remove_uuid(TPMTOK_PRIVATE_LEAF_KEY_ID); 1448 local_uuid_clear(&privateLeafKeyUUID); 1449 1450 (void) Tspi_Context_UnregisterKey(hContext, 1451 TSS_PS_TYPE_USER, privateRootKeyUUID, 1452 &hPrivateRootKey); 1453 (void) remove_uuid(TPMTOK_PRIVATE_ROOT_KEY_ID); 1454 local_uuid_clear(&privateRootKeyUUID); 1455 1456 Tspi_Context_CloseObject(hContext, hPrivateRootKey); 1457 hPrivateRootKey = NULL_HKEY; 1458 1459 Tspi_Context_CloseObject(hContext, hPrivateLeafKey); 1460 hPrivateRootKey = NULL_HKEY; 1461 1462 return (CKR_FUNCTION_FAILED); 1463 } 1464 return (rc); 1465 } 1466 1467 static CK_RV 1468 token_create_public_tree(TSS_HCONTEXT hContext, CK_BYTE *pinHash) 1469 { 1470 CK_RV rc; 1471 TSS_RESULT result; 1472 int ret; 1473 TSS_FLAG initFlags = TSS_KEY_SIZE_2048 | 1474 TSS_KEY_NO_AUTHORIZATION | TSS_KEY_TYPE_STORAGE; 1475 TSS_UUID srk_uuid = TSS_UUID_SRK; 1476 TSS_HKEY hSRK; 1477 1478 if (token_load_srk(hContext, &hSRK)) 1479 return (CKR_FUNCTION_FAILED); 1480 1481 /* 1482 * - create publicRootKeyUUID 1483 * - Tspi_Context_RegisterKey(hContext, hPublicRootKey, 1484 * USER, publicRootKeyUUID, system, UUID_SRK); 1485 * - store publicRootKeyUUID in users private token space. 1486 */ 1487 if ((result = tss_generate_key(hContext, initFlags, NULL, hSRK, 1488 &hPublicRootKey))) { 1489 return (CKR_FUNCTION_FAILED); 1490 } 1491 if (local_uuid_is_null(&publicRootKeyUUID)) 1492 local_uuid_generate(&publicRootKeyUUID); 1493 1494 result = Tspi_Context_RegisterKey(hContext, hPublicRootKey, 1495 TSS_PS_TYPE_USER, publicRootKeyUUID, 1496 TSS_PS_TYPE_SYSTEM, srk_uuid); 1497 1498 if (result) { 1499 local_uuid_clear(&publicRootKeyUUID); 1500 return (CKR_FUNCTION_FAILED); 1501 } 1502 1503 ret = add_uuid(TPMTOK_PUBLIC_ROOT_KEY_ID, &publicRootKeyUUID); 1504 if (ret) { 1505 result = Tspi_Context_UnregisterKey(hContext, 1506 TSS_PS_TYPE_USER, publicRootKeyUUID, 1507 &hPublicRootKey); 1508 /* does result matter here? */ 1509 return (CKR_FUNCTION_FAILED); 1510 } 1511 1512 /* Load the newly created publicRootKey into the TPM using the SRK */ 1513 if ((result = Tspi_Key_LoadKey(hPublicRootKey, hSRK))) { 1514 stlogit("Tspi_Key_LoadKey: 0x%x - %s", result, 1515 Trspi_Error_String(result)); 1516 Tspi_Context_CloseObject(hContext, hPublicRootKey); 1517 hPublicRootKey = NULL_HKEY; 1518 return (CKR_FUNCTION_FAILED); 1519 } 1520 1521 /* create the SO's leaf key */ 1522 if ((rc = token_generate_leaf_key(hContext, TPMTOK_PUBLIC_LEAF_KEY, 1523 pinHash, &hPublicLeafKey))) { 1524 return (rc); 1525 } 1526 1527 if ((result = Tspi_Key_LoadKey(hPublicLeafKey, hPublicRootKey))) { 1528 stlogit("Tspi_Key_LoadKey: 0x%0x - %s", 1529 result, Trspi_Error_String(result)); 1530 1531 /* Unregister keys and clear UUIDs */ 1532 (void) Tspi_Context_UnregisterKey(hContext, 1533 TSS_PS_TYPE_USER, publicLeafKeyUUID, 1534 &hPublicLeafKey); 1535 (void) remove_uuid(TPMTOK_PUBLIC_LEAF_KEY_ID); 1536 1537 (void) Tspi_Context_UnregisterKey(hContext, 1538 TSS_PS_TYPE_USER, publicRootKeyUUID, 1539 &hPublicRootKey); 1540 (void) remove_uuid(TPMTOK_PUBLIC_ROOT_KEY_ID); 1541 1542 Tspi_Context_CloseObject(hContext, hPublicRootKey); 1543 hPublicRootKey = NULL_HKEY; 1544 1545 Tspi_Context_CloseObject(hContext, hPublicLeafKey); 1546 hPublicLeafKey = NULL_HKEY; 1547 1548 return (CKR_FUNCTION_FAILED); 1549 } 1550 1551 return (rc); 1552 } 1553 1554 CK_RV 1555 token_specific_login( 1556 TSS_HCONTEXT hContext, 1557 CK_USER_TYPE userType, 1558 CK_CHAR_PTR pPin, 1559 CK_ULONG ulPinLen) 1560 { 1561 CK_RV rc; 1562 CK_BYTE hash_sha[SHA1_DIGEST_LENGTH]; 1563 TSS_RESULT result; 1564 TSS_HKEY hSRK; 1565 1566 /* Make sure the SRK is loaded into the TPM */ 1567 if ((result = token_load_srk(hContext, &hSRK))) { 1568 return (CKR_FUNCTION_FAILED); 1569 } 1570 1571 if ((rc = compute_sha(pPin, ulPinLen, hash_sha))) { 1572 return (CKR_FUNCTION_FAILED); 1573 } 1574 1575 if (userType == CKU_USER) { 1576 /* 1577 * If the public root key doesn't exist yet, 1578 * the SO hasn't init'd the token. 1579 */ 1580 if ((result = token_load_public_root_key(hContext))) { 1581 if (result == TPM_E_DECRYPT_ERROR) { 1582 return (CKR_USER_PIN_NOT_INITIALIZED); 1583 } 1584 } 1585 1586 /* 1587 * - find privateRootKeyUUID 1588 * - load by UUID (SRK parent) 1589 */ 1590 if (local_uuid_is_null(&privateRootKeyUUID) && 1591 find_uuid(TPMTOK_PRIVATE_ROOT_KEY_ID, 1592 &privateRootKeyUUID)) { 1593 if (memcmp(hash_sha, 1594 default_user_pin_sha, 1595 SHA1_DIGEST_LENGTH)) 1596 return (CKR_PIN_INCORRECT); 1597 1598 not_initialized = 1; 1599 return (CKR_OK); 1600 } 1601 1602 if ((rc = verify_user_pin(hContext, hash_sha))) { 1603 return (rc); 1604 } 1605 1606 (void) memcpy(current_user_pin_sha, hash_sha, 1607 SHA1_DIGEST_LENGTH); 1608 1609 rc = load_private_token_objects(hContext); 1610 if (rc == CKR_OK) { 1611 (void) XProcLock(xproclock); 1612 global_shm->priv_loaded = TRUE; 1613 (void) XProcUnLock(xproclock); 1614 } 1615 } else { 1616 /* 1617 * SO login logic: 1618 * 1619 * - find publicRootKey UUID 1620 * - load by UUID wrap with hSRK from above 1621 */ 1622 if (local_uuid_is_null(&publicRootKeyUUID) && 1623 find_uuid(TPMTOK_PUBLIC_ROOT_KEY_ID, 1624 &publicRootKeyUUID)) { 1625 if (memcmp(hash_sha, 1626 default_so_pin_sha, 1627 SHA1_DIGEST_LENGTH)) 1628 return (CKR_PIN_INCORRECT); 1629 1630 not_initialized = 1; 1631 return (CKR_OK); 1632 1633 } 1634 if (hPublicRootKey == NULL_HKEY) { 1635 result = tss_find_and_load_key( 1636 hContext, 1637 TPMTOK_PUBLIC_ROOT_KEY_ID, 1638 &publicRootKeyUUID, hSRK, NULL, 1639 &hPublicRootKey); 1640 1641 if (result) 1642 return (CKR_FUNCTION_FAILED); 1643 } 1644 1645 /* find, load the public leaf key */ 1646 if (hPublicLeafKey == NULL_HKEY) { 1647 result = tss_find_and_load_key( 1648 hContext, 1649 TPMTOK_PUBLIC_LEAF_KEY_ID, 1650 &publicLeafKeyUUID, hPublicRootKey, hash_sha, 1651 &hPublicLeafKey); 1652 if (result) 1653 return (CKR_FUNCTION_FAILED); 1654 } 1655 1656 if ((rc = token_verify_pin(hContext, hPublicLeafKey))) { 1657 return (rc); 1658 } 1659 1660 (void) memcpy(current_so_pin_sha, hash_sha, SHA1_DIGEST_LENGTH); 1661 } 1662 1663 return (rc); 1664 } 1665 1666 CK_RV 1667 token_specific_logout(TSS_HCONTEXT hContext) 1668 { 1669 if (hPrivateLeafKey != NULL_HKEY) { 1670 Tspi_Key_UnloadKey(hPrivateLeafKey); 1671 hPrivateLeafKey = NULL_HKEY; 1672 } else if (hPublicLeafKey != NULL_HKEY) { 1673 Tspi_Key_UnloadKey(hPublicLeafKey); 1674 hPublicLeafKey = NULL_HKEY; 1675 } 1676 1677 local_uuid_clear(&publicRootKeyUUID); 1678 local_uuid_clear(&publicLeafKeyUUID); 1679 local_uuid_clear(&privateRootKeyUUID); 1680 local_uuid_clear(&privateLeafKeyUUID); 1681 1682 (void) memset(current_so_pin_sha, 0, SHA1_DIGEST_LENGTH); 1683 (void) memset(current_user_pin_sha, 0, SHA1_DIGEST_LENGTH); 1684 1685 (void) object_mgr_purge_private_token_objects(hContext); 1686 1687 return (CKR_OK); 1688 } 1689 1690 /*ARGSUSED*/ 1691 CK_RV 1692 token_specific_init_pin(TSS_HCONTEXT hContext, 1693 CK_CHAR_PTR pPin, CK_ULONG ulPinLen) 1694 { 1695 /* 1696 * Since the SO must log in before calling C_InitPIN, we will 1697 * be able to return (CKR_OK) automatically here. 1698 * This is because the USER key structure is created at the 1699 * time of her first login, not at C_InitPIN time. 1700 */ 1701 return (CKR_OK); 1702 } 1703 1704 static CK_RV 1705 check_pin_properties(CK_USER_TYPE userType, CK_BYTE *pinHash, 1706 CK_ULONG ulPinLen) 1707 { 1708 /* make sure the new PIN is different */ 1709 if (userType == CKU_USER) { 1710 if (!memcmp(pinHash, default_user_pin_sha, 1711 SHA1_DIGEST_LENGTH)) { 1712 LogError1("new PIN must not be the default"); 1713 return (CKR_PIN_INVALID); 1714 } 1715 } else { 1716 if (!memcmp(pinHash, default_so_pin_sha, 1717 SHA1_DIGEST_LENGTH)) { 1718 LogError1("new PIN must not be the default"); 1719 return (CKR_PIN_INVALID); 1720 } 1721 } 1722 1723 if (ulPinLen > MAX_PIN_LEN || ulPinLen < MIN_PIN_LEN) { 1724 LogError1("New PIN is out of size range"); 1725 return (CKR_PIN_LEN_RANGE); 1726 } 1727 1728 return (CKR_OK); 1729 } 1730 1731 /* 1732 * This function is called from set_pin only, where a non-logged-in public 1733 * session can provide the user pin which must be verified. This function 1734 * assumes that the pin has already been set once, so there's no migration 1735 * path option or checking of the default user pin. 1736 */ 1737 static CK_RV 1738 verify_user_pin(TSS_HCONTEXT hContext, CK_BYTE *hash_sha) 1739 { 1740 CK_RV rc; 1741 TSS_RESULT result; 1742 TSS_HKEY hSRK; 1743 1744 if (token_load_srk(hContext, &hSRK)) 1745 return (CKR_FUNCTION_FAILED); 1746 1747 /* 1748 * Verify the user by loading the privateLeafKey 1749 * into the TPM (if it's not already) and then 1750 * call the verify_pin operation. 1751 * 1752 * The hashed PIN is assigned to the private leaf key. 1753 * If it is incorrect (not the same as the one originally 1754 * used when the key was created), the verify operation 1755 * will fail. 1756 */ 1757 if (hPrivateRootKey == NULL_HKEY) { 1758 result = tss_find_and_load_key( 1759 hContext, 1760 TPMTOK_PRIVATE_ROOT_KEY_ID, 1761 &privateRootKeyUUID, hSRK, NULL, &hPrivateRootKey); 1762 if (result) 1763 return (CKR_FUNCTION_FAILED); 1764 } 1765 1766 if (hPrivateLeafKey == NULL_HKEY) { 1767 result = tss_find_and_load_key( 1768 hContext, 1769 TPMTOK_PRIVATE_LEAF_KEY_ID, 1770 &privateLeafKeyUUID, hPrivateRootKey, hash_sha, 1771 &hPrivateLeafKey); 1772 1773 if (result) 1774 return (CKR_FUNCTION_FAILED); 1775 } 1776 1777 /* 1778 * Verify that the PIN is correct by attempting to wrap/unwrap some 1779 * random data. 1780 */ 1781 if ((rc = token_verify_pin(hContext, hPrivateLeafKey))) { 1782 return (rc); 1783 } 1784 1785 return (CKR_OK); 1786 } 1787 1788 CK_RV 1789 token_specific_set_pin(ST_SESSION_HANDLE session, 1790 CK_CHAR_PTR pOldPin, CK_ULONG ulOldPinLen, 1791 CK_CHAR_PTR pNewPin, CK_ULONG ulNewPinLen) 1792 { 1793 SESSION *sess = session_mgr_find(session.sessionh); 1794 CK_BYTE oldpin_hash[SHA1_DIGEST_LENGTH]; 1795 CK_BYTE newpin_hash[SHA1_DIGEST_LENGTH]; 1796 CK_RV rc; 1797 TSS_HKEY hSRK; 1798 1799 if (!sess) { 1800 return (CKR_SESSION_HANDLE_INVALID); 1801 } 1802 1803 if ((rc = compute_sha(pOldPin, ulOldPinLen, oldpin_hash))) { 1804 return (CKR_FUNCTION_FAILED); 1805 } 1806 if ((rc = compute_sha(pNewPin, ulNewPinLen, newpin_hash))) { 1807 return (CKR_FUNCTION_FAILED); 1808 } 1809 1810 if (token_load_srk(sess->hContext, &hSRK)) { 1811 return (CKR_FUNCTION_FAILED); 1812 } 1813 1814 /* 1815 * From the PKCS#11 2.20 spec: "C_SetPIN modifies the PIN of 1816 * the user that is currently logged in, or the CKU_USER PIN 1817 * if the session is not logged in." 1818 * A non R/W session fails with CKR_SESSION_READ_ONLY. 1819 */ 1820 if (sess->session_info.state == CKS_RW_USER_FUNCTIONS || 1821 sess->session_info.state == CKS_RW_PUBLIC_SESSION) { 1822 if (not_initialized) { 1823 if (memcmp(oldpin_hash, default_user_pin_sha, 1824 SHA1_DIGEST_LENGTH)) { 1825 return (CKR_PIN_INCORRECT); 1826 } 1827 1828 if ((rc = check_pin_properties(CKU_USER, newpin_hash, 1829 ulNewPinLen))) { 1830 return (rc); 1831 } 1832 1833 if ((rc = token_create_private_tree(sess->hContext, 1834 newpin_hash))) { 1835 return (CKR_FUNCTION_FAILED); 1836 } 1837 1838 nv_token_data->token_info.flags &= 1839 ~(CKF_USER_PIN_TO_BE_CHANGED); 1840 nv_token_data->token_info.flags |= 1841 CKF_USER_PIN_INITIALIZED; 1842 1843 nv_token_data->token_info.flags &= 1844 ~(CKF_USER_PIN_TO_BE_CHANGED); 1845 nv_token_data->token_info.flags |= 1846 CKF_USER_PIN_INITIALIZED; 1847 1848 return (save_token_data(nv_token_data)); 1849 } 1850 1851 if (sess->session_info.state == CKS_RW_USER_FUNCTIONS) { 1852 /* if we're already logged in, just verify the hash */ 1853 if (memcmp(current_user_pin_sha, oldpin_hash, 1854 SHA1_DIGEST_LENGTH)) { 1855 return (CKR_PIN_INCORRECT); 1856 } 1857 } else { 1858 if ((rc = verify_user_pin(sess->hContext, 1859 oldpin_hash))) { 1860 return (rc); 1861 } 1862 } 1863 1864 if ((rc = check_pin_properties(CKU_USER, newpin_hash, 1865 ulNewPinLen))) 1866 return (rc); 1867 1868 /* change the auth on the TSS object */ 1869 if (tss_change_auth(sess->hContext, 1870 hPrivateLeafKey, hPrivateRootKey, 1871 privateLeafKeyUUID, privateRootKeyUUID, 1872 newpin_hash)) 1873 return (CKR_FUNCTION_FAILED); 1874 1875 } else if (sess->session_info.state == CKS_RW_SO_FUNCTIONS) { 1876 if (not_initialized) { 1877 if (memcmp(default_so_pin_sha, oldpin_hash, 1878 SHA1_DIGEST_LENGTH)) 1879 return (CKR_PIN_INCORRECT); 1880 1881 if ((rc = check_pin_properties(CKU_SO, 1882 newpin_hash, ulNewPinLen))) 1883 return (rc); 1884 1885 if ((rc = token_create_public_tree(sess->hContext, 1886 newpin_hash))) 1887 return (CKR_FUNCTION_FAILED); 1888 1889 nv_token_data->token_info.flags &= 1890 ~(CKF_SO_PIN_TO_BE_CHANGED); 1891 1892 return (save_token_data(nv_token_data)); 1893 } 1894 1895 if (memcmp(current_so_pin_sha, oldpin_hash, 1896 SHA1_DIGEST_LENGTH)) 1897 return (CKR_PIN_INCORRECT); 1898 1899 if ((rc = check_pin_properties(CKU_SO, newpin_hash, 1900 ulNewPinLen))) 1901 return (rc); 1902 1903 /* change auth on the SO's leaf key */ 1904 if (tss_change_auth(sess->hContext, 1905 hPublicLeafKey, hPublicRootKey, 1906 publicLeafKeyUUID, publicRootKeyUUID, 1907 newpin_hash)) 1908 return (CKR_FUNCTION_FAILED); 1909 1910 } else { 1911 rc = CKR_SESSION_READ_ONLY; 1912 } 1913 1914 return (rc); 1915 } 1916 1917 /* only called at token init time */ 1918 CK_RV 1919 token_specific_verify_so_pin(TSS_HCONTEXT hContext, CK_CHAR_PTR pPin, 1920 CK_ULONG ulPinLen) 1921 { 1922 CK_BYTE hash_sha[SHA1_DIGEST_LENGTH]; 1923 CK_RV rc; 1924 TSS_RESULT result; 1925 TSS_HKEY hSRK; 1926 1927 if ((rc = compute_sha(pPin, ulPinLen, hash_sha))) { 1928 return (CKR_FUNCTION_FAILED); 1929 } 1930 if ((rc = token_load_srk(hContext, &hSRK))) { 1931 return (CKR_FUNCTION_FAILED); 1932 } 1933 1934 /* 1935 * TRYME INSTEAD: 1936 * - find publicRootKeyUUID 1937 * - Load publicRootKey by UUID (SRK parent) 1938 * - find publicLeafKeyUUID 1939 * - Load publicLeafKey by UUID (publicRootKey parent) 1940 * - set password policy on publicLeafKey 1941 */ 1942 if (local_uuid_is_null(&publicRootKeyUUID) && 1943 find_uuid(TPMTOK_PUBLIC_ROOT_KEY_ID, &publicRootKeyUUID)) { 1944 /* 1945 * The SO hasn't set her PIN yet, compare the 1946 * login pin with the hard-coded value. 1947 */ 1948 if (memcmp(default_so_pin_sha, hash_sha, 1949 SHA1_DIGEST_LENGTH)) { 1950 return (CKR_PIN_INCORRECT); 1951 } 1952 return (CKR_OK); 1953 } 1954 1955 result = Tspi_Context_GetKeyByUUID(hContext, 1956 TSS_PS_TYPE_USER, publicRootKeyUUID, &hPublicRootKey); 1957 1958 if (result) 1959 return (CKR_FUNCTION_FAILED); 1960 1961 result = Tspi_Key_LoadKey(hPublicRootKey, hSRK); 1962 if (result) 1963 return (CKR_FUNCTION_FAILED); 1964 1965 if (local_uuid_is_null(&publicLeafKeyUUID) && 1966 find_uuid(TPMTOK_PUBLIC_LEAF_KEY_ID, &publicLeafKeyUUID)) 1967 return (CKR_FUNCTION_FAILED); 1968 1969 result = Tspi_Context_GetKeyByUUID(hContext, 1970 TSS_PS_TYPE_USER, publicLeafKeyUUID, &hPublicLeafKey); 1971 if (result) 1972 return (CKR_FUNCTION_FAILED); 1973 1974 result = tss_assign_secret_key_policy(hContext, TSS_POLICY_USAGE, 1975 hPublicLeafKey, hash_sha); 1976 if (result) 1977 return (CKR_FUNCTION_FAILED); 1978 1979 result = Tspi_Key_LoadKey(hPublicLeafKey, hPublicRootKey); 1980 if (result) 1981 return (CKR_FUNCTION_FAILED); 1982 1983 /* If the hash given is wrong, the verify will fail */ 1984 if ((rc = token_verify_pin(hContext, hPublicLeafKey))) { 1985 return (rc); 1986 } 1987 1988 return (CKR_OK); 1989 } 1990 1991 CK_RV 1992 token_specific_final(TSS_HCONTEXT hContext) 1993 { 1994 if (hPublicRootKey != NULL_HKEY) { 1995 Tspi_Context_CloseObject(hContext, hPublicRootKey); 1996 hPublicRootKey = NULL_HKEY; 1997 } 1998 if (hPublicLeafKey != NULL_HKEY) { 1999 Tspi_Context_CloseObject(hContext, hPublicLeafKey); 2000 hPublicLeafKey = NULL_HKEY; 2001 } 2002 if (hPrivateRootKey != NULL_HKEY) { 2003 Tspi_Context_CloseObject(hContext, hPrivateRootKey); 2004 hPrivateRootKey = NULL_HKEY; 2005 } 2006 if (hPrivateLeafKey != NULL_HKEY) { 2007 Tspi_Context_CloseObject(hContext, hPrivateLeafKey); 2008 hPrivateLeafKey = NULL_HKEY; 2009 } 2010 return (CKR_OK); 2011 } 2012 2013 /* 2014 * Wrap the 20 bytes of auth data and store in an attribute of the two 2015 * keys. 2016 */ 2017 static CK_RV 2018 token_wrap_auth_data(TSS_HCONTEXT hContext, 2019 CK_BYTE *authData, TEMPLATE *publ_tmpl, 2020 TEMPLATE *priv_tmpl) 2021 { 2022 CK_RV rc; 2023 CK_ATTRIBUTE *new_attr; 2024 2025 TSS_RESULT ret; 2026 TSS_HKEY hParentKey; 2027 TSS_HENCDATA hEncData; 2028 BYTE *blob; 2029 UINT32 blob_size; 2030 2031 if ((hPrivateLeafKey == NULL_HKEY) && (hPublicLeafKey == NULL_HKEY)) { 2032 return (CKR_FUNCTION_FAILED); 2033 } else if (hPublicLeafKey != NULL_HKEY) { 2034 hParentKey = hPublicLeafKey; 2035 } else { 2036 hParentKey = hPrivateLeafKey; 2037 } 2038 2039 /* create the encrypted data object */ 2040 if ((ret = Tspi_Context_CreateObject(hContext, 2041 TSS_OBJECT_TYPE_ENCDATA, TSS_ENCDATA_BIND, &hEncData))) { 2042 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 2043 ret, Trspi_Error_String(ret)); 2044 return (CKR_FUNCTION_FAILED); 2045 } 2046 2047 if ((ret = Tspi_Data_Bind(hEncData, hParentKey, SHA1_DIGEST_LENGTH, 2048 authData))) { 2049 stlogit("Tspi_Data_Bind: 0x%0x - %s", 2050 ret, Trspi_Error_String(ret)); 2051 return (CKR_FUNCTION_FAILED); 2052 } 2053 2054 /* pull the encrypted data out of the encrypted data object */ 2055 if ((ret = Tspi_GetAttribData(hEncData, TSS_TSPATTRIB_ENCDATA_BLOB, 2056 TSS_TSPATTRIB_ENCDATABLOB_BLOB, &blob_size, &blob))) { 2057 stlogit("Tspi_SetAttribData: 0x%0x - %s", 2058 ret, Trspi_Error_String(ret)); 2059 return (CKR_FUNCTION_FAILED); 2060 } 2061 2062 if ((rc = build_attribute(CKA_ENC_AUTHDATA, blob, blob_size, 2063 &new_attr))) { 2064 return (rc); 2065 } 2066 (void) template_update_attribute(publ_tmpl, new_attr); 2067 2068 if ((rc = build_attribute(CKA_ENC_AUTHDATA, blob, 2069 blob_size, &new_attr))) { 2070 return (rc); 2071 } 2072 (void) template_update_attribute(priv_tmpl, new_attr); 2073 2074 return (rc); 2075 } 2076 2077 static CK_RV 2078 token_unwrap_auth_data(TSS_HCONTEXT hContext, CK_BYTE *encAuthData, 2079 CK_ULONG encAuthDataLen, TSS_HKEY hKey, 2080 BYTE **authData) 2081 { 2082 TSS_RESULT result; 2083 TSS_HENCDATA hEncData; 2084 BYTE *buf; 2085 UINT32 buf_size; 2086 2087 if ((result = Tspi_Context_CreateObject(hContext, 2088 TSS_OBJECT_TYPE_ENCDATA, TSS_ENCDATA_BIND, &hEncData))) { 2089 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 2090 result, Trspi_Error_String(result)); 2091 return (CKR_FUNCTION_FAILED); 2092 } 2093 2094 if ((result = Tspi_SetAttribData(hEncData, 2095 TSS_TSPATTRIB_ENCDATA_BLOB, TSS_TSPATTRIB_ENCDATABLOB_BLOB, 2096 encAuthDataLen, encAuthData))) { 2097 stlogit("Tspi_SetAttribData: 0x%0x - %s", 2098 result, Trspi_Error_String(result)); 2099 return (CKR_FUNCTION_FAILED); 2100 } 2101 2102 /* unbind the data, receiving the plaintext back */ 2103 if ((result = Tspi_Data_Unbind(hEncData, hKey, &buf_size, &buf))) { 2104 stlogit("Tspi_Data_Unbind: 0x%0x - %s", 2105 result, Trspi_Error_String(result)); 2106 return (CKR_FUNCTION_FAILED); 2107 } 2108 2109 if (buf_size != SHA1_DIGEST_LENGTH) { 2110 return (CKR_FUNCTION_FAILED); 2111 } 2112 2113 *authData = buf; 2114 2115 return (CKR_OK); 2116 } 2117 2118 CK_RV 2119 token_specific_rsa_generate_keypair( 2120 TSS_HCONTEXT hContext, 2121 TEMPLATE *publ_tmpl, 2122 TEMPLATE *priv_tmpl) 2123 { 2124 CK_ATTRIBUTE *attr = NULL; 2125 CK_ULONG mod_bits = 0; 2126 CK_BBOOL flag; 2127 CK_RV rc; 2128 2129 TSS_FLAG initFlags = 0; 2130 BYTE authHash[SHA1_DIGEST_LENGTH]; 2131 BYTE *authData = NULL; 2132 TSS_HKEY hKey = NULL_HKEY; 2133 TSS_HKEY hParentKey = NULL_HKEY; 2134 TSS_RESULT result; 2135 UINT32 ulBlobLen; 2136 BYTE *rgbBlob; 2137 2138 /* Make sure the public exponent is usable */ 2139 if ((util_check_public_exponent(publ_tmpl))) { 2140 return (CKR_TEMPLATE_INCONSISTENT); 2141 } 2142 2143 flag = template_attribute_find(publ_tmpl, CKA_MODULUS_BITS, &attr); 2144 if (!flag) { 2145 return (CKR_TEMPLATE_INCOMPLETE); 2146 } 2147 mod_bits = *(CK_ULONG *)attr->pValue; 2148 2149 if ((initFlags = util_get_keysize_flag(mod_bits)) == 0) { 2150 return (CKR_KEY_SIZE_RANGE); 2151 } 2152 2153 /* 2154 * If we're not logged in, hPrivateLeafKey and hPublicLeafKey 2155 * should be NULL. 2156 */ 2157 if ((hPrivateLeafKey == NULL_HKEY) && 2158 (hPublicLeafKey == NULL_HKEY)) { 2159 /* public session, wrap key with the PRK */ 2160 initFlags |= TSS_KEY_TYPE_LEGACY | 2161 TSS_KEY_NO_AUTHORIZATION | TSS_KEY_MIGRATABLE; 2162 2163 if ((result = token_load_public_root_key(hContext))) { 2164 return (CKR_FUNCTION_FAILED); 2165 } 2166 2167 hParentKey = hPublicRootKey; 2168 } else if (hPrivateLeafKey != NULL_HKEY) { 2169 /* logged in USER session */ 2170 initFlags |= TSS_KEY_TYPE_LEGACY | 2171 TSS_KEY_AUTHORIZATION | TSS_KEY_MIGRATABLE; 2172 2173 /* get a random SHA1 hash for the auth data */ 2174 if ((rc = token_rng(hContext, authHash, SHA1_DIGEST_LENGTH))) { 2175 return (CKR_FUNCTION_FAILED); 2176 } 2177 2178 authData = authHash; 2179 hParentKey = hPrivateRootKey; 2180 } else { 2181 /* logged in SO session */ 2182 initFlags |= TSS_KEY_TYPE_LEGACY | 2183 TSS_KEY_AUTHORIZATION | TSS_KEY_MIGRATABLE; 2184 2185 /* get a random SHA1 hash for the auth data */ 2186 if ((rc = token_rng(hContext, authHash, SHA1_DIGEST_LENGTH))) { 2187 return (CKR_FUNCTION_FAILED); 2188 } 2189 2190 authData = authHash; 2191 hParentKey = hPublicRootKey; 2192 } 2193 2194 if ((result = tss_generate_key(hContext, initFlags, authData, 2195 hParentKey, &hKey))) { 2196 return (result); 2197 } 2198 2199 if ((result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_KEY_BLOB, 2200 TSS_TSPATTRIB_KEYBLOB_BLOB, &ulBlobLen, &rgbBlob))) { 2201 stlogit("Tspi_GetAttribData: 0x%0x - %s", 2202 result, Trspi_Error_String(result)); 2203 return (CKR_FUNCTION_FAILED); 2204 } 2205 2206 if ((rc = build_attribute(CKA_IBM_OPAQUE, rgbBlob, 2207 ulBlobLen, &attr))) { 2208 Tspi_Context_FreeMemory(hContext, rgbBlob); 2209 return (rc); 2210 } 2211 (void) template_update_attribute(priv_tmpl, attr); 2212 if ((rc = build_attribute(CKA_IBM_OPAQUE, rgbBlob, 2213 ulBlobLen, &attr))) { 2214 Tspi_Context_FreeMemory(hContext, rgbBlob); 2215 return (rc); 2216 } 2217 (void) template_update_attribute(publ_tmpl, attr); 2218 2219 Tspi_Context_FreeMemory(hContext, rgbBlob); 2220 2221 /* grab the public key to put into the public key object */ 2222 if ((result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_RSAKEY_INFO, 2223 TSS_TSPATTRIB_KEYINFO_RSA_MODULUS, &ulBlobLen, &rgbBlob))) { 2224 stlogit("Tspi_GetAttribData: 0x%0x - %s", 2225 result, Trspi_Error_String(result)); 2226 return (result); 2227 } 2228 2229 /* add the public key blob to the object template */ 2230 if ((rc = build_attribute(CKA_MODULUS, rgbBlob, ulBlobLen, &attr))) { 2231 Tspi_Context_FreeMemory(hContext, rgbBlob); 2232 return (rc); 2233 } 2234 (void) template_update_attribute(publ_tmpl, attr); 2235 2236 /* add the public key blob to the object template */ 2237 if ((rc = build_attribute(CKA_MODULUS, rgbBlob, ulBlobLen, &attr))) { 2238 Tspi_Context_FreeMemory(hContext, rgbBlob); 2239 return (rc); 2240 } 2241 (void) template_update_attribute(priv_tmpl, attr); 2242 Tspi_Context_FreeMemory(hContext, rgbBlob); 2243 2244 /* wrap the authdata and put it into an object */ 2245 if (authData != NULL) { 2246 rc = token_wrap_auth_data(hContext, authData, publ_tmpl, 2247 priv_tmpl); 2248 } 2249 2250 return (rc); 2251 } 2252 2253 static CK_RV 2254 token_rsa_load_key( 2255 TSS_HCONTEXT hContext, 2256 OBJECT *key_obj, 2257 TSS_HKEY *phKey) 2258 { 2259 TSS_RESULT result; 2260 TSS_HPOLICY hPolicy = NULL_HPOLICY; 2261 TSS_HKEY hParentKey; 2262 BYTE *authData = NULL; 2263 CK_ATTRIBUTE *attr; 2264 CK_RV rc; 2265 CK_OBJECT_HANDLE handle; 2266 CK_ULONG class; 2267 2268 if (hPrivateLeafKey != NULL_HKEY) { 2269 hParentKey = hPrivateRootKey; 2270 } else { 2271 if ((result = token_load_public_root_key(hContext))) 2272 return (CKR_FUNCTION_FAILED); 2273 2274 hParentKey = hPublicRootKey; 2275 } 2276 2277 *phKey = NULL; 2278 if (template_attribute_find(key_obj->template, CKA_CLASS, 2279 &attr) == FALSE) { 2280 return (CKR_TEMPLATE_INCOMPLETE); 2281 } 2282 class = *((CK_ULONG *)attr->pValue); 2283 2284 rc = template_attribute_find(key_obj->template, 2285 CKA_IBM_OPAQUE, &attr); 2286 /* 2287 * A public key cannot use the OPAQUE data attribute so they 2288 * must be created in software. A private key may not yet 2289 * have its "opaque" data defined and needs to be created 2290 * and loaded so it can be used inside the TPM. 2291 */ 2292 if (class == CKO_PUBLIC_KEY || rc == FALSE) { 2293 rc = object_mgr_find_in_map2(hContext, key_obj, &handle); 2294 if (rc != CKR_OK) 2295 return (CKR_FUNCTION_FAILED); 2296 2297 if ((rc = token_load_key(hContext, 2298 handle, hParentKey, NULL, phKey))) { 2299 return (rc); 2300 } 2301 } 2302 /* 2303 * If this is a private key, get the blob and load it in the TPM. 2304 * If it is public, the key is already loaded in software. 2305 */ 2306 if (class == CKO_PRIVATE_KEY) { 2307 /* If we already have a handle, just load it */ 2308 if (*phKey != NULL) { 2309 result = Tspi_Key_LoadKey(*phKey, hParentKey); 2310 if (result) { 2311 stlogit("Tspi_Context_LoadKeyByBlob: " 2312 "0x%0x - %s", 2313 result, Trspi_Error_String(result)); 2314 return (CKR_FUNCTION_FAILED); 2315 } 2316 } else { 2317 /* try again to get the CKA_IBM_OPAQUE attr */ 2318 if ((rc = template_attribute_find(key_obj->template, 2319 CKA_IBM_OPAQUE, &attr)) == FALSE) { 2320 return (rc); 2321 } 2322 if ((result = Tspi_Context_LoadKeyByBlob(hContext, 2323 hParentKey, attr->ulValueLen, attr->pValue, 2324 phKey))) { 2325 stlogit("Tspi_Context_LoadKeyByBlob: " 2326 "0x%0x - %s", 2327 result, Trspi_Error_String(result)); 2328 return (CKR_FUNCTION_FAILED); 2329 } 2330 } 2331 } 2332 2333 /* auth data may be required */ 2334 if (template_attribute_find(key_obj->template, CKA_ENC_AUTHDATA, 2335 &attr) == TRUE && attr) { 2336 if ((hPrivateLeafKey == NULL_HKEY) && 2337 (hPublicLeafKey == NULL_HKEY)) { 2338 return (CKR_FUNCTION_FAILED); 2339 } else if (hPublicLeafKey != NULL_HKEY) { 2340 hParentKey = hPublicLeafKey; 2341 } else { 2342 hParentKey = hPrivateLeafKey; 2343 } 2344 2345 if ((result = token_unwrap_auth_data(hContext, 2346 attr->pValue, attr->ulValueLen, 2347 hParentKey, &authData))) { 2348 return (CKR_FUNCTION_FAILED); 2349 } 2350 2351 if ((result = Tspi_GetPolicyObject(*phKey, 2352 TSS_POLICY_USAGE, &hPolicy))) { 2353 stlogit("Tspi_GetPolicyObject: 0x%0x - %s", 2354 result, Trspi_Error_String(result)); 2355 return (CKR_FUNCTION_FAILED); 2356 } 2357 2358 /* 2359 * If the policy handle returned is the same as the 2360 * context's default policy, then a new policy must 2361 * be created and assigned to the key. Otherwise, just set the 2362 * secret in the policy. 2363 */ 2364 if (hPolicy == hDefaultPolicy) { 2365 if ((result = Tspi_Context_CreateObject(hContext, 2366 TSS_OBJECT_TYPE_POLICY, TSS_POLICY_USAGE, 2367 &hPolicy))) { 2368 stlogit("Tspi_Context_CreateObject: " 2369 "0x%0x - %s", 2370 result, Trspi_Error_String(result)); 2371 return (CKR_FUNCTION_FAILED); 2372 } 2373 2374 if ((result = Tspi_Policy_SetSecret(hPolicy, 2375 TSS_SECRET_MODE_SHA1, 2376 SHA1_DIGEST_LENGTH, authData))) { 2377 stlogit("Tspi_Policy_SetSecret: " 2378 "0x%0x - %s", 2379 result, Trspi_Error_String(result)); 2380 return (CKR_FUNCTION_FAILED); 2381 } 2382 2383 if ((result = Tspi_Policy_AssignToObject(hPolicy, 2384 *phKey))) { 2385 stlogit("Tspi_Policy_AssignToObject: " 2386 "0x%0x - %s", 2387 result, Trspi_Error_String(result)); 2388 return (CKR_FUNCTION_FAILED); 2389 } 2390 } else if ((result = Tspi_Policy_SetSecret(hPolicy, 2391 TSS_SECRET_MODE_SHA1, SHA1_DIGEST_LENGTH, authData))) { 2392 stlogit("Tspi_Policy_SetSecret: 0x%0x - %s", 2393 result, Trspi_Error_String(result)); 2394 return (CKR_FUNCTION_FAILED); 2395 } 2396 2397 Tspi_Context_FreeMemory(hContext, authData); 2398 } 2399 2400 return (CKR_OK); 2401 } 2402 2403 CK_RV 2404 tpm_decrypt_data( 2405 TSS_HCONTEXT hContext, 2406 TSS_HKEY hKey, 2407 CK_BYTE * in_data, 2408 CK_ULONG in_data_len, 2409 CK_BYTE * out_data, 2410 CK_ULONG * out_data_len) 2411 { 2412 TSS_RESULT result; 2413 TSS_HENCDATA hEncData = NULL_HENCDATA; 2414 UINT32 buf_size = 0, modLen; 2415 BYTE *buf = NULL, *modulus = NULL; 2416 CK_ULONG chunklen, remain, outlen; 2417 2418 /* push the data into the encrypted data object */ 2419 if ((result = Tspi_Context_CreateObject(hContext, 2420 TSS_OBJECT_TYPE_ENCDATA, TSS_ENCDATA_BIND, &hEncData))) { 2421 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 2422 result, Trspi_Error_String(result)); 2423 return (CKR_FUNCTION_FAILED); 2424 } 2425 2426 /* 2427 * Figure out the modulus size so we can break the data 2428 * into smaller chunks if necessary. 2429 */ 2430 if ((result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_RSAKEY_INFO, 2431 TSS_TSPATTRIB_KEYINFO_RSA_MODULUS, &modLen, &modulus))) { 2432 stlogit("Tspi_GetAttribData: 0x%0x - %s", 2433 result, Trspi_Error_String(result)); 2434 return (result); 2435 } 2436 /* we don't need the actual modulus */ 2437 Tspi_Context_FreeMemory(hContext, modulus); 2438 2439 chunklen = (in_data_len > modLen ? modLen : in_data_len); 2440 remain = in_data_len; 2441 outlen = 0; 2442 2443 while (remain > 0) { 2444 if ((result = Tspi_SetAttribData(hEncData, 2445 TSS_TSPATTRIB_ENCDATA_BLOB, 2446 TSS_TSPATTRIB_ENCDATABLOB_BLOB, 2447 chunklen, in_data))) { 2448 stlogit("Tspi_SetAttribData: 0x%0x - %s", 2449 result, Trspi_Error_String(result)); 2450 return (CKR_FUNCTION_FAILED); 2451 } 2452 2453 /* unbind the data, receiving the plaintext back */ 2454 if ((result = Tspi_Data_Unbind(hEncData, hKey, 2455 &buf_size, &buf))) { 2456 stlogit("Tspi_Data_Unbind: 0x%0x - %s", 2457 result, Trspi_Error_String(result)); 2458 return (CKR_FUNCTION_FAILED); 2459 } 2460 2461 if (*out_data_len < buf_size + outlen) { 2462 Tspi_Context_FreeMemory(hContext, buf); 2463 return (CKR_BUFFER_TOO_SMALL); 2464 } 2465 2466 (void) memcpy(out_data + outlen, buf, buf_size); 2467 2468 outlen += buf_size; 2469 in_data += chunklen; 2470 remain -= chunklen; 2471 2472 Tspi_Context_FreeMemory(hContext, buf); 2473 if (chunklen > remain) 2474 chunklen = remain; 2475 } 2476 *out_data_len = outlen; 2477 return (CKR_OK); 2478 } 2479 2480 CK_RV 2481 token_specific_rsa_decrypt( 2482 TSS_HCONTEXT hContext, 2483 CK_BYTE * in_data, 2484 CK_ULONG in_data_len, 2485 CK_BYTE * out_data, 2486 CK_ULONG * out_data_len, 2487 OBJECT * key_obj) 2488 { 2489 CK_RV rc; 2490 TSS_HKEY hKey; 2491 2492 if ((rc = token_rsa_load_key(hContext, key_obj, &hKey))) { 2493 return (rc); 2494 } 2495 2496 rc = tpm_decrypt_data(hContext, hKey, in_data, in_data_len, 2497 out_data, out_data_len); 2498 2499 return (rc); 2500 } 2501 2502 CK_RV 2503 token_specific_rsa_verify( 2504 TSS_HCONTEXT hContext, 2505 CK_BYTE * in_data, 2506 CK_ULONG in_data_len, 2507 CK_BYTE * sig, 2508 CK_ULONG sig_len, 2509 OBJECT * key_obj) 2510 { 2511 TSS_RESULT result; 2512 TSS_HHASH hHash; 2513 TSS_HKEY hKey; 2514 CK_RV rc; 2515 2516 if ((rc = token_rsa_load_key(hContext, key_obj, &hKey))) { 2517 return (rc); 2518 } 2519 2520 /* Create the hash object we'll use to sign */ 2521 if ((result = Tspi_Context_CreateObject(hContext, 2522 TSS_OBJECT_TYPE_HASH, TSS_HASH_OTHER, &hHash))) { 2523 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 2524 result, Trspi_Error_String(result)); 2525 return (CKR_FUNCTION_FAILED); 2526 } 2527 2528 /* Insert the data into the hash object */ 2529 if ((result = Tspi_Hash_SetHashValue(hHash, in_data_len, 2530 in_data))) { 2531 stlogit("Tspi_Hash_SetHashValue: 0x%0x - %s", 2532 result, Trspi_Error_String(result)); 2533 return (CKR_FUNCTION_FAILED); 2534 } 2535 2536 /* Verify */ 2537 result = Tspi_Hash_VerifySignature(hHash, hKey, sig_len, sig); 2538 if (result != TSS_SUCCESS && 2539 TPMTOK_TSS_ERROR_CODE(result) != TSS_E_FAIL) { 2540 stlogit("Tspi_Hash_VerifySignature: 0x%0x - %s", 2541 result, Trspi_Error_String(result)); 2542 } 2543 2544 if (TPMTOK_TSS_ERROR_CODE(result) == TSS_E_FAIL) { 2545 rc = CKR_SIGNATURE_INVALID; 2546 } else { 2547 rc = CKR_OK; 2548 } 2549 2550 return (rc); 2551 } 2552 2553 CK_RV 2554 token_specific_rsa_sign( 2555 TSS_HCONTEXT hContext, 2556 CK_BYTE * in_data, 2557 CK_ULONG in_data_len, 2558 CK_BYTE * out_data, 2559 CK_ULONG * out_data_len, 2560 OBJECT * key_obj) 2561 { 2562 TSS_RESULT result; 2563 TSS_HHASH hHash; 2564 BYTE *sig; 2565 UINT32 sig_len; 2566 TSS_HKEY hKey; 2567 CK_RV rc; 2568 2569 if ((rc = token_rsa_load_key(hContext, key_obj, &hKey))) { 2570 return (rc); 2571 } 2572 2573 /* Create the hash object we'll use to sign */ 2574 if ((result = Tspi_Context_CreateObject(hContext, 2575 TSS_OBJECT_TYPE_HASH, TSS_HASH_OTHER, &hHash))) { 2576 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 2577 result, Trspi_Error_String(result)); 2578 return (CKR_FUNCTION_FAILED); 2579 } 2580 2581 /* Insert the data into the hash object */ 2582 if ((result = Tspi_Hash_SetHashValue(hHash, in_data_len, 2583 in_data))) { 2584 stlogit("Tspi_Hash_SetHashValue: 0x%0x - %s", 2585 result, Trspi_Error_String(result)); 2586 return (CKR_FUNCTION_FAILED); 2587 } 2588 2589 /* Sign */ 2590 if ((result = Tspi_Hash_Sign(hHash, hKey, &sig_len, &sig))) { 2591 stlogit("Tspi_Hash_Sign: 0x%0x - %s", 2592 result, Trspi_Error_String(result)); 2593 return (CKR_DATA_LEN_RANGE); 2594 } 2595 2596 if (sig_len > *out_data_len) { 2597 Tspi_Context_FreeMemory(hContext, sig); 2598 return (CKR_BUFFER_TOO_SMALL); 2599 } 2600 2601 (void) memcpy(out_data, sig, sig_len); 2602 *out_data_len = sig_len; 2603 Tspi_Context_FreeMemory(hContext, sig); 2604 2605 return (CKR_OK); 2606 } 2607 2608 CK_RV 2609 tpm_encrypt_data( 2610 TSS_HCONTEXT hContext, 2611 TSS_HKEY hKey, 2612 CK_BYTE *in_data, 2613 CK_ULONG in_data_len, 2614 CK_BYTE *out_data, 2615 CK_ULONG *out_data_len) 2616 { 2617 TSS_RESULT result; 2618 TSS_HENCDATA hEncData; 2619 BYTE *dataBlob, *modulus; 2620 UINT32 dataBlobSize, modLen; 2621 CK_ULONG chunklen, remain; 2622 CK_ULONG outlen; 2623 UINT32 keyusage, scheme, maxsize; 2624 2625 if ((result = Tspi_Context_CreateObject(hContext, 2626 TSS_OBJECT_TYPE_ENCDATA, TSS_ENCDATA_BIND, &hEncData))) { 2627 stlogit("Tspi_Context_CreateObject: 0x%0x - %s", 2628 result, Trspi_Error_String(result)); 2629 return (CKR_FUNCTION_FAILED); 2630 } 2631 /* 2632 * Figure out the modulus size so we can break the data 2633 * into smaller chunks if necessary. 2634 */ 2635 if ((result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_RSAKEY_INFO, 2636 TSS_TSPATTRIB_KEYINFO_RSA_MODULUS, &modLen, &modulus))) { 2637 stlogit("Tspi_GetAttribData: 0x%0x - %s", 2638 result, Trspi_Error_String(result)); 2639 return (result); 2640 } 2641 /* we don't need the actual modulus */ 2642 Tspi_Context_FreeMemory(hContext, modulus); 2643 2644 /* 2645 * According to TSS spec for Tspi_Data_Bind (4.3.4.21.5), 2646 * Max input data size varies depending on the key type and 2647 * encryption scheme. 2648 */ 2649 if ((result = Tspi_GetAttribUint32(hKey, TSS_TSPATTRIB_KEY_INFO, 2650 TSS_TSPATTRIB_KEYINFO_USAGE, &keyusage))) { 2651 stlogit("Cannot find USAGE: %s\n", 2652 Trspi_Error_String(result)); 2653 return (result); 2654 } 2655 if ((result = Tspi_GetAttribUint32(hKey, TSS_TSPATTRIB_KEY_INFO, 2656 TSS_TSPATTRIB_KEYINFO_ENCSCHEME, &scheme))) { 2657 stlogit("Cannot find ENCSCHEME: %s\n", 2658 Trspi_Error_String(result)); 2659 return (result); 2660 } 2661 switch (scheme) { 2662 case TSS_ES_RSAESPKCSV15: 2663 if (keyusage == TSS_KEYUSAGE_BIND) 2664 maxsize = 16; 2665 else /* legacy */ 2666 maxsize = 11; 2667 break; 2668 case TSS_ES_RSAESOAEP_SHA1_MGF1: 2669 maxsize = 47; 2670 break; 2671 default: 2672 maxsize = 0; 2673 } 2674 2675 modLen -= maxsize; 2676 2677 chunklen = (in_data_len > modLen ? modLen : in_data_len); 2678 remain = in_data_len; 2679 outlen = 0; 2680 while (remain > 0) { 2681 if ((result = Tspi_Data_Bind(hEncData, hKey, 2682 chunklen, in_data))) { 2683 stlogit("Tspi_Data_Bind: 0x%0x - %s", 2684 result, Trspi_Error_String(result)); 2685 return (CKR_FUNCTION_FAILED); 2686 } 2687 2688 if ((result = Tspi_GetAttribData(hEncData, 2689 TSS_TSPATTRIB_ENCDATA_BLOB, 2690 TSS_TSPATTRIB_ENCDATABLOB_BLOB, 2691 &dataBlobSize, &dataBlob))) { 2692 stlogit("Tspi_GetAttribData: 0x%0x - %s", 2693 result, Trspi_Error_String(result)); 2694 return (CKR_FUNCTION_FAILED); 2695 } 2696 2697 if (outlen + dataBlobSize > *out_data_len) { 2698 Tspi_Context_FreeMemory(hContext, dataBlob); 2699 return (CKR_DATA_LEN_RANGE); 2700 } 2701 2702 (void) memcpy(out_data + outlen, 2703 dataBlob, dataBlobSize); 2704 2705 outlen += dataBlobSize; 2706 in_data += chunklen; 2707 remain -= chunklen; 2708 2709 if (chunklen > remain) 2710 chunklen = remain; 2711 2712 Tspi_Context_FreeMemory(hContext, dataBlob); 2713 } 2714 *out_data_len = outlen; 2715 2716 return (CKR_OK); 2717 } 2718 2719 CK_RV 2720 token_specific_rsa_encrypt( 2721 TSS_HCONTEXT hContext, 2722 CK_BYTE * in_data, 2723 CK_ULONG in_data_len, 2724 CK_BYTE * out_data, 2725 CK_ULONG * out_data_len, 2726 OBJECT * key_obj) 2727 { 2728 TSS_HKEY hKey; 2729 CK_RV rc; 2730 2731 if ((rc = token_rsa_load_key(hContext, key_obj, &hKey))) { 2732 return (rc); 2733 } 2734 2735 rc = tpm_encrypt_data(hContext, hKey, in_data, in_data_len, 2736 out_data, out_data_len); 2737 2738 return (rc); 2739 } 2740 2741 /* 2742 * RSA Verify Recover 2743 * 2744 * Public key crypto is done in software, not by the TPM. 2745 * We bypass the TSPI library here in favor of calls directly 2746 * to OpenSSL because we don't want to add any padding, the in_data (signature) 2747 * already contains the data stream to be decrypted and is already 2748 * padded and formatted correctly. 2749 */ 2750 CK_RV 2751 token_specific_rsa_verify_recover( 2752 TSS_HCONTEXT hContext, 2753 CK_BYTE *in_data, /* signature */ 2754 CK_ULONG in_data_len, 2755 CK_BYTE *out_data, /* decrypted */ 2756 CK_ULONG *out_data_len, 2757 OBJECT *key_obj) 2758 { 2759 TSS_HKEY hKey; 2760 TSS_RESULT result; 2761 CK_RV rc; 2762 BYTE *modulus; 2763 UINT32 modLen; 2764 RSA *rsa = NULL; 2765 uchar_t exp[] = { 0x01, 0x00, 0x01 }; 2766 int sslrv, num; 2767 BYTE temp[MAX_RSA_KEYLENGTH]; 2768 BYTE outdata[MAX_RSA_KEYLENGTH]; 2769 int i; 2770 2771 if ((rc = token_rsa_load_key(hContext, key_obj, &hKey))) { 2772 return (rc); 2773 } 2774 2775 if ((result = Tspi_GetAttribData(hKey, TSS_TSPATTRIB_RSAKEY_INFO, 2776 TSS_TSPATTRIB_KEYINFO_RSA_MODULUS, &modLen, &modulus))) { 2777 stlogit("Tspi_GetAttribData: 0x%0x - %s", 2778 result, Trspi_Error_String(result)); 2779 return (CKR_FUNCTION_FAILED); 2780 } 2781 2782 if (in_data_len != modLen) { 2783 rc = CKR_SIGNATURE_LEN_RANGE; 2784 goto end; 2785 } 2786 2787 rsa = RSA_new(); 2788 if (rsa == NULL) { 2789 rc = CKR_HOST_MEMORY; 2790 goto end; 2791 } 2792 2793 rsa->n = BN_bin2bn(modulus, modLen, rsa->n); 2794 rsa->e = BN_bin2bn(exp, sizeof (exp), rsa->e); 2795 if (rsa->n == NULL || rsa->e == NULL) { 2796 rc = CKR_HOST_MEMORY; 2797 goto end; 2798 } 2799 2800 rsa->flags |= RSA_FLAG_SIGN_VER; 2801 2802 /* use RSA_NO_PADDING because the data is already padded (PKCS1) */ 2803 sslrv = RSA_public_encrypt(in_data_len, in_data, outdata, 2804 rsa, RSA_NO_PADDING); 2805 if (sslrv == -1) { 2806 rc = CKR_FUNCTION_FAILED; 2807 goto end; 2808 } 2809 2810 /* Strip leading 0's before stripping the padding */ 2811 for (i = 0; i < sslrv; i++) 2812 if (outdata[i] != 0) 2813 break; 2814 2815 num = BN_num_bytes(rsa->n); 2816 2817 /* Use OpenSSL function for stripping PKCS#1 padding */ 2818 sslrv = RSA_padding_check_PKCS1_type_1(temp, sizeof (temp), 2819 &outdata[i], sslrv - i, num); 2820 2821 if (sslrv < 0) { 2822 rc = CKR_FUNCTION_FAILED; 2823 goto end; 2824 } 2825 2826 if (*out_data_len < sslrv) { 2827 rc = CKR_BUFFER_TOO_SMALL; 2828 *out_data_len = 0; 2829 goto end; 2830 } 2831 2832 /* The return code indicates the number of bytes remaining */ 2833 (void) memcpy(out_data, temp, sslrv); 2834 *out_data_len = sslrv; 2835 end: 2836 Tspi_Context_FreeMemory(hContext, modulus); 2837 if (rsa) 2838 RSA_free(rsa); 2839 2840 return (rc); 2841 } 2842