TSS_RESULT Tspi_Key_LoadKey(TSS_HKEY hKey, /* in */ TSS_HKEY hUnwrappingKey) /* in */ { TPM_AUTH auth; TCPA_DIGEST digest; TSS_RESULT result; UINT32 keyslot; TSS_HCONTEXT tspContext; TSS_HPOLICY hPolicy; UINT32 keySize; BYTE *keyBlob; TCS_KEY_HANDLE tcsKey, tcsParentHandle; TSS_BOOL usesAuth; TPM_AUTH *pAuth; Trspi_HashCtx hashCtx; TPM_COMMAND_CODE ordinal; if (!obj_is_rsakey(hUnwrappingKey)) return TSPERR(TSS_E_INVALID_HANDLE); if ((result = obj_rsakey_get_tsp_context(hKey, &tspContext))) return result; if ((result = obj_context_get_loadkey_ordinal(tspContext, &ordinal))) return result; if ((result = obj_rsakey_get_blob(hKey, &keySize, &keyBlob))) return result; if ((result = obj_rsakey_get_tcs_handle(hUnwrappingKey, &tcsParentHandle))) return result; if ((result = obj_rsakey_get_policy(hUnwrappingKey, TSS_POLICY_USAGE, &hPolicy, &usesAuth))) { free_tspi(tspContext, keyBlob); return result; } if (usesAuth) { result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); result |= Trspi_Hash_UINT32(&hashCtx, ordinal); result |= Trspi_HashUpdate(&hashCtx, keySize, keyBlob); if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) { free_tspi(tspContext, keyBlob); return result; } if ((result = secret_PerformAuth_OIAP(hUnwrappingKey, ordinal, hPolicy, FALSE, &digest, &auth))) { free_tspi(tspContext, keyBlob); return result; } pAuth = &auth; } else { pAuth = NULL; } if ((result = TCS_API(tspContext)->LoadKeyByBlob(tspContext, tcsParentHandle, keySize, keyBlob, pAuth, &tcsKey, &keyslot))) { free_tspi(tspContext, keyBlob); return result; } free_tspi(tspContext, keyBlob); if (usesAuth) { result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); result |= Trspi_Hash_UINT32(&hashCtx, result); result |= Trspi_Hash_UINT32(&hashCtx, ordinal); if (ordinal == TPM_ORD_LoadKey) result |= Trspi_Hash_UINT32(&hashCtx, keyslot); if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) return result; if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &auth))) return result; } return obj_rsakey_set_tcs_handle(hKey, tcsKey); }
TSS_RESULT Tspi_Context_LoadKeyByBlob(TSS_HCONTEXT tspContext, /* in */ TSS_HKEY hUnwrappingKey, /* in */ UINT32 ulBlobLength, /* in */ BYTE * rgbBlobData, /* in */ TSS_HKEY * phKey) /* out */ { TPM_AUTH auth; UINT64 offset; TCPA_DIGEST digest; TSS_RESULT result; UINT32 keyslot; TSS_HPOLICY hPolicy; TCS_KEY_HANDLE tcsParentHandle, myTCSKeyHandle; TSS_KEY keyContainer; TSS_BOOL useAuth; TPM_AUTH *pAuth; TSS_FLAG initFlags; UINT16 realKeyBlobSize; TCPA_KEY_USAGE keyUsage; UINT32 pubLen; Trspi_HashCtx hashCtx; TPM_COMMAND_CODE ordinal; if (phKey == NULL || rgbBlobData == NULL ) return TSPERR(TSS_E_BAD_PARAMETER); if (!obj_is_rsakey(hUnwrappingKey)) return TSPERR(TSS_E_INVALID_HANDLE); if ((result = obj_context_get_loadkey_ordinal(tspContext, &ordinal))) return result; if ((result = obj_rsakey_get_tcs_handle(hUnwrappingKey, &tcsParentHandle))) return result; offset = 0; if ((result = UnloadBlob_TSS_KEY(&offset, rgbBlobData, &keyContainer))) return result; realKeyBlobSize = offset; pubLen = keyContainer.pubKey.keyLength; keyUsage = keyContainer.keyUsage; /* free these now, since they're not used below */ free_key_refs(&keyContainer); if ((result = obj_rsakey_get_policy(hUnwrappingKey, TSS_POLICY_USAGE, &hPolicy, &useAuth))) return result; if (useAuth) { /* Create the Authorization */ result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); result |= Trspi_Hash_UINT32(&hashCtx, ordinal); result |= Trspi_HashUpdate(&hashCtx, ulBlobLength, rgbBlobData); if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) return result; if ((result = secret_PerformAuth_OIAP(hUnwrappingKey, ordinal, hPolicy, FALSE, &digest, &auth))) return result; pAuth = &auth; } else { pAuth = NULL; } if ((result = TCS_API(tspContext)->LoadKeyByBlob(tspContext, tcsParentHandle, ulBlobLength, rgbBlobData, pAuth, &myTCSKeyHandle, &keyslot))) return result; if (useAuth) { /* --- Validate return auth */ result = Trspi_HashInit(&hashCtx, TSS_HASH_SHA1); result |= Trspi_Hash_UINT32(&hashCtx, result); result |= Trspi_Hash_UINT32(&hashCtx, ordinal); if (ordinal == TPM_ORD_LoadKey) result |= Trspi_Hash_UINT32(&hashCtx, keyslot); if ((result |= Trspi_HashFinal(&hashCtx, digest.digest))) return result; if ((result = obj_policy_validate_auth_oiap(hPolicy, &digest, &auth))) return result; } /* --- Create a new Object */ initFlags = 0; if (pubLen == 0x100) initFlags |= TSS_KEY_SIZE_2048; else if (pubLen == 0x80) initFlags |= TSS_KEY_SIZE_1024; else if (pubLen == 0x40) initFlags |= TSS_KEY_SIZE_512; /* clear the key type field */ initFlags &= ~TSS_KEY_TYPE_MASK; if (keyUsage == TPM_KEY_STORAGE) initFlags |= TSS_KEY_TYPE_STORAGE; else initFlags |= TSS_KEY_TYPE_SIGNING; /* loading the blob will fix this back to what it should be. */ if ((result = obj_rsakey_add(tspContext, initFlags, phKey))) { LogDebug("Failed create object"); return TSPERR(TSS_E_INTERNAL_ERROR); } if ((result = obj_rsakey_set_tcpakey(*phKey,realKeyBlobSize, rgbBlobData))) { LogDebug("Key loaded but failed to setup the key object" "correctly"); return TSPERR(TSS_E_INTERNAL_ERROR); } return obj_rsakey_set_tcs_handle(*phKey, myTCSKeyHandle); }
TSS_RESULT Tspi_Context_LoadKeyByUUID(TSS_HCONTEXT tspContext, /* in */ TSS_FLAG persistentStorageType, /* in */ TSS_UUID uuidData, /* in */ TSS_HKEY * phKey) /* out */ { TSS_RESULT result; TSS_UUID parentUUID; UINT32 keyBlobSize, parentPSType; BYTE *keyBlob = NULL; TCS_KEY_HANDLE tcsKeyHandle; TSS_HKEY parentTspHandle; TCS_LOADKEY_INFO info; UINT32 ulPubKeyLength; BYTE *rgbPubKey; TPM_COMMAND_CODE ordinal; if (phKey == NULL) return TSPERR(TSS_E_BAD_PARAMETER); if ((!obj_is_context(tspContext))) return TSPERR(TSS_E_INVALID_HANDLE); if ((result = obj_context_get_loadkey_ordinal(tspContext, &ordinal))) return result; /* This key is in the System Persistant storage */ if (persistentStorageType == TSS_PS_TYPE_SYSTEM) { #if 1 __tspi_memset(&info, 0, sizeof(TCS_LOADKEY_INFO)); result = RPC_LoadKeyByUUID(tspContext, uuidData, &info, &tcsKeyHandle); if (TSS_ERROR_CODE(result) == TCS_E_KM_LOADFAILED) { TSS_HKEY keyHandle; TSS_HPOLICY hPolicy; /* load failed, due to some key in the chain needing auth * which doesn't yet exist at the TCS level. However, the * auth may already be set in policies at the TSP level. * To find out, get the key handle of the key requiring * auth. First, look at the list of keys in memory. */ if ((obj_rsakey_get_by_uuid(&info.parentKeyUUID, &keyHandle))) { /* If that failed, look on disk, in User PS. */ if (ps_get_key_by_uuid(tspContext, &info.parentKeyUUID, &keyHandle)) return result; } if (obj_rsakey_get_policy(keyHandle, TSS_POLICY_USAGE, &hPolicy, NULL)) return result; if (secret_PerformAuth_OIAP(keyHandle, ordinal, hPolicy, FALSE, &info.paramDigest, &info.authData)) return result; if ((result = RPC_LoadKeyByUUID(tspContext, uuidData, &info, &tcsKeyHandle))) return result; } else if (result) return result; /*check if provided UUID has an owner evict key UUID prefix */ if (!memcmp(&uuidData, &owner_evict_uuid, sizeof(TSS_UUID)-1)) { if ((result = obj_rsakey_add(tspContext, TSS_RSAKEY_FLAG_OWNEREVICT, phKey))) return result; if ((result = obj_rsakey_set_tcs_handle(*phKey, tcsKeyHandle))) return result; //The cached public key portion of the owner evict key is used //further by TPM_KEY_CONTROLOWNER command for sanity check if ((result = Tspi_Key_GetPubKey(*phKey, &ulPubKeyLength, &rgbPubKey))) return result; result = obj_rsakey_set_pubkey(*phKey, FALSE, rgbPubKey); free_tspi(tspContext,rgbPubKey); if (result != TSS_SUCCESS) return result; } else { if ((result = RPC_GetRegisteredKeyBlob(tspContext, uuidData, &keyBlobSize, &keyBlob))) return result; if ((result = obj_rsakey_add_by_key(tspContext, &uuidData, keyBlob, TSS_OBJ_FLAG_SYSTEM_PS, phKey))) { free (keyBlob); return result; } result = obj_rsakey_set_tcs_handle(*phKey, tcsKeyHandle); free (keyBlob); } #else if ((result = load_from_system_ps(tspContext, &uuidData, phKey))) return result; #endif } else if (persistentStorageType == TSS_PS_TYPE_USER) { if ((result = ps_get_parent_uuid_by_uuid(&uuidData, &parentUUID))) return result; /* If the parent is not in memory, recursively call ourselves on it */ if (obj_rsakey_get_by_uuid(&parentUUID, &parentTspHandle) != TSS_SUCCESS) { if ((result = ps_get_parent_ps_type_by_uuid(&uuidData, &parentPSType))) return result; if ((result = Tspi_Context_LoadKeyByUUID(tspContext, parentPSType, parentUUID, &parentTspHandle))) return result; } if ((result = ps_get_key_by_uuid(tspContext, &uuidData, phKey))) return result; /* The parent is loaded and we have the parent key handle, so call the TCS to * actually load the child. */ return Tspi_Key_LoadKey(*phKey, parentTspHandle); } else { return TSPERR(TSS_E_BAD_PARAMETER); } return TSS_SUCCESS; }