Talk:Trusted Platform Module
Uses and security implications
I'm still not sure what TPM is used for and whether or not it's a good idea to use it at all. It seems like TPM can be used to store LUKS private keys [1]. What's the point of that? It seems like Windows uses it so that a user only has to enter their user password both to unlock the partition and to login [2]. VeraCrypt (and previously TrueCrypt) is against the usage of TPM. [3] —This unsigned comment is by Rdeckard (talk) 11:39, 23 February 2018. Please sign your posts with ~~~~!
PCR 0 should be avoided
This --tpm2-pcrs=0+7
flag is flat out wrong, but copied from howto to howto. :-/ (It appeared in a few blogposts, e.g. here, sometimes even with a ,
instead of a +
, which is “doubly wrong”, in a way.)
The man
page for systemd-cryptenroll
explicitly discourages the use of PCR 0: “For most applications it should be sufficient to bind against PCR 7… …it's typically not advisable to include PCRs such as 0…”
The reason is that the key should not be bound to PCRs that change routinely and whose changes are benign. This includes system firmware (PCR 0). On recent Lenovo laptops, for example, firmware updates (fwupdmgr refresh; fwupdmgr upgrade;
) can appear often, perhaps monthly. The key enrollment should not be invalidated after each firmware upgrade.
That↑ said, the default PCR 7 (picked in absence of the --tpm2-pcrs
flag) is all that’s needed.
Andrej (talk) 20:06, 29 March 2023 (UTC)
- I'm not an expert, but I'm not sure I agree with the advice given in the man page. Or, at least, I would like to see a source for the claim that "since the program code they cover should already be protected indirectly through the certificates measured into PCR 7." As far as I understand it, if you don't bind to PCR 0, someone could flash malicious firmware to your device, boot it up, have the TPM automatically unlock your drive (because you didn't bind to PCR 0 so it doesn't care if the firmware changed) and then use the malicious firmware to steal your data without knowing your user password. This could theoretically be done without physical access to your system, if you download malware that automatically flashes your BIOS. Of course, one could dispute the probability of this scenario, but I think it would be possible if you don't bind to PCR 0.
- I'm pretty sure Windows binds to PCRs 0 and 7 (at least). That's why if you update your UEFI on a Windows laptop it will ask you to suspend disk encryption for one reboot cycle, so it can rebind the TPM PCRs. Not that we should blindly follow whatever Microsoft does, but I don't think it's bad to consider wider industry practice. I guess, in my opinion, the firmware is the ultimate root of trust, since it's the lowest layer of software on your computer (other than maybe IME), so it's integrity should be assured before anything else. I'm open to being convinced otherwise, though, especially since the man page seems to imply that it should be indirectly measured through PCR 7. I've just never heard that before.
- Forgonewarrior (talk) 19:54, 11 April 2023 (UTC)
- If firmware is forged then PCR0 is already useless. At boot chain UEFI BIOS is inherently trusted, so an advanced Evil Maid can just forge PCR0 read output. While NIST already gave out guidelines for signed BIOS and SPI Protected Range, but the implementation is up to the manufacturers, so PCR0 is useless. Source: https://www.c7zero.info/stuff/Evil%20Maid%20Just%20Got%20Angrier.pdf
- Bitlocker doesn't use 0 and 7. It uses either 0 2 4 11 or 7 11 (the latter is preferred when 7 is bindable - for TPM 2.0, this is because PCR 7 on TPM 2.0 performs platform attestation in addition to just storing Secure Boot flag from TPM 1.2) https://learn.microsoft.com/en-us/windows-hardware/test/hlk/testref/954cf796-a640-4134-b742-eaf0ed2663ff#troubleshooting
- So conclusion, PCR0 binding is useless (BIOS firmware inherently trusted). Binding PCR 4 will require rebinding everytime bootloader update, PCR 2 need rebinding after adding PCIe and other stuffs. On TPM 2.0 binding 7 is enough, on TPM 1.2 nothing is safe but at least TPM 7 is still a decent default (maybe bind 4 and 7 + hook to rebind everytime grub updates)
- TL;DR: PCR 7 is a good default, especially for TPM 2.0. PCR 0 should not be used
- N0k0m3 (talk) 03:53, 5 May 2023 (UTC)
- Agree with the above and the notion that PCR 0 is arguably unnecessary.
- The man page as of systemd 254 advises not to use PCR 0 and 2 as it is both redundant and fragile. Putting aside whether this advice is correct or not or unnecessary, measuring against literal PCR values for this component is certainly more fragile compared to signatures as firmware upgrade would risk locking the user out.
- Unless binding to signatures are supported for PCR 0, this should not be recommended. Nu4425 (talk) 22:04, 6 October 2023 (UTC)
- N0k0m3 (talk) 03:53, 5 May 2023 (UTC)
- I've added [4] and am still in contemplation if current suffices to close the topic. Opinions/edits welcome. One consideration to keep in mind is that systemd-cryptenroll requires a prior passphrase/luks-key. So, the worst case of a user locking themself out (totally) via misconfiguration is reduced by that. --Indigo (talk) 15:02, 8 October 2023 (UTC)
- That's true. The user wouldn't be completely locked out unless TPM2 is the only method for unlocking the LUKS2 volume.
- The necessity of PCR 0 is still up for debate, and would actually be interested in another opinion. Since this is the case, it should not be included in the default example which I've already changed.
- The default example on the wiki which should be left simple--kept to systemd-cryptenroll's current defaults and recommendations. As of systemd 254 this is PCR 7. Nu4425 (talk) 05:11, 9 October 2023 (UTC)
- I've added [4] and am still in contemplation if current suffices to close the topic. Opinions/edits welcome. One consideration to keep in mind is that systemd-cryptenroll requires a prior passphrase/luks-key. So, the worst case of a user locking themself out (totally) via misconfiguration is reduced by that. --Indigo (talk) 15:02, 8 October 2023 (UTC)
PCR register table
The referred UAPI table is itself not authoritative and makes exclusions like "How other operating systems — in particular Windows — use PCRs, is out of scope of this document.", which we need to cover to some extent. The PCR register itself is stable, we'd mostly remove links to our own content and a place for contextual info (e.g. users multi-booting). So, I'm against removal for now. Indigo (talk) 19:33, 6 December 2024 (UTC)
- I'm against its removal too. IMO we can improve the table to a better state than what the UAPI group or TCG has. The only thing missing from our table would be an "Extended by" column listing which software changes a PCR. -- nl6720 (talk) 07:19, 7 December 2024 (UTC)
- Thanks for putting up the talk page. I agree that the uapi table is not authoritative, but it still is more accurate right now than the wiki one. I was about to copy paste some of the missing stuff and figured this makes no sense, just like duplicating man pages.
- For most people, a lot of the PCRs really aren't useful. That's why I think focusing (1) the useful PCRs and explaining why they make sense and (2) adding info which is missing from the uapi table makes more sense than yet another table. Cvlc (talk) 22:55, 7 December 2024 (UTC)
- As soon as I find some time I'll put up an article on signed PCR policies and PCRlock, which both make more sense in my opinion and really aren't any harder to use anymore than raw PCR hashes. That's why as much as I'm interested in PCR hashes, I'm afraid keeping all this info might confuse people more than be useful to anyone. Cvlc (talk) 23:01, 7 December 2024 (UTC)
- I think these are all valid points and clearly good additions. More and more software will make use of PCR registers, so it's indeed seems useful to not only use the table as a crosslink anchor but be able to add context with a new column where applicable.
- At the same time I follow the point that most users will benefit from a structured approach to deploy the new systemd tools. Albeit they may be most useful for their main intend first - "factory"-style images/hosts/machines. Yet, that should not matter, many users will be able to apply a structured guidance for their hardware/purpose. Just keep in mind it's systemd tools. The kernel offers different API to the TPM, systemd decides on one that's useful for its purpose, but other software other use cases.
- IMO you should switch the remove template to Template:Expansion. Depending on phrasing, we can keep this item linked to it for the time being regarding scoping, or open a new one. --Indigo (talk) 20:24, 9 December 2024 (UTC)
- Changed the template to expansion. I still think the table in its actual form needs to go though :)
- Maybe a subsection per meaningful PCR, and examples as to why they make sense ? For example, the warning which is somewhere about making sure SB is enabled before tying to PCR 7 would go under PCR 7, etc.. Cvlc (talk) 23:41, 29 December 2024 (UTC)
- I changed the table slightly. IMO the PCR descriptions need a lot of improvement (I wonder from where they originated), but I still think it's worth it to keep the table. ❄️❄️ nl6720 (talk) 11:24, 30 December 2024 (UTC)
- A more up to date version of this table is also being maintained here, although it is missing the bits relating to Windows. https://man.archlinux.org/man/systemd-cryptenroll.1#TPM2_PCRs_and_policies Kolly (talk) 13:34, 7 January 2025 (UTC)
- That's a neat man presentation, yes. I'd vouch to link it instead of the UAPI, but it also misses all the addendum notes that page has. Then again, it lists PCR 16/23 when the UAPI does not even mention them .. It makes sense to link it from systemd-* articles and, in my opinion, it does not hurt to crosslink all sources above the table either, maybe pointing out differences. Example: I write from a notebook which uses PCR16 optionally. It is a corner-case, but there will be a few of such. --Indigo (talk) 21:19, 7 January 2025 (UTC)
- A more up to date version of this table is also being maintained here, although it is missing the bits relating to Windows. https://man.archlinux.org/man/systemd-cryptenroll.1#TPM2_PCRs_and_policies Kolly (talk) 13:34, 7 January 2025 (UTC)
- I changed the table slightly. IMO the PCR descriptions need a lot of improvement (I wonder from where they originated), but I still think it's worth it to keep the table. ❄️❄️ nl6720 (talk) 11:24, 30 December 2024 (UTC)
Using PCR policies at different stages requires separate keys
The introduction in Trusted Platform Module#PCR policies advertises separate access to secrets in the initrd and the running system. While the given example technically works in that the volumes can be unlocked, the use of single key pair for different phases results in all secrets being accessible in all phases. This defeats the purpose of the access separation and the example is misleading at best. The proper implementation of this implementation should follow Example 5 of the ukify man page (v257.8-2). For the wiki here, I would propose to:
- drop the item on manual key generation
- use separate keys for the initrd and system phase (in the example to be used for swap, but the key is bound to the system phase), e.g.
/etc/systemd/tpm2-pcr-initrd-private-key.pem
and/etc/systemd/tpm2-pcr-system-private-key.pem
(and corresponding public keys) - use
ukify genkey --config=/etc/kernel/uki.conf
to generate all keys in one go (NB: requires temporarily commenting out the SB signing keys if they already exist) - enroll policies with explicit reference to the public key to bind it to the desired phase, i.e.
# systemd-cryptenroll --wipe-slot tpm2 --tpm2-device auto --tpm2-pcrs="" --tpm2-public-key=/etc/systemd/tpm2-pcr-initrd-public-key.pem /dev/disk/by-label/root # systemd-cryptenroll --wipe-slot tpm2 --tpm2-device auto --tpm2-pcrs="" --tpm2-public-key=/etc/systemd/tpm2-pcr-system-public-key.pem /dev/disk/by-label/swap
- optionally specify which PCRs to use for the policy:
--tpm2-public-key-pcrs=11
(default 11)
I am happy to incorporate these changes in the wiki page if there are no objections or further items for discussion. I Qgp (talk) 19:35, 23 August 2025 (UTC)
- Hmm, are you sure this is true ? Using this setup, I can decrypt neither the root or swap volumes from the booted system. Cvlc (talk) 18:11, 27 August 2025 (UTC)
- Indeed, the
uki.conf
currently on the wiki page only listsPhases=enter-initrd:leave-initrd
for swap decryption, i.e.sysinit
andready
are not included. Consequently, neither of the two decryptions works in the fully booted system. Root decryption only has to work in the initrd, swap decryption only in the early phase of userspace (systemd). If you wanted swap decryption to work later, you would have to extendPhases
with the sequences includingsysinit
andready
. Qgp (talk) 19:58, 27 August 2025 (UTC)- That's my point, I don't see how using the same signing key breaks the assumption that the specific volume key won't be accessible after the system has switched to a subsequent phase. Isn't the most important thing that the key cannot be released from the booted system? And the example achieves that ? Cvlc (talk) 20:11, 27 August 2025 (UTC)
- The example advertises the separation of the two secrets in the two stages, i.e. initrd and early phase of userspace (systemd). That is not achieved when using the same key. So, if this separation is wanted, the current example is not enough.
- If a secret shared between initrd and early phase of userspace is enough (which is a separate question if it is), the example is overly complicated since a single stance of
[PCRSignature:shared
with both phases, i.e.Phases=enter-initrd enter-initrd:leave-initrd
would be enough. - So, my point is that the current version is misleading in that it advertises separate policies (quote: "For example, one policy can be used for the root volume key, making it accessible only from the initrd, while another policy can be set for the swap encryption key, which needs to be available later in the boot process when the swap is mounted."), while in fact both secrets are accessible in both stages (i.e. initrd and early userspace, but indeed not in the fully booted system). Qgp (talk) 20:22, 27 August 2025 (UTC)
My understanding is that the system state is compared to the signed expected state. I don't really see how which key is used to sign the policy is relevant? Does using the same signing key for the policy really mean the two encrypted volumes share the same volume key ?Cvlc (talk) 20:30, 27 August 2025 (UTC)- Oh ok, you mean since we can provide a valid signature for the set of PCR values for both phases then the TPM would release the key everytime in both cases.
- Then I guess it would better to simplify the PCRsignature= example rather than add a different signing key, unless there's a specific reason to separate them ? My point here was mainly to have a minimal working example with a separate encrypted swap partition, and the volume key not being accessible from the booted system. Cvlc (talk) 20:53, 27 August 2025 (UTC)
- I acted on your suggestion of [PCRSignature:shared], what do you think ? I think it's more relevant to a real life use case than splitting root and swap across different signing keys ? we could also add such an example, but I guess it's covered in the man page already. Cvlc (talk) 10:45, 28 August 2025 (UTC)
- Exactly, the unsealing of the secret relies on the pcr signature, which is checked against the public key (stored in he LUKS header). With a single key, both signatures are valid for both volumes and allow the unsealing.
- Sharing access to secrets between initrd and userspace makes you vulnerable for a commonly known attack:
- you replace the root partition with one of your own for which you know a LUKS password
- the TPM2 decryption of the root partition in the initrd fails
- systemd falls back to asking you for the password - which you know for your own root partition
- you boot into your own root partition with your own userspace and now have access to the secret used for the encryption of the original root partition (userspace in your root partition is under your control, so you can retrieve secrets at any stage or control what is used for PCR extension)
- similarly, you could extract secrets for the decryption of other partitions, be it swap, home, var, ...
- So, a setup with shared access to secrets comes with an impact on security. Of course, one can consider this acceptable, but I think if you want to go for the shared secrets a warning on the security implications is due.
- My preference for a simple solution would be to use the TPM for the encryption/decryption of the root partition only and restrict access to the secret strictly to the initrd. Other partitions can then be decrypted with keys stored on the (encrypted) root partitions (the only exception of that being decryption of swap for resume, which has to happen in the initrd, which will only be supported by the upcoming systemd v258, but then this would be another secret for the initrd).
- In addition, a pointer to the example of properly separated secrets in the example of the ukify manpage could be helpful as well.
- Does this make sense to you? Qgp (talk) 11:51, 28 August 2025 (UTC)
- Makes sense; so maybe simplify the example by removing swap altogether for now (i.e. until systemd 258) ? and point to the ukify manpage for more info ? Cvlc (talk) 17:48, 29 August 2025 (UTC)
- Good for me. Let me know if I can be of any help. Qgp (talk) 12:38, 30 August 2025 (UTC)
- Can you double check my last edit ? also tried to simplify wording a little. Thanks ! Cvlc (talk) 16:31, 30 August 2025 (UTC)
- Looks good to me, thanks for the discussion and the editing :-) Qgp (talk) 18:38, 31 August 2025 (UTC)
- Thanks for pointing in the right direction. Let's see after 258 is released if it ends up working properly for swap. Cvlc (talk) 19:12, 31 August 2025 (UTC)
- Looks good to me, thanks for the discussion and the editing :-) Qgp (talk) 18:38, 31 August 2025 (UTC)
- Can you double check my last edit ? also tried to simplify wording a little. Thanks ! Cvlc (talk) 16:31, 30 August 2025 (UTC)
- Good for me. Let me know if I can be of any help. Qgp (talk) 12:38, 30 August 2025 (UTC)
- Makes sense; so maybe simplify the example by removing swap altogether for now (i.e. until systemd 258) ? and point to the ukify manpage for more info ? Cvlc (talk) 17:48, 29 August 2025 (UTC)
- That's my point, I don't see how using the same signing key breaks the assumption that the specific volume key won't be accessible after the system has switched to a subsequent phase. Isn't the most important thing that the key cannot be released from the booted system? And the example achieves that ? Cvlc (talk) 20:11, 27 August 2025 (UTC)
- Indeed, the