Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
57 commits
Select commit Hold shift + click to select a range
d21b735
add draft of debug block
magicxyyz Sep 24, 2025
55880e4
Merge branch 'master' into debug-block
magicxyyz Sep 25, 2025
dc79489
set chain config in debug block
magicxyyz Sep 25, 2025
0fa4d20
cleanup sequencer config
magicxyyz Sep 25, 2025
94f58b2
open arbosstate for writing chain config in debug block
magicxyyz Sep 25, 2025
b7583c5
use chainConfig.ArbitrumChainParams.DebugAddress in debug block
magicxyyz Sep 26, 2025
9664d99
update geth pin
magicxyyz Sep 29, 2025
28a48ba
Merge branch 'master' into debug-block
magicxyyz Sep 29, 2025
0089af3
use build tag to guard debug block injection
magicxyyz Sep 30, 2025
f591e5a
add dangerous config for debugblock, guard impl with build tag
magicxyyz Oct 1, 2025
b6deb16
publish debug tx to trigger next block
magicxyyz Oct 2, 2025
8f96031
update geth pin
magicxyyz Oct 2, 2025
f0d4fd9
Merge branch 'master' into debug-block
magicxyyz Oct 2, 2025
45039a6
fix returning error from stubbed debugblock.ConfigAddOptions
magicxyyz Oct 2, 2025
c55d177
use hardcoded account to trigger debug block
magicxyyz Oct 3, 2025
0e1dd84
add system test for debug block injection
magicxyyz Oct 3, 2025
4352417
expand trigger account comment
magicxyyz Oct 3, 2025
01a3e3c
test that debug block injection doesn't affect prod build
magicxyyz Oct 3, 2025
7c10a57
rename debug block test file
magicxyyz Oct 3, 2025
e737880
fix challenge test build
magicxyyz Oct 6, 2025
967954d
update geth pin
magicxyyz Oct 6, 2025
efdc491
Merge branch 'master' into debug-block
magicxyyz Oct 6, 2025
f1434ef
Merge branch 'master' into debug-block
magicxyyz Oct 7, 2025
3fcbad7
add experimental tooling tests to ci workflow
magicxyyz Oct 7, 2025
6d32415
execute only TestExperimental tests in experimental ci step
magicxyyz Oct 7, 2025
6a4986c
add nitro-node-experimental to Dockerfile
magicxyyz Oct 7, 2025
2668155
Merge branch 'master' into debug-block
magicxyyz Oct 7, 2025
a989d74
copy debugblock package into wasm-bin-builder
magicxyyz Oct 7, 2025
4e34dce
Merge branch 'master' into debug-block
magicxyyz Oct 7, 2025
229410c
Merge branch 'master' into debug-block
magicxyyz Oct 8, 2025
009dbb1
use DebugAddress as pointer
magicxyyz Oct 9, 2025
1d954f8
update geth pin
magicxyyz Oct 9, 2025
1979462
add BenchSequencer
magicxyyz Oct 9, 2025
373946d
add missing newline
magicxyyz Oct 10, 2025
d7d885a
Merge branch 'master' into debug-block
magicxyyz Oct 10, 2025
1dbc550
add bench sequencer system tests
magicxyyz Oct 10, 2025
e53f1a4
Merge branch 'debug-block' into bench-sequencer
magicxyyz Oct 10, 2025
1c6308a
remove unnecessery BenchSequencer.StopAndWait
magicxyyz Oct 13, 2025
ae315ef
remove unused config param from NewBenchSequencer
magicxyyz Oct 22, 2025
547bad7
update geth pin
magicxyyz Oct 22, 2025
15200f6
Merge branch 'master' into debug-block
magicxyyz Nov 5, 2025
64466d8
update geth pin
magicxyyz Nov 5, 2025
faf8fc6
Merge branch 'master' into debug-block
magicxyyz Nov 5, 2025
d46410c
fix debug block test param
magicxyyz Nov 5, 2025
c7ff5df
fix missing chain config overwrite in common_test
magicxyyz Nov 5, 2025
0dcd27f
Merge branch 'debug-block' into bench-sequencer
magicxyyz Nov 5, 2025
fca5848
apply lint format
magicxyyz Nov 5, 2025
e8ddbe5
update debug block tx warning message
magicxyyz Nov 5, 2025
c9a6fa5
add missing copyright comments
magicxyyz Nov 5, 2025
3516227
fix challange test build
magicxyyz Nov 5, 2025
0333e8a
Merge branch 'debug-block' into bench-sequencer
magicxyyz Nov 6, 2025
341aca2
add benchseq rpc returning retry queue length
magicxyyz Nov 7, 2025
67f607a
Merge pull request #3806 from OffchainLabs/bench-sequencer
joshuacolvin0 Nov 7, 2025
ec34f2e
update geth pin
magicxyyz Nov 10, 2025
c2f5f47
Merge branch 'master' into debug-block
magicxyyz Nov 10, 2025
1bf903c
improve debug block accounts prefunding
magicxyyz Nov 11, 2025
6a011ef
fix debug block prefund
magicxyyz Nov 11, 2025
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
11 changes: 9 additions & 2 deletions .github/workflows/_go-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ jobs:
strategy:
fail-fast: false
matrix:
test-mode: [defaults-A, defaults-B, flaky, pathdb, challenge, stylus, l3challenge]
test-mode: [defaults-A, defaults-B, flaky, pathdb, challenge, stylus, l3challenge, experimental]
services:
redis:
image: redis
Expand Down Expand Up @@ -147,14 +147,21 @@ jobs:
${{ github.workspace }}/.github/workflows/gotestsum.sh
--tags challengetest --run TestL3Challenge --timeout 120m --cover

# --------------------- CHALLENGE MODES ---------------------
# --------------------- STYLUS MODE --------------------------

- name: run stylus tests
if: matrix.test-mode == 'stylus'
run: >-
${{ github.workspace }}/.github/workflows/gotestsum.sh
--tags stylustest --run TestProgramArbitrator --timeout 60m --cover

# --------------------- EXPERIMENTAL MODE --------------------
- name: run experimental tooling tests
if: matrix.test-mode == 'experimental'
run: >-
${{ github.workspace }}/.github/workflows/gotestsum.sh
--tags debugblock --run TestExperimental --timeout 60m --cover

# --------------------- ARCHIVE LOGS FOR ALL MODES ---------------------

- name: Archive detailed run log
Expand Down
7 changes: 7 additions & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ COPY ./contracts/package.json ./contracts/yarn.lock ./contracts/
COPY ./safe-smart-account ./safe-smart-account
COPY ./solgen/gen.go ./solgen/
COPY ./go-ethereum ./go-ethereum
COPY ./experimental/debugblock ./experimental/debugblock
COPY scripts/remove_reference_types.sh scripts/
COPY --from=brotli-wasm-export / target/
COPY --from=contracts-builder workspace/contracts-local/out/precompiles/ contracts-local/out/precompiles/
Expand Down Expand Up @@ -390,5 +391,11 @@ RUN export DEBIAN_FRONTEND=noninteractive && \

USER user

FROM nitro-node AS nitro-node-experimental
USER root
COPY --from=node-builder /workspace/target/bin/nitro-experimental /usr/local/bin/
ENTRYPOINT [ "/usr/local/bin/nitro-experimental" , "--validation.wasm.allowed-wasm-module-roots", "/home/user/nitro-legacy/machines,/home/user/target/machines"]
USER user

FROM nitro-node AS nitro-node-default
# Just to ensure nitro-node-dist is default
11 changes: 10 additions & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -165,7 +165,7 @@ all: build build-replay-env test-gen-proofs
@touch .make/all

.PHONY: build
build: $(patsubst %,$(output_root)/bin/%, nitro deploy relay daprovider daserver autonomous-auctioneer bidder-client datool blobtool el-proxy mockexternalsigner seq-coordinator-invalidate nitro-val seq-coordinator-manager dbconv genesis-generator)
build: $(patsubst %,$(output_root)/bin/%, nitro deploy relay daprovider daserver autonomous-auctioneer bidder-client datool blobtool el-proxy mockexternalsigner seq-coordinator-invalidate nitro-val seq-coordinator-manager dbconv genesis-generator nitro-experimental)
@printf $(done)

.PHONY: build-node-deps
Expand Down Expand Up @@ -244,6 +244,11 @@ test-go-gas-dimensions: test-go-deps
.github/workflows/gotestsum.sh --timeout 120m --run "TestDim(Log|TxOp)" --tags gasdimensionstest --nolog
@printf $(done)

.PHONY: test-go-experimental
test-go-experimental: test-go-deps
.github/workflows/gotestsum.sh --timeout 120m --run TestExperimental --tags debugblock,benchsequencer --nolog
@printf $(done)

.PHONY: test-gen-proofs
test-gen-proofs: \
$(arbitrator_test_wasms) \
Expand Down Expand Up @@ -351,6 +356,10 @@ $(output_root)/bin/seq-coordinator-manager: $(DEP_PREDICATE) build-node-deps
$(output_root)/bin/dbconv: $(DEP_PREDICATE) build-node-deps
go build $(GOLANG_PARAMS) -o $@ "$(CURDIR)/cmd/dbconv"

# nitro built with experimental tooling enabled
$(output_root)/bin/nitro-experimental: $(DEP_PREDICATE) build-node-deps
go build $(GOLANG_PARAMS) --tags debugblock,benchsequencer -o $@ "$(CURDIR)/cmd/nitro"

# recompile wasm, but don't change timestamp unless files differ
$(replay_wasm): $(DEP_PREDICATE) $(go_source) .make/solgen
mkdir -p `dirname $(replay_wasm)`
Expand Down
5 changes: 5 additions & 0 deletions arbos/block_processor.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import (
"github.com/offchainlabs/nitro/arbos/arbostypes"
"github.com/offchainlabs/nitro/arbos/l2pricing"
"github.com/offchainlabs/nitro/arbos/util"
"github.com/offchainlabs/nitro/experimental/debugblock"
"github.com/offchainlabs/nitro/util/arbmath"
)

Expand Down Expand Up @@ -241,6 +242,10 @@ func ProduceBlockAdvanced(

firstTx := types.NewTx(startTx)

if chainConfig.DebugMode() && header.Number.Uint64() == chainConfig.ArbitrumChainParams.DebugBlock {
debugblock.DebugBlockStateUpdate(statedb, expectedBalanceDelta, chainConfig)
}

for {
// repeatedly process the next tx, doing redeems created along the way in FIFO order

Expand Down
3 changes: 3 additions & 0 deletions cmd/nitro/init.go
Original file line number Diff line number Diff line change
Expand Up @@ -621,6 +621,9 @@ func openInitializeChainDb(ctx context.Context, stack *node.Node, config *NodeCo
if err := dbutil.UnfinishedConversionCheck(chainData); err != nil {
return nil, nil, fmt.Errorf("l2chaindata unfinished database conversion check error: %w", err)
}
if config.Execution.Dangerous.DebugBlock.OverwriteChainConfig {
config.Execution.Dangerous.DebugBlock.Apply(chainConfig)
}
wasmDb, err := stack.OpenDatabaseWithOptions("wasm", node.DatabaseOptions{Cache: config.Execution.Caching.DatabaseCache, Handles: config.Persistent.Handles, MetricsNamespace: "wasm/", PebbleExtraOptions: persistentConfig.Pebble.ExtraOptions("wasm"), NoFreezer: true})
if err != nil {
return nil, nil, err
Expand Down
2 changes: 1 addition & 1 deletion cmd/util/confighelpers/configuration.go
Original file line number Diff line number Diff line change
Expand Up @@ -209,7 +209,7 @@ func devFlagArgs() []string {
"--init.empty=false",
"--http.port", "8547",
"--http.addr", "127.0.0.1",
"--http.api=net,web3,eth,arb,arbdebug,debug",
"--http.api=net,web3,eth,arb,arbdebug,debug,benchseq",
"--node.transaction-streamer.track-block-metadata-from=1",
}
return args
Expand Down
90 changes: 90 additions & 0 deletions execution/gethexec/bench_sequencer.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
//go:build benchsequencer

package gethexec

import (
"context"

"github.com/ethereum/go-ethereum/log"
"github.com/offchainlabs/nitro/util/containers"
"github.com/offchainlabs/nitro/util/stopwaiter"
"github.com/spf13/pflag"
)

func BenchSequencerConfigAddOptions(prefix string, f *pflag.FlagSet) {
f.Bool(prefix+".enable", BenchSequencerConfigDefault.Enable, "enables transaction indexer")
}

func (c *BenchSequencerConfig) Validate() error {
if c.Enable {
log.Warn("DANGER! BenchSequencer enabled")
}
return nil
}

func NewBenchSequencer(sequencer *Sequencer) (TransactionPublisher, interface{}) {
benchSequencer := &BenchSequencer{
Sequencer: sequencer,
semaphore: make(chan struct{}, 1),
}
return benchSequencer, NewBenchSequencerAPI(benchSequencer)
}

type BenchSequencer struct {
*Sequencer
semaphore chan struct{}
}

func (s *BenchSequencer) Start(ctx context.Context) error {
// override Sequencer.Start to not start the inner sequencer
s.StopWaiter.Start(ctx, s)
s.semaphore <- struct{}{}
return nil
}

func (s *BenchSequencer) TxQueueLength(includeRetryTxQueue bool) int {
if includeRetryTxQueue {
return len(s.Sequencer.txQueue) + s.Sequencer.txRetryQueue.Len()
}
return len(s.Sequencer.txQueue)
}

func (s *BenchSequencer) TxRetryQueueLength() int {
return s.Sequencer.txRetryQueue.Len()
}

func (s *BenchSequencer) CreateBlock() containers.PromiseInterface[bool] {
return stopwaiter.LaunchPromiseThread[bool](s, func(ctx context.Context) (bool, error) {
select {
// createBlock can't be run in parallel
case <-s.semaphore:
defer func() {
// release semaphore, also in case of panic
s.semaphore <- struct{}{}
}()
return s.createBlock(ctx), nil
case <-ctx.Done():
return false, ctx.Err()
}
})
}

type BenchSequencerAPI struct {
benchSequencer *BenchSequencer
}

func (a *BenchSequencerAPI) TxQueueLength(includeRetryTxQueue bool) int {
return a.benchSequencer.TxQueueLength(includeRetryTxQueue)
}

func (a *BenchSequencerAPI) TxRetryQueueLength() int {
return a.benchSequencer.TxRetryQueueLength()
}

func (a *BenchSequencerAPI) CreateBlock(ctx context.Context) (bool, error) {
return a.benchSequencer.CreateBlock().Await(ctx)
}

func NewBenchSequencerAPI(benchSequencer *BenchSequencer) *BenchSequencerAPI {
return &BenchSequencerAPI{benchSequencer: benchSequencer}
}
12 changes: 12 additions & 0 deletions execution/gethexec/bench_sequencer_config.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// DANGER! this file is included in all builds
// DANGER! do not place any of the experimental logic and features here

package gethexec

type BenchSequencerConfig struct {
Enable bool `koanf:"enable"`
}

var BenchSequencerConfigDefault = BenchSequencerConfig{
Enable: false,
}
25 changes: 25 additions & 0 deletions execution/gethexec/bench_sequencer_stub.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
//go:build !benchsequencer

package gethexec

import (
"github.com/spf13/pflag"

"github.com/ethereum/go-ethereum/log"
)

func BenchSequencerConfigAddOptions(_ string, _ *pflag.FlagSet) {
// don't add any options
}

func (c *BenchSequencerConfig) Validate() error {
if c.Enable {
log.Warn("BenchSequencer is not supported in this build")
}
return nil
}

func NewBenchSequencer(sequencer *Sequencer) (TransactionPublisher, interface{}) {
// do nothing
return sequencer, nil
}
42 changes: 42 additions & 0 deletions execution/gethexec/node.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ import (
"github.com/offchainlabs/nitro/arbos/programs"
"github.com/offchainlabs/nitro/arbutil"
"github.com/offchainlabs/nitro/execution"
"github.com/offchainlabs/nitro/experimental/debugblock"
"github.com/offchainlabs/nitro/solgen/go/precompilesgen"
"github.com/offchainlabs/nitro/util"
"github.com/offchainlabs/nitro/util/arbmath"
Expand Down Expand Up @@ -127,6 +128,7 @@ type Config struct {
BlockMetadataApiBlocksLimit uint64 `koanf:"block-metadata-api-blocks-limit"`
VmTrace LiveTracingConfig `koanf:"vmtrace"`
ExposeMultiGas bool `koanf:"expose-multi-gas"`
Dangerous DangerousConfig `koanf:"dangerous"`

forwardingTarget string
}
Expand Down Expand Up @@ -155,6 +157,9 @@ func (c *Config) Validate() error {
if err := c.RPC.Validate(); err != nil {
return err
}
if err := c.Dangerous.Validate(); err != nil {
return err
}
return nil
}

Expand All @@ -176,6 +181,7 @@ func ConfigAddOptions(prefix string, f *pflag.FlagSet) {
f.Uint64(prefix+".block-metadata-api-blocks-limit", ConfigDefault.BlockMetadataApiBlocksLimit, "maximum number of blocks allowed to be queried for blockMetadata per arb_getRawBlockMetadata query. Enabled by default, set 0 to disable the limit")
f.Bool(prefix+".expose-multi-gas", false, "experimental: expose multi-dimensional gas in transaction receipts")
LiveTracingConfigAddOptions(prefix+".vmtrace", f)
DangerousConfigAddOptions(prefix+".dangerous", f)
}

type LiveTracingConfig struct {
Expand All @@ -193,6 +199,31 @@ func LiveTracingConfigAddOptions(prefix string, f *pflag.FlagSet) {
f.String(prefix+".json-config", DefaultLiveTracingConfig.JSONConfig, "(experimental) Tracer configuration in JSON format")
}

type DangerousConfig struct {
DebugBlock debugblock.Config `koanf:"debug-block"`
BenchSequencer BenchSequencerConfig `koanf:"bench-sequencer"`
}

var DefaultDangerousConfig = DangerousConfig{
DebugBlock: debugblock.ConfigDefault,
BenchSequencer: BenchSequencerConfigDefault,
}

func DangerousConfigAddOptions(prefix string, f *pflag.FlagSet) {
debugblock.ConfigAddOptions(prefix+".debug-block", f)
BenchSequencerConfigAddOptions(prefix+".bench-sequencer", f)
}

func (c *DangerousConfig) Validate() error {
if err := c.DebugBlock.Validate(); err != nil {
return err
}
if err := c.BenchSequencer.Validate(); err != nil {
return err
}
return nil
}

var ConfigDefault = Config{
RPC: arbitrum.DefaultConfig,
TxIndexer: DefaultTxIndexerConfig,
Expand Down Expand Up @@ -273,13 +304,17 @@ func CreateExecutionNode(
log.Warn("sequencer enabled without l1 client")
}

var benchSequencerService interface{}
if config.Sequencer.Enable {
seqConfigFetcher := func() *SequencerConfig { return &configFetcher.Get().Sequencer }
sequencer, err = NewSequencer(execEngine, parentChainReader, seqConfigFetcher, parentChainID)
if err != nil {
return nil, err
}
txPublisher = sequencer
if config.Dangerous.BenchSequencer.Enable {
txPublisher, benchSequencerService = NewBenchSequencer(sequencer)
}
} else {
if config.Forwarder.RedisUrl != "" {
txPublisher = NewRedisTxForwarder(config.forwardingTarget, &config.Forwarder)
Expand Down Expand Up @@ -373,6 +408,13 @@ func CreateExecutionNode(
Service: eth.NewDebugAPI(eth.NewArbEthereum(l2BlockChain, chainDB)),
Public: false,
})
if benchSequencerService != nil {
apis = append(apis, rpc.API{
Namespace: "benchseq",
Service: benchSequencerService,
Public: false,
})
}

stack.RegisterAPIs(apis)

Expand Down
Loading