From 52f22af3ae07235145b611851019c77cd0c8c7f2 Mon Sep 17 00:00:00 2001 From: HAOYUatHZ <37070449+HAOYUatHZ@users.noreply.github.com> Date: Tue, 7 Jun 2022 13:52:14 +0800 Subject: [PATCH] Refactor l2witness/opt-storage-proof (#112) * rename GetStateData to GetLiveStateObject * revert EvmTxTraces type * rename GetLiveStateObject to GetLiveStateAccount * fix typo * some renamings * format codes * fix typo * fix typos * format codes some reverts some renamings some renamings format codes * update comments update comments * update comments update comments update comments * update comments update comments update comments * rename * rename * update * update comments --- .gitattributes | 2 +- core/blockchain.go | 18 +++++------ core/state/statedb.go | 2 +- core/types/l2trace.go | 42 +++++++++++--------------- core/vm/interface.go | 2 +- core/vm/logger.go | 48 +++++++++++++++--------------- core/vm/logger_trace.go | 66 ++++++++++++++++++++--------------------- miner/worker.go | 56 +++++++++++++++++----------------- 8 files changed, 114 insertions(+), 122 deletions(-) diff --git a/.gitattributes b/.gitattributes index f3ce1b091a65..c90b62c99e1c 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1,4 +1,4 @@ # Auto detect text files and perform LF normalization * text=auto *.sol linguist-language=Solidity -*.go text eol=lf \ No newline at end of file +*.go text eol=lf diff --git a/core/blockchain.go b/core/blockchain.go index 14671c7b7f8a..39d5fcc8018e 100644 --- a/core/blockchain.go +++ b/core/blockchain.go @@ -1193,17 +1193,17 @@ func (bc *BlockChain) writeKnownBlock(block *types.Block) error { } // WriteBlockWithState writes the block and all associated state to the database. -func (bc *BlockChain) WriteBlockWithState(block *types.Block, receipts []*types.Receipt, logs []*types.Log, evmTraces *types.EvmTxTraces, state *state.StateDB, emitHeadEvent bool) (status WriteStatus, err error) { +func (bc *BlockChain) WriteBlockWithState(block *types.Block, receipts []*types.Receipt, logs []*types.Log, evmTraces []*types.ExecutionResult, storageTrace *types.StorageTrace, state *state.StateDB, emitHeadEvent bool) (status WriteStatus, err error) { if !bc.chainmu.TryLock() { return NonStatTy, errInsertionInterrupted } defer bc.chainmu.Unlock() - return bc.writeBlockWithState(block, receipts, logs, evmTraces, state, emitHeadEvent) + return bc.writeBlockWithState(block, receipts, logs, evmTraces, storageTrace, state, emitHeadEvent) } // writeBlockWithState writes the block and all associated state to the database, // but is expects the chain mutex to be held. -func (bc *BlockChain) writeBlockWithState(block *types.Block, receipts []*types.Receipt, logs []*types.Log, evmTraces *types.EvmTxTraces, state *state.StateDB, emitHeadEvent bool) (status WriteStatus, err error) { +func (bc *BlockChain) writeBlockWithState(block *types.Block, receipts []*types.Receipt, logs []*types.Log, evmTraces []*types.ExecutionResult, storageTrace *types.StorageTrace, state *state.StateDB, emitHeadEvent bool) (status WriteStatus, err error) { if bc.insertStopped() { return NonStatTy, errInsertionInterrupted } @@ -1327,7 +1327,7 @@ func (bc *BlockChain) writeBlockWithState(block *types.Block, receipts []*types. // Fill blockResult content var blockResult *types.BlockResult if evmTraces != nil { - blockResult = bc.writeBlockResult(state, block, evmTraces) + blockResult = bc.writeBlockResult(state, block, evmTraces, storageTrace) bc.blockResultCache.Add(block.Hash(), blockResult) } @@ -1351,10 +1351,10 @@ func (bc *BlockChain) writeBlockWithState(block *types.Block, receipts []*types. } // Fill blockResult content -func (bc *BlockChain) writeBlockResult(state *state.StateDB, block *types.Block, evmTraces *types.EvmTxTraces) *types.BlockResult { +func (bc *BlockChain) writeBlockResult(state *state.StateDB, block *types.Block, evmTraces []*types.ExecutionResult, storageTrace *types.StorageTrace) *types.BlockResult { blockResult := &types.BlockResult{ - ExecutionResults: evmTraces.TxResults, - StorageTrace: evmTraces.Storage, + ExecutionResults: evmTraces, + StorageTrace: storageTrace, } coinbase := types.AccountWrapper{ Address: block.Coinbase(), @@ -1692,8 +1692,8 @@ func (bc *BlockChain) insertChain(chain types.Blocks, verifySeals bool) (int, er // Write the block to the chain and get the status. substart = time.Now() - // EvmTraces is nil is safe because l2geth's p2p server is stoped and the code will not execute there. - status, err := bc.writeBlockWithState(block, receipts, logs, nil, statedb, false) + // EvmTraces & StorageTrace being nil is safe because l2geth's p2p server is stoped and the code will not execute there. + status, err := bc.writeBlockWithState(block, receipts, logs, nil, nil, statedb, false) atomic.StoreUint32(&followupInterrupt, 1) if err != nil { return it.index, err diff --git a/core/state/statedb.go b/core/state/statedb.go index b655ed642476..e0d06c3cc560 100644 --- a/core/state/statedb.go +++ b/core/state/statedb.go @@ -325,7 +325,7 @@ func (s *StateDB) GetProofByHash(addrHash common.Hash) ([][]byte, error) { return proof, err } -func (s *StateDB) GetStateData(addr common.Address) *types.StateAccount { +func (s *StateDB) GetLiveStateAccount(addr common.Address) *types.StateAccount { obj, ok := s.stateObjects[addr] if !ok { return nil diff --git a/core/types/l2trace.go b/core/types/l2trace.go index 56940b3c087a..f883238b2e7a 100644 --- a/core/types/l2trace.go +++ b/core/types/l2trace.go @@ -41,13 +41,6 @@ type StorageTrace struct { StorageProofs map[string]map[string][]hexutil.Bytes `json:"storageProofs,omitempty"` } -// EvmTxTraces groups trace data from each executation of tx and left -// some field to be finished from blockResult -type EvmTxTraces struct { - TxResults []*ExecutionResult - Storage *StorageTrace -} - // ExecutionResult groups all structured logs emitted by the EVM // while replaying a transaction in debug mode as well as transaction // execution status, the amount of gas used and the return value @@ -55,19 +48,19 @@ type ExecutionResult struct { Gas uint64 `json:"gas"` Failed bool `json:"failed"` ReturnValue string `json:"returnValue,omitempty"` - // Sender's account proof (before Tx).. + // Sender's account state (before Tx) From *AccountWrapper `json:"from,omitempty"` - // Receiver's account proof. + // Receiver's account state (before Tx) To *AccountWrapper `json:"to,omitempty"` - // AccountCreated record the account in case tx is create - // (for creating inside contracts we handle CREATE op) + // AccountCreated record the account if the tx is "create" + // (for creating inside a contract, we just handle CREATE op) AccountCreated *AccountWrapper `json:"accountCreated,omitempty"` // Record all accounts' state which would be affected AFTER tx executed - // currently they are just sender and to account + // currently they are just `from` and `to` account AccountsAfter []*AccountWrapper `json:"accountAfter"` - // It's exist only when tx is a contract call. + // `CodeHash` only exists when tx is a contract call. CodeHash *common.Hash `json:"codeHash,omitempty"` // If it is a contract call, the contract code is returned. ByteCode string `json:"byteCode,omitempty"` @@ -107,21 +100,22 @@ func NewStructLogResBasic(pc uint64, op string, gas, gasCost uint64, depth int, } type ExtraData struct { - // Indicate the call success or not for CALL/CREATE op + // Indicate the call succeeds or not for CALL/CREATE op CallFailed bool `json:"callFailed,omitempty"` // CALL | CALLCODE | DELEGATECALL | STATICCALL: [tx.to address’s code, stack.nth_last(1) address’s code] CodeList [][]byte `json:"codeList,omitempty"` // SSTORE | SLOAD: [storageProof] - // SELFDESTRUCT: [contract address’s accountProof, stack.nth_last(0) address’s accountProof] - // SELFBALANCE: [contract address’s accountProof] - // BALANCE | EXTCODEHASH: [stack.nth_last(0) address’s accountProof] - // CREATE | CREATE2: [created contract address’s accountProof (before constructed), - // created contract address's data (after constructed)] - // CALL | CALLCODE: [caller contract address’s accountProof, stack.nth_last(1) (i.e. called) address’s accountProof - // called contract address's data (value updated, before called)] - // STATICCALL: [stack.nth_last(1) (i.e. called) address’s accountProof - // called contract address's data (before called)] - ProofList []*AccountWrapper `json:"proofList,omitempty"` + // SELFDESTRUCT: [contract address’s account, stack.nth_last(0) address’s account] + // SELFBALANCE: [contract address’s account] + // BALANCE | EXTCODEHASH: [stack.nth_last(0) address’s account] + // CREATE | CREATE2: [created contract address’s account (before constructed), + // created contract address's account (after constructed)] + // CALL | CALLCODE: [caller contract address’s account, + // stack.nth_last(1) (i.e. callee) address’s account, + // callee contract address's account (value updated, before called)] + // STATICCALL: [stack.nth_last(1) (i.e. callee) address’s account, + // callee contract address's account (before called)] + StateList []*AccountWrapper `json:"proofList,omitempty"` } type AccountWrapper struct { diff --git a/core/vm/interface.go b/core/vm/interface.go index f554ebcfb267..bd594b9c8265 100644 --- a/core/vm/interface.go +++ b/core/vm/interface.go @@ -48,7 +48,7 @@ type StateDB interface { SetState(common.Address, common.Hash, common.Hash) GetRootHash() common.Hash - GetStateData(addr common.Address) *types.StateAccount + GetLiveStateAccount(addr common.Address) *types.StateAccount GetProof(addr common.Address) ([][]byte, error) GetProofByHash(addrHash common.Hash) ([][]byte, error) GetStorageProof(a common.Address, key common.Hash) ([][]byte, error) diff --git a/core/vm/logger.go b/core/vm/logger.go index 7db514ee0aa4..9dd17f046bd7 100644 --- a/core/vm/logger.go +++ b/core/vm/logger.go @@ -165,7 +165,7 @@ type StructLogger struct { cfg LogConfig env *EVM - states map[common.Address]struct{} + statesAffected map[common.Address]struct{} storage map[common.Address]Storage createdAccount *types.AccountWrapper @@ -178,8 +178,8 @@ type StructLogger struct { // NewStructLogger returns a new logger func NewStructLogger(cfg *LogConfig) *StructLogger { logger := &StructLogger{ - storage: make(map[common.Address]Storage), - states: make(map[common.Address]struct{}), + storage: make(map[common.Address]Storage), + statesAffected: make(map[common.Address]struct{}), } if cfg != nil { logger.cfg = *cfg @@ -190,7 +190,7 @@ func NewStructLogger(cfg *LogConfig) *StructLogger { // Reset clears the data held by the logger. func (l *StructLogger) Reset() { l.storage = make(map[common.Address]Storage) - l.states = make(map[common.Address]struct{}) + l.statesAffected = make(map[common.Address]struct{}) l.output = make([]byte, 0) l.logs = l.logs[:0] l.callStackLogInd = nil @@ -199,21 +199,21 @@ func (l *StructLogger) Reset() { } // CaptureStart implements the EVMLogger interface to initialize the tracing operation. -func (l *StructLogger) CaptureStart(env *EVM, from common.Address, to common.Address, create bool, input []byte, gas uint64, value *big.Int) { +func (l *StructLogger) CaptureStart(env *EVM, from common.Address, to common.Address, isCreate bool, input []byte, gas uint64, value *big.Int) { l.env = env - if create { - //Notice codeHash is set AFTER CreateTx has exited, so heree codeHash is still empty + if isCreate { + // notice codeHash is set AFTER CreateTx has exited, so here codeHash is still empty l.createdAccount = &types.AccountWrapper{ - //Nonce is 1 after EIP158, so we query it from stateDb + Address: to, + // nonce is 1 after EIP158, so we query it from stateDb Nonce: env.StateDB.GetNonce(to), Balance: (*hexutil.Big)(value), - Address: to, } } - l.states[from] = struct{}{} - l.states[to] = struct{}{} + l.statesAffected[from] = struct{}{} + l.statesAffected[to] = struct{}{} } // CaptureState logs a new structured log message and pushes it out to the environment @@ -263,7 +263,7 @@ func (l *StructLogger) CaptureState(pc uint64, op OpCode, gas, cost uint64, scop l.storage[contractAddress][storageKey] = storageValue structlog.Storage = l.storage[contractAddress].Copy() - if err := traceStorageProof(l, scope, structlog.getOrInitExtraData()); err != nil { + if err := traceStorage(l, scope, structlog.getOrInitExtraData()); err != nil { log.Error("Failed to trace data", "opcode", op.String(), "err", err) } } @@ -305,20 +305,20 @@ func (l *StructLogger) CaptureEnd(output []byte, gasUsed uint64, t time.Duration } func (l *StructLogger) CaptureEnter(typ OpCode, from common.Address, to common.Address, input []byte, gas uint64, value *big.Int) { - //the last logged op should be CALL/CREATE + // the last logged op should be CALL/STATICCALL/CALLCODE/CREATE/CREATE2 lastLogPos := len(l.logs) - 1 log.Debug("mark call stack", "pos", lastLogPos, "op", l.logs[lastLogPos].Op) l.callStackLogInd = append(l.callStackLogInd, lastLogPos) - //sanity check + // sanity check if len(l.callStackLogInd) != l.env.depth { panic("unexpected evm depth in capture enter") } - l.states[to] = struct{}{} + l.statesAffected[to] = struct{}{} theLog := l.logs[lastLogPos] - // handling additional updating for CREATE only + // handling additional updating for CALL/STATICCALL/CALLCODE/CREATE/CREATE2 only // append extraData part for the log, capture the account status (the nonce / balance has been updated in capture enter) - wrappedStatus, _ := getWrappedForAddr(l, to) - theLog.ExtraData.ProofList = append(theLog.ExtraData.ProofList, wrappedStatus) + wrappedStatus, _ := getWrappedAccountForAddr(l, to) + theLog.ExtraData.StateList = append(theLog.ExtraData.StateList, wrappedStatus) } // in CaptureExit phase, a CREATE has its target address's code being set and queryable @@ -331,7 +331,7 @@ func (l *StructLogger) CaptureExit(output []byte, gasUsed uint64, err error) { theLogPos := l.callStackLogInd[stackH-1] l.callStackLogInd = l.callStackLogInd[:stackH-1] theLog := l.logs[theLogPos] - //update "forecast" data + // update "forecast" data if err != nil { theLog.ExtraData.CallFailed = true } @@ -340,14 +340,14 @@ func (l *StructLogger) CaptureExit(output []byte, gasUsed uint64, err error) { switch theLog.Op { case CREATE, CREATE2: // append extraData part for the log whose op is CREATE(2), capture the account status (the codehash would be updated in capture exit) - dataLen := len(theLog.ExtraData.ProofList) + dataLen := len(theLog.ExtraData.StateList) if dataLen == 0 { panic("unexpected data capture for target op") } - lastAccData := theLog.ExtraData.ProofList[dataLen-1] - wrappedStatus, _ := getWrappedForAddr(l, lastAccData.Address) - theLog.ExtraData.ProofList = append(theLog.ExtraData.ProofList, wrappedStatus) + lastAccData := theLog.ExtraData.StateList[dataLen-1] + wrappedStatus, _ := getWrappedAccountForAddr(l, lastAccData.Address) + theLog.ExtraData.StateList = append(theLog.ExtraData.StateList, wrappedStatus) default: //do nothing for other op code return @@ -357,7 +357,7 @@ func (l *StructLogger) CaptureExit(output []byte, gasUsed uint64, err error) { // UpdatedAccounts is used to collect all "touched" accounts func (l *StructLogger) UpdatedAccounts() map[common.Address]struct{} { - return l.states + return l.statesAffected } // UpdatedStorages is used to collect all "touched" storage slots diff --git a/core/vm/logger_trace.go b/core/vm/logger_trace.go index ad838910c4b0..0e2e1abe9e68 100644 --- a/core/vm/logger_trace.go +++ b/core/vm/logger_trace.go @@ -11,18 +11,18 @@ type traceFunc func(l *StructLogger, scope *ScopeContext, extraData *types.Extra var ( // OpcodeExecs the map to load opcodes' trace funcs. OpcodeExecs = map[OpCode][]traceFunc{ - CALL: {traceToAddressCode, traceLastNAddressCode(1), traceCallerProof, traceLastNAddressProof(1)}, - CALLCODE: {traceToAddressCode, traceLastNAddressCode(1), traceCallerProof, traceLastNAddressProof(1)}, + CALL: {traceToAddressCode, traceLastNAddressCode(1), traceCaller, traceLastNAddressAccount(1)}, + CALLCODE: {traceToAddressCode, traceLastNAddressCode(1), traceCaller, traceLastNAddressAccount(1)}, DELEGATECALL: {traceToAddressCode, traceLastNAddressCode(1)}, - STATICCALL: {traceToAddressCode, traceLastNAddressCode(1), traceLastNAddressProof(1)}, - CREATE: {}, // sender's wrapped_proof is already recorded in BlockChain.writeBlockResult - CREATE2: {}, // sender's wrapped_proof is already recorded in BlockChain.writeBlockResult - SLOAD: {}, // record storage_proof in `captureState` instead of here, to handle `l.cfg.DisableStorage` flag - SSTORE: {}, // record storage_proof in `captureState` instead of here, to handle `l.cfg.DisableStorage` flag - SELFDESTRUCT: {traceContractProof, traceLastNAddressProof(0)}, - SELFBALANCE: {traceContractProof}, - BALANCE: {traceLastNAddressProof(0)}, - EXTCODEHASH: {traceLastNAddressProof(0)}, + STATICCALL: {traceToAddressCode, traceLastNAddressCode(1), traceLastNAddressAccount(1)}, + CREATE: {}, // sender is already recorded in ExecutionResult, callee is recorded in CaptureEnter&CaptureExit + CREATE2: {}, // sender is already recorded in ExecutionResult, callee is recorded in CaptureEnter&CaptureExit + SLOAD: {}, // trace storage in `captureState` instead of here, to handle `l.cfg.DisableStorage` flag + SSTORE: {}, // trace storage in `captureState` instead of here, to handle `l.cfg.DisableStorage` flag + SELFDESTRUCT: {traceContractAccount, traceLastNAddressAccount(0)}, + SELFBALANCE: {traceContractAccount}, + BALANCE: {traceLastNAddressAccount(0)}, + EXTCODEHASH: {traceLastNAddressAccount(0)}, } ) @@ -50,32 +50,32 @@ func traceLastNAddressCode(n int) traceFunc { } } -// traceStorageProof get contract's storage proof at storage_address -func traceStorageProof(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { +// traceStorage get contract's storage at storage_address +func traceStorage(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { if scope.Stack.len() == 0 { return nil } key := common.Hash(scope.Stack.peek().Bytes32()) - proof, err := getWrappedForStorage(l, scope.Contract.Address(), key) + storage, err := getWrappedAccountForStorage(l, scope.Contract.Address(), key) if err == nil { - extraData.ProofList = append(extraData.ProofList, proof) + extraData.StateList = append(extraData.StateList, storage) } return err } -// traceContractProof gets the contract's account proof -func traceContractProof(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { - // Get account proof. - proof, err := getWrappedForAddr(l, scope.Contract.Address()) +// traceContractAccount gets the contract's account +func traceContractAccount(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { + // Get account state. + state, err := getWrappedAccountForAddr(l, scope.Contract.Address()) if err == nil { - extraData.ProofList = append(extraData.ProofList, proof) - l.states[scope.Contract.Address()] = struct{}{} + extraData.StateList = append(extraData.StateList, state) + l.statesAffected[scope.Contract.Address()] = struct{}{} } return err } -// traceLastNAddressProof returns func about the last N's address proof. -func traceLastNAddressProof(n int) traceFunc { +// traceLastNAddressAccount returns func about the last N's address account. +func traceLastNAddressAccount(n int) traceFunc { return func(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { stack := scope.Stack if stack.len() <= n { @@ -83,28 +83,28 @@ func traceLastNAddressProof(n int) traceFunc { } address := common.Address(stack.data[stack.len()-1-n].Bytes20()) - proof, err := getWrappedForAddr(l, address) + state, err := getWrappedAccountForAddr(l, address) if err == nil { - extraData.ProofList = append(extraData.ProofList, proof) - l.states[scope.Contract.Address()] = struct{}{} + extraData.StateList = append(extraData.StateList, state) + l.statesAffected[scope.Contract.Address()] = struct{}{} } return err } } -// traceCallerProof gets caller address's proof. -func traceCallerProof(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { +// traceCaller gets caller address's account. +func traceCaller(l *StructLogger, scope *ScopeContext, extraData *types.ExtraData) error { address := scope.Contract.CallerAddress - proof, err := getWrappedForAddr(l, address) + state, err := getWrappedAccountForAddr(l, address) if err == nil { - extraData.ProofList = append(extraData.ProofList, proof) - l.states[scope.Contract.Address()] = struct{}{} + extraData.StateList = append(extraData.StateList, state) + l.statesAffected[scope.Contract.Address()] = struct{}{} } return err } // StorageWrapper will be empty -func getWrappedForAddr(l *StructLogger, address common.Address) (*types.AccountWrapper, error) { +func getWrappedAccountForAddr(l *StructLogger, address common.Address) (*types.AccountWrapper, error) { return &types.AccountWrapper{ Address: address, Nonce: l.env.StateDB.GetNonce(address), @@ -113,7 +113,7 @@ func getWrappedForAddr(l *StructLogger, address common.Address) (*types.AccountW }, nil } -func getWrappedForStorage(l *StructLogger, address common.Address, key common.Hash) (*types.AccountWrapper, error) { +func getWrappedAccountForStorage(l *StructLogger, address common.Address, key common.Hash) (*types.AccountWrapper, error) { return &types.AccountWrapper{ Address: address, Nonce: l.env.StateDB.GetNonce(address), diff --git a/miner/worker.go b/miner/worker.go index 3f820c0c5a9f..cd92fed9b474 100644 --- a/miner/worker.go +++ b/miner/worker.go @@ -642,12 +642,10 @@ func (w *worker) resultLoop() { } // Different block could share same sealhash, deep copy here to prevent write-write conflict. var ( - receipts = make([]*types.Receipt, len(task.receipts)) - evmTraces = &types.EvmTxTraces{ - TxResults: make([]*types.ExecutionResult, len(task.executionResults)), - Storage: new(types.StorageTrace), - } - logs []*types.Log + receipts = make([]*types.Receipt, len(task.receipts)) + evmTraces = make([]*types.ExecutionResult, len(task.executionResults)) + logs []*types.Log + storageTrace = new(types.StorageTrace) ) for i, taskReceipt := range task.receipts { receipt := new(types.Receipt) @@ -655,9 +653,9 @@ func (w *worker) resultLoop() { *receipt = *taskReceipt evmTrace := new(types.ExecutionResult) - evmTraces.TxResults[i] = evmTrace + evmTraces[i] = evmTrace *evmTrace = *task.executionResults[i] - *evmTraces.Storage = *task.storageResults + *storageTrace = *task.storageResults // add block location fields receipt.BlockHash = hash @@ -676,7 +674,7 @@ func (w *worker) resultLoop() { logs = append(logs, receipt.Logs...) } // Commit block and state to database. - _, err := w.chain.WriteBlockWithState(block, receipts, logs, evmTraces, task.state, true) + _, err := w.chain.WriteBlockWithState(block, receipts, logs, evmTraces, storageTrace, task.state, true) if err != nil { log.Error("Failed writing block to chain", "err", err) continue @@ -832,7 +830,7 @@ func (w *worker) commitTransaction(tx *types.Transaction, coinbase common.Addres to = &createdAcc.Address } - //collect affected account after tx being applied + // collect affected account after tx being applied for _, acc := range []*common.Address{&from, to} { after = append(after, &types.AccountWrapper{ Address: *acc, @@ -842,46 +840,46 @@ func (w *worker) commitTransaction(tx *types.Transaction, coinbase common.Addres }) } - //merge required proof data - proofAcc := tracer.UpdatedAccounts() - for addr := range proofAcc { - addrs := addr.String() - if _, existed := w.current.proofs[addrs]; !existed { + // merge required proof data + proofAccounts := tracer.UpdatedAccounts() + for addr := range proofAccounts { + addrStr := addr.String() + if _, existed := w.current.proofs[addrStr]; !existed { proof, err := w.current.state.GetProof(addr) if err != nil { - log.Error("Proof not available", "address", addrs) - //but we still mark the proofs map with nil array + log.Error("Proof not available", "address", addrStr) + // but we still mark the proofs map with nil array } wrappedProof := make([]hexutil.Bytes, len(proof)) for _, bt := range proof { wrappedProof = append(wrappedProof, bt) } - w.current.proofs[addrs] = wrappedProof + w.current.proofs[addrStr] = wrappedProof } } - proofStg := tracer.UpdatedStorages() - for addr, stgM := range proofStg { - for key := range stgM { - addrs := addr.String() - keys := key.String() - m, existed := w.current.storageProofs[addrs] + proofStorages := tracer.UpdatedStorages() + for addr, keys := range proofStorages { + for key := range keys { + addrStr := addr.String() + m, existed := w.current.storageProofs[addrStr] if !existed { m = make(map[string][]hexutil.Bytes) - w.current.storageProofs[addrs] = m + w.current.storageProofs[addrStr] = m } - if _, existed := m[keys]; !existed { + keyStr := key.String() + if _, existed := m[keyStr]; !existed { proof, err := w.current.state.GetStorageTrieProof(addr, key) if err != nil { - log.Error("Storage proof not available", "address", addrs, "key", keys) - //but we still mark the proofs map with nil array + log.Error("Storage proof not available", "address", addrStr, "key", keyStr) + // but we still mark the proofs map with nil array } wrappedProof := make([]hexutil.Bytes, len(proof)) for _, bt := range proof { wrappedProof = append(wrappedProof, hexutil.Bytes(bt)) } - m[keys] = wrappedProof + m[keyStr] = wrappedProof } } }