Skip to content
Merged
Show file tree
Hide file tree
Changes from 9 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 0 additions & 2 deletions cmd/geth/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -185,8 +185,6 @@ var (
utils.DARecoverySignBlocksFlag,
utils.DARecoveryL2EndBlockFlag,
utils.DARecoveryProduceBlocksFlag,
utils.L2BaseFeeScalarFlag,
utils.L2BaseFeeOverheadFlag,
}

rpcFlags = []cli.Flag{
Expand Down
2 changes: 0 additions & 2 deletions cmd/geth/usage.go
Original file line number Diff line number Diff line change
Expand Up @@ -236,8 +236,6 @@ var AppHelpFlagGroups = []flags.FlagGroup{
utils.L1DeploymentBlockFlag,
utils.L1DisableMessageQueueV2Flag,
utils.RollupVerifyEnabledFlag,
utils.L2BaseFeeScalarFlag,
utils.L2BaseFeeOverheadFlag,
utils.DASyncEnabledFlag,
utils.DABlobScanAPIEndpointFlag,
utils.DABlockNativeAPIEndpointFlag,
Expand Down
37 changes: 0 additions & 37 deletions cmd/utils/flags.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,6 @@ import (
"github.com/scroll-tech/go-ethereum/consensus"
"github.com/scroll-tech/go-ethereum/consensus/clique"
"github.com/scroll-tech/go-ethereum/consensus/ethash"
"github.com/scroll-tech/go-ethereum/consensus/misc"
"github.com/scroll-tech/go-ethereum/core"
"github.com/scroll-tech/go-ethereum/core/rawdb"
"github.com/scroll-tech/go-ethereum/core/vm"
Expand Down Expand Up @@ -935,18 +934,6 @@ var (
Name: "da.recovery.produceblocks",
Usage: "Produce unsigned blocks after L1 recovery for permissionless batch submission",
}

// L2 base fee settings
L2BaseFeeScalarFlag = BigFlag{
Name: "basefee.scalar",
Usage: "Scalar used in the l2 base fee formula. Signer nodes will use this for computing the next block's base fee. Follower nodes will use this in RPC.",
Value: misc.DefaultBaseFeeScalar,
}
L2BaseFeeOverheadFlag = BigFlag{
Name: "basefee.overhead",
Usage: "Overhead used in the l2 base fee formula. Signer nodes will use this for computing the next block's base fee. Follower nodes will use this in RPC.",
Value: misc.DefaultBaseFeeOverhead,
}
)

// MakeDataDir retrieves the currently requested data directory, terminating
Expand Down Expand Up @@ -1722,29 +1709,6 @@ func setDA(ctx *cli.Context, cfg *ethconfig.Config) {
}
}

func setBaseFee(ctx *cli.Context, cfg *ethconfig.Config) {
cfg.BaseFeeScalar = misc.DefaultBaseFeeScalar
if ctx.GlobalIsSet(L2BaseFeeScalarFlag.Name) {
cfg.BaseFeeScalar = GlobalBig(ctx, L2BaseFeeScalarFlag.Name)
}
cfg.BaseFeeOverhead = misc.DefaultBaseFeeOverhead
if ctx.GlobalIsSet(L2BaseFeeOverheadFlag.Name) {
cfg.BaseFeeOverhead = GlobalBig(ctx, L2BaseFeeOverheadFlag.Name)
}

log.Info("L2 base fee coefficients", "scalar", cfg.BaseFeeScalar, "overhead", cfg.BaseFeeOverhead)

var minBaseFee uint64
if fee := misc.MinBaseFee(cfg.BaseFeeScalar, cfg.BaseFeeOverhead); fee.IsUint64() {
minBaseFee = fee.Uint64()
}

if cfg.TxPool.PriceLimit < minBaseFee {
log.Warn("Updating txpool price limit to min L2 base fee", "provided", cfg.TxPool.PriceLimit, "updated", minBaseFee)
cfg.TxPool.PriceLimit = minBaseFee
}
}

func setMaxBlockRange(ctx *cli.Context, cfg *ethconfig.Config) {
if ctx.GlobalIsSet(MaxBlockRangeFlag.Name) {
cfg.MaxBlockRange = ctx.GlobalInt64(MaxBlockRangeFlag.Name)
Expand Down Expand Up @@ -1821,7 +1785,6 @@ func SetEthConfig(ctx *cli.Context, stack *node.Node, cfg *ethconfig.Config) {
setCircuitCapacityCheck(ctx, cfg)
setEnableRollupVerify(ctx, cfg)
setDA(ctx, cfg)
setBaseFee(ctx, cfg)
setMaxBlockRange(ctx, cfg)
if ctx.GlobalIsSet(ShadowforkPeersFlag.Name) {
cfg.ShadowForkPeerIDs = ctx.GlobalStringSlice(ShadowforkPeersFlag.Name)
Expand Down
45 changes: 32 additions & 13 deletions consensus/misc/eip1559.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,10 @@ package misc
import (
"fmt"
"math/big"
"sync"

"github.com/scroll-tech/go-ethereum/core/types"
"github.com/scroll-tech/go-ethereum/log"
"github.com/scroll-tech/go-ethereum/params"
)

Expand All @@ -33,11 +35,35 @@ const MaximumL2BaseFee = 10000000000
// `scalar` accounts for finalization costs. `overhead` accounts for sequencing and proving costs.
// we use 1e18 for precision to match the contract implementation.
var (
BaseFeePrecision = new(big.Int).SetUint64(1e18)
DefaultBaseFeeScalar = new(big.Int).SetUint64(34000000000000)
DefaultBaseFeeOverhead = new(big.Int).SetUint64(15680000)
BaseFeePrecision = new(big.Int).SetUint64(1e18)

// scalar and overhead are updated automatically in `Blockchain.writeBlockWithState`.
baseFeeScalar = big.NewInt(0)
baseFeeOverhead = big.NewInt(0)

lock sync.RWMutex
)

func UpdateL2BaseFeeOverhead(newOverhead *big.Int) {
if newOverhead == nil {
log.Error("Failed to set L2 base fee overhead, new value is <nil>")
return
}
lock.Lock()
defer lock.Unlock()
baseFeeOverhead.Set(newOverhead)
}

func UpdateL2BaseFeeScalar(newScalar *big.Int) {
if newScalar == nil {
log.Error("Failed to set L2 base fee scalar, new value is <nil>")
return
}
lock.Lock()
defer lock.Unlock()
baseFeeScalar.Set(newScalar)
}

// VerifyEip1559Header verifies some header attributes which were changed in EIP-1559,
// - gas limit check
// - basefee check
Expand Down Expand Up @@ -65,16 +91,9 @@ func CalcBaseFee(config *params.ChainConfig, parent *types.Header, parentL1BaseF
return big.NewInt(10000000) // 0.01 Gwei
}

scalar := config.Scroll.BaseFeeScalar
if scalar == nil {
scalar = DefaultBaseFeeScalar
}
overhead := config.Scroll.BaseFeeOverhead
if overhead == nil {
overhead = DefaultBaseFeeOverhead
}

return calcBaseFee(scalar, overhead, parentL1BaseFee)
lock.RLock()
defer lock.RUnlock()
return calcBaseFee(baseFeeScalar, baseFeeOverhead, parentL1BaseFee)
}

// MinBaseFee calculates the minimum L2 base fee based on the configured coefficients.
Expand Down
8 changes: 5 additions & 3 deletions consensus/misc/eip1559_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,8 +122,8 @@ func TestCalcBaseFee(t *testing.T) {
}
for i, test := range tests {
config := config()
config.Scroll.BaseFeeScalar = big.NewInt(10000000)
config.Scroll.BaseFeeOverhead = big.NewInt(1)
UpdateL2BaseFeeScalar(big.NewInt(10000000))
UpdateL2BaseFeeOverhead(big.NewInt(1))
if have, want := CalcBaseFee(config, nil, big.NewInt(test.parentL1BaseFee)), big.NewInt(test.expectedL2BaseFee); have.Cmp(want) != 0 {
t.Errorf("test %d: have %d want %d, ", i, have, want)
}
Expand All @@ -142,6 +142,8 @@ func TestCalcBaseFee(t *testing.T) {
{644149677419355, 10000000000}, // cap at max L2 base fee
}
for i, test := range testsWithDefaults {
UpdateL2BaseFeeScalar(big.NewInt(34000000000000))
UpdateL2BaseFeeOverhead(big.NewInt(15680000))
if have, want := CalcBaseFee(config(), nil, big.NewInt(test.parentL1BaseFee)), big.NewInt(test.expectedL2BaseFee); have.Cmp(want) != 0 {
t.Errorf("test %d: have %d want %d, ", i, have, want)
}
Expand All @@ -150,7 +152,7 @@ func TestCalcBaseFee(t *testing.T) {

// TestMinBaseFee assumes all blocks are 1559-blocks
func TestMinBaseFee(t *testing.T) {
if have, want := MinBaseFee(DefaultBaseFeeScalar, DefaultBaseFeeOverhead), big.NewInt(15680000); have.Cmp(want) != 0 {
if have, want := MinBaseFee(big.NewInt(34000000000000), big.NewInt(15680000)), big.NewInt(15680000); have.Cmp(want) != 0 {
t.Errorf("have %d want %d, ", have, want)
}

Expand Down
33 changes: 32 additions & 1 deletion core/blockchain.go
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@ import (
"github.com/scroll-tech/go-ethereum/common/mclock"
"github.com/scroll-tech/go-ethereum/common/prque"
"github.com/scroll-tech/go-ethereum/consensus"
"github.com/scroll-tech/go-ethereum/consensus/misc"
"github.com/scroll-tech/go-ethereum/core/rawdb"
"github.com/scroll-tech/go-ethereum/core/state"
"github.com/scroll-tech/go-ethereum/core/state/snapshot"
Expand All @@ -45,6 +46,7 @@ import (
"github.com/scroll-tech/go-ethereum/log"
"github.com/scroll-tech/go-ethereum/metrics"
"github.com/scroll-tech/go-ethereum/params"
"github.com/scroll-tech/go-ethereum/rollup/rcfg"
"github.com/scroll-tech/go-ethereum/trie"
)

Expand All @@ -55,7 +57,8 @@ var (
headTimeGapGauge = metrics.NewRegisteredGauge("chain/head/timegap", nil)
headL1MessageGauge = metrics.NewRegisteredGauge("chain/head/l1msg", nil)

l2BaseFeeGauge = metrics.NewRegisteredGauge("chain/fees/l2basefee", nil)
l2BaseFeeGauge = metrics.NewRegisteredGauge("chain/fees/l2basefee", nil)
l2BaseFeeUpdateTimer = metrics.NewRegisteredTimer("chain/fees/updates", nil)

accountReadTimer = metrics.NewRegisteredTimer("chain/account/reads", nil)
accountHashTimer = metrics.NewRegisteredTimer("chain/account/hashes", nil)
Expand Down Expand Up @@ -1269,6 +1272,34 @@ func (bc *BlockChain) writeBlockWithState(block *types.Block, receipts []*types.
l2BaseFeeGauge.Update(0)
}

// Update L2 base fee coefficients.
// Coefficient updates are written into L2 state and emit an event.
// We could use either here; we read from the event to avoid state reads.
// In the future, if the base fee setting becomes part of block validation,
// reading from state will be more appropriate.
l2SystemConfigAddress := bc.Config().Scroll.L2SystemConfigAddress()
start := time.Now()

for _, r := range logs {
if r.Address != l2SystemConfigAddress {
continue
}
switch r.Topics[0] {
case rcfg.BaseFeeOverheadUpdatedTopic:
old := r.Topics[1].Big()
new := r.Topics[2].Big()
misc.UpdateL2BaseFeeOverhead(new)
log.Info("Updated L2 base fee overhead", "blockNumber", block.NumberU64(), "blockHash", block.Hash().Hex(), "old", old, "new", new)
case rcfg.BaseFeeScalarUpdatedTopic:
old := r.Topics[1].Big()
new := r.Topics[2].Big()
misc.UpdateL2BaseFeeScalar(new)
log.Info("Updated L2 base fee scalar", "blockNumber", block.NumberU64(), "blockHash", block.Hash().Hex(), "old", old, "new", new)
}
}

l2BaseFeeUpdateTimer.Update(time.Since(start))

// Note the latest relayed L1 message queue index (if any)
updateHeadL1msgGauge(block)

Expand Down
4 changes: 2 additions & 2 deletions core/state_processor_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -389,13 +389,13 @@ func TestStateProcessorErrors(t *testing.T) {
txs: []*types.Transaction{
mkDynamicCreationTx(0, 500000, common.Big0, misc.CalcBaseFee(config, genesis.Header(), parentL1BaseFee), tooBigInitCode[:]),
},
want: "could not apply tx 0 [0x9fff9d187a68f9dce9664475ed9a01a5178992f15b44ce88ee7b1129a183e6af]: max initcode size exceeded: code size 49153 limit 49152",
want: "could not apply tx 0 [0x7b33776d375660694a23ef992c090265682f3687607e0099b14503fdb65d73e3]: max initcode size exceeded: code size 49153 limit 49152",
},
{ // ErrIntrinsicGas: Not enough gas to cover init code
txs: []*types.Transaction{
mkDynamicCreationTx(0, 54299, common.Big0, misc.CalcBaseFee(config, genesis.Header(), parentL1BaseFee), smallInitCode[:]),
},
want: "could not apply tx 0 [0x272eefb0eeb3b973e933ae5dba17e7ecf6bfded5ce358f2a78426153c247f677]: intrinsic gas too low: have 54299, want 54300",
want: "could not apply tx 0 [0x98e54c5ecfa7986a66480d65ba32f2c6a2a6aedc3a67abb91b1e118b0717ed2d]: intrinsic gas too low: have 54299, want 54300",
},
} {
block := GenerateBadBlock(genesis, ethash.NewFaker(), tt.txs, gspec.Config)
Expand Down
24 changes: 17 additions & 7 deletions eth/backend.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ import (
"github.com/scroll-tech/go-ethereum/common/hexutil"
"github.com/scroll-tech/go-ethereum/consensus"
"github.com/scroll-tech/go-ethereum/consensus/clique"
"github.com/scroll-tech/go-ethereum/consensus/misc"
"github.com/scroll-tech/go-ethereum/consensus/system_contract"
"github.com/scroll-tech/go-ethereum/consensus/wrapper"
"github.com/scroll-tech/go-ethereum/core"
Expand Down Expand Up @@ -60,6 +61,7 @@ import (
"github.com/scroll-tech/go-ethereum/rollup/ccc"
"github.com/scroll-tech/go-ethereum/rollup/da_syncer"
"github.com/scroll-tech/go-ethereum/rollup/l1"
"github.com/scroll-tech/go-ethereum/rollup/rcfg"
"github.com/scroll-tech/go-ethereum/rollup/rollup_sync_service"
"github.com/scroll-tech/go-ethereum/rollup/sync_service"
"github.com/scroll-tech/go-ethereum/rpc"
Expand Down Expand Up @@ -148,13 +150,6 @@ func New(stack *node.Node, config *ethconfig.Config, l1Client l1.Client) (*Ether
if _, ok := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !ok {
return nil, genesisErr
}

// Hacky workaround:
// It's hard to pass these fields to `CalcBaseFee`, etc.
// So pass them as part of the genesis config instead.
chainConfig.Scroll.BaseFeeScalar = config.BaseFeeScalar
chainConfig.Scroll.BaseFeeOverhead = config.BaseFeeOverhead

log.Info("Initialised chain configuration", "config", chainConfig)

if err := pruner.RecoverPruning(stack.ResolvePath(""), chainDb, stack.ResolvePath(config.TrieCleanCacheJournal)); err != nil {
Expand Down Expand Up @@ -220,6 +215,21 @@ func New(stack *node.Node, config *ethconfig.Config, l1Client l1.Client) (*Ether
eth.blockchain.Validator().WithAsyncValidator(eth.asyncChecker.Check)
}

// initialize L2 base fee coefficients
state, err := eth.blockchain.State()
if err != nil {
return nil, err
}
if l2SystemConfig := chainConfig.Scroll.L2SystemConfigAddress(); l2SystemConfig != (common.Address{}) {
l2BaseFeeOverhead := state.GetState(chainConfig.Scroll.L2SystemConfigAddress(), rcfg.L2BaseFeeOverheadSlot).Big()
l2BaseFeeScalar := state.GetState(chainConfig.Scroll.L2SystemConfigAddress(), rcfg.L2BaseFeeScalarSlot).Big()
misc.UpdateL2BaseFeeOverhead(l2BaseFeeOverhead)
misc.UpdateL2BaseFeeScalar(l2BaseFeeScalar)
log.Info("Initialized L2 base fee coefficients", "overhead", l2BaseFeeOverhead, "scalar", l2BaseFeeScalar)
} else {
log.Warn("L2SystemConfig address is not configured")
}

// Rewind the chain in case of an incompatible config upgrade.
if compat, ok := genesisErr.(*params.ConfigCompatError); ok {
log.Warn("Rewinding chain to upgrade configuration", "err", compat)
Expand Down
4 changes: 0 additions & 4 deletions eth/ethconfig/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -230,10 +230,6 @@ type Config struct {

// DA syncer options
DA da_syncer.Config

// L2 base fee coefficients for the formula: `l2BaseFee = (l1BaseFee * scalar) / PRECISION + overhead`.
BaseFeeScalar *big.Int
BaseFeeOverhead *big.Int
}

// CreateConsensusEngine creates a consensus engine for the given chain configuration.
Expand Down
Loading
Loading