For the most part, the move from 1.1 to 1.2 will be seamless. A lot of work was done in the 1.2 specification to make sure that programs written for the 1.1 stack would continue to work for the 1.2 stack. There is really only one exception. This has to do with the reading of the SRK public key. This now can be set to be possible only with the owner key, and by default this setting is selected on many implementations. Other changes to the TPM specification due to security holes were discovered early enough that the older broken functions never made it into the 1.1 TSS specification.
The biggest change going from 1.1 to 1.2 is the addition of a number of features to the TPM specification that are exposed in the 1.2 TSS specification. These features include a Certified Migratable Key (CMK), delegation, Direct Anonymous Authentication (DAA), locality, PCRlong, NVRAM, auditing functions, monotonic counter, tick counter, a SOAP interface for remote commands sent to the TCS, transport sessions, and some new administrative commands.
The CMK is a kind of key that is halfway between a non-migratable key and a migratable key. Migratable keys can be generated anywhere and, if they are migrated to an insecure key or from an insecure location, can be inherently insecure. The TPM cannot tell. Non-migratable keys are generated inside the TPM and never leave it, so they are inherently secure, but are not transportable between TPMs.
CMKs, on the other hand, are generated inside a TPM, but at the time they are generated, the creator has to pick a Migration Authority (MA) or a Migration Selection Authority (MSA), which will have the authority to migrate the key. All the normal controls on migration of a key continue to exist with a CMA—the owner of the chip must authorize MSAs and MAs with a “ticket,” and the owner of the created key has to decide to migrate a key before the key is migrated. If an MA is selected at the time of key creation, that MA cannot ever be changed. If an MSA is selected at the time of key creation, that MSA cannot ever be changed, but the MSA can change the MAs that are allowed. Why do all this? A CMK can be certified by a TPM as being a CMK, and that certificate will list the MSA (or MAs) that are allowed to migrate the key. Thus, CMKs can both be migrated and also be considered secure (if you trust the MSA and MAs allowed to migrate the key).
Purpose: The CMK command is kind of dangerous in that control for migration is being given away from a user to another entity. As a result, an implied contract is being made at the time a key is created. If the MA or MSA decides later to charge an unreasonable price for the service of migrating a key, the end user has no options. As a result, the Tspi_TPM_CMKSetRestrictionsCommand was implemented. This command, which is one of few that cannot be delegated, allows the owner to decide which types of CMK keys a delegated authority can create on behalf of the owner.
Usage: Tspi_CMKSetRestrictions ( TSS_HTPM hTPM
TSS_CMK_DELEGATE CmkDelegate
)
Here hTPM is the handle of the TPM, and CmkDelegate is a bitmask, with each bit representing a type of key (storage, signing, and so on) that a delegated entity will be authorized to create on behalf of the owner.
Returns: TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used to allow delegated software to handle the details of using CMKs for backing up keys or for creating CMK keys in general. In so doing, the owner is allowing the delegated entity to create an implied contract with an MA or MSA.
Tspi_TPM_CMKApproveMA
Tspi_TPM_CMKCreateTicket
Purpose: The first step after creating a CMK is probably to create the CMK blob. This is an encrypted set of data that can be used by the MA or MSA to migrate the key to a new TPM.
Tspi_CMKCreateBlob ( TSS_HKEY hKeyToMigrate
TSS_HKEY hParentKey
TSS_HMIGDATA hMigrationData
UINT32* pRandomLength
BYTE** pRandom
)
Here hKeyToMigrate is the handle of the key being migrated, hParentKey is the parent of the key being migrated, and hMigrationData is the handle to an object in which the data is sent to the TPM and the encrypted blob is put. pRandomLength is a pointer to where the length of the random data (used to XOR the inside of the blob) is stored, and pRandom is a pointer to where the array of random bytes is stored.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used to allow delegated software to handle the details of using CMKs for backing up keys or for creating CMK keys in general. In so doing, the owner is allowing the delegated entity to create an implied contract with an MA or MSA.
Tspi_TPM_CMKApproveMA
Tspi_TPM_CMKCreateTicket
Purpose: This command just re-wraps migration data so that a TPM can be used by an MA in migrating CMKs.
Usage:
Tspi_Key_MigrateKey ( TSS_HKey hMaKey
TSS_HKey hPublicKey
TSS_HMIGDATAhMigData
)
Here hMaKey is the handle of the Migration Authority Private Key, hPublicKey is the public key to which the key is migrating, and hMigData contains the encrypted key data (doubly encrypted, once with the MA public key and once internally with the random number).
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the passed parameters was wrong.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used by an MA to perform migration.
Purpose: In a way analogous to migratable keys, the owner of the TPM has to create a ticket authorizing the use of an MA before it can be used to create a CMK tied to that MA.
Usage:
Tspi_CMKSetRestrictions ( TSS_HTPM hTPM
TSS_HMIGDATA hMaAuthData
)
Here hTPM is the handle of the TPM, and hMaAuthData contains the information about the MA in question.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command must be used by the owner before a CMK is created. It creates a ticket necessary to authorize the target MA.
Purpose: This command is used to prove to a TPM that a signature over a digest was correctly created by a TPM.
Usage:
Tspi_CMKCreateTicket ( TSS_HTPM hTPM
TSS_HKEY hVerifyKey
TSS_HMIGDATA hSigData
)
Here hTPM is the handle of the TPM, and hVerifyKey contains the public key used to verify the signature contained in hSigData.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used to verify a signature.
Purpose: This command is the one used to install a migrated key into a new TPM.
Tspi_CMKConvertMigration ( TSS_HKEY hKeyToMigrate
TSS_HKEY hParentKey
TSS_HMIGDATA hMigrationData
UINT32 ulRandomLength
BYTE* rbgRandom
)
Here hKey is the handle of the key being migrated, hParentKey is the key it is wrapped with, rgbRandom is the random data needed to do the internal decryption, and hMigrationData is a handle to the structure in which the migration blob is input and the newly created key blob is returned. In order to be used, the keyblob has to be loaded with a normal LoadKey operation.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is only used after a data is given to the TSS from an MA with a particular parent key in mind. This data is then sent to the TPM, the random number input, and the TPM decrypts it externally with the parent private key and internally with the random number; the TPM then wraps the result with the parent public key and returns it in the structure that hMigrationData refers to.
In the TSS 1.1 specification, some keys and functions required knowledge of authorization data. In order to delegate use of a function or key, it was necessary to give that authorization data away. Once given away, it became difficult to remove the authorization to use those functions or keys. Authorization data could be changed, of course, but the authorization data itself was the gate to changing that data, so more authority was being given with the authorization data than just use authorization. This problem was particularly acute in the case of keys, because the blobs that contained the authorization data were stored outside the TPM, making it impossible for the TPM to be sure that all copies of the authorization data were changed. In this case, it wasn’t possible to be entirely sure that even changing authorization data removed the ability for the delegatee to use the key. (The owner could migrate all non-suspect keys to a second key, change the SRK, and then migrate all non-suspect keys back to the new SRK, but this requires discarding all non-migratable keys, and is not ideal.)
Although convoluted means existed to use the 1.1 TPM to accomplish most of what the delegation function in 1.2 provides, Delegation is much more straightforward. Basically, it allows the TPM to keep track of a secondary authentication that can be used to provide authorization to use either a key or an owner-authorized function. This secondary authorization is “delegated” to either trusted software or a trusted user to provide them authorization to use a function or key. This authorization can also be revoked by the person who knows the primary authorization.
The TPM uses two internal tables to keep track of what functions/keys have been delegated, and what users have been associated with a group of delegations. The two tables are Delegation Tables and Family Tables. The Delegation Table is the easiest to understand. It contains a list of ordinals that are to be delegated, or a key that is being delegated, and the process that can use those ordinals (identified by PCR values), a new AuthData that can also be used (in addition to the owner auth) to authorize those ordinals, a delegation label, a family ID (to associate it with the user), and a verification count (used to invalidate a delegation row).
Before we can address what is in a Family Table, we need to describe what a family is. It is just a collection of delegated rows associated with a particular delegatee. It is collected so that there is a way to manage the delegation of a group of commands and keys without having to touch each one individually. So for example, I may delegate owner-authorized commands or keys to a piece of trusted software. A year later, my trusted software is found to have a security hole. I upgrade the software. I now want to delegate those same commands to the upgraded software—and delete the ability of my old software to use those commands. Or I may want to modify which commands my software has access to due to some new regulation or law that has been passed.
Another example is a group of keys that I delegate to my secretary. A year later, my secretary is changed. I now want to delete all delegations of keys to my old secretary, and re-delegate all those keys to my new secretary. By grouping the keys this way, it makes it easy to administrate them.
Another less-obvious property of delegation is that it allows you to associate particular PCR values to commands that used to be associated only to an owner—and it provides a means to associate the use of a migratable key with PCR values.
Delegated rows, like keys, can be stored either inside or outside the TPM. Enough room is required in a TPM to store at least two of them inside the TPM, for storage constrained situations. A new command has been created specifically to store (and evict) a row in non-volatile space.
In order to create a delegated row, one first creates a family row, so that one will have a familyID necessary for the creation of the delegated row. Delegated rows are similar to normal users in a Linux system, and the owner of the TPM or owner of a key are like super-users—able to add or delete users to a command or key, under limited circumstances.
A typical life cycle of delegation use would be as follows:
1. Create a family row (user).
AddFamily
GetFamily
2. Create a delegation of TPM owner-authorized commands to the user.
CreateDelegation
3. Create a delegation of keys to the user.
CreateDelegation
4. Cache one or more of those delegations into the TPM.
CacheOwnerDelegation
5. Read out what delegations are stored in the TPM.
ReadTables
6. Invalidate a delegation (by incrementing VerificationCount).
CreateDelegation (with ulFlags = incrementVerification)
7. Reauthorize delegations killed by the invalidation of a particular delegation belonging to same user.
UpdateVerificationCount
8. Invalidate a family (user).
InvalidateFamily
Purpose: This command is used to add a new row to the Family Table inside the TPM.
Usage:
Tspi_CMKCreateTicket ( TSS_HTPM hTPM
BYTE bLabel
TSS_HDELFAMILY* phFamily
)
Here hTPM is the handle of the TPM, and bLabel contains a label to be used by software to determine which family is being referred to. You can consider the bLabel to be the delegated user name, but software has to translate the user name into the correct BYTE. For ease of use, you may want the bLabel to be simply the first byte of the hash of the user_name.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command should be run before you delegate a group of commands or a key to a user, so that you have a user to delegate them to.
Purpose: This command is used to get a handle to a previously created row of the Family Table.
Usage:
Tspi_TPM_Delegate_GetFamily ( TSS_HTPM hTPM
BYTE ulFamilyID
TSS_HDELFAMILY* phFamily
)
Here hTPM is the handle of the TPM, and ulFamilyID contains a label to be used by software to determine which user is being referred to. phFamily returns a pointer to the handle of the family row.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used for management of a group of delegation rows that all belong to the same user.
Purpose: This command is used to invalidate all delegations made to a particular user.
Usage:
Tspi_DelegateInvalidateFamily( TSS_HTPM hTPM
TSS_HDELFAMILY hFamily
)
Here hTPM is the handle of the TPM, and hFamily is the handle of the family member (user or trusted software) that is being invalidated.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: In order to find out the hFamily to use, use the Tspi_TPM_Delegate_GetFamily command.
Purpose: This command is used to create a new delegation made to a particular user or to invalidate all old delegations made to a user (by using IncrementVerification for the ulFlags parameter).
Usage:
Tspi_Delegate_CreateDelegation (TSS_HOBJECT hObject
BYTE bLabel
UINT32 ulFlags
TSS_HPCRS hPcr
TSS_HDELFAMILY hFamily
TSS_HPOLICY hDelegation
)
Here hObject tells the story of what is being delegated. If hObject contains the TPM handle (hTPM) with an owner authorization policy attached, then this will delegate owner authorization. If it contains the handle of a key (hKey) along with a key use authorization policy, then a key is being delegated. bLabel is the BYTE that is used to determine the user to which the owner authorization or key is being delegated. UlFlags is NULL if a new delegation is happening and IncrementVerification if the command is being used to revoke all delegations made to a user. hPcr is a handle to a structure that defines what PCRs with which values are going to being delegated to, hFamily is the handle of the family member (user or trusted software), and hDelegation is an existing policy, in which the delegated authorization is stored.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: In order to use this function, one must first establish at least one family member (user) who is going to be the recipient of the delegation.
Purpose: This command is used to store a particular delegation in NVRAM in the TPM. Each 1.2 TPM has to have room for at least two delegations stored internally (although more are allowed).
Tspi_Delegate_CacheOwnerDelegation (TSS_HTPM hTPM
TSS_HPOLICY hDelegation
UINT32 ulIndex
UINT32 ulFlags
)
Here hTPM of course refers to the TPM in which the delegation is to be stored. HDelegation is the delegation to be stored, ulIndex is the location in which it is to be stored, and ulFlags currently can only have a value of OverwriteExisting.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_NV_AREA_EXIST Index doesn’t exist in this TPM.
TSS_E_INTERNAL_ERROR The command failed.
Context: In order to use this function, one must first establish a delegation and find out how many indices one’s TPM can store. It is also wise to read the Delegation Table and find out if you are about to overwrite an existing delegation.
Purpose: When a delegation is being revoked, an internal counter (called the verification counter) in the TPM is incremented, to make sure that an old delegation stored outside the TPM is no longer allowed to function. However, this means that no delegation outside the TPM can function any longer. The solution is to use this command to update the verification counter for delegation blobs. It needs to be done to all the blobs in a family if any are to survive one of them being deleted.
Usage:
Tspi_Delegate_UpdateVerificationCount ( TSS_HTPM hTPM
TSS_HPOLICY hDelegation
)
Here hTPM is the TPM whose verification count has been incremented, and hDelegation is the delegation that needs to be re-set to the current verification counter of the TPM.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is typically used after a delegation has been revoked, to keep other delegations from the same family authorized.
Purpose: This command is used to check if a delegation is currently active.
Usage:
Tspi_Delegate_VerifyDelegation (
TSS_HPOLICY hDelegation
)
Here hDelegation is an existing policy, and this command checks to see if it is currently active.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: One, of course, has to have created a delegation to use this command.
Purpose: This command is used to find out what delegations (and families) currently are stored on TPM. It does not (of course) reveal any private information of those delegations.
Usage:
Tspi_Delegate_CreateDelegation (
TSS_HCONTEXT hContext
UINT32* pulFamilyTableSize
TSS_KM_KEYINFO** ppFamilyTable
UINT32* pulDelegateTableSize
TSS_KM_KEYINFO** ppDelegateTable
)
Here hContext is the context set up with the TPM, and the ppFamilyTable and ppDelegateTable receive the information from the TPM.
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command can be executed by anyone.
In the original 1.1 TPM, a lot of work was put into designing a system that would allow the owner of a TPM, together with a Certificate Authority (CA), to provide certificates to keys that could be proven to be non-migratable TPM keys, but which did not weaken privacy protections. The successful design incorporated the EK (Endorsement Key). However, for the protocol to work, it was necessary that there be CAs available. No CAs have shown up yet (probably due to a dearth of EK credentials—without which there are no privacy threats), so there was some skepticism voiced in the privacy community about the efficacy of the solution.
The solution to this problem was a new protocol built into the TPM based on research into group signatures. A group signature provides a means for a group of people to all have the ability to sign things as “members of the group” without having a global secret susceptible to a Break Once Run Everywhere (BORE) attack, and without allowing members of the group to tell which one of them signed a particular hash. Nevertheless, in spite of having these properties, if the individual secret used by a particular member of the group is revealed, it is possible to invalidate it without revealing or invalidating the secrets of the other members of the group. It is quite a trick mathematically.
The solution embedded into the TPM 1.2 is known as DAA, or Direct Anonymous Authentication. It provides a means for AIKs to be certified as being a member of the group of TPM AIKs, without requiring each AIK be individually certified by a CA. Instead, a DAA authority, one time, authenticates some TPM secrets as belonging to a TPM that is authentic. This authentication can be done before the TPM is shipped out to its final owner, though it need not be. Authentication in the field can be based on the EK and its certificate.
There are a number of things that should be noted about DAA. It is a very complicated protocol, based on group signatures. There are not, at the time of this writing, any DAA authorities that exist, to provide the DAA certificate necessary to run the protocol. It is only useful in the limited case that a remote end user with no direct access to the TPM wants to verify that it is talking to a genuine TPM, and the owner of the TPM wants to protect all information that might be used to identify him.
In the case of a business that is managing TPMs of systems owned by the business, it is not important to use DAA at all—the EK mechanism is perfectly fine, with the business acting the part of the third-party verifier. It is difficult to imagine how DAA (at least by itself) could provide the means to purchase something anonymously online. After all, money has to travel from the purchaser to the store. And if what is being bought is tangible, it has to travel from the store to the purchaser.
One might imagine that DAA would be used some time in the future to provide some sort of DRM management where a key is stored in the TPM to enable use of software or media, but as we have already pointed out, on a PC, a TPM does not provide ideal help for such things—clearly other special-purpose hardware would be used by such a solution. And if that is being done, there are much easier ways to enforce DRM.
The best scenario we can think of to illustrate the functions of DAA would be in providing a way to do anonymous Internet voting. First, one proves to a DAA authority that one is a member of the group eligible to vote. This amounts to “joining” the group. After this is done, a certificate is given to the owner of the TPM, which enables his TPM to vote. Next one signs one’s vote using the DAA protocol, for each vote that is presented.
Votes are tallied, and though it is clear that no one voted more than once, and only eligible voters voted, no one can tell how anyone voted. If all the votes that were counted are displayed, it is possible for everyone to tell that their own vote was counted as well.
Revocation of a particular voter is difficult, however (unless their TPM has been disassembled and the keys become public on the web), and probably entails every member of the group who remains eligible re-joining the group.
Because these functions are not available in a 1.1 TPM or TSS, the first thing a programmer needs to know before using any of these functions is what level TPM and TSS stack he is talking to. This is done easily using the GetCapability command.
The basic life cycle of a DAA certificate goes like this:
Get a DAA certificate, proving your TPM belongs to the group of TPMs.
• DAA authority: Start the protocol.
• IssueSetup (sets up the DAA authority’s public and private key)—usually done once
• IssueInit (Start the process of providing a certificate)
• TCG application: Check the pub key of the DAA authority; compute the TPM DAA pub key.
• JoinInit
• TCG application: Create messages back to the DAA authority providing information to the certification.
• JoinCreateDaaPubKey
• DAA authority: Issue a credential to the TPM.
• IssueCredential
• TCG application: Finish up the creation of the DAA credential.
• JoinStoreCredential
Use an existing DAA certificate/key to sign a message (for example, a vote).
• TCG application
• Sign a message
• Message recipient
• IssuerKeyVerification
• VerifyInit
• VerifySignature
Revoke a DAA certificate.
• DAA issuer
• RevokeSetup
Purpose: This command is used in the protocol that establishes a DAA Credential.
Usage:
Tspi_TPM_DAA_JoinInit (TSS_HDAA hDAA
TSS_HTPM hTPM
UINT32 daaCounter
TSS_HKEY issuerPk
UINT32 issuerAuthPKsLength
TSS_HKEY* issuerAuthPKs
UINT32 issuerAuthPK
SignaturesLength
BYTE** issuerAuthPKSignatures
UINT32* capitalUprimeLength
BYTE** capitalUprime
TSS_DAA_IDENTITY_ identityProof
PROOF*
TSS_DAA_JOIN_ joinSession
SESSION*
)
Here hDAA is the handle of the DAA object, hTPM is the handle of the PTM, daaCounter is the daaCounter, issuerAuthPK is the public key of the DAA certificate issuer, issuerAuthPKSignatures is the signature of the authorizer, captialUprime is an intermediate variable, identityProof contains the endorsement, platform, and conformance credential, and joinSession contains some session information.
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is used as the first of three commands that are needed to establish a DAA credential for a TPM.
Purpose: This command is used to create a Daa key.
Usage:
Tspi_TPM_DAA_JoinCreateDaaPubKey (
TSS_HDAA hDAA
TSS_HTPM hTPM
UINT32 authenticationChallengeLength
BYTE* authenticationChallenge
UINT32 nonceIssuerLength
BYTE* nonceIssuer
UINT32 attributesPlatformLength
BYTE** attributesPlatform
TSS_DAA_JOIN_SESSION* joinSession
TSS_DAA_CREDENTIAL_ credentialRequest
REQUEST*
)
Here hDAA is the DAA object handle, hTPM is the TPM handle, the authenticationChallenge is the second nonce the issuer sends (encrypted with the EK pub), nonceIssuer is the nonce of the DAA issuer, attributesPlatform are the attributes of the platform requesting a DAA certificate, joinSession is information of the current joining session, and credentialRequest is where the blinded DAA pub key goes for the platform for which the cert is being issued.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is used as the second of the three commands to establish a DAA certificate.
Purpose: The last step in getting a DAA credential.
Usage:
Tspi_TPM_DAA_JoinStoreCredential (
TSS_HDAA hDAA
TSS_HTPM hTPM
TSS_DAA_CRED_ISSUER credIssuer
TSS_DAA_JOIN_SESSION joinSession
TSS_HKEY* hDaaCredential
)
Here hDAA is the handle of the DAA object, hTPM the handle of the TPM, and credIssuer is the credential issued, including its proof of correctness. JoinSession contains session information and hDaaCredential is the handle to the DAA credential.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is the last step in getting a DAA credential. The first are: Tspi_DAA_JoinInit and Tspi_DAA_JoinCreateDaaPubKey.
Purpose: This command is used to sign a message with a DAA key.
Usage:
Tspi_TPM_DAA_Sign (
)
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is the command used to prove to prove ownership of a DAA credential, and which also allows that proof to be joined to a message via a signature. It cannot be used until a credential exists.
Purpose: This command is used to create new delegations made to a particular user.
Usage: Tspi_TPM_DAA_IssuerKeyVerification (
)
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used to verify that a DAA credential of a public key is correct. It is used by the recipient of a DAA_signed message.
Purpose: This command is used by a DAA authority (certificate issuer) to create their public/private key pair, so that they are ready to become a DAA authority. It also creates a proof that the public keys were correctly chosen. It is interesting that this type of signature allows the platform to choose attributes (such as age, address, and marital status) that are not visible to the DAA issuer, but which can be made visible during a signature at the will of the signer.
Usage:
Tspi_TPM_DAA_IssueSetup ( TSS_HDAA hDAA
UINT32 issuerBaseNameLength
BYTE* issuerBaseName
UINT32 numberPlatformAttributes
UINT32 numberIssuerAttributes
TSS_HKEY* keyPair
TSS_DAA_PK_ publicKeyProof
PROOF*
)
Here hDAA is the handle to a DAA object, and issuerBaseName is, of course, the name of the DAA issuer. The next two parameters represent the number of attributes the platform can choose that will not be visible to the issuer, and the number of attributes that will be visible to both the platform and the issuer. The last parameter is the proof that the public keys were correctly selected.
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Purpose: When a DAA authority is set up, it can then start issuing certificates. It is a two-command process, as far as the DAA authority is concerned, and this is the first of the two commands he uses. Before he issues this command, he should check credentials that verify that the platform he is about to issue a certificate for are genuine. These could be EK credentials, or physical presence, or on a manufacturing line.
Usage:
Tspi_TPM_DAA_IssueInit ( TSS_HDAA hDAA
TSS_HKEY issuerAuthPK
TSS_HKEY issuerKeyPair
TSS_DAA_IDENTITY_ identityProof
PROOF
UINT32 capitalUPrimeLength
UINT32* nonceIssuerLength
BYTE** nonceIssuer
UINT32* authentication
ChallengeLength
TSS_DAAA_JOIN_
ISSUER_SESSION* joinSession
)
hDAA is, of course, the DAA object. The issuerAuthPK is a public/private key pair of the DAA issuer, and issuerKeyPair comes from IssueSetup; so does the identityProof. The remaining variables are used in the protocol by sending them to the TSS application on the requesting platform, where they will be processed and then results returned to the DAA authority, which will use the result to perform the IssueCredential command.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE The DAA handle is invalid.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is the first of two commands the DAA authority performs to create a certificate for a TPM platform.
Purpose: This command is used by the receiver of a DAA signed message. It is the first of a two-part command, as it creates a challenge (nonce) for the TPM to use to prove it is a correctly signed DAA message.
Usage:
Tspi_TPM_DAA_VerifyInit ( TSS_HDAA hDAA
UINT32* nonceVerifierLength
BYTE** nonceVerifier
)
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Incorrect DAA object handle.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is the first command used by the recipient of a DAA signature to verify it.
Purpose: This command is the second (and final) command used by the recipient of a DAA signed message to verify a DAA signature.
Usage:
Tspi_TPM_DAA_VerifySignature (
TSS_HDAA hDAA
TSS_DAA_SIGNATURE daaSignature
TSS_HKEY hPubKeyIssuer
UINT32 attributesLength
BYTE** attributes
UINT32* nonceVerifier
Length
BYTE** nonceVerifier
UINT32* baseNameLength
BYTE** baseName
TSS_BOOL* isCorrect
)
hDDA is the handle of the DAA object, daaSignature is the daaSignature (returned from the TPM), hPubKeyIssuer is the handle of the public key of the DAA authority, attributes refers to the attributes exposed in the signature, nonceVerifier is the random challenge number produced by the recipient with the VerifyInit command, and baseName is the name that was chosen for the signature. Of course, isCorrect returns whether or not the signature verified correctly.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is the second command used by the recipient of a DAA signature to verify it.
Purpose: This command is used by the DAA authority to revoke a DAA certificate if the base secrets (which are supposed to be held securely in a TPM) become known. This could happen if a chip were delayered, for example.
Usage:
Tspi_TPM_DAA_RevokeSetup ( TSS_HDAA hDAA
TSS_HKEY daaPublicKey
TSS_HKEY* keyPair
)
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is used to revoke a DAA certificate if the private keys that are supposed to be held securely in the TPM become exposed. It returns a public/private key, which can be used to show a key has been revoked.
Purpose: This command is used to create new delegations made to a particular user.
Usage:
Tspi_TPM_DAA_ARDecrypt (
)
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM,
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements,
TSS_E_INTERNAL_ERROR The command failed.
Context: This is used to revoke a DAA certificate if the private keys inside it have been compromised and become known (for example, by publishing them on the Internet).
Locality is a new authorization mechanism in the TPM. In 1.1, the TPM could be authorized to perform a function based on an HMAC or based on PCRs being in a particular state. In 1.2, an additional function, called locality, can be used. There are six locality states: none, 0, 1, 2, 3, and 4. Locality is a state of the TPM that is based on special signals sent to the TPM. Locality is so called because the locality setting is supposed to be used to represent where a command is coming from. If a command is coming from a location that is trusted (for example, a special processor executing ROM code), then that command can be trusted in how it performs. In that case, the command may be running at locality 4. As the number increases in locality, so does the trust—so a process running in locality 4 is trusted more than a process running in locality 3, and so forth.
If the command, on the other hand, is running from Windows 95, it will run in either locality none or 0. “None” differs from 0 only in the bus used to talk with the chip, so that is irrelevant to software.
At key creation, or at sealing time, data or keys now can be “locked” to HMACs, PCR values, and/or locality.
Additional authentication techniques will likely be added in future revisions of the TPM.
Locality itself does not have any particular commands, but rather is a status that is maintained within the TPM. However, it is a property of the PCRlong structure.
As discussed earlier in the book, when data is sealed to a set of PCRs, the value of those PCRs at time of sealing is also recorded, and can be read out and verified at time of unsealing. However, the PCRs recorded were not independent of the PCRs used for unlocking the data. A new structure was put together, called PCRlong, which includes both the locality and two separate PCR structures: one for the historical data and one for the release data. Older commands were “overloaded” so that the TPM could receive either the older PCR data or the newer PCRlong data, and a 1.2 TPM will notice which is being input and do the appropriate thing with it. Older 1.1 TPMs will, of course, not be able to handle the data and will return an error.
Additionally some PCRs are given some new functionality, which is a bit complicated. Some PCRs can be reset! (In particular, PCR 16 can be generally reset to be all 0’s.)
Some PCRs can be reset only by certain localities (for example, PCR 17 and 18 can only be reset by locality 4) and when reset, they are reset to all F’s rather than all 0’s.
The PCRlong structure is used in a number of existing commands, but also appears in some new commands: For the most part, differences in commands are hidden in the TCS layer.
Commands:
Tspi_Context_GetRegisteredKeysByUUID2
Tspi_TPM_PcrReset
Tspi_Data_SealX
Tspi_TPM_Quote2
Tspi_PcrComposite_SetPcrLocality
Tspi_PcrComposite_GetPcrLocality
Tspi_PcrComposite_GetCompositeHash
Tspi_PcrComposite_SelectPcrIndexEx
In the 1.1 specification, the TPM had only 20 bytes of data that could be used to store things (in the DIR register). This space was not large enough to be considered useful for most purposes. Additionally, there were problems with the idea of a certificate for the EK—most PC OEMs had no place to put such a beast. If it were located on the hard drive, it would be easily lost, especially as many customers wipe the hard disk as soon as they get a new system and then put their own preload on it.
As a result of these considerations, the TPM was given its own variable-sized NVRAM (variable according to the TPM manufacturer), and special location handles were set aside to hold a certificate, if one were present, and other specific data.
The NVRAM was not merely stock NVRAM, though. When a region of the NVRAM was selected, locks were established separately into read locks and write locks. Then either HMAC or PCR authentication could be used to unlock those. Strangely enough, locality is not a selectable authentication, but it is possible to additionally select those areas of NVRAM to be either readable or writeable only once per power on. Another useful property is that GPIOs of the chip can be selected to be on or off by writing a 1 or a 0 into specified reserved location handles of NVRAM.
Reserved NVRAM indices are
TPM_NV_INDEX_GPIO_xx 0x00011600
PC Client GPIO_Express_00 00
PC Client reserved 01-7F
PC Client VendorSpecified 80-FF
PC Client GPIO_Express_00_bit 0x01
Purpose: This command sets aside a section of the NVRAM space to be used with a specific set of authorization values. The PCRs for read and write are set with this command directly. In order to set the authorization data to be used for read and write (should it be required), a policy object is used. The permissions needed are set with flags in the NV Storage object before using this command.
Usage:
Tspi_TPM_NV_DefineSpace ( TSS_HNVSTORE hNVStore
TSS_HPCRS hReadPcrComposite
TSS_HPCRS hWritePcrComposite
)
Here hNVStore is the handle of the NV storage object. You must set it up to have the correct values to make this object be set as “write once per boot” and “read once per boot.”
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: First, an NV storage object is created, and its permissions set. Then a policy object is created and associated with the NV storage object (if authorization data is needed for the object). Then this command is used, with PCR values set for read and write authorization, if they are selected in the policy object.
Purpose: This command reverses the DefineSpace, zeroing and releasing the space back to general usage.
Usage:
Tspi_TPM_NV_ReleaseSpace ( TSS_HNVSTORE hNVStore
)
Here hNVStore is the handle of the NV storage object to be released.
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: You must have a handle to an NV storage object already assigned in order to release it.
Purpose: This command fills in the values in an NV storage object inside the TPM.
Usage:
Tspi_TPM_NV_WriteValue ( TSS_HNVSTORE hNVStore
UINT32 offset
UINT32 ulDataLength
BYTE* rgbDataToWrite
)
Here hNVStore is the handle of the NV storage object. The variable offset tells where to begin writing inside the storage object, DataToWrite is the data to write there, and ulDataLength is the length of that data.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: You must have already used the DefineSpace command to use this.
Purpose: This command reads the data stored in an NV storage object.
Usage:
Tspi_TPM_NV_DefineSpace ( TSS_HNVSTORE hNVStore
UINT32 offset
UINT32* pulDataLength
BYTE** prgbDataRead
)
Here hNVStore is the handle of the NV storage object. The variable offset tells where to begin reading. A pointer to the length of the data to read is ulDataLength, and prgDataToRead tells the TSS where to dump the data read.
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: You must have written some data in the NV storage object before it makes sense to use this command.
The owner of a TPM ought to be able to tell how that TPM has been used. This is a basic property of security, since well before the rainbow series of books. In order to determine that a TPM has not been misused, it is necessary first to determine how it has been used. The 1.1 TPM had audit functions built in, but they were easily bypassed, and hence were not exposed by the 1.1 TSS. In the 1.2 TPM, those functions were completely replaced with a new set that has utility. Be warned, though, that the audit functions are not required in the PC-specific specification, so it is likely they will only exist on server TPMs.
The audit functions allow a TPM owner to select which TPM functions will be audited. It then keeps a running hash internal to the TPM of those functions (which are to be audited), to be used to validate the external history kept of the TPM functions. The monotonic counter (see the next section) is incremented every time the machine boots, and the audit function then uses that command to write out the data kept in the internal hash to make sure that an unbreakable chain of audit logs is kept.
Purpose: This command is used to define exactly which ordinals will be audited. The command itself is audited by default. Once set, any use of the command ordinal will be elected in the audit log.
Usage:
Tspi_TPM_NV_DefineSpace ( TSS_HTPM hTPM
TSS_COMMAND_CODE ordinalToAudit
TSS_BOOL auditStatus
)
Here hTPM is the TPM handle, and ordinalToAudit is the ordinal whose audit status is being changed. The auditStatus will either be TRUE (to be audited) or FALSE (not to be audited).
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is used to select ordinals that should be audited.
Purpose: This command gets an AIK signed audit log, along with necessary data to determine if it is correct. Audit is not required in the PC-specific specification, but will likely be required in the server specification.
Usage:
Tspi_TPM_NV_DefineSpace ( TSS_HTPM hTPM
TSS_HKEY hAIK
TSS_BOOL closeAudit
TPM_DIGEST* pAuditDigest
TPM_COUNTER_VALUE* pCounterValue
TSS_VALIDATION pValidationData
UINT32* ordSize
UINT32** ordList
)
Here hTPM is the handle of the TPM, hAIK is the handle of the AIK that is to be used to sign the TPM information necessary to validate the audit log, TSS_BOOL is a means to close an audit session when it is read, the pCounterValue and pValidationData are used to validate the audit log, and the ordList is the list of ordinals being audited.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used after a set of ordinals have been set to be audited, and then later it is checked. An example use would be if this set of commands was used to audit creation of a signing key followed by use of that signing key.
Another addition to the TPM was the monotonic counter. This counter has the property that it only increments in a step size of 1, and it will only increase—it can never be reset to zero. Obviously such a design is not entirely possible—either the counter will eventually “roll over” or it will stop incrementing. The design was set to make sure that the counter would not roll over for at least seven years, even if it were subject to a denial-of-service attack. This is achieved by throttling the speed at which the counter can be incremented. How much throttling is necessary is up to the TPM manufacturer, who presumably knows the capability of his process.
The monotonic counter was necessary to allow for auditing functions to work. Auditing functions are used by the owner of the TPM to determine exactly how it has been used. They also provide guarantees to the owner of a key that the key has not been used without permission.
Actually, there are four monotonic counters in the TPM. It is assumed that this provides the ability for four separate operating systems to each use their own monotonic counter. The counter that is in use is fixed at boot time—one cannot change between counters after the boot sequence. When a new counter is instantiated, it always starts at a value that is at least 1 more than the highest extant counter.
Purpose: This command is used to read the current value of the currently chosen counter. There are no TSP layer commands to increment the counter or create new counters. This is because if two different applications were each to increment the counter without communicating, the counter would lose its “monotonic” character.
Usage:
Tspi_TPM_ReadCurrentCounter ( TSS_HTPM hTPM
UINT32* counterValue
)
Here hTPM is the handle of the TPM and counterValue is the value of the currently selected counter.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER The counterValue passed is invalid.
TSS_E_INTERNAL_ERROR The command failed.
Context: It is probably the case that this command will only be used by the operating system, which will then provide a virtualized counter available to the applications.
A secure clock was still considered too expensive for a TPM during the 1.2 TPM time frame. Additional problems occur with a secure clock, including battery lifetime, voltage drift, and inaccuracies due to temperature variations. However, the function itself is useful, so a subset of the secure clock was added into the TPM. This is the tick counter. Every time the TPM is turned on, it generates a random number to associate with the tick counter, and starts an internal clock with a starting value of 0.
The TPM is then able to sign data and embed into the signature both the random number and also the current clock tick. By exchanging messages with a known correct time-stamping service, the ticks can be associated with a real time. Known accuracy, drift, and so on of the internal clock can then be used to associate any clock tick (associated with that random number) with a real time.
Purpose: This command reads the current tick value of the tick counter.
Usage:
Tspi_TPM_ReadCurrentTicks ( TSS_HTP hTPM
TPM_CURRENT_TICKS* pTickCount
)
Here hTPM is the handle of the TPM, and pTickCount is a pointer to where the tick count will be returned.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This can be run any time.
Purpose: This command sets aside a section of the NVRAM space to be used with a specific set of authorization values. The PCRs for read and write are set with this command directly. In order to set the authorization data to be used for read and write (should it be required), a policy object is used. The permissions needed are set with flags in the NV storage object before using this command.
Tspi_TPM_TickStampBlob ( TSS_HHASH hHash
TSS_KEY_HANDLE hAIK
TSS_VALIDATION* pValidationData
)
Here hHash is the hash being signed by the AIK, together with the current tick count and the random number that corresponds to the current tick counter. The pValidationData is a structure. Before calling this function, an anti-replay nonce should be put into the structure. On return, the structure will contain the signature and the buffer that was signed.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: Clever usage of this command can associate the tick count with an actual time. This can be done in a number of ways. For example, a tickstamped blob can be signed and sent to a Time Stamping Authority (TSA). The resulting signature is then tickstamped. Now it is easily shown that the tick stamp that corresponds to the TSA signature must lie between the two tick counts of the TPM. If one then knows the accuracy and precision of the TPM, one can easily associate any future tickstamp (or even a past tickstamp) with an actual time, with some error.
In 1.1, DCOM was the only interface defined for talking remotely to the 1.1 TCS stack. However, DCOM had problems—it was a Microsoft technology, so most Unix implementations could not take advantage of it, and it was getting long in the tooth on the OSs that did use it. SOAP is the defined replacement for DCOM, though DCOM will likely remain available in most implementations for some time.
Remote access to a TPM is a scary thing for privacy gurus, though. It is not wise to allow a remote user to have direct access to hardware that exists on a client platform. So by default, access to functions remotely is turned off, and the user is allowed a fine control over access to functionality he permits remote users to have on his platform.
This fine control is determined using an XML document, which the TCS stack can read. It allows an end user to control either by function the commands that are going to be available to the end user or by group of functions in a certain order.
In the 1.1 specification, it was possible to securely authorize a command, using an HMAC, so that a listener on the line could not determine the authorization data used. However, if an UNBIND or UNSEAL operation was securely authorized, the results of that command were released in the clear by the TPM. This is clearly a design mistake, as the unprotected released data (usually a key) was usually more valuable than the protected authorization data.
In the 1.2 TPM, this was fixed by creating a secure “tunnel” to the TPM using a transport session. Transport sessions are the default used to communicate remotely to a TPM through the TCS, but it is possible that a transport session would be used even in a local communication. The design is not particularly compute heavy, and it is usually better to be safe than sorry. On the other hand, when using a transport session, it is equally important that the programmer be aware that no 1.1 TPM will be able to understand the command.
Purpose: This command is used to set up an encryption “tunnel” between an application and the TPM so that any software listening in at the TPM cannot view any sensitive data going in or out of the TPM.
Usage:
Tspi_Context_SetTransEncryptionKey ( TSS_HCONTEXT hContext,
TSS_HKEY hKey
)
hKey will have associated with it a symmetric key used to create the secure tunnel. HContext is the context that is to use the secure tunnel.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: One must first set the symmetric key information into the key object addressed by hKey using Tspi_SetAttribData before calling this command.
Purpose: This ends the transport session started by SetTransEncryptionKey.
Usage:
Tspi_Context_CloseSignTransport ( TSS_HCONTEXT hContext
TSS_HKEY hSigningKey
TSS_VALIDATION* pValidationData
)
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: One first must have started a SetTransEncryptionKey session before one can end it.
One of the most important administrative functions in the 1.2 spec is the ability for the owner to “lock” keys in non-volatile memory of the TPM so that they are always available. This can provide a means for a pre-boot restricted environment to log on to a remote service securely. (Recall that SRKs, the only keys non-volatile in a 1.1 environment, can only be used for storage, not signing.) This is called “registering” a key.
Second, a byte of NVRAM has been set aside to keep information on how the owner of the TPM would like resources partitioned across VMs in the event that a hypervisor is being used to talk to the TPM. In this case, each VM will likely have its own communication path to the TPM, and so the only place where this data can reside that is available to the end user is in the TPM itself.
Third, some people were sure that TPMs must be designed to have a back door in them. (This is not true.) Because the EK was the only thing in the chip as it was shipped, they assumed that the EK was used as a back door. The real reason the EK was unerasable was that the credential that may ship with it would be difficult (and expensive) to replace. But rather than have people believe there was a back door, two new commands were added—one to erase the EK, and another to generate a new one.
Because DER and BER encoding are needed in various places, for convenience two functions were added to put a TssBlob in DER or BER encoding.
Some of these new functions are very specific to the hardware itself, and thus are only exposed in the TCS. Others are exposed all the way to the TSP layer.
Purpose: This requests the TPM to create an endorsement key and password. With knowledge of the password, the endorsement key can be revoked. If a certificate already exists for an endorsement key, it is recommended that the endorsement key not be revoked, as it costs money to create a new certificate.
Tspi_TPM_CreateRevocableEndorsementKey (
TSS_HTPM hTPM
TSS_HKEY hKey
TSS_VALIDATION* pValidationData
UINT32* pulEkResetDataLength
BYTE** prgbEkResetData
)
Here hTPM is the handle of the TPM that is going to create a new EK. HKey is used to specify the attributes of the new endorsement key. The pValidationData is a pointer to a validation instruction. If the length pointed to by pulEkResetDataLength is zero, that means the TPM should self-generate the password used to revoke the EK, returning that value in rgbEkResetData, and its length in pulEkResetDataLength. Otherwise, the authentication data necessary to revoke the key stored in the pointer rgbEkResetData is used.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements (likely the number of sessions is too large).
TSS_E_INTERNAL_ERROR The command failed.
Context: This allows a user to decide to create an endorsement key that cannot be easily erased by a denial-of-service attack. (The password/auth data controls the removal of the endorsement key.) One suggestion for the use of this is by a manufacturer, who could set the revocation password to be the machine serial number hashed with a manufacturer secret. Another is if the EK is squirted, it could be the hash of the public EK with a manufacturer secret. This way, the revocation password could be given to end users who requested it, but it would not be susceptible to a general virus style denial-of-service attack.
Purpose: This requests the TPM to create an endorsement key and password. With knowledge of the password, the endorsement key can be revoked.
Usage:
Tspi_TPM_RevokeEndorsementKey ( TSS_HTPM hTPM
UINT32 ulEkResetDataLength
BYTE* rgbEkResetData
)
Here hTPM is the handle of the TPM with the EK to be revoked, rgbEkResetData is the authentication data necessary to revoke it, and ulEkResetDataLength is the length of the authentication data.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This allows a user to revoke an endorsement key, assuming he knows the correct password.
Purpose: It is clear that whatever decision is made for the apportionment of a limited number of concurrent sessions (minimum 16) among localities would be wrong. So this command allows the end user to put his request for the apportionment in NVRAM in the TPM itself. There is no way to enforce this, but it does register the user’s wishes.
Usage:
Tspi_Admin_TSS_SessionPerLocality ( TSS_HCONTEXT hContext
UINT32 ulLocality
UINT32 ulSessions
TPM_AUTH* pOwnerAuth
)
By default, all localities are given 0 sessions. This command is used to change the number of sessions given to a locality. If ulSessions is larger than the number of remaining unassigned sessions, then an error message is thrown. The memory region being used is a pre-allocated index (TPM_NV_INDEX_Sessions) and requires owner authorization for writing.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This allows a user to register his preference for apportionment of sessions among localities.
Purpose: This command is similar to SessionsPerLocality—it allows the user to register how much time he would like the system to allow any locality to have exclusive use of the TPM. There is nothing that enforces this in the system, however.
Usage:
Tcsi_Admin_TSS_MaxTimePerLocality ( TSS_HCONTEXT hContext
UINT32 ulLocality
UINT32 ulMaxTime
TPM_AUTH* pOwnerAuth
)
The hContext is the context handle, the ulLocality is the locality in question, the ulMaxTime is the maximum amount of time that a locality should wait before releasing a PTM, and pOwnerAuth is a pointer to the owner authorization.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This allows a user to register his wishes for the amount of time a locality can have exclusive use of the TPM.
Purpose: This checks to see if the maintenance public key is correct. It is used at manufacturing time to determine if the correct maintenance public key was used.
Usage:
Tspi_TPM_CheckMaintenancePolicy (
TSS_HTPM hTPM
TSS_HKEY hMaintenanceKey
TSS_Validation* pValidationData
)
A nonce is sent to the TPM, which hashes it together with the maintenance public key. The pValidationData is a pointer to the validation data, which consists of the hash of the maintenance public key together with the nonce. The maintenance public key was not returned lest it be considered a privacy problem (although it is likely that a large number of machines would have the same value).
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This allows a user to check to see if the maintenance public key stored in his TPM (if it has one) is correct.
Purpose: This is used to put a key into non-volatile storage (persistent storage) in the TPM so that it is always loaded. This is useful in a low memory environment (like preboot).
Usage:
Tspi_Context_RegisterKey ( TSS_HCONTEXT hContext TSS_HKEY hKey TSS_FLAG persistentStorageType TSS_UUID uuidKey TSS_FLAG persistentStorage TypeParent TSS_UUID uuidParentKey )
Here hContext is the context handle, hKey is the key being registered, uuidKey is the UUID by which the key is registered in persistent storage (note that this may change after a boot), TSS_FLAG is used to note if the parent key has PCR restrictions, and uuidParentKey is the UUID of the parent key.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: The user must have a key already created and have the system in the correct state to load the key when registering a key. It should be noted: If a parent key of the key being registered needed the PCRs to be in a particular state to load the key, and that state was being used to guarantee that the key being registered is also being used in that state, registering such a key would obviate that requirement. As a result, it is not possible to register a key that has a parent or ancestor that requires a particular set of PCR values. (Of course, this cannot be guaranteed of migratable keys as they can be created/wrapped entirely outside the TPM.)
Purpose: This removes a key from the NVRAM of the TPM so that it is no longer available until it is loaded.
Usage:
Tspi_Context_UnregisterKey ( TSS_HCONTEXT hContext TSS_FLAG persistentStorageType TSS_UUID uuidKey TSS_HKEY* phKey )
Here hContext is the context handle, TSS_FLAG indicates if it is a user or system persistent storage, uuidKey is the UUID of the key being discarded, and phKey is a pointer to the handle of the key object containing the info (from the archive). Normally anyone can unregister a key, but KeyControlOwner can change that.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This can only be used after a key has been registered. It can’t be used on the EK or the SRK—they each have their own command to get rid of them.
Purpose: This command allows setting a “super user” control of a registered key. An owner can set a bit on a registered key such that the key remains in non-volatile storage inside the TPM. Only the owner is able to evict the key from the internal registry.
Usage:
Tspi_TPM_KeyControlOwner ( TSS_HTPM hTPM TSS_HKEY hKey UINT32 attribName TSS_BOOL attribValue TSS_UUID* pUuidData )
The hTPM variable refers to the TPM where the key is being semi-permanently stored. HKey is the key itself. The attribName and attribValue variables are used to set (or unset) the bit to keep the key in storage. (TSS_TSPATTRIB_KEYCONTROL_OWNEREVICT can be either TRUE or FALSE.) The pUuidData is the UUID by which the key was registered as a TPM resident key. Note that this UUID is volatile in the sense that with every new boot sequence, another UUID may be set to the key—if a key has been added or evicted from the TPM during the previous boot cycle.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: This command is used by the TPM owner typically to establish a signing key in the TPM, which can be used to establish that a platform in pre-boot state is the one it says it is.
Purpose: This lists the keys that are currently loaded in NVRAM in the TPM. It is a TCS layer command, and usually used by the key manager to make sure that the correct key is pointed to when a TSP caller calls for a key.
Usage:
Tspi_Context_CloseSignTransport( TSS_HCONTEXT hContext TSS_UUID* pKeyUUID UINT32* pcKeyHierarchySize TSS_KM_KEYINFO** ppKeyHierarchy )
Here hContext is the context handle, pKeyUUID is NULL for all keys, and ppKeyHierarchy is a pointer to the array of structures in the key hierarchy.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_FAIL The command did not complete successfully
Context: This is used to find out all the information of the keys currently registered in the TPM. If no keys are added or removed, the information will remain static.
Purpose: Get a key handle for a UUID that belongs to a registered key. Works well for static registered keys. (If keys are registered or unregistered, all UUIDs may change.)
Tspi_GetRegisteredKeyByUUID ( TSS_HCONTEXT hContext TSS_FLAG persistentStorageType TSS_UUID uuidData TSS_HKEY* phKey )
Here hContext is the handle to the established context, persistentStorageType is either user or platform, uuidData is the UUID of the key we want a handle for, and phKey is a pointer to where the handle is placed.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_PS_KEY_NOTFOUND No such UUID in registered keys.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is one way to get the handle to a key in registered storage in the TPM so it can be used.
Purpose: Get a key handle for a UUID that belongs to a registered key. Works well for static registered keys. (If keys are registered or unregistered, all UUIDs may change.)
Usage:
Tspi_Context_GetRegisteredKeyByPublicInfo ( TSS_HCONTEXT hContext TSS_FLAG persistentStorageType TSS_ALGORITHYM_ID algID UINT32 ulPublicInfoLength BYTE* rgbPublicInfo TSS_HKEY* phKey )
Here hContext is the handle to the established context, persistentStorageType is either user or platform, algID is the type of key (usually RSA), rgbPublicInfo is the public info of the key we want the handle for, and phKey is a pointer to where the handle is placed.
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_PS_KEY_NOTFOUND No such UUID in registered keys.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is one way to get the handle to a key in registered storage in the TPM so it can be used.
Purpose: This is to get the entire array of TSS_KM_KEYINFO structures for the registered key hierarchy.
Usage:
Tspi_Context_GetRegisteredKeysByUUID ( TSS_HCONTEXT hContext TSS_FLAG persistentStorageType TSS_UUID* puuidData UINT32* pulKeyHierarchySize TSS_KM)_KEYINFO** ppKeyHierarchy )
Here hContext is the handle to the established context, persistentStorageType is either user or platform, puuidData is usually set to NULL to get everything, and ppKeyHierarchy is a pointer to where the results are put.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_PS_KEY_NOTFOUND No such UUID in registered keys.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is one way to get the handle to a key in registered storage in the TPM so it can be used.
Purpose: This is to get the entire array of TSS_KM_KEYINFO2 structures for the registered key hierarchy.
Tspi_Context_GetRegisteredKeysByUUID2 ( TSS_HCONTEXT hContext TSS_FLAG persistentStorageType TSS_UUID* puuidData UINT32* pulKeyHierarchySize TSS_KM)_KEYINFO** ppKeyHierarchy )
Here hContext is the handle to the established context, persistentStorageType is either user or platform, puuidData is usually set to NULL to get everything, and ppKeyHierarchy is a pointer to where the results are put.
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_PS_KEY_NOTFOUND No such UUID in registered keys.
TSS_E_INTERNAL_ERROR The command failed.
Context: This is used to get information about all the keys registered in the TPM. It is the same as GetRegisteredKeysByUUID2 except that it returns KEYINFO2 structures instead of KEYINFO structures. The only difference between a TSS_KM_KEYINFO and a TSS_KM_KEYINFO2 structure is the addition of information as to whether the key (and its parent) are registered in the user hierarchy or the platform hierarchy.
Purpose: This is a helper command in the TSS stack used to take a TssBlob and put it into the standard DER encoding used to transfer blobs between different machines.
Usage:
Tcsip_Context_CloseSignTransport ( TSS_HTPM hTPM )
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: One needs to check the header of a blob to see if it is already DER encoded before using this command.
Purpose: This is a helper command in the TSS stack used to take a TssBlob and put it into the standard BER encoding used to transfer blobs between different machines.
Usage:
Tcsip_Context_CloseSignTransport ( TSS_HTPM hTPM )
Returns:
TSS_SUCCESS The command completed successfully.
TSS_E_INVALID HANDLE Can’t find the TPM.
TSS_E_BAD_PARAMETER One of the parameters does not meet the requirements.
TSS_E_INTERNAL_ERROR The command failed.
Context: One needs to check the header of a blob to see if it is already BER encoded before using this.
1. Determine the level of a TPM and the TSS being spoken to.
2. Create a transport session to talk with the TPM.
3. Turn on auditing of creation of CMKs.
4. Delegate the use of the CMK to another user.
5. Create a CMK key locked to a particular locality, and register the values in PCRs 0 and 1.
6. Sign the CMK with an AIK.
7. Sign the AIK with DAA.
8. Check the audit log.
The TSS 1.2 specification was announced in February 2006 with the header files following shortly after. Machines with 1.2 TSS stacks began shipping before the end of 2006. At that point, these new functions became available. It was not possible for us to provide tested code for the book using the 1.2 functions, as the stacks were not available; however, we thought it important to provide an analysis of those functions—how they can be used, and why they are written the way they are—so that the programmer and architect will be able to make use of this book for the next several years.
As the TPM specification is updated with new functionality, so the TSS must also keep pace. This section of the book provided a look at many functions that have not yet been taken advantage of, that exist in the new TSS 1.2 specification. In the future, the TPM specification will likely have more functionality added to it, but the intent of the TSS specification writers is that any code written using previous TSS APIs will continue to work with new TSS software stacks.
18.118.227.69