-
Notifications
You must be signed in to change notification settings - Fork 220
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
Warp stapling block context #823
Conversation
…dicates with gomocks
Co-authored-by: Darioush Jalali <darioush.jalali@avalabs.org> Signed-off-by: aaronbuchwald <aaron.buchwald56@gmail.com>
@@ -59,7 +59,7 @@ func (*configurator) MakeConfig() precompileconfig.Config { | |||
// This function is called by the EVM once per precompile contract activation. | |||
// You can use this function to set up your precompile contract's initial state, | |||
// by using the [cfg] config and [state] stateDB. | |||
func (*configurator) Configure(chainConfig precompileconfig.ChainConfig, cfg precompileconfig.Config, state contract.StateDB, blockContext contract.BlockContext) error { | |||
func (*configurator) Configure(chainConfig precompileconfig.ChainConfig, cfg precompileconfig.Config, state contract.StateDB, blockContext contract.ConfigurationBlockContext) error { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can be broken into a separate preparation PR if preferred
} | ||
|
||
for address, predicates := range predicateArguments { | ||
predicate := rules.Predicates[address] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: add comment noting that if predicateArguments
was populated with this address, then the predicate must be present in rules.Predicates
return fmt.Errorf("predicate %s failed verification for tx %s: %w", address, tx.Hash(), err) | ||
} | ||
|
||
predicateArguments[address] = append(predicateArguments[address], predicateutils.HashSliceToBytes(accessTuple.StorageKeys)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why do we append those instead of directly verify each predicate here and set the result bit set here instead of VerifyPredicate
? I feel like we can save at least 2 loops here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This was so that the predicate can take in all of the byte slices for the transaction in one call rather than doing it one at a time and return the bit set as a byte slice.
Alternatively, we could switch back to VerifyPredicate
taking in a single value and CheckPredicates
assembling the bit set from those results. This would make the code a bit simpler at the cost of constraining the precompile predicates to return a true/false value instead of an arbitrary byte array.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I feel like using a single value for VerifyPredicate
could be simpler + cleaner (and costs less loops). It would be easier for 3rd party implementations as well.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could we make this a follow-on PR to try out the alternative?
This also means that we need to track the indices used by each precompile address to create that bitset, so I'm not sure if it will be cleaner.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Created #844
core/state/statedb.go
Outdated
func (s *StateDB) GetTxHash() common.Hash { | ||
return s.thash | ||
} | ||
|
||
// GetPredicateStorageSlots returns the storage slots associated with a given address, and whether or not |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
add index
to comments
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Updated the comment on GetPredicateStorageSlots
to include an example and added a comment to GetTxHash
type TxPredicateResults map[common.Address][]byte | ||
|
||
// PredicateResults encodes the precompile predicate results included in a block on a per transaction basis. | ||
// PredicateResults is not thread-safe. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
don't we need this to be thread-safe?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We currently only modify this synchronously in the worker and during block verification. It is only read from the EVM when it is either a unique instance or is being used synchronously in the worker. For the APIs that may re-use a block context, they will only perform read operations on an instance that is never modified.
We could make it thread-safe, but I don't think it's necessary atm. Is there a specific case you're concerned about?
x/warp/contract.go
Outdated
if !warpIndex.IsInt64() { | ||
return nil, false | ||
} | ||
warpIndexInt := int(warpIndex.Int64()) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
paranoid 🤖: could someone issue a very big int (MaxInt32<x<MaxInt64) and cause this casting to be not lossless (in 32-bit systems)?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ya I'll update the input type to uint32 so that we don't have to do this at all.
core/state/statedb.go
Outdated
if !exists { | ||
return nil, false | ||
} | ||
if index >= len(predicates) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should we check if index is negative (or simply require uint64 indexes here)?
this is related to the comment about lossless conversion between int<>int64 below.
* Warp stapling block context (#823) * Add GetPredicateResults to BlockContext * Serve predicate results from blockContext * Allow extra data to extend past DynamicFeeWindow post DUpgrade * Get vm warp unit tests working * Bump ANR to intermediate version to fix incompatibility with AvalancheGo * Add kc to EthKeyChain * Bump avalanchego dep in scripts for CI * Add block hash payload support * Use gomocks for precompileconfig and predicater and re-write CheckPredicates with gomocks * Use gomock for mock accessible state and block context * Fix existing warp contract tests with mock block context * Remove unused mockPredicater impl * x/warp: add contract execution unit tests * Update NewEVMBlockContext * Add AppendExtra to syncervm to fix tests * x/warp: add unit test for multiple predicate results * core: add unit test for CheckPredicates insufficient gas * Update receive warp message test to trace block and assert the expected result * Fix lint * Update warp solidity contracts * Fix block context mocks for bench * Update precompile/precompileconfig/config.go Co-authored-by: Darioush Jalali <darioush.jalali@avalabs.org> Signed-off-by: aaronbuchwald <aaron.buchwald56@gmail.com> * Cleanup * precompile/results: Add predicate results tests + comments * nits * precompile/results: omit tx predicate results if empty * core: add invariant comment to predicate check * Address PR comments * Fix unpackWarpMessage and add unit tests * Rename OriginChainID -> SourceChainID to match ago warp message type * nits * x/warp: set public key in warp predicate unit tests * Update payload format * Clarify IWarpMessenger verified message return types * core/state: improve statedb warp specific comments * Update input param type to uint32 to avoid potential overflow on conversion * Update GetPredicateStorageSlots arg type to uint32 * warp/payload: add README for payload serialization (#835) * Fix merge * x/warp: add unit test for PrimaryNetwork to Subnet predicate verification (#831) * precompilebind: add ChainConfig with DUpgrade enabled to precompile chain config verify template
* update npm package * expand allowlist.configure * add activation func to precompile functions * move chainconfig to precompileconfig * use chainconfig in verification * trim unnecessary changes * add manager role * fix tests * add verify test * nits * add mocks * reviews * fix linter * fix benchmarks * nits * nits * fix alow list bind tests & ensure they're being tested (#841) * simplify can modify check * fix vm tests * Add manager allowlist role merge (#850) * Warp stapling block context (#823) * Add GetPredicateResults to BlockContext * Serve predicate results from blockContext * Allow extra data to extend past DynamicFeeWindow post DUpgrade * Get vm warp unit tests working * Bump ANR to intermediate version to fix incompatibility with AvalancheGo * Add kc to EthKeyChain * Bump avalanchego dep in scripts for CI * Add block hash payload support * Use gomocks for precompileconfig and predicater and re-write CheckPredicates with gomocks * Use gomock for mock accessible state and block context * Fix existing warp contract tests with mock block context * Remove unused mockPredicater impl * x/warp: add contract execution unit tests * Update NewEVMBlockContext * Add AppendExtra to syncervm to fix tests * x/warp: add unit test for multiple predicate results * core: add unit test for CheckPredicates insufficient gas * Update receive warp message test to trace block and assert the expected result * Fix lint * Update warp solidity contracts * Fix block context mocks for bench * Update precompile/precompileconfig/config.go Co-authored-by: Darioush Jalali <darioush.jalali@avalabs.org> Signed-off-by: aaronbuchwald <aaron.buchwald56@gmail.com> * Cleanup * precompile/results: Add predicate results tests + comments * nits * precompile/results: omit tx predicate results if empty * core: add invariant comment to predicate check * Address PR comments * Fix unpackWarpMessage and add unit tests * Rename OriginChainID -> SourceChainID to match ago warp message type * nits * x/warp: set public key in warp predicate unit tests * Update payload format * Clarify IWarpMessenger verified message return types * core/state: improve statedb warp specific comments * Update input param type to uint32 to avoid potential overflow on conversion * Update GetPredicateStorageSlots arg type to uint32 * warp/payload: add README for payload serialization (#835) * Fix merge * x/warp: add unit test for PrimaryNetwork to Subnet predicate verification (#831) * precompilebind: add ChainConfig with DUpgrade enabled to precompile chain config verify template
* Add GetPredicateResults to BlockContext * Serve predicate results from blockContext * Allow extra data to extend past DynamicFeeWindow post DUpgrade * Get vm warp unit tests working * Bump ANR to intermediate version to fix incompatibility with AvalancheGo * Add kc to EthKeyChain * Bump avalanchego dep in scripts for CI * Add block hash payload support * Use gomocks for precompileconfig and predicater and re-write CheckPredicates with gomocks * Use gomock for mock accessible state and block context * Fix existing warp contract tests with mock block context * Remove unused mockPredicater impl * x/warp: add contract execution unit tests * Update NewEVMBlockContext * Add AppendExtra to syncervm to fix tests * x/warp: add unit test for multiple predicate results * core: add unit test for CheckPredicates insufficient gas * Update receive warp message test to trace block and assert the expected result * Fix lint * Update warp solidity contracts * Fix block context mocks for bench * Update precompile/precompileconfig/config.go Co-authored-by: Darioush Jalali <darioush.jalali@avalabs.org> Signed-off-by: aaronbuchwald <aaron.buchwald56@gmail.com> * Cleanup * precompile/results: Add predicate results tests + comments * nits * precompile/results: omit tx predicate results if empty * core: add invariant comment to predicate check * Address PR comments * Fix unpackWarpMessage and add unit tests * Rename OriginChainID -> SourceChainID to match ago warp message type * nits * x/warp: set public key in warp predicate unit tests * Update payload format * Clarify IWarpMessenger verified message return types * core/state: improve statedb warp specific comments * Update input param type to uint32 to avoid potential overflow on conversion * Update GetPredicateStorageSlots arg type to uint32 * warp/payload: add README for payload serialization (#835) * Fix merge
* update npm package * expand allowlist.configure * add activation func to precompile functions * move chainconfig to precompileconfig * use chainconfig in verification * trim unnecessary changes * add manager role * fix tests * add verify test * nits * add mocks * reviews * fix linter * fix benchmarks * nits * nits * fix alow list bind tests & ensure they're being tested (#841) * simplify can modify check * fix vm tests * Add manager allowlist role merge (#850) * Warp stapling block context (#823) * Add GetPredicateResults to BlockContext * Serve predicate results from blockContext * Allow extra data to extend past DynamicFeeWindow post DUpgrade * Get vm warp unit tests working * Bump ANR to intermediate version to fix incompatibility with AvalancheGo * Add kc to EthKeyChain * Bump avalanchego dep in scripts for CI * Add block hash payload support * Use gomocks for precompileconfig and predicater and re-write CheckPredicates with gomocks * Use gomock for mock accessible state and block context * Fix existing warp contract tests with mock block context * Remove unused mockPredicater impl * x/warp: add contract execution unit tests * Update NewEVMBlockContext * Add AppendExtra to syncervm to fix tests * x/warp: add unit test for multiple predicate results * core: add unit test for CheckPredicates insufficient gas * Update receive warp message test to trace block and assert the expected result * Fix lint * Update warp solidity contracts * Fix block context mocks for bench * Update precompile/precompileconfig/config.go Co-authored-by: Darioush Jalali <darioush.jalali@avalabs.org> Signed-off-by: aaronbuchwald <aaron.buchwald56@gmail.com> * Cleanup * precompile/results: Add predicate results tests + comments * nits * precompile/results: omit tx predicate results if empty * core: add invariant comment to predicate check * Address PR comments * Fix unpackWarpMessage and add unit tests * Rename OriginChainID -> SourceChainID to match ago warp message type * nits * x/warp: set public key in warp predicate unit tests * Update payload format * Clarify IWarpMessenger verified message return types * core/state: improve statedb warp specific comments * Update input param type to uint32 to avoid potential overflow on conversion * Update GetPredicateStorageSlots arg type to uint32 * warp/payload: add README for payload serialization (#835) * Fix merge * x/warp: add unit test for PrimaryNetwork to Subnet predicate verification (#831) * precompilebind: add ChainConfig with DUpgrade enabled to precompile chain config verify template
Why this should be merged
This PR addresses #735 and #734
How this works
This PR creates a predicate results type to encode the per-transaction predicate results into the block header. This is intended to remove the possibility that predicate verification may fail and require dropping the transaction from the mempool/block, which creates a potential DoS vector as per: https://ethresear.ch/t/dos-vectors-in-account-abstraction-aa-or-validation-generalization-a-case-study-in-geth/7937.
Additionally, this PR adds a
BlockHashPayload
to allow signing a block hash instead of the existing point-to-pointAddressedPayload
.To handle the
BlockHashPayload
this PR adds a new functiongetVerifiedWarpBlockHash
to read the verified block hash and return it to the caller.How this was tested
traceBlock
)How is this documented
TODO: update Warp README