diff options
Diffstat (limited to 'internal/monitor')
-rw-r--r-- | internal/monitor/monitor.go | 7 | ||||
-rw-r--r-- | internal/monitor/tail.go | 72 |
2 files changed, 22 insertions, 57 deletions
diff --git a/internal/monitor/monitor.go b/internal/monitor/monitor.go index 6de7193..2fe4d88 100644 --- a/internal/monitor/monitor.go +++ b/internal/monitor/monitor.go @@ -11,6 +11,7 @@ package monitor import ( "context" + "crypto/sha256" "crypto/x509" "encoding/base64" "fmt" @@ -32,10 +33,12 @@ type MonitoredLog struct { } // State is the latest append-only state the monitor observed from its local -// vantage point. The next entry to download is specified by NextIndex. +// vantage point. The compact range covers [0, NextIndex). The next entry to +// download from the log is at index NextIndex. type State struct { ct.SignedTreeHead `json:"latest_sth"` - NextIndex uint64 `json:"next_index"` + CompactRange [][sha256.Size]byte `json:"compact_range"` + NextIndex uint64 `json:"next_index"` } // Event carries the latest consistent monitor state, found matches, as well as diff --git a/internal/monitor/tail.go b/internal/monitor/tail.go index 0e16476..6be165b 100644 --- a/internal/monitor/tail.go +++ b/internal/monitor/tail.go @@ -2,15 +2,14 @@ package monitor import ( "context" - "crypto/sha256" "fmt" "sync" - "time" - ct "github.com/google/certificate-transparency-go" "github.com/google/certificate-transparency-go/client" "github.com/google/certificate-transparency-go/scanner" "gitlab.torproject.org/rgdd/ct/pkg/merkle" + "rgdd.se/silent-ct/internal/ioutil" + "rgdd.se/silent-ct/internal/logutil" ) type tail struct { @@ -118,7 +117,7 @@ func (t *tail) nextState(ctx context.Context, state State, c *chunk) (State, err } func (t *tail) nextConsistentState(ctx context.Context, state State) (State, error) { - sth, err := getSignedTreeHead(ctx, t.checker) + sth, err := logutil.GetSignedTreeHead(ctx, t.checker) if err != nil { return State{}, fmt.Errorf("%s: get-sth: %v", t.checker.BaseURI(), err) } @@ -128,73 +127,36 @@ func (t *tail) nextConsistentState(ctx context.Context, state State) (State, err newSize := sth.TreeSize newRoot := sth.SHA256RootHash - proof, err := getConsistencyProof(ctx, t.checker, oldSize, newSize) + proof, err := logutil.GetConsistencyProof(ctx, t.checker, oldSize, newSize) if err != nil { return State{}, fmt.Errorf("%s: get-consistency: %v", t.checker.BaseURI(), err) } - if err := merkle.VerifyConsistency(oldSize, newSize, oldRoot, newRoot, unslice(proof)); err != nil { + if err := merkle.VerifyConsistency(oldSize, newSize, oldRoot, newRoot, proof); err != nil { return State{}, fmt.Errorf("%s: verify consistency: %v", t.checker.BaseURI(), err) } - return State{SignedTreeHead: *sth, NextIndex: state.NextIndex}, nil + return State{SignedTreeHead: *sth, CompactRange: ioutil.CopyHashes(state.CompactRange), NextIndex: state.NextIndex}, nil } func (t *tail) nextIncludedState(ctx context.Context, state State, c *chunk) (State, error) { - leafHash := c.leafHashes[0] - oldSize := state.NextIndex + uint64(len(c.leafHashes)) - iproof, err := getInclusionProof(ctx, t.checker, leafHash, oldSize) // FIXME: set leaf index in ctx to hack into tile API - if err != nil { - return State{}, fmt.Errorf("%s: get-inclusion: %v", t.checker.BaseURI(), err) - } - if got, want := uint64(iproof.LeafIndex), state.NextIndex; got != want { - return State{}, fmt.Errorf("%s: wrong index for get-inclusion proof query %x:%d", t.checker.BaseURI(), leafHash[:], oldSize) - } - oldRoot, err := merkle.TreeHeadFromRangeProof(c.leafHashes, state.NextIndex, unslice(iproof.AuditPath)) + cr, err := logutil.AppendCompactRange(state.CompactRange, state.NextIndex, c.leafHashes) if err != nil { - return State{}, fmt.Errorf("%s: range proof: %v", t.checker.BaseURI(), err) + panic(fmt.Sprintf("bug: %v", err)) } - - newSize := state.TreeSize + oldRoot := logutil.RootHash(cr) + oldSize := state.NextIndex + uint64(len(c.leafHashes)) newRoot := state.SHA256RootHash - cproof, err := getConsistencyProof(ctx, t.checker, oldSize, newSize) + newSize := state.TreeSize + + proof, err := logutil.GetConsistencyProof(ctx, t.checker, oldSize, newSize) if err != nil { - return State{}, fmt.Errorf("%s: get-consistency: %v", t.checker.BaseURI(), err) + return State{}, fmt.Errorf("%s: tree: get-consistency: %v", t.checker.BaseURI(), err) } - if err := merkle.VerifyConsistency(oldSize, newSize, oldRoot, newRoot, unslice(cproof)); err != nil { - return State{}, fmt.Errorf("%s: verify consistency: %v", t.checker.BaseURI(), err) + if err := merkle.VerifyConsistency(oldSize, newSize, oldRoot, newRoot, proof); err != nil { + return State{}, fmt.Errorf("%s: tree: verify consistency: %v", t.checker.BaseURI(), err) } state.NextIndex += uint64(len(c.leafHashes)) + state.CompactRange = ioutil.UnsliceHashes(cr.Hashes()) return state, nil } - -func getInclusionProof(ctx context.Context, cli client.CheckLogClient, leafHash [sha256.Size]byte, size uint64) (*ct.GetProofByHashResponse, error) { - rctx, cancel := context.WithTimeout(ctx, 10*time.Second) - defer cancel() - return cli.GetProofByHash(rctx, leafHash[:], size) -} - -func getConsistencyProof(ctx context.Context, cli client.CheckLogClient, oldSize, newSize uint64) ([][]byte, error) { - if oldSize == 0 || oldSize >= newSize { - return [][]byte{}, nil - } - rctx, cancel := context.WithTimeout(ctx, 10*time.Second) - defer cancel() - return cli.GetSTHConsistency(rctx, oldSize, newSize) -} - -func getSignedTreeHead(ctx context.Context, cli client.CheckLogClient) (*ct.SignedTreeHead, error) { - rctx, cancel := context.WithTimeout(ctx, 10*time.Second) - defer cancel() - return cli.GetSTH(rctx) -} - -func unslice(hashes [][]byte) [][sha256.Size]byte { - var ret [][sha256.Size]byte - for _, hash := range hashes { - var h [sha256.Size]byte - copy(h[:], hash) - ret = append(ret, h) - } - return ret -} |