tpm2-software / tpm2-tools

The source repository for the Trusted Platform Module (TPM2.0) tools
https://tpm2-software.github.io
705 stars 377 forks source link

tpm2-tools-2.1.0 and tpm_server (ibmtpm974) #469

Closed tomaszpr closed 6 years ago

tomaszpr commented 6 years ago

There are some errors on debian when I use:

tpm_server (ibmtpm974) tpm2-tss-1.2.0 tpm2-tools-2.1.0 tpm2-abrmd-1.1.1

  1. NVchip is deleted

  2. tpm_server is running: TPM command server listening on port 2321 Platform server listening on port 2322

  3. tpm2-abrmd is running: ./tpm2-abrmd -t socket from tpm_server I get: Client accepted Client accepted

  4. when I try to init TPM simulator and create keys I get:

./tpm2_startup -clear -T tabrmd -V
INFO on line: "142" in file: "tools/tpm2_startup.c": Sending TPM_Startup command with type: TPM_SU_CLEAR
INFO on line: "150" in file: "tools/tpm2_startup.c": Success. TSS2_RC: 0x100

./tpm2_takeownership -o ownerpass -e endorsepass -l lockpass -T tabrmd -V
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Owner
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Endorsement
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Lockout

./tpm2_createprimary -A e -K objectpass -g 0x000b -G 0x0001 -C po_end.ctx -P endorsepass -T tabrmd -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_end.ctx
CreatePrimary Succeed ! Handle: 0x800000ff

./tpm2_createprimary -A o -K objectpass -g 0x000b -G 0x0001 -C po_own.ctx -P ownerpass -T tabrmd -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_own.ctx
CreatePrimary Succeed ! Handle: 0x800000ff

Strange, I get twice the same Handle: 0x800000ff for both primary keys. But I want to show something different.

After first execute of this command: ./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T tabrmd -V I get:

contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Failed ! ErrorCode: 0x922

But when I retry it succed, the same call, the same arguments, no other calls between them.

contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Succeed !

As I found it happens with ibmtpm974. There is no problem with 532. But on the 532 is the same problem with the same Handle: 0x800000ff after tpm2_createprimary

When I don't use tpm2-abrmd it's working in another way.

When I use: tpm_server (ibmtpm974) tpm2-tss-1.2.0 tpm2-tools-2.1.0

./tpm2_startup -clear -T socket -V
INFO on line: "142" in file: "tools/tpm2_startup.c": Sending TPM_Startup command with type: TPM_SU_CLEAR
INFO on line: "150" in file: "tools/tpm2_startup.c": Success. TSS2_RC: 0x0

./tpm2_takeownership -o ownerpass -e endorsepass -l lockpass -T socket -V
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Owner
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Endorsement
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Lockout

./tpm2_createprimary -A e -K objectpass -g 0x000b -G 0x0001 -C po_end.ctx -P endorsepass -T socket -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_end.ctx
CreatePrimary Succeed ! Handle: 0x80000000

./tpm2_createprimary -A o -K objectpass -g 0x000b -G 0x0001 -C po_own.ctx -P ownerpass -T socket -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_own.ctx
CreatePrimary Succeed ! Handle: 0x80000001

Success! Different handles, but :

 ./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T socket -V
contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Failed ! ErrorCode: 0x922

Command repeated:

./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T socket -V
contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ERROR on line: "269" in file: "lib/files.c": ContextLoad Error. TPM Error:0x902

./tpm2_rc_decode 0x902
error layer
  hex: 0x0
  identifier: TSS2_TPM_ERROR_LEVEL
  description: Error produced by the TPM
format 0 warning code
  hex: 0x02
  name: TPM_RC_OBJECT_MEMORY
  description: out of memory for object contexts

When I use tpm_server ver.532, error happens in another place: tpm_server (ibmtpm532) tpm2-tss-1.2.0 tpm2-tools-2.1.0

./tpm2_startup -clear -T socket -V
INFO on line: "142" in file: "tools/tpm2_startup.c": Sending TPM_Startup command with type: TPM_SU_CLEAR
INFO on line: "150" in file: "tools/tpm2_startup.c": Success. TSS2_RC: 0x0

./tpm2_takeownership -o ownerpass -e endorsepass -l lockpass -T socket -V
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Owner
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Endorsement
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Lockout

./tpm2_createprimary -A e -K objectpass -g 0x000b -G 0x0001 -C po_end.ctx -P endorsepass -T socket -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_end.ctx
CreatePrimary Succeed ! Handle: 0x80000000

./tpm2_createprimary -A o -K objectpass -g 0x000b -G 0x0001 -C po_own.ctx -P ownerpass -T socket -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_own.ctx
CreatePrimary Succeed ! Handle: 0x80000001

./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T socket -V
contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Succeed !

Now it is ok, but:

./tpm2_load -c po_own.ctx -P objectpass -u key.pub -r key.priv -n key.name -C obj.ctx -T socket -V
contextParentFile = po_own.ctx
contextFile = obj.ctx
ERROR on line: "269" in file: "lib/files.c": ContextLoad Error. TPM Error:0x902

./tpm2_rc_decode 0x902
error layer
  hex: 0x0
  identifier: TSS2_TPM_ERROR_LEVEL
  description: Error produced by the TPM
format 0 warning code
  hex: 0x02
  name: TPM_RC_OBJECT_MEMORY
  description: out of memory for object contexts

I noticed that when tpm2-abrmd is used, there are the same handles returned for different keys.

tpm_server (ibmtpm974) tpm2-tss-1.2.0 tpm2-tools-2.1.0 tpm2-abrmd-1.1.1

./tpm2_startup -clear -T tabrmd -V
INFO on line: "142" in file: "tools/tpm2_startup.c": Sending TPM_Startup command with type: TPM_SU_CLEAR
INFO on line: "150" in file: "tools/tpm2_startup.c": Success. TSS2_RC: 0x100

./tpm2_takeownership -o ownerpass -e endorsepass -l lockpass -T tabrmd -V
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Owner
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Endorsement
INFO on line: "167" in file: "tools/tpm2_takeownership.c": Successfully changed hierarchy for Lockout

./tpm2_createprimary -A e -K objectpass -g 0x000b -G 0x0001 -C po_end.ctx -P endorsepass -T tabrmd -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_end.ctx
CreatePrimary Succeed ! Handle: 0x800000ff

./tpm2_createprimary -A o -K objectpass -g 0x000b -G 0x0001 -C po_own.ctx -P ownerpass -T tabrmd -V
nameAlg = 0x000b
type = 0x0001
contextFile = po_own.ctx
CreatePrimary Succeed ! Handle: 0x800000ff

Handle repeated!

And ...

./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T tabrmd -V
contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Failed ! ErrorCode: 0x922

the same key, second chanse (issue described before):

./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T tabrmd -V
contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Succeed !

./tpm2_load -c po_own.ctx -P objectpass -u key.pub -r key.priv -n key.name -C obj.ctx -T tabrmd -V
contextParentFile = po_own.ctx
contextFile = obj.ctx
Load succ.
LoadedHandle: 0x80000100

second key:

./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key2.pub -O key2.priv -T tabrmd -V
contextParentFile = po_own.ctx
nameAlg = 0x000b
type = 0x0001
ObjectAttribute: 0x00060072
Create Object Succeed !

./tpm2_load -c po_own.ctx -P objectpass -u key2.pub -r key2.priv -n key2.name -C obj2.ctx -T tabrmd -V
contextParentFile = po_own.ctx
contextFile = obj2.ctx
Load succ.
LoadedHandle: 0x80000100

but Handle repeated!

So, conclusion is: when tpm2-abrmd is used, it returns the same handles for different keys, and it works in another way when tpm2-abrmd is used and when is not used.

Thanks in advance! Best regards, Tomek

tstruk commented 6 years ago

Hi Tomasz, Could you restart the TPM simulator before each test with "./tpm_server -rm" The 0x902 error code it usually caused by some inconsistent NV memory state.

williamcroberts commented 6 years ago

Any resource manager visualizes handles between clients, so it's possible that two clients have the same handle, but the RM is routing them differently under-the-covers.

With that said, your issues arise on 974 and not 532. Does the tpm2-tools test suite pass if run against 974?

Looking at this, I am not really sure what the issue is, @flihp any comments?

flihp commented 6 years ago

Hi Tomasz,

I'm trimming this down a bit to focus on the relevant stuff:

On Thu, 2017-09-07 at 03:05 -0700, tomaszpr wrote:

CreatePrimary Succeed ! Handle: 0x800000ff

Strange, I get twice the same Handle: 0x800000ff for both primary keys.

This is expected behavior. The tabrmd is recycling handles that are freed up after it unloads the objects you're using.

But I want to show something different. After first execute of this command: ./tpm2_create -c po_own.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T tabrmd -V I get: contextParentFile = po_own.ctx nameAlg = 0x000b type = 0x0001 ObjectAttribute: 0x00060072 Create Object Failed ! ErrorCode: 0x922

But when I retry it succed, the same call, the same arguments, no other calls between them.

Funny enough if you decode this response code (using the tpm2_rc_decode tool from the tools project) it decodes to TPM_RC_RETRY. So retrying is the right thing. Think of this as an analog to an interrupted systemcall returning EINTR.

In a pending PR for the TSS I've added a macro to our test harness that's similar to the GNU TEMP_FAILURE_RETRY macro:

https://github.com/01org/tpm2-tss/pull/522/commits/8d2cdf21b159035746c1 5d3fe3536d2c37d92873#diff-e4a2320e253ceed5791461849737710dR39

Would be interested to know if this works for you too. Might be something we want to expose through the TSS headers.

Regards, Philip

flihp commented 6 years ago

Sorry, email interface borked up my link. The relevant macro is here: https://github.com/01org/tpm2-tss/pull/522/commits/8d2cdf21b159035746c15d3fe3536d2c37d92873#diff-e4a2320e253ceed5791461849737710dR39

williamcroberts commented 6 years ago

We might want to consider wrapping the tool invocations in the retry macro...

flihp commented 6 years ago

I'm considering having the tabrmd retry for the caller. Not sure if this will cause more problems than it solves though.

williamcroberts commented 6 years ago

If you do it in abrmd, I would need to add it to the device TCTI as well so it's consistent. What do you think about that?

martinezjavier commented 6 years ago

@williamcroberts If the retry logic is in the abrmd, then I think that for consistency it should be in the kernel resource manager and not in the device TCTI.

In the same way that the device TCTI doesn't do context swapping and that is left to the kernel RM, it shouldn't abstract from the TPM returning a TPM_RC_RETRY code IMHO.

IOW, the device TCTI (without the in-kernel RM) should expose a "raw" (what's the correct term for this?) access to the TPM.

williamcroberts commented 6 years ago

What about if your using /dev/tpm0 and not /dev/tpmrm0?

From: Javier Martinez Canillas [mailto:notifications@github.com] Sent: Friday, September 8, 2017 11:31 AM To: 01org/tpm2-tools tpm2-tools@noreply.github.com Cc: Roberts, William C william.c.roberts@intel.com; Mention mention@noreply.github.com Subject: Re: [01org/tpm2-tools] tpm2-tools-2.1.0 and tpm_server (ibmtpm974) (#469)

@williamcrobertshttps://github.com/williamcroberts If the retry logic is in the abrmd, then I think that for consistency it should be in the kernel resource manager and not in the device TCTI.

In the same way that the device TCTI doesn't do context swapping and that is left to the kernel RM, it shouldn't abstract from the TPM returning a TPM_RC_RETRY code IMHO.

IOW, the device TCTI (without the in-kernel RM) should expose a "raw" (what's the correct term for this?) access to the TPM.

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHubhttps://github.com/01org/tpm2-tools/issues/469#issuecomment-328180662, or mute the threadhttps://github.com/notifications/unsubscribe-auth/AQ7bBw6mzAJrrEuI6JblnDe65EDddsSXks5sgYfogaJpZM4PPleT.

martinezjavier commented 6 years ago

@williamcroberts that's precisely my point. There's already a difference between using /dev/tpm0 and /dev/tpmrm0.

With /dev/tpm0, you get 0x902 (TPM_RC_OBJECT_MEMORY) errors when creating more than TPM_PT_HR_TRANSIENT_MIN objects due the TPM running out of space for them. But that doesn't happen when having a resource manager (either /dev/tpmrm0 or tabrmd).

So in the same way, if tabrmd will abstract users about the 0x922 (TPM_RC_RETRY) error and just retry, I think that's fair to expect the same when using /dev/tpmrm0.

But that's not necessarily true when using /dev/tpm0, since just like the device TCTI doesn't handle the TPM_RC_OBJECT_MEMORY error, I don't think is its responsibility to deal with TPM_RC_RETRY.

tomaszpr commented 6 years ago

Could you restart the TPM simulator before each test with "./tpm_server -rm" The 0x902 error code it usually caused by some inconsistent NV memory state.

@tstruk Hi Tadeusz! Thank you for answering. Before each retest I do that:

Do yout think than use of tpm_server -rm will change something ? I think that removing of NVChip give the same effect. Or I'm wrong ?

webmeister commented 6 years ago

IOW, the device TCTI (without the in-kernel RM) should expose a "raw" (what's the correct term for this?) access to the TPM.

Right, there should be some way to talk to the TPM without anything interfering with the commands/responses being sent.

@williamcroberts If the retry logic is in the abrmd, then I think that for consistency it should be in the kernel resource manager and not in the device TCTI.

Having a central implementation that just does "the right thing", so that not every application needs to contain the same logic, would be nice. But is the resource manager the correct place? Retrying a command has nothing to do with resources, and I'd guess for this reason alone it might be rejected for the kernel RM (which aims for a rather minimalistic implementation).

Also, what is the correct way to handle TPM_RC_RETRY? I only found the description "the TPM was not able to start the command" in the specification, but no further information. Can you simply send the same byte stream again (even when using sessions/nonces)? What if you receive the same error? Do you add a small delay? When do you give up?

There are a couple more response codes that sound like they could be handled in the same way: TPM_RC_YIELDED, TPM_RC_TESTING, TPM_RC_NV_RATE

williamcroberts commented 6 years ago

@webmeister I don't think any retry code is appropriate for inside the resource manager itself and should be handled at the application level.

martinezjavier commented 6 years ago

Right, I didn't say that the retry logic should be in the resource manager (I still lack understanding about the resource manager spec to have an informed opinion).

What I said is that if the retry logic will be in the D-Bus tabrmd (as IIUC @flihp suggested), then for consistency it should be in the in-kernel resource manager and not in the device TCTI.

But I think is OK if that logic is both in the tabrmd and device TCTI libraries.

williamcroberts commented 6 years ago

@martinezjavier than we agree. I don't think the RMs should have retry logic. @flihp?

tomaszpr commented 6 years ago

Funny enough if you decode this response code (using the tpm2_rc_decode tool from the tools project) it decodes to TPM_RC_RETRY. So retrying is the right thing. Think of this as an analog to an interrupted systemcall returning EINTR.

But why simulator returns retry ? There is only one context. There is no interrupt. Always in the same place.

tstruk commented 6 years ago

On 09/10/2017 11:23 PM, tomaszpr wrote:

@tstruk https://github.com/tstruk Hi Tadeusz! Thank you for answering. Before each retest I do that:

  • stop tpm2-abrmd,
  • stop tpm_server,
  • remove NVChip file,
  • start tpm_server,
  • start tpm2-abrmd.

Do yout think than use of tpm_server -rm will change something ? I think that removing of NVChip give the same effect. Or I'm wrong ?

Hi Tomasz, Yes, you are right. Removing NVChip file and restarting tpm_server is equivalent to restarting tpm_server with -rm option. Just thought that it will help for the 0x902 (out of memory for object contexts) error. I usually get this error when I forget clean the NV store. Thanks, -- Tadeusz

tomaszpr commented 6 years ago

Hi, tpm2-tools version master, tpm2-tss version master, tpm2-abrmd version master, tpm_server 974,

./tpm2_startup --clear -T abrmd -V
./tpm2_takeownership -o ownerpass -e endorsepass -l lockpass -T abrmd -V
./tpm2_createprimary -A e -K objectpass -g 0x000b -G 0x0001 -C po.ctx -P endorsepass -T abrmd -V
CreatePrimary Succeed ! Handle: 0x800000ff

./tpm2_create -c po.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T abrmd -V
Create Object Failed ! ErrorCode: 0x922

Repeated:

./tpm2_create -c po.ctx -P objectpass -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T abrmd -V
Create Object Failed ! ErrorCode: 0x98e
./tpm2_rc_decode 0x98e
error layer
  hex: 0x0
  identifier: TSS2_TPM_ERROR_LEVEL
  description: Error produced by the TPM
format 1 error code
  hex: 0x0e
  identifier: TPM_RC_AUTH_FAIL
  description: the authorization HMAC check failed and DA counter incremented
session
  hex: 0x100
  identifier: TPM_RC_1
  description:  (null)

When I repeat this test from the begining without 'objectpass', the test succeed.

./tpm2_createprimary -A e -g 0x000b -G 0x0001 -C po.ctx -P endorsepass -T abrmd -V

./tpm2_create -c po.ctx -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T abrmd -V
Create Object Failed ! ErrorCode: 0x922
./tpm2_create -c po.ctx -K subobjectpass -g 0x000b -G 0x0001 -o key.pub -O key.priv -T abrmd -V
Create Object Succeed !

It doesn't happen with: tpm2-tss-1.2.0 tpm2-tools-2.1.0 tpm2-abrmd-1.1.1

williamcroberts commented 6 years ago

I wonder what would happen if you tried it with:

tpm2-tools version master,
tpm2-tss-1.2.0
tpm2-abrmd-1.1.1
tpm_server 974
williamcroberts commented 6 years ago

Blocked on: https://github.com/01org/tpm2-abrmd/issues/224

williamcroberts commented 6 years ago

Doing this in the TSS would be nice, this way I don't have to wrap my tss calls in something like a temp_failure_retry ala glibc macro.

flihp commented 6 years ago

I ran into this again while working on #586. Since integrating the retry logic in the stack is a bit intrusive I'm polling the TCG TSS WG members for their thoughts. While I'm waitnig on that my plan is to implement the TEMP_FAILURE_RETRY ish macro to unblock this.

flihp commented 6 years ago

There's a PR including this work in #585

flihp commented 6 years ago

585 contained a fix for this & was merged yesterday