TPM on Embedded Systems: Pitfalls and Caveats to Watch Out For
Trusted Platform Module (TPM) chips have been around since the release of the TPM 1.2 specification more than 20 years ago, and the TPM 2.0 specification was released in 2014. The technology is now seeing widespread adoption in various computing sectors. TPMs have been a standard feature in PCs, particularly notebooks, for some time. With integration into tools like systemd’s tooling for LUKS/dm-crypt and legal requirements like EU’s CRA, TPM functionality is also now making its way into the embedded Linux sector. In this post, we’ll highlight common pitfalls and considerations for using TPM chips on embedded devices.
Brief Overview: Trusted Platform Module (TPM)
Usually, a TPM is a dedicated chip that is connected to the CPU via a bus like LPC, SPI, or I2C. In modern PCs, a firmware-based TPM (fTPM) is common, where the firmware (e.g., UEFI) emulates a TPM in a secure environment. The same is also possible on embedded devices, for example, by using Arm TrustZone to emulate a TPM.
There are three common use cases for TPM:
Secret storage: A core feature of a TPM is its ability to protect data using secure, internal keys. These keys are protected in a way that makes them usable only by and within the TPM itself. A TPM 2.0 chip supports multiple key hierarchies that reflect different trust scenarios, with the Platform Hierarchy and Storage Hierarchy being the most commonly used ones. A TPM client can create a new key in a hierarchy where the parent key’s handle is used to protect (encrypt and authenticate) the child key’s data (then known as blob) when it is placed in external storage. This process is known as binding. When the secret is needed again, the protected blob is passed back to the TPM, which verifies and decrypts it before returning it to the client.
The TPM 2.0 specification defines a multitude of cryptographic algorithms such as hash functions, symmetric/asymmetric ciphers and message authentication codes (MACs). This enables its use for network protocols like TLS and storage security like LUKS/dm-crypt on Linux or BitLocker on Windows.
Measured boot: Each TPM chip contains a set of 24 Platform Configuration Registers (PCRs). Their values are hashes produced from log events that reflect the boot and configuration state of the platform. This is primarily used to secure the boot chain of a system, where each stage of the boot process measures relevant components (bootloader, drivers, firmware, configuration data, etc.) and uses these measurements to extend the cryptographic hash of the respective PCRs. Concurrently, the details of these measurements are recorded in the TPM’s event log. The full set of PCR values provides a record of the boot state. Should a component be manipulated, the final PCR value will change, which indicates a potential security issue.
This can be combined with TPM keys, where each key can be tied to a set of PCR values (known as sealing). If the PCRs contain the expected values, the TPM allows the key to be used. Otherwise, its use is prevented. This enables tight control over when a key is usable and provides an integrity measure.
(Remote) Attestation: TPMs provide the ability to produce cryptographic proof of the boot and configuration state of a system. This is done through a dedicated attestation protocol. For the protocol to work, a trust chain must be established by verifying the TPM’s identity and its Attestation Key (AK). The attestation procedure utilizes a TPM key that is bound to a set of PCR values. This enforces that the attestation can only be run when the system is in a known, secure state. The result of this process is a signed Quote from the TPM, which contains the current PCR values and a signature that proves their origin.
... continue reading