Skip to content
Merged
Show file tree
Hide file tree
Changes from all 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
57 changes: 43 additions & 14 deletions arbitrum/apibackend.go
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ func (a *APIBackend) FeeHistory(
rewardPercentiles []float64,
) (*big.Int, [][]*big.Int, []*big.Int, []float64, error) {

if core.GetArbOSComputeRate == nil {
if core.GetArbOSSpeedLimitPerSecond == nil {
return nil, nil, nil, nil, errors.New("ArbOS not installed")
}

Expand Down Expand Up @@ -128,41 +128,70 @@ func (a *APIBackend) FeeHistory(
rewards = nil
}

gasUsed := make([]float64, blocks)
basefees := make([]*big.Int, blocks+1) // the RPC semantics are to predict the future value

// use the most recent average compute rate for all blocks
// note: while we could query this value for each block, it'd be prohibitively expensive
state, _, err := a.StateAndHeaderByNumber(ctx, rpc.BlockNumber(newestBlock))
if err != nil {
return common.Big0, nil, nil, nil, err
}
computeRate, err := core.GetArbOSComputeRate(state)
speedLimit, err := core.GetArbOSSpeedLimitPerSecond(state)
if err != nil {
return common.Big0, nil, nil, nil, err
}

// In vanilla geth, this RPC returns the gasUsed ratio so a client can infer how the basefee will change
// To emulate this, we translate the compute rate into something like that, centered at an analogous 0.5
fullnessAnalogue := computeRate / 2
if fullnessAnalogue > 1.0 {
fullnessAnalogue = 1.0
}
for i := range gasUsed {
gasUsed[i] = fullnessAnalogue
}
gasUsed := make([]float64, blocks)
basefees := make([]*big.Int, blocks+1) // the RPC semantics are to predict the future value

// collect the basefees
baseFeeLookup := newestBlock + 1
if newestBlock == latestBlock {
baseFeeLookup = newestBlock
}
var prevTimestamp uint64
var timeSinceLastTimeChange uint64
var currentTimestampGasUsed uint64
if rpc.BlockNumber(oldestBlock) > nitroGenesis {
header, err := a.HeaderByNumber(ctx, rpc.BlockNumber(oldestBlock-1))
if err != nil {
return common.Big0, nil, nil, nil, err
}
prevTimestamp = header.Time
}
for block := oldestBlock; block <= int(baseFeeLookup); block++ {
header, err := a.HeaderByNumber(ctx, rpc.BlockNumber(block))
if err != nil {
return common.Big0, nil, nil, nil, err
}
basefees[block-oldestBlock] = header.BaseFee

if header.Time > prevTimestamp {
timeSinceLastTimeChange = header.Time - prevTimestamp
currentTimestampGasUsed = 0
}

receipts := a.blockChain().GetReceiptsByHash(header.ReceiptHash)
for _, receipt := range receipts {
if receipt.GasUsed > receipt.GasUsedForL1 {
currentTimestampGasUsed += receipt.GasUsed - receipt.GasUsedForL1
}
}

prevTimestamp = header.Time

// In vanilla geth, this RPC returns the gasUsed ratio so a client can infer how the basefee will change
// To emulate this, we translate the compute rate into something like that, centered at an analogous 0.5
var fullnessAnalogue float64
if timeSinceLastTimeChange > 0 {
fullnessAnalogue = float64(currentTimestampGasUsed) / float64(speedLimit) / float64(timeSinceLastTimeChange) / 2.0
if fullnessAnalogue > 1.0 {
fullnessAnalogue = 1.0
}
} else {
// We haven't looked far enough back to know the last timestamp change, so treat this block as full.
fullnessAnalogue = 1.0
}
gasUsed[block-oldestBlock] = fullnessAnalogue

}
if newestBlock == latestBlock {
basefees[blocks] = basefees[blocks-1] // guess the basefee won't change
Expand Down
4 changes: 2 additions & 2 deletions core/arbitrum_hooks.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,8 @@ var InterceptRPCMessage func(
backend NodeInterfaceBackendAPI,
) (types.Message, *ExecutionResult, error)

// Gets ArbOS's approximation of how quickly compute gas is being burnt relative to the speed limit.
var GetArbOSComputeRate func(statedb *state.StateDB) (float64, error)
// Gets ArbOS's maximum intended gas per second
var GetArbOSSpeedLimitPerSecond func(statedb *state.StateDB) (uint64, error)

// Allows ArbOS to update the gas cap so that it ignores the message's specific L1 poster costs.
var InterceptRPCGasCap func(gascap *uint64, msg types.Message, header *types.Header, statedb *state.StateDB)
Expand Down
20 changes: 10 additions & 10 deletions params/config_arbitrum.go
Original file line number Diff line number Diff line change
Expand Up @@ -72,13 +72,13 @@ func ArbitrumOneParams() ArbitrumChainParams {
}
}

func ArbitrumTestnetParams() ArbitrumChainParams {
func ArbitrumDevnetParams() ArbitrumChainParams {
return ArbitrumChainParams{
EnableArbOS: true,
AllowDebugPrecompiles: false,
DataAvailabilityCommittee: false,
InitialArbOSVersion: 1,
InitialChainOwner: common.Address{}, // TODO
InitialChainOwner: common.HexToAddress("0x186B56023d42B2B4E7616589a5C62EEf5FCa21DD"),
}
}

Expand All @@ -87,7 +87,7 @@ func ArbitrumDevTestParams() ArbitrumChainParams {
EnableArbOS: true,
AllowDebugPrecompiles: true,
DataAvailabilityCommittee: false,
InitialArbOSVersion: 4,
InitialArbOSVersion: 1,
InitialChainOwner: common.Address{},
}
}
Expand All @@ -97,7 +97,7 @@ func ArbitrumDevTestDASParams() ArbitrumChainParams {
EnableArbOS: true,
AllowDebugPrecompiles: true,
DataAvailabilityCommittee: true,
InitialArbOSVersion: 4,
InitialArbOSVersion: 1,
InitialChainOwner: common.Address{},
}
}
Expand All @@ -107,7 +107,7 @@ func ArbitrumDevnetDASParams() ArbitrumChainParams {
EnableArbOS: true,
AllowDebugPrecompiles: false,
DataAvailabilityCommittee: true,
InitialArbOSVersion: 3,
InitialArbOSVersion: 1,
InitialChainOwner: common.HexToAddress("0x186B56023d42B2B4E7616589a5C62EEf5FCa21DD"),
}
}
Expand Down Expand Up @@ -147,9 +147,9 @@ func ArbitrumOneChainConfig() *ChainConfig {
}
}

func ArbitrumTestnetChainConfig() *ChainConfig {
func ArbitrumDevnetChainConfig() *ChainConfig {
return &ChainConfig{
ChainID: big.NewInt(421612),
ChainID: big.NewInt(421613),
HomesteadBlock: big.NewInt(0),
DAOForkBlock: nil,
DAOForkSupport: true,
Expand All @@ -164,7 +164,7 @@ func ArbitrumTestnetChainConfig() *ChainConfig {
MuirGlacierBlock: big.NewInt(0),
BerlinBlock: big.NewInt(0),
LondonBlock: big.NewInt(0),
ArbitrumChainParams: ArbitrumTestnetParams(),
ArbitrumChainParams: ArbitrumDevnetParams(),
Clique: &CliqueConfig{
Period: 0,
Epoch: 0,
Expand Down Expand Up @@ -224,7 +224,7 @@ func ArbitrumDevTestDASChainConfig() *ChainConfig {

func ArbitrumDevnetDASChainConfig() *ChainConfig {
return &ChainConfig{
ChainID: big.NewInt(421702),
ChainID: big.NewInt(421703),
HomesteadBlock: big.NewInt(0),
DAOForkBlock: nil,
DAOForkSupport: true,
Expand All @@ -249,7 +249,7 @@ func ArbitrumDevnetDASChainConfig() *ChainConfig {

var ArbitrumSupportedChainConfigs = []*ChainConfig{
ArbitrumOneChainConfig(),
ArbitrumTestnetChainConfig(),
ArbitrumDevnetChainConfig(),
ArbitrumDevTestChainConfig(),
ArbitrumDevTestDASChainConfig(),
ArbitrumDevnetDASChainConfig(),
Expand Down