mirror of
https://github.com/linuxboot/heads.git
synced 2024-12-19 21:17:55 +00:00
This commit is contained in:
parent
d06ba0a851
commit
f99944abe5
@ -1,5 +1,6 @@
|
|||||||
# Configuration for a x230 running Qubes OS
|
# Configuration for a x230 running Qubes OS
|
||||||
BOARD=x230
|
BOARD=x230
|
||||||
|
|
||||||
CONFIG_CRYPTSETUP=y
|
CONFIG_CRYPTSETUP=y
|
||||||
CONFIG_FLASHROM=y
|
CONFIG_FLASHROM=y
|
||||||
CONFIG_GPG=y
|
CONFIG_GPG=y
|
||||||
@ -15,3 +16,9 @@ CONFIG_XEN=y
|
|||||||
|
|
||||||
CONFIG_LINUX_USB=y
|
CONFIG_LINUX_USB=y
|
||||||
CONFIG_LINUX_E1000E=y
|
CONFIG_LINUX_E1000E=y
|
||||||
|
|
||||||
|
CONFIG_BOOTSCRIPT=/bin/qubes-init
|
||||||
|
|
||||||
|
# Disks encrypted by the TPM LUKS key
|
||||||
|
CONFIG_QUBES_BOOT_DEV="/dev/sda1"
|
||||||
|
CONFIG_QUBES_DEVS="/dev/sda2 /dev/sda3 /dev/sda5"
|
||||||
|
18
initrd/bin/mount-usb
Executable file
18
initrd/bin/mount-usb
Executable file
@ -0,0 +1,18 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
# Mount a USB device
|
||||||
|
die() { echo >&2 "!!!!! $@"; exit 1; }
|
||||||
|
|
||||||
|
if ! lsmod | grep -q ehci_hcd; then
|
||||||
|
insmod /lib/modules/ehci-hcd.ko \
|
||||||
|
|| die "ehci_hcd: module load failed"
|
||||||
|
fi
|
||||||
|
if ! lsmod | grep -q ehci_pci; then
|
||||||
|
insmod /lib/modules/ehci-pci.ko \
|
||||||
|
|| die "ehci_pci: module load failed"
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ ! -d /media ]; then
|
||||||
|
mkdir /media
|
||||||
|
fi
|
||||||
|
|
||||||
|
mount -o ro $1 /media
|
65
initrd/bin/qubes-init
Executable file
65
initrd/bin/qubes-init
Executable file
@ -0,0 +1,65 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
# Boot a Qubes installation that has already been setup.
|
||||||
|
# This depends on the PCR 4 being "normal-boot":
|
||||||
|
# f8fa3b6e32e7c6fe04c366e74636e505b28f3b0d
|
||||||
|
# which is only set if the top level /init script has started
|
||||||
|
# without user intervention or dropping into a recovery shell.
|
||||||
|
|
||||||
|
recovery() {
|
||||||
|
echo >&2 "!!!!! $@"
|
||||||
|
rm -f /tmp/secret.key
|
||||||
|
tpm extend -ix 4 -if recovery
|
||||||
|
|
||||||
|
echo >&2 "!!!!! Starting recovery shell"
|
||||||
|
exec /bin/ash
|
||||||
|
}
|
||||||
|
|
||||||
|
. /config
|
||||||
|
|
||||||
|
# TODO: Allow /boot to be encrypted?
|
||||||
|
# This would require a different TPM key or a user
|
||||||
|
# passphrase to decrypt it.
|
||||||
|
mount -o ro "$CONFIG_QUBES_BOOT_DEV" /boot \
|
||||||
|
|| recovery '$CONFIG_BOOT_DEV: Unable to mount /boot'
|
||||||
|
|
||||||
|
# TODO: Allow these to be specified on the /boot device
|
||||||
|
XEN=/boot/xen-4.6.3.heads
|
||||||
|
INITRD=/boot/initramfs-4.4.31-11.pvops.qubes.x86_64.img
|
||||||
|
KERNEL=/boot/vmlinuz-4.4.31-11.pvops.qubes.x86_64
|
||||||
|
|
||||||
|
echo "+++ Checking $XEN"
|
||||||
|
gpgv "${XEN}.asc" "${XEN}" \
|
||||||
|
|| recovery 'Xen signature failed'
|
||||||
|
|
||||||
|
echo "+++ Checking $INITRD"
|
||||||
|
gpgv "${INITRD}.asc" "${INITRD}" \
|
||||||
|
|| recovery 'Initrd signature failed'
|
||||||
|
|
||||||
|
echo "+++ Checking $KERNEL"
|
||||||
|
gpgv "${KERNEL}.asc" "${KERNEL}" \
|
||||||
|
|| recovery 'Kernel signature failed'
|
||||||
|
|
||||||
|
# Measure the LUKS headers before we unseal the disk key
|
||||||
|
/bin/qubes-measure-luks $CONFIG_QUBES_DEVS \
|
||||||
|
|| recovery "LUKS measure failed"
|
||||||
|
|
||||||
|
# Attempt to unseal the disk key from the TPM
|
||||||
|
# should we give this some number of tries?
|
||||||
|
unseal-key \
|
||||||
|
|| recovery 'Unseal disk key failed. Starting recovery shell'
|
||||||
|
|
||||||
|
# command line arguments are in the hash, so they are "correct".
|
||||||
|
kexec \
|
||||||
|
-l \
|
||||||
|
--module "${KERNEL} root=LABEL=root rhgb" \
|
||||||
|
--module "${INITRD}" \
|
||||||
|
--command-line "no-real-mode reboot=no console=vga dom0_mem=min:1024M dom0_mem=max:4096M" \
|
||||||
|
"${XEN}" \
|
||||||
|
|| recovery "kexec load failed"
|
||||||
|
|
||||||
|
# Last step is to override PCR 6 so that user can't read the key
|
||||||
|
tpm extend -ix 4 -ic qubes \
|
||||||
|
|| recovery 'Unable to scramble PCR'
|
||||||
|
|
||||||
|
echo "+++ Starting Qubes..."
|
||||||
|
exec kexec -e
|
14
initrd/bin/qubes-measure-luks
Executable file
14
initrd/bin/qubes-measure-luks
Executable file
@ -0,0 +1,14 @@
|
|||||||
|
#!/bin/sh
|
||||||
|
# Measure all of the luks disk encryption headers into
|
||||||
|
# a PCR so that we can detect disk swap attacks.
|
||||||
|
|
||||||
|
die() { echo >&2 "$@"; exit 1; }
|
||||||
|
|
||||||
|
# Measure the luks headers into PCR 6
|
||||||
|
for dev in "$@"; do
|
||||||
|
cryptsetup luksDump $dev \
|
||||||
|
|| die "$dev: Unable to measure"
|
||||||
|
done > /tmp/luksDump.txt
|
||||||
|
|
||||||
|
tpm extend -ix 6 -if /tmp/luksDump.txt \
|
||||||
|
|| die "Unable to extend PCR"
|
@ -7,15 +7,36 @@ TPM_INDEX=3
|
|||||||
TPM_SIZE=312
|
TPM_SIZE=312
|
||||||
KEY_FILE=/tmp/secret.key
|
KEY_FILE=/tmp/secret.key
|
||||||
|
|
||||||
die() { echo >&2 "$@"; exit 1; }
|
. /config
|
||||||
|
|
||||||
|
die() {
|
||||||
|
echo >&2 "$@";
|
||||||
|
rm -f /tmp/secret.key /tmp/recovery.key /tmp/sealed
|
||||||
|
exit 1;
|
||||||
|
}
|
||||||
warn() { echo >&2 "$@"; }
|
warn() { echo >&2 "$@"; }
|
||||||
|
|
||||||
read -s -p "New key password: " key_password
|
# Key slot 0 is the manual recovery pass phrase
|
||||||
|
# that they user entered when they installed Qubes,
|
||||||
|
# key slot 1 is the one that we've generated.
|
||||||
|
read -s -p "Enter disk recovery key: " disk_password
|
||||||
|
echo -n "$disk_password" > /tmp/recovery.key
|
||||||
|
echo
|
||||||
|
|
||||||
|
for dev in $CONFIG_QUBES_DEVS; do
|
||||||
|
echo "++++++ $dev: Removing old key slot"
|
||||||
|
cryptsetup luksKillSlot \
|
||||||
|
--key-file /tmp/recovery.key \
|
||||||
|
$dev 1 \
|
||||||
|
|| warn "$dev: ignoring problem"
|
||||||
|
done
|
||||||
|
|
||||||
|
read -s -p "New disk decryption password for booting: " key_password
|
||||||
echo
|
echo
|
||||||
read -s -p "Repeat password: " key_password2
|
read -s -p "Repeat password: " key_password2
|
||||||
echo
|
echo
|
||||||
|
|
||||||
if [ "$key_password" -ne "$key_password2" ]; then
|
if [ "$key_password" != "$key_password2" ]; then
|
||||||
die "Key passwords do not match"
|
die "Key passwords do not match"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
@ -27,11 +48,28 @@ dd \
|
|||||||
2>/dev/null \
|
2>/dev/null \
|
||||||
|| die "Unable to generate 128 random bytes"
|
|| die "Unable to generate 128 random bytes"
|
||||||
|
|
||||||
|
for dev in $CONFIG_QUBES_DEVS; do
|
||||||
|
echo "+++++ $dev: Adding key"
|
||||||
|
cryptsetup luksAddKey \
|
||||||
|
--key-file /tmp/recovery.key \
|
||||||
|
--key-slot 1 \
|
||||||
|
$dev "$KEY_FILE" \
|
||||||
|
|| die "$dev: Unable to add key"
|
||||||
|
done
|
||||||
|
|
||||||
# Use the current values of the PCRs, which will be read
|
# Now that we have setup the new keys, measure the PCRs
|
||||||
|
/bin/qubes-measure-luks $CONFIG_QUBES_DEVS \
|
||||||
|
|| die "Unable to measure the LUKS headers"
|
||||||
|
|
||||||
|
# Note that PCR 4 needs to be set with the "normal-boot"
|
||||||
|
# path value, which we do not have right now since we are
|
||||||
|
# in a recovery shell.
|
||||||
|
# PCR 5 must be all zero since no kernel modules should have
|
||||||
|
# been loaded during a normal boot, but might have been
|
||||||
|
# loaded in the recovery shell.
|
||||||
|
# Otherwise use the current values of the PCRs, which will be read
|
||||||
# from the TPM as part of the sealing ("X").
|
# from the TPM as part of the sealing ("X").
|
||||||
# should this read the storage root key?
|
tpm sealfile2 \
|
||||||
sealfile2 \
|
|
||||||
-if "$KEY_FILE" \
|
-if "$KEY_FILE" \
|
||||||
-of /tmp/sealed \
|
-of /tmp/sealed \
|
||||||
-pwdd "$key_password" \
|
-pwdd "$key_password" \
|
||||||
@ -40,10 +78,12 @@ sealfile2 \
|
|||||||
-ix 1 X \
|
-ix 1 X \
|
||||||
-ix 2 X \
|
-ix 2 X \
|
||||||
-ix 3 X \
|
-ix 3 X \
|
||||||
-ix 4 X \
|
-ix 4 f8fa3b6e32e7c6fe04c366e74636e505b28f3b0d \
|
||||||
|
-ix 5 0000000000000000000000000000000000000000 \
|
||||||
|
-ix 6 X \
|
||||||
|| die "Unable to seal secret"
|
|| die "Unable to seal secret"
|
||||||
|
|
||||||
rm "$KEY_FILE"
|
rm -f "$KEY_FILE"
|
||||||
|
|
||||||
|
|
||||||
# to create an nvram space we need the TPM owner password
|
# to create an nvram space we need the TPM owner password
|
||||||
@ -51,24 +91,23 @@ rm "$KEY_FILE"
|
|||||||
#
|
#
|
||||||
# The permissions are 0 since there is nothing special
|
# The permissions are 0 since there is nothing special
|
||||||
# about the sealed file
|
# about the sealed file
|
||||||
physicalpresence -s \
|
tpm physicalpresence -s \
|
||||||
|| warn "Warning: Unable to assert physical presence"
|
|| warn "Warning: Unable to assert physical presence"
|
||||||
|
|
||||||
read -s -p "TPM Owner password: " tpm_password
|
read -s -p "TPM Owner password: " tpm_password
|
||||||
echo
|
echo
|
||||||
|
|
||||||
nv_definespace \
|
tpm nv_definespace \
|
||||||
-in $TPM_INDEX \
|
-in $TPM_INDEX \
|
||||||
-sz $TPM_SIZE \
|
-sz $TPM_SIZE \
|
||||||
-pwdo "$tpm_password" \
|
-pwdo "$tpm_password" \
|
||||||
-per 0 \
|
-per 0 \
|
||||||
|| die "Warning: Unable to define NVRAM space; trying anyway"
|
|| warn "Warning: Unable to define NVRAM space; trying anyway"
|
||||||
|
|
||||||
|
|
||||||
nv_writevalue \
|
tpm nv_writevalue \
|
||||||
-in $TPM_INDEX \
|
-in $TPM_INDEX \
|
||||||
-if /tmp/sealed \
|
-if /tmp/sealed \
|
||||||
|| die "Unable to write sealed secret to NVRAM"
|
|| die "Unable to write sealed secret to NVRAM"
|
||||||
|
|
||||||
rm /tmp/sealed
|
rm /tmp/sealed
|
||||||
|
|
||||||
|
@ -13,22 +13,22 @@ if [ -z "$key_file" ]; then
|
|||||||
key_file=/tmp/secret.key
|
key_file=/tmp/secret.key
|
||||||
fi
|
fi
|
||||||
|
|
||||||
read -s -p "Encryption password: " tpm_password
|
read -s -p "Disk encryption password: " tpm_password
|
||||||
echo
|
echo
|
||||||
|
|
||||||
nv_readvalue \
|
tpm nv_readvalue \
|
||||||
-in "$TPM_INDEX" \
|
-in "$TPM_INDEX" \
|
||||||
-sz "$TPM_SIZE" \
|
-sz "$TPM_SIZE" \
|
||||||
-of /tmp/sealed \
|
-of /tmp/sealed \
|
||||||
|| die "Unable to read key from TPM NVRAM"
|
|| die "Unable to read key from TPM NVRAM"
|
||||||
|
|
||||||
unsealfile \
|
tpm unsealfile \
|
||||||
-if /tmp/sealed \
|
-if /tmp/sealed \
|
||||||
-of "$key_file" \
|
-of "$key_file" \
|
||||||
-pwdd "$tpm_password" \
|
-pwdd "$tpm_password" \
|
||||||
-hk 40000000 \
|
-hk 40000000 \
|
||||||
|| die "Unable to unseal disk encryption key"
|
|| die "Unable to unseal disk encryption key"
|
||||||
|
|
||||||
rm /tmp/sealed
|
rm -f /tmp/sealed
|
||||||
|
|
||||||
|
|
||||||
|
exit 0
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
#!/bin/ash
|
#!/bin/ash
|
||||||
# First thing it is vital to mount the /dev and other system directories
|
# First thing it is vital to mount the /dev and other system directories
|
||||||
mkdir /proc /sys /dev /tmp /boot 2>&- 1>&-
|
mkdir /proc /sys /dev /tmp /boot /media 2>&- 1>&-
|
||||||
mount -t devtmpfs none /dev
|
mount -t devtmpfs none /dev
|
||||||
mount -t proc none /proc
|
mount -t proc none /proc
|
||||||
mount -t sysfs none /sys
|
mount -t sysfs none /sys
|
||||||
|
Loading…
Reference in New Issue
Block a user