TPM 2.0 in qemu

If you want to test software which exploits TPM 2.0 functionality inside the qemu-kvm emulator, this can be challenging because the software stack is still quite new. Here is how I did it.

First, you need a new enough qemu. The version on Ubuntu xenial does not suffice. The 2.11 version in Ubuntu bionic does. I believe the 2.10 version in artful is also too old, but might be mis-remembering haven’t tested that lately.

The two pieces of software I needed were libtpms and swtpm. For libtpms I used the tpm2-preview.rev146.v2 branch, and for swtpm I used the tpm2-preview.v2 branch.

apt -y install libtool autoconf tpm-tools expect socat libssl-dev
git clone https://github.com/stefanberger/libtpms
( cd libtpms &&
  git checkout tpm2-preview.rev146.v2 &&
  ./bootstrap.sh &&
  ./configure --prefix=/usr --with-openssl --with-tpm2 &&
  make && make install)
git clone https://github.com/stefanberger/swtpm
(cd swtpm &&
  git checkout tpm2-preview.v2 &&
  ./bootstrap.sh &&
  configure --prefix=/usr --with-openssl --with-tpm2 &&
  make &&
  make install)

For each qemu instance, I create a tpm device. The relevant part of the script I used looks like this:

#!/bin/bash

i=0
while [ -d /tmp/mytpm$i ]; do
let i=i+1
done
tpm=/tmp/tpm$i

mkdir $tpm
echo "Starting $tpm"
sudo swtpm socket --tpmstate dir=$tpm --tpm2 \
             --ctrl type=unixio,path=/$tpm/swtpm-sock &
sleep 2 # this should be changed to a netstat query

next_vnc() {
    vncport=0
    port=5900
    while nc -z 127.0.0.1 $port; do
        port=$((port + 1))
        vncport=$((vncport + 1))
    done
    echo $vncport
}

nextvnc=$(next_vnc)
sudo kvm -drive file=${disk},format=raw,if=virtio,cache=none -chardev socket,id=chrtpm,path=/$tpm/swtpm-sock -tpmdev emulator,id=tpm0,chardev=chrtpm -device tpm-tis,tpmdev=tpm0 -vnc :$nextvnc -m 2048
This entry was posted in Uncategorized. Bookmark the permalink.

11 Responses to TPM 2.0 in qemu

  1. Pingback: Links 3/6/2018: Linux 4.17, Mesa 18.0.5, GitHub’s Death, FreeBSD 11.2 RC1 | Techrights

  2. Pingback: TPM 2.0 in QEMU | Firmware Security

  3. Luke Hinds says:

    So is this creating an emulated (or simulated) TPM or is this some sort of paravirtualization of a hardware TPM exposed via QEMU?

    • s3hh says:

      Hi – sorry for the late reply. It’s an emulated TPM.

      • Luke Hinds says:

        Hi, thanks for reply and apologies for my late reply. I guess what I mean is does the keys, quotes etc reside in the hardware TPM and the vTPM acts a paravirtualized instance of the TPM, or does it exist soley on its own and the keys are stored on disc / memory (for example, you could run it with a hardware TPM present). Hope that makes sense.

      • s3hh says:

        Exist solely on its own.

  4. s3hh says:

    Update: the branches have been merged into the main branches for both libtpms and swtpm, so you no longer need to do the ‘git checkout’ in the instructions above.

  5. Blathers says:

    I’m trying to run this now but it giving me an error “kvm: -drive file=,format=raw,if=virtio,cache=none: A block device must be specified for “file””

    It looks like “${disk}” isn’t set. Any ideas?

Leave a comment