Skip to content
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

Add initial StateTransitioner & FraudProver #156

Conversation

karlfloersch
Copy link
Contributor

@karlfloersch karlfloersch commented Jun 15, 2020

Description

This PR adds a StateTransitioner & a FraudProver and a bunch of helper contracts to build up a first pass fraud proof system. It does not have good test coverage, but it does have enough that I think it mostly works & most importantly gets the point across.

TODO in later PR

  • We've got to update the ExecutionManager to use getOvmContractHash(..) instead of calling the codeContractHash version of the function. I didn't include this in this PR because @ben-chain is touching a bunch of EM stuff & so I don't want to make too many medium-sized changes to the EM at the same time

Metadata

Fixes

  • YAS-200
  • YAS-201
  • YAS-203

Contributing Agreement

* @param _codeContractAddress The address of the code contract.
* @return The bytecode at this address.
*/
function getCodeContractBytecode(address _codeContractAddress) public view returns (bytes memory codeContractBytecode) {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

make sure we verify the code contract bytecode even if it doesn't exist

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added another function getOvmContractBytecode(...) which will flag invalid state access

@@ -582,8 +582,6 @@ contract ExecutionManager {
restoreContractContext(oldMsgSender, oldActiveContract);
return false;
}
// Associate the code contract with our ovm contract
stateManager.associateCodeContract(_newOvmContractAddress, codeContractAddress);
bytes memory codeContractBytecode = stateManager.getCodeContractBytecode(codeContractAddress);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note that we need to have code hash(and probably size) authenticated in the SM, so we should be pulling this directly.

Comment on lines 16 to 18
// First, call stateManager.initNewTransactionExecution()
// (probably do the same with the ExecutionManager)
// Then actually call `executeTransaction(tx)` with the tx in question!
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there any reason not to combine both of these? Where executeTransaction would just do the init logic.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah because the init logic would not be strictly necessary inside of the L2Geth

}
}

function ensureVerifiedContract(address _ovmContractAddress) private {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

FWIW there is some nuance here where e.g. ovmEXTCODEHASH would not require the bytecode itself be verified to be a valid state access. In fact if we ship that opcode, it's probably necessary to limit fraud proof size, or a contract doing a bunch of these could be problematic.

* @param _codeContractAddress The address of the code contract.
* @return The bytecode at this address.
*/
function getCodeContractBytecode(address _codeContractAddress) public view returns (bytes memory codeContractBytecode) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

left a comment on this above, but definitely seems like if we are smart about this, we can do everything needed passing around hashes and not the full bytecode.

* @return The hash of the bytecode at this address.
*/
function getCodeContractHash(address _codeContractAddress) public view returns (bytes32 _codeContractHash) {
// TODO: Look up cached hash values eventually to avoid having to load all of this bytecode
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yep, this should be authenticated against the state anyway. And ofc. also note the EXTCODEHASH opcode can be used.

* @param _ovmContractInitcode The bytecode of the contract to be deployed
* @return the codeContractAddress.
*/
function deployContract(
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This will be changed what with moving safety check into EM, etc. so not reviewing for now

@karlfloersch karlfloersch changed the title [WIP] Add partial state manager Add initial fraud proof system Jun 22, 2020
@karlfloersch karlfloersch changed the title Add initial fraud proof system Add initial StateTransitioner & FraudProver Jun 22, 2020
@karlfloersch karlfloersch removed the wip label Jun 22, 2020
Copy link
Collaborator

@ben-chain ben-chain left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice, looking siiiiick! Left another round of comments.

Comment on lines +103 to +105
function setStateManager(address _stateManagerAddress) external {
stateManager = FullStateManager(_stateManagerAddress);
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this function meant to be atomically called before executeTransaction? If so, might be able to move that logic there in a future PR. If not atomic, do we need to authenticate that it's coming from the fraud prover?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah i totally agree we might as well put it into executeTransaction(..) itself

@@ -104,7 +104,7 @@ contract FullStateManager is StateManager {
* @param _ovmContractAddress The address of the OVM contract we'd like to associate with some code.
* @param _codeContractAddress The address of the code contract that's been deployed.
*/
function associateCodeContract(address _ovmContractAddress, address _codeContractAddress) external {
function associateCodeContract(address _ovmContractAddress, address _codeContractAddress) public {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this need to be authenticated? Would expect only the Fraud Verifier to be able to populate these associations.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, whoops, I see that this isn't the PSM. Will just resurface the nit/bikeshed that TestStateManager and TestExecutionManager could be better names for these non-fraud-proof contracts.

Comment on lines +21 to +26
function verifyFraud(uint _transitionIndex) public returns(bool) {
// TODO:
// Simply verify that the state transitioner has completed, and that the state root
// at _preStateTransitionIndex+1 is not equal to the state root which was committed for that index.
return true;
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note that in the current contracts I believe that the FraudVerifier is meant to call out to the state commitment chain to delete if there is fraud. It's a small change, but should update either this TODO or have one for the commitment chain.

* Pre-Execution *
****************/

function insertVerifiedStorage(address _ovmContractAddress, bytes32 _slot, bytes32 _value) external onlyStateTransitioner {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We could potentially add a require here that the _ovmContrractAddress has been verified. I assume this would already be enforced by the state transitioner, but could be a good extra sanity check.

ovmContractStorage[_ovmContractAddress][_slot] = _value;
}

function insertVerifiedContract(address _ovmContractAddress, address _codeContractAddress, uint _nonce) external onlyStateTransitioner {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I may have mentioned this already, but it would be nice to be able to insert the code hash and size without submitting the code itself. This would allow us to place a higher bound on the number of ovmEXTCODESIZE and ovmEXTCODEHASH. Relatively minor edge case, though; I don't think they get used very much.

* Transaction Execution *
************************/
function applyTransaction() public returns(bool) {
// TODO:
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fill or delete :)

************************/
function applyTransaction() public returns(bool) {
// TODO:
stateManager.initNewTransactionExecution();
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this confirms for me that we can wrap this call into executeTransaction. LMK if you think makes sense and we can write up a ticket for it.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah we can deff add this to executeTransaction (of course gas cost stuff needs to be ensured to be deterministic but that should be fine)

import {PartialStateManager} from "../PartialStateManager.sol";

/**
* @title StubExecutionManager
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: FWIW we have a pretty frequent convention of Mock* in the rest of our codebase. Would recommend we change this and the stub safety checker to follow, but up to you.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah agreed!

// Just call the state manager to store values a couple times
stateManager.setStorage(0x1111111111111111111111111111111111111111, 0x1111111111111111111111111111111111111111111111111111111111111111, 0x1111111111111111111111111111111111111111111111111111111111111111);
stateManager.setStorage(0x2222222222222222222222222222222222222222, 0x2222222222222222222222222222222222222222222222222222222222222222, 0x2222222222222222222222222222222222222222222222222222222222222222);
// TODO: Make this a bit more comprehensive. Could even make it configurable?
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I can def see a world in which the callBytes is an array of raw calldata which the EM sends off unquestioningly to the SM. Would probably make unit tests very clean

pragma solidity ^0.5.0;

/**
* @title StubSafetyChecker
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same Mock nit

@karlfloersch karlfloersch force-pushed the YAS-200/FraudVerifier/AddPartialStateManager branch from 3122c49 to 73fae93 Compare June 29, 2020 15:40
- Remove extra TODO comment
- Remvoe unneeded functions from the PartialStateManager
Copy link
Collaborator

@ben-chain ben-chain left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Approving--there are minor fixes left, but we can push those off in the interest of avoiding big merge conflicts.

@karlfloersch karlfloersch merged commit 88f93e2 into ethereum-optimism:master Jul 1, 2020
snario pushed a commit that referenced this pull request Apr 14, 2021
* Separates storage from SCC and CTC (#151)

* First pass version

* More minor tweaks for tests to pass

* Add authentication

* Minor config updates

* Fix lint error

* Fix naming changes per review

* Enable Deployer Whitelist (#119)

* first pass, test runner updated

* add ability to only validate flag, test passes

* all tests passing

* clean up console.logs

* enforce gas refund preservation

* more cleanup/import removal

* whitelisted -> allowed

* first pass, test runner updated

* add ability to only validate flag, test passes

* all tests passing

* clean up console.logs

* enforce gas refund preservation

* more cleanup/import removal

* whitelisted -> allowed

* remove whitespace

* Restrict StateTransitionerFactory (#140)

* added msg sender check

* add create test

* cleanup

* add param

* add addressmanager.address param

* CTC Chain Monotonicity Fixes (#93)

* [wip] Fix block time logic

* some sad path and happy tests passing

* more progress

* first pass sad cases tested

* cleanup, adding empty tests

* more reversion tests

* rename shouldstartat}

* add final couple tests

* enable more tests

* cleanup

* remove .only

* textual cleanup

* make queue length public

* improve structure, comments

* update deploy config

* address nits

Co-authored-by: Karl Floersch <karl@karlfloersch.com>

* fix declarations, lint (#152)

* Adds river's new Merkle tree implementation, with some cleanup (#148)

* Reverts an accidental breaking merge

* Added new merkle tree impl

* add comments

* Final cleanups and merge

Co-authored-by: Ben Jones <ben@pseudonym.party>

* Fix run gas Lower Bound (#94)

* added the check

* add test

* lower OVM TX size for Kovan

* re-remove gas check

* update gas vals slightly

* lint

* lint

* Merge master into freeze integration branch  (#153)

* update solidity version to ^0.7.0 (#122)

* update solc version to ^0.7.0

* interfaces back to solidity >0.6.0 <0.8.0

* update solc to 0.7.6

* back to 0.7.4

* upgrade to 0.7.6, fix EXTCODESIZE check

* versions >0.5.0 <0.8.0 for xdomain msgers

* ctc: disable appendQueueBatch (#150)

* ctc: disable appendSequencerBatch

* typo: fix

* re-enable verifyQueueTransaction test:

* add explicit test for verifying queue elements against either append

Co-authored-by: Ben Jones <ben@pseudonym.party>

* fix up test

* remove .only

Co-authored-by: Alina <alina@optimism.io>
Co-authored-by: Mark Tyneway <mark.tyneway@gmail.com>

* add check, simple test, update deploy (#154)

* go back to first name (#155)

* lint

* fix js number error

* add error logging to help debug deploy

* [code freeze] Fix deploy script (#156)

* fix deploy script

* add block time config

* ensure value is integer

* lint

* remove console logs from deploy

* Moves gas check to applyTransaction (#161)

* move to OVM_ST, pass test

* remove old test because functionality moved

* linting

* remove leaf hasing

* use safe EXEMRG wrapper (#162)

* use safeREQUIRE

* add owner getter

* relayer: add to config (#160)

* relayer: add to config

* lint: fix

* Fix minor error in test config

Co-authored-by: Kelvin Fichter <kelvinfichter@gmail.com>
Co-authored-by: ben-chain <ben@pseudonym.party>
Co-authored-by: Alina <alina@optimism.io>
Co-authored-by: Mark Tyneway <mark.tyneway@gmail.com>
Co-authored-by: Kevin Ho <kevinjho1996@gmail.com>
ClaytonNorthey92 added a commit to hemilabs/optimism that referenced this pull request Jun 27, 2024
b5b564702 popm/wasm: add wasm-opt target to optimise wasm binary (ethereum-optimism#146)
27a5081e3 tbc: allow seeds to be overwritten (ethereum-optimism#158)
18afbc403 Fix missing panic (ethereum-optimism#156)
05cee0afb tbc: remove height as the terminal condition for indexers (ethereum-optimism#152)
4402060d6 Use hemilabs/websocket fork of nhooyr.io/websocket (ethereum-optimism#153)
3df5001c4 Add initial CODEOWNERS file (ethereum-optimism#149)
a4685a57f popm/wasm: improve and tidy up Go code (ethereum-optimism#144)
41a0009c1 Add forking detection to TBC (ethereum-optimism#101)
bbeed8bac ignore ulimits in tbc when on localnet (ethereum-optimism#142)
4e1914cc6 Stopgap to re-fetch blocks with no children (ethereum-optimism#131)
12eefff06 e2e: fix issues detected by staticcheck (ethereum-optimism#134)
80153372f Add more documentation for TBC and related RPC protocol (ethereum-optimism#86)
723b63704 bfg: fix issues reported by staticcheck (ethereum-optimism#132)
509fb1be6 electrumx: fix unhandled error in NewJSONRPCRequest (ethereum-optimism#133)
b19af1e1f hemictl: use sort.Strings(...) instead of sort.Sort(sort.StringSlice(...)) (S1032) (ethereum-optimism#123)
cf7c570f9 popmd: remove unused 'handle' func and return err in connectBFG (ethereum-optimism#124)
fa2a4c4de ci: fix bug that makes version type always 'unstable' (ethereum-optimism#125)
ddc39655a ci: use org DOCKERHUB_TOKEN secret (ethereum-optimism#128)
6457d16f5 bfgd: drop btc_blocks_can refresh triggers for l2_keystones/pop_basis (ethereum-optimism#120)
2b3c096bd popm: simplify receivedKeystones variable in tests (ethereum-optimism#116)
6140bbf24 tbc: move RPC tests to a separate test file (ethereum-optimism#114)
c76571ff0 Add configuration option for static fees to web PoP miner (ethereum-optimism#119)
233817e65 popm: use simple conversion instead of unnecessary fmt.Sprintf (S1025) (ethereum-optimism#115)
2879f5fa7 e2e: improve name for variable with type `time.Duration` (ST1011) (ethereum-optimism#117)
4f31965e6 database,e2e: remove use of deprecated io/ioutil (SA1019) (ethereum-optimism#118)
e9e090696 tbc: do not recreate outpoint for ScriptHashByOutpoint. (ethereum-optimism#109)
52eefb136 ignore l2 keystones notifications in tests (ethereum-optimism#112)
eb607994c Sync Docker image environment variables with daemon configs (ethereum-optimism#111)
57281bc5d added a way to monitor and sanity-test localnet (ethereum-optimism#106)
ea1a1c94c bfgd: fix loops unconditionally exited after one interation (SA4004) (ethereum-optimism#108)
29f116fb4 Add pprof http server to daemons (ethereum-optimism#105)
18a315d7e Added README for generating forks in BTC regtest for TBC fork resolution testing (ethereum-optimism#100)
55b8f52cb more robust nextPort (ethereum-optimism#103)
48f8b293f tbcapi: use reverse byte order for hashes in serialised, tidy up (ethereum-optimism#104)
b7e9f5ecb restart initialblocks on-failure (ethereum-optimism#102)
f9d52d423 Update required Go version to v1.22.2 (ethereum-optimism#96)
f6808aa5b Fix op-proposer op-node dependency condition (fixes ethereum-optimism#98) (ethereum-optimism#99)
a882529e8 Kill all pending block downloads if a peer fails (ethereum-optimism#95)
eb66345e1 e2e: tidy up docker-compose file (ethereum-optimism#81)
34766f725 Track pending blocks with ttl package (ethereum-optimism#90)
6ed3eb88b Added configurable fee-per-vB to PoP Miner (ethereum-optimism#91)
509e31fbc Replace os.Kill with syscall.SIGTERM in signal.Notify calls (ethereum-optimism#87)

git-subtree-dir: heminetwork
git-subtree-split: b5b564702e8d3bedcdf0e0a52c22e383d7fd4dbe
bap2pecs pushed a commit to babylonlabs-io/optimism that referenced this pull request Jul 31, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants