eth, eth/filters: try accessing db before returning error 4444

This commit is contained in:
Felix Lange 2025-04-01 12:11:16 +02:00
parent 959bc4e401
commit d5a0d6256e
5 changed files with 33 additions and 24 deletions

View file

@ -34,6 +34,7 @@ import (
"github.com/ethereum/go-ethereum/core/txpool"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm"
"github.com/ethereum/go-ethereum/eth/ethconfig"
"github.com/ethereum/go-ethereum/eth/gasprice"
"github.com/ethereum/go-ethereum/eth/tracers"
"github.com/ethereum/go-ethereum/ethdb"
@ -42,12 +43,6 @@ import (
"github.com/ethereum/go-ethereum/rpc"
)
// ErrorPrunedHistory is returned when the requested history is pruned.
type ErrorPrunedHistory struct{}
func (e *ErrorPrunedHistory) Error() string { return "Pruned history unavailable" }
func (e *ErrorPrunedHistory) ErrorCode() int { return 4444 }
// EthAPIBackend implements ethapi.Backend and tracers.Backend for full nodes
type EthAPIBackend struct {
extRPCEnabled bool
@ -159,10 +154,13 @@ func (b *EthAPIBackend) BlockByNumber(ctx context.Context, number rpc.BlockNumbe
if number == rpc.EarliestBlockNumber {
bn = b.eth.blockchain.HistoryPruningCutoff()
}
if bn < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ErrorPrunedHistory{}
// bn is the resolved number.
block := b.eth.blockchain.GetBlockByNumber(bn)
if block == nil && bn < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ethconfig.PrunedHistoryError{}
}
return b.eth.blockchain.GetBlockByNumber(bn), nil
return nil, nil
}
func (b *EthAPIBackend) BlockByHash(ctx context.Context, hash common.Hash) (*types.Block, error) {
@ -170,10 +168,11 @@ func (b *EthAPIBackend) BlockByHash(ctx context.Context, hash common.Hash) (*typ
if number == nil {
return nil, nil
}
if *number < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ErrorPrunedHistory{}
block := b.eth.blockchain.GetBlock(hash, *number)
if block == nil && *number < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ethconfig.PrunedHistoryError{}
}
return b.eth.blockchain.GetBlock(hash, *number), nil
return nil, nil
}
// GetBody returns body of a block. It does not resolve special block numbers.
@ -181,11 +180,15 @@ func (b *EthAPIBackend) GetBody(ctx context.Context, hash common.Hash, number rp
if number < 0 || hash == (common.Hash{}) {
return nil, errors.New("invalid arguments; expect hash and no special block numbers")
}
if body := b.eth.blockchain.GetBody(hash); body != nil {
return body, nil
body := b.eth.blockchain.GetBody(hash)
if body == nil {
if uint64(number) < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ethconfig.PrunedHistoryError{}
}
return nil, errors.New("block body not found")
}
return body, nil
}
func (b *EthAPIBackend) BlockByNumberOrHash(ctx context.Context, blockNrOrHash rpc.BlockNumberOrHash) (*types.Block, error) {
if blockNr, ok := blockNrOrHash.Number(); ok {
@ -199,11 +202,11 @@ func (b *EthAPIBackend) BlockByNumberOrHash(ctx context.Context, blockNrOrHash r
if blockNrOrHash.RequireCanonical && b.eth.blockchain.GetCanonicalHash(header.Number.Uint64()) != hash {
return nil, errors.New("hash is not currently canonical")
}
if header.Number.Uint64() < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ErrorPrunedHistory{}
}
block := b.eth.blockchain.GetBlock(hash, header.Number.Uint64())
if block == nil {
if header.Number.Uint64() < b.eth.blockchain.HistoryPruningCutoff() {
return nil, &ethconfig.PrunedHistoryError{}
}
return nil, errors.New("header found, but block body is missing")
}
return block, nil

View file

@ -90,3 +90,9 @@ var HistoryPrunePoints = map[common.Hash]*HistoryPrunePoint{
BlockHash: common.HexToHash("0x229f6b18ca1552f1d5146deceb5387333f40dc6275aebee3f2c5c4ece07d02db"),
},
}
// PrunedHistoryError is returned when the requested history is pruned.
type PrunedHistoryError struct{}
func (e *PrunedHistoryError) Error() string { return "pruned history unavailable" }
func (e *PrunedHistoryError) ErrorCode() int { return 4444 }

View file

@ -29,7 +29,7 @@ import (
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/eth/ethconfig"
"github.com/ethereum/go-ethereum/internal/ethapi"
"github.com/ethereum/go-ethereum/rpc"
)
@ -360,7 +360,7 @@ func (api *FilterAPI) GetLogs(ctx context.Context, crit FilterCriteria) ([]*type
return nil, errInvalidBlockRange
}
if begin > 0 && begin < int64(api.events.backend.HistoryPruningCutoff()) {
return nil, &eth.ErrorPrunedHistory{}
return nil, &ethconfig.PrunedHistoryError{}
}
// Construct the range filter
filter = api.sys.NewRangeFilter(begin, end, crit.Addresses, crit.Topics)

View file

@ -27,7 +27,7 @@ import (
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/filtermaps"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/eth/ethconfig"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/rpc"
)
@ -88,7 +88,7 @@ func (f *Filter) Logs(ctx context.Context) ([]*types.Log, error) {
return nil, errors.New("unknown block")
}
if header.Number.Uint64() < f.sys.backend.HistoryPruningCutoff() {
return nil, &eth.ErrorPrunedHistory{}
return nil, &ethconfig.PrunedHistoryError{}
}
return f.blockLogs(ctx, header)
}

View file

@ -31,7 +31,7 @@ import (
"github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/filtermaps"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/eth/ethconfig"
"github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/event"
"github.com/ethereum/go-ethereum/log"
@ -311,7 +311,7 @@ func (es *EventSystem) SubscribeLogs(crit ethereum.FilterQuery, logs chan []*typ
}
// Queries beyond the pruning cutoff are not supported.
if uint64(from) < es.backend.HistoryPruningCutoff() {
return nil, &eth.ErrorPrunedHistory{}
return nil, &ethconfig.PrunedHistoryError{}
}
// only interested in new mined logs