From owner-dev-commits-src-branches@freebsd.org  Sun Aug 22 14:54:20 2021
Return-Path: <owner-dev-commits-src-branches@freebsd.org>
Delivered-To: dev-commits-src-branches@mailman.nyi.freebsd.org
Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2610:1c1:1:606c::19:1])
 by mailman.nyi.freebsd.org (Postfix) with ESMTP id B1D416567C4;
 Sun, 22 Aug 2021 14:54:20 +0000 (UTC) (envelope-from git@FreeBSD.org)
Received: from mxrelay.nyi.freebsd.org (mxrelay.nyi.freebsd.org
 [IPv6:2610:1c1:1:606c::19:3])
 (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)
 key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256
 client-signature RSA-PSS (4096 bits) client-digest SHA256)
 (Client CN "mxrelay.nyi.freebsd.org", Issuer "R3" (verified OK))
 by mx1.freebsd.org (Postfix) with ESMTPS id 4Gsz0r4TkSz3mF6;
 Sun, 22 Aug 2021 14:54:20 +0000 (UTC) (envelope-from git@FreeBSD.org)
Received: from gitrepo.freebsd.org (gitrepo.freebsd.org
 [IPv6:2610:1c1:1:6068::e6a:5])
 (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)
 key-exchange X25519 server-signature RSA-PSS (4096 bits) server-digest SHA256)
 (Client did not present a certificate)
 by mxrelay.nyi.freebsd.org (Postfix) with ESMTPS id 818EA22A7E;
 Sun, 22 Aug 2021 14:54:20 +0000 (UTC) (envelope-from git@FreeBSD.org)
Received: from gitrepo.freebsd.org ([127.0.1.44])
 by gitrepo.freebsd.org (8.16.1/8.16.1) with ESMTP id 17MEsKEN090854;
 Sun, 22 Aug 2021 14:54:20 GMT (envelope-from git@gitrepo.freebsd.org)
Received: (from git@localhost)
 by gitrepo.freebsd.org (8.16.1/8.16.1/Submit) id 17MEsK9m090853;
 Sun, 22 Aug 2021 14:54:20 GMT (envelope-from git)
Date: Sun, 22 Aug 2021 14:54:20 GMT
Message-Id: <202108221454.17MEsK9m090853@gitrepo.freebsd.org>
To: src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org,
 dev-commits-src-branches@FreeBSD.org
From: Allan Jude <allanjude@FreeBSD.org>
Subject: git: e81b2348d210 - stable/13 - Add zfskeys rc.d script for
 auto-loading encryption keys
MIME-Version: 1.0
Content-Type: text/plain; charset=utf-8
Content-Transfer-Encoding: 8bit
X-Git-Committer: allanjude
X-Git-Repository: src
X-Git-Refname: refs/heads/stable/13
X-Git-Reftype: branch
X-Git-Commit: e81b2348d2101f33043e4a4ab3e24f4d69bac073
Auto-Submitted: auto-generated
X-BeenThere: dev-commits-src-branches@freebsd.org
X-Mailman-Version: 2.1.34
Precedence: list
List-Id: Commits to the stable branches of the FreeBSD src repository
 <dev-commits-src-branches.freebsd.org>
List-Unsubscribe: <https://lists.freebsd.org/mailman/options/dev-commits-src-branches>, 
 <mailto:dev-commits-src-branches-request@freebsd.org?subject=unsubscribe>
List-Archive: <http://lists.freebsd.org/pipermail/dev-commits-src-branches/>
List-Post: <mailto:dev-commits-src-branches@freebsd.org>
List-Help: <mailto:dev-commits-src-branches-request@freebsd.org?subject=help>
List-Subscribe: <https://lists.freebsd.org/mailman/listinfo/dev-commits-src-branches>, 
 <mailto:dev-commits-src-branches-request@freebsd.org?subject=subscribe>
X-List-Received-Date: Sun, 22 Aug 2021 14:54:20 -0000

The branch stable/13 has been updated by allanjude:

URL: https://cgit.FreeBSD.org/src/commit/?id=e81b2348d2101f33043e4a4ab3e24f4d69bac073

commit e81b2348d2101f33043e4a4ab3e24f4d69bac073
Author:     Eirik Øverby <ltning-freebsd@anduin.net>
AuthorDate: 2021-07-28 16:11:35 +0000
Commit:     Allan Jude <allanjude@FreeBSD.org>
CommitDate: 2021-08-22 14:53:21 +0000

    Add zfskeys rc.d script for auto-loading encryption keys
    
    ZFS in 13 supports encryption, but for the use case where keys are
    available in plaintext on disk there is no mechanism for automatically
    loading keys on startup.
    
    This script will, by default, look for any dataset with encryption and
    keylocation prefixed with file://. It will attempt to unlock, timing
    out after 10 seconds for each dataset found.
    User can optionally specify explicitly which datasets to attempt to
    unlock.
    
    Also supports (optionally by force) unmounting filesystems and unloading
    associated keys.
    
    Sponsored by:   Modirum
    Differential Revision:  https://reviews.freebsd.org/D30015
    
    (cherry picked from commit 33ff39796ffe469a764e485ac49c31700a51fd6f)
---
 libexec/rc/rc.d/zfskeys | 119 ++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 119 insertions(+)

diff --git a/libexec/rc/rc.d/zfskeys b/libexec/rc/rc.d/zfskeys
new file mode 100755
index 000000000000..c558eb3af5d7
--- /dev/null
+++ b/libexec/rc/rc.d/zfskeys
@@ -0,0 +1,119 @@
+#!/bin/sh
+
+# PROVIDE: zfskeys
+# REQUIRE: zpool
+# BEFORE: zfs zvol
+
+. /etc/rc.subr
+
+name="zfskeys"
+desc="Load dataset keys"
+rcvar="zfskeys_enable"
+extra_commands="status"
+start_cmd="load_zfs_keys"
+stop_cmd="unload_zfs_keys"
+status_cmd="status_zfs_keys"
+required_modules="zfs"
+
+# Note that zfskeys_datasets must have any character found in IFS escaped.
+# Forcibly unmounting/unloading only applies to filesystems; ignored for zvols.
+: ${zfskeys_datasets:=''}
+: ${zfskeys_timeout:=10}
+: ${zfskeys_unload_force:='NO'}
+
+encode_args()
+{
+    shift && [ $# -gt 0 ] && printf "%s\0" "$@" | b64encode -r -
+}
+
+list_datasets()
+{
+    if [ "$zfskeys_args" ]; then
+        echo "$zfskeys_args" | b64decode -r |
+            xargs -0 zfs get -H -s local -o value,name keylocation
+    elif [ ! "$zfskeys_datasets" ]; then
+        zfs get -H -t filesystem,volume -s local -o value,name keylocation
+    else
+        echo "$zfskeys_datasets" | xargs -n 1 zfs get -H -s local \
+            -o value,name keylocation
+    fi
+}
+
+unlock_fs()
+{
+    local fs="$1"
+    local kl="$2"
+    local k="${kl##file://}"
+
+    if [ "$k" ] && [ -f "$k" ] && [ -s "$k" ] && [ -r "$k" ]; then
+        if [ "$(zfs get -Ho value keystatus "$fs")" = 'available' ]; then
+            echo "Key already loaded for $fs."
+        elif keytest=$(zfs load-key -n -L "$kl" "$fs" 2>&1); then
+            echo "Loading key for $fs from $kl.."
+            if ! keyload=$(timeout $zfskeys_timeout zfs load-key -L "$kl" "$fs" 2>&1) ; then
+                if [ $? -eq 124 ]; then
+                    echo "Timed out loading key from $kl for $fs"
+                else
+                    echo "Failed to load key from $kl for $fs:"
+                    echo "$keyload"
+                fi
+            fi
+        else
+            echo "Could not verify key from $kl for $fs:"
+            echo "$keytest"
+        fi
+    else
+        echo "Key file $k not found, empty or unreadable. Skipping $fs.."
+    fi
+}
+
+lock_fs()
+{
+    local fs=$1
+
+    if [ "$(zfs get -Ho value mounted "$fs")" = 'yes' ]; then
+        if checkyesno zfskeys_unload_force ; then
+            zfs unmount -f "$fs" && echo "Forcibly unmounted $fs."
+        else
+            zfs unmount "$fs" && echo "Unmounted $fs."
+        fi
+    fi
+    if [ "$?" -ne 0 ]; then
+        echo "Unmount failed for $fs"
+    elif [ "$(zfs get -Ho value keystatus "$fs")" = 'available' ]; then
+        zfs unload-key "$fs" && echo "Unloaded key for $fs."
+    else
+        echo "No key loaded for $fs."
+    fi
+}
+
+status_zfs_keys()
+{
+    local IFS=$(printf "\t")
+
+    list_datasets | while read kl fs ; do
+        echo "$fs: $(zfs get -Ho value keystatus "$fs")"
+    done
+}
+
+load_zfs_keys()
+{
+    local IFS=$(printf "\t")
+
+    list_datasets | while read kl fs ; do
+        unlock_fs "$fs" "$kl"
+    done
+}
+
+unload_zfs_keys()
+{
+    local IFS=$(printf "\t")
+
+    list_datasets | while read kl fs ; do
+        lock_fs "$fs"
+    done
+}
+
+zfskeys_args=$(encode_args "$@")
+load_rc_config $name
+run_rc_command "$1"