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