Gravity v1.7.0
Release: v1.7.0
Full Changelog: v1.6.2...v1.7.0
Related pinned components:
- gravity-reth: rev
0adbb4c9— picks up three greth PRs since v1.6.2: #341 (EIP-2935), #343 (EIP-7702 filter), #345 (grevm bump for EIP-7702 self-auth fix)
This is the Prague release on Gravity. Under the hood it lights up EIP-2935 (8,191-block history precompile via the HISTORY_STORAGE deployment hook) and EIP-7702 (SetCode authorizations), both gated by pragueTime in chainspec. A dedicated single-node Prague e2e suite under gravity_e2e/cluster_test_cases/prague/ ships alongside. Plus a fresh round of audit-#602 consensus picks.
Tagged as a pre-release. The Prague gates are dormant until
pragueTimeis set in genesis; mainnet networks without that key continue to behave like v1.6.x.
Breaking Changes
Prague hardfork wiring (gravity-reth)
The new behaviour activates when genesis.config.pragueTime is set to a value > the genesis timestamp. pragueTime = 0 silently leaves HISTORY_STORAGE unallocated, because the deployment hook gate is parent_ts < pragueTime <= current_ts. Networks intending to enable Prague at block 1 must set pragueTime = genesis_timestamp_secs + 1.
EIP-2935 HISTORY_STORAGE returns the Aptos consensus block_id, not the EVM block_hash
The pipe layer hijacks header.parent_hash with ordered_block.parent_id before the upstream SystemCaller SSTOREs into HISTORY_STORAGE. The slot stored is therefore the parent's Aptos block_id, and the same value is exposed via parentBeaconBlockRoot on the RPC side. Clients querying historical hashes through the new precompile must treat the returned value as a consensus block_id, not an EVM block_hash. The supplied helper _block_id(n) reads block(n+1).parentBeaconBlockRoot.
What's Changed
Features / Tests
- test(e2e): add Prague hardfork (EIP-2935 / EIP-7702) acceptance suite by @nekomoto911 in #734
- New single-node suite under
gravity_e2e/cluster_test_cases/prague/, 10 cases, ~83 s wall-clock:- P-A1..P-A5 (EIP-2935) — direct
eth_call(HISTORY_STORAGE)returns the queried block's id; multi-block lookups across an 8-block window; Solidity contractHistoryReader.solusingstaticcall;eth_call(n >= block.number)reverts; lookups still work after an epoch boundary. - P-B1..P-B5 (EIP-7702) — delegated stateless / stateful calls; revocation (
target = 0x00…00) reverts an authority to plain-EOA behaviour; pipe-exec filter dropsgas_limit < 21000 + 25000·N(auths)SetCode txs; sufficiently-gassed SetCode txs pass.
- P-A1..P-A5 (EIP-2935) — direct
- Bumps
eth-accountminimum to0.13.6(signsSignedSetCodeAuthorization). - Genesis config notes:
chain_id = 1337, single validator, faucet pre-funded;cluster.tomluses the post-#690validator_portnaming.
- New single-node suite under
Bug Fixes — Consensus (audit #602 picks)
- fix: Pick audit 602 consensus fixes by @Lchangliang in #735
Dependencies (greth)
- chore(deps): bump gravity-reth to 0adbb4c9 (EIP-7702 self-auth fix) + e2e by @nekomoto911 in #738
- Bumps greth
46c91f9 → 0adbb4c9(gravity-reth#345 merge). Net effect: grevm26b586c(v2.2.4) →3c09e7c(Galxe/grevm#102). - Why: v2.2.4 panicked deterministically inside
StateAsyncCommit::commiton type-4 SetCode txs wheretx.fromwas also listed in the authorization list as an authority. That is the exactsimple-bench --transfer-type eip7702pattern that halted Gravity testnet at block 1400868 on 2026-06-09, and the same input shape is reachable on mainnet once EIP-7702 opens. The grevm fix relaxes the caller-nonce assertion. - Locks in a regression test
test_p_b6_self_sponsored_self_delegationso the chain-halt shape cannot silently come back. Three regression oracles: receipt arrives within timeout (pre-fix the validator panicked, no receipt would ever come back);receipt.status == 1; a new block is produced afterreceipt.blockNumberwithin 30 s. - Generalizes the shared
_send_setcode_txhelper: whensender == authority, signs the auth tuple withsender_nonce + 1instead ofsender_nonce. Per EIP-7702 the authorization is applied after the tx's own nonce bump, so for self-sponsored self-delegation the auth-tuple nonce must be one ahead.
- Bumps greth
Documentation
- docs: add gravity cli skill by @Lchangliang in #729
- Adds
.agents/skills/gravity-cli/SKILL.md— documents the command tree, config/profile defaults, signer behaviour, source-vs-binary command availability fordoctorandqs-db, and safety notes.
- Adds
- docs: update genesis assets by @Lchangliang in #736
- Updates testnet
genesis.json/waypoint.txtfromGalxe/mono-grav docs/testnet/cluster; adds mainnetgenesis.json/waypoint.txtfromGalxe/gravity-mainnet-gitops; removes moved testnet docs fromgenesis/testnet/docs.
- Updates testnet
CI
- ci(release): switch to v.. tag trigger and add workflow_dispatch* by @nekomoto911 in #739
- Auto-trigger is scoped to
v*.*.*tags only — the legacygravity-mainnet-*/gravity-testnet-*patterns are dropped. Future releases follow a singlev<major>.<minor>.<patch>track. - Adds a
workflow_dispatchinput so a release can be re-run manually from the Actions UI against any existingv*.*.*tag (useful for retrying a failed upload). Resolve tagstep validates^v[0-9]+\.[0-9]+\.[0-9]+for both push and dispatch paths.
- Auto-trigger is scoped to
gravity-reth changes since v1.6.2
The greth pin moved from acc45884 to 0adbb4c9. Three commits, all Prague-related; v1.7.0 ships them as a coherent set:
#341 feat(eip-2935): serve 8191-block history via Prague-gated activation (ba7e9494)
Deploys the HISTORY_STORAGE contract on the Prague activation block as an irregular state change driven from the pipe layer, then lets upstream SystemCaller drive the per-block SSTORE. Activation is dormant until pragueTime is set in chainspec.
- Block executor stays a pure execution engine (only runs system calls + transactions); the pipe-layer orchestration owns the fork-block irregular state change — matches the layering of mainnet's own pre-Pectra EOA deployment of HISTORY_STORAGE.
- New evm-trait methods:
ParallelExecutor::apply_state_change(state_diff)andExecutor::apply_state_change(state_diff)for irregular-state-change mutations that are inherently not transaction-shaped (CREATE/CREATE2cannot target the canonical vanity address without a mined deployer key). Implemented acrossGrevmExecutor,BasicBlockExecutor,Either,WrapExecutor(delegating to the newExecutormethod sodisable_grevm=truebehaves identically). - Pipe layer:
create_block_for_executorsetsheader.parent_hash = ordered_block.parent_idso the SystemCaller picks up the consensusblock_id.
#343 fix(eip-7702): filter intrinsic gas + Gravity acceptance tests (46c91f90)
The pre-execution filter now mirrors the pool's ensure_intrinsic_gas, so a TxEip7702 with gas_limit < 21000 + 25000·N injected outside the pool's fork-gate is discarded instead of reaching grevm and panicking the executor with IntrinsicGasTooLow. Closes gravity-audit#668.
Also splits filter_invalid_txs and its tests into a new tx_filter module per the pipe-exec-layer-lib-refactor design — shrinks lib.rs from 1829 to 1448 lines and gives audit follow-ups a self-contained surface.
#345 fix(deps): bump grevm to 3c09e7c for EIP-7702 self-auth nonce fix (0adbb4c9)
Pins grevm by rev to the merge of Galxe/grevm#102, which relaxes the StateAsyncCommit caller-nonce assertion so EIP-7702 self-sponsored self-delegation no longer panics. The deployed v2.2.4 pin (26b586c) crashed deterministically on type-4 SetCode txs where tx.from was also listed as an authority — the bench pattern that halted Gravity testnet at block 1400868 on 2026-06-09 and that is reachable on mainnet via the same input. Also pulls in two grevm security-audit fixes (Galxe/grevm#99 / #101) that landed between v2.2.4 and the EIP-7702 fix.
Refs Galxe/gravity-audit#677.