Skip to content

Commit 28d8e00

Browse files
authored
Merge pull request #81 from deeglaze/moreuuids
Add CertTableOptions for "extra" certs
2 parents a6bdd4c + b6001c9 commit 28d8e00

File tree

9 files changed

+245
-89
lines changed

9 files changed

+245
-89
lines changed

abi/abi.go

Lines changed: 25 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@ import (
2222
"fmt"
2323
"math/big"
2424

25-
"github.com/google/go-sev-guest/gce"
2625
pb "github.com/google/go-sev-guest/proto/sevsnp"
2726
"github.com/google/logger"
2827
"github.com/pborman/uuid"
@@ -769,33 +768,36 @@ func (c *CertTable) GetByGUIDString(guid string) ([]byte, error) {
769768
// so missing certificates aren't an error. If certificates are missing, you can
770769
// choose to fetch them yourself by calling verify.GetAttestationFromReport.
771770
func (c *CertTable) Proto() *pb.CertificateChain {
772-
var vcek, vlek, ask, ark []byte
773-
var err, cerr, lerr error
774-
// Whereas a host is permitted to populate its certificate chain blob with both a VCEK and VLEK
775-
// certificate, doing so is unusual since the choice of VCEK vs VLEK is an infrastructural choice.
776-
// To keep the implementation clean, we don't pun vcek and vlek in the same field.
777-
vcek, cerr = c.GetByGUIDString(VcekGUID)
778-
vlek, lerr = c.GetByGUIDString(VlekGUID)
779-
if cerr != nil && lerr != nil {
771+
vcekGUID := uuid.Parse(VcekGUID)
772+
vlekGUID := uuid.Parse(VlekGUID)
773+
askGUID := uuid.Parse(AskGUID)
774+
arkGUID := uuid.Parse(ArkGUID)
775+
result := &pb.CertificateChain{Extras: make(map[string][]byte)}
776+
for _, entry := range c.Entries {
777+
switch {
778+
case uuid.Equal(entry.GUID, vcekGUID):
779+
result.VcekCert = entry.RawCert
780+
case uuid.Equal(entry.GUID, vlekGUID):
781+
result.VlekCert = entry.RawCert
782+
case uuid.Equal(entry.GUID, askGUID):
783+
result.AskCert = entry.RawCert
784+
case uuid.Equal(entry.GUID, arkGUID):
785+
result.ArkCert = entry.RawCert
786+
default:
787+
result.Extras[entry.GUID.String()] = entry.RawCert
788+
}
789+
}
790+
if (result.VcekCert == nil) && (result.VlekCert == nil) {
780791
logger.Warning("Warning: Neither VCEK nor VLEK certificate found in data pages")
781792
}
782793

783-
ask, err = c.GetByGUIDString(AskGUID)
784-
if err != nil {
785-
logger.Warningf("ASK certificate not found in data pages: %v", err)
786-
}
787-
ark, err = c.GetByGUIDString(ArkGUID)
788-
if err != nil {
789-
logger.Warningf("ARK certificate not found in data pages: %v", err)
794+
if result.AskCert == nil {
795+
logger.Warningf("ASK certificate not found in data pages")
790796
}
791-
firmware, _ := c.GetByGUIDString(gce.FirmwareCertGUID)
792-
return &pb.CertificateChain{
793-
VcekCert: vcek,
794-
VlekCert: vlek,
795-
AskCert: ask,
796-
ArkCert: ark,
797-
FirmwareCert: firmware,
797+
if result.ArkCert == nil {
798+
logger.Warningf("ARK certificate not found in data pages")
798799
}
800+
return result
799801
}
800802

801803
// cpuid returns the 4 register results of CPUID[EAX=op,ECX=0].

abi/abi_test.go

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,11 +15,14 @@
1515
package abi
1616

1717
import (
18+
"bytes"
19+
"encoding/hex"
1820
"math/rand"
1921
"strings"
2022
"testing"
2123

2224
spb "github.com/google/go-sev-guest/proto/sevsnp"
25+
"github.com/pborman/uuid"
2326
"google.golang.org/protobuf/encoding/prototext"
2427
)
2528

@@ -208,3 +211,52 @@ func TestSnpPlatformInfo(t *testing.T) {
208211
}
209212
}
210213
}
214+
215+
func TestCertTableProto(t *testing.T) {
216+
headers := make([]CertTableHeaderEntry, 6) // ARK, ASK, VCEK, VLEK, extra, NULL
217+
arkraw := []byte("ark")
218+
askraw := []byte("ask")
219+
vcekraw := []byte("vcek")
220+
vlekraw := []byte("vlek")
221+
extraraw := []byte("extra")
222+
headers[0].GUID = uuid.Parse(ArkGUID)
223+
headers[0].Offset = uint32(len(headers) * CertTableEntrySize)
224+
headers[0].Length = uint32(len(arkraw))
225+
226+
headers[1].GUID = uuid.Parse(AskGUID)
227+
headers[1].Offset = headers[0].Offset + headers[0].Length
228+
headers[1].Length = uint32(len(askraw))
229+
230+
headers[2].GUID = uuid.Parse(VcekGUID)
231+
headers[2].Offset = headers[1].Offset + headers[1].Length
232+
headers[2].Length = uint32(len(vcekraw))
233+
234+
headers[3].GUID = uuid.Parse(VlekGUID)
235+
headers[3].Offset = headers[2].Offset + headers[2].Length
236+
headers[3].Length = uint32(len(vlekraw))
237+
238+
extraGUID := "00000000-0000-c0de-0000-000000000000"
239+
headers[4].GUID = uuid.Parse(extraGUID)
240+
headers[4].Offset = headers[3].Offset + headers[3].Length
241+
headers[4].Length = uint32(len(extraraw))
242+
243+
result := make([]byte, headers[4].Offset+headers[4].Length)
244+
for i, cert := range [][]byte{arkraw, askraw, vcekraw, vlekraw, extraraw} {
245+
if err := (&headers[i]).Write(result[i*CertTableEntrySize:]); err != nil {
246+
t.Fatalf("could not write header %d: %v", i, err)
247+
}
248+
copy(result[headers[i].Offset:], cert)
249+
}
250+
c := new(CertTable)
251+
if err := c.Unmarshal(result); err != nil {
252+
t.Errorf("c.Unmarshal(%s) = %v, want nil", hex.Dump(result), err)
253+
}
254+
p := c.Proto()
255+
if len(p.Extras) != 1 {
256+
t.Fatalf("got cert table Extras length %d, want 1", len(p.Extras))
257+
}
258+
gotExtra, ok := p.Extras[extraGUID]
259+
if !ok || !bytes.Equal(gotExtra, extraraw) {
260+
t.Fatalf("Extras[%q] = %v, want %v", extraGUID, gotExtra, extraraw)
261+
}
262+
}

gce/gce.go

Lines changed: 0 additions & 19 deletions
This file was deleted.

proto/check/check.pb.go

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

proto/fakekds/fakekds.pb.go

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

proto/sevsnp.proto

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,10 @@ message CertificateChain {
7272

7373
// A certificate the host may inject to endorse the measurement of the
7474
// firmware.
75-
bytes firmware_cert = 4;
75+
bytes firmware_cert = 4 [deprecated = true];
76+
77+
// Non-standard certificates the host may inject.
78+
map<string, bytes> extras = 7;
7679
}
7780

7881
// The CPUID[EAX=1] version information includes product info as described in

proto/sevsnp/sevsnp.pb.go

Lines changed: 65 additions & 43 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)