Trusted Boot with OpenBSD

classic Classic list List threaded Threaded
2 messages Options
Reply | Threaded
Open this post in threaded view
|

Trusted Boot with OpenBSD

Julius Zint
As part of my master thesis i wrote code to enable a trusted boot
with OpenBSD. This short manual is for everyone who wants to try it.
Feedback on the code and the feature itself is also appreciated.

Requirements:
    1: OpenBSD 6.5 (might also work with 6.6 but only tested with 6.5)
    2: Default installation with Full Disk Encryption (FDE)
    3: Clean sys source code in /usr/src/sys/**
    4: Firmware with Logical Block Adressing (LBA) support
    5: 64-Bit Processor
    6: System with a dedicated TPM 1.2 Chip
    7: Downloaded all attachments to this email in /tmp
    8: Adventurous mindset (this might brick your installation)



1: Updating the MBR startprogram to measure biosboot(8)
The following commands are meant to be inserted one by one by the user
and need adjustments depending on the system.

cd /usr/src/sys/arch/amd64/stand/mbr/

# patch the source code and compile the new MBR
patch mbr.S /tmp/mbr.patch
make CPPFLAGS+=-DTPM_MEASURE CPPFLAGS+=-DNO_CHS

# updating MBR on disk (replace X with drive). To preserve partition
# table copy existing, overwrite startprogram and write back
dd if=/dev/rsdXc of=mbr.img bs=512 count=1
dd if=mbr of=mbr.img bs=440 count=1 conv=notrunc
dd if=mbr.img of=/dev/rsdXc bs=512 count=1
rm mbr.img



2: Updating biosboot(8) and boot(8)
Same as in the first step. These commands contain absolute paths and
drive numbers that need to be changed by the user.

cd /usr/src/sys/arch/amd64/stand/biosboot/

# patch the biosboot(8) source code and compile
patch biosboot.S /tmp/biosboot.patch
make DEBUGFLAGS+=-DNO_CHS DEBUGFLAGS+=-DTPM_MEASURE

# patch the boot(8) source code and compile
cd /usr/src/sys/arch/amd64/stand
patch ./boot/Makefile /tmp/makefile.patch

# this fix got already included in the OpenBSD source but did not make
# it in 6.6
patch ./libsa/gidt.S /tmp/boot/gidt.patch

patch ./libsa/cmd_i386.c /tmp/cmd_i386.patch
cp /tmp/tpm.c ./libsa/
cp /tmp/tpm.h ./libsa/
cd ./boot
make

# install biosboot(8) and boot(8)
# replace X with the drive number of the virtual softraid device
cd /usr/src/sys/arch/amd64/stand
installboot sdX  ./biosboot/biosboot ./boot/boot

If every step finished successfully, your system extends the measurement
chain from a small immutable piece of firmware up to boot(8). The
updated mbr(8) measures biosboot(8) and biosboot(8) measures boot(8).




The TPM has to be initialized bevor any of the tpm commands will work.
To perform the initialization:
    1: reset the TPM in the firmware
    2: create a bootable Fedora USB-Stick
    3: start the system with it
    4: and execute the following commands:
        sudo dnf install tpm-tools
        tpm_takeownership -z -y

boot(8) supports the machine specific command "tpm". This allows a
user to:

1: read the current contents of the Platform Control Registers (PCR)
   with the "pcr" parameter

   machine tpm p[cr]

2: seal a user supplied secret to the current PCR values and store it
   in the second block on a disk, that can be altered via a parameter.
   WARNING: If there is any other data in this block, it will be
   overwritten without asking again.

   machine tpm s[eal] secret [DiskNumber]

3: unseal a previously sealed secrent and display it to the user. This
   command just reads the second block of the disk that can be
   specified by the user and unseals it via the TPM

   machine tpm u[nseal] [DiskNumber]


Lets hope everything works as it does on my machine :). I will now be
away from my computer for a month. So if this feature is something the
OpenBSD would welcome, i would put in the other 90% it takes to bring
this feature from a prototype to something that could actually be
merged.

Kind Regards

Julius


tpm.h (1K) Download Attachment
tpm.c (53K) Download Attachment
biosboot.patch (3K) Download Attachment
cmd_i386.patch (6K) Download Attachment
gidt.patch (481 bytes) Download Attachment
makefile.patch (449 bytes) Download Attachment
mbr.patch (2K) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: Trusted Boot with OpenBSD

Frank Beuth
On Mon, Feb 24, 2020 at 03:22:28PM +0100, Julius Zint wrote:

>boot(8) supports the machine specific command "tpm". This allows a
>user to:
>
>1: read the current contents of the Platform Control Registers (PCR)
>   with the "pcr" parameter
>
>   machine tpm p[cr]
>
>2: seal a user supplied secret to the current PCR values and store it
>   in the second block on a disk, that can be altered via a parameter.
>   WARNING: If there is any other data in this block, it will be
>   overwritten without asking again.
>
>   machine tpm s[eal] secret [DiskNumber]
>
>3: unseal a previously sealed secrent and display it to the user. This
>   command just reads the second block of the disk that can be
>   specified by the user and unseals it via the TPM
>
>   machine tpm u[nseal] [DiskNumber]

I hope you are enjoying your (well-earned) vacation.

I can't tell from the instructions how the FDE encryption key is stored
-- do we manually seal it to the TPM and then manually unseal and
copy/paste it every time we boot? Or is it assumed the user will write a
script to handle this -- a script which itself will have to be measured
by the TPM?