You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
// If we're dumping the pending state, we need to request
// both the pending block as well as the pending state from
// the miner and operate on those
_, _, stateDb=api.eth.miner.Pending()
ifstateDb==nil {
return state.Dump{}, errors.New("pending state is not available")
}
} else {
varheader*types.Header
switchnumber {
caserpc.LatestBlockNumber:
header=api.eth.blockchain.CurrentBlock()
Description: Root cause — DebugAPI.AccountRange accepts maxResults as a plain int with no bounds-validation error path; the method treats it as an internal "sanity limit" over RPC rather than a validated request parameter, so nonpositive or over-256 values are clamped to a default/maximum bound before the account iteration runs, instead of the call failing or honoring the exact page size the caller asked for.
Method: debug_accountRange
2. debug_chaindbProperty: The documented debug_chaindbProperty Console/RPC signatures retain a property argument that DebugAPI.ChaindbProperty no longer has
Statement: The documented debug_chaindbProperty Console/RPC signatures retain a property argument that DebugAPI.ChaindbProperty no longer has.
Max: AccountRangeMaxResults, // Sanity limit over RPC
}
ifblockNr==rpc.PendingBlockNumber {
// If we're dumping the pending state, we need to request
// both the pending block as well as the pending state from
// the miner and operate on those
_, _, stateDb:=api.eth.miner.Pending()
ifstateDb==nil {
return state.Dump{}, errors.New("pending state is not available")
}
returnstateDb.RawDump(opts), nil
}
varheader*types.Header
switchblockNr {
caserpc.LatestBlockNumber:
Description: Root cause — DebugAPI.ChaindbProperty is declared with zero parameters (func (api *DebugAPI) ChaindbProperty() (string, error)) and simply forwards to the database's Stat() call; the Go method's property string argument was removed at some point without updating the documented Console (debug.chaindbProperty(property string)) and raw-RPC (params: [property]) signatures, so a caller that follows the documented arity supplies an argument the current handler no longer accepts.
Method: debug_chaindbProperty
3. debug_dumpBlock: The debug_dumpBlock Console documentation copies debug_traceBlockByHash with an unsupported options argument instead of the DumpBlock invocation
Statement: The debug_dumpBlock Console documentation copies debug_traceBlockByHash with an unsupported options argument instead of the DumpBlock invocation.
Description: Root cause — DebugAPI.DumpBlock(blockNr rpc.BlockNumber) (state.Dump, error) takes a single block-number selector decoded by rpc.BlockNumber.UnmarshalJSON and has no second (options) parameter at all; the Console doc example was authored by copy-pasting the neighboring debug_traceBlockByHash(hash, options) snippet instead of describing the real one-argument DumpBlock call, so it documents an argument the handler cannot accept.
Method: debug_dumpBlock
4. debug_dumpBlock: debug_dumpBlock returns state.Dump rather than the documented state.World
Statement: debug_dumpBlock returns state.Dump rather than the documented state.World.
Description: Root cause — DebugAPI.DumpBlock's declared return type is (state.Dump, error), and every code path (including the pending-state branch) returns the value produced by StateDB.RawDump, whose signature is func (s *StateDB) RawDump(opts *DumpConfig) Dump. No state.World type is constructed or returned anywhere in the call chain; state.World is a stale type name left over from a prior API shape that the documentation never updated.
Method: debug_dumpBlock
5. debug_setHead: debug_setHead takes hexutil.Uint64 and therefore uses hex-quantity decoding, not the documented plain uint64 Go signature
Statement: debug_setHead takes hexutil.Uint64 and therefore uses hex-quantity decoding, not the documented plain uint64 Go signature.
returnerrors.New("current header is not available")
}
ifheader.Number.Uint64() <=uint64(number) {
returnerrors.New("not allowed to rewind to a future block")
}
returnapi.b.SetHead(uint64(number))
}
Description: Root cause — DebugAPI.SetHead(number hexutil.Uint64) error declares its parameter as hexutil.Uint64, a type whose JSON unmarshaler requires a 0x-prefixed hex string and rejects a plain decimal JSON number. The documented plain-uint64 Go signature describes a type that would accept a decimal number, which does not match the type actually wired into the JSON-RPC method table.
Method: debug_setHead
6. debug_stacks: debug_stacks can apply an optional filter and return matching goroutine stacks rather than all stacks
Statement: debug_stacks can apply an optional filter and return matching goroutine stacks rather than all stacks.
Description: Root cause — HandlerT.Stacks(filter *string) string accepts an optional filter argument that, when non-empty, is compiled into a boolean expression over goroutine package names ((eth || snap) && !p2p style syntax) and used to select which goroutine stacks from pprof.Lookup("goroutine") are written into the response, rather than always dumping every goroutine's stack unconditionally.
Method: debug_stacks
7. debug_traceBlockByHash: debug_traceBlockByHash returns a slice of transaction trace results rather than BlockTraceResult
Statement: debug_traceBlockByHash returns a slice of transaction trace results rather than BlockTraceResult.
err=fmt.Errorf("unexpected type %T for Hash", input)
}
returnerr
}
Description: Root cause — API.traceBlock allocates results := make([]*txTraceResult, len(txs)) and populates one entry per transaction, and this slice is what is ultimately returned to the JSON-RPC layer for debug_traceBlockByHash. There is no BlockTraceResult wrapper struct anywhere in the trace path; the response shape has always been a flat, per-transaction array, so the documented named type does not correspond to any type constructed by the implementation.
Method: debug_traceBlockByHash
8. debug_traceCall: The debug_traceCall curl example selects pending even though tracing on pending errors before any documented successful result fields can be produced
Statement: The debug_traceCall curl example selects pending even though tracing on pending errors before any documented successful result fields can be produced.
Description: Root cause — API.TraceCall explicitly short-circuits with return nil, errors.New("tracing on top of pending is not supported") whenever the block selector resolves to the pending block, before any state is captured or traceTx is invoked. The documented curl example builds its request against "pending", so following it verbatim can never reach the successful trace-result fields the surrounding documentation describes, because the pending branch always errors first.
Method: debug_traceCall
9. debug_traceTransaction: TraceConfig exposes no reexec option, so neither its existence nor a uint64 type is valid for debug_traceTransaction
Statement: TraceConfig exposes no reexec option, so neither its existence nor a uint64 type is valid for debug_traceTransaction.
Description: Root cause — API.TraceTransaction(ctx, hash, config *TraceConfig) decodes its config parameter as *TraceConfig, and re-execution depth in the current implementation is governed internally (e.g. by traceChain's worker/state-tracker plumbing), not by a caller-supplied field on TraceConfig. Because TraceConfig carries no reexec field at all, the documented reexec uint64 option describes a knob that was either removed or never implemented on this struct, so it has no effect regardless of the type asserted for it.
Method: debug_traceTransaction
10. debug_traceTransaction: debug_traceTransaction accepts tracerConfig as raw JSON, not the documented JSON String type
Statement: debug_traceTransaction accepts tracerConfig as raw JSON, not the documented JSON String type.
Description: Root cause — API.traceTx reads config.TracerConfig and passes it straight to the tracer constructor as a json.RawMessage-backed value that the selected tracer unmarshals into its own option struct; the field is declared to hold arbitrary JSON, not a JSON string. Any tracer-specific config object (a map/object literal) is accepted directly, so the documented "JSON String" typing does not describe the field's actual decode behavior.
Method: debug_traceTransaction
11. debug_writeMemProfile: The debug_writeMemProfile documentation names debug_writeBlockProfile instead of the implemented WriteMemProfile method
Statement: The debug_writeMemProfile documentation names debug_writeBlockProfile instead of the implemented WriteMemProfile method.
Description: Root cause — the exported handler for the "heap" pprof profile is HandlerT.WriteMemProfile(file string) error, which calls the shared writeProfile("heap", file) helper; the JSON-RPC method name derived from this handler is debug_writeMemProfile. The documentation section describing this handler is captioned with the unrelated method name debug_writeBlockProfile (which maps to a different handler entirely), so readers following the documented method name will call the wrong endpoint.
Method: debug_writeMemProfile
12. debug_dumpBlock / debug_traceBlockByNumber: Methods backed by rpc.BlockNumber reject values above MaxInt64 although their documentation presents the selector as uint64
Statement: Methods backed by rpc.BlockNumber reject values above MaxInt64 although their documentation presents the selector as uint64.
Description: Root cause — both DebugAPI.DumpBlock(blockNr rpc.BlockNumber) and the block-number entry point feeding API.traceBlock decode their selector through rpc.BlockNumber, which is backed by a signed int64 and whose UnmarshalJSON rejects any decoded value that does not fit in that signed range (so block numbers at or above 2^63 fail decoding entirely, while 2^63-1 is the practical ceiling). The documented Go signatures describe the parameter as an unsigned uint64, which would admit the full unsigned range, so the selector's real capacity is narrower than advertised.
Method: debug_dumpBlock, debug_traceBlockByNumber
13. debug_standardTraceBlockToFile: StdTraceConfig uses a value common.Hash for TxHash, not a nullable *common.Hash
Statement: StdTraceConfig uses a value common.Hash for TxHash, not a nullable *common.Hash.
Description: Root cause — standardTraceBlockToFile tests "was a specific transaction requested" with config != nil && config.TxHash != (common.Hash{}), i.e. it compares the field against the zero value of a value-typed common.Hash, not a nil check on a pointer. Because TxHash is declared as a plain (non-pointer) common.Hash on StdTraceConfig, "no transaction specified" and "transaction hash equal to the zero hash" are indistinguishable at the type level, unlike the nullable pointer the documentation implies.
Method: debug_standardTraceBlockToFile
14. debug_traceTransaction: debug_traceTransaction returns a dynamic interface result, so custom tracers can return scalar values rather than *ExecutionResult
Statement: debug_traceTransaction returns a dynamic interface result, so custom tracers can return scalar values rather than *ExecutionResult.
Description: Root cause — API.TraceTransaction is declared to return (interface{}, error), and the concrete value placed in that interface comes from whichever tracer's GetResult() was selected; built-in struct-log tracing returns an *ExecutionResult-shaped value, but custom (e.g. JS/native) tracers are free to return any JSON-marshalable value, including bare scalars or strings, because the RPC layer never asserts a concrete result type. The documented fixed *ExecutionResult return type therefore only describes the default tracer's output, not the endpoint's actual, tracer-dependent contract.
1.
debug_accountRange:debug_accountRangesilently clamps nonpositive or over-256maxResultsinstead of returning the requested page sizedebug_accountRangesilently clamps nonpositive or over-256maxResultsinstead of returning the requested page size.eth/api_debug.go:138-155—go-ethereum/eth/api_debug.go
Lines 138 to 155 in 81ab8b5
DebugAPI.AccountRangeacceptsmaxResultsas a plainintwith no bounds-validation error path; the method treats it as an internal "sanity limit" over RPC rather than a validated request parameter, so nonpositive or over-256 values are clamped to a default/maximum bound before the account iteration runs, instead of the call failing or honoring the exact page size the caller asked for.debug_accountRange2.
debug_chaindbProperty: The documenteddebug_chaindbPropertyConsole/RPC signatures retain apropertyargument thatDebugAPI.ChaindbPropertyno longer hasdebug_chaindbPropertyConsole/RPC signatures retain apropertyargument thatDebugAPI.ChaindbPropertyno longer has.internal/ethapi/api.go:2119-2121—go-ethereum/internal/ethapi/api.go
Lines 2119 to 2121 in 81ab8b5
eth/api_debug.go:52-69—go-ethereum/eth/api_debug.go
Lines 52 to 69 in 81ab8b5
DebugAPI.ChaindbPropertyis declared with zero parameters (func (api *DebugAPI) ChaindbProperty() (string, error)) and simply forwards to the database'sStat()call; the Go method'sproperty stringargument was removed at some point without updating the documented Console (debug.chaindbProperty(property string)) and raw-RPC (params: [property]) signatures, so a caller that follows the documented arity supplies an argument the current handler no longer accepts.debug_chaindbProperty3.
debug_dumpBlock: Thedebug_dumpBlockConsole documentation copiesdebug_traceBlockByHashwith an unsupported options argument instead of theDumpBlockinvocationdebug_dumpBlockConsole documentation copiesdebug_traceBlockByHashwith an unsupported options argument instead of theDumpBlockinvocation.eth/api_debug.go:52-69—go-ethereum/eth/api_debug.go
Lines 52 to 69 in 81ab8b5
rpc/types.go:80-97—go-ethereum/rpc/types.go
Lines 80 to 97 in 81ab8b5
DebugAPI.DumpBlock(blockNr rpc.BlockNumber) (state.Dump, error)takes a single block-number selector decoded byrpc.BlockNumber.UnmarshalJSONand has no second (options) parameter at all; the Console doc example was authored by copy-pasting the neighboringdebug_traceBlockByHash(hash, options)snippet instead of describing the real one-argumentDumpBlockcall, so it documents an argument the handler cannot accept.debug_dumpBlock4.
debug_dumpBlock:debug_dumpBlockreturnsstate.Dumprather than the documentedstate.Worlddebug_dumpBlockreturnsstate.Dumprather than the documentedstate.World.eth/api_debug.go:52-69—go-ethereum/eth/api_debug.go
Lines 52 to 69 in 81ab8b5
core/state/dump.go:241-248—go-ethereum/core/state/dump.go
Lines 241 to 248 in 81ab8b5
DebugAPI.DumpBlock's declared return type is(state.Dump, error), and every code path (including the pending-state branch) returns the value produced byStateDB.RawDump, whose signature isfunc (s *StateDB) RawDump(opts *DumpConfig) Dump. Nostate.Worldtype is constructed or returned anywhere in the call chain;state.Worldis a stale type name left over from a prior API shape that the documentation never updated.debug_dumpBlock5.
debug_setHead:debug_setHeadtakeshexutil.Uint64and therefore uses hex-quantity decoding, not the documented plainuint64Go signaturedebug_setHeadtakeshexutil.Uint64and therefore uses hex-quantity decoding, not the documented plainuint64Go signature.internal/ethapi/api.go:2145-2154—go-ethereum/internal/ethapi/api.go
Lines 2145 to 2154 in 81ab8b5
DebugAPI.SetHead(number hexutil.Uint64) errordeclares its parameter ashexutil.Uint64, a type whose JSON unmarshaler requires a0x-prefixed hex string and rejects a plain decimal JSON number. The documented plain-uint64Go signature describes a type that would accept a decimal number, which does not match the type actually wired into the JSON-RPC method table.debug_setHead6.
debug_stacks:debug_stackscan apply an optional filter and return matching goroutine stacks rather than all stacksdebug_stackscan apply an optional filter and return matching goroutine stacks rather than all stacks.internal/debug/api.go:192-209—go-ethereum/internal/debug/api.go
Lines 192 to 209 in 81ab8b5
HandlerT.Stacks(filter *string) stringaccepts an optionalfilterargument that, when non-empty, is compiled into a boolean expression over goroutine package names ((eth || snap) && !p2pstyle syntax) and used to select which goroutine stacks frompprof.Lookup("goroutine")are written into the response, rather than always dumping every goroutine's stack unconditionally.debug_stacks7.
debug_traceBlockByHash:debug_traceBlockByHashreturns a slice of transaction trace results rather thanBlockTraceResultdebug_traceBlockByHashreturns a slice of transaction trace results rather thanBlockTraceResult.eth/tracers/api.go:588-605—go-ethereum/eth/tracers/api.go
Lines 588 to 605 in 81ab8b5
common/types.go:195-204—go-ethereum/common/types.go
Lines 195 to 204 in 81ab8b5
API.traceBlockallocatesresults := make([]*txTraceResult, len(txs))and populates one entry per transaction, and this slice is what is ultimately returned to the JSON-RPC layer fordebug_traceBlockByHash. There is noBlockTraceResultwrapper struct anywhere in the trace path; the response shape has always been a flat, per-transaction array, so the documented named type does not correspond to any type constructed by the implementation.debug_traceBlockByHash8.
debug_traceCall: Thedebug_traceCallcurl example selectspendingeven though tracing onpendingerrors before any documented successful result fields can be produceddebug_traceCallcurl example selectspendingeven though tracing onpendingerrors before any documented successful result fields can be produced.eth/tracers/api.go:895-912—go-ethereum/eth/tracers/api.go
Lines 895 to 912 in 81ab8b5
eth/tracers/api.go:1009-1026—go-ethereum/eth/tracers/api.go
Lines 1009 to 1026 in 81ab8b5
API.TraceCallexplicitly short-circuits withreturn nil, errors.New("tracing on top of pending is not supported")whenever the block selector resolves to the pending block, before any state is captured ortraceTxis invoked. The documented curl example builds its request against"pending", so following it verbatim can never reach the successful trace-result fields the surrounding documentation describes, because the pending branch always errors first.debug_traceCall9.
debug_traceTransaction:TraceConfigexposes noreexecoption, so neither its existence nor auint64type is valid fordebug_traceTransactionTraceConfigexposes noreexecoption, so neither its existence nor auint64type is valid fordebug_traceTransaction.eth/tracers/api.go:240-257—go-ethereum/eth/tracers/api.go
Lines 240 to 257 in 81ab8b5
eth/tracers/api.go:837-854—go-ethereum/eth/tracers/api.go
Lines 837 to 854 in 81ab8b5
API.TraceTransaction(ctx, hash, config *TraceConfig)decodes its config parameter as*TraceConfig, and re-execution depth in the current implementation is governed internally (e.g. bytraceChain's worker/state-tracker plumbing), not by a caller-supplied field onTraceConfig. BecauseTraceConfigcarries noreexecfield at all, the documentedreexec uint64option describes a knob that was either removed or never implemented on this struct, so it has no effect regardless of the type asserted for it.debug_traceTransaction10.
debug_traceTransaction:debug_traceTransactionacceptstracerConfigas raw JSON, not the documented JSON String typedebug_traceTransactionacceptstracerConfigas raw JSON, not the documented JSON String type.eth/tracers/api.go:971-988—go-ethereum/eth/tracers/api.go
Lines 971 to 988 in 81ab8b5
common/types.go:476-486—go-ethereum/common/types.go
Lines 476 to 486 in 81ab8b5
API.traceTxreadsconfig.TracerConfigand passes it straight to the tracer constructor as ajson.RawMessage-backed value that the selected tracer unmarshals into its own option struct; the field is declared to hold arbitrary JSON, not a JSON string. Any tracer-specific config object (a map/object literal) is accepted directly, so the documented "JSON String" typing does not describe the field's actual decode behavior.debug_traceTransaction11.
debug_writeMemProfile: Thedebug_writeMemProfiledocumentation namesdebug_writeBlockProfileinstead of the implementedWriteMemProfilemethoddebug_writeMemProfiledocumentation namesdebug_writeBlockProfileinstead of the implementedWriteMemProfilemethod.internal/debug/api.go:185-187—go-ethereum/internal/debug/api.go
Lines 185 to 187 in 81ab8b5
internal/debug/api.go:259-268—go-ethereum/internal/debug/api.go
Lines 259 to 268 in 81ab8b5
HandlerT.WriteMemProfile(file string) error, which calls the sharedwriteProfile("heap", file)helper; the JSON-RPC method name derived from this handler isdebug_writeMemProfile. The documentation section describing this handler is captioned with the unrelated method namedebug_writeBlockProfile(which maps to a different handler entirely), so readers following the documented method name will call the wrong endpoint.debug_writeMemProfile12.
debug_dumpBlock/debug_traceBlockByNumber: Methods backed byrpc.BlockNumberreject values aboveMaxInt64although their documentation presents the selector asuint64rpc.BlockNumberreject values aboveMaxInt64although their documentation presents the selector asuint64.eth/api_debug.go:52-69—go-ethereum/eth/api_debug.go
Lines 52 to 69 in 81ab8b5
eth/tracers/api.go:565-582—go-ethereum/eth/tracers/api.go
Lines 565 to 582 in 81ab8b5
DebugAPI.DumpBlock(blockNr rpc.BlockNumber)and the block-number entry point feedingAPI.traceBlockdecode their selector throughrpc.BlockNumber, which is backed by a signedint64and whoseUnmarshalJSONrejects any decoded value that does not fit in that signed range (so block numbers at or above 2^63 fail decoding entirely, while 2^63-1 is the practical ceiling). The documented Go signatures describe the parameter as an unsigneduint64, which would admit the full unsigned range, so the selector's real capacity is narrower than advertised.debug_dumpBlock,debug_traceBlockByNumber13.
debug_standardTraceBlockToFile:StdTraceConfiguses a valuecommon.HashforTxHash, not a nullable*common.HashStdTraceConfiguses a valuecommon.HashforTxHash, not a nullable*common.Hash.eth/tracers/api.go:707-724—go-ethereum/eth/tracers/api.go
Lines 707 to 724 in 81ab8b5
eth/tracers/api.go:484-490—go-ethereum/eth/tracers/api.go
Lines 484 to 490 in 81ab8b5
standardTraceBlockToFiletests "was a specific transaction requested" withconfig != nil && config.TxHash != (common.Hash{}), i.e. it compares the field against the zero value of a value-typedcommon.Hash, not a nil check on a pointer. BecauseTxHashis declared as a plain (non-pointer)common.HashonStdTraceConfig, "no transaction specified" and "transaction hash equal to the zero hash" are indistinguishable at the type level, unlike the nullable pointer the documentation implies.debug_standardTraceBlockToFile14.
debug_traceTransaction:debug_traceTransactionreturns a dynamic interface result, so custom tracers can return scalar values rather than*ExecutionResultdebug_traceTransactionreturns a dynamic interface result, so custom tracers can return scalar values rather than*ExecutionResult.eth/tracers/api.go:837-854—go-ethereum/eth/tracers/api.go
Lines 837 to 854 in 81ab8b5
eth/tracers/api.go:138-147—go-ethereum/eth/tracers/api.go
Lines 138 to 147 in 81ab8b5
API.TraceTransactionis declared to return(interface{}, error), and the concrete value placed in that interface comes from whichever tracer'sGetResult()was selected; built-in struct-log tracing returns an*ExecutionResult-shaped value, but custom (e.g. JS/native) tracers are free to return any JSON-marshalable value, including bare scalars or strings, because the RPC layer never asserts a concrete result type. The documented fixed*ExecutionResultreturn type therefore only describes the default tracer's output, not the endpoint's actual, tracer-dependent contract.debug_traceTransaction