1 2 /* 3 * Licensed Materials - Property of IBM 4 * 5 * trousers - An open source TCG Software Stack 6 * 7 * (C) Copyright International Business Machines Corp. 2004-2007 8 * 9 */ 10 11 12 #include <stdlib.h> 13 #include <stdio.h> 14 #include <string.h> 15 16 #include "trousers/tss.h" 17 #include "trousers/trousers.h" 18 #include "trousers_types.h" 19 #include "trousers_types.h" 20 #include "spi_utils.h" 21 #include "capabilities.h" 22 #include "tsplog.h" 23 #include "obj.h" 24 #include "authsess.h" 25 26 27 TSS_RESULT 28 Tspi_Key_UnloadKey(TSS_HKEY hKey) /* in */ 29 { 30 TSS_HCONTEXT tspContext; 31 TCS_KEY_HANDLE hTcsKey; 32 TSS_RESULT result; 33 34 if ((result = obj_rsakey_get_tsp_context(hKey, &tspContext))) 35 return result; 36 37 if ((result = obj_rsakey_get_tcs_handle(hKey, &hTcsKey))) 38 return result; 39 40 return __tspi_free_resource(tspContext, hTcsKey, TPM_RT_KEY); 41 } 42 43 TSS_RESULT 44 Tspi_Key_LoadKey(TSS_HKEY hKey, /* in */ 45 TSS_HKEY hUnwrappingKey) /* in */ 46 { 47 TPM_AUTH auth; 48 TCPA_DIGEST digest; 49 TSS_RESULT result; 50 UINT32 keyslot; 51 TSS_HCONTEXT tspContext; 52 TSS_HPOLICY hPolicy; 53 UINT32 keySize; 54 BYTE *keyBlob; 55 TCS_KEY_HANDLE tcsKey, tcsParentHandle; 56 TSS_BOOL usesAuth; 57 TPM_AUTH *pAuth; 58 Trspi_HashCtx hashCtx; 59 TPM_COMMAND_CODE ordinal; 60 61 if (!obj_is_rsakey(hUnwrappingKey)) 62 return TSPERR(TSS_E_INVALID_HANDLE); 63 64 if ((result = obj_rsakey_get_tsp_context(hKey, &tspContext))) 65 return result; 66 67 if ((result = obj_context_get_loadkey_ordinal(tspContext, &ordinal))) 68 return result; 69 70 if ((result = obj_rsakey_get_blob(hKey, &keySize, &keyBlob))) 71 return result; 72 73 if ((result = obj_rsakey_get_tcs_handle(hUnwrappingKey, &tcsParentHandle))) 74 return result; 75 76 if ((result = obj_rsakey_get_policy(hUnwrappingKey, TSS_POLICY_USAGE, &hPolicy, 77 &usesAuth))) { 78 free_tspi(tspContext, keyBlob); 79 return result; 80 } 81 82 if (usesAuth) { 83 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 84 result |= Trspi_Hash_UINT32(&hashCtx, ordinal); 85 result |= Trspi_HashUpdate(&hashCtx, keySize, keyBlob); 86 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) { 87 free_tspi(tspContext, keyBlob); 88 return result; 89 } 90 91 if ((result = secret_PerformAuth_OIAP(hUnwrappingKey, ordinal, hPolicy, FALSE, 92 &digest, &auth))) { 93 free_tspi(tspContext, keyBlob); 94 return result; 95 } 96 pAuth = &auth; 97 } else { 98 pAuth = NULL; 99 } 100 101 if ((result = TCS_API(tspContext)->LoadKeyByBlob(tspContext, tcsParentHandle, keySize, 102 keyBlob, pAuth, &tcsKey, &keyslot))) { 103 free_tspi(tspContext, keyBlob); 104 return result; 105 } 106 107 free_tspi(tspContext, keyBlob); 108 109 if (usesAuth) { 110 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 111 result |= Trspi_Hash_UINT32(&hashCtx, result); 112 result |= Trspi_Hash_UINT32(&hashCtx, ordinal); 113 if (ordinal == TPM_ORD_LoadKey) 114 result |= Trspi_Hash_UINT32(&hashCtx, keyslot); 115 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 116 return result; 117 118 if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &auth))) 119 return result; 120 } 121 122 return obj_rsakey_set_tcs_handle(hKey, tcsKey); 123 } 124 125 TSS_RESULT 126 Tspi_Key_GetPubKey(TSS_HKEY hKey, /* in */ 127 UINT32 * pulPubKeyLength, /* out */ 128 BYTE ** prgbPubKey) /* out */ 129 { 130 TPM_AUTH auth; 131 TPM_AUTH *pAuth; 132 TCPA_DIGEST digest; 133 TCPA_RESULT result; 134 TSS_HCONTEXT tspContext; 135 TSS_HPOLICY hPolicy; 136 TCS_KEY_HANDLE tcsKeyHandle; 137 TSS_BOOL usesAuth; 138 Trspi_HashCtx hashCtx; 139 140 if (pulPubKeyLength == NULL || prgbPubKey == NULL) 141 return TSPERR(TSS_E_BAD_PARAMETER); 142 143 if ((result = obj_rsakey_get_tsp_context(hKey, &tspContext))) 144 return result; 145 146 if ((result = obj_rsakey_get_policy(hKey, TSS_POLICY_USAGE, 147 &hPolicy, &usesAuth))) 148 return result; 149 150 if ((result = obj_rsakey_get_tcs_handle(hKey, &tcsKeyHandle))) 151 return result; 152 153 if (usesAuth) { 154 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 155 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_GetPubKey); 156 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 157 return result; 158 159 if ((result = secret_PerformAuth_OIAP(hKey, TPM_ORD_GetPubKey, hPolicy, FALSE, 160 &digest, &auth))) 161 return result; 162 pAuth = &auth; 163 } else { 164 pAuth = NULL; 165 } 166 167 if ((result = TCS_API(tspContext)->GetPubKey(tspContext, tcsKeyHandle, pAuth, 168 pulPubKeyLength, prgbPubKey))) 169 return result; 170 171 if (usesAuth) { 172 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 173 result |= Trspi_Hash_UINT32(&hashCtx, result); 174 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_GetPubKey); 175 result |= Trspi_HashUpdate(&hashCtx, *pulPubKeyLength, *prgbPubKey); 176 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 177 goto error; 178 179 /* goto error here since prgbPubKey has been set */ 180 if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &auth))) 181 goto error; 182 } 183 184 if ((result = __tspi_add_mem_entry(tspContext, *prgbPubKey))) 185 goto error; 186 187 if (tcsKeyHandle == TPM_KEYHND_SRK) 188 obj_rsakey_set_pubkey(hKey, TRUE, *prgbPubKey); 189 190 return TSS_SUCCESS; 191 error: 192 free(*prgbPubKey); 193 *prgbPubKey = NULL; 194 *pulPubKeyLength = 0; 195 return result; 196 } 197 198 TSS_RESULT 199 Tspi_Key_CreateKey(TSS_HKEY hKey, /* in */ 200 TSS_HKEY hWrappingKey, /* in */ 201 TSS_HPCRS hPcrComposite) /* in, may be NULL */ 202 { 203 #ifdef TSS_BUILD_CMK 204 UINT32 blobSize; 205 BYTE *blob; 206 TSS_BOOL isCmk = FALSE; 207 TPM_HMAC msaApproval; 208 TPM_DIGEST msaDigest; 209 #endif 210 TCPA_DIGEST digest; 211 TCPA_RESULT result; 212 TCS_KEY_HANDLE parentTCSKeyHandle; 213 BYTE *keyBlob = NULL; 214 UINT32 keySize; 215 UINT32 newKeySize; 216 BYTE *newKey = NULL; 217 UINT32 ordinal = TPM_ORD_CreateWrapKey; 218 TSS_HCONTEXT tspContext; 219 Trspi_HashCtx hashCtx; 220 struct authsess *xsap = NULL; 221 222 if ((result = obj_rsakey_get_tsp_context(hKey, &tspContext))) 223 return result; 224 225 if (hPcrComposite) { 226 /* its possible that hPcrComposite could be a bad handle here, 227 * or that no indices of it are yet set, which would throw 228 * internal error. Blanket both those codes with bad 229 * parameter to help the user out */ 230 if ((result = obj_rsakey_set_pcr_data(hKey, hPcrComposite))) 231 return TSPERR(TSS_E_BAD_PARAMETER); 232 } 233 234 if ((result = obj_rsakey_get_tcs_handle(hWrappingKey, &parentTCSKeyHandle))) 235 return result; 236 237 if ((result = obj_rsakey_get_blob(hKey, &keySize, &keyBlob))) 238 return result; 239 240 #ifdef TSS_BUILD_CMK 241 isCmk = obj_rsakey_is_cmk(hKey); 242 if (isCmk) { 243 if ((result = obj_rsakey_get_msa_approval(hKey, &blobSize, &blob))) 244 goto done; 245 memcpy(msaApproval.digest, blob, sizeof(msaApproval.digest)); 246 free_tspi(tspContext, blob); 247 248 if ((result = obj_rsakey_get_msa_digest(hKey, &blobSize, &blob))) 249 goto done; 250 memcpy(msaDigest.digest, blob, sizeof(msaDigest.digest)); 251 free_tspi(tspContext, blob); 252 253 ordinal = TPM_ORD_CMK_CreateKey; 254 } 255 #endif 256 257 if ((result = authsess_xsap_init(tspContext, hWrappingKey, hKey, TSS_AUTH_POLICY_REQUIRED, 258 ordinal, TPM_ET_KEYHANDLE, &xsap))) 259 return result; 260 261 /* Setup the Hash Data for the HMAC */ 262 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 263 result |= Trspi_Hash_UINT32(&hashCtx, ordinal); 264 #ifdef TSS_BUILD_CMK 265 if (isCmk) { 266 result |= Trspi_Hash_ENCAUTH(&hashCtx, xsap->encAuthUse.authdata); 267 result |= Trspi_HashUpdate(&hashCtx, keySize, keyBlob); 268 result |= Trspi_Hash_HMAC(&hashCtx, msaApproval.digest); 269 result |= Trspi_Hash_DIGEST(&hashCtx, msaDigest.digest); 270 } else { 271 #endif 272 result |= Trspi_Hash_DIGEST(&hashCtx, xsap->encAuthUse.authdata); 273 result |= Trspi_Hash_DIGEST(&hashCtx, xsap->encAuthMig.authdata); 274 result |= Trspi_HashUpdate(&hashCtx, keySize, keyBlob); 275 #ifdef TSS_BUILD_CMK 276 } 277 #endif 278 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 279 goto done; 280 281 if ((result = authsess_xsap_hmac(xsap, &digest))) 282 goto done; 283 284 /* Now call the function */ 285 #ifdef TSS_BUILD_CMK 286 if (isCmk) { 287 if ((newKey = malloc(keySize)) == NULL) { 288 LogError("malloc of %u bytes failed.", keySize); 289 result = TSPERR(TSS_E_OUTOFMEMORY); 290 goto done; 291 } 292 memcpy(newKey, keyBlob, keySize); 293 newKeySize = keySize; 294 295 if ((result = RPC_CMK_CreateKey(tspContext, parentTCSKeyHandle, 296 (TPM_ENCAUTH *)&xsap->encAuthUse, 297 &msaApproval, &msaDigest, &newKeySize, &newKey, 298 xsap->pAuth))) 299 goto done; 300 } else { 301 #endif 302 if ((result = TCS_API(tspContext)->CreateWrapKey(tspContext, parentTCSKeyHandle, 303 (TPM_ENCAUTH *)&xsap->encAuthUse, 304 (TPM_ENCAUTH *)&xsap->encAuthMig, 305 keySize, keyBlob, &newKeySize, 306 &newKey, xsap->pAuth))) 307 goto done; 308 #ifdef TSS_BUILD_CMK 309 } 310 #endif 311 312 /* Validate the Authorization before using the new key */ 313 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 314 result |= Trspi_Hash_UINT32(&hashCtx, result); 315 result |= Trspi_Hash_UINT32(&hashCtx, ordinal); 316 result |= Trspi_HashUpdate(&hashCtx, newKeySize, newKey); 317 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 318 goto done; 319 320 if (authsess_xsap_verify(xsap, &digest)) { 321 result = TSPERR(TSS_E_TSP_AUTHFAIL); 322 goto done; 323 } 324 325 /* Push the new key into the existing object */ 326 result = obj_rsakey_set_tcpakey(hKey, newKeySize, newKey); 327 328 done: 329 authsess_free(xsap); 330 free_tspi(tspContext, keyBlob); 331 free(newKey); 332 333 return result; 334 } 335 336 TSS_RESULT 337 Tspi_Key_WrapKey(TSS_HKEY hKey, /* in */ 338 TSS_HKEY hWrappingKey, /* in */ 339 TSS_HPCRS hPcrComposite) /* in, may be NULL */ 340 { 341 TSS_HPOLICY hUsePolicy, hMigPolicy; 342 TCPA_SECRET usage, migration; 343 TSS_RESULT result; 344 BYTE *keyPrivBlob = NULL, *wrappingPubKey = NULL, *keyBlob = NULL; 345 UINT32 keyPrivBlobLen, wrappingPubKeyLen, keyBlobLen; 346 BYTE newPrivKey[214]; /* its not magic, see TPM 1.1b spec p.71 */ 347 BYTE encPrivKey[256]; 348 UINT32 newPrivKeyLen = 214, encPrivKeyLen = 256; 349 UINT64 offset; 350 TSS_KEY keyContainer; 351 TCPA_DIGEST digest; 352 TSS_HCONTEXT tspContext; 353 Trspi_HashCtx hashCtx; 354 355 if ((result = obj_rsakey_get_tsp_context(hKey, &tspContext))) 356 return result; 357 358 if (hPcrComposite) { 359 if ((result = obj_rsakey_set_pcr_data(hKey, hPcrComposite))) 360 return result; 361 } 362 363 /* get the key to be wrapped's private key */ 364 if ((result = obj_rsakey_get_priv_blob(hKey, &keyPrivBlobLen, &keyPrivBlob))) 365 goto done; 366 367 /* get the key to be wrapped's blob */ 368 if ((result = obj_rsakey_get_blob(hKey, &keyBlobLen, &keyBlob))) 369 goto done; 370 371 /* get the wrapping key's public key */ 372 if ((result = obj_rsakey_get_modulus(hWrappingKey, &wrappingPubKeyLen, &wrappingPubKey))) 373 goto done; 374 375 /* get the key to be wrapped's usage policy */ 376 if ((result = obj_rsakey_get_policy(hKey, TSS_POLICY_USAGE, &hUsePolicy, NULL))) 377 goto done; 378 379 if ((result = obj_rsakey_get_policy(hKey, TSS_POLICY_MIGRATION, &hMigPolicy, NULL))) 380 goto done; 381 382 if ((result = obj_policy_get_secret(hUsePolicy, TR_SECRET_CTX_NEW, &usage))) 383 goto done; 384 385 if ((result = obj_policy_get_secret(hMigPolicy, TR_SECRET_CTX_NEW, &migration))) 386 goto done; 387 388 memset(&keyContainer, 0, sizeof(TSS_KEY)); 389 390 /* unload the key to be wrapped's blob */ 391 offset = 0; 392 if ((result = UnloadBlob_TSS_KEY(&offset, keyBlob, &keyContainer))) 393 return result; 394 395 /* load the key's attributes into an object and get its hash value */ 396 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 397 result |= Hash_TSS_PRIVKEY_DIGEST(&hashCtx, &keyContainer); 398 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 399 return result; 400 401 free_key_refs(&keyContainer); 402 403 /* create the plaintext private key blob */ 404 offset = 0; 405 Trspi_LoadBlob_BYTE(&offset, TCPA_PT_ASYM, newPrivKey); 406 Trspi_LoadBlob(&offset, 20, newPrivKey, usage.authdata); 407 Trspi_LoadBlob(&offset, 20, newPrivKey, migration.authdata); 408 Trspi_LoadBlob(&offset, 20, newPrivKey, digest.digest); 409 Trspi_LoadBlob_UINT32(&offset, keyPrivBlobLen, newPrivKey); 410 Trspi_LoadBlob(&offset, keyPrivBlobLen, newPrivKey, keyPrivBlob); 411 newPrivKeyLen = offset; 412 413 /* encrypt the private key blob */ 414 if ((result = Trspi_RSA_Encrypt(newPrivKey, newPrivKeyLen, encPrivKey, 415 &encPrivKeyLen, wrappingPubKey, 416 wrappingPubKeyLen))) 417 goto done; 418 419 /* set the new encrypted private key in the wrapped key object */ 420 if ((result = obj_rsakey_set_privkey(hKey, FALSE, encPrivKeyLen, encPrivKey))) 421 goto done; 422 423 done: 424 free_tspi(tspContext, keyPrivBlob); 425 free_tspi(tspContext, keyBlob); 426 free_tspi(tspContext, wrappingPubKey); 427 return result; 428 } 429 430 TSS_RESULT 431 Tspi_Context_LoadKeyByBlob(TSS_HCONTEXT tspContext, /* in */ 432 TSS_HKEY hUnwrappingKey, /* in */ 433 UINT32 ulBlobLength, /* in */ 434 BYTE * rgbBlobData, /* in */ 435 TSS_HKEY * phKey) /* out */ 436 { 437 TPM_AUTH auth; 438 UINT64 offset; 439 TCPA_DIGEST digest; 440 TSS_RESULT result; 441 UINT32 keyslot; 442 TSS_HPOLICY hPolicy; 443 TCS_KEY_HANDLE tcsParentHandle, myTCSKeyHandle; 444 TSS_KEY keyContainer; 445 TSS_BOOL useAuth; 446 TPM_AUTH *pAuth; 447 TSS_FLAG initFlags; 448 UINT16 realKeyBlobSize; 449 TCPA_KEY_USAGE keyUsage; 450 UINT32 pubLen; 451 Trspi_HashCtx hashCtx; 452 TPM_COMMAND_CODE ordinal; 453 454 if (phKey == NULL || rgbBlobData == NULL ) 455 return TSPERR(TSS_E_BAD_PARAMETER); 456 457 if (!obj_is_rsakey(hUnwrappingKey)) 458 return TSPERR(TSS_E_INVALID_HANDLE); 459 460 if ((result = obj_context_get_loadkey_ordinal(tspContext, &ordinal))) 461 return result; 462 463 if ((result = obj_rsakey_get_tcs_handle(hUnwrappingKey, &tcsParentHandle))) 464 return result; 465 466 offset = 0; 467 if ((result = UnloadBlob_TSS_KEY(&offset, rgbBlobData, &keyContainer))) 468 return result; 469 realKeyBlobSize = offset; 470 pubLen = keyContainer.pubKey.keyLength; 471 keyUsage = keyContainer.keyUsage; 472 /* free these now, since they're not used below */ 473 free_key_refs(&keyContainer); 474 475 if ((result = obj_rsakey_get_policy(hUnwrappingKey, TSS_POLICY_USAGE, &hPolicy, &useAuth))) 476 return result; 477 478 if (useAuth) { 479 /* Create the Authorization */ 480 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 481 result |= Trspi_Hash_UINT32(&hashCtx, ordinal); 482 result |= Trspi_HashUpdate(&hashCtx, ulBlobLength, rgbBlobData); 483 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 484 return result; 485 486 if ((result = secret_PerformAuth_OIAP(hUnwrappingKey, ordinal, hPolicy, FALSE, 487 &digest, &auth))) 488 return result; 489 490 pAuth = &auth; 491 } else { 492 pAuth = NULL; 493 } 494 495 if ((result = TCS_API(tspContext)->LoadKeyByBlob(tspContext, tcsParentHandle, ulBlobLength, 496 rgbBlobData, pAuth, &myTCSKeyHandle, 497 &keyslot))) 498 return result; 499 500 if (useAuth) { 501 /* --- Validate return auth */ 502 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 503 result |= Trspi_Hash_UINT32(&hashCtx, result); 504 result |= Trspi_Hash_UINT32(&hashCtx, ordinal); 505 if (ordinal == TPM_ORD_LoadKey) 506 result |= Trspi_Hash_UINT32(&hashCtx, keyslot); 507 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 508 return result; 509 510 if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &auth))) 511 return result; 512 } 513 514 /* --- Create a new Object */ 515 initFlags = 0; 516 if (pubLen == 0x100) 517 initFlags |= TSS_KEY_SIZE_2048; 518 else if (pubLen == 0x80) 519 initFlags |= TSS_KEY_SIZE_1024; 520 else if (pubLen == 0x40) 521 initFlags |= TSS_KEY_SIZE_512; 522 523 /* clear the key type field */ 524 initFlags &= ~TSS_KEY_TYPE_MASK; 525 526 if (keyUsage == TPM_KEY_STORAGE) 527 initFlags |= TSS_KEY_TYPE_STORAGE; 528 else 529 initFlags |= TSS_KEY_TYPE_SIGNING; /* loading the blob 530 will fix this 531 back to what it 532 should be. */ 533 534 if ((result = obj_rsakey_add(tspContext, initFlags, phKey))) { 535 LogDebug("Failed create object"); 536 return TSPERR(TSS_E_INTERNAL_ERROR); 537 } 538 539 if ((result = obj_rsakey_set_tcpakey(*phKey,realKeyBlobSize, rgbBlobData))) { 540 LogDebug("Key loaded but failed to setup the key object" 541 "correctly"); 542 return TSPERR(TSS_E_INTERNAL_ERROR); 543 } 544 545 return obj_rsakey_set_tcs_handle(*phKey, myTCSKeyHandle); 546 } 547 548 TSS_RESULT 549 Tspi_TPM_OwnerGetSRKPubKey(TSS_HTPM hTPM, /* in */ 550 UINT32 * pulPuKeyLength, /* out */ 551 BYTE ** prgbPubKey) /* out */ 552 { 553 TSS_RESULT result; 554 TSS_HPOLICY hPolicy; 555 TSS_HCONTEXT tspContext; 556 TCS_KEY_HANDLE hKey; 557 TPM_AUTH auth; 558 Trspi_HashCtx hashCtx; 559 TCPA_DIGEST digest; 560 561 if (pulPuKeyLength == NULL || prgbPubKey == NULL) 562 return TSPERR(TSS_E_BAD_PARAMETER); 563 564 if ((result = obj_tpm_get_tsp_context(hTPM, &tspContext))) 565 return result; 566 567 hKey = TPM_KEYHND_SRK; 568 569 if ((result = obj_tpm_get_policy(hTPM, TSS_POLICY_USAGE, &hPolicy))) 570 return result; 571 572 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 573 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_OwnerReadInternalPub); 574 result |= Trspi_Hash_UINT32(&hashCtx, hKey); 575 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 576 return result; 577 578 if ((result = secret_PerformAuth_OIAP(hTPM, TPM_ORD_OwnerReadInternalPub, 579 hPolicy, FALSE, &digest, &auth))) 580 return result; 581 582 if ((result = TCS_API(tspContext)->OwnerReadInternalPub(tspContext, hKey, &auth, 583 pulPuKeyLength, prgbPubKey))) 584 return result; 585 586 /* Validate return auth */ 587 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 588 result |= Trspi_Hash_UINT32(&hashCtx, TSS_SUCCESS); 589 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_OwnerReadInternalPub); 590 result |= Trspi_HashUpdate(&hashCtx, *pulPuKeyLength, *prgbPubKey); 591 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 592 goto error; 593 594 if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &auth))) 595 goto error; 596 597 /* Call a special SRK-seeking command to transparently add the public data to the object */ 598 if ((result = obj_rsakey_set_srk_pubkey(*prgbPubKey))) { 599 LogError("Error setting SRK public data, SRK key object may not exist"); 600 } 601 602 if ((result = __tspi_add_mem_entry(tspContext, *prgbPubKey))) 603 goto error; 604 605 return result; 606 607 error: 608 free(*prgbPubKey); 609 pulPuKeyLength = 0; 610 return result; 611 } 612 613 /* TSS 1.2-only interfaces */ 614 #ifdef TSS_BUILD_TSS12 615 TSS_RESULT 616 Tspi_TPM_KeyControlOwner(TSS_HTPM hTPM, /* in */ 617 TSS_HKEY hTssKey, /* in */ 618 UINT32 attribName, /* in */ 619 TSS_BOOL attribValue, /* in */ 620 TSS_UUID* pUuidData) /* out */ 621 { 622 TSS_RESULT result; 623 TSS_HPOLICY hPolicy; 624 TSS_HCONTEXT tspContext; 625 TCS_KEY_HANDLE hTcsKey; 626 BYTE *pubKey = NULL; 627 UINT32 pubKeyLen; 628 TPM_KEY_CONTROL tpmAttribName; 629 Trspi_HashCtx hashCtx; 630 TCPA_DIGEST digest; 631 TPM_AUTH ownerAuth; 632 633 LogDebugFn("Enter"); 634 635 /* Check valid TPM context, get TSP context */ 636 if ((result = obj_tpm_get_tsp_context(hTPM, &tspContext))) 637 return result; 638 639 /* Get Tcs KeyHandle */ 640 if ((result = obj_rsakey_get_tcs_handle(hTssKey, &hTcsKey))) 641 return result; 642 643 /* Validate/convert attribName */ 644 switch (attribName) { 645 case TSS_TSPATTRIB_KEYCONTROL_OWNEREVICT: 646 tpmAttribName = TPM_KEY_CONTROL_OWNER_EVICT; 647 break; 648 default: 649 return TSPERR(TSS_E_BAD_PARAMETER); 650 } 651 652 /* Begin Auth - get TPM Policy Handler */ 653 if ((result = obj_tpm_get_policy(hTPM, TSS_POLICY_USAGE, &hPolicy))) 654 return result; 655 656 /* Get associated pubKey */ 657 if ((result = obj_rsakey_get_pub_blob(hTssKey, &pubKeyLen, &pubKey))) 658 return result; 659 660 /* Create hash digest */ 661 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 662 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_KeyControlOwner); 663 LogDebugData(pubKeyLen, pubKey); 664 result |= Trspi_HashUpdate(&hashCtx, pubKeyLen, pubKey); 665 result |= Trspi_Hash_UINT32(&hashCtx, tpmAttribName); 666 result |= Trspi_Hash_BOOL(&hashCtx, attribValue); 667 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) { 668 free_tspi(tspContext, pubKey); 669 return result; 670 } 671 672 if ((result = secret_PerformAuth_OIAP(hTPM, TPM_ORD_KeyControlOwner, hPolicy, FALSE, 673 &digest, &ownerAuth))) { 674 free_tspi(tspContext, pubKey); 675 return result; 676 } 677 678 if ((result = RPC_KeyControlOwner(tspContext, hTcsKey, pubKeyLen, pubKey, tpmAttribName, 679 attribValue, &ownerAuth, pUuidData))) { 680 free_tspi(tspContext, pubKey); 681 return result; 682 } 683 684 /* Validate return auth */ 685 result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); 686 result |= Trspi_Hash_UINT32(&hashCtx, TSS_SUCCESS); 687 result |= Trspi_Hash_UINT32(&hashCtx, TPM_ORD_KeyControlOwner); 688 if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) 689 return result; 690 691 if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &ownerAuth))) 692 return result; 693 694 /* change hKey internal flag, according to attrib[Name|Value] */ 695 switch (attribName) { 696 case TSS_TSPATTRIB_KEYCONTROL_OWNEREVICT: 697 result = obj_rsakey_set_ownerevict(hTssKey, attribValue); 698 break; 699 default: 700 /* NOT-REACHED */ 701 result = TSPERR(TSS_E_BAD_PARAMETER); 702 } 703 704 return result; 705 } 706 #endif 707