dracut/0001-crypt-gpg-For-GnuPG-2.1-support-OpenPGP-smartcards.patch
Harald Hoyer 3763a85444 dracut 045-18.git20170515
- git snapshot
2017-05-15 14:31:19 +02:00

99 lines
4.4 KiB
Diff
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

From 2a1723ed83accdcb6871e12c722c03dac35dc35e Mon Sep 17 00:00:00 2001
From: Moritz Maxeiner <moritz@ucworks.org>
Date: Fri, 10 Jul 2015 15:38:59 +0200
Subject: [PATCH] crypt-gpg: For GnuPG >= 2.1 support OpenPGP smartcards
---
modules.d/91crypt-gpg/crypt-gpg-lib.sh | 34 ++++++++++++++++++++++++++++++++--
modules.d/91crypt-gpg/module-setup.sh | 17 +++++++++++++++++
2 files changed, 49 insertions(+), 2 deletions(-)
diff --git a/modules.d/91crypt-gpg/crypt-gpg-lib.sh b/modules.d/91crypt-gpg/crypt-gpg-lib.sh
index 5c7ea855..b85ed2b8 100755
--- a/modules.d/91crypt-gpg/crypt-gpg-lib.sh
+++ b/modules.d/91crypt-gpg/crypt-gpg-lib.sh
@@ -4,7 +4,7 @@ command -v ask_for_password >/dev/null || . /lib/dracut-crypt-lib.sh
# gpg_decrypt mnt_point keypath keydev device
#
-# Decrypts encrypted symmetrically key to standard output.
+# Decrypts symmetrically encrypted (password or OpenPGP smartcard) key to standard output.
#
# mnt_point - mount point where <keydev> is already mounted
# keypath - GPG encrypted key path relative to <mnt_point>
@@ -22,10 +22,40 @@ gpg_decrypt() {
mkdir -m 0700 -p "$gpghome"
+ # Setup GnuPG home and gpg-agent for usage of OpenPGP smartcard.
+ # This requires GnuPG >= 2.1, as it uses the new ,,pinentry-mode´´
+ # feature, which - when set to ,,loopback´´ - allows us to pipe
+ # the smartcard's pin to GnuPG (instead of using a normal pinentry
+ # program needed with GnuPG < 2.1), making for uncomplicated
+ # integration with the existing codebase.
+ local useSmartcard="0"
+ local gpgMajorVersion="$(gpg --version | sed -n 1p | sed -n -r -e 's|.* ([0-9]*).*|\1|p')"
+ local gpgMinorVersion="$(gpg --version | sed -n 1p | sed -n -r -e 's|.* [0-9]*\.([0-9]*).*|\1|p')"
+
+ if [ "${gpgMajorVersion}" -ge 2 ] && [ "${gpgMinorVersion}" -ge 1 ] \
+ && [ -f /root/crypt-public-key.gpg ] && getargbool 1 rd.luks.smartcard ; then
+ useSmartcard="1"
+ echo "allow-loopback-pinentry" >> "$gpghome/gpg-agent.conf"
+ GNUPGHOME="$gpghome" gpg-agent --quiet --daemon
+ GNUPGHOME="$gpghome" gpg --quiet --no-tty --import < /root/crypt-public-key.gpg
+ local smartcardSerialNumber="$(GNUPGHOME=$gpghome gpg --no-tty --card-status \
+ | sed -n -r -e 's|Serial number.*: ([0-9]*)|\1|p' | tr -d '\n')"
+ if [ -n "${smartcardSerialNumber}" ]; then
+ inputPrompt="PIN (OpenPGP card ${smartcardSerialNumber})"
+ fi
+ GNUPGHOME="$gpghome" gpg-connect-agent 1>/dev/null learn /bye
+ opts="$opts --pinentry-mode=loopback"
+ fi
+
ask_for_password \
--cmd "gpg $opts --decrypt $mntp/$keypath" \
- --prompt "Password ($keypath on $keydev for $device)" \
+ --prompt "${inputPrompt:-Password ($keypath on $keydev for $device)}" \
--tries 3 --tty-echo-off
+ # Clean up the smartcard gpg-agent
+ if [ "${useSmartcard}" == "1" ]; then
+ GNUPGHOME="$gpghome" gpg-connect-agent 1>/dev/null killagent /bye
+ fi
+
rm -rf -- "$gpghome"
}
diff --git a/modules.d/91crypt-gpg/module-setup.sh b/modules.d/91crypt-gpg/module-setup.sh
index d328c04c..1323a181 100755
--- a/modules.d/91crypt-gpg/module-setup.sh
+++ b/modules.d/91crypt-gpg/module-setup.sh
@@ -5,6 +5,12 @@
check() {
require_binaries gpg || return 1
+ if [ -f "${initdir}/root/crypt-public-key.gpg" ]; then
+ require_binaries gpg-agent || return 1
+ require_binaries gpg-connect-agent || return 1
+ require_binaries /usr/libexec/scdaemon || return 1
+ fi
+
return 255
}
@@ -17,4 +23,15 @@ depends() {
install() {
inst_multiple gpg
inst "$moddir/crypt-gpg-lib.sh" "/lib/dracut-crypt-gpg-lib.sh"
+
+ local gpgMajorVersion="$(gpg --version | sed -n 1p | sed -n -r -e 's|.* ([0-9]*).*|\1|p')"
+ local gpgMinorVersion="$(gpg --version | sed -n 1p | sed -n -r -e 's|.* [0-9]*\.([0-9]*).*|\1|p')"
+ if [ "${gpgMajorVersion}" -ge 2 ] && [ "${gpgMinorVersion}" -ge 1 ] && [ -f /etc/dracut.conf.d/crypt-public-key.gpg ]; then
+ inst_multiple gpg-agent
+ inst_multiple gpg-connect-agent
+ inst_multiple /usr/libexec/scdaemon || derror "crypt-gpg: gnugpg with scdaemon required for smartcard support in the initramfs"
+ cp "/etc/dracut.conf.d/crypt-public-key.gpg" "${initdir}/root/"
+ elif [ -f /etc/dracut.conf.d/crypt-public-key.gpg ]; then
+ dwarning "crypt-gpg: gnupg >= 2.1 required for smartcard support in the initramfs"
+ fi
}