Skip to content

Instantly share code, notes, and snippets.

@Birch-san
Last active February 20, 2025 00:12
Show Gist options
  • Save Birch-san/ec0c765fc497ce0c36a4c3cbf2d2ff22 to your computer and use it in GitHub Desktop.
Save Birch-san/ec0c765fc497ce0c36a4c3cbf2d2ff22 to your computer and use it in GitHub Desktop.
ZFS home encryption Ubuntu 22.10

I started with a basic Ubuntu 22.10 installation, where I chose in the installer to use ZFS as my volume manager.
I wanted to encrypt my home folder.

I followed the article (and comments, including Christoph Hagemann's) from:
https://talldanestale.dk/2020/04/06/zfs-and-homedir-encryption/

To achieve:

  • Home directory (a ZFS rpool mount) is encrypted
  • You are only prompted for password if you are trying to login to that user
    • So PC can boot fine to login screen without intervention
  • Password prompt authenticates you as the user and decrypts the home folder's rpool
  • SSH users get the same experience as physical users
    • You can power on the PC, then SSH in
  • Once rpool is unlocked: subsequent SSH login can use key exchange instead of password
  • Once all sessions log out: rpool is encrypted and unmounted again
@adamarbour
Copy link

adamarbour commented Jun 14, 2024

FYI - I modified this a bit to use only pam no need for a service. I made the following modifications. This unlocks and locks whenever I logout.

file: /sbin/mount-zfs-homedir

#!/bin/bash

set -eu

USER=$PAM_USER
PASS=$(cat -)
TYPE=$PAM_TYPE
SESSION_COUNT=$(ps -u $USER -o user= | wc -l)

zfs get -s local -H -o name,value canmount | while read volname canmount; do
    [[ $canmount = 'noauto' ]] || continue
    
    user=$(zfs get -s local -H -o value void.automount.homedir:user $volname) # NOTE: I created my own property
    [[ $user = $USER ]] || continue

    if [ "$TYPE" = "auth" ]; then
        MOUNTPOINT="$(zfs get -o value -H -r mountpoint "$volname")"
        findmnt "$MOUNTPOINT" && continue

        zfs load-key "$volname" <<< "$PASS" || continue
        zfs mount "$volname" || true
    fi

    if [ "$TYPE" = "close_session" ] && [ "$SESSION_COUNT" -eq 0 ]; then
        zfs unmount "$volname" || continue
        zfs unload-key "$volname" || true
    fi
done

file: /etc/pam.d/system-login
NOTE: This might be different on other systems

....
auth         optional    pam_exec.so    expose_authtok    /sbin/mount-zfs-home-dir
...
...
...
session    optional    pam_exec.so    /sbin/mount-zfs-homedir
...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment