Uses Clevis, not systemd-cryptenroll:
Ubuntu's initramfs is initramfs-tools, which has no systemd-cryptsetup, so
tpm2-device=auto in /etc/crypttab is silently ignored.
| Item | Value |
|---|---|
| LUKS partition | /dev/nvme0n1p3 |
| LUKS UUID | be0ce340-cee1-47bd-aa84-c0d630f56569 |
| Mapper name | cryptroot |
| Layout | LUKS → LVM (ubuntu--vg-ubuntu--lv = /, ubuntu--vg-swap) |
| TPM | Discrete Infineon (IFX) 2.0, firmware 15.23 |
| Kernel | 6.8.0-137-generic |
Discrete TPM, so sealed keys survive BIOS updates, CMOS clear, and battery removal. Only an explicit "Clear TPM" in BIOS or a PCR 7 change breaks unlock.
cat /sys/class/tpm/tpm0/tpm_version_major # 2
ls -l /dev/tpm* # tpm0, tpmrm0
mokutil --sb-state # Secure Boot state
sudo tpm2_getcap properties-fixed | grep -A2 TPM2_PT_MANUFACTURERSubiquity writes the target as dm_crypt-0, but the device is actually opened
as cryptroot. Left unfixed, any update-initramfs run produces an
initramfs with no root unlock config and the next boot drops to busybox.
sudo dmsetup ls --target crypt # authoritative name
cat -A /etc/crypttab # -A exposes stray whitespace/CRsIf they disagree:
sudo sed -i 's/^dm_crypt-0\b/cryptroot/' /etc/crypttabTarget line should read:
cryptroot UUID=be0ce340-cee1-47bd-aa84-c0d630f56569 none luks
Optionally append ,discard for SSD TRIM (minor information leak — reveals
which blocks are unused; generally acceptable on NVMe).
sudo apt install -y clevis clevis-luks clevis-tpm2 clevis-initramfs tpm2-tools
sudo clevis luks bind -d /dev/nvme0n1p3 tpm2 '{"pcr_ids":"7","pcr_bank":"sha256"}'Prompts for the existing passphrase. Adds a new keyslot; passphrase slots stay intact.
Run this exactly once. Each repeat adds another duplicate keyslot.
PCR 7 measures Secure Boot policy — stable across kernel updates and initramfs rebuilds. Don't add PCR 0 or 1; they pick up firmware measurements and break on every BIOS update.
clevis-initramfs does not copy the tss user/group into the initramfs, so the
TPM2 tools fail at early boot and the passphrase prompt appears anyway. This is
the step most guides omit.
sudo tee /etc/initramfs-tools/hooks/tss-user >/dev/null <<'EOF'
#!/bin/sh
PREREQ=""
prereqs() { echo "$PREREQ"; }
case "$1" in prereqs) prereqs; exit 0;; esac
. /usr/share/initramfs-tools/hook-functions
grep '^tss:' /etc/passwd >> "$DESTDIR/etc/passwd"
grep '^tss:' /etc/group >> "$DESTDIR/etc/group"
EOF
sudo chmod +x /etc/initramfs-tools/hooks/tss-usersudo update-initramfs -u -k allMust complete without cryptsetup: WARNING: target 'cryptroot' not found in /etc/crypttab. If that warning appears, go back to step 2 — do not reboot.
The I: The initramfs will attempt to resume from /dev/dm-2 line is unrelated
and harmless (swap on LVM inside the container).
cd /tmp && rm -rf ird && mkdir ird && cd ird
unmkinitramfs /boot/initrd.img-$(uname -r) .
cat main/cryptroot/crypttab # cryptroot UUID=be0ce340-...
grep '^tss:' main/etc/passwd main/etc/group # tss present in both
lsinitramfs /boot/initrd.img-$(uname -r) | grep -E 'tpm2_(unseal|load|createprimary)'
sudo clevis luks list -d /dev/nvme0n1p3 # one tpm2 slot, pcr_ids 7Note: on cryptsetup 2.7 (24.04) the config lives at main/cryptroot/crypttab,
not the older main/conf/conf.d/cryptroot.
If clevis luks list shows more than one TPM2 slot, confirm a passphrase slot
works before removing anything:
sudo cryptsetup luksDump /dev/nvme0n1p3 | grep -E '^ [0-9]+: luks2|^Tokens:|^ [0-9]+: clevis'
sudo cryptsetup luksOpen --test-passphrase --key-slot 0 /dev/nvme0n1p3 && echo "slot 0 OK"Then unbind the extras (-s is the keyslot number; tokens follow
automatically):
sudo clevis luks unbind -d /dev/nvme0n1p3 -s 3
sudo clevis luks unbind -d /dev/nvme0n1p3 -s 5
sudo clevis luks list -d /dev/nvme0n1p3No initramfs rebuild needed — clevis reads tokens off the disk at boot.
Keep the passphrase to hand. If it still prompts:
journalctl -b | grep -iE 'clevis|tpm|cryptroot'| Event | Action |
|---|---|
| Kernel update | None. Hook and clevis are re-included automatically. |
| BIOS/UEFI update | Usually fine (PCR 7). If it prompts for the passphrase, re-seal. |
| Secure Boot key change | Re-seal. |
| TPM firmware update | Re-seal — field upgrades invalidate sealed data. |
| BIOS "Clear TPM" | Re-seal. |
Re-seal:
sudo clevis luks regen -d /dev/nvme0n1p3 -s <slot>Do not flip the BIOS fTPM switch to "AMD CPU fTPM". The platform has both; switching to the Ryzen firmware TPM presents a different TPM with different keys, and unlock fails until re-bound.
sudo clevis luks unbind -d /dev/nvme0n1p3 -s <slot>
sudo rm /etc/initramfs-tools/hooks/tss-user
sudo update-initramfs -u -k allcryptsetup open /dev/nvme0n1p3 cryptroot
exit
Boot continues; fix /etc/crypttab from the running system.
Understand what this does and doesn't buy:
- Ubuntu's initramfs is neither signed nor measured. Someone with physical access can modify it, boot, and the TPM releases the key — PCR 7 is unchanged. This is exactly why Ubuntu hasn't shipped TPM auto-unlock natively.
- With PCR 7 alone under stock Microsoft-signed Secure Boot, any other MS-signed bootloader (a stock Ubuntu live USB) yields the same PCR 7 value.
Net: this protects a stolen drive, not a machine an attacker has hands on.
For a demo box that's a reasonable trade. For anything holding customer data on
a factory floor, the harder path is dracut + systemd-cryptenroll --tpm2-with-pin=yes, or enrolling your own Secure Boot keys and signing a UKI.
Always keep a passphrase keyslot, and store the passphrase somewhere reachable by whoever might have to stand in front of this machine.