---
title: Reproducing Google Cloud Measurements
framework: Private Cloud Compute Security Guide
role: article
role_heading: Article
path: private-cloud-compute/reproducinggooglecloudmeasurements
---

# Reproducing Google Cloud Measurements

Recompute the boot and firmware measurements from a released host image and confirm they match the transparency log.

## Overview

Overview You can recompute the measurements a release publishes from the host image it names, and confirm they match. One pccvre command does the comparison: it re-measures the boot artifacts in the image, re-derives the GPU driver’s reference values from NVIDIA’s public service when you pass --verify-nvidia-driver, and reports how each published measurement compares. The measurements you reproduce here are the reference values a client checks during node attestation, described in Google Cloud Node Attestation. You can’t reproduce every measurement a node attests to this way: the hardware roots contribute firmware measurements that a separate release publishes, and how far you can independently derive each of those varies. Google Cloud Software Transparency grades every component on the transparency-level scale and states where independent reproduction falls short; for an overview of the Google Cloud research environment and the tools these procedures use, see Google Cloud Research Environment and Google Cloud Research Tooling. Understand what one host image covers A node’s host operating system runs directly on the machine and holds two guest VMs in its partitions: the Key Protection Service VM and the Workload VM. The two guest disk images, the firmware that launches them, and the enclave that signs their quotes are all files inside the host image. A release records these measurements: Each boot measurement is published at the hash length of its register: SHA-256 for the host, whose TPM registers use SHA-256, and SHA-384 for the two guests, whose TDX registers use SHA-384. Both guests publish the same firmware measurement, as the host launches both from the same OVMF binary. A release also records the container image that carries Apple’s runtime, the Workload Megacontainer. Google Cloud Software Transparency describes how the container is published. Its measurement comes from the container rather than from the host image, so you reproduce it separately. Reproduce the measurements To set up the measurements, you need pccvre, which ships with macOS, and roughly 40 GB of free local storage; the released host-image archive is a few gigabytes, and re-measuring it expands the raw disk image the archive contains. Re-deriving the GPU driver’s reference values additionally needs network access to NVIDIA’s public reference-integrity-manifest (RIM) service. Find and download the release Locate the release you want to reproduce in the transparency log, and inspect what it publishes: % pccvre release dump --release <release-index> --detail Replace <release-index> with the log index of the release. Inspecting Releases covers finding a release in the log. The release metadata’s operating system asset names the host image Apple used to build the release. Download the release, which retrieves the release manifest and the assets it names: % pccvre release download --release <release-index> The verification step reads both the release manifest and that asset from your local asset directory. Re-measure the image Point pccvre at the release to re-measure the host image it names and compare the results: % pccvre release verify --release <release-index> \     --verify-nvidia-driver \     --detail Passing --verify-nvidia-driver reads the driver version from the Workload VM’s root file system inside the image, fetches the matching RIM from NVIDIA, and compares the SPDM blocks one by one; without it, the published driver values are reported without being re-derived. The run prints the release digest, the image and container layout it measured, and a summary line giving how many fields matched. Passing --detail adds the comparison report, one object per measurement, as a JSON document: {   "fields": [     {"expected": "adb892e7…", "field": "host.uki", "measured": "adb892e7…", "note": null, "status": "match"},     {"expected": "70ba5343…", "field": "workload.uki", "measured": "70ba5343…", "note": null, "status": "match"},     {"expected": "ea216f26…", "field": "workload.ovmf", "measured": "ea216f26…", "note": null, "status": "match"},     {"expected": "120c34de…", "field": "workload.nvidiaDriver.block[15]", "measured": "120c34de…", "note": null, "status": "match"},     {"expected": null, "field": "variant", "measured": null, "note": "afm (not re-derived from image)", "status": "info"}   ],   "matched": true,   "releaseDigest": "3f2b9c6f…" } The tool emits that report on one line, with digests at full length; it is formatted and truncated here for reading. The report covers every measurement the release records, not only the ones shown: the Key Protection Service VM’s boot and firmware measurements, the quoting enclave’s four identity fields, and one object per NVIDIA SPDM block. A field’s status is match, mismatch with both values present, missingExpected where the release records no such measurement, or info where the run did not re-derive the value. The run reports success only when at least one field was compared and none mismatched, so a run that re-derived nothing fails rather than passing on an empty comparison. Understand how pccvre computes the firmware measurement The MRTD is not a hash of the firmware binary. Launching a confidential VM measures the memory image into which the host loads the firmware, so reproducing the value means reconstructing that image rather than digesting the file. To do this, pccvre parses the GUID table at the end of the firmware binary, locates the TDX metadata the table references, and builds the memory regions that the metadata declares: Boot and configuration firmware volumes Handoff block the host synthesizes for the VM Temporary memory from which the firmware runs It then folds those regions with SHA-384 in launch order. Every region contributes its guest-physical addresses, and only the boot firmware volume, which the metadata marks for measurement, contributes its contents. A node measures the contents of the other regions into RTMR[0] at runtime. Google publishes its own extraction and simulation tooling in the confidential-space repository; that tooling computes the MRTD from an OVMF binary extracted from the image on a Linux host — a second implementation of the same reconstruction. note: CloudAttestation-GoogleCloud: image measurement, firmware reference manifests confidential-space Reproduce the container image digest The measurements above cover the boot chain beneath Apple’s runtime. The runtime itself is covered by one more value in the same release, the digest of the workload container image, and that value is re-derived from the container rather than from the host image. A release’s metadata names the container as a downloadable asset, and that asset’s URL is content-addressed: the digest is part of the address, so fetching the container and confirming what you received already ties the bytes to the name you requested. You still have to confirm that the digest the release publishes is the digest of the image you hold. release download retrieves that asset alongside the operating system image, and a release verify run picks it up from disk without being asked. To measure a layout of your own instead — an unpacked directory or an archive — pass its path: % pccvre release verify --release <release-index> --container-image-layout <container-layout-path> --detail pccvre re-derives the manifest digest from the layout and compares it against the containerImageDigest the release records. The header of each run reports the layout it used, or prints (none — containerImageDigest will be reported info-only) where it found neither a downloaded asset nor a supplied path. Read that line before treating the digest as confirmed. Google Cloud Workload Modification covers unpacking the container image and inspecting its contents. Understand the basis of each result The rows a run produces are not all the same kind of claim, and the distinction matters when you decide what a match has told you: Derived from the image alone: The three UKI digests, the firmware MRTD, and the quoting enclave’s identity come from bytes you hold. A match means the release’s boot measurements describe the image you downloaded, and you need nothing but that image to establish it. Checked against NVIDIA’s reference service: The driver rows compare the release against NVIDIA’s signed reference values. The image pins only the driver version; the block digests come from the RIM service over the network. A match means the release agrees with NVIDIA’s published reference for the driver that the image ships; that agreement rests on NVIDIA’s service as a second source rather than on the image. Handle when a measurement doesn’t match A mismatch means the image you measured is not the image Apple used to build the release. The run ends in FAILED to verify image against published v2 release and exits non-zero, and the report names the fields that differ. Before treating one as a finding, rule out the benign causes: The wrong image: A release names its host image in its metadata. Confirm the image you measured is the one it names, rather than a different build. A debug image measured against a production release: Debug and hardened images are separate artifacts with separate measurements. Apple publishes production releases only for hardened images, so a debug image matches no release in the production log. Appendix: Google Cloud Debug and Hardened Images describes how the two variants differ. A partial download: pccvre reports a truncated archive as a partition that extends beyond the image rather than as a wrong digest, but an interrupted transfer is worth ruling out first. Check a measurement against a node’s attestation Recomputing a measurement tells you what a released image produces. To confirm that a running node booted that image, compare the recomputed value against the node’s attestation. Google Cloud Node Attestation describes the evidence a node produces, Appendix: Google Cloud Attestation Bundle Contents gives its wire format, and Google Cloud Research Tooling covers parsing a bundle with pccvre. A bundle carries one Intel TDX quote per confidential VM, one for the Workload VM and one for the Key Protection Service VM, plus a host attestation rooted in the machine’s TPM. Each TDX quote holds that VM’s MRTD, its four RTMRs, and the Confidential Computing Event Log (CCEL) recording the events that extended the RTMRs, and each quote’s signature data holds the report of the enclave that signed it. The workload quote additionally carries a launch event log recording what the node started, including the container image digest. The host attestation holds a TPM quote over the host’s PCRs and the PC Client boot event log behind it. The measurements you reproduced map onto that evidence as follows:  |   |   |   |   |   |   |  The host launches both guests from one firmware binary, so both guests attest the same MRTD and both published firmware measurements record that value. Each TDX quote covers only the boot chain of the VM that produced it, so nothing running inside either confidential VM measures the host beneath it, and the host measurement appears only in the host attestation. Those quotes still constrain the host image indirectly: the firmware and both guest UKIs are files inside that image, so matching guest measurements confirm that the node launched the firmware and the guest payloads the image ships. Rather than reading a bundle field by field, extract the release a bundle attests and compare it against the release you reproduced: % pccvre attestation canonicalize --input-format attestation-bundle:protobuf <bundle-path> --detail A node running the same host image as a release you have reproduced attests the same host, guest, and firmware measurements, even when the rest of the release differs. The command projects the bundle onto two releases and prints the digest and contents of each: the software release covered above and the platform firmware release covered below. Comparing releases this way tells you what a bundle asserts, which is a different question from whether the bundle’s evidence holds up. An event log is unsigned data traveling alongside a quote, and a node that lies about its boot might equally lie about its log; what the hardware signs is the register. Validating a bundle against an environment’s policy reconciles the two by confirming that replaying each event log reproduces the register its quote signs, and that each signature chains to its vendor root: % pccvre attestation verify --input-format attestation-bundle:protobuf <bundle-path> For the mapping from the event log indices to the registers they extend, see Appendix: Google Cloud Measurement Registers. Check the platform firmware release Alongside the release covering the measurements above, a bundle carries a second release recording the hardware roots’ own firmware: the security chip’s firmware hash, the baseboard management controller firmware digest, the host BIOS digest, the Intel TDX module identity and platform trusted-computing-base values, and the GPU’s VBIOS measurement blocks, which are distinct from the driver blocks you re-derived. That release is published in the transparency log as its own entry, with its own digest and its own assets. Because a bundle carries the digest of the firmware release it attests, you can look that digest up in the log and confirm the node’s firmware evidence corresponds to a published release, without recomputing anything. How far each of its measurements can be independently derived varies: Google Cloud Software Transparency grades each component on the transparency-level scale and states what independent verification is possible for each.
