fix(rpc): derived transaction support for tracing and block responses - #28
Merged
Merged
Conversation
AryaLanjewar3005
changed the base branch from
audit/evm-merge
to
audit/evm-merge-trace
June 15, 2026 09:28
AryaLanjewar3005
merged commit Jun 15, 2026
25adde0
into
audit/evm-merge-trace
10 of 21 checks passed
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.
Description
fix(rpc): derived transaction support for tracing and block responses
Summary
Two bugs in the 0.5.0 merge caused derived transactions (EVM executions synthesized from non-EVM Cosmos messages) to fail in two separate RPC endpoints. Both regressions are present in
audit/evm-merge-inconsistent-logsbut not infeat/derived-tx-evm-0.4.0.Bug 1 —
debug_traceTransactionreturns "invalid transaction v, r, s values" for derived txsRoot Cause
traceTxinx/vm/keeper/grpc_query.gocallscore.TransactionToMessage(tx, signer, cfg.BaseFee)unconditionally. Derived transactions have no Ethereum signature — they are synthesized from Cosmos ABCI events and carryV=R=S=0.TransactionToMessagetries to recover the sender from these zero-value signature fields and fails with:The predecessor loop (lines 552–560) was already correctly patched with an
isUnsignedguard that callsunsignedTxAsMessage(from, tx, baseFee)instead ofTransactionToMessage. However,traceTxitself — which processes the target transaction, not predecessors — was never updated with the same logic. Thefrom common.Addressparameter was passed in from the call site (common.BytesToAddress(req.Msg.GetFrom())) but was silently ignored insidetraceTx.Fix
x/vm/keeper/grpc_query.go—traceTxfunction:Added the same
isUnsignedcheck that already exists in the predecessor loop. When the target tx is unsigned (derived), construct the EVM message from the pre-populatedfromaddress directly instead of attempting signature recovery.Bug 2 —
eth_getBlockByHashreturns 0 transactions when the block contains only derived txsRoot Cause
The 0.5.0 merge split block building across two functions:
EthBlockFromCometBlock— builds a proper*ethtypes.Block. It intentionally excludes derived txs from the block body (correct: the Ethereum block trie should only contain signed native EVM txs for hash integrity). The comment at that line reads "exclude derived txs from the ETH block body".RPCMarshalBlock— converts the ethBlock to the JSON-RPC response. It builds the"transactions"field fromblock.Transactions(), which are the transactions in the ethBlock body — i.e., only native EVM txs. Derived txs are gone.RPCBlockFromCometBlockcalls both and passes amsgsslice (which does include derived txs) toRPCMarshalBlock, butRPCMarshalBlocknever readsmsgs— it only readsblock.Transactions().In
feat/derived-tx-evm-0.4.0,RPCBlockFromCometBlockbuilt the transaction list manually frommsgs+txsAdditional, using the ABCI event-assigned hash for each derived tx. That path was lost in the 0.5.0 restructure.Fix
rpc/backend/comet_to_eth.go—RPCBlockFromCometBlockfunction:After
RPCMarshalBlockreturns the base block fields, override the"transactions"field with a list built frommsgs+txsAdditional:fullTx=false): use the ABCI event hash for derived txs andethMsg.Hash()for native EVM txs.fullTx=true): useNewTransactionFromMsgfor native EVM txs andNewRPCTransactionFromIncompleteMsg(with the event hash) for derived txs.This restores the behaviour from the working branch while keeping
EthBlockFromCometBlockcorrect (derived txs remain excluded from the actual*ethtypes.Blockbody used for hash computation).Files Changed
x/vm/keeper/grpc_query.goisUnsignedguard intraceTxto useunsignedTxAsMessagefor derived txs instead of failing on signature recoveryrpc/backend/comet_to_eth.goRPCBlockFromCometBlocknow overrides the"transactions"field usingmsgs+txsAdditionalso derived txs appear in block responsesTesting
All 11 existing
BackendTestSuite/TestTraceTransaction*unit tests pass (-tags=test). The two fixes are independently verifiable by tracing a derived-tx hash and by callingeth_getBlockByHashon a block that contains only non-EVM Cosmos txs that triggered EVM executions.Author Checklist
All items are required. Please add a note to the item if the item is not applicable and
please add links to any relevant follow up issues.
I have...
mainbranch