-
Notifications
You must be signed in to change notification settings - Fork 492
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
Live tracing experimental MVP support for arbitrum nitro #2934
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -7,6 +7,7 @@ import ( | |
"encoding/binary" | ||
"errors" | ||
"fmt" | ||
"github.com/ethereum/go-ethereum/core/tracing" | ||
"math" | ||
"math/big" | ||
|
||
|
@@ -147,6 +148,7 @@ func ProduceBlock( | |
chainConfig *params.ChainConfig, | ||
isMsgForPrefetch bool, | ||
runMode core.MessageRunMode, | ||
blockChain *core.BlockChain, | ||
) (*types.Block, types.Receipts, error) { | ||
txes, err := ParseL2Transactions(message, chainConfig.ChainID) | ||
if err != nil { | ||
|
@@ -156,7 +158,17 @@ func ProduceBlock( | |
|
||
hooks := NoopSequencingHooks() | ||
return ProduceBlockAdvanced( | ||
message.Header, txes, delayedMessagesRead, lastBlockHeader, statedb, chainContext, chainConfig, hooks, isMsgForPrefetch, runMode, | ||
message.Header, | ||
txes, | ||
delayedMessagesRead, | ||
lastBlockHeader, | ||
statedb, | ||
chainContext, | ||
chainConfig, | ||
hooks, | ||
isMsgForPrefetch, | ||
runMode, | ||
blockChain, | ||
) | ||
} | ||
|
||
|
@@ -172,7 +184,21 @@ func ProduceBlockAdvanced( | |
sequencingHooks *SequencingHooks, | ||
isMsgForPrefetch bool, | ||
runMode core.MessageRunMode, | ||
) (*types.Block, types.Receipts, error) { | ||
blockChain *core.BlockChain, | ||
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. seems better to get a VMConfig than a BlockChain. |
||
) (outBlock *types.Block, outReceipt types.Receipts, outError error) { | ||
// IMPORTANT: | ||
// func to get the VMConfig from the blockChain, or a default one if it's not available | ||
// this is a way how we propagate Tenderly tracer to the VMConfig instead of vm.Config{} | ||
getVMConfig := func() vm.Config { | ||
if blockChain != nil && blockChain.GetVMConfig() != nil { | ||
return *blockChain.GetVMConfig() | ||
} | ||
return vm.Config{} | ||
} | ||
|
||
defer func() { | ||
getVMConfig().Tracer.OnBlockEnd(outError) | ||
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. This hook was missing a call, so I've added it manually here |
||
}() | ||
|
||
arbState, err := arbosState.OpenSystemArbosState(statedb, nil, true) | ||
if err != nil { | ||
|
@@ -192,6 +218,16 @@ func ProduceBlockAdvanced( | |
} | ||
|
||
header := createNewHeader(lastBlockHeader, l1Info, arbState, chainConfig) | ||
|
||
getVMConfig().Tracer.OnBlockStart( | ||
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. This hook was missing a call, so I've added it manually here |
||
tracing.BlockEvent{ | ||
Block: types.NewBlock(header, &types.Body{Transactions: nil}, nil, trie.NewStackTrie(nil)), | ||
TD: nil, | ||
Finalized: nil, | ||
Safe: nil, | ||
}, | ||
) | ||
|
||
signer := types.MakeSigner(chainConfig, header.Number, header.Time) | ||
// Note: blockGasLeft will diverge from the actual gas left during execution in the event of invalid txs, | ||
// but it's only used as block-local representation limiting the amount of work done in a block. | ||
|
@@ -312,6 +348,9 @@ func ProduceBlockAdvanced( | |
statedb.SetTxContext(tx.Hash(), len(receipts)) // the number of successful state transitions | ||
|
||
gasPool := gethGas | ||
|
||
statedb.SetLogger(getVMConfig().Tracer) | ||
|
||
receipt, result, err := core.ApplyTransactionWithResultFilter( | ||
chainConfig, | ||
chainContext, | ||
|
@@ -321,7 +360,7 @@ func ProduceBlockAdvanced( | |
header, | ||
tx, | ||
&header.GasUsed, | ||
vm.Config{}, | ||
getVMConfig(), | ||
runMode, | ||
func(result *core.ExecutionResult) error { | ||
return hooks.PostTxFilter(header, statedb, arbState, tx, sender, dataGas, result) | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,8 +1,10 @@ | ||
package gethexec | ||
|
||
import ( | ||
"encoding/json" | ||
"errors" | ||
"fmt" | ||
"github.com/ethereum/go-ethereum/eth/tracers/live" | ||
"math/big" | ||
"time" | ||
|
||
|
@@ -202,13 +204,25 @@ func WriteOrTestChainConfig(chainDb ethdb.Database, config *params.ChainConfig) | |
return nil | ||
} | ||
|
||
func GetBlockChain(chainDb ethdb.Database, cacheConfig *core.CacheConfig, chainConfig *params.ChainConfig, txLookupLimit uint64) (*core.BlockChain, error) { | ||
func GetBlockChain( | ||
chainDb ethdb.Database, | ||
cacheConfig *core.CacheConfig, | ||
chainConfig *params.ChainConfig, | ||
txLookupLimit uint64, | ||
tracingConfig json.RawMessage, | ||
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. I think you should not need to chainge blockchain at all. However, if you do - seems better to get here *tracing.Hooks that a json.RawMessage. |
||
) (*core.BlockChain, error) { | ||
engine := arbos.Engine{ | ||
IsSequencer: true, | ||
} | ||
|
||
tenderlySimpleTracerHooks, err := live.NewTenderlySimpleTracerHooks(tracingConfig) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
vmConfig := vm.Config{ | ||
EnablePreimageRecording: false, | ||
Tracer: tenderlySimpleTracerHooks, | ||
} | ||
|
||
return core.NewBlockChain(chainDb, cacheConfig, chainConfig, nil, nil, engine, vmConfig, shouldPreserveFalse, &txLookupLimit) | ||
|
@@ -220,7 +234,7 @@ func WriteOrTestBlockChain(chainDb ethdb.Database, cacheConfig *core.CacheConfig | |
// When using path scheme, and the stored state trie is not empty, | ||
// WriteOrTestGenBlock is not able to recover EmptyRootHash state trie node. | ||
// In that case Nitro doesn't test genblock, but just returns the BlockChain. | ||
return GetBlockChain(chainDb, cacheConfig, chainConfig, txLookupLimit) | ||
return GetBlockChain(chainDb, cacheConfig, chainConfig, txLookupLimit, nil) | ||
} | ||
|
||
err := WriteOrTestGenblock(chainDb, cacheConfig, initData, chainConfig, initMessage, accountsPerSync) | ||
|
@@ -231,7 +245,7 @@ func WriteOrTestBlockChain(chainDb ethdb.Database, cacheConfig *core.CacheConfig | |
if err != nil { | ||
return nil, err | ||
} | ||
return GetBlockChain(chainDb, cacheConfig, chainConfig, txLookupLimit) | ||
return GetBlockChain(chainDb, cacheConfig, chainConfig, txLookupLimit, nil) | ||
} | ||
|
||
// Don't preserve reorg'd out blocks | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -525,6 +525,7 @@ func (s *ExecutionEngine) sequenceTransactionsWithBlockMutex(header *arbostypes. | |
hooks, | ||
false, | ||
core.MessageCommitMode, | ||
nil, | ||
) | ||
if err != nil { | ||
return nil, err | ||
|
@@ -696,6 +697,7 @@ func (s *ExecutionEngine) createBlockFromNextMessage(msg *arbostypes.MessageWith | |
s.bc.Config(), | ||
isMsgForPrefetch, | ||
runMode, | ||
s.bc, | ||
) | ||
|
||
return block, statedb, receipts, err | ||
|
@@ -873,14 +875,18 @@ func (s *ExecutionEngine) digestMessageWithBlockMutex(num arbutil.MessageIndex, | |
} | ||
|
||
startTime := time.Now() | ||
if s.prefetchBlock && msgForPrefetch != nil { | ||
go func() { | ||
_, _, _, err := s.createBlockFromNextMessage(msgForPrefetch, true) | ||
if err != nil { | ||
return | ||
} | ||
}() | ||
} | ||
|
||
// TODO: IMPORTANT !!! | ||
// This will cause a tracer to be called multiple times for the same block concurrently | ||
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. This is probably not the only thing that'll cause tracer to be called multiple times. I didn't view geth side yet, but I think a better solution will be to:
|
||
// Removed for now, but this should be properly addressed | ||
//if s.prefetchBlock && msgForPrefetch != nil { | ||
// go func() { | ||
// _, _, _, err := s.createBlockFromNextMessage(msgForPrefetch, true) | ||
// if err != nil { | ||
// return | ||
// } | ||
// }() | ||
//} | ||
|
||
block, statedb, receipts, err := s.createBlockFromNextMessage(msg, false) | ||
if err != nil { | ||
|
+46 −0 | eth/tracers/live/tenderly_simple_hooks.go | |
+137 −0 | eth/tracers/live/tenderly_simple_tracer.go |
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.
remove this change.
You should have a separate PR to our go-ethereum fork, point to it from your comment ("this pulls in + link"), and add a commit which sets go-ethereum to the specific commit of your geth-change.
We have merge checks that will not allow nitro commit to be merged before the geth PR is also merged.