Repository navigation
fix(grovedb): require proofs to descend to the query path - #12
Merged
Merged
Conversation
GroveDB's layered verifier finds the next layer by the proof envelope's lower_layers map key, which is not hash-bound. A prover who renames or drops the entry for a subtree on the query path gets the same root hash with that subtree's results silently gone, so a proof of one value verifies as a proof of absence. checkEnvelope walks the envelope down every segment of the query path and pins prove_options to the chain default; verifyItemProof and verifyQueryProof pass the path through when they have it.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
GroveDB's layered verifier looks the next layer up by the proof envelope's
lower_layersmap key, and that key is not hash-bound. A prover who renames or drops the entry for a subtree on the query path gets the same root hash with that subtree's results silently gone — a proof ofK = Vverifies as a proof thatKis absent.This adds
checkEnvelope(proof, expectedPath): the envelope must carry a lower layer for every segment of the query path (once a layer is present its root is hash-bound to the parent), nothing may hang below the path, andprove_options— prover-chosen bytes that steer limit accounting — is pinned to the chain default.verifyGroveDBProoftakesexpectedPath;verifyItemProofpasses itspaththrough;verifyQueryProoftakesoptions.path.The TS verifier was already refusing the renamed-layer case by accident — the orphaned tree node falls into the leaf branch and its value bytes fail the committed-valueHash binding — so for this SDK the change is a stated property with a precise error, plus the
prove_optionspin. The fixtures are real grovedb 3.1.0 proofs over the indexed-data layout[subgroves, aave-v3-lending, indexed, Supply].Testing
real proofs verify to the root at their path— four real proofs (single key, range, absent key, limited range) verify at their path with the right result counts.without the path check … leaf binding— pins that the bare verifier still rejects the renamed layer, and why.renamed lower layer is rejected at the query path/dropped lower layer …— both forgeries fail withdoes not descend.a shorter or longer path is rejected— the path must match the envelope exactly.non-default prove_options is rejected even without a path.verifyItemProof descends when given the path/verifyQueryProof descends when options.path is given— the wrappers wire it.prove_optionsbyte like every real proof; the fixture test accepts the new wrong-path message.Full suite: 485 passed (481 before), 11 skipped.
Why
A client that treats "not in the results" as "absent" would accept a lie of omission from any API server, with a valid root. Requiring the proof to reach the queried path is what makes an empty result at that path a proven absence.