Trust Domain at Runtime¶
On this page, we provide instructions on topics concerning a Trust Domain (TD) at runtime.
Perform Remote Attestation¶
As explained in the Intel TDX Remote Attestation section of the Infrastructure Setup page, remote attestation is one of the main features of Intel TDX.
In this section, we assume that your infrastructure provider has done the necessary setup steps. This includes the setup of a collateral caching service in the infrastructure and ensuring that a Quote Generation Service (QGS) is running on the same host as the TD.
Then, we show how TD Quotes can be generated, which always has to happen inside a TD.
We also describe how generated TD Quotes can be verified to close the loop. TD Quote Verification can be done by any party at any place. Examples:
- Inside the TD by the TD owner.
- In the host OS by the host OS owner.
- On any remote platform by the owner of the remote platform.
Note that there are multiple TD Quote Verification alternatives.
TD Quote Generation¶
TD Quote Generation must always happen inside the TD. There are multiple ways to generate a TD Quote. In the following, we explore two alternative for TD Quote Generation using the Linux kernel's built-in configfs-tsm interface:
Manual Shell Commands¶
Execute the following shell commands to generate a TD Quote on your distro of choice:
REPORT_DIR="/sys/kernel/config/tsm/report"
REPORT="$REPORT_DIR/report0"
# Ensure configfs is mounted
if ! mountpoint -q /sys/kernel/config; then
sudo mount -t configfs none /sys/kernel/config
fi
# Create report directory
sudo mkdir -p "$REPORT"
# Provide 64 bytes of REPORTDATA (nonce)
head -c 64 /dev/urandom | sudo tee "$REPORT/inblob" > /dev/null
# Retrieve the Quote
echo "[*] Retrieving TD Quote..."
sudo cat "$REPORT/outblob" > quote.dat
# Check if the output file is empty
if [ ! -s quote.dat ]; then
echo "[!] Error: TD Quote is empty. Retrieval may have failed." >&2
sudo rmdir "$REPORT"
else
# Show formatted output
echo "[*] Hexdump of the TD Quote:"
sudo hexdump -C quote.dat
# Cleanup
sudo rmdir "$REPORT"
echo "[*] Quote saved to quote.dat"
fi
REPORT_DIR="/sys/kernel/config/tsm/report"
REPORT="$REPORT_DIR/report0"
# Ensure configfs is mounted
if ! mountpoint -q /sys/kernel/config; then
mount -t configfs none /sys/kernel/config
fi
# Create report directory
mkdir -p "$REPORT"
# Provide 64 bytes of REPORTDATA (nonce)
head -c 64 /dev/urandom | tee "$REPORT/inblob" > /dev/null
# Retrieve the Quote
echo "[*] Retrieving TD Quote..."
cat "$REPORT/outblob" > quote.dat
# Check if the output file is empty
if [ ! -s quote.dat ]; then
echo "[!] Error: TD Quote is empty. Retrieval may have failed." >&2
rmdir "$REPORT"
else
# Show formatted output
echo "[*] Hexdump of the TD Quote:"
hexdump -C quote.dat
# Cleanup
rmdir "$REPORT"
echo "[*] Quote saved to quote.dat"
fi
REPORT_DIR="/sys/kernel/config/tsm/report"
REPORT="$REPORT_DIR/report0"
# Ensure configfs is mounted
if ! mountpoint -q /sys/kernel/config; then
sudo mount -t configfs none /sys/kernel/config
fi
# Create report directory
sudo mkdir -p "$REPORT"
# Provide 64 bytes of REPORTDATA (nonce)
head -c 64 /dev/urandom | sudo tee "$REPORT/inblob" > /dev/null
# Retrieve the Quote
echo "[*] Retrieving TD Quote..."
sudo cat "$REPORT/outblob" > quote.dat
# Check if the output file is empty
if [ ! -s quote.dat ]; then
echo "[!] Error: TD Quote is empty. Retrieval may have failed." >&2
sudo rmdir "$REPORT"
else
# Show formatted output
echo "[*] Hexdump of the TD Quote:"
sudo hexdump -C quote.dat
# Cleanup
sudo rmdir "$REPORT"
echo "[*] Quote saved to quote.dat"
fi
REPORT_DIR="/sys/kernel/config/tsm/report"
REPORT="$REPORT_DIR/report0"
# Ensure configfs is mounted
if ! mountpoint -q /sys/kernel/config; then
mount -t configfs none /sys/kernel/config
fi
# Create report directory
mkdir -p "$REPORT"
# Provide 64 bytes of REPORTDATA (nonce)
head -c 64 /dev/urandom | tee "$REPORT/inblob" > /dev/null
# Retrieve the Quote
echo "[*] Retrieving TD Quote..."
cat "$REPORT/outblob" > quote.dat
# Check if the output file is empty
if [ ! -s quote.dat ]; then
echo "[!] Error: TD Quote is empty. Retrieval may have failed." >&2
rmdir "$REPORT"
else
# Show formatted output
echo "[*] Hexdump of the TD Quote:"
hexdump -C quote.dat
# Cleanup
rmdir "$REPORT"
echo "[*] Quote saved to quote.dat"
fi
REPORT_DIR="/sys/kernel/config/tsm/report"
REPORT="$REPORT_DIR/report0"
# Ensure configfs is mounted
if ! mountpoint -q /sys/kernel/config; then
sudo mount -t configfs none /sys/kernel/config
fi
# Create report directory
sudo mkdir -p "$REPORT"
# Provide 64 bytes of REPORTDATA (nonce)
head -c 64 /dev/urandom | sudo tee "$REPORT/inblob" > /dev/null
# Retrieve the Quote
echo "[*] Retrieving TD Quote..."
sudo cat "$REPORT/outblob" > quote.dat
# Check if the output file is empty
if [ ! -s quote.dat ]; then
echo "[!] Error: TD Quote is empty. Retrieval may have failed." >&2
sudo rmdir "$REPORT"
else
# Show formatted output
echo "[*] Hexdump of the TD Quote:"
sudo hexdump -C quote.dat
# Cleanup
sudo rmdir "$REPORT"
echo "[*] Quote saved to quote.dat"
fi
If successful, a TD Quote will be written to disk in a quote.dat file.
This quote.dat file can now be verified as described in the next TD Quote Verification section.
Intel TDX Quote Generation Sample¶
Execute the following commands to generate a TD Quote using the Intel TDX Quote Generation Sample on your distro of choice:
-
If not done during another component installation, set up the appropriate Intel SGX package repository for your distribution of choice:
sudo dnf install -y yum-utils wget tar sudo mkdir -p /opt/intel wget https://download.01.org/intel-sgx/latest/dcap-latest/linux/distro/centos-stream10/sgx_rpm_local_repo.tgz sudo tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel sudo yum-config-manager --add-repo file:///opt/intel/sgx_rpm_local_repo sudo wget https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key -O /opt/intel/intel-sgx.key sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.gpgkey=file:///opt/intel/intel-sgx.key # Set the priority of the local repo to 1 (highest) to avoid conflicts with other repos sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.priority=1zypper install -y wget tar mkdir -p /opt/intel rpm --import https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key wget https://download.01.org/intel-sgx/sgx-dcap/1.27.1/linux/distro/suse16-server/sgx_rpm_local_repo.tgz tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel zypper addrepo /opt/intel/sgx_rpm_local_repo sgx_rpm_local_reposudo dnf install -y yum-utils wget tar sudo mkdir -p /opt/intel wget https://download.01.org/intel-sgx/latest/dcap-latest/linux/distro/rhel10.2-server/sgx_rpm_local_repo.tgz sudo tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel sudo yum-config-manager --add-repo file:///opt/intel/sgx_rpm_local_repo sudo wget https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key -O /opt/intel/intel-sgx.key sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.gpgkey=file:///opt/intel/intel-sgx.key # Set the priority of the local repo to 1 (highest) to avoid conflicts with other repos sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.priority=1zypper install -y wget tar mkdir -p /opt/intel rpm --import https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key wget https://download.01.org/intel-sgx/sgx-dcap/1.27.1/linux/distro/suse16-server/sgx_rpm_local_repo.tgz tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel zypper addrepo /opt/intel/sgx_rpm_local_repo sgx_rpm_local_repoecho 'deb [signed-by=/etc/apt/keyrings/intel-sgx-keyring.asc arch=amd64]' \ 'https://download.01.org/intel-sgx/sgx_repo/ubuntu resolute main' \ | sudo tee /etc/apt/sources.list.d/intel-sgx.list curl -fsSLO https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key sudo mkdir -p /etc/apt/keyrings sudo mv intel-sgx-deb.key /etc/apt/keyrings/intel-sgx-keyring.asc sudo apt-get updateecho 'deb [signed-by=/etc/apt/keyrings/intel-sgx-keyring.asc arch=amd64]' \ 'file:///opt/intel/sgx_debian_local_repo resolute main' \ | sudo tee /etc/apt/sources.list.d/intel-sgx-local.list curl -fsSLO https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key sudo mkdir -p /etc/apt/keyrings /opt/intel sudo mv intel-sgx-deb.key /etc/apt/keyrings/intel-sgx-keyring.asc curl -fsSLO https://download.01.org/intel-sgx/latest/dcap-latest/linux/distro/ubuntu26.04-server/sgx_debian_local_repo.tgz sudo tar -xvzf sgx_debian_local_repo.tgz -C /opt/intel sudo apt-get update -
Install, build, and run the Intel TDX Quote Generation Sample application (
test_tdx_attest)sudo dnf install -y libtdx-attest-devel make gcc cd /opt/intel/tdx-quote-generation-sample make ./test_tdx_attest mv ./quote.dat ~/quote.datzypper install -y make gcc libtdx-attest-devel cd /opt/intel/tdx-quote-generation-sample make ./test_tdx_attest mv ./quote.dat ~/quote.datsudo dnf install -y libtdx-attest-devel make gcc cd /opt/intel/tdx-quote-generation-sample make ./test_tdx_attest mv ./quote.dat ~/quote.datzypper install -y make gcc libtdx-attest-devel cd /opt/intel/tdx-quote-generation-sample make ./test_tdx_attest mv ./quote.dat ~/quote.datsudo apt install -y libtdx-attest-dev make gcc cd /opt/intel/tdx-quote-generation-sample make ./test_tdx_attest mv ./quote.dat ~/quote.datIf successful, a TD Quote will be written to disk in a
quote.datfile. Thisquote.datfile can now be verified as described in the TD Quote Verification section.
TD Quote Verification¶
TD Quote Verification can be done by any party at an arbitrary place. There are multiple TD Quote Verification alternatives. In the following, we explore how TD Quote Verification can be tested using the Quote Verification Sample application deployed in the host OS.
Steps:
-
Copy the TD Quote file (e.g.,
quote.dat) to the host OS. Use a tool of your choice for this operation. Possible commands usingscporvirt-copy-out:Note
SSH access to your TD is necessary for this approach. If the VM is started with sudo privileges, ensure you execute the following command with sudo.
Adjust the following command to your environment and use it to copy the file:
scp -i ./guest_TD_root_id -p <TD SSH port> <TD user>@<TD IP>:<guest-path-to>/quote.dat <host_directory>/.Example command:
scp -i ./guest_TD_root_id -P 10022 root@localhost:/root/quote.dat ~/quote.datNote
Host OS access is necessary for this approach. Also, you must shutdown the TD before accessing the guest image.
Terminate TD. Then, adjust the following command to your environment and use it to copy the file:
sudo virt-copy-out -a <image_path> <guest-path-to>/quote.dat <host_directory>Example command:
sudo virt-copy-out -a ~/ubuntu-26.04-server-cloudimg-amd64.img /root/quote.dat ~ -
If not done during another component installation, setup the appropriate Intel SGX package repository for your distribution of choice:
sudo dnf install -y yum-utils wget tar sudo mkdir -p /opt/intel wget https://download.01.org/intel-sgx/latest/dcap-latest/linux/distro/centos-stream10/sgx_rpm_local_repo.tgz sudo tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel sudo yum-config-manager --add-repo file:///opt/intel/sgx_rpm_local_repo sudo wget https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key -O /opt/intel/intel-sgx.key sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.gpgkey=file:///opt/intel/intel-sgx.key # Set the priority of the local repo to 1 (highest) to avoid conflicts with other repos sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.priority=1sudo zypper install -y wget tar sudo mkdir -p /opt/intel sudo rpm --import https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key wget https://download.01.org/intel-sgx/sgx-dcap/1.27.1/linux/distro/suse16-server/sgx_rpm_local_repo.tgz sudo tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel sudo zypper addrepo /opt/intel/sgx_rpm_local_repo sgx_rpm_local_reposudo dnf install -y yum-utils wget tar sudo mkdir -p /opt/intel wget https://download.01.org/intel-sgx/latest/dcap-latest/linux/distro/rhel10.2-server/sgx_rpm_local_repo.tgz sudo tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel sudo yum-config-manager --add-repo file:///opt/intel/sgx_rpm_local_repo sudo wget https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key -O /opt/intel/intel-sgx.key sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.gpgkey=file:///opt/intel/intel-sgx.key # Set the priority of the local repo to 1 (highest) to avoid conflicts with other repos sudo yum-config-manager --save --setopt=*sgx_rpm_local_repo.priority=1sudo zypper install -y wget tar sudo mkdir -p /opt/intel sudo rpm --import https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key wget https://download.01.org/intel-sgx/sgx-dcap/1.27.1/linux/distro/suse16-server/sgx_rpm_local_repo.tgz sudo tar -xvzf sgx_rpm_local_repo.tgz -C /opt/intel sudo zypper addrepo /opt/intel/sgx_rpm_local_repo sgx_rpm_local_repoecho 'deb [signed-by=/etc/apt/keyrings/intel-sgx-keyring.asc arch=amd64]' \ 'https://download.01.org/intel-sgx/sgx_repo/ubuntu resolute main' \ | sudo tee /etc/apt/sources.list.d/intel-sgx.list curl -fsSLO https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key sudo mkdir -p /etc/apt/keyrings sudo mv intel-sgx-deb.key /etc/apt/keyrings/intel-sgx-keyring.asc sudo apt-get updateecho 'deb [signed-by=/etc/apt/keyrings/intel-sgx-keyring.asc arch=amd64]' \ 'file:///opt/intel/sgx_debian_local_repo resolute main' \ | sudo tee /etc/apt/sources.list.d/intel-sgx-local.list curl -fsSLO https://download.01.org/intel-sgx/sgx_repo/ubuntu/intel-sgx-deb.key sudo mkdir -p /etc/apt/keyrings /opt/intel sudo mv intel-sgx-deb.key /etc/apt/keyrings/intel-sgx-keyring.asc curl -fsSLO https://download.01.org/intel-sgx/latest/dcap-latest/linux/distro/ubuntu26.04-server/sgx_debian_local_repo.tgz sudo tar -xvzf sgx_debian_local_repo.tgz -C /opt/intel sudo apt-get update -
Execute the following command to install the dependencies for the Quote Verification Sample application, retrieve the application, build the application, and use the application to verify the TD Quote (i.e.,
quote.dat):sudo dnf install -y gcc make git g++ sudo dnf install -y libsgx-enclave-common-devel \ libsgx-dcap-quote-verify-devel libsgx-dcap-default-qpl-devel cd ~ git clone https://github.com/intel/confidential-computing.tee.dcap.git cd confidential-computing.tee.dcap/SampleCode/QuoteVerificationSample make QVL_ONLY=1 ./app -quote ~/quote.datsudo zypper install -y make gcc-c++ git \ libsgx-enclave-common-devel libsgx-dcap-quote-verify-devel libsgx-dcap-default-qpl-devel git clone https://github.com/intel/confidential-computing.tee.dcap.git cd confidential-computing.tee.dcap/SampleCode/QuoteVerificationSample make QVL_ONLY=1 ./app -quote ~/quote.datsudo dnf install -y gcc make git g++ sudo dnf install -y libsgx-enclave-common-devel \ libsgx-dcap-quote-verify-devel libsgx-dcap-default-qpl-devel cd ~ git clone https://github.com/intel/confidential-computing.tee.dcap.git cd confidential-computing.tee.dcap/SampleCode/QuoteVerificationSample make QVL_ONLY=1 ./app -quote ~/quote.datsudo zypper install -y make gcc-c++ git \ libsgx-enclave-common-devel libsgx-dcap-quote-verify-devel libsgx-dcap-default-qpl-devel git clone https://github.com/intel/confidential-computing.tee.dcap.git cd confidential-computing.tee.dcap/SampleCode/QuoteVerificationSample make QVL_ONLY=1 ./app -quote ~/quote.datsudo apt install -y make g++ libsgx-enclave-common-dev \ libsgx-dcap-quote-verify-dev libsgx-dcap-default-qpl-dev git clone https://github.com/intel/confidential-computing.tee.dcap.git cd confidential-computing.tee.dcap/SampleCode/QuoteVerificationSample make QVL_ONLY=1 ./app -quote ~/quote.datIf TD Quote Verification is successful, the output will contain
Verification completed.