zfs icon indicating copy to clipboard operation
zfs copied to clipboard

Support non-automatic loading of keys for encrypted datasets on boot

Open thedeadliestcatch opened this issue 1 year ago • 9 comments
trafficstars

Describe the feature would like to see added to OpenZFS

At the moment, all encrypted datasets are mounted/have their keys loaded automatically on boot time. This interrupts boot when the key is not available or a passphrase is required to "open" the dataset.

Ideally, some property should be added, ex. "noauto", so that the key is only manually loaded and the dataset is ignored during boot.

How will this feature improve OpenZFS?

It will prevent systems with encryption-at-rest from having the boot process interrupted when the keys are loaded via a manual or more complex system that depends on external tooling.

Additional context

This can be observed by creating a password-based encrypted dataset in a system coexisting with datasets encrypted using key files.

thedeadliestcatch avatar Jan 30 '24 18:01 thedeadliestcatch

Is it enough to set canmount=off or canmount=noauto on the datasets you don't want mounted?

robn avatar Jan 31 '24 09:01 robn

It doesn't seem like that helps @robn , the loading of the keys is not done via mount triggers.

thedeadliestcatch avatar Feb 02 '24 19:02 thedeadliestcatch

To document this further, for example on Ubuntu (development release):

There is a global setting in /etc/default/zfs:

# Run `zfs load-key` during system start?
ZFS_LOAD_KEY='yes'

From /etc/init.d/zfs-load-key:

# Load keys for all datasets/filesystems
do_load_keys()
{
	zfs_log_begin_msg "Load ZFS filesystem(s) keys"

	"$ZFS" list -Ho name,encryptionroot,keystatus,keylocation |
	    while IFS="	" read -r name encryptionroot keystatus keylocation; do
		if [ "$encryptionroot" != "-" ] &&
			[ "$name" = "$encryptionroot" ] &&
			[ "$keystatus" = "unavailable" ] &&
			[ "$keylocation" != "prompt" ] &&
			[ "$keylocation" != "none" ]
		then
			zfs_action "Load key for $encryptionroot" \
			    "$ZFS" load-key "$encryptionroot"
		fi
	done

	zfs_log_end_msg 0

	return 0
}

One would assume that the key loading is only automated for datasets with keylocation != prompt.

I will have to copy over the scripts from another Debian system to verify, since the above is not the stable release. I will then write another comment or update this one. I can confirm though that with a dataset that has keylocation=prompt, for a Debian based system (replicated also with Proxmox, latest stable release), init process is halted waiting for the user input.

I will report back.

thedeadliestcatch avatar Feb 02 '24 19:02 thedeadliestcatch

Right, I see. That's OpenZFS' etc/init.d/zfs-load-key.in, which of course distros are under no obligation to use but at least we could make some change if necessary.

It looks like that's doing load-key if keylocation is not prompt or none, that is, it asserts a real location. Is that right?

If that's the case, and you do have a manual/external process, I think probably you should set keylocation=none and then in your separate process, use zfs load-key -L <keylocation> to specify the location directly at the proper time. It seems like it doesn't make a lot of sense to add a special property to say "don't do this thing I asked you to do".

If that's not the case, well, tell me more!

robn avatar Feb 03 '24 04:02 robn

Let me revisit the issue this week. I believe some Debian based systems are rolling out with an incomplete set of scripts. The OpenZFS zfs-load-key.in behavior is actually spot on to avoid prompt-based key loading.

thedeadliestcatch avatar Feb 07 '24 08:02 thedeadliestcatch

We currently run encrypted zfs for the rpool (mirrorred) and data pools (RAIDZ2). The rpools are password based and will wait at boot time for the password, and these can be loaded remotely using dropbear-intramfs. The datapools are using binary keys and are started using a systemd service which waits for the binary key to be loaded. None of this required any special magic. Simply systemctl disable zfs-load-key.service and setup your own systemd services for what you want to load when...

f1d094 avatar Mar 01 '24 23:03 f1d094

Our systems are currently debian bookworm with a couple Ubuntu systems, but each is otherwise similarly configured.

f1d094 avatar Mar 01 '24 23:03 f1d094

It's not possible to set keylocation=none on an encrypted filesystem:

# zfs set keylocation=none zroot/enc
cannot set property for 'zroot/enc': keylocation must not be 'none' for encrypted datasets

Setting it to canmount=noauto would be my preferred way to skip the automatic loading of the filesystem at boot, but on second thought this might make the zfs mount -a command ambiguous.

Currently, any linux distribution that loads all the filesystems with zfs load-key -a cannot be told to skip any individual filesystem. I'd be very happy if this can be overridden from zfs in some way - I want a prompt for some filesystems, but not load them at boot time.

voidzero avatar Jun 08 '24 10:06 voidzero

I just discovered that NixOS has the following setting: boot.zfs.requestEncryptionCredentials

That really made my day.

voidzero avatar Jun 12 '24 20:06 voidzero