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