Why is the LUKS partition mounted without asking for a passphrase

cryptsetupluksraspbian

On my system, I have two encrypted disks:

  1. crypt containing the root partition of raspbian stretch
  2. usb-crypt is an external usb disk. LVM is used on that disk.

Both disks are protected using the same passphrase, but the master key is different according to "cryptsetup luksDump". Neither of the two disks are configured using a key file (only one key slot is used for each LUKS container).

When the system is booting, it is asking for the passphrase of "crypt", but usb-crypt is automatically mounted without asking for a passphrase. Note: I started with an unencrypted root partition, and with that setup, I was asked for the passphrase of usb-crypt during boot.

Here is the detailed setup:

$ sudo dmsetup ls --target crypt
crypt   (254, 0)
usb-crypt       (254, 1)

$ sudo cat /etc/fstab
/dev/mmcblk0p1  /boot           vfat    defaults          0       2
/dev/mapper/crypt  /            ext4    defaults,noatime  0       1
# ...
UUID=b9fb061f-0877-4d2c-bd3c-9c155b8f88a5       /mountpoint       ext4            rw,auto                 0       0

$ sudo cat /etc/crypttab 
# <target name> <source device>         <key file>      <options>
crypt   /dev/mmcblk0p2  none    luks
usb-crypt       UUID=31fb8df7-6148-4408-90a2-93b8ec752fa0       none    luks

While having only to type the passphrase once is convenient, I am surprised seeing this behaviour. I'd have expected to be asked for both passphrases.

Is this related to using the same passphrase on both disks? Or is the master key of the usb disk automatically saved somewhere in the encrypted root partition of "crypt"? I'd appreciate if someone could explain what's going on here and maybe give some hints to relevant log files, etc.

Thanks in advance!

Best Answer

Depends on what the init script that asks the password of you is doing with it.

If it's systemd, it might just be a feature. systemd-ask-password comes with a cache functionality that might be responsible.

https://www.freedesktop.org/software/systemd/man/systemd-ask-password.html

--accept-cached

    If passed, accept cached passwords, i.e. passwords previously entered.

--multiple

    When used in conjunction with --accept-cached accept multiple passwords.
    This will output one password per line.

In this fashion it would first try the passwords you already entered, and only ask for another passwords if that didn't work.

The downside of such an idea is that checking a password takes 1 second of CPU time with LUKS, so if you had a lot of LUKS containers, these attempts might slow you down. But most people have only one or two and it's actually not uncommon for them to use the same passphrase.

I actually couldn't locate the source code specifically responsible for this, so the above is only conjecture and I have no idea if this is a feature you could choose to disable somehow.


Found what seems to be the responsible code, see it here on Github.

There's a for loop that starts with tries = 0 and increments tries by one each iteration.

This loop calls get_password() with bool accept_cached set to true if tries == 0 && !arg_verify. So if there are already passwords cached in the first iteration of the loop, it will just return the cached passwords. If those don't work, next iteration with tries == 1 sets accept_cached to false and only then it will ask you to provide another passphrase to try with.

The list of passwords is passed on to attach_luks_or_plain(). This will be the previously cached password(s) in the first iteration, and the single new password in all following ones, so it won't re-try previously tried passwords (unless perhaps if you keep typing in the same one).

As for keeping passwords plaintext in memory, the list of passwords is declared as a _cleanup_strv_free_erase_ char **passwords = NULL; so that at least makes it sounds like cleanup will be taken care of properly at some point.

Keys are always in memory somewhere, that much can't be helped, crypt needs masterkey to work, as long as the container is open, you can always see it with dmsetup table --showkeys.


It seems like you normally have arg_tries = 3 three attempts to enter a working passphrase, but if you have multiple containers and the cached passwords didn't work, it will only give you two tries to enter the passphrase, since the cached password attempt already counts as the first try. I have no encrypted systemd machine to test if this is true or I'm just misreading the code somewhere.

Related Question