From f04b97620059d08b37d9e80ada397e742bb2f311 Mon Sep 17 00:00:00 2001 From: ogelpre Date: Sun, 12 Dec 2021 20:17:14 +0100 Subject: [PATCH] Add init script to load keys MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add new init scripts which allow automatic loading of keys if keylocation property is set to a URI. Reviewed-by: Ahelenia ZiemiaƄska Reviewed-by: Brian Behlendorf Signed-off-by: Benedikt Neuffer Closes #11659 Closes #11662 --- etc/default/zfs.in | 8 ++- etc/init.d/.gitignore | 1 + etc/init.d/Makefile.am | 2 +- etc/init.d/README.md | 11 ++-- etc/init.d/zfs-load-key.in | 131 +++++++++++++++++++++++++++++++++++++ etc/zfs/zfs-functions.in | 9 ++- rpm/generic/zfs.spec.in | 2 + 7 files changed, 155 insertions(+), 9 deletions(-) create mode 100755 etc/init.d/zfs-load-key.in diff --git a/etc/default/zfs.in b/etc/default/zfs.in index 93d98058ecfb..fb4a1b65e348 100644 --- a/etc/default/zfs.in +++ b/etc/default/zfs.in @@ -1,4 +1,4 @@ -# ZoL userland configuration. +# OpenZFS userland configuration. # NOTE: This file is intended for sysv init and initramfs. # Changing some of these settings may not make any difference on @@ -10,6 +10,12 @@ # Anything else will be interpreted as unset. # shellcheck disable=SC2034 +# Run `zfs load-key` during system start? +ZFS_LOAD_KEY='yes' + +# Run `zfs unload-key` during system stop? +ZFS_UNLOAD_KEY='no' + # Run `zfs mount -a` during system start? ZFS_MOUNT='yes' diff --git a/etc/init.d/.gitignore b/etc/init.d/.gitignore index 43a673d55343..b3402f831806 100644 --- a/etc/init.d/.gitignore +++ b/etc/init.d/.gitignore @@ -1,4 +1,5 @@ zfs-import +zfs-load-key zfs-mount zfs-share zfs-zed diff --git a/etc/init.d/Makefile.am b/etc/init.d/Makefile.am index f93af1fd77e0..658623fda4aa 100644 --- a/etc/init.d/Makefile.am +++ b/etc/init.d/Makefile.am @@ -3,7 +3,7 @@ include $(top_srcdir)/config/Shellcheck.am EXTRA_DIST += README.md -init_SCRIPTS = zfs-import zfs-mount zfs-share zfs-zed +init_SCRIPTS = zfs-import zfs-load-key zfs-mount zfs-share zfs-zed SUBSTFILES += $(init_SCRIPTS) diff --git a/etc/init.d/README.md b/etc/init.d/README.md index c14b01937db2..f417b24c5923 100644 --- a/etc/init.d/README.md +++ b/etc/init.d/README.md @@ -42,14 +42,16 @@ INSTALLING INIT SCRIPT LINKS To setup the init script links in /etc/rc?.d manually on a Debian GNU/Linux (or derived) system, run the following commands (the order is important!): - update-rc.d zfs-import start 07 S . stop 07 0 1 6 . - update-rc.d zfs-mount start 02 2 3 4 5 . stop 06 0 1 6 . - update-rc.d zfs-zed start 07 2 3 4 5 . stop 08 0 1 6 . - update-rc.d zfs-share start 27 2 3 4 5 . stop 05 0 1 6 . + update-rc.d zfs-import start 07 S . stop 07 0 1 6 . + update-rc.d zfs-load-key start 02 2 3 4 5 . stop 06 0 1 6 . + update-rc.d zfs-mount start 02 2 3 4 5 . stop 06 0 1 6 . + update-rc.d zfs-zed start 07 2 3 4 5 . stop 08 0 1 6 . + update-rc.d zfs-share start 27 2 3 4 5 . stop 05 0 1 6 . To do the same on RedHat, Fedora and/or CentOS: chkconfig zfs-import + chkconfig zfs-load-key chkconfig zfs-mount chkconfig zfs-zed chkconfig zfs-share @@ -57,6 +59,7 @@ INSTALLING INIT SCRIPT LINKS On Gentoo: rc-update add zfs-import boot + rc-update add zfs-load-key boot rc-update add zfs-mount boot rc-update add zfs-zed default rc-update add zfs-share default diff --git a/etc/init.d/zfs-load-key.in b/etc/init.d/zfs-load-key.in new file mode 100755 index 000000000000..2f8deffdc809 --- /dev/null +++ b/etc/init.d/zfs-load-key.in @@ -0,0 +1,131 @@ +#!@DEFAULT_INIT_SHELL@ +# +# zfs-load-key This script will load/unload the zfs filesystems keys. +# +# chkconfig: 2345 06 99 +# description: This script will load or unload the zfs filesystems keys during +# system boot/shutdown. Only filesystems with key path set +# in keylocation property. See the zfs(8) man page for details. +# probe: true +# +### BEGIN INIT INFO +# Provides: zfs-load-key +# Required-Start: $local_fs zfs-import +# Required-Stop: $local_fs zfs-import +# Default-Start: 2 3 4 5 +# Default-Stop: 0 1 6 +# X-Start-Before: zfs-mount +# X-Stop-After: zfs-zed +# Short-Description: Load ZFS keys for filesystems and volumes +# Description: Run the `zfs load-key` or `zfs unload-key` commands. +### END INIT INFO +# +# Released under the 2-clause BSD license. +# +# This script is based on debian/zfsutils.zfs.init from the +# Debian GNU/kFreeBSD zfsutils 8.1-3 package, written by Aurelien Jarno. + +# Source the common init script +. @sysconfdir@/zfs/zfs-functions + +# ---------------------------------------------------- + +do_depend() +{ + # bootmisc will log to /var which may be a different zfs than root. + before bootmisc logger zfs-mount + + after zfs-import sysfs + keyword -lxc -openvz -prefix -vserver +} + +# 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 +} + +# Unload keys for all datasets/filesystems +do_unload_keys() +{ + zfs_log_begin_msg "Unload ZFS filesystem(s) key" + + "$ZFS" list -Ho name,encryptionroot,keystatus | sed '1!G;h;$!d' | + while IFS=" " read -r name encryptionroot keystatus; do + if [ "$encryptionroot" != "-" ] && + [ "$name" = "$encryptionroot" ] && + [ "$keystatus" = "available" ] + then + zfs_action "Unload key for $encryptionroot" \ + "$ZFS" unload-key "$encryptionroot" + fi + done + + zfs_log_end_msg 0 + + return 0 +} + +do_start() +{ + check_boolean "$ZFS_LOAD_KEY" || exit 0 + + check_module_loaded "zfs" || exit 0 + + do_load_keys +} + +do_stop() +{ + check_boolean "$ZFS_UNLOAD_KEY" || exit 0 + + check_module_loaded "zfs" || exit 0 + + do_unload_keys +} + +# ---------------------------------------------------- + +if [ ! -e /sbin/openrc-run ] +then + case "$1" in + start) + do_start + ;; + stop) + do_stop + ;; + force-reload|condrestart|reload|restart|status) + # no-op + ;; + *) + [ -n "$1" ] && echo "Error: Unknown command $1." + echo "Usage: $0 {start|stop}" + exit 3 + ;; + esac + + exit $? +else + # Create wrapper functions since Gentoo don't use the case part. + depend() { do_depend; } + start() { do_start; } + stop() { do_stop; } +fi diff --git a/etc/zfs/zfs-functions.in b/etc/zfs/zfs-functions.in index a27d4c6cb073..30441dc35d4b 100644 --- a/etc/zfs/zfs-functions.in +++ b/etc/zfs/zfs-functions.in @@ -1,5 +1,5 @@ -# This is a script with common functions etc used by zfs-import, zfs-mount, -# zfs-share and zfs-zed. +# This is a script with common functions etc used by zfs-import, zfs-load-key, +# zfs-mount, zfs-share and zfs-zed. # # It is _NOT_ to be called independently # @@ -92,6 +92,8 @@ ZPOOL="@sbindir@/zpool" ZPOOL_CACHE="@sysconfdir@/zfs/zpool.cache" # Sensible defaults +ZFS_LOAD_KEY='yes' +ZFS_UNLOAD_KEY='no' ZFS_MOUNT='yes' ZFS_UNMOUNT='yes' ZFS_SHARE='yes' @@ -104,7 +106,8 @@ fi # ---------------------------------------------------- -export ZFS ZED ZPOOL ZPOOL_CACHE ZFS_MOUNT ZFS_UNMOUNT ZFS_SHARE ZFS_UNSHARE +export ZFS ZED ZPOOL ZPOOL_CACHE ZFS_LOAD_KEY ZFS_UNLOAD_KEY ZFS_MOUNT ZFS_UNMOUNT \ + ZFS_SHARE ZFS_UNSHARE zfs_action() { diff --git a/rpm/generic/zfs.spec.in b/rpm/generic/zfs.spec.in index 4a37ae8ce1d5..25beadce7c1f 100644 --- a/rpm/generic/zfs.spec.in +++ b/rpm/generic/zfs.spec.in @@ -424,6 +424,7 @@ fi %else if [ -x /sbin/chkconfig ]; then /sbin/chkconfig --add zfs-import + /sbin/chkconfig --add zfs-load-key /sbin/chkconfig --add zfs-mount /sbin/chkconfig --add zfs-share /sbin/chkconfig --add zfs-zed @@ -454,6 +455,7 @@ fi %else if [ "$1" = "0" -o "$1" = "remove" ] && [ -x /sbin/chkconfig ]; then /sbin/chkconfig --del zfs-import + /sbin/chkconfig --del zfs-load-key /sbin/chkconfig --del zfs-mount /sbin/chkconfig --del zfs-share /sbin/chkconfig --del zfs-zed