Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > linux.kernel > #1603429 > unrolled thread

RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands

Started by<Alexander.Steffen@infineon.com>
First post2017-03-17 17:00 +0100
Last post2017-03-27 07:30 +0200
Articles 10 — 5 participants

Back to article view | Back to linux.kernel

This discussion starts older than the indexed window; earlier articles aren't shown. The article labeled Started by below is the oldest one visible, not the original post.


Contents

  RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands <Alexander.Steffen@infineon.com> - 2017-03-17 17:00 +0100
    Re: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands Jason Gunthorpe <jgunthorpe@obsidianresearch.com> - 2017-03-17 17:20 +0100
      RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands <Peter.Huewe@infineon.com> - 2017-03-17 17:40 +0100
        RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands <Alexander.Steffen@infineon.com> - 2017-03-20 11:00 +0100
          Re: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands Jason Gunthorpe <jgunthorpe@obsidianresearch.com> - 2017-03-20 18:30 +0100
          Re: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands Ken Goldman <kgold@linux.vnet.ibm.com> - 2017-03-20 23:50 +0100
            RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands <Alexander.Steffen@infineon.com> - 2017-03-21 17:00 +0100
    Re: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands Jarkko Sakkinen <jarkko.sakkinen@linux.intel.com> - 2017-03-17 21:50 +0100
      RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands <Alexander.Steffen@infineon.com> - 2017-03-20 11:00 +0100
        Re: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands Jarkko Sakkinen <jarkko.sakkinen@linux.intel.com> - 2017-03-27 07:30 +0200

#1603429 — RE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands

From<Alexander.Steffen@infineon.com>
Date2017-03-17 17:00 +0100
SubjectRE: [tpmdd-devel] [PATCH v3 2/7] tpm: validate TPM 2.0 commands
Message-ID<tm2si-kO-33@gated-at.bofh.it>
> Check for every TPM 2.0 command that the command code is supported and
> the command buffer has at least the length that can contain the header
> and the handle area.

This breaks several use cases for me:

1. I've got a TPM that implements vendor-specific command codes. Those cannot be send to the TPM anymore, but are rejected with EINVAL.

2. When upgrading the firmware on my TPM, it switches to a non-standard communication mode for the upgrade process and does not communicate using TPM2.0 commands during this time. Rejecting non-TPM2.0 commands means upgrading won't be possible anymore.

3. I'd like to use the kernel driver to test my TPM implementation. So for example, I send an invalid command code to the TPM and expect TPM_RC_COMMAND_CODE in response, but now I get EINVAL instead and the TPM never sees the command.

From my point of view, the kernel driver should provide a transparent communication channel to the TPM. Whatever I write to /dev/tpm<n> should arrive at the TPM device, so that the TPM can handle it and return the appropriate response. Otherwise, you'll end up reimplementing all the command handling logic, that is already part of the TPM's job, and as soon as you miss one case and behave differently than the TPM, something relying on this behavior will break.

I see two possible solutions:

1. When the driver does not know a command code, it passes through the command unmodified. This bears the risk of unknown side effects though, so TPM spaces might not be as independent as they should be.

2. Since the command code lookup is only really necessary for TPM spaces, it only gets activated when space != NULL. So the change will not affect /dev/tpm<n>, but only the new /dev/tpmrm<n>. As /dev/tpmrm<n> is not meant to be a transparent interface anyway, rejecting unknown commands is acceptable.

Alexander

[toc] | [next] | [standalone]


#1603439

FromJason Gunthorpe <jgunthorpe@obsidianresearch.com>
Date2017-03-17 17:20 +0100
Message-ID<tm2LE-KO-25@gated-at.bofh.it>
In reply to#1603429
On Fri, Mar 17, 2017 at 03:40:15PM +0000, Alexander.Steffen@infineon.com wrote:

> 1. I've got a TPM that implements vendor-specific command
> codes. Those cannot be send to the TPM anymore, but are rejected
> with EINVAL.
> 
> 2. When upgrading the firmware on my TPM, it switches to a
> non-standard communication mode for the upgrade process and does not
> communicate using TPM2.0 commands during this time. Rejecting
> non-TPM2.0 commands means upgrading won't be possible anymore.

How non standard? Is the basic header even there? Are the lengths
and status code right?

This might be an argument to add a 'raw' ioctl or something
specifically for this special case.

Jason

[toc] | [prev] | [next] | [standalone]


#1603447

From<Peter.Huewe@infineon.com>
Date2017-03-17 17:40 +0100
Message-ID<tm350-Ro-17@gated-at.bofh.it>
In reply to#1603439
> 1. I've got a TPM that implements vendor-specific command codes. Those
> cannot be send to the TPM anymore, but are rejected with EINVAL.
>
>> 2. When upgrading the firmware on my TPM, it switches to a
>> non-standard communication mode for the upgrade process and does not
>> communicate using TPM2.0 commands during this time. Rejecting
>> non-TPM2.0 commands means upgrading won't be possible anymore.

>How non standard? Is the basic header even there? Are the lengths and status code right?

>This might be an argument to add a 'raw' ioctl or something specifically for this special case.

It follows the regular TPM command syntax and looks something like 1.2 commands.

Peter

[toc] | [prev] | [next] | [standalone]


#1604320

From<Alexander.Steffen@infineon.com>
Date2017-03-20 11:00 +0100
Message-ID<tn2gB-2R9-73@gated-at.bofh.it>
In reply to#1603447
>>> 2. When upgrading the firmware on my TPM, it switches to a
>>> non-standard communication mode for the upgrade process and does not
>>> communicate using TPM2.0 commands during this time. Rejecting
>>> non-TPM2.0 commands means upgrading won't be possible anymore.
>>
>> How non standard? Is the basic header even there? Are the lengths and
>> status code right?
>>
>> This might be an argument to add a 'raw' ioctl or something specifically
>> for this special case.
>
> It follows the regular TPM command syntax and looks something like 1.2
> commands.

Yep, so most of it already works with the current implementation.

There are a few special cases that need some thought though. For example, it is possible to use an upgrade to switch the TPM family from 1.2 to 2.0 (or vice versa). In this case it seems useful to let the kernel reinitialize the TPM driver, so it uses the correct timeouts for communication, activates the correct features (resource manager or not?), etc., without needing to reboot the system.

Another problem arises when the upgrade process is interrupted, e.g. because power is lost. Then the TPM is stuck in its non-standard upgrade mode, so the kernel does not recognize it as a valid TPM device and does not export /dev/tpm<n>. But without the device node the upgrader is unable to restart the upgrade process, leaving the TPM forever inaccessible.

I'll try to work on those problems in the coming weeks and provide the fixes. Any input is appreciated.

Alexander

[toc] | [prev] | [next] | [standalone]


#1604833

FromJason Gunthorpe <jgunthorpe@obsidianresearch.com>
Date2017-03-20 18:30 +0100
Message-ID<tn9i2-7Yx-41@gated-at.bofh.it>
In reply to#1604320
On Mon, Mar 20, 2017 at 09:54:41AM +0000, Alexander.Steffen@infineon.com wrote:
> >>> 2. When upgrading the firmware on my TPM, it switches to a
> >>> non-standard communication mode for the upgrade process and does not
> >>> communicate using TPM2.0 commands during this time. Rejecting
> >>> non-TPM2.0 commands means upgrading won't be possible anymore.
> >>
> >> How non standard? Is the basic header even there? Are the lengths and
> >> status code right?
> >>
> >> This might be an argument to add a 'raw' ioctl or something specifically
> >> for this special case.
> >
> > It follows the regular TPM command syntax and looks something like 1.2
> > commands.
> 
> Yep, so most of it already works with the current implementation.
> 
> There are a few special cases that need some thought though. For
> example, it is possible to use an upgrade to switch the TPM family
> from 1.2 to 2.0 (or vice versa). In this case it seems useful to let
> the kernel reinitialize the TPM driver, so it uses the correct
> timeouts for communication, activates the correct features (resource
> manager or not?), etc., without needing to reboot the system.

It would be nice to do this via plug/unplug with existing sysfs
machinery.

> Another problem arises when the upgrade process is interrupted,
> e.g. because power is lost. Then the TPM is stuck in its
> non-standard upgrade mode, so the kernel does not recognize it as a
> valid TPM device and does not export /dev/tpm<n>. But without the
> device node the upgrader is unable to restart the upgrade process,
> leaving the TPM forever inaccessible.

I guess you'd have to teach the TPM core about a new chip mode besides
1.2, 2.0 - some kind of 'upgrade' mode.

So the flow would be to send the upgrade command, unplug/replug the
driver to switch to 'upgrade' mode (which could happen if there was a
reboot?) do the upgrade, then unplug/replug to rediscover the 'new'
TPM.

Jason

[toc] | [prev] | [next] | [standalone]


#1605184

FromKen Goldman <kgold@linux.vnet.ibm.com>
Date2017-03-20 23:50 +0100
Message-ID<tnehH-2Ul-9@gated-at.bofh.it>
In reply to#1604320
On 3/20/2017 5:54 AM, Alexander.Steffen@infineon.com wrote:
>
> There are a few special cases that need some thought though. For
> example, it is possible to use an upgrade to switch the TPM family
> from 1.2 to 2.0 (or vice versa). In this case it seems useful to let
> the kernel reinitialize the TPM driver, so it uses the correct
> timeouts for communication, activates the correct features (resource
> manager or not?), etc., without needing to reboot the system.

In practice, would a TPM upgrade from TPM 1.2 to TPM 2.0 even occur 
without a reboot?  Is it an important use case?

1 - It would leave the SHA-256 PCRs in the reset state.

2 - It's possible that this upgrade would also require a BIOS upgrade.

[toc] | [prev] | [next] | [standalone]


#1605752

From<Alexander.Steffen@infineon.com>
Date2017-03-21 17:00 +0100
Message-ID<tnumt-5mU-11@gated-at.bofh.it>
In reply to#1605184
> > There are a few special cases that need some thought though. For
> > example, it is possible to use an upgrade to switch the TPM family
> > from 1.2 to 2.0 (or vice versa). In this case it seems useful to let
> > the kernel reinitialize the TPM driver, so it uses the correct
> > timeouts for communication, activates the correct features (resource
> > manager or not?), etc., without needing to reboot the system.
> 
> In practice, would a TPM upgrade from TPM 1.2 to TPM 2.0 even occur
> without a reboot?  Is it an important use case?
> 
> 1 - It would leave the SHA-256 PCRs in the reset state.
> 
> 2 - It's possible that this upgrade would also require a BIOS upgrade.

For a traditional PC and when your goal is platform integrity, a reboot is probably the way to go. But in an embedded environment where there is no BIOS or if you use the TPM more like a smartcard just to store some keys (or generate random numbers), a reboot is unnecessary and it is more comfortable to avoid it.

We probably should inform the kernel before the upgrade anyway, so that it can shut down the TPM gracefully (and maybe switch to the upgrade mode, as Jason suggested). With that infrastructure in place, it does not seem like a lot of effort to also let it switch the TPM back to normal operation mode once the upgrade is complete.

Alexander

[toc] | [prev] | [next] | [standalone]


#1603618

FromJarkko Sakkinen <jarkko.sakkinen@linux.intel.com>
Date2017-03-17 21:50 +0100
Message-ID<tm6YV-3Hs-21@gated-at.bofh.it>
In reply to#1603429
On Fri, Mar 17, 2017 at 03:40:15PM +0000, Alexander.Steffen@infineon.com wrote:
> > Check for every TPM 2.0 command that the command code is supported and
> > the command buffer has at least the length that can contain the header
> > and the handle area.
> 
> This breaks several use cases for me:

Thank you for reporting these. This is really great feedback to get.

> 1. I've got a TPM that implements vendor-specific command codes. Those
> cannot be send to the TPM anymore, but are rejected with EINVAL.
> 
> 2. When upgrading the firmware on my TPM, it switches to a
> non-standard communication mode for the upgrade process and does not
> communicate using TPM2.0 commands during this time. Rejecting
> non-TPM2.0 commands means upgrading won't be possible anymore.
> 
> 3. I'd like to use the kernel driver to test my TPM implementation. So
> for example, I send an invalid command code to the TPM and expect
> TPM_RC_COMMAND_CODE in response, but now I get EINVAL instead and the
> TPM never sees the command.
> 
> From my point of view, the kernel driver should provide a transparent
> communication channel to the TPM. Whatever I write to /dev/tpm<n>
> should arrive at the TPM device, so that the TPM can handle it and
> return the appropriate response. Otherwise, you'll end up
> reimplementing all the command handling logic, that is already part of
> the TPM's job, and as soon as you miss one case and behave differently
> than the TPM, something relying on this behavior will break.
> 
> I see two possible solutions:
> 
> 1. When the driver does not know a command code, it passes through the
> command unmodified. This bears the risk of unknown side effects
> though, so TPM spaces might not be as independent as they should be.
> 
> 2. Since the command code lookup is only really necessary for TPM
> spaces, it only gets activated when space != NULL. So the change will
> not affect /dev/tpm<n>, but only the new /dev/tpmrm<n>. As
> /dev/tpmrm<n> is not meant to be a transparent interface anyway,
> rejecting unknown commands is acceptable.
> 
> Alexander

I think the most straight-forward way to sort this out would be to limit
validation to the resource manager. If I send a fix, would you care to
test it? If your issues get sorted, I'll squash it to the existing
commits.

Thanks again!

/Jarkko

[toc] | [prev] | [next] | [standalone]


#1604319

From<Alexander.Steffen@infineon.com>
Date2017-03-20 11:00 +0100
Message-ID<tn2gA-2R9-71@gated-at.bofh.it>
In reply to#1603618
> I think the most straight-forward way to sort this out would be to limit
> validation to the resource manager.

Sounds good to me.

> If I send a fix, would you care to test it?

Sure, will do.

Alexander

[toc] | [prev] | [next] | [standalone]


#1609453

FromJarkko Sakkinen <jarkko.sakkinen@linux.intel.com>
Date2017-03-27 07:30 +0200
Message-ID<tpvo6-2YI-5@gated-at.bofh.it>
In reply to#1604319
On Mon, Mar 20, 2017 at 09:56:17AM +0000, Alexander.Steffen@infineon.com wrote:
> > I think the most straight-forward way to sort this out would be to limit
> > validation to the resource manager.
> 
> Sounds good to me.
> 
> > If I send a fix, would you care to test it?
> 
> Sure, will do.
> 
> Alexander

I sent the patch. Please check it out.

/Jarkko

[toc] | [prev] | [standalone]


Back to top | Article view | linux.kernel


csiph-web