Skip to content

feat: suggest gas price based on latest block's transactions #291

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 22 commits into
base: scroll
Choose a base branch
from

Conversation

yiweichi
Copy link
Member

This PR focus on implementing a simplified version of the GPO without needing to look at the tx pool, however look at the status of latest block. Suggest gas price base on if the latest block is at capacity. this will help to:

  • reduce node configuration complexity by removing congestion threshold parameter
  • reduce RPC node overhead by removing expensive query of tx pool size
  • enable private mempool while any RPC node is still able to provide reasonable gas price estimate

Two JSON_RPC methods are effected.

  1. eth_gasPrice, if the latest block is not at capacity, this will return a minimal suggest gas price.
  2. eth_feeHistory, if the latest block is not at capacity, the reward field of return will be the minimal suggest gas price.

Copy link

codspeed-hq bot commented Jul 27, 2025

CodSpeed Performance Report

Merging #291 will not alter performance

Comparing feat-simplify-gas-price-oracle (02c2e15) with scroll (357655f)

Summary

✅ 77 untouched benchmarks

Copy link
Collaborator

@frisitano frisitano left a comment

Choose a reason for hiding this comment

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

I will leave review of the logic to @jonastheis and @greged93 who have better gas oracle related context. However, I wonder if we can avoid making changes to crates/rpc/rpc-eth-types/src/gas_oracle.rs and instead exclusively use overrides in crates/scroll/* code? Our objective is to minimise our fork diff with upstream.

@yiweichi
Copy link
Member Author

I will leave review of the logic to @jonastheis and @greged93 who have better gas oracle related context. However, I wonder if we can avoid making changes to crates/rpc/rpc-eth-types/src/gas_oracle.rs and instead exclusively use overrides in crates/scroll/* code? Our objective is to minimise our fork diff with upstream.

Yes, that's a good one. I tried to keep crates/rpc/rpc-eth-types/src/gas_oracle.rs as is or make as less changes as possible, but can't find a good way to do so. Mainly because GasPriceOracle on Reth is a struct instead of a trait, seems hard to override it on crates/scroll/*.
@greged93 may I ask any input on this?

Copy link
Collaborator

@greged93 greged93 left a comment

Choose a reason for hiding this comment

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

couple of comments but looks good!

@greged93
Copy link
Collaborator

@greged93 may I ask any input on this?

It looks a little tricky yes, upstream would need to abstract the GasOracle, right now I don't really see any solution.

Base automatically changed from feat-add-max-da-block-size to scroll July 28, 2025 14:12
Copy link
Collaborator

@greged93 greged93 left a comment

Choose a reason for hiding this comment

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

noticed some default values that I think need to be updated.

Copy link
Collaborator

@greged93 greged93 left a comment

Choose a reason for hiding this comment

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

Couple of small comments and questions, I think we can merge after this!

Comment on lines 423 to 434
// get the gas used by each transaction in the block, by subtracting the
// cumulative gas used of the previous transaction from the cumulative gas used of
// the current transaction. This is because there is no gas_used()
// method on the Receipt trait.
.windows(2)
.map(|window| {
let prev = window[0].cumulative_gas_used();
let curr = window[1].cumulative_gas_used();
curr - prev
})
.max()
.expect("len >= 2 guarantees at least one window"),
Copy link
Collaborator

Choose a reason for hiding this comment

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

now that I think about it, won't this always fail to return the gas used for the first receipt? if we have [receipt_one, receipt_two], this would return receipt_two.cumulative_gas_used - receipt_one.cumulative_gas_used right? so you miss receipt_one.cumulative_gas_used?

/// A block is considered at capacity if its total gas used plus the maximum single transaction
/// gas would exceed the block's gas limit, or the total block payload size plus the maximum
/// single transaction would exceed the block's payload size limit.
pub async fn scroll_suggest_tip_cap(
Copy link
Collaborator

Choose a reason for hiding this comment

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

I was checking the gas oracle code from l2geth, and noticed the following:

  • l2geth has these lines to set the suggestion to defaultGasTipCap or defaultBasePrice based on the fork. Do we not need this because Reth will never run on forks pre-Curie?
  • l2geth has two sanity checks here. Should we add these?

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.

3 participants