2015-07-06 19:54:22 -05:00
|
|
|
// Copyright 2014 The go-ethereum Authors
|
|
|
|
// This file is part of go-ethereum.
|
|
|
|
//
|
|
|
|
// go-ethereum is free software: you can redistribute it and/or modify
|
|
|
|
// it under the terms of the GNU General Public License as published by
|
|
|
|
// the Free Software Foundation, either version 3 of the License, or
|
|
|
|
// (at your option) any later version.
|
|
|
|
//
|
|
|
|
// go-ethereum is distributed in the hope that it will be useful,
|
|
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
2015-07-22 11:48:40 -05:00
|
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
2015-07-06 19:54:22 -05:00
|
|
|
// GNU General Public License for more details.
|
|
|
|
//
|
|
|
|
// You should have received a copy of the GNU General Public License
|
2015-07-22 11:48:40 -05:00
|
|
|
// along with go-ethereum. If not, see <http://www.gnu.org/licenses/>.
|
2014-11-10 04:47:37 -06:00
|
|
|
|
2015-07-06 22:08:16 -05:00
|
|
|
// evm executes EVM code snippets.
|
2014-11-10 04:47:37 -06:00
|
|
|
package main
|
|
|
|
|
|
|
|
import (
|
|
|
|
"fmt"
|
2024-12-02 08:18:02 -06:00
|
|
|
"io/fs"
|
2014-11-10 04:47:37 -06:00
|
|
|
"os"
|
2024-12-02 08:18:02 -06:00
|
|
|
"path/filepath"
|
2014-11-10 04:47:37 -06:00
|
|
|
|
2020-06-30 03:12:51 -05:00
|
|
|
"github.com/ethereum/go-ethereum/cmd/evm/internal/t8ntool"
|
2024-12-02 08:18:02 -06:00
|
|
|
"github.com/ethereum/go-ethereum/core/state"
|
|
|
|
"github.com/ethereum/go-ethereum/core/tracing"
|
|
|
|
"github.com/ethereum/go-ethereum/eth/tracers/logger"
|
2023-09-19 06:41:16 -05:00
|
|
|
"github.com/ethereum/go-ethereum/internal/debug"
|
2020-07-14 03:35:32 -05:00
|
|
|
"github.com/ethereum/go-ethereum/internal/flags"
|
2022-06-27 11:22:36 -05:00
|
|
|
"github.com/urfave/cli/v2"
|
2023-12-18 08:16:25 -06:00
|
|
|
|
|
|
|
// Force-load the tracer engines to trigger registration
|
|
|
|
_ "github.com/ethereum/go-ethereum/eth/tracers/js"
|
|
|
|
_ "github.com/ethereum/go-ethereum/eth/tracers/native"
|
2014-11-10 04:47:37 -06:00
|
|
|
)
|
|
|
|
|
2024-12-02 08:18:02 -06:00
|
|
|
// Some other nice-to-haves:
|
|
|
|
// * accumulate traces into an object to bundle with test
|
|
|
|
// * write tx identifier for trace before hand (blocktest only)
|
|
|
|
// * combine blocktest and statetest runner logic using unified test interface
|
|
|
|
|
|
|
|
const traceCategory = "TRACING"
|
|
|
|
|
2022-06-27 11:22:36 -05:00
|
|
|
var (
|
2024-12-02 08:18:02 -06:00
|
|
|
// Test running flags.
|
|
|
|
RunFlag = &cli.StringFlag{
|
|
|
|
Name: "run",
|
|
|
|
Value: ".*",
|
|
|
|
Usage: "Run only those tests matching the regular expression.",
|
2015-08-30 03:19:10 -05:00
|
|
|
}
|
2022-06-27 11:22:36 -05:00
|
|
|
BenchFlag = &cli.BoolFlag{
|
2023-09-19 06:41:16 -05:00
|
|
|
Name: "bench",
|
|
|
|
Usage: "benchmark the execution",
|
|
|
|
Category: flags.VMCategory,
|
2019-12-18 02:43:18 -06:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
WitnessCrossCheckFlag = &cli.BoolFlag{
|
|
|
|
Name: "cross-check",
|
|
|
|
Aliases: []string{"xc"},
|
|
|
|
Usage: "Cross-check stateful execution against stateless, verifying the witness generation.",
|
2016-06-14 09:09:27 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
|
|
|
|
// Debugging flags.
|
|
|
|
DumpFlag = &cli.BoolFlag{
|
|
|
|
Name: "dump",
|
|
|
|
Usage: "dumps the state after the run",
|
2017-06-07 10:09:08 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
HumanReadableFlag = &cli.BoolFlag{
|
|
|
|
Name: "human",
|
|
|
|
Usage: "\"Human-readable\" output",
|
2017-06-07 10:09:08 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
StatDumpFlag = &cli.BoolFlag{
|
|
|
|
Name: "statdump",
|
|
|
|
Usage: "displays stack and heap memory information",
|
2017-06-07 10:09:08 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
|
|
|
|
// Tracing flags.
|
|
|
|
TraceFlag = &cli.BoolFlag{
|
|
|
|
Name: "trace",
|
|
|
|
Usage: "Enable tracing and output trace log.",
|
|
|
|
Category: traceCategory,
|
|
|
|
}
|
|
|
|
TraceFormatFlag = &cli.StringFlag{
|
|
|
|
Name: "trace.format",
|
|
|
|
Usage: "Trace output format to use (struct|json)",
|
|
|
|
Value: "struct",
|
|
|
|
Category: traceCategory,
|
2017-08-15 04:31:36 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
TraceDisableMemoryFlag = &cli.BoolFlag{
|
|
|
|
Name: "trace.nomemory",
|
|
|
|
Aliases: []string{"nomemory"},
|
2023-09-19 06:41:16 -05:00
|
|
|
Value: true,
|
|
|
|
Usage: "disable memory output",
|
2024-12-02 08:18:02 -06:00
|
|
|
Category: traceCategory,
|
2017-06-21 07:52:31 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
TraceDisableStackFlag = &cli.BoolFlag{
|
|
|
|
Name: "trace.nostack",
|
|
|
|
Aliases: []string{"nostack"},
|
2023-09-19 06:41:16 -05:00
|
|
|
Usage: "disable stack output",
|
2024-12-02 08:18:02 -06:00
|
|
|
Category: traceCategory,
|
2017-06-21 07:52:31 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
TraceDisableStorageFlag = &cli.BoolFlag{
|
|
|
|
Name: "trace.nostorage",
|
|
|
|
Aliases: []string{"nostorage"},
|
2023-09-19 06:41:16 -05:00
|
|
|
Usage: "disable storage output",
|
2024-12-02 08:18:02 -06:00
|
|
|
Category: traceCategory,
|
2020-07-16 07:06:19 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
TraceDisableReturnDataFlag = &cli.BoolFlag{
|
|
|
|
Name: "trace.noreturndata",
|
|
|
|
Aliases: []string{"noreturndata"},
|
2023-09-19 06:41:16 -05:00
|
|
|
Value: true,
|
|
|
|
Usage: "enable return data output",
|
2024-12-02 08:18:02 -06:00
|
|
|
Category: traceCategory,
|
2020-07-16 07:06:19 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
|
|
|
|
// Deprecated flags.
|
|
|
|
DebugFlag = &cli.BoolFlag{
|
|
|
|
Name: "debug",
|
|
|
|
Usage: "output full trace logs (deprecated)",
|
|
|
|
Hidden: true,
|
|
|
|
Category: traceCategory,
|
core/vm, cmd/evm: implement eof validation (#30418)
The bulk of this PR is authored by @lightclient , in the original
EOF-work. More recently, the code has been picked up and reworked for the new EOF
specification, by @MariusVanDerWijden , in https://github.com/ethereum/go-ethereum/pull/29518, and also @shemnon has contributed with fixes.
This PR is an attempt to start eating the elephant one small bite at a
time, by selecting only the eof-validation as a standalone piece which
can be merged without interfering too much in the core stuff.
In this PR:
- [x] Validation of eof containers, lifted from #29518, along with
test-vectors from consensus-tests and fuzzing, to ensure that the move
did not lose any functionality.
- [x] Definition of eof opcodes, which is a prerequisite for validation
- [x] Addition of `undefined` to a jumptable entry item. I'm not
super-happy with this, but for the moment it seems the least invasive
way to do it. A better way might be to go back and allowing nil-items or
nil execute-functions to denote "undefined".
- [x] benchmarks of eof validation speed
---------
Co-authored-by: lightclient <lightclient@protonmail.com>
Co-authored-by: Marius van der Wijden <m.vanderwijden@live.de>
Co-authored-by: Danno Ferrin <danno.ferrin@shemnon.com>
2024-10-02 08:05:50 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
MachineFlag = &cli.BoolFlag{
|
|
|
|
Name: "json",
|
|
|
|
Usage: "output trace logs in machine readable format, json (deprecated)",
|
|
|
|
Hidden: true,
|
|
|
|
Category: traceCategory,
|
core/vm, cmd/evm: implement eof validation (#30418)
The bulk of this PR is authored by @lightclient , in the original
EOF-work. More recently, the code has been picked up and reworked for the new EOF
specification, by @MariusVanDerWijden , in https://github.com/ethereum/go-ethereum/pull/29518, and also @shemnon has contributed with fixes.
This PR is an attempt to start eating the elephant one small bite at a
time, by selecting only the eof-validation as a standalone piece which
can be merged without interfering too much in the core stuff.
In this PR:
- [x] Validation of eof containers, lifted from #29518, along with
test-vectors from consensus-tests and fuzzing, to ensure that the move
did not lose any functionality.
- [x] Definition of eof opcodes, which is a prerequisite for validation
- [x] Addition of `undefined` to a jumptable entry item. I'm not
super-happy with this, but for the moment it seems the least invasive
way to do it. A better way might be to go back and allowing nil-items or
nil execute-functions to denote "undefined".
- [x] benchmarks of eof validation speed
---------
Co-authored-by: lightclient <lightclient@protonmail.com>
Co-authored-by: Marius van der Wijden <m.vanderwijden@live.de>
Co-authored-by: Danno Ferrin <danno.ferrin@shemnon.com>
2024-10-02 08:05:50 -05:00
|
|
|
}
|
2014-11-10 04:47:37 -06:00
|
|
|
)
|
|
|
|
|
2024-12-02 08:18:02 -06:00
|
|
|
// Command definitions.
|
core/vm, cmd/evm: implement eof validation (#30418)
The bulk of this PR is authored by @lightclient , in the original
EOF-work. More recently, the code has been picked up and reworked for the new EOF
specification, by @MariusVanDerWijden , in https://github.com/ethereum/go-ethereum/pull/29518, and also @shemnon has contributed with fixes.
This PR is an attempt to start eating the elephant one small bite at a
time, by selecting only the eof-validation as a standalone piece which
can be merged without interfering too much in the core stuff.
In this PR:
- [x] Validation of eof containers, lifted from #29518, along with
test-vectors from consensus-tests and fuzzing, to ensure that the move
did not lose any functionality.
- [x] Definition of eof opcodes, which is a prerequisite for validation
- [x] Addition of `undefined` to a jumptable entry item. I'm not
super-happy with this, but for the moment it seems the least invasive
way to do it. A better way might be to go back and allowing nil-items or
nil execute-functions to denote "undefined".
- [x] benchmarks of eof validation speed
---------
Co-authored-by: lightclient <lightclient@protonmail.com>
Co-authored-by: Marius van der Wijden <m.vanderwijden@live.de>
Co-authored-by: Danno Ferrin <danno.ferrin@shemnon.com>
2024-10-02 08:05:50 -05:00
|
|
|
var (
|
|
|
|
stateTransitionCommand = &cli.Command{
|
|
|
|
Name: "transition",
|
|
|
|
Aliases: []string{"t8n"},
|
|
|
|
Usage: "Executes a full state transition",
|
|
|
|
Action: t8ntool.Transition,
|
|
|
|
Flags: []cli.Flag{
|
|
|
|
t8ntool.TraceFlag,
|
|
|
|
t8ntool.TraceTracerFlag,
|
|
|
|
t8ntool.TraceTracerConfigFlag,
|
|
|
|
t8ntool.TraceEnableMemoryFlag,
|
|
|
|
t8ntool.TraceDisableStackFlag,
|
|
|
|
t8ntool.TraceEnableReturnDataFlag,
|
|
|
|
t8ntool.TraceEnableCallFramesFlag,
|
|
|
|
t8ntool.OutputBasedir,
|
|
|
|
t8ntool.OutputAllocFlag,
|
|
|
|
t8ntool.OutputResultFlag,
|
|
|
|
t8ntool.OutputBodyFlag,
|
|
|
|
t8ntool.InputAllocFlag,
|
|
|
|
t8ntool.InputEnvFlag,
|
|
|
|
t8ntool.InputTxsFlag,
|
|
|
|
t8ntool.ForknameFlag,
|
|
|
|
t8ntool.ChainIDFlag,
|
|
|
|
t8ntool.RewardFlag,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
transactionCommand = &cli.Command{
|
|
|
|
Name: "transaction",
|
|
|
|
Aliases: []string{"t9n"},
|
|
|
|
Usage: "Performs transaction validation",
|
|
|
|
Action: t8ntool.Transaction,
|
|
|
|
Flags: []cli.Flag{
|
|
|
|
t8ntool.InputTxsFlag,
|
|
|
|
t8ntool.ChainIDFlag,
|
|
|
|
t8ntool.ForknameFlag,
|
|
|
|
},
|
|
|
|
}
|
2020-06-30 03:12:51 -05:00
|
|
|
|
core/vm, cmd/evm: implement eof validation (#30418)
The bulk of this PR is authored by @lightclient , in the original
EOF-work. More recently, the code has been picked up and reworked for the new EOF
specification, by @MariusVanDerWijden , in https://github.com/ethereum/go-ethereum/pull/29518, and also @shemnon has contributed with fixes.
This PR is an attempt to start eating the elephant one small bite at a
time, by selecting only the eof-validation as a standalone piece which
can be merged without interfering too much in the core stuff.
In this PR:
- [x] Validation of eof containers, lifted from #29518, along with
test-vectors from consensus-tests and fuzzing, to ensure that the move
did not lose any functionality.
- [x] Definition of eof opcodes, which is a prerequisite for validation
- [x] Addition of `undefined` to a jumptable entry item. I'm not
super-happy with this, but for the moment it seems the least invasive
way to do it. A better way might be to go back and allowing nil-items or
nil execute-functions to denote "undefined".
- [x] benchmarks of eof validation speed
---------
Co-authored-by: lightclient <lightclient@protonmail.com>
Co-authored-by: Marius van der Wijden <m.vanderwijden@live.de>
Co-authored-by: Danno Ferrin <danno.ferrin@shemnon.com>
2024-10-02 08:05:50 -05:00
|
|
|
blockBuilderCommand = &cli.Command{
|
|
|
|
Name: "block-builder",
|
|
|
|
Aliases: []string{"b11r"},
|
|
|
|
Usage: "Builds a block",
|
|
|
|
Action: t8ntool.BuildBlock,
|
|
|
|
Flags: []cli.Flag{
|
|
|
|
t8ntool.OutputBasedir,
|
|
|
|
t8ntool.OutputBlockFlag,
|
|
|
|
t8ntool.InputHeaderFlag,
|
|
|
|
t8ntool.InputOmmersFlag,
|
|
|
|
t8ntool.InputWithdrawalsFlag,
|
|
|
|
t8ntool.InputTxsRlpFlag,
|
|
|
|
t8ntool.SealCliqueFlag,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
)
|
2021-11-22 02:25:35 -06:00
|
|
|
|
2023-09-19 06:41:16 -05:00
|
|
|
// traceFlags contains flags that configure tracing output.
|
|
|
|
var traceFlags = []cli.Flag{
|
2024-12-02 08:18:02 -06:00
|
|
|
TraceFlag,
|
|
|
|
TraceFormatFlag,
|
|
|
|
TraceDisableStackFlag,
|
|
|
|
TraceDisableMemoryFlag,
|
|
|
|
TraceDisableStorageFlag,
|
|
|
|
TraceDisableReturnDataFlag,
|
|
|
|
|
|
|
|
// deprecated
|
2023-09-19 06:41:16 -05:00
|
|
|
DebugFlag,
|
|
|
|
MachineFlag,
|
|
|
|
}
|
|
|
|
|
2022-09-23 07:08:25 -05:00
|
|
|
var app = flags.NewApp("the evm command line interface")
|
|
|
|
|
2015-07-17 08:43:16 -05:00
|
|
|
func init() {
|
2024-12-02 08:18:02 -06:00
|
|
|
app.Flags = debug.Flags
|
2022-06-27 11:22:36 -05:00
|
|
|
app.Commands = []*cli.Command{
|
2017-02-28 18:11:24 -06:00
|
|
|
runCommand,
|
2023-01-27 07:30:13 -06:00
|
|
|
blockTestCommand,
|
2017-09-05 04:24:26 -05:00
|
|
|
stateTestCommand,
|
2020-06-30 03:12:51 -05:00
|
|
|
stateTransitionCommand,
|
2021-09-13 06:57:40 -05:00
|
|
|
transactionCommand,
|
2021-11-22 02:25:35 -06:00
|
|
|
blockBuilderCommand,
|
core/vm, cmd/evm: implement eof validation (#30418)
The bulk of this PR is authored by @lightclient , in the original
EOF-work. More recently, the code has been picked up and reworked for the new EOF
specification, by @MariusVanDerWijden , in https://github.com/ethereum/go-ethereum/pull/29518, and also @shemnon has contributed with fixes.
This PR is an attempt to start eating the elephant one small bite at a
time, by selecting only the eof-validation as a standalone piece which
can be merged without interfering too much in the core stuff.
In this PR:
- [x] Validation of eof containers, lifted from #29518, along with
test-vectors from consensus-tests and fuzzing, to ensure that the move
did not lose any functionality.
- [x] Definition of eof opcodes, which is a prerequisite for validation
- [x] Addition of `undefined` to a jumptable entry item. I'm not
super-happy with this, but for the moment it seems the least invasive
way to do it. A better way might be to go back and allowing nil-items or
nil execute-functions to denote "undefined".
- [x] benchmarks of eof validation speed
---------
Co-authored-by: lightclient <lightclient@protonmail.com>
Co-authored-by: Marius van der Wijden <m.vanderwijden@live.de>
Co-authored-by: Danno Ferrin <danno.ferrin@shemnon.com>
2024-10-02 08:05:50 -05:00
|
|
|
eofParseCommand,
|
|
|
|
eofDumpCommand,
|
2015-07-17 16:09:36 -05:00
|
|
|
}
|
2023-09-19 06:41:16 -05:00
|
|
|
app.Before = func(ctx *cli.Context) error {
|
|
|
|
flags.MigrateGlobalFlags(ctx)
|
|
|
|
return debug.Setup(ctx)
|
|
|
|
}
|
|
|
|
app.After = func(ctx *cli.Context) error {
|
|
|
|
debug.Exit()
|
|
|
|
return nil
|
|
|
|
}
|
2015-07-17 08:43:16 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
func main() {
|
|
|
|
if err := app.Run(os.Args); err != nil {
|
2024-12-02 08:18:02 -06:00
|
|
|
fmt.Fprintln(os.Stderr, err)
|
|
|
|
os.Exit(1)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// tracerFromFlags parses the cli flags and returns the specified tracer.
|
|
|
|
func tracerFromFlags(ctx *cli.Context) *tracing.Hooks {
|
|
|
|
config := &logger.Config{
|
|
|
|
EnableMemory: !ctx.Bool(TraceDisableMemoryFlag.Name),
|
|
|
|
DisableStack: ctx.Bool(TraceDisableStackFlag.Name),
|
|
|
|
DisableStorage: ctx.Bool(TraceDisableStorageFlag.Name),
|
|
|
|
EnableReturnData: !ctx.Bool(TraceDisableReturnDataFlag.Name),
|
|
|
|
}
|
|
|
|
switch {
|
|
|
|
case ctx.Bool(TraceFlag.Name) && ctx.String(TraceFormatFlag.Name) == "struct":
|
|
|
|
return logger.NewStructLogger(config).Hooks()
|
|
|
|
case ctx.Bool(TraceFlag.Name) && ctx.String(TraceFormatFlag.Name) == "json":
|
|
|
|
return logger.NewJSONLogger(config, os.Stderr)
|
|
|
|
case ctx.Bool(MachineFlag.Name):
|
|
|
|
return logger.NewJSONLogger(config, os.Stderr)
|
|
|
|
case ctx.Bool(DebugFlag.Name):
|
|
|
|
return logger.NewStructLogger(config).Hooks()
|
|
|
|
default:
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// collectJSONFiles walks the given path and accumulates all files with json
|
|
|
|
// extension.
|
|
|
|
func collectJSONFiles(path string) []string {
|
|
|
|
var out []string
|
|
|
|
err := filepath.Walk(path, func(path string, info fs.FileInfo, err error) error {
|
|
|
|
if err != nil {
|
|
|
|
return err
|
2020-06-30 03:12:51 -05:00
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
if !info.IsDir() && filepath.Ext(info.Name()) == ".json" {
|
|
|
|
out = append(out, path)
|
|
|
|
}
|
|
|
|
return nil
|
|
|
|
})
|
|
|
|
if err != nil {
|
2015-07-17 08:43:16 -05:00
|
|
|
fmt.Fprintln(os.Stderr, err)
|
|
|
|
}
|
2024-12-02 08:18:02 -06:00
|
|
|
return out
|
|
|
|
}
|
|
|
|
|
|
|
|
// dump returns a state dump for the most current trie.
|
|
|
|
func dump(s *state.StateDB) *state.Dump {
|
|
|
|
root := s.IntermediateRoot(false)
|
|
|
|
cpy, _ := state.New(root, s.Database())
|
|
|
|
dump := cpy.RawDump(nil)
|
|
|
|
return &dump
|
2014-11-10 04:47:37 -06:00
|
|
|
}
|