Unverified Commit 6cf0ab38 authored by Péter Szilágyi's avatar Péter Szilágyi Committed by GitHub

core/rawdb: separate raw database access to own package (#16666)

parent 5463ed99
...@@ -31,6 +31,7 @@ import ( ...@@ -31,6 +31,7 @@ import (
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -159,7 +160,7 @@ func (b *SimulatedBackend) StorageAt(ctx context.Context, contract common.Addres ...@@ -159,7 +160,7 @@ func (b *SimulatedBackend) StorageAt(ctx context.Context, contract common.Addres
// TransactionReceipt returns the receipt of a transaction. // TransactionReceipt returns the receipt of a transaction.
func (b *SimulatedBackend) TransactionReceipt(ctx context.Context, txHash common.Hash) (*types.Receipt, error) { func (b *SimulatedBackend) TransactionReceipt(ctx context.Context, txHash common.Hash) (*types.Receipt, error) {
receipt, _, _, _ := core.GetReceipt(b.database, txHash) receipt, _, _, _ := rawdb.ReadReceipt(b.database, txHash)
return receipt, nil return receipt, nil
} }
...@@ -430,11 +431,19 @@ func (fb *filterBackend) HeaderByNumber(ctx context.Context, block rpc.BlockNumb ...@@ -430,11 +431,19 @@ func (fb *filterBackend) HeaderByNumber(ctx context.Context, block rpc.BlockNumb
} }
func (fb *filterBackend) GetReceipts(ctx context.Context, hash common.Hash) (types.Receipts, error) { func (fb *filterBackend) GetReceipts(ctx context.Context, hash common.Hash) (types.Receipts, error) {
return core.GetBlockReceipts(fb.db, hash, core.GetBlockNumber(fb.db, hash)), nil number := rawdb.ReadHeaderNumber(fb.db, hash)
if number == nil {
return nil, nil
}
return rawdb.ReadReceipts(fb.db, hash, *number), nil
} }
func (fb *filterBackend) GetLogs(ctx context.Context, hash common.Hash) ([][]*types.Log, error) { func (fb *filterBackend) GetLogs(ctx context.Context, hash common.Hash) ([][]*types.Log, error) {
receipts := core.GetBlockReceipts(fb.db, hash, core.GetBlockNumber(fb.db, hash)) number := rawdb.ReadHeaderNumber(fb.db, hash)
if number == nil {
return nil, nil
}
receipts := rawdb.ReadReceipts(fb.db, hash, *number)
if receipts == nil { if receipts == nil {
return nil, nil return nil, nil
} }
......
...@@ -24,7 +24,7 @@ import ( ...@@ -24,7 +24,7 @@ import (
"testing" "testing"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
) )
...@@ -131,8 +131,8 @@ func testDAOForkBlockNewChain(t *testing.T, test int, genesis string, expectBloc ...@@ -131,8 +131,8 @@ func testDAOForkBlockNewChain(t *testing.T, test int, genesis string, expectBloc
if genesis != "" { if genesis != "" {
genesisHash = daoGenesisHash genesisHash = daoGenesisHash
} }
config, err := core.GetChainConfig(db, genesisHash) config := rawdb.ReadChainConfig(db, genesisHash)
if err != nil { if config == nil {
t.Errorf("test %d: failed to retrieve chain config: %v", test, err) t.Errorf("test %d: failed to retrieve chain config: %v", test, err)
return // we want to return here, the other checks can't make it past this point (nil panic). return // we want to return here, the other checks can't make it past this point (nil panic).
} }
......
...@@ -29,6 +29,7 @@ import ( ...@@ -29,6 +29,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -271,15 +272,13 @@ func ImportPreimages(db *ethdb.LDBDatabase, fn string) error { ...@@ -271,15 +272,13 @@ func ImportPreimages(db *ethdb.LDBDatabase, fn string) error {
// Accumulate the preimages and flush when enough ws gathered // Accumulate the preimages and flush when enough ws gathered
preimages[crypto.Keccak256Hash(blob)] = common.CopyBytes(blob) preimages[crypto.Keccak256Hash(blob)] = common.CopyBytes(blob)
if len(preimages) > 1024 { if len(preimages) > 1024 {
if err := core.WritePreimages(db, 0, preimages); err != nil { rawdb.WritePreimages(db, 0, preimages)
return err
}
preimages = make(map[common.Hash][]byte) preimages = make(map[common.Hash][]byte)
} }
} }
// Flush the last batch preimage data // Flush the last batch preimage data
if len(preimages) > 0 { if len(preimages) > 0 {
return core.WritePreimages(db, 0, preimages) rawdb.WritePreimages(db, 0, preimages)
} }
return nil return nil
} }
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -81,7 +82,7 @@ func (r *testerChainReader) GetBlock(common.Hash, uint64) *types.Block { panic ...@@ -81,7 +82,7 @@ func (r *testerChainReader) GetBlock(common.Hash, uint64) *types.Block { panic
func (r *testerChainReader) GetHeaderByHash(common.Hash) *types.Header { panic("not supported") } func (r *testerChainReader) GetHeaderByHash(common.Hash) *types.Header { panic("not supported") }
func (r *testerChainReader) GetHeaderByNumber(number uint64) *types.Header { func (r *testerChainReader) GetHeaderByNumber(number uint64) *types.Header {
if number == 0 { if number == 0 {
return core.GetHeader(r.db, core.GetCanonicalHash(r.db, 0), 0) return rawdb.ReadHeader(r.db, rawdb.ReadCanonicalHash(r.db, 0), 0)
} }
panic("not supported") panic("not supported")
} }
......
...@@ -26,6 +26,7 @@ import ( ...@@ -26,6 +26,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
...@@ -234,13 +235,15 @@ func makeChainForBench(db ethdb.Database, full bool, count uint64) { ...@@ -234,13 +235,15 @@ func makeChainForBench(db ethdb.Database, full bool, count uint64) {
ReceiptHash: types.EmptyRootHash, ReceiptHash: types.EmptyRootHash,
} }
hash = header.Hash() hash = header.Hash()
WriteHeader(db, header)
WriteCanonicalHash(db, hash, n) rawdb.WriteHeader(db, header)
WriteTd(db, hash, n, big.NewInt(int64(n+1))) rawdb.WriteCanonicalHash(db, hash, n)
rawdb.WriteTd(db, hash, n, big.NewInt(int64(n+1)))
if full || n == 0 { if full || n == 0 {
block := types.NewBlockWithHeader(header) block := types.NewBlockWithHeader(header)
WriteBody(db, hash, n, block.Body()) rawdb.WriteBody(db, hash, n, block.Body())
WriteBlockReceipts(db, hash, n, nil) rawdb.WriteReceipts(db, hash, n, nil)
} }
} }
} }
...@@ -292,11 +295,10 @@ func benchReadChain(b *testing.B, full bool, count uint64) { ...@@ -292,11 +295,10 @@ func benchReadChain(b *testing.B, full bool, count uint64) {
header := chain.GetHeaderByNumber(n) header := chain.GetHeaderByNumber(n)
if full { if full {
hash := header.Hash() hash := header.Hash()
GetBody(db, hash, n) rawdb.ReadBody(db, hash, n)
GetBlockReceipts(db, hash, n) rawdb.ReadReceipts(db, hash, n)
} }
} }
chain.Stop() chain.Stop()
db.Close() db.Close()
} }
......
This diff is collapsed.
...@@ -26,6 +26,7 @@ import ( ...@@ -26,6 +26,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -128,8 +129,8 @@ func testBlockChainImport(chain types.Blocks, blockchain *BlockChain) error { ...@@ -128,8 +129,8 @@ func testBlockChainImport(chain types.Blocks, blockchain *BlockChain) error {
return err return err
} }
blockchain.mu.Lock() blockchain.mu.Lock()
WriteTd(blockchain.db, block.Hash(), block.NumberU64(), new(big.Int).Add(block.Difficulty(), blockchain.GetTdByHash(block.ParentHash()))) rawdb.WriteTd(blockchain.db, block.Hash(), block.NumberU64(), new(big.Int).Add(block.Difficulty(), blockchain.GetTdByHash(block.ParentHash())))
WriteBlock(blockchain.db, block) rawdb.WriteBlock(blockchain.db, block)
statedb.Commit(false) statedb.Commit(false)
blockchain.mu.Unlock() blockchain.mu.Unlock()
} }
...@@ -146,8 +147,8 @@ func testHeaderChainImport(chain []*types.Header, blockchain *BlockChain) error ...@@ -146,8 +147,8 @@ func testHeaderChainImport(chain []*types.Header, blockchain *BlockChain) error
} }
// Manually insert the header into the database, but don't reorganise (allows subsequent testing) // Manually insert the header into the database, but don't reorganise (allows subsequent testing)
blockchain.mu.Lock() blockchain.mu.Lock()
WriteTd(blockchain.db, header.Hash(), header.Number.Uint64(), new(big.Int).Add(header.Difficulty, blockchain.GetTdByHash(header.ParentHash))) rawdb.WriteTd(blockchain.db, header.Hash(), header.Number.Uint64(), new(big.Int).Add(header.Difficulty, blockchain.GetTdByHash(header.ParentHash)))
WriteHeader(blockchain.db, header) rawdb.WriteHeader(blockchain.db, header)
blockchain.mu.Unlock() blockchain.mu.Unlock()
} }
return nil return nil
...@@ -173,7 +174,7 @@ func TestLastBlock(t *testing.T) { ...@@ -173,7 +174,7 @@ func TestLastBlock(t *testing.T) {
if _, err := blockchain.InsertChain(blocks); err != nil { if _, err := blockchain.InsertChain(blocks); err != nil {
t.Fatalf("Failed to insert block: %v", err) t.Fatalf("Failed to insert block: %v", err)
} }
if blocks[len(blocks)-1].Hash() != GetHeadBlockHash(blockchain.db) { if blocks[len(blocks)-1].Hash() != rawdb.ReadHeadBlockHash(blockchain.db) {
t.Fatalf("Write/Get HeadBlockHash failed") t.Fatalf("Write/Get HeadBlockHash failed")
} }
} }
...@@ -639,13 +640,13 @@ func TestFastVsFullChains(t *testing.T) { ...@@ -639,13 +640,13 @@ func TestFastVsFullChains(t *testing.T) {
} else if types.CalcUncleHash(fblock.Uncles()) != types.CalcUncleHash(ablock.Uncles()) { } else if types.CalcUncleHash(fblock.Uncles()) != types.CalcUncleHash(ablock.Uncles()) {
t.Errorf("block #%d [%x]: uncles mismatch: have %v, want %v", num, hash, fblock.Uncles(), ablock.Uncles()) t.Errorf("block #%d [%x]: uncles mismatch: have %v, want %v", num, hash, fblock.Uncles(), ablock.Uncles())
} }
if freceipts, areceipts := GetBlockReceipts(fastDb, hash, GetBlockNumber(fastDb, hash)), GetBlockReceipts(archiveDb, hash, GetBlockNumber(archiveDb, hash)); types.DeriveSha(freceipts) != types.DeriveSha(areceipts) { if freceipts, areceipts := rawdb.ReadReceipts(fastDb, hash, *rawdb.ReadHeaderNumber(fastDb, hash)), rawdb.ReadReceipts(archiveDb, hash, *rawdb.ReadHeaderNumber(archiveDb, hash)); types.DeriveSha(freceipts) != types.DeriveSha(areceipts) {
t.Errorf("block #%d [%x]: receipts mismatch: have %v, want %v", num, hash, freceipts, areceipts) t.Errorf("block #%d [%x]: receipts mismatch: have %v, want %v", num, hash, freceipts, areceipts)
} }
} }
// Check that the canonical chains are the same between the databases // Check that the canonical chains are the same between the databases
for i := 0; i < len(blocks)+1; i++ { for i := 0; i < len(blocks)+1; i++ {
if fhash, ahash := GetCanonicalHash(fastDb, uint64(i)), GetCanonicalHash(archiveDb, uint64(i)); fhash != ahash { if fhash, ahash := rawdb.ReadCanonicalHash(fastDb, uint64(i)), rawdb.ReadCanonicalHash(archiveDb, uint64(i)); fhash != ahash {
t.Errorf("block #%d: canonical hash mismatch: have %v, want %v", i, fhash, ahash) t.Errorf("block #%d: canonical hash mismatch: have %v, want %v", i, fhash, ahash)
} }
} }
...@@ -821,28 +822,28 @@ func TestChainTxReorgs(t *testing.T) { ...@@ -821,28 +822,28 @@ func TestChainTxReorgs(t *testing.T) {
// removed tx // removed tx
for i, tx := range (types.Transactions{pastDrop, freshDrop}) { for i, tx := range (types.Transactions{pastDrop, freshDrop}) {
if txn, _, _, _ := GetTransaction(db, tx.Hash()); txn != nil { if txn, _, _, _ := rawdb.ReadTransaction(db, tx.Hash()); txn != nil {
t.Errorf("drop %d: tx %v found while shouldn't have been", i, txn) t.Errorf("drop %d: tx %v found while shouldn't have been", i, txn)
} }
if rcpt, _, _, _ := GetReceipt(db, tx.Hash()); rcpt != nil { if rcpt, _, _, _ := rawdb.ReadReceipt(db, tx.Hash()); rcpt != nil {
t.Errorf("drop %d: receipt %v found while shouldn't have been", i, rcpt) t.Errorf("drop %d: receipt %v found while shouldn't have been", i, rcpt)
} }
} }
// added tx // added tx
for i, tx := range (types.Transactions{pastAdd, freshAdd, futureAdd}) { for i, tx := range (types.Transactions{pastAdd, freshAdd, futureAdd}) {
if txn, _, _, _ := GetTransaction(db, tx.Hash()); txn == nil { if txn, _, _, _ := rawdb.ReadTransaction(db, tx.Hash()); txn == nil {
t.Errorf("add %d: expected tx to be found", i) t.Errorf("add %d: expected tx to be found", i)
} }
if rcpt, _, _, _ := GetReceipt(db, tx.Hash()); rcpt == nil { if rcpt, _, _, _ := rawdb.ReadReceipt(db, tx.Hash()); rcpt == nil {
t.Errorf("add %d: expected receipt to be found", i) t.Errorf("add %d: expected receipt to be found", i)
} }
} }
// shared tx // shared tx
for i, tx := range (types.Transactions{postponed, swapped}) { for i, tx := range (types.Transactions{postponed, swapped}) {
if txn, _, _, _ := GetTransaction(db, tx.Hash()); txn == nil { if txn, _, _, _ := rawdb.ReadTransaction(db, tx.Hash()); txn == nil {
t.Errorf("share %d: expected tx to be found", i) t.Errorf("share %d: expected tx to be found", i)
} }
if rcpt, _, _, _ := GetReceipt(db, tx.Hash()); rcpt == nil { if rcpt, _, _, _ := rawdb.ReadReceipt(db, tx.Hash()); rcpt == nil {
t.Errorf("share %d: expected receipt to be found", i) t.Errorf("share %d: expected receipt to be found", i)
} }
} }
...@@ -997,14 +998,14 @@ func TestCanonicalBlockRetrieval(t *testing.T) { ...@@ -997,14 +998,14 @@ func TestCanonicalBlockRetrieval(t *testing.T) {
// try to retrieve a block by its canonical hash and see if the block data can be retrieved. // try to retrieve a block by its canonical hash and see if the block data can be retrieved.
for { for {
ch := GetCanonicalHash(blockchain.db, block.NumberU64()) ch := rawdb.ReadCanonicalHash(blockchain.db, block.NumberU64())
if ch == (common.Hash{}) { if ch == (common.Hash{}) {
continue // busy wait for canonical hash to be written continue // busy wait for canonical hash to be written
} }
if ch != block.Hash() { if ch != block.Hash() {
t.Fatalf("unknown canonical hash, want %s, got %s", block.Hash().Hex(), ch.Hex()) t.Fatalf("unknown canonical hash, want %s, got %s", block.Hash().Hex(), ch.Hex())
} }
fb := GetBlock(blockchain.db, ch, block.NumberU64()) fb := rawdb.ReadBlock(blockchain.db, ch, block.NumberU64())
if fb == nil { if fb == nil {
t.Fatalf("unable to retrieve block %d for canonical hash: %s", block.NumberU64(), ch.Hex()) t.Fatalf("unable to retrieve block %d for canonical hash: %s", block.NumberU64(), ch.Hex())
} }
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"time" "time"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/event" "github.com/ethereum/go-ethereum/event"
...@@ -206,7 +207,7 @@ func (c *ChainIndexer) eventLoop(currentHeader *types.Header, events chan ChainE ...@@ -206,7 +207,7 @@ func (c *ChainIndexer) eventLoop(currentHeader *types.Header, events chan ChainE
// TODO(karalabe): This operation is expensive and might block, causing the event system to // TODO(karalabe): This operation is expensive and might block, causing the event system to
// potentially also lock up. We need to do with on a different thread somehow. // potentially also lock up. We need to do with on a different thread somehow.
if h := FindCommonAncestor(c.chainDb, prevHeader, header); h != nil { if h := rawdb.FindCommonAncestor(c.chainDb, prevHeader, header); h != nil {
c.newHead(h.Number.Uint64(), true) c.newHead(h.Number.Uint64(), true)
} }
} }
...@@ -349,11 +350,11 @@ func (c *ChainIndexer) processSection(section uint64, lastHead common.Hash) (com ...@@ -349,11 +350,11 @@ func (c *ChainIndexer) processSection(section uint64, lastHead common.Hash) (com
} }
for number := section * c.sectionSize; number < (section+1)*c.sectionSize; number++ { for number := section * c.sectionSize; number < (section+1)*c.sectionSize; number++ {
hash := GetCanonicalHash(c.chainDb, number) hash := rawdb.ReadCanonicalHash(c.chainDb, number)
if hash == (common.Hash{}) { if hash == (common.Hash{}) {
return common.Hash{}, fmt.Errorf("canonical block #%d unknown", number) return common.Hash{}, fmt.Errorf("canonical block #%d unknown", number)
} }
header := GetHeader(c.chainDb, hash, number) header := rawdb.ReadHeader(c.chainDb, hash, number)
if header == nil { if header == nil {
return common.Hash{}, fmt.Errorf("block #%d [%x…] not found", number, hash[:4]) return common.Hash{}, fmt.Errorf("block #%d [%x…] not found", number, hash[:4])
} else if header.ParentHash != lastHead { } else if header.ParentHash != lastHead {
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"time" "time"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
) )
...@@ -92,10 +93,10 @@ func testChainIndexer(t *testing.T, count int) { ...@@ -92,10 +93,10 @@ func testChainIndexer(t *testing.T, count int) {
inject := func(number uint64) { inject := func(number uint64) {
header := &types.Header{Number: big.NewInt(int64(number)), Extra: big.NewInt(rand.Int63()).Bytes()} header := &types.Header{Number: big.NewInt(int64(number)), Extra: big.NewInt(rand.Int63()).Bytes()}
if number > 0 { if number > 0 {
header.ParentHash = GetCanonicalHash(db, number-1) header.ParentHash = rawdb.ReadCanonicalHash(db, number-1)
} }
WriteHeader(db, header) rawdb.WriteHeader(db, header)
WriteCanonicalHash(db, header.Hash(), number) rawdb.WriteCanonicalHash(db, header.Hash(), number)
} }
// Start indexer with an already existing chain // Start indexer with an already existing chain
for i := uint64(0); i <= 100; i++ { for i := uint64(0); i <= 100; i++ {
......
This diff is collapsed.
...@@ -28,6 +28,7 @@ import ( ...@@ -28,6 +28,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil" "github.com/ethereum/go-ethereum/common/hexutil"
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -155,7 +156,7 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig ...@@ -155,7 +156,7 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig
} }
// Just commit the new block if there is no stored genesis block. // Just commit the new block if there is no stored genesis block.
stored := GetCanonicalHash(db, 0) stored := rawdb.ReadCanonicalHash(db, 0)
if (stored == common.Hash{}) { if (stored == common.Hash{}) {
if genesis == nil { if genesis == nil {
log.Info("Writing default main-net genesis block") log.Info("Writing default main-net genesis block")
...@@ -177,14 +178,11 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig ...@@ -177,14 +178,11 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig
// Get the existing chain configuration. // Get the existing chain configuration.
newcfg := genesis.configOrDefault(stored) newcfg := genesis.configOrDefault(stored)
storedcfg, err := GetChainConfig(db, stored) storedcfg := rawdb.ReadChainConfig(db, stored)
if err != nil { if storedcfg == nil {
if err == ErrChainConfigNotFound {
// This case happens if a genesis write was interrupted.
log.Warn("Found genesis block without chain config") log.Warn("Found genesis block without chain config")
err = WriteChainConfig(db, stored, newcfg) rawdb.WriteChainConfig(db, stored, newcfg)
} return newcfg, stored, nil
return newcfg, stored, err
} }
// Special case: don't change the existing config of a non-mainnet chain if no new // Special case: don't change the existing config of a non-mainnet chain if no new
// config is supplied. These chains would get AllProtocolChanges (and a compat error) // config is supplied. These chains would get AllProtocolChanges (and a compat error)
...@@ -195,15 +193,16 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig ...@@ -195,15 +193,16 @@ func SetupGenesisBlock(db ethdb.Database, genesis *Genesis) (*params.ChainConfig
// Check config compatibility and write the config. Compatibility errors // Check config compatibility and write the config. Compatibility errors
// are returned to the caller unless we're already at block zero. // are returned to the caller unless we're already at block zero.
height := GetBlockNumber(db, GetHeadHeaderHash(db)) height := rawdb.ReadHeaderNumber(db, rawdb.ReadHeadHeaderHash(db))
if height == missingNumber { if height == nil {
return newcfg, stored, fmt.Errorf("missing block number for head header hash") return newcfg, stored, fmt.Errorf("missing block number for head header hash")
} }
compatErr := storedcfg.CheckCompatible(newcfg, height) compatErr := storedcfg.CheckCompatible(newcfg, *height)
if compatErr != nil && height != 0 && compatErr.RewindTo != 0 { if compatErr != nil && *height != 0 && compatErr.RewindTo != 0 {
return newcfg, stored, compatErr return newcfg, stored, compatErr
} }
return newcfg, stored, WriteChainConfig(db, stored, newcfg) rawdb.WriteChainConfig(db, stored, newcfg)
return newcfg, stored, nil
} }
func (g *Genesis) configOrDefault(ghash common.Hash) *params.ChainConfig { func (g *Genesis) configOrDefault(ghash common.Hash) *params.ChainConfig {
...@@ -267,29 +266,19 @@ func (g *Genesis) Commit(db ethdb.Database) (*types.Block, error) { ...@@ -267,29 +266,19 @@ func (g *Genesis) Commit(db ethdb.Database) (*types.Block, error) {
if block.Number().Sign() != 0 { if block.Number().Sign() != 0 {
return nil, fmt.Errorf("can't commit genesis block with number > 0") return nil, fmt.Errorf("can't commit genesis block with number > 0")
} }
if err := WriteTd(db, block.Hash(), block.NumberU64(), g.Difficulty); err != nil { rawdb.WriteTd(db, block.Hash(), block.NumberU64(), g.Difficulty)
return nil, err rawdb.WriteBlock(db, block)
} rawdb.WriteReceipts(db, block.Hash(), block.NumberU64(), nil)
if err := WriteBlock(db, block); err != nil { rawdb.WriteCanonicalHash(db, block.Hash(), block.NumberU64())
return nil, err rawdb.WriteHeadBlockHash(db, block.Hash())
} rawdb.WriteHeadHeaderHash(db, block.Hash())
if err := WriteBlockReceipts(db, block.Hash(), block.NumberU64(), nil); err != nil {
return nil, err
}
if err := WriteCanonicalHash(db, block.Hash(), block.NumberU64()); err != nil {
return nil, err
}
if err := WriteHeadBlockHash(db, block.Hash()); err != nil {
return nil, err
}
if err := WriteHeadHeaderHash(db, block.Hash()); err != nil {
return nil, err
}
config := g.Config config := g.Config
if config == nil { if config == nil {
config = params.AllEthashProtocolChanges config = params.AllEthashProtocolChanges
} }
return block, WriteChainConfig(db, block.Hash(), config) rawdb.WriteChainConfig(db, block.Hash(), config)
return block, nil
} }
// MustCommit writes the genesis block and state to db, panicking on error. // MustCommit writes the genesis block and state to db, panicking on error.
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"github.com/davecgh/go-spew/spew" "github.com/davecgh/go-spew/spew"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
...@@ -154,7 +155,7 @@ func TestSetupGenesis(t *testing.T) { ...@@ -154,7 +155,7 @@ func TestSetupGenesis(t *testing.T) {
t.Errorf("%s: returned hash %s, want %s", test.name, hash.Hex(), test.wantHash.Hex()) t.Errorf("%s: returned hash %s, want %s", test.name, hash.Hex(), test.wantHash.Hex())
} else if err == nil { } else if err == nil {
// Check database content. // Check database content.
stored := GetBlock(db, test.wantHash, 0) stored := rawdb.ReadBlock(db, test.wantHash, 0)
if stored.Hash() != test.wantHash { if stored.Hash() != test.wantHash {
t.Errorf("%s: block in DB has hash %s, want %s", test.name, stored.Hash(), test.wantHash) t.Errorf("%s: block in DB has hash %s, want %s", test.name, stored.Hash(), test.wantHash)
} }
......
...@@ -28,6 +28,7 @@ import ( ...@@ -28,6 +28,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus" "github.com/ethereum/go-ethereum/consensus"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
...@@ -97,7 +98,7 @@ func NewHeaderChain(chainDb ethdb.Database, config *params.ChainConfig, engine c ...@@ -97,7 +98,7 @@ func NewHeaderChain(chainDb ethdb.Database, config *params.ChainConfig, engine c
} }
hc.currentHeader.Store(hc.genesisHeader) hc.currentHeader.Store(hc.genesisHeader)
if head := GetHeadBlockHash(chainDb); head != (common.Hash{}) { if head := rawdb.ReadHeadBlockHash(chainDb); head != (common.Hash{}) {
if chead := hc.GetHeaderByHash(head); chead != nil { if chead := hc.GetHeaderByHash(head); chead != nil {
hc.currentHeader.Store(chead) hc.currentHeader.Store(chead)
} }
...@@ -109,13 +110,14 @@ func NewHeaderChain(chainDb ethdb.Database, config *params.ChainConfig, engine c ...@@ -109,13 +110,14 @@ func NewHeaderChain(chainDb ethdb.Database, config *params.ChainConfig, engine c
// GetBlockNumber retrieves the block number belonging to the given hash // GetBlockNumber retrieves the block number belonging to the given hash
// from the cache or database // from the cache or database
func (hc *HeaderChain) GetBlockNumber(hash common.Hash) uint64 { func (hc *HeaderChain) GetBlockNumber(hash common.Hash) *uint64 {
if cached, ok := hc.numberCache.Get(hash); ok { if cached, ok := hc.numberCache.Get(hash); ok {
return cached.(uint64) number := cached.(uint64)
return &number
} }
number := GetBlockNumber(hc.chainDb, hash) number := rawdb.ReadHeaderNumber(hc.chainDb, hash)
if number != missingNumber { if number != nil {
hc.numberCache.Add(hash, number) hc.numberCache.Add(hash, *number)
} }
return number return number
} }
...@@ -147,20 +149,19 @@ func (hc *HeaderChain) WriteHeader(header *types.Header) (status WriteStatus, er ...@@ -147,20 +149,19 @@ func (hc *HeaderChain) WriteHeader(header *types.Header) (status WriteStatus, er
if err := hc.WriteTd(hash, number, externTd); err != nil { if err := hc.WriteTd(hash, number, externTd); err != nil {
log.Crit("Failed to write header total difficulty", "err", err) log.Crit("Failed to write header total difficulty", "err", err)
} }
if err := WriteHeader(hc.chainDb, header); err != nil { rawdb.WriteHeader(hc.chainDb, header)
log.Crit("Failed to write header content", "err", err)
}
// If the total difficulty is higher than our known, add it to the canonical chain // If the total difficulty is higher than our known, add it to the canonical chain
// Second clause in the if statement reduces the vulnerability to selfish mining. // Second clause in the if statement reduces the vulnerability to selfish mining.
// Please refer to http://www.cs.cornell.edu/~ie53/publications/btcProcFC.pdf // Please refer to http://www.cs.cornell.edu/~ie53/publications/btcProcFC.pdf
if externTd.Cmp(localTd) > 0 || (externTd.Cmp(localTd) == 0 && mrand.Float64() < 0.5) { if externTd.Cmp(localTd) > 0 || (externTd.Cmp(localTd) == 0 && mrand.Float64() < 0.5) {
// Delete any canonical number assignments above the new head // Delete any canonical number assignments above the new head
for i := number + 1; ; i++ { for i := number + 1; ; i++ {
hash := GetCanonicalHash(hc.chainDb, i) hash := rawdb.ReadCanonicalHash(hc.chainDb, i)
if hash == (common.Hash{}) { if hash == (common.Hash{}) {
break break
} }
DeleteCanonicalHash(hc.chainDb, i) rawdb.DeleteCanonicalHash(hc.chainDb, i)
} }
// Overwrite any stale canonical number assignments // Overwrite any stale canonical number assignments
var ( var (
...@@ -168,20 +169,17 @@ func (hc *HeaderChain) WriteHeader(header *types.Header) (status WriteStatus, er ...@@ -168,20 +169,17 @@ func (hc *HeaderChain) WriteHeader(header *types.Header) (status WriteStatus, er
headNumber = header.Number.Uint64() - 1 headNumber = header.Number.Uint64() - 1
headHeader = hc.GetHeader(headHash, headNumber) headHeader = hc.GetHeader(headHash, headNumber)
) )
for GetCanonicalHash(hc.chainDb, headNumber) != headHash { for rawdb.ReadCanonicalHash(hc.chainDb, headNumber) != headHash {
WriteCanonicalHash(hc.chainDb, headHash, headNumber) rawdb.WriteCanonicalHash(hc.chainDb, headHash, headNumber)
headHash = headHeader.ParentHash headHash = headHeader.ParentHash
headNumber = headHeader.Number.Uint64() - 1 headNumber = headHeader.Number.Uint64() - 1
headHeader = hc.GetHeader(headHash, headNumber) headHeader = hc.GetHeader(headHash, headNumber)
} }
// Extend the canonical chain with the new header // Extend the canonical chain with the new header
if err := WriteCanonicalHash(hc.chainDb, hash, number); err != nil { rawdb.WriteCanonicalHash(hc.chainDb, hash, number)
log.Crit("Failed to insert header number", "err", err) rawdb.WriteHeadHeaderHash(hc.chainDb, hash)
}
if err := WriteHeadHeaderHash(hc.chainDb, hash); err != nil {
log.Crit("Failed to insert head header hash", "err", err)
}
hc.currentHeaderHash = hash hc.currentHeaderHash = hash
hc.currentHeader.Store(types.CopyHeader(header)) hc.currentHeader.Store(types.CopyHeader(header))
...@@ -316,7 +314,7 @@ func (hc *HeaderChain) GetTd(hash common.Hash, number uint64) *big.Int { ...@@ -316,7 +314,7 @@ func (hc *HeaderChain) GetTd(hash common.Hash, number uint64) *big.Int {
if cached, ok := hc.tdCache.Get(hash); ok { if cached, ok := hc.tdCache.Get(hash); ok {
return cached.(*big.Int) return cached.(*big.Int)
} }
td := GetTd(hc.chainDb, hash, number) td := rawdb.ReadTd(hc.chainDb, hash, number)
if td == nil { if td == nil {
return nil return nil
} }
...@@ -328,15 +326,17 @@ func (hc *HeaderChain) GetTd(hash common.Hash, number uint64) *big.Int { ...@@ -328,15 +326,17 @@ func (hc *HeaderChain) GetTd(hash common.Hash, number uint64) *big.Int {
// GetTdByHash retrieves a block's total difficulty in the canonical chain from the // GetTdByHash retrieves a block's total difficulty in the canonical chain from the
// database by hash, caching it if found. // database by hash, caching it if found.
func (hc *HeaderChain) GetTdByHash(hash common.Hash) *big.Int { func (hc *HeaderChain) GetTdByHash(hash common.Hash) *big.Int {
return hc.GetTd(hash, hc.GetBlockNumber(hash)) number := hc.GetBlockNumber(hash)
if number == nil {
return nil
}
return hc.GetTd(hash, *number)
} }
// WriteTd stores a block's total difficulty into the database, also caching it // WriteTd stores a block's total difficulty into the database, also caching it
// along the way. // along the way.
func (hc *HeaderChain) WriteTd(hash common.Hash, number uint64, td *big.Int) error { func (hc *HeaderChain) WriteTd(hash common.Hash, number uint64, td *big.Int) error {
if err := WriteTd(hc.chainDb, hash, number, td); err != nil { rawdb.WriteTd(hc.chainDb, hash, number, td)
return err
}
hc.tdCache.Add(hash, new(big.Int).Set(td)) hc.tdCache.Add(hash, new(big.Int).Set(td))
return nil return nil
} }
...@@ -348,7 +348,7 @@ func (hc *HeaderChain) GetHeader(hash common.Hash, number uint64) *types.Header ...@@ -348,7 +348,7 @@ func (hc *HeaderChain) GetHeader(hash common.Hash, number uint64) *types.Header
if header, ok := hc.headerCache.Get(hash); ok { if header, ok := hc.headerCache.Get(hash); ok {
return header.(*types.Header) return header.(*types.Header)
} }
header := GetHeader(hc.chainDb, hash, number) header := rawdb.ReadHeader(hc.chainDb, hash, number)
if header == nil { if header == nil {
return nil return nil
} }
...@@ -360,7 +360,11 @@ func (hc *HeaderChain) GetHeader(hash common.Hash, number uint64) *types.Header ...@@ -360,7 +360,11 @@ func (hc *HeaderChain) GetHeader(hash common.Hash, number uint64) *types.Header
// GetHeaderByHash retrieves a block header from the database by hash, caching it if // GetHeaderByHash retrieves a block header from the database by hash, caching it if
// found. // found.
func (hc *HeaderChain) GetHeaderByHash(hash common.Hash) *types.Header { func (hc *HeaderChain) GetHeaderByHash(hash common.Hash) *types.Header {
return hc.GetHeader(hash, hc.GetBlockNumber(hash)) number := hc.GetBlockNumber(hash)
if number == nil {
return nil
}
return hc.GetHeader(hash, *number)
} }
// HasHeader checks if a block header is present in the database or not. // HasHeader checks if a block header is present in the database or not.
...@@ -368,14 +372,13 @@ func (hc *HeaderChain) HasHeader(hash common.Hash, number uint64) bool { ...@@ -368,14 +372,13 @@ func (hc *HeaderChain) HasHeader(hash common.Hash, number uint64) bool {
if hc.numberCache.Contains(hash) || hc.headerCache.Contains(hash) { if hc.numberCache.Contains(hash) || hc.headerCache.Contains(hash) {
return true return true
} }
ok, _ := hc.chainDb.Has(headerKey(hash, number)) return rawdb.HasHeader(hc.chainDb, hash, number)
return ok
} }
// GetHeaderByNumber retrieves a block header from the database by number, // GetHeaderByNumber retrieves a block header from the database by number,
// caching it (associated with its hash) if found. // caching it (associated with its hash) if found.
func (hc *HeaderChain) GetHeaderByNumber(number uint64) *types.Header { func (hc *HeaderChain) GetHeaderByNumber(number uint64) *types.Header {
hash := GetCanonicalHash(hc.chainDb, number) hash := rawdb.ReadCanonicalHash(hc.chainDb, number)
if hash == (common.Hash{}) { if hash == (common.Hash{}) {
return nil return nil
} }
...@@ -390,9 +393,8 @@ func (hc *HeaderChain) CurrentHeader() *types.Header { ...@@ -390,9 +393,8 @@ func (hc *HeaderChain) CurrentHeader() *types.Header {
// SetCurrentHeader sets the current head header of the canonical chain. // SetCurrentHeader sets the current head header of the canonical chain.
func (hc *HeaderChain) SetCurrentHeader(head *types.Header) { func (hc *HeaderChain) SetCurrentHeader(head *types.Header) {
if err := WriteHeadHeaderHash(hc.chainDb, head.Hash()); err != nil { rawdb.WriteHeadHeaderHash(hc.chainDb, head.Hash())
log.Crit("Failed to insert head header hash", "err", err)
}
hc.currentHeader.Store(head) hc.currentHeader.Store(head)
hc.currentHeaderHash = head.Hash() hc.currentHeaderHash = head.Hash()
} }
...@@ -416,13 +418,14 @@ func (hc *HeaderChain) SetHead(head uint64, delFn DeleteCallback) { ...@@ -416,13 +418,14 @@ func (hc *HeaderChain) SetHead(head uint64, delFn DeleteCallback) {
if delFn != nil { if delFn != nil {
delFn(hash, num) delFn(hash, num)
} }
DeleteHeader(hc.chainDb, hash, num) rawdb.DeleteHeader(hc.chainDb, hash, num)
DeleteTd(hc.chainDb, hash, num) rawdb.DeleteTd(hc.chainDb, hash, num)
hc.currentHeader.Store(hc.GetHeader(hdr.ParentHash, hdr.Number.Uint64()-1)) hc.currentHeader.Store(hc.GetHeader(hdr.ParentHash, hdr.Number.Uint64()-1))
} }
// Roll back the canonical chain numbering // Roll back the canonical chain numbering
for i := height; i > head; i-- { for i := height; i > head; i-- {
DeleteCanonicalHash(hc.chainDb, i) rawdb.DeleteCanonicalHash(hc.chainDb, i)
} }
// Clear out any stale content from the caches // Clear out any stale content from the caches
hc.headerCache.Purge() hc.headerCache.Purge()
...@@ -434,9 +437,7 @@ func (hc *HeaderChain) SetHead(head uint64, delFn DeleteCallback) { ...@@ -434,9 +437,7 @@ func (hc *HeaderChain) SetHead(head uint64, delFn DeleteCallback) {
} }
hc.currentHeaderHash = hc.CurrentHeader().Hash() hc.currentHeaderHash = hc.CurrentHeader().Hash()
if err := WriteHeadHeaderHash(hc.chainDb, hc.currentHeaderHash); err != nil { rawdb.WriteHeadHeaderHash(hc.chainDb, hc.currentHeaderHash)
log.Crit("Failed to reset head header hash", "err", err)
}
} }
// SetGenesis sets a new genesis block header for the chain // SetGenesis sets a new genesis block header for the chain
......
This diff is collapsed.
// Copyright 2018 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
package rawdb
import (
"encoding/binary"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/rlp"
)
// ReadTxLookupEntry retrieves the positional metadata associated with a transaction
// hash to allow retrieving the transaction or receipt by hash.
func ReadTxLookupEntry(db DatabaseReader, hash common.Hash) (common.Hash, uint64, uint64) {
data, _ := db.Get(append(txLookupPrefix, hash.Bytes()...))
if len(data) == 0 {
return common.Hash{}, 0, 0
}
var entry TxLookupEntry
if err := rlp.DecodeBytes(data, &entry); err != nil {
log.Error("Invalid transaction lookup entry RLP", "hash", hash, "err", err)
return common.Hash{}, 0, 0
}
return entry.BlockHash, entry.BlockIndex, entry.Index
}
// WriteTxLookupEntries stores a positional metadata for every transaction from
// a block, enabling hash based transaction and receipt lookups.
func WriteTxLookupEntries(db DatabaseWriter, block *types.Block) {
for i, tx := range block.Transactions() {
entry := TxLookupEntry{
BlockHash: block.Hash(),
BlockIndex: block.NumberU64(),
Index: uint64(i),
}
data, err := rlp.EncodeToBytes(entry)
if err != nil {
log.Crit("Failed to encode transaction lookup entry", "err", err)
}
if err := db.Put(append(txLookupPrefix, tx.Hash().Bytes()...), data); err != nil {
log.Crit("Failed to store transaction lookup entry", "err", err)
}
}
}
// DeleteTxLookupEntry removes all transaction data associated with a hash.
func DeleteTxLookupEntry(db DatabaseDeleter, hash common.Hash) {
db.Delete(append(txLookupPrefix, hash.Bytes()...))
}
// ReadTransaction retrieves a specific transaction from the database, along with
// its added positional metadata.
func ReadTransaction(db DatabaseReader, hash common.Hash) (*types.Transaction, common.Hash, uint64, uint64) {
blockHash, blockNumber, txIndex := ReadTxLookupEntry(db, hash)
if blockHash == (common.Hash{}) {
return nil, common.Hash{}, 0, 0
}
body := ReadBody(db, blockHash, blockNumber)
if body == nil || len(body.Transactions) <= int(txIndex) {
log.Error("Transaction referenced missing", "number", blockNumber, "hash", blockHash, "index", txIndex)
return nil, common.Hash{}, 0, 0
}
return body.Transactions[txIndex], blockHash, blockNumber, txIndex
}
// ReadReceipt retrieves a specific transaction receipt from the database, along with
// its added positional metadata.
func ReadReceipt(db DatabaseReader, hash common.Hash) (*types.Receipt, common.Hash, uint64, uint64) {
blockHash, blockNumber, receiptIndex := ReadTxLookupEntry(db, hash)
if blockHash == (common.Hash{}) {
return nil, common.Hash{}, 0, 0
}
receipts := ReadReceipts(db, blockHash, blockNumber)
if len(receipts) <= int(receiptIndex) {
log.Error("Receipt refereced missing", "number", blockNumber, "hash", blockHash, "index", receiptIndex)
return nil, common.Hash{}, 0, 0
}
return receipts[receiptIndex], blockHash, blockNumber, receiptIndex
}
// ReadBloomBits retrieves the compressed bloom bit vector belonging to the given
// section and bit index from the.
func ReadBloomBits(db DatabaseReader, bit uint, section uint64, head common.Hash) ([]byte, error) {
key := append(append(bloomBitsPrefix, make([]byte, 10)...), head.Bytes()...)
binary.BigEndian.PutUint16(key[1:], uint16(bit))
binary.BigEndian.PutUint64(key[3:], section)
return db.Get(key)
}
// WriteBloomBits stores the compressed bloom bits vector belonging to the given
// section and bit index.
func WriteBloomBits(db DatabaseWriter, bit uint, section uint64, head common.Hash, bits []byte) {
key := append(append(bloomBitsPrefix, make([]byte, 10)...), head.Bytes()...)
binary.BigEndian.PutUint16(key[1:], uint16(bit))
binary.BigEndian.PutUint64(key[3:], section)
if err := db.Put(key, bits); err != nil {
log.Crit("Failed to store bloom bits", "err", err)
}
}
// Copyright 2018 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
package rawdb
import (
"math/big"
"testing"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb"
)
// Tests that positional lookup metadata can be stored and retrieved.
func TestLookupStorage(t *testing.T) {
db, _ := ethdb.NewMemDatabase()
tx1 := types.NewTransaction(1, common.BytesToAddress([]byte{0x11}), big.NewInt(111), 1111, big.NewInt(11111), []byte{0x11, 0x11, 0x11})
tx2 := types.NewTransaction(2, common.BytesToAddress([]byte{0x22}), big.NewInt(222), 2222, big.NewInt(22222), []byte{0x22, 0x22, 0x22})
tx3 := types.NewTransaction(3, common.BytesToAddress([]byte{0x33}), big.NewInt(333), 3333, big.NewInt(33333), []byte{0x33, 0x33, 0x33})
txs := []*types.Transaction{tx1, tx2, tx3}
block := types.NewBlock(&types.Header{Number: big.NewInt(314)}, txs, nil, nil)
// Check that no transactions entries are in a pristine database
for i, tx := range txs {
if txn, _, _, _ := ReadTransaction(db, tx.Hash()); txn != nil {
t.Fatalf("tx #%d [%x]: non existent transaction returned: %v", i, tx.Hash(), txn)
}
}
// Insert all the transactions into the database, and verify contents
WriteBlock(db, block)
WriteTxLookupEntries(db, block)
for i, tx := range txs {
if txn, hash, number, index := ReadTransaction(db, tx.Hash()); txn == nil {
t.Fatalf("tx #%d [%x]: transaction not found", i, tx.Hash())
} else {
if hash != block.Hash() || number != block.NumberU64() || index != uint64(i) {
t.Fatalf("tx #%d [%x]: positional metadata mismatch: have %x/%d/%d, want %x/%v/%v", i, tx.Hash(), hash, number, index, block.Hash(), block.NumberU64(), i)
}
if tx.Hash() != txn.Hash() {
t.Fatalf("tx #%d [%x]: transaction mismatch: have %v, want %v", i, tx.Hash(), txn, tx)
}
}
}
// Delete the transactions and check purge
for i, tx := range txs {
DeleteTxLookupEntry(db, tx.Hash())
if txn, _, _, _ := ReadTransaction(db, tx.Hash()); txn != nil {
t.Fatalf("tx #%d [%x]: deleted transaction returned: %v", i, tx.Hash(), txn)
}
}
}
// Copyright 2018 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
package rawdb
import (
"encoding/json"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/params"
"github.com/ethereum/go-ethereum/rlp"
)
// ReadDatabaseVersion retrieves the version number of the database.
func ReadDatabaseVersion(db DatabaseReader) int {
var version int
enc, _ := db.Get(databaseVerisionKey)
rlp.DecodeBytes(enc, &version)
return version
}
// WriteDatabaseVersion stores the version number of the database
func WriteDatabaseVersion(db DatabaseWriter, version int) {
enc, _ := rlp.EncodeToBytes(version)
if err := db.Put(databaseVerisionKey, enc); err != nil {
log.Crit("Failed to store the database version", "err", err)
}
}
// ReadChainConfig retrieves the consensus settings based on the given genesis hash.
func ReadChainConfig(db DatabaseReader, hash common.Hash) *params.ChainConfig {
data, _ := db.Get(append(configPrefix, hash[:]...))
if len(data) == 0 {
return nil
}
var config params.ChainConfig
if err := json.Unmarshal(data, &config); err != nil {
log.Error("Invalid chain config JSON", "hash", hash, "err", err)
return nil
}
return &config
}
// WriteChainConfig writes the chain config settings to the database.
func WriteChainConfig(db DatabaseWriter, hash common.Hash, cfg *params.ChainConfig) {
if cfg == nil {
return
}
data, err := json.Marshal(cfg)
if err != nil {
log.Crit("Failed to JSON encode chain config", "err", err)
}
if err := db.Put(append(configPrefix, hash[:]...), data); err != nil {
log.Crit("Failed to store chain config", "err", err)
}
}
// ReadPreimage retrieves a single preimage of the provided hash.
func ReadPreimage(db DatabaseReader, hash common.Hash) []byte {
data, _ := db.Get(append(preimagePrefix, hash.Bytes()...))
return data
}
// WritePreimages writes the provided set of preimages to the database. `number` is the
// current block number, and is used for debug messages only.
func WritePreimages(db DatabaseWriter, number uint64, preimages map[common.Hash][]byte) {
for hash, preimage := range preimages {
if err := db.Put(append(preimagePrefix, hash.Bytes()...), preimage); err != nil {
log.Crit("Failed to store trie preimage", "err", err)
}
}
preimageCounter.Inc(int64(len(preimages)))
preimageHitCounter.Inc(int64(len(preimages)))
}
// Copyright 2018 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
package rawdb
// DatabaseReader wraps the Has and Get method of a backing data store.
type DatabaseReader interface {
Has(key []byte) (bool, error)
Get(key []byte) ([]byte, error)
}
// DatabaseWriter wraps the Put method of a backing data store.
type DatabaseWriter interface {
Put(key []byte, value []byte) error
}
// DatabaseDeleter wraps the Delete method of a backing data store.
type DatabaseDeleter interface {
Delete(key []byte) error
}
// Copyright 2018 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
// Package rawdb contains a collection of low level database accessors.
package rawdb
import (
"encoding/binary"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/metrics"
)
// The fields below define the low level database schema prefixing.
var (
// databaseVerisionKey tracks the current database version.
databaseVerisionKey = []byte("DatabaseVersion")
// headHeaderKey tracks the latest know header's hash.
headHeaderKey = []byte("LastHeader")
// headBlockKey tracks the latest know full block's hash.
headBlockKey = []byte("LastBlock")
// headFastBlockKey tracks the latest known incomplete block's hash duirng fast sync.
headFastBlockKey = []byte("LastFast")
// fastTrieProgressKey tracks the number of trie entries imported during fast sync.
fastTrieProgressKey = []byte("TrieSync")
// Data item prefixes (use single byte to avoid mixing data types, avoid `i`, used for indexes).
headerPrefix = []byte("h") // headerPrefix + num (uint64 big endian) + hash -> header
headerTDSuffix = []byte("t") // headerPrefix + num (uint64 big endian) + hash + headerTDSuffix -> td
headerHashSuffix = []byte("n") // headerPrefix + num (uint64 big endian) + headerHashSuffix -> hash
headerNumberPrefix = []byte("H") // headerNumberPrefix + hash -> num (uint64 big endian)
blockBodyPrefix = []byte("b") // blockBodyPrefix + num (uint64 big endian) + hash -> block body
blockReceiptsPrefix = []byte("r") // blockReceiptsPrefix + num (uint64 big endian) + hash -> block receipts
txLookupPrefix = []byte("l") // txLookupPrefix + hash -> transaction/receipt lookup metadata
bloomBitsPrefix = []byte("B") // bloomBitsPrefix + bit (uint16 big endian) + section (uint64 big endian) + hash -> bloom bits
preimagePrefix = []byte("secure-key-") // preimagePrefix + hash -> preimage
configPrefix = []byte("ethereum-config-") // config prefix for the db
// Chain index prefixes (use `i` + single byte to avoid mixing data types).
BloomBitsIndexPrefix = []byte("iB") // BloomBitsIndexPrefix is the data table of a chain indexer to track its progress
preimageCounter = metrics.NewRegisteredCounter("db/preimage/total", nil)
preimageHitCounter = metrics.NewRegisteredCounter("db/preimage/hits", nil)
)
// TxLookupEntry is a positional metadata to help looking up the data content of
// a transaction or receipt given only its hash.
type TxLookupEntry struct {
BlockHash common.Hash
BlockIndex uint64
Index uint64
}
// encodeBlockNumber encodes a block number as big endian uint64
func encodeBlockNumber(number uint64) []byte {
enc := make([]byte, 8)
binary.BigEndian.PutUint64(enc, number)
return enc
}
...@@ -19,6 +19,7 @@ package eth ...@@ -19,6 +19,7 @@ package eth
import ( import (
"compress/gzip" "compress/gzip"
"context" "context"
"errors"
"fmt" "fmt"
"io" "io"
"math/big" "math/big"
...@@ -28,6 +29,7 @@ import ( ...@@ -28,6 +29,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil" "github.com/ethereum/go-ethereum/common/hexutil"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
...@@ -343,8 +345,10 @@ func NewPrivateDebugAPI(config *params.ChainConfig, eth *Ethereum) *PrivateDebug ...@@ -343,8 +345,10 @@ func NewPrivateDebugAPI(config *params.ChainConfig, eth *Ethereum) *PrivateDebug
// Preimage is a debug API function that returns the preimage for a sha3 hash, if known. // Preimage is a debug API function that returns the preimage for a sha3 hash, if known.
func (api *PrivateDebugAPI) Preimage(ctx context.Context, hash common.Hash) (hexutil.Bytes, error) { func (api *PrivateDebugAPI) Preimage(ctx context.Context, hash common.Hash) (hexutil.Bytes, error) {
db := core.PreimageTable(api.eth.ChainDb()) if preimage := rawdb.ReadPreimage(api.eth.ChainDb(), hash); preimage != nil {
return db.Get(hash.Bytes()) return preimage, nil
}
return nil, errors.New("unknown preimage")
} }
// GetBadBLocks returns a list of the last 'bad blocks' that the client has seen on the network // GetBadBLocks returns a list of the last 'bad blocks' that the client has seen on the network
......
...@@ -25,6 +25,7 @@ import ( ...@@ -25,6 +25,7 @@ import (
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -96,16 +97,23 @@ func (b *EthApiBackend) StateAndHeaderByNumber(ctx context.Context, blockNr rpc. ...@@ -96,16 +97,23 @@ func (b *EthApiBackend) StateAndHeaderByNumber(ctx context.Context, blockNr rpc.
return stateDb, header, err return stateDb, header, err
} }
func (b *EthApiBackend) GetBlock(ctx context.Context, blockHash common.Hash) (*types.Block, error) { func (b *EthApiBackend) GetBlock(ctx context.Context, hash common.Hash) (*types.Block, error) {
return b.eth.blockchain.GetBlockByHash(blockHash), nil return b.eth.blockchain.GetBlockByHash(hash), nil
} }
func (b *EthApiBackend) GetReceipts(ctx context.Context, blockHash common.Hash) (types.Receipts, error) { func (b *EthApiBackend) GetReceipts(ctx context.Context, hash common.Hash) (types.Receipts, error) {
return core.GetBlockReceipts(b.eth.chainDb, blockHash, core.GetBlockNumber(b.eth.chainDb, blockHash)), nil if number := rawdb.ReadHeaderNumber(b.eth.chainDb, hash); number != nil {
return rawdb.ReadReceipts(b.eth.chainDb, hash, *number), nil
}
return nil, nil
} }
func (b *EthApiBackend) GetLogs(ctx context.Context, blockHash common.Hash) ([][]*types.Log, error) { func (b *EthApiBackend) GetLogs(ctx context.Context, hash common.Hash) ([][]*types.Log, error) {
receipts := core.GetBlockReceipts(b.eth.chainDb, blockHash, core.GetBlockNumber(b.eth.chainDb, blockHash)) number := rawdb.ReadHeaderNumber(b.eth.chainDb, hash)
if number == nil {
return nil, nil
}
receipts := rawdb.ReadReceipts(b.eth.chainDb, hash, *number)
if receipts == nil { if receipts == nil {
return nil, nil return nil, nil
} }
......
...@@ -29,6 +29,7 @@ import ( ...@@ -29,6 +29,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil" "github.com/ethereum/go-ethereum/common/hexutil"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -533,7 +534,7 @@ func (api *PrivateDebugAPI) computeStateDB(block *types.Block, reexec uint64) (* ...@@ -533,7 +534,7 @@ func (api *PrivateDebugAPI) computeStateDB(block *types.Block, reexec uint64) (*
// and returns them as a JSON object. // and returns them as a JSON object.
func (api *PrivateDebugAPI) TraceTransaction(ctx context.Context, hash common.Hash, config *TraceConfig) (interface{}, error) { func (api *PrivateDebugAPI) TraceTransaction(ctx context.Context, hash common.Hash, config *TraceConfig) (interface{}, error) {
// Retrieve the transaction and assemble its EVM context // Retrieve the transaction and assemble its EVM context
tx, blockHash, _, index := core.GetTransaction(api.eth.ChainDb(), hash) tx, blockHash, _, index := rawdb.ReadTransaction(api.eth.ChainDb(), hash)
if tx == nil { if tx == nil {
return nil, fmt.Errorf("transaction %x not found", hash) return nil, fmt.Errorf("transaction %x not found", hash)
} }
......
...@@ -33,6 +33,7 @@ import ( ...@@ -33,6 +33,7 @@ import (
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
"github.com/ethereum/go-ethereum/eth/downloader" "github.com/ethereum/go-ethereum/eth/downloader"
...@@ -64,7 +65,6 @@ type Ethereum struct { ...@@ -64,7 +65,6 @@ type Ethereum struct {
// Channel for shutting down the service // Channel for shutting down the service
shutdownChan chan bool // Channel for shutting down the Ethereum shutdownChan chan bool // Channel for shutting down the Ethereum
stopDbUpgrade func() error // stop chain db sequential key upgrade
// Handlers // Handlers
txPool *core.TxPool txPool *core.TxPool
...@@ -112,7 +112,6 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) { ...@@ -112,7 +112,6 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
if err != nil { if err != nil {
return nil, err return nil, err
} }
stopDbUpgrade := upgradeDeduplicateData(chainDb)
chainConfig, genesisHash, genesisErr := core.SetupGenesisBlock(chainDb, config.Genesis) chainConfig, genesisHash, genesisErr := core.SetupGenesisBlock(chainDb, config.Genesis)
if _, ok := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !ok { if _, ok := genesisErr.(*params.ConfigCompatError); genesisErr != nil && !ok {
return nil, genesisErr return nil, genesisErr
...@@ -127,7 +126,6 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) { ...@@ -127,7 +126,6 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
accountManager: ctx.AccountManager, accountManager: ctx.AccountManager,
engine: CreateConsensusEngine(ctx, &config.Ethash, chainConfig, chainDb), engine: CreateConsensusEngine(ctx, &config.Ethash, chainConfig, chainDb),
shutdownChan: make(chan bool), shutdownChan: make(chan bool),
stopDbUpgrade: stopDbUpgrade,
networkId: config.NetworkId, networkId: config.NetworkId,
gasPrice: config.GasPrice, gasPrice: config.GasPrice,
etherbase: config.Etherbase, etherbase: config.Etherbase,
...@@ -138,11 +136,11 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) { ...@@ -138,11 +136,11 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
log.Info("Initialising Ethereum protocol", "versions", ProtocolVersions, "network", config.NetworkId) log.Info("Initialising Ethereum protocol", "versions", ProtocolVersions, "network", config.NetworkId)
if !config.SkipBcVersionCheck { if !config.SkipBcVersionCheck {
bcVersion := core.GetBlockChainVersion(chainDb) bcVersion := rawdb.ReadDatabaseVersion(chainDb)
if bcVersion != core.BlockChainVersion && bcVersion != 0 { if bcVersion != core.BlockChainVersion && bcVersion != 0 {
return nil, fmt.Errorf("Blockchain DB version mismatch (%d / %d). Run geth upgradedb.\n", bcVersion, core.BlockChainVersion) return nil, fmt.Errorf("Blockchain DB version mismatch (%d / %d). Run geth upgradedb.\n", bcVersion, core.BlockChainVersion)
} }
core.WriteBlockChainVersion(chainDb, core.BlockChainVersion) rawdb.WriteDatabaseVersion(chainDb, core.BlockChainVersion)
} }
var ( var (
vmConfig = vm.Config{EnablePreimageRecording: config.EnablePreimageRecording} vmConfig = vm.Config{EnablePreimageRecording: config.EnablePreimageRecording}
...@@ -156,7 +154,7 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) { ...@@ -156,7 +154,7 @@ func New(ctx *node.ServiceContext, config *Config) (*Ethereum, error) {
if compat, ok := genesisErr.(*params.ConfigCompatError); ok { if compat, ok := genesisErr.(*params.ConfigCompatError); ok {
log.Warn("Rewinding chain to upgrade configuration", "err", compat) log.Warn("Rewinding chain to upgrade configuration", "err", compat)
eth.blockchain.SetHead(compat.RewindTo) eth.blockchain.SetHead(compat.RewindTo)
core.WriteChainConfig(chainDb, genesisHash, chainConfig) rawdb.WriteChainConfig(chainDb, genesisHash, chainConfig)
} }
eth.bloomIndexer.Start(eth.blockchain) eth.bloomIndexer.Start(eth.blockchain)
...@@ -411,9 +409,6 @@ func (s *Ethereum) Start(srvr *p2p.Server) error { ...@@ -411,9 +409,6 @@ func (s *Ethereum) Start(srvr *p2p.Server) error {
// Stop implements node.Service, terminating all internal goroutines used by the // Stop implements node.Service, terminating all internal goroutines used by the
// Ethereum protocol. // Ethereum protocol.
func (s *Ethereum) Stop() error { func (s *Ethereum) Stop() error {
if s.stopDbUpgrade != nil {
s.stopDbUpgrade()
}
s.bloomIndexer.Close() s.bloomIndexer.Close()
s.blockchain.Stop() s.blockchain.Stop()
s.protocolManager.Stop() s.protocolManager.Stop()
......
...@@ -23,6 +23,7 @@ import ( ...@@ -23,6 +23,7 @@ import (
"github.com/ethereum/go-ethereum/common/bitutil" "github.com/ethereum/go-ethereum/common/bitutil"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
...@@ -60,8 +61,8 @@ func (eth *Ethereum) startBloomHandlers() { ...@@ -60,8 +61,8 @@ func (eth *Ethereum) startBloomHandlers() {
task := <-request task := <-request
task.Bitsets = make([][]byte, len(task.Sections)) task.Bitsets = make([][]byte, len(task.Sections))
for i, section := range task.Sections { for i, section := range task.Sections {
head := core.GetCanonicalHash(eth.chainDb, (section+1)*params.BloomBitsBlocks-1) head := rawdb.ReadCanonicalHash(eth.chainDb, (section+1)*params.BloomBitsBlocks-1)
if compVector, err := core.GetBloomBits(eth.chainDb, task.Bit, section, head); err == nil { if compVector, err := rawdb.ReadBloomBits(eth.chainDb, task.Bit, section, head); err == nil {
if blob, err := bitutil.DecompressBytes(compVector, int(params.BloomBitsBlocks)/8); err == nil { if blob, err := bitutil.DecompressBytes(compVector, int(params.BloomBitsBlocks)/8); err == nil {
task.Bitsets[i] = blob task.Bitsets[i] = blob
} else { } else {
...@@ -107,7 +108,7 @@ func NewBloomIndexer(db ethdb.Database, size uint64) *core.ChainIndexer { ...@@ -107,7 +108,7 @@ func NewBloomIndexer(db ethdb.Database, size uint64) *core.ChainIndexer {
db: db, db: db,
size: size, size: size,
} }
table := ethdb.NewTable(db, string(core.BloomBitsIndexPrefix)) table := ethdb.NewTable(db, string(rawdb.BloomBitsIndexPrefix))
return core.NewChainIndexer(db, table, backend, size, bloomConfirms, bloomThrottling, "bloombits") return core.NewChainIndexer(db, table, backend, size, bloomConfirms, bloomThrottling, "bloombits")
} }
...@@ -137,7 +138,7 @@ func (b *BloomIndexer) Commit() error { ...@@ -137,7 +138,7 @@ func (b *BloomIndexer) Commit() error {
if err != nil { if err != nil {
return err return err
} }
core.WriteBloomBits(batch, uint(i), b.section, b.head, bitutil.CompressBytes(bits)) rawdb.WriteBloomBits(batch, uint(i), b.section, b.head, bitutil.CompressBytes(bits))
} }
return batch.Write() return batch.Write()
} }
// Copyright 2016 The go-ethereum Authors
// This file is part of the go-ethereum library.
//
// The go-ethereum library is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// The go-ethereum library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
// Package eth implements the Ethereum protocol.
package eth
import (
"bytes"
"time"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/rlp"
)
var deduplicateData = []byte("dbUpgrade_20170714deduplicateData")
// upgradeDeduplicateData checks the chain database version and
// starts a background process to make upgrades if necessary.
// Returns a stop function that blocks until the process has
// been safely stopped.
func upgradeDeduplicateData(db ethdb.Database) func() error {
// If the database is already converted or empty, bail out
data, _ := db.Get(deduplicateData)
if len(data) > 0 && data[0] == 42 {
return nil
}
if data, _ := db.Get([]byte("LastHeader")); len(data) == 0 {
db.Put(deduplicateData, []byte{42})
return nil
}
// Start the deduplication upgrade on a new goroutine
log.Warn("Upgrading database to use lookup entries")
stop := make(chan chan error)
go func() {
// Create an iterator to read the entire database and covert old lookup entires
it := db.(*ethdb.LDBDatabase).NewIterator()
defer func() {
if it != nil {
it.Release()
}
}()
var (
converted uint64
failed error
)
for failed == nil && it.Next() {
// Skip any entries that don't look like old transaction meta entries (<hash>0x01)
key := it.Key()
if len(key) != common.HashLength+1 || key[common.HashLength] != 0x01 {
continue
}
// Skip any entries that don't contain metadata (name clash between <hash>0x01 and <some-prefix><hash>)
var meta struct {
BlockHash common.Hash
BlockIndex uint64
Index uint64
}
if err := rlp.DecodeBytes(it.Value(), &meta); err != nil {
continue
}
// Skip any already upgraded entries (clash due to <hash> ending with 0x01 (old suffix))
hash := key[:common.HashLength]
if hash[0] == byte('l') {
// Potential clash, the "old" `hash` must point to a live transaction.
if tx, _, _, _ := core.GetTransaction(db, common.BytesToHash(hash)); tx == nil || !bytes.Equal(tx.Hash().Bytes(), hash) {
continue
}
}
// Convert the old metadata to a new lookup entry, delete duplicate data
if failed = db.Put(append([]byte("l"), hash...), it.Value()); failed == nil { // Write the new lookup entry
if failed = db.Delete(hash); failed == nil { // Delete the duplicate transaction data
if failed = db.Delete(append([]byte("receipts-"), hash...)); failed == nil { // Delete the duplicate receipt data
if failed = db.Delete(key); failed != nil { // Delete the old transaction metadata
break
}
}
}
}
// Bump the conversion counter, and recreate the iterator occasionally to
// avoid too high memory consumption.
converted++
if converted%100000 == 0 {
it.Release()
it = db.(*ethdb.LDBDatabase).NewIterator()
it.Seek(key)
log.Info("Deduplicating database entries", "deduped", converted)
}
// Check for termination, or continue after a bit of a timeout
select {
case errc := <-stop:
errc <- nil
return
case <-time.After(time.Microsecond * 100):
}
}
// Upgrade finished, mark a such and terminate
if failed == nil {
log.Info("Database deduplication successful", "deduped", converted)
db.Put(deduplicateData, []byte{42})
} else {
log.Error("Database deduplication failed", "deduped", converted, "err", failed)
}
it.Release()
it = nil
errc := <-stop
errc <- failed
}()
// Assembly the cancellation callback
return func() error {
errc := make(chan error)
stop <- errc
return <-errc
}
}
...@@ -27,7 +27,7 @@ import ( ...@@ -27,7 +27,7 @@ import (
ethereum "github.com/ethereum/go-ethereum" ethereum "github.com/ethereum/go-ethereum"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/event" "github.com/ethereum/go-ethereum/event"
...@@ -224,7 +224,7 @@ func New(mode SyncMode, stateDb ethdb.Database, mux *event.TypeMux, chain BlockC ...@@ -224,7 +224,7 @@ func New(mode SyncMode, stateDb ethdb.Database, mux *event.TypeMux, chain BlockC
stateCh: make(chan dataPack), stateCh: make(chan dataPack),
stateSyncStart: make(chan *stateSync), stateSyncStart: make(chan *stateSync),
syncStatsState: stateSyncStats{ syncStatsState: stateSyncStats{
processed: core.GetTrieSyncProgress(stateDb), processed: rawdb.ReadFastTrieProgress(stateDb),
}, },
trackStateReq: make(chan *stateReq), trackStateReq: make(chan *stateReq),
} }
......
...@@ -21,6 +21,7 @@ import ( ...@@ -21,6 +21,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
) )
...@@ -126,7 +127,7 @@ func (p *FakePeer) RequestBodies(hashes []common.Hash) error { ...@@ -126,7 +127,7 @@ func (p *FakePeer) RequestBodies(hashes []common.Hash) error {
uncles [][]*types.Header uncles [][]*types.Header
) )
for _, hash := range hashes { for _, hash := range hashes {
block := core.GetBlock(p.db, hash, p.hc.GetBlockNumber(hash)) block := rawdb.ReadBlock(p.db, hash, *p.hc.GetBlockNumber(hash))
txs = append(txs, block.Transactions()) txs = append(txs, block.Transactions())
uncles = append(uncles, block.Uncles()) uncles = append(uncles, block.Uncles())
...@@ -140,7 +141,7 @@ func (p *FakePeer) RequestBodies(hashes []common.Hash) error { ...@@ -140,7 +141,7 @@ func (p *FakePeer) RequestBodies(hashes []common.Hash) error {
func (p *FakePeer) RequestReceipts(hashes []common.Hash) error { func (p *FakePeer) RequestReceipts(hashes []common.Hash) error {
var receipts [][]*types.Receipt var receipts [][]*types.Receipt
for _, hash := range hashes { for _, hash := range hashes {
receipts = append(receipts, core.GetBlockReceipts(p.db, hash, p.hc.GetBlockNumber(hash))) receipts = append(receipts, rawdb.ReadReceipts(p.db, hash, *p.hc.GetBlockNumber(hash)))
} }
p.dl.DeliverReceipts(p.id, receipts) p.dl.DeliverReceipts(p.id, receipts)
return nil return nil
......
...@@ -23,7 +23,7 @@ import ( ...@@ -23,7 +23,7 @@ import (
"time" "time"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/crypto/sha3" "github.com/ethereum/go-ethereum/crypto/sha3"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -476,6 +476,6 @@ func (s *stateSync) updateStats(written, duplicate, unexpected int, duration tim ...@@ -476,6 +476,6 @@ func (s *stateSync) updateStats(written, duplicate, unexpected int, duration tim
log.Info("Imported new state entries", "count", written, "elapsed", common.PrettyDuration(duration), "processed", s.d.syncStatsState.processed, "pending", s.d.syncStatsState.pending, "retry", len(s.tasks), "duplicate", s.d.syncStatsState.duplicate, "unexpected", s.d.syncStatsState.unexpected) log.Info("Imported new state entries", "count", written, "elapsed", common.PrettyDuration(duration), "processed", s.d.syncStatsState.processed, "pending", s.d.syncStatsState.pending, "retry", len(s.tasks), "duplicate", s.d.syncStatsState.duplicate, "unexpected", s.d.syncStatsState.unexpected)
} }
if written > 0 { if written > 0 {
core.WriteTrieSyncProgress(s.d.stateDB, s.d.syncStatsState.processed) rawdb.WriteFastTrieProgress(s.d.stateDB, s.d.syncStatsState.processed)
} }
} }
...@@ -25,8 +25,8 @@ import ( ...@@ -25,8 +25,8 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/bitutil" "github.com/ethereum/go-ethereum/common/bitutil"
"github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/event" "github.com/ethereum/go-ethereum/event"
...@@ -71,20 +71,20 @@ func benchmarkBloomBits(b *testing.B, sectionSize uint64) { ...@@ -71,20 +71,20 @@ func benchmarkBloomBits(b *testing.B, sectionSize uint64) {
if err != nil { if err != nil {
b.Fatalf("error opening database at %v: %v", benchDataDir, err) b.Fatalf("error opening database at %v: %v", benchDataDir, err)
} }
head := core.GetHeadBlockHash(db) head := rawdb.ReadHeadBlockHash(db)
if head == (common.Hash{}) { if head == (common.Hash{}) {
b.Fatalf("chain data not found at %v", benchDataDir) b.Fatalf("chain data not found at %v", benchDataDir)
} }
clearBloomBits(db) clearBloomBits(db)
fmt.Println("Generating bloombits data...") fmt.Println("Generating bloombits data...")
headNum := core.GetBlockNumber(db, head) headNum := rawdb.ReadHeaderNumber(db, head)
if headNum < sectionSize+512 { if headNum == nil || *headNum < sectionSize+512 {
b.Fatalf("not enough blocks for running a benchmark") b.Fatalf("not enough blocks for running a benchmark")
} }
start := time.Now() start := time.Now()
cnt := (headNum - 512) / sectionSize cnt := (*headNum - 512) / sectionSize
var dataSize, compSize uint64 var dataSize, compSize uint64
for sectionIdx := uint64(0); sectionIdx < cnt; sectionIdx++ { for sectionIdx := uint64(0); sectionIdx < cnt; sectionIdx++ {
bc, err := bloombits.NewGenerator(uint(sectionSize)) bc, err := bloombits.NewGenerator(uint(sectionSize))
...@@ -93,14 +93,14 @@ func benchmarkBloomBits(b *testing.B, sectionSize uint64) { ...@@ -93,14 +93,14 @@ func benchmarkBloomBits(b *testing.B, sectionSize uint64) {
} }
var header *types.Header var header *types.Header
for i := sectionIdx * sectionSize; i < (sectionIdx+1)*sectionSize; i++ { for i := sectionIdx * sectionSize; i < (sectionIdx+1)*sectionSize; i++ {
hash := core.GetCanonicalHash(db, i) hash := rawdb.ReadCanonicalHash(db, i)
header = core.GetHeader(db, hash, i) header = rawdb.ReadHeader(db, hash, i)
if header == nil { if header == nil {
b.Fatalf("Error creating bloomBits data") b.Fatalf("Error creating bloomBits data")
} }
bc.AddBloom(uint(i-sectionIdx*sectionSize), header.Bloom) bc.AddBloom(uint(i-sectionIdx*sectionSize), header.Bloom)
} }
sectionHead := core.GetCanonicalHash(db, (sectionIdx+1)*sectionSize-1) sectionHead := rawdb.ReadCanonicalHash(db, (sectionIdx+1)*sectionSize-1)
for i := 0; i < types.BloomBitLength; i++ { for i := 0; i < types.BloomBitLength; i++ {
data, err := bc.Bitset(uint(i)) data, err := bc.Bitset(uint(i))
if err != nil { if err != nil {
...@@ -109,7 +109,7 @@ func benchmarkBloomBits(b *testing.B, sectionSize uint64) { ...@@ -109,7 +109,7 @@ func benchmarkBloomBits(b *testing.B, sectionSize uint64) {
comp := bitutil.CompressBytes(data) comp := bitutil.CompressBytes(data)
dataSize += uint64(len(data)) dataSize += uint64(len(data))
compSize += uint64(len(comp)) compSize += uint64(len(comp))
core.WriteBloomBits(db, uint(i), sectionIdx, sectionHead, comp) rawdb.WriteBloomBits(db, uint(i), sectionIdx, sectionHead, comp)
} }
//if sectionIdx%50 == 0 { //if sectionIdx%50 == 0 {
// fmt.Println(" section", sectionIdx, "/", cnt) // fmt.Println(" section", sectionIdx, "/", cnt)
...@@ -180,11 +180,11 @@ func BenchmarkNoBloomBits(b *testing.B) { ...@@ -180,11 +180,11 @@ func BenchmarkNoBloomBits(b *testing.B) {
if err != nil { if err != nil {
b.Fatalf("error opening database at %v: %v", benchDataDir, err) b.Fatalf("error opening database at %v: %v", benchDataDir, err)
} }
head := core.GetHeadBlockHash(db) head := rawdb.ReadHeadBlockHash(db)
if head == (common.Hash{}) { if head == (common.Hash{}) {
b.Fatalf("chain data not found at %v", benchDataDir) b.Fatalf("chain data not found at %v", benchDataDir)
} }
headNum := core.GetBlockNumber(db, head) headNum := rawdb.ReadHeaderNumber(db, head)
clearBloomBits(db) clearBloomBits(db)
...@@ -192,10 +192,10 @@ func BenchmarkNoBloomBits(b *testing.B) { ...@@ -192,10 +192,10 @@ func BenchmarkNoBloomBits(b *testing.B) {
start := time.Now() start := time.Now()
mux := new(event.TypeMux) mux := new(event.TypeMux)
backend := &testBackend{mux, db, 0, new(event.Feed), new(event.Feed), new(event.Feed), new(event.Feed)} backend := &testBackend{mux, db, 0, new(event.Feed), new(event.Feed), new(event.Feed), new(event.Feed)}
filter := New(backend, 0, int64(headNum), []common.Address{{}}, nil) filter := New(backend, 0, int64(*headNum), []common.Address{{}}, nil)
filter.Logs(context.Background()) filter.Logs(context.Background())
d := time.Since(start) d := time.Since(start)
fmt.Println("Finished running filter benchmarks") fmt.Println("Finished running filter benchmarks")
fmt.Println(" ", d, "total ", d*time.Duration(1000000)/time.Duration(headNum+1), "per million blocks") fmt.Println(" ", d, "total ", d*time.Duration(1000000)/time.Duration(*headNum+1), "per million blocks")
db.Close() db.Close()
} }
...@@ -28,6 +28,7 @@ import ( ...@@ -28,6 +28,7 @@ import (
ethereum "github.com/ethereum/go-ethereum" ethereum "github.com/ethereum/go-ethereum"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/event" "github.com/ethereum/go-ethereum/event"
"github.com/ethereum/go-ethereum/rpc" "github.com/ethereum/go-ethereum/rpc"
...@@ -348,11 +349,11 @@ func (es *EventSystem) lightFilterNewHead(newHeader *types.Header, callBack func ...@@ -348,11 +349,11 @@ func (es *EventSystem) lightFilterNewHead(newHeader *types.Header, callBack func
for oldh.Hash() != newh.Hash() { for oldh.Hash() != newh.Hash() {
if oldh.Number.Uint64() >= newh.Number.Uint64() { if oldh.Number.Uint64() >= newh.Number.Uint64() {
oldHeaders = append(oldHeaders, oldh) oldHeaders = append(oldHeaders, oldh)
oldh = core.GetHeader(es.backend.ChainDb(), oldh.ParentHash, oldh.Number.Uint64()-1) oldh = rawdb.ReadHeader(es.backend.ChainDb(), oldh.ParentHash, oldh.Number.Uint64()-1)
} }
if oldh.Number.Uint64() < newh.Number.Uint64() { if oldh.Number.Uint64() < newh.Number.Uint64() {
newHeaders = append(newHeaders, newh) newHeaders = append(newHeaders, newh)
newh = core.GetHeader(es.backend.ChainDb(), newh.ParentHash, newh.Number.Uint64()-1) newh = rawdb.ReadHeader(es.backend.ChainDb(), newh.ParentHash, newh.Number.Uint64()-1)
if newh == nil { if newh == nil {
// happens when CHT syncing, nothing to do // happens when CHT syncing, nothing to do
newh = oldh newh = oldh
......
...@@ -30,6 +30,7 @@ import ( ...@@ -30,6 +30,7 @@ import (
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/event" "github.com/ethereum/go-ethereum/event"
...@@ -56,26 +57,37 @@ func (b *testBackend) EventMux() *event.TypeMux { ...@@ -56,26 +57,37 @@ func (b *testBackend) EventMux() *event.TypeMux {
} }
func (b *testBackend) HeaderByNumber(ctx context.Context, blockNr rpc.BlockNumber) (*types.Header, error) { func (b *testBackend) HeaderByNumber(ctx context.Context, blockNr rpc.BlockNumber) (*types.Header, error) {
var hash common.Hash var (
var num uint64 hash common.Hash
num uint64
)
if blockNr == rpc.LatestBlockNumber { if blockNr == rpc.LatestBlockNumber {
hash = core.GetHeadBlockHash(b.db) hash = rawdb.ReadHeadBlockHash(b.db)
num = core.GetBlockNumber(b.db, hash) number := rawdb.ReadHeaderNumber(b.db, hash)
if number == nil {
return nil, nil
}
num = *number
} else { } else {
num = uint64(blockNr) num = uint64(blockNr)
hash = core.GetCanonicalHash(b.db, num) hash = rawdb.ReadCanonicalHash(b.db, num)
} }
return core.GetHeader(b.db, hash, num), nil return rawdb.ReadHeader(b.db, hash, num), nil
} }
func (b *testBackend) GetReceipts(ctx context.Context, blockHash common.Hash) (types.Receipts, error) { func (b *testBackend) GetReceipts(ctx context.Context, hash common.Hash) (types.Receipts, error) {
number := core.GetBlockNumber(b.db, blockHash) if number := rawdb.ReadHeaderNumber(b.db, hash); number != nil {
return core.GetBlockReceipts(b.db, blockHash, number), nil return rawdb.ReadReceipts(b.db, hash, *number), nil
}
return nil, nil
} }
func (b *testBackend) GetLogs(ctx context.Context, blockHash common.Hash) ([][]*types.Log, error) { func (b *testBackend) GetLogs(ctx context.Context, hash common.Hash) ([][]*types.Log, error) {
number := core.GetBlockNumber(b.db, blockHash) number := rawdb.ReadHeaderNumber(b.db, hash)
receipts := core.GetBlockReceipts(b.db, blockHash, number) if number == nil {
return nil, nil
}
receipts := rawdb.ReadReceipts(b.db, hash, *number)
logs := make([][]*types.Log, len(receipts)) logs := make([][]*types.Log, len(receipts))
for i, receipt := range receipts { for i, receipt := range receipts {
...@@ -121,8 +133,8 @@ func (b *testBackend) ServiceFilter(ctx context.Context, session *bloombits.Matc ...@@ -121,8 +133,8 @@ func (b *testBackend) ServiceFilter(ctx context.Context, session *bloombits.Matc
task.Bitsets = make([][]byte, len(task.Sections)) task.Bitsets = make([][]byte, len(task.Sections))
for i, section := range task.Sections { for i, section := range task.Sections {
if rand.Int()%4 != 0 { // Handle occasional missing deliveries if rand.Int()%4 != 0 { // Handle occasional missing deliveries
head := core.GetCanonicalHash(b.db, (section+1)*params.BloomBitsBlocks-1) head := rawdb.ReadCanonicalHash(b.db, (section+1)*params.BloomBitsBlocks-1)
task.Bitsets[i], _ = core.GetBloomBits(b.db, task.Bit, section, head) task.Bitsets[i], _ = rawdb.ReadBloomBits(b.db, task.Bit, section, head)
} }
} }
request <- task request <- task
......
...@@ -26,6 +26,7 @@ import ( ...@@ -26,6 +26,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -84,16 +85,10 @@ func BenchmarkFilters(b *testing.B) { ...@@ -84,16 +85,10 @@ func BenchmarkFilters(b *testing.B) {
} }
}) })
for i, block := range chain { for i, block := range chain {
core.WriteBlock(db, block) rawdb.WriteBlock(db, block)
if err := core.WriteCanonicalHash(db, block.Hash(), block.NumberU64()); err != nil { rawdb.WriteCanonicalHash(db, block.Hash(), block.NumberU64())
b.Fatalf("failed to insert block number: %v", err) rawdb.WriteHeadBlockHash(db, block.Hash())
} rawdb.WriteReceipts(db, block.Hash(), block.NumberU64(), receipts[i])
if err := core.WriteHeadBlockHash(db, block.Hash()); err != nil {
b.Fatalf("failed to insert block number: %v", err)
}
if err := core.WriteBlockReceipts(db, block.Hash(), block.NumberU64(), receipts[i]); err != nil {
b.Fatal("error writing block receipts:", err)
}
} }
b.ResetTimer() b.ResetTimer()
...@@ -174,16 +169,10 @@ func TestFilters(t *testing.T) { ...@@ -174,16 +169,10 @@ func TestFilters(t *testing.T) {
} }
}) })
for i, block := range chain { for i, block := range chain {
core.WriteBlock(db, block) rawdb.WriteBlock(db, block)
if err := core.WriteCanonicalHash(db, block.Hash(), block.NumberU64()); err != nil { rawdb.WriteCanonicalHash(db, block.Hash(), block.NumberU64())
t.Fatalf("failed to insert block number: %v", err) rawdb.WriteHeadBlockHash(db, block.Hash())
} rawdb.WriteReceipts(db, block.Hash(), block.NumberU64(), receipts[i])
if err := core.WriteHeadBlockHash(db, block.Hash()); err != nil {
t.Fatalf("failed to insert block number: %v", err)
}
if err := core.WriteBlockReceipts(db, block.Hash(), block.NumberU64(), receipts[i]); err != nil {
t.Fatal("error writing block receipts:", err)
}
} }
filter := New(backend, 0, -1, []common.Address{addr}, [][]common.Hash{{hash1, hash2, hash3, hash4}}) filter := New(backend, 0, -1, []common.Address{addr}, [][]common.Hash{{hash1, hash2, hash3, hash4}})
......
...@@ -33,6 +33,7 @@ import ( ...@@ -33,6 +33,7 @@ import (
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
...@@ -1006,7 +1007,7 @@ func (s *PublicTransactionPoolAPI) GetTransactionCount(ctx context.Context, addr ...@@ -1006,7 +1007,7 @@ func (s *PublicTransactionPoolAPI) GetTransactionCount(ctx context.Context, addr
// GetTransactionByHash returns the transaction for the given hash // GetTransactionByHash returns the transaction for the given hash
func (s *PublicTransactionPoolAPI) GetTransactionByHash(ctx context.Context, hash common.Hash) *RPCTransaction { func (s *PublicTransactionPoolAPI) GetTransactionByHash(ctx context.Context, hash common.Hash) *RPCTransaction {
// Try to return an already finalized transaction // Try to return an already finalized transaction
if tx, blockHash, blockNumber, index := core.GetTransaction(s.b.ChainDb(), hash); tx != nil { if tx, blockHash, blockNumber, index := rawdb.ReadTransaction(s.b.ChainDb(), hash); tx != nil {
return newRPCTransaction(tx, blockHash, blockNumber, index) return newRPCTransaction(tx, blockHash, blockNumber, index)
} }
// No finalized transaction, try to retrieve it from the pool // No finalized transaction, try to retrieve it from the pool
...@@ -1022,7 +1023,7 @@ func (s *PublicTransactionPoolAPI) GetRawTransactionByHash(ctx context.Context, ...@@ -1022,7 +1023,7 @@ func (s *PublicTransactionPoolAPI) GetRawTransactionByHash(ctx context.Context,
var tx *types.Transaction var tx *types.Transaction
// Retrieve a finalized transaction, or a pooled otherwise // Retrieve a finalized transaction, or a pooled otherwise
if tx, _, _, _ = core.GetTransaction(s.b.ChainDb(), hash); tx == nil { if tx, _, _, _ = rawdb.ReadTransaction(s.b.ChainDb(), hash); tx == nil {
if tx = s.b.GetPoolTransaction(hash); tx == nil { if tx = s.b.GetPoolTransaction(hash); tx == nil {
// Transaction not found anywhere, abort // Transaction not found anywhere, abort
return nil, nil return nil, nil
...@@ -1034,7 +1035,7 @@ func (s *PublicTransactionPoolAPI) GetRawTransactionByHash(ctx context.Context, ...@@ -1034,7 +1035,7 @@ func (s *PublicTransactionPoolAPI) GetRawTransactionByHash(ctx context.Context,
// GetTransactionReceipt returns the transaction receipt for the given transaction hash. // GetTransactionReceipt returns the transaction receipt for the given transaction hash.
func (s *PublicTransactionPoolAPI) GetTransactionReceipt(ctx context.Context, hash common.Hash) (map[string]interface{}, error) { func (s *PublicTransactionPoolAPI) GetTransactionReceipt(ctx context.Context, hash common.Hash) (map[string]interface{}, error) {
tx, blockHash, blockNumber, index := core.GetTransaction(s.b.ChainDb(), hash) tx, blockHash, blockNumber, index := rawdb.ReadTransaction(s.b.ChainDb(), hash)
if tx == nil { if tx == nil {
return nil, nil return nil, nil
} }
......
...@@ -25,6 +25,7 @@ import ( ...@@ -25,6 +25,7 @@ import (
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -83,16 +84,22 @@ func (b *LesApiBackend) GetBlock(ctx context.Context, blockHash common.Hash) (*t ...@@ -83,16 +84,22 @@ func (b *LesApiBackend) GetBlock(ctx context.Context, blockHash common.Hash) (*t
return b.eth.blockchain.GetBlockByHash(ctx, blockHash) return b.eth.blockchain.GetBlockByHash(ctx, blockHash)
} }
func (b *LesApiBackend) GetReceipts(ctx context.Context, blockHash common.Hash) (types.Receipts, error) { func (b *LesApiBackend) GetReceipts(ctx context.Context, hash common.Hash) (types.Receipts, error) {
return light.GetBlockReceipts(ctx, b.eth.odr, blockHash, core.GetBlockNumber(b.eth.chainDb, blockHash)) if number := rawdb.ReadHeaderNumber(b.eth.chainDb, hash); number != nil {
return light.GetBlockReceipts(ctx, b.eth.odr, hash, *number)
}
return nil, nil
} }
func (b *LesApiBackend) GetLogs(ctx context.Context, blockHash common.Hash) ([][]*types.Log, error) { func (b *LesApiBackend) GetLogs(ctx context.Context, hash common.Hash) ([][]*types.Log, error) {
return light.GetBlockLogs(ctx, b.eth.odr, blockHash, core.GetBlockNumber(b.eth.chainDb, blockHash)) if number := rawdb.ReadHeaderNumber(b.eth.chainDb, hash); number != nil {
return light.GetBlockLogs(ctx, b.eth.odr, hash, *number)
}
return nil, nil
} }
func (b *LesApiBackend) GetTd(blockHash common.Hash) *big.Int { func (b *LesApiBackend) GetTd(hash common.Hash) *big.Int {
return b.eth.blockchain.GetTdByHash(blockHash) return b.eth.blockchain.GetTdByHash(hash)
} }
func (b *LesApiBackend) GetEVM(ctx context.Context, msg core.Message, state *state.StateDB, header *types.Header, vmCfg vm.Config) (*vm.EVM, func() error, error) { func (b *LesApiBackend) GetEVM(ctx context.Context, msg core.Message, state *state.StateDB, header *types.Header, vmCfg vm.Config) (*vm.EVM, func() error, error) {
......
...@@ -28,6 +28,7 @@ import ( ...@@ -28,6 +28,7 @@ import (
"github.com/ethereum/go-ethereum/consensus" "github.com/ethereum/go-ethereum/consensus"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/bloombits" "github.com/ethereum/go-ethereum/core/bloombits"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/eth" "github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/eth/downloader" "github.com/ethereum/go-ethereum/eth/downloader"
...@@ -122,7 +123,7 @@ func New(ctx *node.ServiceContext, config *eth.Config) (*LightEthereum, error) { ...@@ -122,7 +123,7 @@ func New(ctx *node.ServiceContext, config *eth.Config) (*LightEthereum, error) {
if compat, ok := genesisErr.(*params.ConfigCompatError); ok { if compat, ok := genesisErr.(*params.ConfigCompatError); ok {
log.Warn("Rewinding chain to upgrade configuration", "err", compat) log.Warn("Rewinding chain to upgrade configuration", "err", compat)
leth.blockchain.SetHead(compat.RewindTo) leth.blockchain.SetHead(compat.RewindTo)
core.WriteChainConfig(chainDb, genesisHash, chainConfig) rawdb.WriteChainConfig(chainDb, genesisHash, chainConfig)
} }
leth.txPool = light.NewTxPool(leth.chainConfig, leth.blockchain, leth.relay) leth.txPool = light.NewTxPool(leth.chainConfig, leth.blockchain, leth.relay)
......
...@@ -25,7 +25,7 @@ import ( ...@@ -25,7 +25,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/mclock" "github.com/ethereum/go-ethereum/common/mclock"
"github.com/ethereum/go-ethereum/consensus" "github.com/ethereum/go-ethereum/consensus"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/light" "github.com/ethereum/go-ethereum/light"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
...@@ -280,7 +280,7 @@ func (f *lightFetcher) announce(p *peer, head *announceData) { ...@@ -280,7 +280,7 @@ func (f *lightFetcher) announce(p *peer, head *announceData) {
// if one of root's children is canonical, keep it, delete other branches and root itself // if one of root's children is canonical, keep it, delete other branches and root itself
var newRoot *fetcherTreeNode var newRoot *fetcherTreeNode
for i, nn := range fp.root.children { for i, nn := range fp.root.children {
if core.GetCanonicalHash(f.pm.chainDb, nn.number) == nn.hash { if rawdb.ReadCanonicalHash(f.pm.chainDb, nn.number) == nn.hash {
fp.root.children = append(fp.root.children[:i], fp.root.children[i+1:]...) fp.root.children = append(fp.root.children[:i], fp.root.children[i+1:]...)
nn.parent = nil nn.parent = nil
newRoot = nn newRoot = nn
...@@ -363,7 +363,7 @@ func (f *lightFetcher) peerHasBlock(p *peer, hash common.Hash, number uint64) bo ...@@ -363,7 +363,7 @@ func (f *lightFetcher) peerHasBlock(p *peer, hash common.Hash, number uint64) bo
// //
// when syncing, just check if it is part of the known chain, there is nothing better we // when syncing, just check if it is part of the known chain, there is nothing better we
// can do since we do not know the most recent block hash yet // can do since we do not know the most recent block hash yet
return core.GetCanonicalHash(f.pm.chainDb, fp.root.number) == fp.root.hash && core.GetCanonicalHash(f.pm.chainDb, number) == hash return rawdb.ReadCanonicalHash(f.pm.chainDb, fp.root.number) == fp.root.hash && rawdb.ReadCanonicalHash(f.pm.chainDb, number) == hash
} }
// requestAmount calculates the amount of headers to be downloaded starting // requestAmount calculates the amount of headers to be downloaded starting
......
...@@ -29,6 +29,7 @@ import ( ...@@ -29,6 +29,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus" "github.com/ethereum/go-ethereum/consensus"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/eth/downloader" "github.com/ethereum/go-ethereum/eth/downloader"
...@@ -528,11 +529,13 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -528,11 +529,13 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
break break
} }
// Retrieve the requested block body, stopping if enough was found // Retrieve the requested block body, stopping if enough was found
if data := core.GetBodyRLP(pm.chainDb, hash, core.GetBlockNumber(pm.chainDb, hash)); len(data) != 0 { if number := rawdb.ReadHeaderNumber(pm.chainDb, hash); number != nil {
if data := rawdb.ReadBodyRLP(pm.chainDb, hash, *number); len(data) != 0 {
bodies = append(bodies, data) bodies = append(bodies, data)
bytes += len(data) bytes += len(data)
} }
} }
}
bv, rcost := p.fcClient.RequestProcessed(costs.baseCost + uint64(reqCnt)*costs.reqCost) bv, rcost := p.fcClient.RequestProcessed(costs.baseCost + uint64(reqCnt)*costs.reqCost)
pm.server.fcCostStats.update(msg.Code, uint64(reqCnt), rcost) pm.server.fcCostStats.update(msg.Code, uint64(reqCnt), rcost)
return p.SendBlockBodiesRLP(req.ReqID, bv, bodies) return p.SendBlockBodiesRLP(req.ReqID, bv, bodies)
...@@ -579,7 +582,8 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -579,7 +582,8 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
} }
for _, req := range req.Reqs { for _, req := range req.Reqs {
// Retrieve the requested state entry, stopping if enough was found // Retrieve the requested state entry, stopping if enough was found
if header := core.GetHeader(pm.chainDb, req.BHash, core.GetBlockNumber(pm.chainDb, req.BHash)); header != nil { if number := rawdb.ReadHeaderNumber(pm.chainDb, req.BHash); number != nil {
if header := rawdb.ReadHeader(pm.chainDb, req.BHash, *number); header != nil {
statedb, err := pm.blockchain.State() statedb, err := pm.blockchain.State()
if err != nil { if err != nil {
continue continue
...@@ -596,6 +600,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -596,6 +600,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
} }
} }
} }
}
bv, rcost := p.fcClient.RequestProcessed(costs.baseCost + uint64(reqCnt)*costs.reqCost) bv, rcost := p.fcClient.RequestProcessed(costs.baseCost + uint64(reqCnt)*costs.reqCost)
pm.server.fcCostStats.update(msg.Code, uint64(reqCnt), rcost) pm.server.fcCostStats.update(msg.Code, uint64(reqCnt), rcost)
return p.SendCode(req.ReqID, bv, data) return p.SendCode(req.ReqID, bv, data)
...@@ -645,7 +650,10 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -645,7 +650,10 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
break break
} }
// Retrieve the requested block's receipts, skipping if unknown to us // Retrieve the requested block's receipts, skipping if unknown to us
results := core.GetBlockReceipts(pm.chainDb, hash, core.GetBlockNumber(pm.chainDb, hash)) var results types.Receipts
if number := rawdb.ReadHeaderNumber(pm.chainDb, hash); number != nil {
results = rawdb.ReadReceipts(pm.chainDb, hash, *number)
}
if results == nil { if results == nil {
if header := pm.blockchain.GetHeaderByHash(hash); header == nil || header.ReceiptHash != types.EmptyRootHash { if header := pm.blockchain.GetHeaderByHash(hash); header == nil || header.ReceiptHash != types.EmptyRootHash {
continue continue
...@@ -705,7 +713,8 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -705,7 +713,8 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
} }
for _, req := range req.Reqs { for _, req := range req.Reqs {
// Retrieve the requested state entry, stopping if enough was found // Retrieve the requested state entry, stopping if enough was found
if header := core.GetHeader(pm.chainDb, req.BHash, core.GetBlockNumber(pm.chainDb, req.BHash)); header != nil { if number := rawdb.ReadHeaderNumber(pm.chainDb, req.BHash); number != nil {
if header := rawdb.ReadHeader(pm.chainDb, req.BHash, *number); header != nil {
statedb, err := pm.blockchain.State() statedb, err := pm.blockchain.State()
if err != nil { if err != nil {
continue continue
...@@ -731,6 +740,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -731,6 +740,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
} }
} }
} }
}
bv, rcost := p.fcClient.RequestProcessed(costs.baseCost + uint64(reqCnt)*costs.reqCost) bv, rcost := p.fcClient.RequestProcessed(costs.baseCost + uint64(reqCnt)*costs.reqCost)
pm.server.fcCostStats.update(msg.Code, uint64(reqCnt), rcost) pm.server.fcCostStats.update(msg.Code, uint64(reqCnt), rcost)
return p.SendProofs(req.ReqID, bv, proofs) return p.SendProofs(req.ReqID, bv, proofs)
...@@ -763,11 +773,13 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -763,11 +773,13 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
if statedb == nil || req.BHash != lastBHash { if statedb == nil || req.BHash != lastBHash {
statedb, root, lastBHash = nil, common.Hash{}, req.BHash statedb, root, lastBHash = nil, common.Hash{}, req.BHash
if header := core.GetHeader(pm.chainDb, req.BHash, core.GetBlockNumber(pm.chainDb, req.BHash)); header != nil { if number := rawdb.ReadHeaderNumber(pm.chainDb, req.BHash); number != nil {
if header := rawdb.ReadHeader(pm.chainDb, req.BHash, *number); header != nil {
statedb, _ = pm.blockchain.State() statedb, _ = pm.blockchain.State()
root = header.Root root = header.Root
} }
} }
}
if statedb == nil { if statedb == nil {
continue continue
} }
...@@ -859,7 +871,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { ...@@ -859,7 +871,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
trieDb := trie.NewDatabase(ethdb.NewTable(pm.chainDb, light.ChtTablePrefix)) trieDb := trie.NewDatabase(ethdb.NewTable(pm.chainDb, light.ChtTablePrefix))
for _, req := range req.Reqs { for _, req := range req.Reqs {
if header := pm.blockchain.GetHeaderByNumber(req.BlockNum); header != nil { if header := pm.blockchain.GetHeaderByNumber(req.BlockNum); header != nil {
sectionHead := core.GetCanonicalHash(pm.chainDb, req.ChtNum*light.CHTFrequencyServer-1) sectionHead := rawdb.ReadCanonicalHash(pm.chainDb, req.ChtNum*light.CHTFrequencyServer-1)
if root := light.GetChtRoot(pm.chainDb, req.ChtNum-1, sectionHead); root != (common.Hash{}) { if root := light.GetChtRoot(pm.chainDb, req.ChtNum-1, sectionHead); root != (common.Hash{}) {
trie, err := trie.New(root, trieDb) trie, err := trie.New(root, trieDb)
if err != nil { if err != nil {
...@@ -1114,10 +1126,10 @@ func (pm *ProtocolManager) getAccount(statedb *state.StateDB, root, hash common. ...@@ -1114,10 +1126,10 @@ func (pm *ProtocolManager) getAccount(statedb *state.StateDB, root, hash common.
func (pm *ProtocolManager) getHelperTrie(id uint, idx uint64) (common.Hash, string) { func (pm *ProtocolManager) getHelperTrie(id uint, idx uint64) (common.Hash, string) {
switch id { switch id {
case htCanonical: case htCanonical:
sectionHead := core.GetCanonicalHash(pm.chainDb, (idx+1)*light.CHTFrequencyClient-1) sectionHead := rawdb.ReadCanonicalHash(pm.chainDb, (idx+1)*light.CHTFrequencyClient-1)
return light.GetChtV2Root(pm.chainDb, idx, sectionHead), light.ChtTablePrefix return light.GetChtV2Root(pm.chainDb, idx, sectionHead), light.ChtTablePrefix
case htBloomBits: case htBloomBits:
sectionHead := core.GetCanonicalHash(pm.chainDb, (idx+1)*light.BloomTrieFrequency-1) sectionHead := rawdb.ReadCanonicalHash(pm.chainDb, (idx+1)*light.BloomTrieFrequency-1)
return light.GetBloomTrieRoot(pm.chainDb, idx, sectionHead), light.BloomTrieTablePrefix return light.GetBloomTrieRoot(pm.chainDb, idx, sectionHead), light.BloomTrieTablePrefix
} }
return common.Hash{}, "" return common.Hash{}, ""
...@@ -1128,8 +1140,8 @@ func (pm *ProtocolManager) getHelperTrieAuxData(req HelperTrieReq) []byte { ...@@ -1128,8 +1140,8 @@ func (pm *ProtocolManager) getHelperTrieAuxData(req HelperTrieReq) []byte {
switch { switch {
case req.Type == htCanonical && req.AuxReq == auxHeader && len(req.Key) == 8: case req.Type == htCanonical && req.AuxReq == auxHeader && len(req.Key) == 8:
blockNum := binary.BigEndian.Uint64(req.Key) blockNum := binary.BigEndian.Uint64(req.Key)
hash := core.GetCanonicalHash(pm.chainDb, blockNum) hash := rawdb.ReadCanonicalHash(pm.chainDb, blockNum)
return core.GetHeaderRLP(pm.chainDb, hash, blockNum) return rawdb.ReadHeaderRLP(pm.chainDb, hash, blockNum)
} }
return nil return nil
} }
...@@ -1142,9 +1154,9 @@ func (pm *ProtocolManager) txStatus(hashes []common.Hash) []txStatus { ...@@ -1142,9 +1154,9 @@ func (pm *ProtocolManager) txStatus(hashes []common.Hash) []txStatus {
// If the transaction is unknown to the pool, try looking it up locally // If the transaction is unknown to the pool, try looking it up locally
if stat == core.TxStatusUnknown { if stat == core.TxStatusUnknown {
if block, number, index := core.GetTxLookupEntry(pm.chainDb, hashes[i]); block != (common.Hash{}) { if block, number, index := rawdb.ReadTxLookupEntry(pm.chainDb, hashes[i]); block != (common.Hash{}) {
stats[i].Status = core.TxStatusIncluded stats[i].Status = core.TxStatusIncluded
stats[i].Lookup = &core.TxLookupEntry{BlockHash: block, BlockIndex: number, Index: index} stats[i].Lookup = &rawdb.TxLookupEntry{BlockHash: block, BlockIndex: number, Index: index}
} }
} }
} }
......
...@@ -26,6 +26,7 @@ import ( ...@@ -26,6 +26,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/eth/downloader" "github.com/ethereum/go-ethereum/eth/downloader"
...@@ -304,7 +305,7 @@ func testGetReceipt(t *testing.T, protocol int) { ...@@ -304,7 +305,7 @@ func testGetReceipt(t *testing.T, protocol int) {
block := bc.GetBlockByNumber(i) block := bc.GetBlockByNumber(i)
hashes = append(hashes, block.Hash()) hashes = append(hashes, block.Hash())
receipts = append(receipts, core.GetBlockReceipts(db, block.Hash(), block.NumberU64())) receipts = append(receipts, rawdb.ReadReceipts(db, block.Hash(), block.NumberU64()))
} }
// Send the hash request and verify the response // Send the hash request and verify the response
cost := peer.GetRequestCost(GetReceiptsMsg, len(hashes)) cost := peer.GetRequestCost(GetReceiptsMsg, len(hashes))
...@@ -555,9 +556,9 @@ func TestTransactionStatusLes2(t *testing.T) { ...@@ -555,9 +556,9 @@ func TestTransactionStatusLes2(t *testing.T) {
} }
// check if their status is included now // check if their status is included now
block1hash := core.GetCanonicalHash(db, 1) block1hash := rawdb.ReadCanonicalHash(db, 1)
test(tx1, false, txStatus{Status: core.TxStatusIncluded, Lookup: &core.TxLookupEntry{BlockHash: block1hash, BlockIndex: 1, Index: 0}}) test(tx1, false, txStatus{Status: core.TxStatusIncluded, Lookup: &rawdb.TxLookupEntry{BlockHash: block1hash, BlockIndex: 1, Index: 0}})
test(tx2, false, txStatus{Status: core.TxStatusIncluded, Lookup: &core.TxLookupEntry{BlockHash: block1hash, BlockIndex: 1, Index: 1}}) test(tx2, false, txStatus{Status: core.TxStatusIncluded, Lookup: &rawdb.TxLookupEntry{BlockHash: block1hash, BlockIndex: 1, Index: 1}})
// create a reorg that rolls them back // create a reorg that rolls them back
gchain, _ = core.GenerateChain(params.TestChainConfig, chain.GetBlockByNumber(0), ethash.NewFaker(), db, 2, func(i int, block *core.BlockGen) {}) gchain, _ = core.GenerateChain(params.TestChainConfig, chain.GetBlockByNumber(0), ethash.NewFaker(), db, 2, func(i int, block *core.BlockGen) {})
......
...@@ -24,7 +24,7 @@ import ( ...@@ -24,7 +24,7 @@ import (
"fmt" "fmt"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -110,7 +110,7 @@ func (r *BlockRequest) Validate(db ethdb.Database, msg *Msg) error { ...@@ -110,7 +110,7 @@ func (r *BlockRequest) Validate(db ethdb.Database, msg *Msg) error {
body := bodies[0] body := bodies[0]
// Retrieve our stored header and validate block content against it // Retrieve our stored header and validate block content against it
header := core.GetHeader(db, r.Hash, r.Number) header := rawdb.ReadHeader(db, r.Hash, r.Number)
if header == nil { if header == nil {
return errHeaderUnavailable return errHeaderUnavailable
} }
...@@ -166,7 +166,7 @@ func (r *ReceiptsRequest) Validate(db ethdb.Database, msg *Msg) error { ...@@ -166,7 +166,7 @@ func (r *ReceiptsRequest) Validate(db ethdb.Database, msg *Msg) error {
receipt := receipts[0] receipt := receipts[0]
// Retrieve our stored header and validate receipt content against it // Retrieve our stored header and validate receipt content against it
header := core.GetHeader(db, r.Hash, r.Number) header := rawdb.ReadHeader(db, r.Hash, r.Number)
if header == nil { if header == nil {
return errHeaderUnavailable return errHeaderUnavailable
} }
......
...@@ -26,6 +26,7 @@ import ( ...@@ -26,6 +26,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -63,9 +64,13 @@ func TestOdrGetReceiptsLes2(t *testing.T) { testOdr(t, 2, 1, odrGetReceipts) } ...@@ -63,9 +64,13 @@ func TestOdrGetReceiptsLes2(t *testing.T) { testOdr(t, 2, 1, odrGetReceipts) }
func odrGetReceipts(ctx context.Context, db ethdb.Database, config *params.ChainConfig, bc *core.BlockChain, lc *light.LightChain, bhash common.Hash) []byte { func odrGetReceipts(ctx context.Context, db ethdb.Database, config *params.ChainConfig, bc *core.BlockChain, lc *light.LightChain, bhash common.Hash) []byte {
var receipts types.Receipts var receipts types.Receipts
if bc != nil { if bc != nil {
receipts = core.GetBlockReceipts(db, bhash, core.GetBlockNumber(db, bhash)) if number := rawdb.ReadHeaderNumber(db, bhash); number != nil {
receipts = rawdb.ReadReceipts(db, bhash, *number)
}
} else { } else {
receipts, _ = light.GetBlockReceipts(ctx, lc.Odr(), bhash, core.GetBlockNumber(db, bhash)) if number := rawdb.ReadHeaderNumber(db, bhash); number != nil {
receipts, _ = light.GetBlockReceipts(ctx, lc.Odr(), bhash, *number)
}
} }
if receipts == nil { if receipts == nil {
return nil return nil
...@@ -178,7 +183,7 @@ func testOdr(t *testing.T, protocol int, expFail uint64, fn odrTestFn) { ...@@ -178,7 +183,7 @@ func testOdr(t *testing.T, protocol int, expFail uint64, fn odrTestFn) {
test := func(expFail uint64) { test := func(expFail uint64) {
for i := uint64(0); i <= pm.blockchain.CurrentHeader().Number.Uint64(); i++ { for i := uint64(0); i <= pm.blockchain.CurrentHeader().Number.Uint64(); i++ {
bhash := core.GetCanonicalHash(db, i) bhash := rawdb.ReadCanonicalHash(db, i)
b1 := fn(light.NoOdr, db, pm.chainConfig, pm.blockchain.(*core.BlockChain), nil, bhash) b1 := fn(light.NoOdr, db, pm.chainConfig, pm.blockchain.(*core.BlockChain), nil, bhash)
ctx, cancel := context.WithTimeout(context.Background(), 200*time.Millisecond) ctx, cancel := context.WithTimeout(context.Background(), 200*time.Millisecond)
......
...@@ -28,6 +28,7 @@ import ( ...@@ -28,6 +28,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/crypto/secp256k1" "github.com/ethereum/go-ethereum/crypto/secp256k1"
"github.com/ethereum/go-ethereum/rlp" "github.com/ethereum/go-ethereum/rlp"
...@@ -223,6 +224,6 @@ type proofsData [][]rlp.RawValue ...@@ -223,6 +224,6 @@ type proofsData [][]rlp.RawValue
type txStatus struct { type txStatus struct {
Status core.TxStatus Status core.TxStatus
Lookup *core.TxLookupEntry `rlp:"nil"` Lookup *rawdb.TxLookupEntry `rlp:"nil"`
Error string Error string
} }
...@@ -22,7 +22,7 @@ import ( ...@@ -22,7 +22,7 @@ import (
"time" "time"
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/eth" "github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -58,15 +58,22 @@ func TestTrieEntryAccessLes1(t *testing.T) { testAccess(t, 1, tfTrieEntryAccess) ...@@ -58,15 +58,22 @@ func TestTrieEntryAccessLes1(t *testing.T) { testAccess(t, 1, tfTrieEntryAccess)
func TestTrieEntryAccessLes2(t *testing.T) { testAccess(t, 2, tfTrieEntryAccess) } func TestTrieEntryAccessLes2(t *testing.T) { testAccess(t, 2, tfTrieEntryAccess) }
func tfTrieEntryAccess(db ethdb.Database, bhash common.Hash, number uint64) light.OdrRequest { func tfTrieEntryAccess(db ethdb.Database, bhash common.Hash, number uint64) light.OdrRequest {
return &light.TrieRequest{Id: light.StateTrieID(core.GetHeader(db, bhash, core.GetBlockNumber(db, bhash))), Key: testBankSecureTrieKey} if number := rawdb.ReadHeaderNumber(db, bhash); number != nil {
return &light.TrieRequest{Id: light.StateTrieID(rawdb.ReadHeader(db, bhash, *number)), Key: testBankSecureTrieKey}
}
return nil
} }
func TestCodeAccessLes1(t *testing.T) { testAccess(t, 1, tfCodeAccess) } func TestCodeAccessLes1(t *testing.T) { testAccess(t, 1, tfCodeAccess) }
func TestCodeAccessLes2(t *testing.T) { testAccess(t, 2, tfCodeAccess) } func TestCodeAccessLes2(t *testing.T) { testAccess(t, 2, tfCodeAccess) }
func tfCodeAccess(db ethdb.Database, bhash common.Hash, number uint64) light.OdrRequest { func tfCodeAccess(db ethdb.Database, bhash common.Hash, num uint64) light.OdrRequest {
header := core.GetHeader(db, bhash, core.GetBlockNumber(db, bhash)) number := rawdb.ReadHeaderNumber(db, bhash)
if number != nil {
return nil
}
header := rawdb.ReadHeader(db, bhash, *number)
if header.Number.Uint64() < testContractDeployed { if header.Number.Uint64() < testContractDeployed {
return nil return nil
} }
...@@ -99,7 +106,7 @@ func testAccess(t *testing.T, protocol int, fn accessTestFn) { ...@@ -99,7 +106,7 @@ func testAccess(t *testing.T, protocol int, fn accessTestFn) {
test := func(expFail uint64) { test := func(expFail uint64) {
for i := uint64(0); i <= pm.blockchain.CurrentHeader().Number.Uint64(); i++ { for i := uint64(0); i <= pm.blockchain.CurrentHeader().Number.Uint64(); i++ {
bhash := core.GetCanonicalHash(db, i) bhash := rawdb.ReadCanonicalHash(db, i)
if req := fn(ldb, bhash, i); req != nil { if req := fn(ldb, bhash, i); req != nil {
ctx, cancel := context.WithTimeout(context.Background(), 200*time.Millisecond) ctx, cancel := context.WithTimeout(context.Background(), 200*time.Millisecond)
defer cancel() defer cancel()
......
...@@ -25,6 +25,7 @@ import ( ...@@ -25,6 +25,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/eth" "github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -329,11 +330,11 @@ func (pm *ProtocolManager) blockLoop() { ...@@ -329,11 +330,11 @@ func (pm *ProtocolManager) blockLoop() {
header := ev.Block.Header() header := ev.Block.Header()
hash := header.Hash() hash := header.Hash()
number := header.Number.Uint64() number := header.Number.Uint64()
td := core.GetTd(pm.chainDb, hash, number) td := rawdb.ReadTd(pm.chainDb, hash, number)
if td != nil && td.Cmp(lastBroadcastTd) > 0 { if td != nil && td.Cmp(lastBroadcastTd) > 0 {
var reorg uint64 var reorg uint64
if lastHead != nil { if lastHead != nil {
reorg = lastHead.Number.Uint64() - core.FindCommonAncestor(pm.chainDb, header, lastHead).Number.Uint64() reorg = lastHead.Number.Uint64() - rawdb.FindCommonAncestor(pm.chainDb, header, lastHead).Number.Uint64()
} }
lastHead = header lastHead = header
lastBroadcastTd = td lastBroadcastTd = td
......
...@@ -20,7 +20,7 @@ import ( ...@@ -20,7 +20,7 @@ import (
"context" "context"
"time" "time"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/eth/downloader" "github.com/ethereum/go-ethereum/eth/downloader"
"github.com/ethereum/go-ethereum/light" "github.com/ethereum/go-ethereum/light"
) )
...@@ -56,7 +56,7 @@ func (pm *ProtocolManager) syncer() { ...@@ -56,7 +56,7 @@ func (pm *ProtocolManager) syncer() {
func (pm *ProtocolManager) needToSync(peerHead blockInfo) bool { func (pm *ProtocolManager) needToSync(peerHead blockInfo) bool {
head := pm.blockchain.CurrentHeader() head := pm.blockchain.CurrentHeader()
currentTd := core.GetTd(pm.chainDb, head.Hash(), head.Number.Uint64()) currentTd := rawdb.ReadTd(pm.chainDb, head.Hash(), head.Number.Uint64())
return currentTd != nil && peerHead.Td.Cmp(currentTd) > 0 return currentTd != nil && peerHead.Td.Cmp(currentTd) > 0
} }
......
...@@ -27,6 +27,7 @@ import ( ...@@ -27,6 +27,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus" "github.com/ethereum/go-ethereum/consensus"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -142,7 +143,7 @@ func (self *LightChain) Odr() OdrBackend { ...@@ -142,7 +143,7 @@ func (self *LightChain) Odr() OdrBackend {
// loadLastState loads the last known chain state from the database. This method // loadLastState loads the last known chain state from the database. This method
// assumes that the chain manager mutex is held. // assumes that the chain manager mutex is held.
func (self *LightChain) loadLastState() error { func (self *LightChain) loadLastState() error {
if head := core.GetHeadHeaderHash(self.chainDb); head == (common.Hash{}) { if head := rawdb.ReadHeadHeaderHash(self.chainDb); head == (common.Hash{}) {
// Corrupt or empty database, init from scratch // Corrupt or empty database, init from scratch
self.Reset() self.Reset()
} else { } else {
...@@ -189,12 +190,9 @@ func (bc *LightChain) ResetWithGenesisBlock(genesis *types.Block) { ...@@ -189,12 +190,9 @@ func (bc *LightChain) ResetWithGenesisBlock(genesis *types.Block) {
defer bc.mu.Unlock() defer bc.mu.Unlock()
// Prepare the genesis block and reinitialise the chain // Prepare the genesis block and reinitialise the chain
if err := core.WriteTd(bc.chainDb, genesis.Hash(), genesis.NumberU64(), genesis.Difficulty()); err != nil { rawdb.WriteTd(bc.chainDb, genesis.Hash(), genesis.NumberU64(), genesis.Difficulty())
log.Crit("Failed to write genesis block TD", "err", err) rawdb.WriteBlock(bc.chainDb, genesis)
}
if err := core.WriteBlock(bc.chainDb, genesis); err != nil {
log.Crit("Failed to write genesis block", "err", err)
}
bc.genesisBlock = genesis bc.genesisBlock = genesis
bc.hc.SetGenesis(bc.genesisBlock.Header()) bc.hc.SetGenesis(bc.genesisBlock.Header())
bc.hc.SetCurrentHeader(bc.genesisBlock.Header()) bc.hc.SetCurrentHeader(bc.genesisBlock.Header())
...@@ -223,7 +221,11 @@ func (self *LightChain) GetBody(ctx context.Context, hash common.Hash) (*types.B ...@@ -223,7 +221,11 @@ func (self *LightChain) GetBody(ctx context.Context, hash common.Hash) (*types.B
body := cached.(*types.Body) body := cached.(*types.Body)
return body, nil return body, nil
} }
body, err := GetBody(ctx, self.odr, hash, self.hc.GetBlockNumber(hash)) number := self.hc.GetBlockNumber(hash)
if number == nil {
return nil, errors.New("unknown block")
}
body, err := GetBody(ctx, self.odr, hash, *number)
if err != nil { if err != nil {
return nil, err return nil, err
} }
...@@ -239,7 +241,11 @@ func (self *LightChain) GetBodyRLP(ctx context.Context, hash common.Hash) (rlp.R ...@@ -239,7 +241,11 @@ func (self *LightChain) GetBodyRLP(ctx context.Context, hash common.Hash) (rlp.R
if cached, ok := self.bodyRLPCache.Get(hash); ok { if cached, ok := self.bodyRLPCache.Get(hash); ok {
return cached.(rlp.RawValue), nil return cached.(rlp.RawValue), nil
} }
body, err := GetBodyRLP(ctx, self.odr, hash, self.hc.GetBlockNumber(hash)) number := self.hc.GetBlockNumber(hash)
if number == nil {
return nil, errors.New("unknown block")
}
body, err := GetBodyRLP(ctx, self.odr, hash, *number)
if err != nil { if err != nil {
return nil, err return nil, err
} }
...@@ -274,7 +280,11 @@ func (self *LightChain) GetBlock(ctx context.Context, hash common.Hash, number u ...@@ -274,7 +280,11 @@ func (self *LightChain) GetBlock(ctx context.Context, hash common.Hash, number u
// GetBlockByHash retrieves a block from the database or ODR service by hash, // GetBlockByHash retrieves a block from the database or ODR service by hash,
// caching it if found. // caching it if found.
func (self *LightChain) GetBlockByHash(ctx context.Context, hash common.Hash) (*types.Block, error) { func (self *LightChain) GetBlockByHash(ctx context.Context, hash common.Hash) (*types.Block, error) {
return self.GetBlock(ctx, hash, self.hc.GetBlockNumber(hash)) number := self.hc.GetBlockNumber(hash)
if number == nil {
return nil, errors.New("unknown block")
}
return self.GetBlock(ctx, hash, *number)
} }
// GetBlockByNumber retrieves a block from the database or ODR service by // GetBlockByNumber retrieves a block from the database or ODR service by
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/params"
...@@ -122,8 +123,8 @@ func testHeaderChainImport(chain []*types.Header, lightchain *LightChain) error ...@@ -122,8 +123,8 @@ func testHeaderChainImport(chain []*types.Header, lightchain *LightChain) error
} }
// Manually insert the header into the database, but don't reorganize (allows subsequent testing) // Manually insert the header into the database, but don't reorganize (allows subsequent testing)
lightchain.mu.Lock() lightchain.mu.Lock()
core.WriteTd(lightchain.chainDb, header.Hash(), header.Number.Uint64(), new(big.Int).Add(header.Difficulty, lightchain.GetTdByHash(header.ParentHash))) rawdb.WriteTd(lightchain.chainDb, header.Hash(), header.Number.Uint64(), new(big.Int).Add(header.Difficulty, lightchain.GetTdByHash(header.ParentHash)))
core.WriteHeader(lightchain.chainDb, header) rawdb.WriteHeader(lightchain.chainDb, header)
lightchain.mu.Unlock() lightchain.mu.Unlock()
} }
return nil return nil
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
) )
...@@ -112,7 +113,7 @@ type BlockRequest struct { ...@@ -112,7 +113,7 @@ type BlockRequest struct {
// StoreResult stores the retrieved data in local database // StoreResult stores the retrieved data in local database
func (req *BlockRequest) StoreResult(db ethdb.Database) { func (req *BlockRequest) StoreResult(db ethdb.Database) {
core.WriteBodyRLP(db, req.Hash, req.Number, req.Rlp) rawdb.WriteBodyRLP(db, req.Hash, req.Number, req.Rlp)
} }
// ReceiptsRequest is the ODR request type for retrieving block bodies // ReceiptsRequest is the ODR request type for retrieving block bodies
...@@ -125,7 +126,7 @@ type ReceiptsRequest struct { ...@@ -125,7 +126,7 @@ type ReceiptsRequest struct {
// StoreResult stores the retrieved data in local database // StoreResult stores the retrieved data in local database
func (req *ReceiptsRequest) StoreResult(db ethdb.Database) { func (req *ReceiptsRequest) StoreResult(db ethdb.Database) {
core.WriteBlockReceipts(db, req.Hash, req.Number, req.Receipts) rawdb.WriteReceipts(db, req.Hash, req.Number, req.Receipts)
} }
// ChtRequest is the ODR request type for state/storage trie entries // ChtRequest is the ODR request type for state/storage trie entries
...@@ -140,11 +141,11 @@ type ChtRequest struct { ...@@ -140,11 +141,11 @@ type ChtRequest struct {
// StoreResult stores the retrieved data in local database // StoreResult stores the retrieved data in local database
func (req *ChtRequest) StoreResult(db ethdb.Database) { func (req *ChtRequest) StoreResult(db ethdb.Database) {
// if there is a canonical hash, there is a header too
core.WriteHeader(db, req.Header)
hash, num := req.Header.Hash(), req.Header.Number.Uint64() hash, num := req.Header.Hash(), req.Header.Number.Uint64()
core.WriteTd(db, hash, num, req.Td)
core.WriteCanonicalHash(db, hash, num) rawdb.WriteHeader(db, req.Header)
rawdb.WriteTd(db, hash, num, req.Td)
rawdb.WriteCanonicalHash(db, hash, num)
} }
// BloomRequest is the ODR request type for retrieving bloom filters from a CHT structure // BloomRequest is the ODR request type for retrieving bloom filters from a CHT structure
...@@ -161,11 +162,11 @@ type BloomRequest struct { ...@@ -161,11 +162,11 @@ type BloomRequest struct {
// StoreResult stores the retrieved data in local database // StoreResult stores the retrieved data in local database
func (req *BloomRequest) StoreResult(db ethdb.Database) { func (req *BloomRequest) StoreResult(db ethdb.Database) {
for i, sectionIdx := range req.SectionIdxList { for i, sectionIdx := range req.SectionIdxList {
sectionHead := core.GetCanonicalHash(db, (sectionIdx+1)*BloomTrieFrequency-1) sectionHead := rawdb.ReadCanonicalHash(db, (sectionIdx+1)*BloomTrieFrequency-1)
// if we don't have the canonical hash stored for this section head number, we'll still store it under // if we don't have the canonical hash stored for this section head number, we'll still store it under
// a key with a zero sectionHead. GetBloomBits will look there too if we still don't have the canonical // a key with a zero sectionHead. GetBloomBits will look there too if we still don't have the canonical
// hash. In the unlikely case we've retrieved the section head hash since then, we'll just retrieve the // hash. In the unlikely case we've retrieved the section head hash since then, we'll just retrieve the
// bit vector again from the network. // bit vector again from the network.
core.WriteBloomBits(db, req.BitIdx, sectionIdx, sectionHead, req.BloomBits[i]) rawdb.WriteBloomBits(db, req.BitIdx, sectionIdx, sectionHead, req.BloomBits[i])
} }
} }
...@@ -28,6 +28,7 @@ import ( ...@@ -28,6 +28,7 @@ import (
"github.com/ethereum/go-ethereum/common/math" "github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/consensus/ethash" "github.com/ethereum/go-ethereum/consensus/ethash"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/core/vm" "github.com/ethereum/go-ethereum/core/vm"
...@@ -70,9 +71,15 @@ func (odr *testOdr) Retrieve(ctx context.Context, req OdrRequest) error { ...@@ -70,9 +71,15 @@ func (odr *testOdr) Retrieve(ctx context.Context, req OdrRequest) error {
} }
switch req := req.(type) { switch req := req.(type) {
case *BlockRequest: case *BlockRequest:
req.Rlp = core.GetBodyRLP(odr.sdb, req.Hash, core.GetBlockNumber(odr.sdb, req.Hash)) number := rawdb.ReadHeaderNumber(odr.sdb, req.Hash)
if number != nil {
req.Rlp = rawdb.ReadBodyRLP(odr.sdb, req.Hash, *number)
}
case *ReceiptsRequest: case *ReceiptsRequest:
req.Receipts = core.GetBlockReceipts(odr.sdb, req.Hash, core.GetBlockNumber(odr.sdb, req.Hash)) number := rawdb.ReadHeaderNumber(odr.sdb, req.Hash)
if number != nil {
req.Receipts = rawdb.ReadReceipts(odr.sdb, req.Hash, *number)
}
case *TrieRequest: case *TrieRequest:
t, _ := trie.New(req.Id.Root, trie.NewDatabase(odr.sdb)) t, _ := trie.New(req.Id.Root, trie.NewDatabase(odr.sdb))
nodes := NewNodeSet() nodes := NewNodeSet()
...@@ -108,9 +115,15 @@ func TestOdrGetReceiptsLes1(t *testing.T) { testChainOdr(t, 1, odrGetReceipts) } ...@@ -108,9 +115,15 @@ func TestOdrGetReceiptsLes1(t *testing.T) { testChainOdr(t, 1, odrGetReceipts) }
func odrGetReceipts(ctx context.Context, db ethdb.Database, bc *core.BlockChain, lc *LightChain, bhash common.Hash) ([]byte, error) { func odrGetReceipts(ctx context.Context, db ethdb.Database, bc *core.BlockChain, lc *LightChain, bhash common.Hash) ([]byte, error) {
var receipts types.Receipts var receipts types.Receipts
if bc != nil { if bc != nil {
receipts = core.GetBlockReceipts(db, bhash, core.GetBlockNumber(db, bhash)) number := rawdb.ReadHeaderNumber(db, bhash)
if number != nil {
receipts = rawdb.ReadReceipts(db, bhash, *number)
}
} else { } else {
receipts, _ = GetBlockReceipts(ctx, lc.Odr(), bhash, core.GetBlockNumber(db, bhash)) number := rawdb.ReadHeaderNumber(db, bhash)
if number != nil {
receipts, _ = GetBlockReceipts(ctx, lc.Odr(), bhash, *number)
}
} }
if receipts == nil { if receipts == nil {
return nil, nil return nil, nil
...@@ -260,7 +273,7 @@ func testChainOdr(t *testing.T, protocol int, fn odrTestFn) { ...@@ -260,7 +273,7 @@ func testChainOdr(t *testing.T, protocol int, fn odrTestFn) {
test := func(expFail int) { test := func(expFail int) {
for i := uint64(0); i <= blockchain.CurrentHeader().Number.Uint64(); i++ { for i := uint64(0); i <= blockchain.CurrentHeader().Number.Uint64(); i++ {
bhash := core.GetCanonicalHash(sdb, i) bhash := rawdb.ReadCanonicalHash(sdb, i)
b1, err := fn(NoOdr, sdb, blockchain, nil, bhash) b1, err := fn(NoOdr, sdb, blockchain, nil, bhash)
if err != nil { if err != nil {
t.Fatalf("error in full-node test for block %d: %v", i, err) t.Fatalf("error in full-node test for block %d: %v", i, err)
......
...@@ -22,6 +22,7 @@ import ( ...@@ -22,6 +22,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto" "github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/rlp" "github.com/ethereum/go-ethereum/rlp"
...@@ -31,10 +32,10 @@ var sha3_nil = crypto.Keccak256Hash(nil) ...@@ -31,10 +32,10 @@ var sha3_nil = crypto.Keccak256Hash(nil)
func GetHeaderByNumber(ctx context.Context, odr OdrBackend, number uint64) (*types.Header, error) { func GetHeaderByNumber(ctx context.Context, odr OdrBackend, number uint64) (*types.Header, error) {
db := odr.Database() db := odr.Database()
hash := core.GetCanonicalHash(db, number) hash := rawdb.ReadCanonicalHash(db, number)
if (hash != common.Hash{}) { if (hash != common.Hash{}) {
// if there is a canonical hash, there is a header too // if there is a canonical hash, there is a header too
header := core.GetHeader(db, hash, number) header := rawdb.ReadHeader(db, hash, number)
if header == nil { if header == nil {
panic("Canonical hash present but header not found") panic("Canonical hash present but header not found")
} }
...@@ -47,14 +48,14 @@ func GetHeaderByNumber(ctx context.Context, odr OdrBackend, number uint64) (*typ ...@@ -47,14 +48,14 @@ func GetHeaderByNumber(ctx context.Context, odr OdrBackend, number uint64) (*typ
) )
if odr.ChtIndexer() != nil { if odr.ChtIndexer() != nil {
chtCount, sectionHeadNum, sectionHead = odr.ChtIndexer().Sections() chtCount, sectionHeadNum, sectionHead = odr.ChtIndexer().Sections()
canonicalHash := core.GetCanonicalHash(db, sectionHeadNum) canonicalHash := rawdb.ReadCanonicalHash(db, sectionHeadNum)
// if the CHT was injected as a trusted checkpoint, we have no canonical hash yet so we accept zero hash too // if the CHT was injected as a trusted checkpoint, we have no canonical hash yet so we accept zero hash too
for chtCount > 0 && canonicalHash != sectionHead && canonicalHash != (common.Hash{}) { for chtCount > 0 && canonicalHash != sectionHead && canonicalHash != (common.Hash{}) {
chtCount-- chtCount--
if chtCount > 0 { if chtCount > 0 {
sectionHeadNum = chtCount*CHTFrequencyClient - 1 sectionHeadNum = chtCount*CHTFrequencyClient - 1
sectionHead = odr.ChtIndexer().SectionHead(chtCount - 1) sectionHead = odr.ChtIndexer().SectionHead(chtCount - 1)
canonicalHash = core.GetCanonicalHash(db, sectionHeadNum) canonicalHash = rawdb.ReadCanonicalHash(db, sectionHeadNum)
} }
} }
} }
...@@ -69,7 +70,7 @@ func GetHeaderByNumber(ctx context.Context, odr OdrBackend, number uint64) (*typ ...@@ -69,7 +70,7 @@ func GetHeaderByNumber(ctx context.Context, odr OdrBackend, number uint64) (*typ
} }
func GetCanonicalHash(ctx context.Context, odr OdrBackend, number uint64) (common.Hash, error) { func GetCanonicalHash(ctx context.Context, odr OdrBackend, number uint64) (common.Hash, error) {
hash := core.GetCanonicalHash(odr.Database(), number) hash := rawdb.ReadCanonicalHash(odr.Database(), number)
if (hash != common.Hash{}) { if (hash != common.Hash{}) {
return hash, nil return hash, nil
} }
...@@ -82,7 +83,7 @@ func GetCanonicalHash(ctx context.Context, odr OdrBackend, number uint64) (commo ...@@ -82,7 +83,7 @@ func GetCanonicalHash(ctx context.Context, odr OdrBackend, number uint64) (commo
// GetBodyRLP retrieves the block body (transactions and uncles) in RLP encoding. // GetBodyRLP retrieves the block body (transactions and uncles) in RLP encoding.
func GetBodyRLP(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) (rlp.RawValue, error) { func GetBodyRLP(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) (rlp.RawValue, error) {
if data := core.GetBodyRLP(odr.Database(), hash, number); data != nil { if data := rawdb.ReadBodyRLP(odr.Database(), hash, number); data != nil {
return data, nil return data, nil
} }
r := &BlockRequest{Hash: hash, Number: number} r := &BlockRequest{Hash: hash, Number: number}
...@@ -111,7 +112,7 @@ func GetBody(ctx context.Context, odr OdrBackend, hash common.Hash, number uint6 ...@@ -111,7 +112,7 @@ func GetBody(ctx context.Context, odr OdrBackend, hash common.Hash, number uint6
// back from the stored header and body. // back from the stored header and body.
func GetBlock(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) (*types.Block, error) { func GetBlock(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) (*types.Block, error) {
// Retrieve the block header and body contents // Retrieve the block header and body contents
header := core.GetHeader(odr.Database(), hash, number) header := rawdb.ReadHeader(odr.Database(), hash, number)
if header == nil { if header == nil {
return nil, ErrNoHeader return nil, ErrNoHeader
} }
...@@ -127,7 +128,7 @@ func GetBlock(ctx context.Context, odr OdrBackend, hash common.Hash, number uint ...@@ -127,7 +128,7 @@ func GetBlock(ctx context.Context, odr OdrBackend, hash common.Hash, number uint
// in a block given by its hash. // in a block given by its hash.
func GetBlockReceipts(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) (types.Receipts, error) { func GetBlockReceipts(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) (types.Receipts, error) {
// Retrieve the potentially incomplete receipts from disk or network // Retrieve the potentially incomplete receipts from disk or network
receipts := core.GetBlockReceipts(odr.Database(), hash, number) receipts := rawdb.ReadReceipts(odr.Database(), hash, number)
if receipts == nil { if receipts == nil {
r := &ReceiptsRequest{Hash: hash, Number: number} r := &ReceiptsRequest{Hash: hash, Number: number}
if err := odr.Retrieve(ctx, r); err != nil { if err := odr.Retrieve(ctx, r); err != nil {
...@@ -141,13 +142,13 @@ func GetBlockReceipts(ctx context.Context, odr OdrBackend, hash common.Hash, num ...@@ -141,13 +142,13 @@ func GetBlockReceipts(ctx context.Context, odr OdrBackend, hash common.Hash, num
if err != nil { if err != nil {
return nil, err return nil, err
} }
genesis := core.GetCanonicalHash(odr.Database(), 0) genesis := rawdb.ReadCanonicalHash(odr.Database(), 0)
config, _ := core.GetChainConfig(odr.Database(), genesis) config := rawdb.ReadChainConfig(odr.Database(), genesis)
if err := core.SetReceiptsData(config, block, receipts); err != nil { if err := core.SetReceiptsData(config, block, receipts); err != nil {
return nil, err return nil, err
} }
core.WriteBlockReceipts(odr.Database(), hash, number, receipts) rawdb.WriteReceipts(odr.Database(), hash, number, receipts)
} }
return receipts, nil return receipts, nil
} }
...@@ -156,7 +157,7 @@ func GetBlockReceipts(ctx context.Context, odr OdrBackend, hash common.Hash, num ...@@ -156,7 +157,7 @@ func GetBlockReceipts(ctx context.Context, odr OdrBackend, hash common.Hash, num
// block given by its hash. // block given by its hash.
func GetBlockLogs(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) ([][]*types.Log, error) { func GetBlockLogs(ctx context.Context, odr OdrBackend, hash common.Hash, number uint64) ([][]*types.Log, error) {
// Retrieve the potentially incomplete receipts from disk or network // Retrieve the potentially incomplete receipts from disk or network
receipts := core.GetBlockReceipts(odr.Database(), hash, number) receipts := rawdb.ReadReceipts(odr.Database(), hash, number)
if receipts == nil { if receipts == nil {
r := &ReceiptsRequest{Hash: hash, Number: number} r := &ReceiptsRequest{Hash: hash, Number: number}
if err := odr.Retrieve(ctx, r); err != nil { if err := odr.Retrieve(ctx, r); err != nil {
...@@ -187,24 +188,24 @@ func GetBloomBits(ctx context.Context, odr OdrBackend, bitIdx uint, sectionIdxLi ...@@ -187,24 +188,24 @@ func GetBloomBits(ctx context.Context, odr OdrBackend, bitIdx uint, sectionIdxLi
) )
if odr.BloomTrieIndexer() != nil { if odr.BloomTrieIndexer() != nil {
bloomTrieCount, sectionHeadNum, sectionHead = odr.BloomTrieIndexer().Sections() bloomTrieCount, sectionHeadNum, sectionHead = odr.BloomTrieIndexer().Sections()
canonicalHash := core.GetCanonicalHash(db, sectionHeadNum) canonicalHash := rawdb.ReadCanonicalHash(db, sectionHeadNum)
// if the BloomTrie was injected as a trusted checkpoint, we have no canonical hash yet so we accept zero hash too // if the BloomTrie was injected as a trusted checkpoint, we have no canonical hash yet so we accept zero hash too
for bloomTrieCount > 0 && canonicalHash != sectionHead && canonicalHash != (common.Hash{}) { for bloomTrieCount > 0 && canonicalHash != sectionHead && canonicalHash != (common.Hash{}) {
bloomTrieCount-- bloomTrieCount--
if bloomTrieCount > 0 { if bloomTrieCount > 0 {
sectionHeadNum = bloomTrieCount*BloomTrieFrequency - 1 sectionHeadNum = bloomTrieCount*BloomTrieFrequency - 1
sectionHead = odr.BloomTrieIndexer().SectionHead(bloomTrieCount - 1) sectionHead = odr.BloomTrieIndexer().SectionHead(bloomTrieCount - 1)
canonicalHash = core.GetCanonicalHash(db, sectionHeadNum) canonicalHash = rawdb.ReadCanonicalHash(db, sectionHeadNum)
} }
} }
} }
for i, sectionIdx := range sectionIdxList { for i, sectionIdx := range sectionIdxList {
sectionHead := core.GetCanonicalHash(db, (sectionIdx+1)*BloomTrieFrequency-1) sectionHead := rawdb.ReadCanonicalHash(db, (sectionIdx+1)*BloomTrieFrequency-1)
// if we don't have the canonical hash stored for this section head number, we'll still look for // if we don't have the canonical hash stored for this section head number, we'll still look for
// an entry with a zero sectionHead (we store it with zero section head too if we don't know it // an entry with a zero sectionHead (we store it with zero section head too if we don't know it
// at the time of the retrieval) // at the time of the retrieval)
bloomBits, err := core.GetBloomBits(db, bitIdx, sectionIdx, sectionHead) bloomBits, err := rawdb.ReadBloomBits(db, bitIdx, sectionIdx, sectionHead)
if err == nil { if err == nil {
result[i] = bloomBits result[i] = bloomBits
} else { } else {
......
...@@ -25,6 +25,7 @@ import ( ...@@ -25,6 +25,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/bitutil" "github.com/ethereum/go-ethereum/common/bitutil"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
"github.com/ethereum/go-ethereum/log" "github.com/ethereum/go-ethereum/log"
...@@ -161,7 +162,7 @@ func (c *ChtIndexerBackend) Process(header *types.Header) { ...@@ -161,7 +162,7 @@ func (c *ChtIndexerBackend) Process(header *types.Header) {
hash, num := header.Hash(), header.Number.Uint64() hash, num := header.Hash(), header.Number.Uint64()
c.lastHash = hash c.lastHash = hash
td := core.GetTd(c.diskdb, hash, num) td := rawdb.ReadTd(c.diskdb, hash, num)
if td == nil { if td == nil {
panic(nil) panic(nil)
} }
...@@ -272,7 +273,7 @@ func (b *BloomTrieIndexerBackend) Commit() error { ...@@ -272,7 +273,7 @@ func (b *BloomTrieIndexerBackend) Commit() error {
binary.BigEndian.PutUint64(encKey[2:10], b.section) binary.BigEndian.PutUint64(encKey[2:10], b.section)
var decomp []byte var decomp []byte
for j := uint64(0); j < b.bloomTrieRatio; j++ { for j := uint64(0); j < b.bloomTrieRatio; j++ {
data, err := core.GetBloomBits(b.diskdb, i, b.section*b.bloomTrieRatio+j, b.sectionHeads[j]) data, err := rawdb.ReadBloomBits(b.diskdb, i, b.section*b.bloomTrieRatio+j, b.sectionHeads[j])
if err != nil { if err != nil {
return err return err
} }
......
...@@ -24,6 +24,7 @@ import ( ...@@ -24,6 +24,7 @@ import (
"github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core" "github.com/ethereum/go-ethereum/core"
"github.com/ethereum/go-ethereum/core/rawdb"
"github.com/ethereum/go-ethereum/core/state" "github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/ethdb" "github.com/ethereum/go-ethereum/ethdb"
...@@ -183,9 +184,8 @@ func (pool *TxPool) checkMinedTxs(ctx context.Context, hash common.Hash, number ...@@ -183,9 +184,8 @@ func (pool *TxPool) checkMinedTxs(ctx context.Context, hash common.Hash, number
if _, err := GetBlockReceipts(ctx, pool.odr, hash, number); err != nil { // ODR caches, ignore results if _, err := GetBlockReceipts(ctx, pool.odr, hash, number); err != nil { // ODR caches, ignore results
return err return err
} }
if err := core.WriteTxLookupEntries(pool.chainDb, block); err != nil { rawdb.WriteTxLookupEntries(pool.chainDb, block)
return err
}
// Update the transaction pool's state // Update the transaction pool's state
for _, tx := range list { for _, tx := range list {
delete(pool.pending, tx.Hash()) delete(pool.pending, tx.Hash())
...@@ -202,7 +202,7 @@ func (pool *TxPool) rollbackTxs(hash common.Hash, txc txStateChanges) { ...@@ -202,7 +202,7 @@ func (pool *TxPool) rollbackTxs(hash common.Hash, txc txStateChanges) {
if list, ok := pool.mined[hash]; ok { if list, ok := pool.mined[hash]; ok {
for _, tx := range list { for _, tx := range list {
txHash := tx.Hash() txHash := tx.Hash()
core.DeleteTxLookupEntry(pool.chainDb, txHash) rawdb.DeleteTxLookupEntry(pool.chainDb, txHash)
pool.pending[txHash] = tx pool.pending[txHash] = tx
txc.setState(txHash, false) txc.setState(txHash, false)
} }
...@@ -258,7 +258,7 @@ func (pool *TxPool) reorgOnNewHead(ctx context.Context, newHeader *types.Header) ...@@ -258,7 +258,7 @@ func (pool *TxPool) reorgOnNewHead(ctx context.Context, newHeader *types.Header)
idx2 := idx - txPermanent idx2 := idx - txPermanent
if len(pool.mined) > 0 { if len(pool.mined) > 0 {
for i := pool.clearIdx; i < idx2; i++ { for i := pool.clearIdx; i < idx2; i++ {
hash := core.GetCanonicalHash(pool.chainDb, i) hash := rawdb.ReadCanonicalHash(pool.chainDb, i)
if list, ok := pool.mined[hash]; ok { if list, ok := pool.mined[hash]; ok {
hashes := make([]common.Hash, len(list)) hashes := make([]common.Hash, len(list))
for i, tx := range list { for i, tx := range list {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment