diff --git a/src/runtime/pkg/README.md b/src/runtime/pkg/README.md index b5b0d07d32..72bf3248bb 100644 --- a/src/runtime/pkg/README.md +++ b/src/runtime/pkg/README.md @@ -7,4 +7,5 @@ This repository contains a number of packages in addition to the |-|-| | [`katatestutils`](katatestutils) | Unit test utilities. | | [`katautils`](katautils) | Utilities. | +| [`sev`](sev) | AMD SEV confidential guest utilities. | | [`signals`](signals) | Signal handling functions. | diff --git a/src/runtime/pkg/sev/README.md b/src/runtime/pkg/sev/README.md new file mode 100644 index 0000000000..8e864f46fa --- /dev/null +++ b/src/runtime/pkg/sev/README.md @@ -0,0 +1,14 @@ +# AMD SEV confidential guest utilities + +This package provides utilities for launching AMD SEV confidential guests. + +## Calculating expected launch digests + +The `CalculateLaunchDigest` function can be used to calculate the expected +SHA-256 of an SEV confidential guest given its firmware, kernel, initrd, and +kernel command-line. + +### Unit test data + +The [`testdata`](testdata) directory contains file used for testing +`CalculateLaunchDigest`. diff --git a/src/runtime/pkg/sev/sev.go b/src/runtime/pkg/sev/sev.go index d95d2012b6..0b84abaa97 100644 --- a/src/runtime/pkg/sev/sev.go +++ b/src/runtime/pkg/sev/sev.go @@ -152,11 +152,13 @@ func CalculateLaunchDigest(firmwarePath, kernelPath, initrdPath, cmdline string) return res, err } - ht, err := constructSevHashesTable(kernelPath, initrdPath, cmdline) - if err != nil { - return res, err + if kernelPath != "" { + ht, err := constructSevHashesTable(kernelPath, initrdPath, cmdline) + if err != nil { + return res, err + } + digest.Write(ht) } - digest.Write(ht) copy(res[:], digest.Sum(nil)) return res, nil diff --git a/src/runtime/pkg/sev/sev_test.go b/src/runtime/pkg/sev/sev_test.go new file mode 100644 index 0000000000..d1ffffa7ff --- /dev/null +++ b/src/runtime/pkg/sev/sev_test.go @@ -0,0 +1,32 @@ +// Copyright contributors to AMD SEV/-ES in Go +// +// SPDX-License-Identifier: Apache-2.0 + +package sev + +import ( + "encoding/hex" + "testing" +) + +func TestCalculateLaunchDigestWithoutKernelHashes(t *testing.T) { + ld, err := CalculateLaunchDigest("testdata/ovmf_suffix.bin", "", "", "") + if err != nil { + t.Fatalf("unexpected err value: %s", err) + } + hexld := hex.EncodeToString(ld[:]) + if hexld != "b184e06e012366fd7b33ebfb361a515d05f00d354dca07b36abbc1e1e177ced5" { + t.Fatalf("wrong measurement: %s", hexld) + } +} + +func TestCalculateLaunchDigestWithKernelHashes(t *testing.T) { + ld, err := CalculateLaunchDigest("testdata/ovmf_suffix.bin", "/dev/null", "/dev/null", "") + if err != nil { + t.Fatalf("unexpected err value: %s", err) + } + hexld := hex.EncodeToString(ld[:]) + if hexld != "d59d7696efd7facfaa653758586e6120c4b6eaec3e327771d278cc6a44786ba5" { + t.Fatalf("wrong measurement: %s", hexld) + } +} diff --git a/src/runtime/pkg/sev/testdata/README.md b/src/runtime/pkg/sev/testdata/README.md new file mode 100644 index 0000000000..34554dc8e2 --- /dev/null +++ b/src/runtime/pkg/sev/testdata/README.md @@ -0,0 +1,9 @@ +# sev/testdata + +The `ovmf_suffix.bin` contains the last 4KB of the `OVMF.fd` binary from edk2's +`OvmfPkg/AmdSev/AmdSevX64.dsc` build. To save space, we committed only the +last 4KB instead of the the full 4MB binary. + +The end of the file contains a GUIDed footer table with entries that hold the +SEV-ES AP reset vector address, which is needed in order to compute VMSAs for +SEV-ES guests. diff --git a/src/runtime/pkg/sev/testdata/ovmf_suffix.bin b/src/runtime/pkg/sev/testdata/ovmf_suffix.bin new file mode 100644 index 0000000000..cc6d7ca7f0 Binary files /dev/null and b/src/runtime/pkg/sev/testdata/ovmf_suffix.bin differ