Skip to content

fix(evm): false positive failed EVM txs due to sdk.GasMeter error after successful ApplyEvmMsg#2521

Merged
Unique-Divine merged 3 commits intomainfrom
ud/fix-gas-err-false-positive
Feb 10, 2026
Merged

fix(evm): false positive failed EVM txs due to sdk.GasMeter error after successful ApplyEvmMsg#2521
Unique-Divine merged 3 commits intomainfrom
ud/fix-gas-err-false-positive

Conversation

@Unique-Divine
Copy link
Copy Markdown
Member

@Unique-Divine Unique-Divine commented Feb 10, 2026

Fix false failed EVM txs from SafeConsumeGas / gas-meter misalignment

Align Cosmos gas accounting with the EVM's own gas usage so that successful EVM transactions (including zero-fee ones) are never reported as failed solely due to a late SafeConsumeGas error on the SDK gas meter.

Key Changes

  • Root cause

    • For the production perps open_trade tx in 26-02-10-zero-gas-debug.md, the EVM trace and receipt show success (23 logs), but eth.evm.v1.EventEthereumTx reports vm_error="gas consumption failed: gasConsumed=719812, gasRemaining=0, {execute EthereumTx}" and status: 0x0.
    • The per-tx sdk.GasMeter was counting both ante/Cosmos work (~138k) and EVM GasUsed (~581k) via a late SafeConsumeGas call in EthereumTx, so gasConsumed could exceed the user's gas limit even when GasUsed ≤ gasLimit.
  • EthereumTx gas accounting

    • In x/evm/evmstate/msg_server.go::EthereumTx, after a successful ApplyEvmMsg we now:
      • Refund any prior gas on the root context's meter (RefundGas(consumed, "reset gas before EVM charge")), preserving the limit but resetting consumption to zero.
      • Re-charge the meter with exactly evmResp.GasUsed via evm.SafeConsumeGas(sdb.RootCtx(), evmResp.GasUsed, "execute EthereumTx"), so the SDK meter reflects only EVM gas.
    • If SafeConsumeGas still errors and evmResp.Failed() == false, we log the error and continue instead of overwriting evmResp.VmError, since EVM gas is the ground truth and a host-side meter issue should not flip a successful tx to failed.
  • Post-execution behavior

    • After syncing gas, both the root context and SDB context are switched to infinite gas meters for bloom updates, block log size, events, and tx index, so bookkeeping cannot change the final gas cost or panic on gas.
    • Refund logic is unchanged: non-zero-fee txs still refund msg.GasLimit - evmResp.GasUsed in wei; zero-fee txs still skip refunds.
  • Ante handler responsibilities

    • x/evm/evmante/evmante_gas_consume.go is documented as a two-phase model:
      • Ante phase: AnteStepGasWanted and AnteStepBlockGasMeter use infinite meters with limits to validate tx/block gas and priority; AnteStepFiniteGasLimitForABCIDeliverTx installs a finite meter so ABCI GasWanted sees the user gas limit.
      • Execution phase: the EVM tracks gas internally; only EthereumTx's SafeConsumeGas call (after the refund-to-zero) records final GasUsed on the SDK meter, avoiding double-counting ante work.
  • Tests and invariants

    • In x/evm/evmstate/funtoken_from_erc20_test.go, the fun-token infinite recursion tests now assert that, after the fix:
      • An underfunded fee-collector case fails explicitly at refund time (no evmResp).
      • With proper funding, a re-run of EthereumTx succeeds and satisfies ctx.GasMeter().GasConsumed() == evmResp.GasUsed, proving Cosmos gas accounting matches EVM GasUsed for that path.
    • Together with the on-chain analysis in 26-02-10-zero-gas-debug.md, these tests guard against regressions where ante + EVM gas are recombined or SafeConsumeGas errors are surfaced as false EVM failures.

Appendix

  • Behavioral impact
    • For users and wallets, gas continues to mean “EVM execution gas limit”, and the reported GasUsed in receipts and ABCI results now reflects only EVM work; a tx the EVM considers successful (receipt status = 0x1) will no longer be marked failed purely due to host gas-meter alignment issues.
    • For operators and debugging, any future SafeConsumeGas error after EVM success will appear only as a log mentioning gas-meter misalignment; the detailed reproduction in 26-02-10-zero-gas-debug.md remains a reference for tracing such issues and confirms that the original 581k/669k scenario no longer yields a false failed EVM tx.

@Unique-Divine Unique-Divine requested a review from a team as a code owner February 10, 2026 11:22
@Unique-Divine Unique-Divine added the x: evm Relates to Nibiru EVM or the EVM Module label Feb 10, 2026
Copy link
Copy Markdown
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

This pull request effectively resolves a critical bug where successful EVM transactions were incorrectly reported as failed due to a gas accounting mismatch between the Cosmos SDK and the EVM. The core logic of resetting the gas meter before applying the EVM's gas usage is a solid and correct approach. I appreciate the detailed explanation and the thoroughness of the changes, including the updated tests which now correctly assert the new gas accounting behavior. My review includes a couple of minor suggestions to improve logging and test code quality.

Comment thread x/evm/evmstate/funtoken_from_erc20_test.go Outdated
Comment thread x/evm/evmstate/msg_server.go
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
@codecov
Copy link
Copy Markdown

codecov bot commented Feb 10, 2026

Codecov Report

❌ Patch coverage is 75.00000% with 3 lines in your changes missing coverage. Please review.
✅ Project coverage is 59.11%. Comparing base (8b47bf1) to head (819a916).
⚠️ Report is 1 commits behind head on main.

Files with missing lines Patch % Lines
x/evm/evmstate/msg_server.go 75.00% 2 Missing and 1 partial ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main    #2521      +/-   ##
==========================================
+ Coverage   59.09%   59.11%   +0.01%     
==========================================
  Files         361      361              
  Lines       24421    24429       +8     
==========================================
+ Hits        14432    14440       +8     
  Misses       8751     8751              
  Partials     1238     1238              
Files with missing lines Coverage Δ
x/evm/evm.go 50.00% <ø> (ø)
x/evm/evmante/evmante_gas_consume.go 82.55% <ø> (ø)
x/evm/evmstate/msg_server.go 85.64% <75.00%> (+0.27%) ⬆️
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@Unique-Divine Unique-Divine enabled auto-merge (squash) February 10, 2026 11:48
@Unique-Divine Unique-Divine merged commit 2b63828 into main Feb 10, 2026
9 checks passed
@Unique-Divine Unique-Divine deleted the ud/fix-gas-err-false-positive branch February 10, 2026 12:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

x: evm Relates to Nibiru EVM or the EVM Module

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants