Skip to content

[DNM] glamsterdam-devnet-4 rebased on main (CI only) - #6772

Closed
edg-l wants to merge 10 commits into
mainfrom
glamsterdam-devnet-4
Closed

edg-l wants to merge 10 commits into
mainfrom
glamsterdam-devnet-4

Conversation

@edg-l

@edg-l edg-l commented Jun 2, 2026

Copy link
Copy Markdown
Contributor

[DNM] — Do Not Merge. Opened to run CI on the rebased glamsterdam-devnet-4 branch.

This branch was rebased onto main via cherry-pick. 5 commits already present on main were dropped (FCU finalized-ancestor work via #6676; BAL storage prefetch via #6732). The 10 commits below are the net-new work:

  • perf(l1): per-tx BAL validation in the par_iter closure
  • perf(l1): batch account-state prefetch via rocksdb multi_get_cf (perf(l1): batch account-state prefetch via rocksdb multi_get_cf #6712)
  • perf(l1): parallelize trie fallback in account batch lookup
  • perf(l1): tighten batch prefetch + drop redundant clone in get_account_state_multi
  • engine_forkchoiceUpdatedV4 targetGasLimit (execution-apis#796)
  • chore(p2p): clean up RLPx handshake logs
  • docs(changelog) entries

Not for merge; tracking CI only.

edg-l and others added 10 commits June 2, 2026 10:22
execute_block_parallel previously returned (current_state, codes,
shadow_touched, shadow_reads) per tx and validated them in a serial post-loop
across all txs (validate_tx_execution + shadow checks + mark
unread_storage_reads / unaccessed_pure_accounts).

Validation is per-tx pure work; only marking the shared sets mutates
cross-tx state. Move validate_tx_execution + shadow_touched/shadow_reads
checks into the closure. Precompute the small (Vec<(Address, H256)>,
Vec<Address>) inputs the serial pass needs to update the shared sets.
Drop current_state + codes inside the closure so they no longer cross
the rayon boundary.

Defer BAL validation errors via Option<EvmError> in the result tuple so
the post-par_iter gas-limit check still takes priority over BAL mismatch
(preserves GAS_USED_OVERFLOW > BAL error ordering for blocks exceeding
the gas limit).

Expected win on 200-tx blocks: the ~3 ms median serial validation pass
goes away. Also reduces per-tx allocator pressure across rayon workers
since the per-tx maps are dropped before the result tuple is constructed.
- reads_satisfied: pre-size with current_state.len() * 4 to skip 2-3
  reallocations on the hot path (rough avg slots-per-account).
- destroyed: keep Vec::new() since selfdestruct is rare post-EIP-6780;
  no-allocation default is optimal.
- Document why the post-collect sort_unstable_by_key is a defensive
  no-op (IndexedParallelIterator preserves order) so a future refactor
  doesn't drop the guard.

Addresses ElFantasma feedback on #6677.
Replace N parallel point-gets in CachingDatabase::prefetch_accounts with
a single multi_get_cf on ACCOUNT_FLATKEYVALUE for FKV-covered addresses,
falling back to per-address trie walks for paths past the FKV cursor.
Reduces warmer-phase cost on the bal-devnet-7 fixture from 6.78 ms to
2.37 ms per block (-65%); total wall time -21.5%.
Address review feedback on PR #6712:

- store.rs: hoist `fkv_cursor` out of the per-address loop and document
  why the comparison matches `BackendTrieDB::flatkeyvalue_computed`'s
  semantics (not the more-conservative
  `flatkeyvalue_computed_with_last_written`). Drop the dead
  `diff_hits` counter.
- vm.rs: comment on why `cache.insert` (vs `or_insert`) is intentional.
- rocksdb.rs: clone a `String` instead of formatting the error per key.
Address review feedback on #6712:

- Parallelize the trie-walk fallback in get_account_states_batch_by_root
  with rayon par_iter, recovering the per-address fan-out that the
  pre-batch prefetch_accounts path had. Matters during initial sync when
  most addresses miss the FKV cursor; no effect on the FKV-hot path.
- Drop per-iteration Nibbles::from_hex(path.clone()) in the classifier
  loop; compare last_written and the leaf path as slices directly
  (Nibbles::Ord delegates to data Vec compare, so this is equivalent).
- Expand multi_get rustdoc to spell out that the default impl is
  equivalent to N get calls on backends without a batched primitive.
…96) for glamsterdam-devnet-4

Extends PayloadAttributesV4 with the new required target_gas_limit field
introduced by execution-apis#796 and consensus-specs#5235 (Gloas /
upstream "Glamsterdam"). The CL is now the authoritative source of the
per-block target gas limit on engine_forkchoiceUpdatedV4 instead of the
EL reading it from the static --builder.gas-limit flag.

validate_attributes_v4 strictly rejects FCUv4 requests that omit the
field with RpcErr::InvalidPayloadAttributes, matching the spec contract.
The paired CL on glamsterdam-devnet-4 ships consensus-specs#5235 and
populates the field on every FCUv4 it sends.

build_payload_v4 sets BuildPayloadArgs.gas_ceil directly from the
attribute. The EIP-1559 1/1024 gas-limit envelope inside calc_gas_limit
continues to clamp the value relative to the parent block. V1/V2/V3 and
non-engine callers (sequencer, dev mode) keep using --builder.gas-limit.

Also fixes a latent collision in BuildPayloadArgs::id(): slot_number was
never hashed and gas_ceil now matters per-call, so two FCUv4s differing
only in CL-supplied targetGasLimit could collide on payload_id. Both
fields are now part of the Keccak input.

Tests added:
- payload-attribute parser round-trips for hex value present, field
  absent, and explicit null
- validator accepts present, rejects absent (matches spec error
  message), and continues to reject pre-Amsterdam timestamps
- BuildPayloadArgs::id() distinguishes different gas_ceil values and
  different slot_number values, and is stable under equal inputs
- calc_gas_limit steps up/down toward target within one EIP-1559 1/1024
  step and clamps when the target is within one step
- Combine the per-protocol "Negotatied eth/snap version" debug pair into
  a single structured line that includes the peer node and client id.
  Two unrelated-looking lines for the same connection are now one.
- Fix the `Negotatied` typo in the same site.
- Demote `early eof` IO errors during the handshake to TRACE; they are
  expected on simultaneous-dial races (both peers initiate, only one
  connection wins). Other handshake failures stay at DEBUG with
  structured `error` field.
@github-actions

github-actions Bot commented Jun 2, 2026

Copy link
Copy Markdown

⚠️ Known Issues — intentionally skipped tests

Source: docs/known_issues.md

Known Issues

Tests intentionally excluded from CI. Source of truth for the Known
Issues
section the L1 workflow appends to each ef-tests job summary
and posts as a sticky PR comment.

EF Tests — Stateless coverage narrowed to EIP-8025 optional-proofs

make -C tooling/ef_tests/blockchain test calls test-stateless-zkevm
instead of test-stateless. The zkevm@v0.3.3 fixtures are filled against
bal@v5.6.1, out of sync with current bal spec; the broad target trips ~549
fixtures. Re-broaden once the zkevm bundle is regenerated.

Why and resolution path

PR #6527 broadened
test-stateless to extract the entire for_amsterdam/ tree from the
zkevm bundle and run all of it under --features stateless; combined with
this branch's bal-devnet-7 semantics that scope produces ~549
GasUsedMismatch / ReceiptsRootMismatch /
BlockAccessListHashMismatch failures.

test-stateless-zkevm filters cargo to the eip8025_optional_proofs
suite, which still validates the stateless harness without the bal-version
mismatch.

Re-broaden by switching test: back to test-stateless in
tooling/ef_tests/blockchain/Makefile once the zkevm bundle is regenerated
against the current bal spec.

@github-actions

github-actions Bot commented Jun 2, 2026

Copy link
Copy Markdown

Lines of code report

Total lines added: 400
Total lines removed: 0
Total lines changed: 400

Detailed view
+--------------------------------------------------------+-------+------+
| File                                                   | Lines | Diff |
+--------------------------------------------------------+-------+------+
| ethrex/crates/blockchain/payload.rs                    | 920   | +66  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/blockchain/vm.rs                         | 269   | +54  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/networking/p2p/rlpx/connection/server.rs | 1526  | +10  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/networking/rpc/engine/fork_choice.rs     | 679   | +117 |
+--------------------------------------------------------+-------+------+
| ethrex/crates/networking/rpc/types/fork_choice.rs      | 57    | +2   |
+--------------------------------------------------------+-------+------+
| ethrex/crates/storage/api/mod.rs                       | 44    | +7   |
+--------------------------------------------------------+-------+------+
| ethrex/crates/storage/backend/rocksdb.rs               | 349   | +20  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/storage/store.rs                         | 2792  | +69  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/vm/backends/levm/db.rs                   | 122   | +11  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/vm/backends/levm/mod.rs                  | 2414  | +18  |
+--------------------------------------------------------+-------+------+
| ethrex/crates/vm/db.rs                                 | 25    | +9   |
+--------------------------------------------------------+-------+------+
| ethrex/crates/vm/levm/src/db/mod.rs                    | 165   | +17  |
+--------------------------------------------------------+-------+------+

@github-actions

github-actions Bot commented Jun 2, 2026

Copy link
Copy Markdown

Benchmark Results Comparison

No significant difference was registered for any benchmark run.

Detailed Results

Benchmark Results: BubbleSort

Command Mean [s] Min [s] Max [s] Relative
main_revm_BubbleSort 3.019 ± 0.019 2.987 3.041 1.07 ± 0.01
main_levm_BubbleSort 2.829 ± 0.013 2.809 2.851 1.00 ± 0.01
pr_revm_BubbleSort 2.982 ± 0.025 2.946 3.025 1.06 ± 0.01
pr_levm_BubbleSort 2.818 ± 0.012 2.801 2.839 1.00

Benchmark Results: ERC20Approval

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_ERC20Approval 971.3 ± 5.8 963.9 981.2 1.00 ± 0.01
main_levm_ERC20Approval 1070.8 ± 12.1 1055.0 1097.8 1.11 ± 0.01
pr_revm_ERC20Approval 966.9 ± 5.4 961.3 980.1 1.00
pr_levm_ERC20Approval 1072.1 ± 8.7 1057.7 1087.2 1.11 ± 0.01

Benchmark Results: ERC20Mint

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_ERC20Mint 132.8 ± 1.0 131.3 135.0 1.00 ± 0.02
main_levm_ERC20Mint 157.7 ± 1.4 156.1 161.2 1.19 ± 0.02
pr_revm_ERC20Mint 132.8 ± 2.1 130.3 136.5 1.00
pr_levm_ERC20Mint 158.6 ± 1.4 157.0 161.7 1.19 ± 0.02

Benchmark Results: ERC20Transfer

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_ERC20Transfer 233.1 ± 3.5 230.3 241.5 1.02 ± 0.02
main_levm_ERC20Transfer 262.9 ± 1.7 261.0 267.0 1.15 ± 0.01
pr_revm_ERC20Transfer 228.1 ± 0.4 227.5 228.8 1.00
pr_levm_ERC20Transfer 265.0 ± 1.8 261.8 267.1 1.16 ± 0.01

Benchmark Results: Factorial

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_Factorial 228.4 ± 1.5 226.2 232.1 1.01 ± 0.01
main_levm_Factorial 273.9 ± 3.4 270.6 282.6 1.21 ± 0.02
pr_revm_Factorial 227.3 ± 1.7 225.6 231.5 1.00
pr_levm_Factorial 274.3 ± 2.5 270.5 278.1 1.21 ± 0.01

Benchmark Results: FactorialRecursive

Command Mean [s] Min [s] Max [s] Relative
main_revm_FactorialRecursive 1.708 ± 0.031 1.653 1.771 1.05 ± 0.02
main_levm_FactorialRecursive 1.633 ± 0.025 1.613 1.691 1.00 ± 0.02
pr_revm_FactorialRecursive 1.686 ± 0.026 1.646 1.720 1.03 ± 0.02
pr_levm_FactorialRecursive 1.631 ± 0.012 1.611 1.651 1.00

Benchmark Results: Fibonacci

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_Fibonacci 208.5 ± 1.2 207.2 210.6 1.01 ± 0.01
main_levm_Fibonacci 253.4 ± 5.2 246.6 262.8 1.22 ± 0.03
pr_revm_Fibonacci 207.3 ± 0.8 206.4 209.1 1.00
pr_levm_Fibonacci 252.2 ± 3.5 247.9 256.9 1.22 ± 0.02

Benchmark Results: FibonacciRecursive

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_FibonacciRecursive 892.8 ± 10.7 875.1 909.2 1.20 ± 0.02
main_levm_FibonacciRecursive 743.3 ± 9.9 728.7 759.8 1.00
pr_revm_FibonacciRecursive 885.0 ± 9.1 876.8 906.0 1.19 ± 0.02
pr_levm_FibonacciRecursive 744.6 ± 4.9 737.5 753.3 1.00 ± 0.01

Benchmark Results: ManyHashes

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_ManyHashes 8.4 ± 0.1 8.3 8.6 1.01 ± 0.01
main_levm_ManyHashes 10.1 ± 0.4 9.7 11.2 1.21 ± 0.05
pr_revm_ManyHashes 8.3 ± 0.0 8.3 8.4 1.00
pr_levm_ManyHashes 10.0 ± 0.2 9.8 10.3 1.20 ± 0.02

Benchmark Results: MstoreBench

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_MstoreBench 265.0 ± 4.5 262.1 277.1 1.15 ± 0.02
main_levm_MstoreBench 231.3 ± 2.1 228.9 235.3 1.00 ± 0.01
pr_revm_MstoreBench 266.3 ± 4.9 262.3 275.6 1.16 ± 0.02
pr_levm_MstoreBench 230.4 ± 1.0 228.8 232.4 1.00

Benchmark Results: Push

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_Push 295.0 ± 1.3 292.7 297.3 1.01 ± 0.01
main_levm_Push 292.2 ± 1.4 290.1 294.5 1.00 ± 0.01
pr_revm_Push 294.5 ± 1.1 292.4 296.5 1.01 ± 0.01
pr_levm_Push 291.7 ± 1.2 290.5 294.1 1.00

Benchmark Results: SstoreBench_no_opt

Command Mean [ms] Min [ms] Max [ms] Relative
main_revm_SstoreBench_no_opt 164.3 ± 3.7 161.7 172.1 1.64 ± 0.04
main_levm_SstoreBench_no_opt 101.8 ± 4.0 100.1 113.3 1.01 ± 0.04
pr_revm_SstoreBench_no_opt 166.9 ± 6.7 162.1 181.2 1.66 ± 0.07
pr_levm_SstoreBench_no_opt 100.4 ± 0.4 100.0 101.1 1.00

@edg-l edg-l closed this Jun 2, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants