From d58be1cb16e62a9821b6dbd0157b8c7ff0b667ec Mon Sep 17 00:00:00 2001 From: Filippo Valsorda Date: Wed, 5 Jun 2024 11:25:04 +0200 Subject: [PATCH] sumdb/tlog: set the hash of the empty tree according to RFC 6962 Updates FiloSottile/sunlight#14 Change-Id: I712ea53fd3a17b66ec310d8f48de44416d0054cc Reviewed-on: https://go-review.googlesource.com/c/mod/+/590715 Reviewed-by: Russ Cox Auto-Submit: Filippo Valsorda LUCI-TryBot-Result: Go LUCI Reviewed-by: Joedian Reid --- sumdb/client.go | 8 ++++++++ sumdb/tlog/tlog.go | 12 ++++++++++-- sumdb/tlog/tlog_test.go | 11 +++++++++++ 3 files changed, 29 insertions(+), 2 deletions(-) diff --git a/sumdb/client.go b/sumdb/client.go index 04c6e24..04dbdfe 100644 --- a/sumdb/client.go +++ b/sumdb/client.go @@ -142,6 +142,14 @@ func (c *Client) initWork() { c.verifiers = note.VerifierList(verifier) c.name = verifier.Name() + if c.latest.N == 0 { + c.latest.Hash, err = tlog.TreeHash(0, nil) + if err != nil { + c.initErr = err + return + } + } + data, err := c.ops.ReadConfig(c.name + "/latest") if err != nil { c.initErr = err diff --git a/sumdb/tlog/tlog.go b/sumdb/tlog/tlog.go index 6a11a75..f7ea753 100644 --- a/sumdb/tlog/tlog.go +++ b/sumdb/tlog/tlog.go @@ -234,14 +234,22 @@ func (f HashReaderFunc) ReadHashes(indexes []int64) ([]Hash, error) { return f(indexes) } +// emptyHash is the hash of the empty tree, per RFC 6962, Section 2.1. +// It is the hash of the empty string. +var emptyHash = Hash{ + 0xe3, 0xb0, 0xc4, 0x42, 0x98, 0xfc, 0x1c, 0x14, + 0x9a, 0xfb, 0xf4, 0xc8, 0x99, 0x6f, 0xb9, 0x24, + 0x27, 0xae, 0x41, 0xe4, 0x64, 0x9b, 0x93, 0x4c, + 0xa4, 0x95, 0x99, 0x1b, 0x78, 0x52, 0xb8, 0x55, +} + // TreeHash computes the hash for the root of the tree with n records, // using the HashReader to obtain previously stored hashes // (those returned by StoredHashes during the writes of those n records). // TreeHash makes a single call to ReadHash requesting at most 1 + logâ‚‚ n hashes. -// The tree of size zero is defined to have an all-zero Hash. func TreeHash(n int64, r HashReader) (Hash, error) { if n == 0 { - return Hash{}, nil + return emptyHash, nil } indexes := subTreeIndex(0, n, nil) hashes, err := r.ReadHashes(indexes) diff --git a/sumdb/tlog/tlog_test.go b/sumdb/tlog/tlog_test.go index 584e728..79db244 100644 --- a/sumdb/tlog/tlog_test.go +++ b/sumdb/tlog/tlog_test.go @@ -6,6 +6,7 @@ package tlog import ( "bytes" + "crypto/sha256" "fmt" "testing" ) @@ -267,3 +268,13 @@ func TestTilePath(t *testing.T) { } } } + +func TestEmptyTree(t *testing.T) { + h, err := TreeHash(0, nil) + if err != nil { + t.Fatal(err) + } + if h != sha256.Sum256(nil) { + t.Fatalf("TreeHash(0) = %x, want SHA-256('')", h) + } +}