-
Notifications
You must be signed in to change notification settings - Fork 807
Add Maybe to the end bound of proofs (Part 1) #1793
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from 29 commits
1d62cda
aa84659
4124fcd
48100d4
15bbbed
02a6ec7
4a7d224
3d44e2d
f931491
716d27b
06f7433
d2c0e6e
869249c
c4d3100
67df793
a005025
48f05c0
b5ec872
2a00683
2439323
20426dd
9d5290b
f5be4fc
8d88e88
c6f57da
9cefc79
f174079
b2a3bd8
1885715
1838bdc
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Large diffs are not rendered by default.
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -70,7 +70,7 @@ type ChangeProofer interface { | |
// - [proof] is non-empty iff [proof.HadRootsInHistory]. | ||
// - All keys in [proof.KeyValues] and [proof.DeletedKeys] are in [start, end]. | ||
// If [start] is empty, all keys are considered > [start]. | ||
// If [end] is empty, all keys are considered < [end]. | ||
// If [end] is nothing, all keys are considered < [end]. | ||
// - [proof.KeyValues] and [proof.DeletedKeys] are sorted in order of increasing key. | ||
// - [proof.StartProof] and [proof.EndProof] are well-formed. | ||
// - When the keys in [proof.KeyValues] are added to [db] and the keys in [proof.DeletedKeys] | ||
|
@@ -83,7 +83,7 @@ type ChangeProofer interface { | |
ctx context.Context, | ||
proof *ChangeProof, | ||
start []byte, | ||
end []byte, | ||
end Maybe[[]byte], | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Should we also use There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Part 2 |
||
expectedEndRootID ids.ID, | ||
) error | ||
|
||
|
@@ -582,20 +582,22 @@ func (db *merkleDB) GetChangeProof( | |
}) | ||
} | ||
|
||
largestKey := end | ||
largestKey := Nothing[[]byte]() | ||
if len(result.KeyChanges) > 0 { | ||
largestKey = result.KeyChanges[len(result.KeyChanges)-1].Key | ||
largestKey = Some(result.KeyChanges[len(result.KeyChanges)-1].Key) | ||
} else if len(end) > 0 { | ||
largestKey = Some(end) | ||
} | ||
|
||
// Since we hold [db.commitlock] we must still have sufficient | ||
// history to recreate the trie at [endRootID]. | ||
historicalView, err := db.getHistoricalViewForRange(endRootID, start, largestKey) | ||
historicalView, err := db.getHistoricalViewForRange(endRootID, start, largestKey.Value()) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
if len(largestKey) > 0 { | ||
endProof, err := historicalView.getProof(ctx, largestKey) | ||
if largestKey.HasValue() { | ||
endProof, err := historicalView.getProof(ctx, largestKey.Value()) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
@@ -958,10 +960,10 @@ func (db *merkleDB) VerifyChangeProof( | |
ctx context.Context, | ||
proof *ChangeProof, | ||
start []byte, | ||
end []byte, | ||
end Maybe[[]byte], | ||
expectedEndRootID ids.ID, | ||
) error { | ||
if len(end) > 0 && bytes.Compare(start, end) > 0 { | ||
if end.HasValue() && bytes.Compare(start, end.Value()) > 0 { | ||
return ErrStartAfterEnd | ||
} | ||
|
||
|
@@ -978,7 +980,7 @@ func (db *merkleDB) VerifyChangeProof( | |
switch { | ||
case proof.Empty(): | ||
return ErrNoMerkleProof | ||
case len(end) > 0 && len(proof.EndProof) == 0: | ||
case end.HasValue() && len(proof.EndProof) == 0: | ||
// We requested an end proof but didn't get one. | ||
return ErrNoEndProof | ||
case len(start) > 0 && len(proof.StartProof) == 0 && len(proof.EndProof) == 0: | ||
|
@@ -1004,17 +1006,18 @@ func (db *merkleDB) VerifyChangeProof( | |
// Find the greatest key in [proof.KeyChanges] | ||
// Note that [proof.EndProof] is a proof for this key. | ||
// [largestPath] is also used when we add children of proof nodes to [trie] below. | ||
largestKey := end | ||
largestPath := Nothing[path]() | ||
if len(proof.KeyChanges) > 0 { | ||
// If [proof] has key-value pairs, we should insert children | ||
// greater than [end] to ancestors of the node containing [end] | ||
// so that we get the expected root ID. | ||
largestKey = proof.KeyChanges[len(proof.KeyChanges)-1].Key | ||
largestPath = Some(newPath(proof.KeyChanges[len(proof.KeyChanges)-1].Key)) | ||
} else if end.HasValue() { | ||
largestPath = Some(newPath(end.Value())) | ||
} | ||
largestPath := newPath(largestKey) | ||
|
||
// Make sure the end proof, if given, is well-formed. | ||
if err := verifyProofPath(proof.EndProof, largestPath); err != nil { | ||
if err := verifyProofPath(proof.EndProof, largestPath.Value()); err != nil { | ||
return err | ||
} | ||
|
||
|
@@ -1074,23 +1077,19 @@ func (db *merkleDB) VerifyChangeProof( | |
if len(smallestPath) > 0 { | ||
dboehm-avalabs marked this conversation as resolved.
Show resolved
Hide resolved
|
||
insertChildrenLessThan = Some(smallestPath) | ||
} | ||
insertChildrenGreaterThan := Nothing[path]() | ||
if len(largestPath) > 0 { | ||
insertChildrenGreaterThan = Some(largestPath) | ||
} | ||
if err := addPathInfo( | ||
view, | ||
proof.StartProof, | ||
insertChildrenLessThan, | ||
insertChildrenGreaterThan, | ||
largestPath, | ||
); err != nil { | ||
return err | ||
} | ||
if err := addPathInfo( | ||
view, | ||
proof.EndProof, | ||
insertChildrenLessThan, | ||
insertChildrenGreaterThan, | ||
largestPath, | ||
); err != nil { | ||
return err | ||
} | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -770,10 +770,14 @@ func runRandDBTest(require *require.Assertions, r *rand.Rand, rt randTest) { | |
} | ||
rangeProof, err := db.GetRangeProofAtRoot(context.Background(), root, step.key, step.value, 100) | ||
require.NoError(err) | ||
end := Nothing[[]byte]() | ||
if len(step.value) > 0 { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. nit: should we update the comments on the randStep struct to mention value/key are used differently for getting range/change proofs? |
||
end = Some(step.value) | ||
} | ||
require.NoError(rangeProof.Verify( | ||
context.Background(), | ||
step.key, | ||
step.value, | ||
end, | ||
root, | ||
)) | ||
require.LessOrEqual(len(rangeProof.KeyValues), 100) | ||
|
@@ -791,11 +795,15 @@ func runRandDBTest(require *require.Assertions, r *rand.Rand, rt randTest) { | |
require.NoError(err) | ||
changeProofDB, err := getBasicDB() | ||
require.NoError(err) | ||
end := Nothing[[]byte]() | ||
if len(step.value) > 0 { | ||
end = Some(step.value) | ||
} | ||
require.NoError(changeProofDB.VerifyChangeProof( | ||
context.Background(), | ||
changeProof, | ||
step.key, | ||
step.value, | ||
end, | ||
root, | ||
)) | ||
require.LessOrEqual(len(changeProof.KeyChanges), 100) | ||
|
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Uh oh!
There was an error while loading. Please reload this page.