github.com/ethxdao/go-ethereum@v0.0.0-20221218102228-5ae34a9cc189/core/blockchain_test.go (about)

     1  // Copyright 2014 The go-ethereum Authors
     2  // This file is part of the go-ethereum library.
     3  //
     4  // The go-ethereum library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The go-ethereum library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package core
    18  
    19  import (
    20  	"errors"
    21  	"fmt"
    22  	"math/big"
    23  	"math/rand"
    24  	"os"
    25  	"sync"
    26  	"testing"
    27  	"time"
    28  
    29  	"github.com/ethxdao/go-ethereum/common"
    30  	"github.com/ethxdao/go-ethereum/common/math"
    31  	"github.com/ethxdao/go-ethereum/consensus"
    32  	"github.com/ethxdao/go-ethereum/consensus/beacon"
    33  	"github.com/ethxdao/go-ethereum/consensus/ethash"
    34  	"github.com/ethxdao/go-ethereum/core/rawdb"
    35  	"github.com/ethxdao/go-ethereum/core/state"
    36  	"github.com/ethxdao/go-ethereum/core/types"
    37  	"github.com/ethxdao/go-ethereum/core/vm"
    38  	"github.com/ethxdao/go-ethereum/crypto"
    39  	"github.com/ethxdao/go-ethereum/eth/tracers/logger"
    40  	"github.com/ethxdao/go-ethereum/ethdb"
    41  	"github.com/ethxdao/go-ethereum/params"
    42  	"github.com/ethxdao/go-ethereum/trie"
    43  )
    44  
    45  // So we can deterministically seed different blockchains
    46  var (
    47  	canonicalSeed = 1
    48  	forkSeed      = 2
    49  )
    50  
    51  // newCanonical creates a chain database, and injects a deterministic canonical
    52  // chain. Depending on the full flag, if creates either a full block chain or a
    53  // header only chain.
    54  func newCanonical(engine consensus.Engine, n int, full bool) (ethdb.Database, *BlockChain, error) {
    55  	var (
    56  		db      = rawdb.NewMemoryDatabase()
    57  		genesis = (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
    58  	)
    59  
    60  	// Initialize a fresh chain with only a genesis block
    61  	blockchain, _ := NewBlockChain(db, nil, params.AllEthashProtocolChanges, engine, vm.Config{}, nil, nil)
    62  	// Create and inject the requested chain
    63  	if n == 0 {
    64  		return db, blockchain, nil
    65  	}
    66  	if full {
    67  		// Full block-chain requested
    68  		blocks := makeBlockChain(genesis, n, engine, db, canonicalSeed)
    69  		_, err := blockchain.InsertChain(blocks)
    70  		return db, blockchain, err
    71  	}
    72  	// Header-only chain requested
    73  	headers := makeHeaderChain(genesis.Header(), n, engine, db, canonicalSeed)
    74  	_, err := blockchain.InsertHeaderChain(headers, 1)
    75  	return db, blockchain, err
    76  }
    77  
    78  func newGwei(n int64) *big.Int {
    79  	return new(big.Int).Mul(big.NewInt(n), big.NewInt(params.GWei))
    80  }
    81  
    82  // Test fork of length N starting from block i
    83  func testFork(t *testing.T, blockchain *BlockChain, i, n int, full bool, comparator func(td1, td2 *big.Int)) {
    84  	// Copy old chain up to #i into a new db
    85  	db, blockchain2, err := newCanonical(ethash.NewFaker(), i, full)
    86  	if err != nil {
    87  		t.Fatal("could not make new canonical in testFork", err)
    88  	}
    89  	defer blockchain2.Stop()
    90  
    91  	// Assert the chains have the same header/block at #i
    92  	var hash1, hash2 common.Hash
    93  	if full {
    94  		hash1 = blockchain.GetBlockByNumber(uint64(i)).Hash()
    95  		hash2 = blockchain2.GetBlockByNumber(uint64(i)).Hash()
    96  	} else {
    97  		hash1 = blockchain.GetHeaderByNumber(uint64(i)).Hash()
    98  		hash2 = blockchain2.GetHeaderByNumber(uint64(i)).Hash()
    99  	}
   100  	if hash1 != hash2 {
   101  		t.Errorf("chain content mismatch at %d: have hash %v, want hash %v", i, hash2, hash1)
   102  	}
   103  	// Extend the newly created chain
   104  	var (
   105  		blockChainB  []*types.Block
   106  		headerChainB []*types.Header
   107  	)
   108  	if full {
   109  		blockChainB = makeBlockChain(blockchain2.CurrentBlock(), n, ethash.NewFaker(), db, forkSeed)
   110  		if _, err := blockchain2.InsertChain(blockChainB); err != nil {
   111  			t.Fatalf("failed to insert forking chain: %v", err)
   112  		}
   113  	} else {
   114  		headerChainB = makeHeaderChain(blockchain2.CurrentHeader(), n, ethash.NewFaker(), db, forkSeed)
   115  		if _, err := blockchain2.InsertHeaderChain(headerChainB, 1); err != nil {
   116  			t.Fatalf("failed to insert forking chain: %v", err)
   117  		}
   118  	}
   119  	// Sanity check that the forked chain can be imported into the original
   120  	var tdPre, tdPost *big.Int
   121  
   122  	if full {
   123  		cur := blockchain.CurrentBlock()
   124  		tdPre = blockchain.GetTd(cur.Hash(), cur.NumberU64())
   125  		if err := testBlockChainImport(blockChainB, blockchain); err != nil {
   126  			t.Fatalf("failed to import forked block chain: %v", err)
   127  		}
   128  		last := blockChainB[len(blockChainB)-1]
   129  		tdPost = blockchain.GetTd(last.Hash(), last.NumberU64())
   130  	} else {
   131  		cur := blockchain.CurrentHeader()
   132  		tdPre = blockchain.GetTd(cur.Hash(), cur.Number.Uint64())
   133  		if err := testHeaderChainImport(headerChainB, blockchain); err != nil {
   134  			t.Fatalf("failed to import forked header chain: %v", err)
   135  		}
   136  		last := headerChainB[len(headerChainB)-1]
   137  		tdPost = blockchain.GetTd(last.Hash(), last.Number.Uint64())
   138  	}
   139  	// Compare the total difficulties of the chains
   140  	comparator(tdPre, tdPost)
   141  }
   142  
   143  // testBlockChainImport tries to process a chain of blocks, writing them into
   144  // the database if successful.
   145  func testBlockChainImport(chain types.Blocks, blockchain *BlockChain) error {
   146  	for _, block := range chain {
   147  		// Try and process the block
   148  		err := blockchain.engine.VerifyHeader(blockchain, block.Header(), true)
   149  		if err == nil {
   150  			err = blockchain.validator.ValidateBody(block)
   151  		}
   152  		if err != nil {
   153  			if err == ErrKnownBlock {
   154  				continue
   155  			}
   156  			return err
   157  		}
   158  		statedb, err := state.New(blockchain.GetBlockByHash(block.ParentHash()).Root(), blockchain.stateCache, nil)
   159  		if err != nil {
   160  			return err
   161  		}
   162  		receipts, _, usedGas, err := blockchain.processor.Process(block, statedb, vm.Config{})
   163  		if err != nil {
   164  			blockchain.reportBlock(block, receipts, err)
   165  			return err
   166  		}
   167  		err = blockchain.validator.ValidateState(block, statedb, receipts, usedGas)
   168  		if err != nil {
   169  			blockchain.reportBlock(block, receipts, err)
   170  			return err
   171  		}
   172  
   173  		blockchain.chainmu.MustLock()
   174  		rawdb.WriteTd(blockchain.db, block.Hash(), block.NumberU64(), new(big.Int).Add(block.Difficulty(), blockchain.GetTd(block.ParentHash(), block.NumberU64()-1)))
   175  		rawdb.WriteBlock(blockchain.db, block)
   176  		statedb.Commit(false)
   177  		blockchain.chainmu.Unlock()
   178  	}
   179  	return nil
   180  }
   181  
   182  // testHeaderChainImport tries to process a chain of header, writing them into
   183  // the database if successful.
   184  func testHeaderChainImport(chain []*types.Header, blockchain *BlockChain) error {
   185  	for _, header := range chain {
   186  		// Try and validate the header
   187  		if err := blockchain.engine.VerifyHeader(blockchain, header, false); err != nil {
   188  			return err
   189  		}
   190  		// Manually insert the header into the database, but don't reorganise (allows subsequent testing)
   191  		blockchain.chainmu.MustLock()
   192  		rawdb.WriteTd(blockchain.db, header.Hash(), header.Number.Uint64(), new(big.Int).Add(header.Difficulty, blockchain.GetTd(header.ParentHash, header.Number.Uint64()-1)))
   193  		rawdb.WriteHeader(blockchain.db, header)
   194  		blockchain.chainmu.Unlock()
   195  	}
   196  	return nil
   197  }
   198  
   199  func TestLastBlock(t *testing.T) {
   200  	_, blockchain, err := newCanonical(ethash.NewFaker(), 0, true)
   201  	if err != nil {
   202  		t.Fatalf("failed to create pristine chain: %v", err)
   203  	}
   204  	defer blockchain.Stop()
   205  
   206  	blocks := makeBlockChain(blockchain.CurrentBlock(), 1, ethash.NewFullFaker(), blockchain.db, 0)
   207  	if _, err := blockchain.InsertChain(blocks); err != nil {
   208  		t.Fatalf("Failed to insert block: %v", err)
   209  	}
   210  	if blocks[len(blocks)-1].Hash() != rawdb.ReadHeadBlockHash(blockchain.db) {
   211  		t.Fatalf("Write/Get HeadBlockHash failed")
   212  	}
   213  }
   214  
   215  // Test inserts the blocks/headers after the fork choice rule is changed.
   216  // The chain is reorged to whatever specified.
   217  func testInsertAfterMerge(t *testing.T, blockchain *BlockChain, i, n int, full bool) {
   218  	// Copy old chain up to #i into a new db
   219  	db, blockchain2, err := newCanonical(ethash.NewFaker(), i, full)
   220  	if err != nil {
   221  		t.Fatal("could not make new canonical in testFork", err)
   222  	}
   223  	defer blockchain2.Stop()
   224  
   225  	// Assert the chains have the same header/block at #i
   226  	var hash1, hash2 common.Hash
   227  	if full {
   228  		hash1 = blockchain.GetBlockByNumber(uint64(i)).Hash()
   229  		hash2 = blockchain2.GetBlockByNumber(uint64(i)).Hash()
   230  	} else {
   231  		hash1 = blockchain.GetHeaderByNumber(uint64(i)).Hash()
   232  		hash2 = blockchain2.GetHeaderByNumber(uint64(i)).Hash()
   233  	}
   234  	if hash1 != hash2 {
   235  		t.Errorf("chain content mismatch at %d: have hash %v, want hash %v", i, hash2, hash1)
   236  	}
   237  
   238  	// Extend the newly created chain
   239  	if full {
   240  		blockChainB := makeBlockChain(blockchain2.CurrentBlock(), n, ethash.NewFaker(), db, forkSeed)
   241  		if _, err := blockchain2.InsertChain(blockChainB); err != nil {
   242  			t.Fatalf("failed to insert forking chain: %v", err)
   243  		}
   244  		if blockchain2.CurrentBlock().NumberU64() != blockChainB[len(blockChainB)-1].NumberU64() {
   245  			t.Fatalf("failed to reorg to the given chain")
   246  		}
   247  		if blockchain2.CurrentBlock().Hash() != blockChainB[len(blockChainB)-1].Hash() {
   248  			t.Fatalf("failed to reorg to the given chain")
   249  		}
   250  	} else {
   251  		headerChainB := makeHeaderChain(blockchain2.CurrentHeader(), n, ethash.NewFaker(), db, forkSeed)
   252  		if _, err := blockchain2.InsertHeaderChain(headerChainB, 1); err != nil {
   253  			t.Fatalf("failed to insert forking chain: %v", err)
   254  		}
   255  		if blockchain2.CurrentHeader().Number.Uint64() != headerChainB[len(headerChainB)-1].Number.Uint64() {
   256  			t.Fatalf("failed to reorg to the given chain")
   257  		}
   258  		if blockchain2.CurrentHeader().Hash() != headerChainB[len(headerChainB)-1].Hash() {
   259  			t.Fatalf("failed to reorg to the given chain")
   260  		}
   261  	}
   262  }
   263  
   264  // Tests that given a starting canonical chain of a given size, it can be extended
   265  // with various length chains.
   266  func TestExtendCanonicalHeaders(t *testing.T) { testExtendCanonical(t, false) }
   267  func TestExtendCanonicalBlocks(t *testing.T)  { testExtendCanonical(t, true) }
   268  
   269  func testExtendCanonical(t *testing.T, full bool) {
   270  	length := 5
   271  
   272  	// Make first chain starting from genesis
   273  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   274  	if err != nil {
   275  		t.Fatalf("failed to make new canonical chain: %v", err)
   276  	}
   277  	defer processor.Stop()
   278  
   279  	// Define the difficulty comparator
   280  	better := func(td1, td2 *big.Int) {
   281  		if td2.Cmp(td1) <= 0 {
   282  			t.Errorf("total difficulty mismatch: have %v, expected more than %v", td2, td1)
   283  		}
   284  	}
   285  	// Start fork from current height
   286  	testFork(t, processor, length, 1, full, better)
   287  	testFork(t, processor, length, 2, full, better)
   288  	testFork(t, processor, length, 5, full, better)
   289  	testFork(t, processor, length, 10, full, better)
   290  }
   291  
   292  // Tests that given a starting canonical chain of a given size, it can be extended
   293  // with various length chains.
   294  func TestExtendCanonicalHeadersAfterMerge(t *testing.T) { testExtendCanonicalAfterMerge(t, false) }
   295  func TestExtendCanonicalBlocksAfterMerge(t *testing.T)  { testExtendCanonicalAfterMerge(t, true) }
   296  
   297  func testExtendCanonicalAfterMerge(t *testing.T, full bool) {
   298  	length := 5
   299  
   300  	// Make first chain starting from genesis
   301  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   302  	if err != nil {
   303  		t.Fatalf("failed to make new canonical chain: %v", err)
   304  	}
   305  	defer processor.Stop()
   306  
   307  	testInsertAfterMerge(t, processor, length, 1, full)
   308  	testInsertAfterMerge(t, processor, length, 10, full)
   309  }
   310  
   311  // Tests that given a starting canonical chain of a given size, creating shorter
   312  // forks do not take canonical ownership.
   313  func TestShorterForkHeaders(t *testing.T) { testShorterFork(t, false) }
   314  func TestShorterForkBlocks(t *testing.T)  { testShorterFork(t, true) }
   315  
   316  func testShorterFork(t *testing.T, full bool) {
   317  	length := 10
   318  
   319  	// Make first chain starting from genesis
   320  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   321  	if err != nil {
   322  		t.Fatalf("failed to make new canonical chain: %v", err)
   323  	}
   324  	defer processor.Stop()
   325  
   326  	// Define the difficulty comparator
   327  	worse := func(td1, td2 *big.Int) {
   328  		if td2.Cmp(td1) >= 0 {
   329  			t.Errorf("total difficulty mismatch: have %v, expected less than %v", td2, td1)
   330  		}
   331  	}
   332  	// Sum of numbers must be less than `length` for this to be a shorter fork
   333  	testFork(t, processor, 0, 3, full, worse)
   334  	testFork(t, processor, 0, 7, full, worse)
   335  	testFork(t, processor, 1, 1, full, worse)
   336  	testFork(t, processor, 1, 7, full, worse)
   337  	testFork(t, processor, 5, 3, full, worse)
   338  	testFork(t, processor, 5, 4, full, worse)
   339  }
   340  
   341  // Tests that given a starting canonical chain of a given size, creating shorter
   342  // forks do not take canonical ownership.
   343  func TestShorterForkHeadersAfterMerge(t *testing.T) { testShorterForkAfterMerge(t, false) }
   344  func TestShorterForkBlocksAfterMerge(t *testing.T)  { testShorterForkAfterMerge(t, true) }
   345  
   346  func testShorterForkAfterMerge(t *testing.T, full bool) {
   347  	length := 10
   348  
   349  	// Make first chain starting from genesis
   350  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   351  	if err != nil {
   352  		t.Fatalf("failed to make new canonical chain: %v", err)
   353  	}
   354  	defer processor.Stop()
   355  
   356  	testInsertAfterMerge(t, processor, 0, 3, full)
   357  	testInsertAfterMerge(t, processor, 0, 7, full)
   358  	testInsertAfterMerge(t, processor, 1, 1, full)
   359  	testInsertAfterMerge(t, processor, 1, 7, full)
   360  	testInsertAfterMerge(t, processor, 5, 3, full)
   361  	testInsertAfterMerge(t, processor, 5, 4, full)
   362  }
   363  
   364  // Tests that given a starting canonical chain of a given size, creating longer
   365  // forks do take canonical ownership.
   366  func TestLongerForkHeaders(t *testing.T) { testLongerFork(t, false) }
   367  func TestLongerForkBlocks(t *testing.T)  { testLongerFork(t, true) }
   368  
   369  func testLongerFork(t *testing.T, full bool) {
   370  	length := 10
   371  
   372  	// Make first chain starting from genesis
   373  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   374  	if err != nil {
   375  		t.Fatalf("failed to make new canonical chain: %v", err)
   376  	}
   377  	defer processor.Stop()
   378  
   379  	testInsertAfterMerge(t, processor, 0, 11, full)
   380  	testInsertAfterMerge(t, processor, 0, 15, full)
   381  	testInsertAfterMerge(t, processor, 1, 10, full)
   382  	testInsertAfterMerge(t, processor, 1, 12, full)
   383  	testInsertAfterMerge(t, processor, 5, 6, full)
   384  	testInsertAfterMerge(t, processor, 5, 8, full)
   385  }
   386  
   387  // Tests that given a starting canonical chain of a given size, creating longer
   388  // forks do take canonical ownership.
   389  func TestLongerForkHeadersAfterMerge(t *testing.T) { testLongerForkAfterMerge(t, false) }
   390  func TestLongerForkBlocksAfterMerge(t *testing.T)  { testLongerForkAfterMerge(t, true) }
   391  
   392  func testLongerForkAfterMerge(t *testing.T, full bool) {
   393  	length := 10
   394  
   395  	// Make first chain starting from genesis
   396  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   397  	if err != nil {
   398  		t.Fatalf("failed to make new canonical chain: %v", err)
   399  	}
   400  	defer processor.Stop()
   401  
   402  	testInsertAfterMerge(t, processor, 0, 11, full)
   403  	testInsertAfterMerge(t, processor, 0, 15, full)
   404  	testInsertAfterMerge(t, processor, 1, 10, full)
   405  	testInsertAfterMerge(t, processor, 1, 12, full)
   406  	testInsertAfterMerge(t, processor, 5, 6, full)
   407  	testInsertAfterMerge(t, processor, 5, 8, full)
   408  }
   409  
   410  // Tests that given a starting canonical chain of a given size, creating equal
   411  // forks do take canonical ownership.
   412  func TestEqualForkHeaders(t *testing.T) { testEqualFork(t, false) }
   413  func TestEqualForkBlocks(t *testing.T)  { testEqualFork(t, true) }
   414  
   415  func testEqualFork(t *testing.T, full bool) {
   416  	length := 10
   417  
   418  	// Make first chain starting from genesis
   419  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   420  	if err != nil {
   421  		t.Fatalf("failed to make new canonical chain: %v", err)
   422  	}
   423  	defer processor.Stop()
   424  
   425  	// Define the difficulty comparator
   426  	equal := func(td1, td2 *big.Int) {
   427  		if td2.Cmp(td1) != 0 {
   428  			t.Errorf("total difficulty mismatch: have %v, want %v", td2, td1)
   429  		}
   430  	}
   431  	// Sum of numbers must be equal to `length` for this to be an equal fork
   432  	testFork(t, processor, 0, 10, full, equal)
   433  	testFork(t, processor, 1, 9, full, equal)
   434  	testFork(t, processor, 2, 8, full, equal)
   435  	testFork(t, processor, 5, 5, full, equal)
   436  	testFork(t, processor, 6, 4, full, equal)
   437  	testFork(t, processor, 9, 1, full, equal)
   438  }
   439  
   440  // Tests that given a starting canonical chain of a given size, creating equal
   441  // forks do take canonical ownership.
   442  func TestEqualForkHeadersAfterMerge(t *testing.T) { testEqualForkAfterMerge(t, false) }
   443  func TestEqualForkBlocksAfterMerge(t *testing.T)  { testEqualForkAfterMerge(t, true) }
   444  
   445  func testEqualForkAfterMerge(t *testing.T, full bool) {
   446  	length := 10
   447  
   448  	// Make first chain starting from genesis
   449  	_, processor, err := newCanonical(ethash.NewFaker(), length, full)
   450  	if err != nil {
   451  		t.Fatalf("failed to make new canonical chain: %v", err)
   452  	}
   453  	defer processor.Stop()
   454  
   455  	testInsertAfterMerge(t, processor, 0, 10, full)
   456  	testInsertAfterMerge(t, processor, 1, 9, full)
   457  	testInsertAfterMerge(t, processor, 2, 8, full)
   458  	testInsertAfterMerge(t, processor, 5, 5, full)
   459  	testInsertAfterMerge(t, processor, 6, 4, full)
   460  	testInsertAfterMerge(t, processor, 9, 1, full)
   461  }
   462  
   463  // Tests that chains missing links do not get accepted by the processor.
   464  func TestBrokenHeaderChain(t *testing.T) { testBrokenChain(t, false) }
   465  func TestBrokenBlockChain(t *testing.T)  { testBrokenChain(t, true) }
   466  
   467  func testBrokenChain(t *testing.T, full bool) {
   468  	// Make chain starting from genesis
   469  	db, blockchain, err := newCanonical(ethash.NewFaker(), 10, full)
   470  	if err != nil {
   471  		t.Fatalf("failed to make new canonical chain: %v", err)
   472  	}
   473  	defer blockchain.Stop()
   474  
   475  	// Create a forked chain, and try to insert with a missing link
   476  	if full {
   477  		chain := makeBlockChain(blockchain.CurrentBlock(), 5, ethash.NewFaker(), db, forkSeed)[1:]
   478  		if err := testBlockChainImport(chain, blockchain); err == nil {
   479  			t.Errorf("broken block chain not reported")
   480  		}
   481  	} else {
   482  		chain := makeHeaderChain(blockchain.CurrentHeader(), 5, ethash.NewFaker(), db, forkSeed)[1:]
   483  		if err := testHeaderChainImport(chain, blockchain); err == nil {
   484  			t.Errorf("broken header chain not reported")
   485  		}
   486  	}
   487  }
   488  
   489  // Tests that reorganising a long difficult chain after a short easy one
   490  // overwrites the canonical numbers and links in the database.
   491  func TestReorgLongHeaders(t *testing.T) { testReorgLong(t, false) }
   492  func TestReorgLongBlocks(t *testing.T)  { testReorgLong(t, true) }
   493  
   494  func testReorgLong(t *testing.T, full bool) {
   495  	testReorg(t, []int64{0, 0, -9}, []int64{0, 0, 0, -9}, 393280+params.GenesisDifficulty.Int64(), full)
   496  }
   497  
   498  // Tests that reorganising a short difficult chain after a long easy one
   499  // overwrites the canonical numbers and links in the database.
   500  func TestReorgShortHeaders(t *testing.T) { testReorgShort(t, false) }
   501  func TestReorgShortBlocks(t *testing.T)  { testReorgShort(t, true) }
   502  
   503  func testReorgShort(t *testing.T, full bool) {
   504  	// Create a long easy chain vs. a short heavy one. Due to difficulty adjustment
   505  	// we need a fairly long chain of blocks with different difficulties for a short
   506  	// one to become heavier than a long one. The 96 is an empirical value.
   507  	easy := make([]int64, 96)
   508  	for i := 0; i < len(easy); i++ {
   509  		easy[i] = 60
   510  	}
   511  	diff := make([]int64, len(easy)-1)
   512  	for i := 0; i < len(diff); i++ {
   513  		diff[i] = -9
   514  	}
   515  	testReorg(t, easy, diff, 12615120+params.GenesisDifficulty.Int64(), full)
   516  }
   517  
   518  func testReorg(t *testing.T, first, second []int64, td int64, full bool) {
   519  	// Create a pristine chain and database
   520  	db, blockchain, err := newCanonical(ethash.NewFaker(), 0, full)
   521  	if err != nil {
   522  		t.Fatalf("failed to create pristine chain: %v", err)
   523  	}
   524  	defer blockchain.Stop()
   525  
   526  	// Insert an easy and a difficult chain afterwards
   527  	easyBlocks, _ := GenerateChain(params.TestChainConfig, blockchain.CurrentBlock(), ethash.NewFaker(), db, len(first), func(i int, b *BlockGen) {
   528  		b.OffsetTime(first[i])
   529  	})
   530  	diffBlocks, _ := GenerateChain(params.TestChainConfig, blockchain.CurrentBlock(), ethash.NewFaker(), db, len(second), func(i int, b *BlockGen) {
   531  		b.OffsetTime(second[i])
   532  	})
   533  	if full {
   534  		if _, err := blockchain.InsertChain(easyBlocks); err != nil {
   535  			t.Fatalf("failed to insert easy chain: %v", err)
   536  		}
   537  		if _, err := blockchain.InsertChain(diffBlocks); err != nil {
   538  			t.Fatalf("failed to insert difficult chain: %v", err)
   539  		}
   540  	} else {
   541  		easyHeaders := make([]*types.Header, len(easyBlocks))
   542  		for i, block := range easyBlocks {
   543  			easyHeaders[i] = block.Header()
   544  		}
   545  		diffHeaders := make([]*types.Header, len(diffBlocks))
   546  		for i, block := range diffBlocks {
   547  			diffHeaders[i] = block.Header()
   548  		}
   549  		if _, err := blockchain.InsertHeaderChain(easyHeaders, 1); err != nil {
   550  			t.Fatalf("failed to insert easy chain: %v", err)
   551  		}
   552  		if _, err := blockchain.InsertHeaderChain(diffHeaders, 1); err != nil {
   553  			t.Fatalf("failed to insert difficult chain: %v", err)
   554  		}
   555  	}
   556  	// Check that the chain is valid number and link wise
   557  	if full {
   558  		prev := blockchain.CurrentBlock()
   559  		for block := blockchain.GetBlockByNumber(blockchain.CurrentBlock().NumberU64() - 1); block.NumberU64() != 0; prev, block = block, blockchain.GetBlockByNumber(block.NumberU64()-1) {
   560  			if prev.ParentHash() != block.Hash() {
   561  				t.Errorf("parent block hash mismatch: have %x, want %x", prev.ParentHash(), block.Hash())
   562  			}
   563  		}
   564  	} else {
   565  		prev := blockchain.CurrentHeader()
   566  		for header := blockchain.GetHeaderByNumber(blockchain.CurrentHeader().Number.Uint64() - 1); header.Number.Uint64() != 0; prev, header = header, blockchain.GetHeaderByNumber(header.Number.Uint64()-1) {
   567  			if prev.ParentHash != header.Hash() {
   568  				t.Errorf("parent header hash mismatch: have %x, want %x", prev.ParentHash, header.Hash())
   569  			}
   570  		}
   571  	}
   572  	// Make sure the chain total difficulty is the correct one
   573  	want := new(big.Int).Add(blockchain.genesisBlock.Difficulty(), big.NewInt(td))
   574  	if full {
   575  		cur := blockchain.CurrentBlock()
   576  		if have := blockchain.GetTd(cur.Hash(), cur.NumberU64()); have.Cmp(want) != 0 {
   577  			t.Errorf("total difficulty mismatch: have %v, want %v", have, want)
   578  		}
   579  	} else {
   580  		cur := blockchain.CurrentHeader()
   581  		if have := blockchain.GetTd(cur.Hash(), cur.Number.Uint64()); have.Cmp(want) != 0 {
   582  			t.Errorf("total difficulty mismatch: have %v, want %v", have, want)
   583  		}
   584  	}
   585  }
   586  
   587  // Tests that the insertion functions detect banned hashes.
   588  func TestBadHeaderHashes(t *testing.T) { testBadHashes(t, false) }
   589  func TestBadBlockHashes(t *testing.T)  { testBadHashes(t, true) }
   590  
   591  func testBadHashes(t *testing.T, full bool) {
   592  	// Create a pristine chain and database
   593  	db, blockchain, err := newCanonical(ethash.NewFaker(), 0, full)
   594  	if err != nil {
   595  		t.Fatalf("failed to create pristine chain: %v", err)
   596  	}
   597  	defer blockchain.Stop()
   598  
   599  	// Create a chain, ban a hash and try to import
   600  	if full {
   601  		blocks := makeBlockChain(blockchain.CurrentBlock(), 3, ethash.NewFaker(), db, 10)
   602  
   603  		BadHashes[blocks[2].Header().Hash()] = true
   604  		defer func() { delete(BadHashes, blocks[2].Header().Hash()) }()
   605  
   606  		_, err = blockchain.InsertChain(blocks)
   607  	} else {
   608  		headers := makeHeaderChain(blockchain.CurrentHeader(), 3, ethash.NewFaker(), db, 10)
   609  
   610  		BadHashes[headers[2].Hash()] = true
   611  		defer func() { delete(BadHashes, headers[2].Hash()) }()
   612  
   613  		_, err = blockchain.InsertHeaderChain(headers, 1)
   614  	}
   615  	if !errors.Is(err, ErrBannedHash) {
   616  		t.Errorf("error mismatch: have: %v, want: %v", err, ErrBannedHash)
   617  	}
   618  }
   619  
   620  // Tests that bad hashes are detected on boot, and the chain rolled back to a
   621  // good state prior to the bad hash.
   622  func TestReorgBadHeaderHashes(t *testing.T) { testReorgBadHashes(t, false) }
   623  func TestReorgBadBlockHashes(t *testing.T)  { testReorgBadHashes(t, true) }
   624  
   625  func testReorgBadHashes(t *testing.T, full bool) {
   626  	// Create a pristine chain and database
   627  	db, blockchain, err := newCanonical(ethash.NewFaker(), 0, full)
   628  	if err != nil {
   629  		t.Fatalf("failed to create pristine chain: %v", err)
   630  	}
   631  	// Create a chain, import and ban afterwards
   632  	headers := makeHeaderChain(blockchain.CurrentHeader(), 4, ethash.NewFaker(), db, 10)
   633  	blocks := makeBlockChain(blockchain.CurrentBlock(), 4, ethash.NewFaker(), db, 10)
   634  
   635  	if full {
   636  		if _, err = blockchain.InsertChain(blocks); err != nil {
   637  			t.Errorf("failed to import blocks: %v", err)
   638  		}
   639  		if blockchain.CurrentBlock().Hash() != blocks[3].Hash() {
   640  			t.Errorf("last block hash mismatch: have: %x, want %x", blockchain.CurrentBlock().Hash(), blocks[3].Header().Hash())
   641  		}
   642  		BadHashes[blocks[3].Header().Hash()] = true
   643  		defer func() { delete(BadHashes, blocks[3].Header().Hash()) }()
   644  	} else {
   645  		if _, err = blockchain.InsertHeaderChain(headers, 1); err != nil {
   646  			t.Errorf("failed to import headers: %v", err)
   647  		}
   648  		if blockchain.CurrentHeader().Hash() != headers[3].Hash() {
   649  			t.Errorf("last header hash mismatch: have: %x, want %x", blockchain.CurrentHeader().Hash(), headers[3].Hash())
   650  		}
   651  		BadHashes[headers[3].Hash()] = true
   652  		defer func() { delete(BadHashes, headers[3].Hash()) }()
   653  	}
   654  	blockchain.Stop()
   655  
   656  	// Create a new BlockChain and check that it rolled back the state.
   657  	ncm, err := NewBlockChain(blockchain.db, nil, blockchain.chainConfig, ethash.NewFaker(), vm.Config{}, nil, nil)
   658  	if err != nil {
   659  		t.Fatalf("failed to create new chain manager: %v", err)
   660  	}
   661  	if full {
   662  		if ncm.CurrentBlock().Hash() != blocks[2].Header().Hash() {
   663  			t.Errorf("last block hash mismatch: have: %x, want %x", ncm.CurrentBlock().Hash(), blocks[2].Header().Hash())
   664  		}
   665  		if blocks[2].Header().GasLimit != ncm.GasLimit() {
   666  			t.Errorf("last  block gasLimit mismatch: have: %d, want %d", ncm.GasLimit(), blocks[2].Header().GasLimit)
   667  		}
   668  	} else {
   669  		if ncm.CurrentHeader().Hash() != headers[2].Hash() {
   670  			t.Errorf("last header hash mismatch: have: %x, want %x", ncm.CurrentHeader().Hash(), headers[2].Hash())
   671  		}
   672  	}
   673  	ncm.Stop()
   674  }
   675  
   676  // Tests chain insertions in the face of one entity containing an invalid nonce.
   677  func TestHeadersInsertNonceError(t *testing.T) { testInsertNonceError(t, false) }
   678  func TestBlocksInsertNonceError(t *testing.T)  { testInsertNonceError(t, true) }
   679  
   680  func testInsertNonceError(t *testing.T, full bool) {
   681  	for i := 1; i < 25 && !t.Failed(); i++ {
   682  		// Create a pristine chain and database
   683  		db, blockchain, err := newCanonical(ethash.NewFaker(), 0, full)
   684  		if err != nil {
   685  			t.Fatalf("failed to create pristine chain: %v", err)
   686  		}
   687  		defer blockchain.Stop()
   688  
   689  		// Create and insert a chain with a failing nonce
   690  		var (
   691  			failAt  int
   692  			failRes int
   693  			failNum uint64
   694  		)
   695  		if full {
   696  			blocks := makeBlockChain(blockchain.CurrentBlock(), i, ethash.NewFaker(), db, 0)
   697  
   698  			failAt = rand.Int() % len(blocks)
   699  			failNum = blocks[failAt].NumberU64()
   700  
   701  			blockchain.engine = ethash.NewFakeFailer(failNum)
   702  			failRes, err = blockchain.InsertChain(blocks)
   703  		} else {
   704  			headers := makeHeaderChain(blockchain.CurrentHeader(), i, ethash.NewFaker(), db, 0)
   705  
   706  			failAt = rand.Int() % len(headers)
   707  			failNum = headers[failAt].Number.Uint64()
   708  
   709  			blockchain.engine = ethash.NewFakeFailer(failNum)
   710  			blockchain.hc.engine = blockchain.engine
   711  			failRes, err = blockchain.InsertHeaderChain(headers, 1)
   712  		}
   713  		// Check that the returned error indicates the failure
   714  		if failRes != failAt {
   715  			t.Errorf("test %d: failure (%v) index mismatch: have %d, want %d", i, err, failRes, failAt)
   716  		}
   717  		// Check that all blocks after the failing block have been inserted
   718  		for j := 0; j < i-failAt; j++ {
   719  			if full {
   720  				if block := blockchain.GetBlockByNumber(failNum + uint64(j)); block != nil {
   721  					t.Errorf("test %d: invalid block in chain: %v", i, block)
   722  				}
   723  			} else {
   724  				if header := blockchain.GetHeaderByNumber(failNum + uint64(j)); header != nil {
   725  					t.Errorf("test %d: invalid header in chain: %v", i, header)
   726  				}
   727  			}
   728  		}
   729  	}
   730  }
   731  
   732  // Tests that fast importing a block chain produces the same chain data as the
   733  // classical full block processing.
   734  func TestFastVsFullChains(t *testing.T) {
   735  	// Configure and generate a sample block chain
   736  	var (
   737  		gendb   = rawdb.NewMemoryDatabase()
   738  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
   739  		address = crypto.PubkeyToAddress(key.PublicKey)
   740  		funds   = big.NewInt(1000000000000000)
   741  		gspec   = &Genesis{
   742  			Config:  params.TestChainConfig,
   743  			Alloc:   GenesisAlloc{address: {Balance: funds}},
   744  			BaseFee: big.NewInt(params.InitialBaseFee),
   745  		}
   746  		genesis = gspec.MustCommit(gendb)
   747  		signer  = types.LatestSigner(gspec.Config)
   748  	)
   749  	blocks, receipts := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), gendb, 1024, func(i int, block *BlockGen) {
   750  		block.SetCoinbase(common.Address{0x00})
   751  
   752  		// If the block number is multiple of 3, send a few bonus transactions to the miner
   753  		if i%3 == 2 {
   754  			for j := 0; j < i%4+1; j++ {
   755  				tx, err := types.SignTx(types.NewTransaction(block.TxNonce(address), common.Address{0x00}, big.NewInt(1000), params.TxGas, block.header.BaseFee, nil), signer, key)
   756  				if err != nil {
   757  					panic(err)
   758  				}
   759  				block.AddTx(tx)
   760  			}
   761  		}
   762  		// If the block number is a multiple of 5, add an uncle to the block
   763  		if i%5 == 4 {
   764  			block.AddUncle(&types.Header{ParentHash: block.PrevBlock(i - 2).Hash(), Number: big.NewInt(int64(i))})
   765  		}
   766  	})
   767  	// Import the chain as an archive node for the comparison baseline
   768  	archiveDb := rawdb.NewMemoryDatabase()
   769  	gspec.MustCommit(archiveDb)
   770  	archive, _ := NewBlockChain(archiveDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   771  	defer archive.Stop()
   772  
   773  	if n, err := archive.InsertChain(blocks); err != nil {
   774  		t.Fatalf("failed to process block %d: %v", n, err)
   775  	}
   776  	// Fast import the chain as a non-archive node to test
   777  	fastDb := rawdb.NewMemoryDatabase()
   778  	gspec.MustCommit(fastDb)
   779  	fast, _ := NewBlockChain(fastDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   780  	defer fast.Stop()
   781  
   782  	headers := make([]*types.Header, len(blocks))
   783  	for i, block := range blocks {
   784  		headers[i] = block.Header()
   785  	}
   786  	if n, err := fast.InsertHeaderChain(headers, 1); err != nil {
   787  		t.Fatalf("failed to insert header %d: %v", n, err)
   788  	}
   789  	if n, err := fast.InsertReceiptChain(blocks, receipts, 0); err != nil {
   790  		t.Fatalf("failed to insert receipt %d: %v", n, err)
   791  	}
   792  	// Freezer style fast import the chain.
   793  	frdir := t.TempDir()
   794  	ancientDb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
   795  	if err != nil {
   796  		t.Fatalf("failed to create temp freezer db: %v", err)
   797  	}
   798  	defer ancientDb.Close()
   799  	gspec.MustCommit(ancientDb)
   800  	ancient, _ := NewBlockChain(ancientDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   801  	defer ancient.Stop()
   802  
   803  	if n, err := ancient.InsertHeaderChain(headers, 1); err != nil {
   804  		t.Fatalf("failed to insert header %d: %v", n, err)
   805  	}
   806  	if n, err := ancient.InsertReceiptChain(blocks, receipts, uint64(len(blocks)/2)); err != nil {
   807  		t.Fatalf("failed to insert receipt %d: %v", n, err)
   808  	}
   809  
   810  	// Iterate over all chain data components, and cross reference
   811  	for i := 0; i < len(blocks); i++ {
   812  		num, hash := blocks[i].NumberU64(), blocks[i].Hash()
   813  
   814  		if ftd, atd := fast.GetTd(hash, num), archive.GetTd(hash, num); ftd.Cmp(atd) != 0 {
   815  			t.Errorf("block #%d [%x]: td mismatch: fastdb %v, archivedb %v", num, hash, ftd, atd)
   816  		}
   817  		if antd, artd := ancient.GetTd(hash, num), archive.GetTd(hash, num); antd.Cmp(artd) != 0 {
   818  			t.Errorf("block #%d [%x]: td mismatch: ancientdb %v, archivedb %v", num, hash, antd, artd)
   819  		}
   820  		if fheader, aheader := fast.GetHeaderByHash(hash), archive.GetHeaderByHash(hash); fheader.Hash() != aheader.Hash() {
   821  			t.Errorf("block #%d [%x]: header mismatch: fastdb %v, archivedb %v", num, hash, fheader, aheader)
   822  		}
   823  		if anheader, arheader := ancient.GetHeaderByHash(hash), archive.GetHeaderByHash(hash); anheader.Hash() != arheader.Hash() {
   824  			t.Errorf("block #%d [%x]: header mismatch: ancientdb %v, archivedb %v", num, hash, anheader, arheader)
   825  		}
   826  		if fblock, arblock, anblock := fast.GetBlockByHash(hash), archive.GetBlockByHash(hash), ancient.GetBlockByHash(hash); fblock.Hash() != arblock.Hash() || anblock.Hash() != arblock.Hash() {
   827  			t.Errorf("block #%d [%x]: block mismatch: fastdb %v, ancientdb %v, archivedb %v", num, hash, fblock, anblock, arblock)
   828  		} else if types.DeriveSha(fblock.Transactions(), trie.NewStackTrie(nil)) != types.DeriveSha(arblock.Transactions(), trie.NewStackTrie(nil)) || types.DeriveSha(anblock.Transactions(), trie.NewStackTrie(nil)) != types.DeriveSha(arblock.Transactions(), trie.NewStackTrie(nil)) {
   829  			t.Errorf("block #%d [%x]: transactions mismatch: fastdb %v, ancientdb %v, archivedb %v", num, hash, fblock.Transactions(), anblock.Transactions(), arblock.Transactions())
   830  		} else if types.CalcUncleHash(fblock.Uncles()) != types.CalcUncleHash(arblock.Uncles()) || types.CalcUncleHash(anblock.Uncles()) != types.CalcUncleHash(arblock.Uncles()) {
   831  			t.Errorf("block #%d [%x]: uncles mismatch: fastdb %v, ancientdb %v, archivedb %v", num, hash, fblock.Uncles(), anblock, arblock.Uncles())
   832  		}
   833  
   834  		// Check receipts.
   835  		freceipts := rawdb.ReadReceipts(fastDb, hash, num, fast.Config())
   836  		anreceipts := rawdb.ReadReceipts(ancientDb, hash, num, fast.Config())
   837  		areceipts := rawdb.ReadReceipts(archiveDb, hash, num, fast.Config())
   838  		if types.DeriveSha(freceipts, trie.NewStackTrie(nil)) != types.DeriveSha(areceipts, trie.NewStackTrie(nil)) {
   839  			t.Errorf("block #%d [%x]: receipts mismatch: fastdb %v, ancientdb %v, archivedb %v", num, hash, freceipts, anreceipts, areceipts)
   840  		}
   841  
   842  		// Check that hash-to-number mappings are present in all databases.
   843  		if m := rawdb.ReadHeaderNumber(fastDb, hash); m == nil || *m != num {
   844  			t.Errorf("block #%d [%x]: wrong hash-to-number mapping in fastdb: %v", num, hash, m)
   845  		}
   846  		if m := rawdb.ReadHeaderNumber(ancientDb, hash); m == nil || *m != num {
   847  			t.Errorf("block #%d [%x]: wrong hash-to-number mapping in ancientdb: %v", num, hash, m)
   848  		}
   849  		if m := rawdb.ReadHeaderNumber(archiveDb, hash); m == nil || *m != num {
   850  			t.Errorf("block #%d [%x]: wrong hash-to-number mapping in archivedb: %v", num, hash, m)
   851  		}
   852  	}
   853  
   854  	// Check that the canonical chains are the same between the databases
   855  	for i := 0; i < len(blocks)+1; i++ {
   856  		if fhash, ahash := rawdb.ReadCanonicalHash(fastDb, uint64(i)), rawdb.ReadCanonicalHash(archiveDb, uint64(i)); fhash != ahash {
   857  			t.Errorf("block #%d: canonical hash mismatch: fastdb %v, archivedb %v", i, fhash, ahash)
   858  		}
   859  		if anhash, arhash := rawdb.ReadCanonicalHash(ancientDb, uint64(i)), rawdb.ReadCanonicalHash(archiveDb, uint64(i)); anhash != arhash {
   860  			t.Errorf("block #%d: canonical hash mismatch: ancientdb %v, archivedb %v", i, anhash, arhash)
   861  		}
   862  	}
   863  }
   864  
   865  // Tests that various import methods move the chain head pointers to the correct
   866  // positions.
   867  func TestLightVsFastVsFullChainHeads(t *testing.T) {
   868  	// Configure and generate a sample block chain
   869  	var (
   870  		gendb   = rawdb.NewMemoryDatabase()
   871  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
   872  		address = crypto.PubkeyToAddress(key.PublicKey)
   873  		funds   = big.NewInt(1000000000000000)
   874  		gspec   = &Genesis{
   875  			Config:  params.TestChainConfig,
   876  			Alloc:   GenesisAlloc{address: {Balance: funds}},
   877  			BaseFee: big.NewInt(params.InitialBaseFee),
   878  		}
   879  		genesis = gspec.MustCommit(gendb)
   880  	)
   881  	height := uint64(1024)
   882  	blocks, receipts := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), gendb, int(height), nil)
   883  
   884  	// makeDb creates a db instance for testing.
   885  	makeDb := func() ethdb.Database {
   886  		dir := t.TempDir()
   887  		db, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), dir, "", false)
   888  		if err != nil {
   889  			t.Fatalf("failed to create temp freezer db: %v", err)
   890  		}
   891  		gspec.MustCommit(db)
   892  		return db
   893  	}
   894  	// Configure a subchain to roll back
   895  	remove := blocks[height/2].NumberU64()
   896  
   897  	// Create a small assertion method to check the three heads
   898  	assert := func(t *testing.T, kind string, chain *BlockChain, header uint64, fast uint64, block uint64) {
   899  		t.Helper()
   900  
   901  		if num := chain.CurrentBlock().NumberU64(); num != block {
   902  			t.Errorf("%s head block mismatch: have #%v, want #%v", kind, num, block)
   903  		}
   904  		if num := chain.CurrentFastBlock().NumberU64(); num != fast {
   905  			t.Errorf("%s head fast-block mismatch: have #%v, want #%v", kind, num, fast)
   906  		}
   907  		if num := chain.CurrentHeader().Number.Uint64(); num != header {
   908  			t.Errorf("%s head header mismatch: have #%v, want #%v", kind, num, header)
   909  		}
   910  	}
   911  	// Import the chain as an archive node and ensure all pointers are updated
   912  	archiveDb := makeDb()
   913  	defer archiveDb.Close()
   914  
   915  	archiveCaching := *defaultCacheConfig
   916  	archiveCaching.TrieDirtyDisabled = true
   917  
   918  	archive, _ := NewBlockChain(archiveDb, &archiveCaching, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   919  	if n, err := archive.InsertChain(blocks); err != nil {
   920  		t.Fatalf("failed to process block %d: %v", n, err)
   921  	}
   922  	defer archive.Stop()
   923  
   924  	assert(t, "archive", archive, height, height, height)
   925  	archive.SetHead(remove - 1)
   926  	assert(t, "archive", archive, height/2, height/2, height/2)
   927  
   928  	// Import the chain as a non-archive node and ensure all pointers are updated
   929  	fastDb := makeDb()
   930  	defer fastDb.Close()
   931  	fast, _ := NewBlockChain(fastDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   932  	defer fast.Stop()
   933  
   934  	headers := make([]*types.Header, len(blocks))
   935  	for i, block := range blocks {
   936  		headers[i] = block.Header()
   937  	}
   938  	if n, err := fast.InsertHeaderChain(headers, 1); err != nil {
   939  		t.Fatalf("failed to insert header %d: %v", n, err)
   940  	}
   941  	if n, err := fast.InsertReceiptChain(blocks, receipts, 0); err != nil {
   942  		t.Fatalf("failed to insert receipt %d: %v", n, err)
   943  	}
   944  	assert(t, "fast", fast, height, height, 0)
   945  	fast.SetHead(remove - 1)
   946  	assert(t, "fast", fast, height/2, height/2, 0)
   947  
   948  	// Import the chain as a ancient-first node and ensure all pointers are updated
   949  	ancientDb := makeDb()
   950  	defer ancientDb.Close()
   951  	ancient, _ := NewBlockChain(ancientDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   952  	defer ancient.Stop()
   953  
   954  	if n, err := ancient.InsertHeaderChain(headers, 1); err != nil {
   955  		t.Fatalf("failed to insert header %d: %v", n, err)
   956  	}
   957  	if n, err := ancient.InsertReceiptChain(blocks, receipts, uint64(3*len(blocks)/4)); err != nil {
   958  		t.Fatalf("failed to insert receipt %d: %v", n, err)
   959  	}
   960  	assert(t, "ancient", ancient, height, height, 0)
   961  	ancient.SetHead(remove - 1)
   962  	assert(t, "ancient", ancient, 0, 0, 0)
   963  
   964  	if frozen, err := ancientDb.Ancients(); err != nil || frozen != 1 {
   965  		t.Fatalf("failed to truncate ancient store, want %v, have %v", 1, frozen)
   966  	}
   967  	// Import the chain as a light node and ensure all pointers are updated
   968  	lightDb := makeDb()
   969  	defer lightDb.Close()
   970  	light, _ := NewBlockChain(lightDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
   971  	if n, err := light.InsertHeaderChain(headers, 1); err != nil {
   972  		t.Fatalf("failed to insert header %d: %v", n, err)
   973  	}
   974  	defer light.Stop()
   975  
   976  	assert(t, "light", light, height, 0, 0)
   977  	light.SetHead(remove - 1)
   978  	assert(t, "light", light, height/2, 0, 0)
   979  }
   980  
   981  // Tests that chain reorganisations handle transaction removals and reinsertions.
   982  func TestChainTxReorgs(t *testing.T) {
   983  	var (
   984  		key1, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
   985  		key2, _ = crypto.HexToECDSA("8a1f9a8f95be41cd7ccb6168179afb4504aefe388d1e14474d32c45c72ce7b7a")
   986  		key3, _ = crypto.HexToECDSA("49a7b37aa6f6645917e7b807e9d1c00d4fa71f18343b0d4122a4d2df64dd6fee")
   987  		addr1   = crypto.PubkeyToAddress(key1.PublicKey)
   988  		addr2   = crypto.PubkeyToAddress(key2.PublicKey)
   989  		addr3   = crypto.PubkeyToAddress(key3.PublicKey)
   990  		db      = rawdb.NewMemoryDatabase()
   991  		gspec   = &Genesis{
   992  			Config:   params.TestChainConfig,
   993  			GasLimit: 3141592,
   994  			Alloc: GenesisAlloc{
   995  				addr1: {Balance: big.NewInt(1000000000000000)},
   996  				addr2: {Balance: big.NewInt(1000000000000000)},
   997  				addr3: {Balance: big.NewInt(1000000000000000)},
   998  			},
   999  		}
  1000  		genesis = gspec.MustCommit(db)
  1001  		signer  = types.LatestSigner(gspec.Config)
  1002  	)
  1003  
  1004  	// Create two transactions shared between the chains:
  1005  	//  - postponed: transaction included at a later block in the forked chain
  1006  	//  - swapped: transaction included at the same block number in the forked chain
  1007  	postponed, _ := types.SignTx(types.NewTransaction(0, addr1, big.NewInt(1000), params.TxGas, big.NewInt(params.InitialBaseFee), nil), signer, key1)
  1008  	swapped, _ := types.SignTx(types.NewTransaction(1, addr1, big.NewInt(1000), params.TxGas, big.NewInt(params.InitialBaseFee), nil), signer, key1)
  1009  
  1010  	// Create two transactions that will be dropped by the forked chain:
  1011  	//  - pastDrop: transaction dropped retroactively from a past block
  1012  	//  - freshDrop: transaction dropped exactly at the block where the reorg is detected
  1013  	var pastDrop, freshDrop *types.Transaction
  1014  
  1015  	// Create three transactions that will be added in the forked chain:
  1016  	//  - pastAdd:   transaction added before the reorganization is detected
  1017  	//  - freshAdd:  transaction added at the exact block the reorg is detected
  1018  	//  - futureAdd: transaction added after the reorg has already finished
  1019  	var pastAdd, freshAdd, futureAdd *types.Transaction
  1020  
  1021  	chain, _ := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 3, func(i int, gen *BlockGen) {
  1022  		switch i {
  1023  		case 0:
  1024  			pastDrop, _ = types.SignTx(types.NewTransaction(gen.TxNonce(addr2), addr2, big.NewInt(1000), params.TxGas, gen.header.BaseFee, nil), signer, key2)
  1025  
  1026  			gen.AddTx(pastDrop)  // This transaction will be dropped in the fork from below the split point
  1027  			gen.AddTx(postponed) // This transaction will be postponed till block #3 in the fork
  1028  
  1029  		case 2:
  1030  			freshDrop, _ = types.SignTx(types.NewTransaction(gen.TxNonce(addr2), addr2, big.NewInt(1000), params.TxGas, gen.header.BaseFee, nil), signer, key2)
  1031  
  1032  			gen.AddTx(freshDrop) // This transaction will be dropped in the fork from exactly at the split point
  1033  			gen.AddTx(swapped)   // This transaction will be swapped out at the exact height
  1034  
  1035  			gen.OffsetTime(9) // Lower the block difficulty to simulate a weaker chain
  1036  		}
  1037  	})
  1038  	// Import the chain. This runs all block validation rules.
  1039  	blockchain, _ := NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1040  	if i, err := blockchain.InsertChain(chain); err != nil {
  1041  		t.Fatalf("failed to insert original chain[%d]: %v", i, err)
  1042  	}
  1043  	defer blockchain.Stop()
  1044  
  1045  	// overwrite the old chain
  1046  	chain, _ = GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 5, func(i int, gen *BlockGen) {
  1047  		switch i {
  1048  		case 0:
  1049  			pastAdd, _ = types.SignTx(types.NewTransaction(gen.TxNonce(addr3), addr3, big.NewInt(1000), params.TxGas, gen.header.BaseFee, nil), signer, key3)
  1050  			gen.AddTx(pastAdd) // This transaction needs to be injected during reorg
  1051  
  1052  		case 2:
  1053  			gen.AddTx(postponed) // This transaction was postponed from block #1 in the original chain
  1054  			gen.AddTx(swapped)   // This transaction was swapped from the exact current spot in the original chain
  1055  
  1056  			freshAdd, _ = types.SignTx(types.NewTransaction(gen.TxNonce(addr3), addr3, big.NewInt(1000), params.TxGas, gen.header.BaseFee, nil), signer, key3)
  1057  			gen.AddTx(freshAdd) // This transaction will be added exactly at reorg time
  1058  
  1059  		case 3:
  1060  			futureAdd, _ = types.SignTx(types.NewTransaction(gen.TxNonce(addr3), addr3, big.NewInt(1000), params.TxGas, gen.header.BaseFee, nil), signer, key3)
  1061  			gen.AddTx(futureAdd) // This transaction will be added after a full reorg
  1062  		}
  1063  	})
  1064  	if _, err := blockchain.InsertChain(chain); err != nil {
  1065  		t.Fatalf("failed to insert forked chain: %v", err)
  1066  	}
  1067  
  1068  	// removed tx
  1069  	for i, tx := range (types.Transactions{pastDrop, freshDrop}) {
  1070  		if txn, _, _, _ := rawdb.ReadTransaction(db, tx.Hash()); txn != nil {
  1071  			t.Errorf("drop %d: tx %v found while shouldn't have been", i, txn)
  1072  		}
  1073  		if rcpt, _, _, _ := rawdb.ReadReceipt(db, tx.Hash(), blockchain.Config()); rcpt != nil {
  1074  			t.Errorf("drop %d: receipt %v found while shouldn't have been", i, rcpt)
  1075  		}
  1076  	}
  1077  	// added tx
  1078  	for i, tx := range (types.Transactions{pastAdd, freshAdd, futureAdd}) {
  1079  		if txn, _, _, _ := rawdb.ReadTransaction(db, tx.Hash()); txn == nil {
  1080  			t.Errorf("add %d: expected tx to be found", i)
  1081  		}
  1082  		if rcpt, _, _, _ := rawdb.ReadReceipt(db, tx.Hash(), blockchain.Config()); rcpt == nil {
  1083  			t.Errorf("add %d: expected receipt to be found", i)
  1084  		}
  1085  	}
  1086  	// shared tx
  1087  	for i, tx := range (types.Transactions{postponed, swapped}) {
  1088  		if txn, _, _, _ := rawdb.ReadTransaction(db, tx.Hash()); txn == nil {
  1089  			t.Errorf("share %d: expected tx to be found", i)
  1090  		}
  1091  		if rcpt, _, _, _ := rawdb.ReadReceipt(db, tx.Hash(), blockchain.Config()); rcpt == nil {
  1092  			t.Errorf("share %d: expected receipt to be found", i)
  1093  		}
  1094  	}
  1095  }
  1096  
  1097  func TestLogReorgs(t *testing.T) {
  1098  	var (
  1099  		key1, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1100  		addr1   = crypto.PubkeyToAddress(key1.PublicKey)
  1101  		db      = rawdb.NewMemoryDatabase()
  1102  		// this code generates a log
  1103  		code    = common.Hex2Bytes("60606040525b7f24ec1d3ff24c2f6ff210738839dbc339cd45a5294d85c79361016243157aae7b60405180905060405180910390a15b600a8060416000396000f360606040526008565b00")
  1104  		gspec   = &Genesis{Config: params.TestChainConfig, Alloc: GenesisAlloc{addr1: {Balance: big.NewInt(10000000000000000)}}}
  1105  		genesis = gspec.MustCommit(db)
  1106  		signer  = types.LatestSigner(gspec.Config)
  1107  	)
  1108  
  1109  	blockchain, _ := NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1110  	defer blockchain.Stop()
  1111  
  1112  	rmLogsCh := make(chan RemovedLogsEvent)
  1113  	blockchain.SubscribeRemovedLogsEvent(rmLogsCh)
  1114  	chain, _ := GenerateChain(params.TestChainConfig, genesis, ethash.NewFaker(), db, 2, func(i int, gen *BlockGen) {
  1115  		if i == 1 {
  1116  			tx, err := types.SignTx(types.NewContractCreation(gen.TxNonce(addr1), new(big.Int), 1000000, gen.header.BaseFee, code), signer, key1)
  1117  			if err != nil {
  1118  				t.Fatalf("failed to create tx: %v", err)
  1119  			}
  1120  			gen.AddTx(tx)
  1121  		}
  1122  	})
  1123  	if _, err := blockchain.InsertChain(chain); err != nil {
  1124  		t.Fatalf("failed to insert chain: %v", err)
  1125  	}
  1126  
  1127  	chain, _ = GenerateChain(params.TestChainConfig, genesis, ethash.NewFaker(), db, 3, func(i int, gen *BlockGen) {})
  1128  	done := make(chan struct{})
  1129  	go func() {
  1130  		ev := <-rmLogsCh
  1131  		if len(ev.Logs) == 0 {
  1132  			t.Error("expected logs")
  1133  		}
  1134  		close(done)
  1135  	}()
  1136  	if _, err := blockchain.InsertChain(chain); err != nil {
  1137  		t.Fatalf("failed to insert forked chain: %v", err)
  1138  	}
  1139  	timeout := time.NewTimer(1 * time.Second)
  1140  	defer timeout.Stop()
  1141  	select {
  1142  	case <-done:
  1143  	case <-timeout.C:
  1144  		t.Fatal("Timeout. There is no RemovedLogsEvent has been sent.")
  1145  	}
  1146  }
  1147  
  1148  // This EVM code generates a log when the contract is created.
  1149  var logCode = common.Hex2Bytes("60606040525b7f24ec1d3ff24c2f6ff210738839dbc339cd45a5294d85c79361016243157aae7b60405180905060405180910390a15b600a8060416000396000f360606040526008565b00")
  1150  
  1151  // This test checks that log events and RemovedLogsEvent are sent
  1152  // when the chain reorganizes.
  1153  func TestLogRebirth(t *testing.T) {
  1154  	var (
  1155  		key1, _       = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1156  		addr1         = crypto.PubkeyToAddress(key1.PublicKey)
  1157  		db            = rawdb.NewMemoryDatabase()
  1158  		gspec         = &Genesis{Config: params.TestChainConfig, Alloc: GenesisAlloc{addr1: {Balance: big.NewInt(10000000000000000)}}}
  1159  		genesis       = gspec.MustCommit(db)
  1160  		signer        = types.LatestSigner(gspec.Config)
  1161  		engine        = ethash.NewFaker()
  1162  		blockchain, _ = NewBlockChain(db, nil, gspec.Config, engine, vm.Config{}, nil, nil)
  1163  	)
  1164  
  1165  	defer blockchain.Stop()
  1166  
  1167  	// The event channels.
  1168  	newLogCh := make(chan []*types.Log, 10)
  1169  	rmLogsCh := make(chan RemovedLogsEvent, 10)
  1170  	blockchain.SubscribeLogsEvent(newLogCh)
  1171  	blockchain.SubscribeRemovedLogsEvent(rmLogsCh)
  1172  
  1173  	// This chain contains a single log.
  1174  	chain, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 2, func(i int, gen *BlockGen) {
  1175  		if i == 1 {
  1176  			tx, err := types.SignTx(types.NewContractCreation(gen.TxNonce(addr1), new(big.Int), 1000000, gen.header.BaseFee, logCode), signer, key1)
  1177  			if err != nil {
  1178  				t.Fatalf("failed to create tx: %v", err)
  1179  			}
  1180  			gen.AddTx(tx)
  1181  		}
  1182  	})
  1183  	if _, err := blockchain.InsertChain(chain); err != nil {
  1184  		t.Fatalf("failed to insert chain: %v", err)
  1185  	}
  1186  	checkLogEvents(t, newLogCh, rmLogsCh, 1, 0)
  1187  
  1188  	// Generate long reorg chain containing another log. Inserting the
  1189  	// chain removes one log and adds one.
  1190  	forkChain, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 2, func(i int, gen *BlockGen) {
  1191  		if i == 1 {
  1192  			tx, err := types.SignTx(types.NewContractCreation(gen.TxNonce(addr1), new(big.Int), 1000000, gen.header.BaseFee, logCode), signer, key1)
  1193  			if err != nil {
  1194  				t.Fatalf("failed to create tx: %v", err)
  1195  			}
  1196  			gen.AddTx(tx)
  1197  			gen.OffsetTime(-9) // higher block difficulty
  1198  		}
  1199  	})
  1200  	if _, err := blockchain.InsertChain(forkChain); err != nil {
  1201  		t.Fatalf("failed to insert forked chain: %v", err)
  1202  	}
  1203  	checkLogEvents(t, newLogCh, rmLogsCh, 1, 1)
  1204  
  1205  	// This chain segment is rooted in the original chain, but doesn't contain any logs.
  1206  	// When inserting it, the canonical chain switches away from forkChain and re-emits
  1207  	// the log event for the old chain, as well as a RemovedLogsEvent for forkChain.
  1208  	newBlocks, _ := GenerateChain(params.TestChainConfig, chain[len(chain)-1], engine, db, 1, func(i int, gen *BlockGen) {})
  1209  	if _, err := blockchain.InsertChain(newBlocks); err != nil {
  1210  		t.Fatalf("failed to insert forked chain: %v", err)
  1211  	}
  1212  	checkLogEvents(t, newLogCh, rmLogsCh, 1, 1)
  1213  }
  1214  
  1215  // This test is a variation of TestLogRebirth. It verifies that log events are emitted
  1216  // when a side chain containing log events overtakes the canonical chain.
  1217  func TestSideLogRebirth(t *testing.T) {
  1218  	var (
  1219  		key1, _       = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1220  		addr1         = crypto.PubkeyToAddress(key1.PublicKey)
  1221  		db            = rawdb.NewMemoryDatabase()
  1222  		gspec         = &Genesis{Config: params.TestChainConfig, Alloc: GenesisAlloc{addr1: {Balance: big.NewInt(10000000000000000)}}}
  1223  		genesis       = gspec.MustCommit(db)
  1224  		signer        = types.LatestSigner(gspec.Config)
  1225  		blockchain, _ = NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1226  	)
  1227  
  1228  	defer blockchain.Stop()
  1229  
  1230  	newLogCh := make(chan []*types.Log, 10)
  1231  	rmLogsCh := make(chan RemovedLogsEvent, 10)
  1232  	blockchain.SubscribeLogsEvent(newLogCh)
  1233  	blockchain.SubscribeRemovedLogsEvent(rmLogsCh)
  1234  
  1235  	chain, _ := GenerateChain(params.TestChainConfig, genesis, ethash.NewFaker(), db, 2, func(i int, gen *BlockGen) {
  1236  		if i == 1 {
  1237  			gen.OffsetTime(-9) // higher block difficulty
  1238  		}
  1239  	})
  1240  	if _, err := blockchain.InsertChain(chain); err != nil {
  1241  		t.Fatalf("failed to insert forked chain: %v", err)
  1242  	}
  1243  	checkLogEvents(t, newLogCh, rmLogsCh, 0, 0)
  1244  
  1245  	// Generate side chain with lower difficulty
  1246  	sideChain, _ := GenerateChain(params.TestChainConfig, genesis, ethash.NewFaker(), db, 2, func(i int, gen *BlockGen) {
  1247  		if i == 1 {
  1248  			tx, err := types.SignTx(types.NewContractCreation(gen.TxNonce(addr1), new(big.Int), 1000000, gen.header.BaseFee, logCode), signer, key1)
  1249  			if err != nil {
  1250  				t.Fatalf("failed to create tx: %v", err)
  1251  			}
  1252  			gen.AddTx(tx)
  1253  		}
  1254  	})
  1255  	if _, err := blockchain.InsertChain(sideChain); err != nil {
  1256  		t.Fatalf("failed to insert forked chain: %v", err)
  1257  	}
  1258  	checkLogEvents(t, newLogCh, rmLogsCh, 0, 0)
  1259  
  1260  	// Generate a new block based on side chain.
  1261  	newBlocks, _ := GenerateChain(params.TestChainConfig, sideChain[len(sideChain)-1], ethash.NewFaker(), db, 1, func(i int, gen *BlockGen) {})
  1262  	if _, err := blockchain.InsertChain(newBlocks); err != nil {
  1263  		t.Fatalf("failed to insert forked chain: %v", err)
  1264  	}
  1265  	checkLogEvents(t, newLogCh, rmLogsCh, 1, 0)
  1266  }
  1267  
  1268  func checkLogEvents(t *testing.T, logsCh <-chan []*types.Log, rmLogsCh <-chan RemovedLogsEvent, wantNew, wantRemoved int) {
  1269  	t.Helper()
  1270  
  1271  	if len(logsCh) != wantNew {
  1272  		t.Fatalf("wrong number of log events: got %d, want %d", len(logsCh), wantNew)
  1273  	}
  1274  	if len(rmLogsCh) != wantRemoved {
  1275  		t.Fatalf("wrong number of removed log events: got %d, want %d", len(rmLogsCh), wantRemoved)
  1276  	}
  1277  	// Drain events.
  1278  	for i := 0; i < len(logsCh); i++ {
  1279  		<-logsCh
  1280  	}
  1281  	for i := 0; i < len(rmLogsCh); i++ {
  1282  		<-rmLogsCh
  1283  	}
  1284  }
  1285  
  1286  func TestReorgSideEvent(t *testing.T) {
  1287  	var (
  1288  		db      = rawdb.NewMemoryDatabase()
  1289  		key1, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1290  		addr1   = crypto.PubkeyToAddress(key1.PublicKey)
  1291  		gspec   = &Genesis{
  1292  			Config: params.TestChainConfig,
  1293  			Alloc:  GenesisAlloc{addr1: {Balance: big.NewInt(10000000000000000)}},
  1294  		}
  1295  		genesis = gspec.MustCommit(db)
  1296  		signer  = types.LatestSigner(gspec.Config)
  1297  	)
  1298  
  1299  	blockchain, _ := NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1300  	defer blockchain.Stop()
  1301  
  1302  	chain, _ := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 3, func(i int, gen *BlockGen) {})
  1303  	if _, err := blockchain.InsertChain(chain); err != nil {
  1304  		t.Fatalf("failed to insert chain: %v", err)
  1305  	}
  1306  
  1307  	replacementBlocks, _ := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 4, func(i int, gen *BlockGen) {
  1308  		tx, err := types.SignTx(types.NewContractCreation(gen.TxNonce(addr1), new(big.Int), 1000000, gen.header.BaseFee, nil), signer, key1)
  1309  		if i == 2 {
  1310  			gen.OffsetTime(-9)
  1311  		}
  1312  		if err != nil {
  1313  			t.Fatalf("failed to create tx: %v", err)
  1314  		}
  1315  		gen.AddTx(tx)
  1316  	})
  1317  	chainSideCh := make(chan ChainSideEvent, 64)
  1318  	blockchain.SubscribeChainSideEvent(chainSideCh)
  1319  	if _, err := blockchain.InsertChain(replacementBlocks); err != nil {
  1320  		t.Fatalf("failed to insert chain: %v", err)
  1321  	}
  1322  
  1323  	// first two block of the secondary chain are for a brief moment considered
  1324  	// side chains because up to that point the first one is considered the
  1325  	// heavier chain.
  1326  	expectedSideHashes := map[common.Hash]bool{
  1327  		replacementBlocks[0].Hash(): true,
  1328  		replacementBlocks[1].Hash(): true,
  1329  		chain[0].Hash():             true,
  1330  		chain[1].Hash():             true,
  1331  		chain[2].Hash():             true,
  1332  	}
  1333  
  1334  	i := 0
  1335  
  1336  	const timeoutDura = 10 * time.Second
  1337  	timeout := time.NewTimer(timeoutDura)
  1338  done:
  1339  	for {
  1340  		select {
  1341  		case ev := <-chainSideCh:
  1342  			block := ev.Block
  1343  			if _, ok := expectedSideHashes[block.Hash()]; !ok {
  1344  				t.Errorf("%d: didn't expect %x to be in side chain", i, block.Hash())
  1345  			}
  1346  			i++
  1347  
  1348  			if i == len(expectedSideHashes) {
  1349  				timeout.Stop()
  1350  
  1351  				break done
  1352  			}
  1353  			timeout.Reset(timeoutDura)
  1354  
  1355  		case <-timeout.C:
  1356  			t.Fatal("Timeout. Possibly not all blocks were triggered for sideevent")
  1357  		}
  1358  	}
  1359  
  1360  	// make sure no more events are fired
  1361  	select {
  1362  	case e := <-chainSideCh:
  1363  		t.Errorf("unexpected event fired: %v", e)
  1364  	case <-time.After(250 * time.Millisecond):
  1365  	}
  1366  }
  1367  
  1368  // Tests if the canonical block can be fetched from the database during chain insertion.
  1369  func TestCanonicalBlockRetrieval(t *testing.T) {
  1370  	_, blockchain, err := newCanonical(ethash.NewFaker(), 0, true)
  1371  	if err != nil {
  1372  		t.Fatalf("failed to create pristine chain: %v", err)
  1373  	}
  1374  	defer blockchain.Stop()
  1375  
  1376  	chain, _ := GenerateChain(blockchain.chainConfig, blockchain.genesisBlock, ethash.NewFaker(), blockchain.db, 10, func(i int, gen *BlockGen) {})
  1377  
  1378  	var pend sync.WaitGroup
  1379  	pend.Add(len(chain))
  1380  
  1381  	for i := range chain {
  1382  		go func(block *types.Block) {
  1383  			defer pend.Done()
  1384  
  1385  			// try to retrieve a block by its canonical hash and see if the block data can be retrieved.
  1386  			for {
  1387  				ch := rawdb.ReadCanonicalHash(blockchain.db, block.NumberU64())
  1388  				if ch == (common.Hash{}) {
  1389  					continue // busy wait for canonical hash to be written
  1390  				}
  1391  				if ch != block.Hash() {
  1392  					t.Errorf("unknown canonical hash, want %s, got %s", block.Hash().Hex(), ch.Hex())
  1393  					return
  1394  				}
  1395  				fb := rawdb.ReadBlock(blockchain.db, ch, block.NumberU64())
  1396  				if fb == nil {
  1397  					t.Errorf("unable to retrieve block %d for canonical hash: %s", block.NumberU64(), ch.Hex())
  1398  					return
  1399  				}
  1400  				if fb.Hash() != block.Hash() {
  1401  					t.Errorf("invalid block hash for block %d, want %s, got %s", block.NumberU64(), block.Hash().Hex(), fb.Hash().Hex())
  1402  					return
  1403  				}
  1404  				return
  1405  			}
  1406  		}(chain[i])
  1407  
  1408  		if _, err := blockchain.InsertChain(types.Blocks{chain[i]}); err != nil {
  1409  			t.Fatalf("failed to insert block %d: %v", i, err)
  1410  		}
  1411  	}
  1412  	pend.Wait()
  1413  }
  1414  
  1415  func TestEIP155Transition(t *testing.T) {
  1416  	// Configure and generate a sample block chain
  1417  	var (
  1418  		db         = rawdb.NewMemoryDatabase()
  1419  		key, _     = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1420  		address    = crypto.PubkeyToAddress(key.PublicKey)
  1421  		funds      = big.NewInt(1000000000)
  1422  		deleteAddr = common.Address{1}
  1423  		gspec      = &Genesis{
  1424  			Config: &params.ChainConfig{ChainID: big.NewInt(1), EIP150Block: big.NewInt(0), EIP155Block: big.NewInt(2), HomesteadBlock: new(big.Int)},
  1425  			Alloc:  GenesisAlloc{address: {Balance: funds}, deleteAddr: {Balance: new(big.Int)}},
  1426  		}
  1427  		genesis = gspec.MustCommit(db)
  1428  	)
  1429  
  1430  	blockchain, _ := NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1431  	defer blockchain.Stop()
  1432  
  1433  	blocks, _ := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 4, func(i int, block *BlockGen) {
  1434  		var (
  1435  			tx      *types.Transaction
  1436  			err     error
  1437  			basicTx = func(signer types.Signer) (*types.Transaction, error) {
  1438  				return types.SignTx(types.NewTransaction(block.TxNonce(address), common.Address{}, new(big.Int), 21000, new(big.Int), nil), signer, key)
  1439  			}
  1440  		)
  1441  		switch i {
  1442  		case 0:
  1443  			tx, err = basicTx(types.HomesteadSigner{})
  1444  			if err != nil {
  1445  				t.Fatal(err)
  1446  			}
  1447  			block.AddTx(tx)
  1448  		case 2:
  1449  			tx, err = basicTx(types.HomesteadSigner{})
  1450  			if err != nil {
  1451  				t.Fatal(err)
  1452  			}
  1453  			block.AddTx(tx)
  1454  
  1455  			tx, err = basicTx(types.LatestSigner(gspec.Config))
  1456  			if err != nil {
  1457  				t.Fatal(err)
  1458  			}
  1459  			block.AddTx(tx)
  1460  		case 3:
  1461  			tx, err = basicTx(types.HomesteadSigner{})
  1462  			if err != nil {
  1463  				t.Fatal(err)
  1464  			}
  1465  			block.AddTx(tx)
  1466  
  1467  			tx, err = basicTx(types.LatestSigner(gspec.Config))
  1468  			if err != nil {
  1469  				t.Fatal(err)
  1470  			}
  1471  			block.AddTx(tx)
  1472  		}
  1473  	})
  1474  
  1475  	if _, err := blockchain.InsertChain(blocks); err != nil {
  1476  		t.Fatal(err)
  1477  	}
  1478  	block := blockchain.GetBlockByNumber(1)
  1479  	if block.Transactions()[0].Protected() {
  1480  		t.Error("Expected block[0].txs[0] to not be replay protected")
  1481  	}
  1482  
  1483  	block = blockchain.GetBlockByNumber(3)
  1484  	if block.Transactions()[0].Protected() {
  1485  		t.Error("Expected block[3].txs[0] to not be replay protected")
  1486  	}
  1487  	if !block.Transactions()[1].Protected() {
  1488  		t.Error("Expected block[3].txs[1] to be replay protected")
  1489  	}
  1490  	if _, err := blockchain.InsertChain(blocks[4:]); err != nil {
  1491  		t.Fatal(err)
  1492  	}
  1493  
  1494  	// generate an invalid chain id transaction
  1495  	config := &params.ChainConfig{ChainID: big.NewInt(2), EIP150Block: big.NewInt(0), EIP155Block: big.NewInt(2), HomesteadBlock: new(big.Int)}
  1496  	blocks, _ = GenerateChain(config, blocks[len(blocks)-1], ethash.NewFaker(), db, 4, func(i int, block *BlockGen) {
  1497  		var (
  1498  			tx      *types.Transaction
  1499  			err     error
  1500  			basicTx = func(signer types.Signer) (*types.Transaction, error) {
  1501  				return types.SignTx(types.NewTransaction(block.TxNonce(address), common.Address{}, new(big.Int), 21000, new(big.Int), nil), signer, key)
  1502  			}
  1503  		)
  1504  		if i == 0 {
  1505  			tx, err = basicTx(types.LatestSigner(config))
  1506  			if err != nil {
  1507  				t.Fatal(err)
  1508  			}
  1509  			block.AddTx(tx)
  1510  		}
  1511  	})
  1512  	_, err := blockchain.InsertChain(blocks)
  1513  	if have, want := err, types.ErrInvalidChainId; !errors.Is(have, want) {
  1514  		t.Errorf("have %v, want %v", have, want)
  1515  	}
  1516  }
  1517  
  1518  func TestEIP161AccountRemoval(t *testing.T) {
  1519  	// Configure and generate a sample block chain
  1520  	var (
  1521  		db      = rawdb.NewMemoryDatabase()
  1522  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1523  		address = crypto.PubkeyToAddress(key.PublicKey)
  1524  		funds   = big.NewInt(1000000000)
  1525  		theAddr = common.Address{1}
  1526  		gspec   = &Genesis{
  1527  			Config: &params.ChainConfig{
  1528  				ChainID:        big.NewInt(1),
  1529  				HomesteadBlock: new(big.Int),
  1530  				EIP155Block:    new(big.Int),
  1531  				EIP150Block:    new(big.Int),
  1532  				EIP158Block:    big.NewInt(2),
  1533  			},
  1534  			Alloc: GenesisAlloc{address: {Balance: funds}},
  1535  		}
  1536  		genesis = gspec.MustCommit(db)
  1537  	)
  1538  	blockchain, _ := NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1539  	defer blockchain.Stop()
  1540  
  1541  	blocks, _ := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 3, func(i int, block *BlockGen) {
  1542  		var (
  1543  			tx     *types.Transaction
  1544  			err    error
  1545  			signer = types.LatestSigner(gspec.Config)
  1546  		)
  1547  		switch i {
  1548  		case 0:
  1549  			tx, err = types.SignTx(types.NewTransaction(block.TxNonce(address), theAddr, new(big.Int), 21000, new(big.Int), nil), signer, key)
  1550  		case 1:
  1551  			tx, err = types.SignTx(types.NewTransaction(block.TxNonce(address), theAddr, new(big.Int), 21000, new(big.Int), nil), signer, key)
  1552  		case 2:
  1553  			tx, err = types.SignTx(types.NewTransaction(block.TxNonce(address), theAddr, new(big.Int), 21000, new(big.Int), nil), signer, key)
  1554  		}
  1555  		if err != nil {
  1556  			t.Fatal(err)
  1557  		}
  1558  		block.AddTx(tx)
  1559  	})
  1560  	// account must exist pre eip 161
  1561  	if _, err := blockchain.InsertChain(types.Blocks{blocks[0]}); err != nil {
  1562  		t.Fatal(err)
  1563  	}
  1564  	if st, _ := blockchain.State(); !st.Exist(theAddr) {
  1565  		t.Error("expected account to exist")
  1566  	}
  1567  
  1568  	// account needs to be deleted post eip 161
  1569  	if _, err := blockchain.InsertChain(types.Blocks{blocks[1]}); err != nil {
  1570  		t.Fatal(err)
  1571  	}
  1572  	if st, _ := blockchain.State(); st.Exist(theAddr) {
  1573  		t.Error("account should not exist")
  1574  	}
  1575  
  1576  	// account mustn't be created post eip 161
  1577  	if _, err := blockchain.InsertChain(types.Blocks{blocks[2]}); err != nil {
  1578  		t.Fatal(err)
  1579  	}
  1580  	if st, _ := blockchain.State(); st.Exist(theAddr) {
  1581  		t.Error("account should not exist")
  1582  	}
  1583  }
  1584  
  1585  // This is a regression test (i.e. as weird as it is, don't delete it ever), which
  1586  // tests that under weird reorg conditions the blockchain and its internal header-
  1587  // chain return the same latest block/header.
  1588  //
  1589  // https://github.com/ethereum/go-ethereum/pull/15941
  1590  func TestBlockchainHeaderchainReorgConsistency(t *testing.T) {
  1591  	// Generate a canonical chain to act as the main dataset
  1592  	engine := ethash.NewFaker()
  1593  
  1594  	db := rawdb.NewMemoryDatabase()
  1595  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  1596  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 64, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  1597  
  1598  	// Generate a bunch of fork blocks, each side forking from the canonical chain
  1599  	forks := make([]*types.Block, len(blocks))
  1600  	for i := 0; i < len(forks); i++ {
  1601  		parent := genesis
  1602  		if i > 0 {
  1603  			parent = blocks[i-1]
  1604  		}
  1605  		fork, _ := GenerateChain(params.TestChainConfig, parent, engine, db, 1, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{2}) })
  1606  		forks[i] = fork[0]
  1607  	}
  1608  	// Import the canonical and fork chain side by side, verifying the current block
  1609  	// and current header consistency
  1610  	diskdb := rawdb.NewMemoryDatabase()
  1611  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(diskdb)
  1612  
  1613  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  1614  	if err != nil {
  1615  		t.Fatalf("failed to create tester chain: %v", err)
  1616  	}
  1617  	for i := 0; i < len(blocks); i++ {
  1618  		if _, err := chain.InsertChain(blocks[i : i+1]); err != nil {
  1619  			t.Fatalf("block %d: failed to insert into chain: %v", i, err)
  1620  		}
  1621  		if chain.CurrentBlock().Hash() != chain.CurrentHeader().Hash() {
  1622  			t.Errorf("block %d: current block/header mismatch: block #%d [%x..], header #%d [%x..]", i, chain.CurrentBlock().Number(), chain.CurrentBlock().Hash().Bytes()[:4], chain.CurrentHeader().Number, chain.CurrentHeader().Hash().Bytes()[:4])
  1623  		}
  1624  		if _, err := chain.InsertChain(forks[i : i+1]); err != nil {
  1625  			t.Fatalf(" fork %d: failed to insert into chain: %v", i, err)
  1626  		}
  1627  		if chain.CurrentBlock().Hash() != chain.CurrentHeader().Hash() {
  1628  			t.Errorf(" fork %d: current block/header mismatch: block #%d [%x..], header #%d [%x..]", i, chain.CurrentBlock().Number(), chain.CurrentBlock().Hash().Bytes()[:4], chain.CurrentHeader().Number, chain.CurrentHeader().Hash().Bytes()[:4])
  1629  		}
  1630  	}
  1631  }
  1632  
  1633  // Tests that importing small side forks doesn't leave junk in the trie database
  1634  // cache (which would eventually cause memory issues).
  1635  func TestTrieForkGC(t *testing.T) {
  1636  	// Generate a canonical chain to act as the main dataset
  1637  	engine := ethash.NewFaker()
  1638  
  1639  	db := rawdb.NewMemoryDatabase()
  1640  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  1641  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 2*TriesInMemory, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  1642  
  1643  	// Generate a bunch of fork blocks, each side forking from the canonical chain
  1644  	forks := make([]*types.Block, len(blocks))
  1645  	for i := 0; i < len(forks); i++ {
  1646  		parent := genesis
  1647  		if i > 0 {
  1648  			parent = blocks[i-1]
  1649  		}
  1650  		fork, _ := GenerateChain(params.TestChainConfig, parent, engine, db, 1, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{2}) })
  1651  		forks[i] = fork[0]
  1652  	}
  1653  	// Import the canonical and fork chain side by side, forcing the trie cache to cache both
  1654  	diskdb := rawdb.NewMemoryDatabase()
  1655  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(diskdb)
  1656  
  1657  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  1658  	if err != nil {
  1659  		t.Fatalf("failed to create tester chain: %v", err)
  1660  	}
  1661  	for i := 0; i < len(blocks); i++ {
  1662  		if _, err := chain.InsertChain(blocks[i : i+1]); err != nil {
  1663  			t.Fatalf("block %d: failed to insert into chain: %v", i, err)
  1664  		}
  1665  		if _, err := chain.InsertChain(forks[i : i+1]); err != nil {
  1666  			t.Fatalf("fork %d: failed to insert into chain: %v", i, err)
  1667  		}
  1668  	}
  1669  	// Dereference all the recent tries and ensure no past trie is left in
  1670  	for i := 0; i < TriesInMemory; i++ {
  1671  		chain.stateCache.TrieDB().Dereference(blocks[len(blocks)-1-i].Root())
  1672  		chain.stateCache.TrieDB().Dereference(forks[len(blocks)-1-i].Root())
  1673  	}
  1674  	if len(chain.stateCache.TrieDB().Nodes()) > 0 {
  1675  		t.Fatalf("stale tries still alive after garbase collection")
  1676  	}
  1677  }
  1678  
  1679  // Tests that doing large reorgs works even if the state associated with the
  1680  // forking point is not available any more.
  1681  func TestLargeReorgTrieGC(t *testing.T) {
  1682  	// Generate the original common chain segment and the two competing forks
  1683  	engine := ethash.NewFaker()
  1684  
  1685  	db := rawdb.NewMemoryDatabase()
  1686  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  1687  
  1688  	shared, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 64, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  1689  	original, _ := GenerateChain(params.TestChainConfig, shared[len(shared)-1], engine, db, 2*TriesInMemory, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{2}) })
  1690  	competitor, _ := GenerateChain(params.TestChainConfig, shared[len(shared)-1], engine, db, 2*TriesInMemory+1, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{3}) })
  1691  
  1692  	// Import the shared chain and the original canonical one
  1693  	diskdb := rawdb.NewMemoryDatabase()
  1694  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(diskdb)
  1695  
  1696  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  1697  	if err != nil {
  1698  		t.Fatalf("failed to create tester chain: %v", err)
  1699  	}
  1700  	if _, err := chain.InsertChain(shared); err != nil {
  1701  		t.Fatalf("failed to insert shared chain: %v", err)
  1702  	}
  1703  	if _, err := chain.InsertChain(original); err != nil {
  1704  		t.Fatalf("failed to insert original chain: %v", err)
  1705  	}
  1706  	// Ensure that the state associated with the forking point is pruned away
  1707  	if node, _ := chain.stateCache.TrieDB().Node(shared[len(shared)-1].Root()); node != nil {
  1708  		t.Fatalf("common-but-old ancestor still cache")
  1709  	}
  1710  	// Import the competitor chain without exceeding the canonical's TD and ensure
  1711  	// we have not processed any of the blocks (protection against malicious blocks)
  1712  	if _, err := chain.InsertChain(competitor[:len(competitor)-2]); err != nil {
  1713  		t.Fatalf("failed to insert competitor chain: %v", err)
  1714  	}
  1715  	for i, block := range competitor[:len(competitor)-2] {
  1716  		if node, _ := chain.stateCache.TrieDB().Node(block.Root()); node != nil {
  1717  			t.Fatalf("competitor %d: low TD chain became processed", i)
  1718  		}
  1719  	}
  1720  	// Import the head of the competitor chain, triggering the reorg and ensure we
  1721  	// successfully reprocess all the stashed away blocks.
  1722  	if _, err := chain.InsertChain(competitor[len(competitor)-2:]); err != nil {
  1723  		t.Fatalf("failed to finalize competitor chain: %v", err)
  1724  	}
  1725  	for i, block := range competitor[:len(competitor)-TriesInMemory] {
  1726  		if node, _ := chain.stateCache.TrieDB().Node(block.Root()); node != nil {
  1727  			t.Fatalf("competitor %d: competing chain state missing", i)
  1728  		}
  1729  	}
  1730  }
  1731  
  1732  func TestBlockchainRecovery(t *testing.T) {
  1733  	// Configure and generate a sample block chain
  1734  	var (
  1735  		gendb   = rawdb.NewMemoryDatabase()
  1736  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1737  		address = crypto.PubkeyToAddress(key.PublicKey)
  1738  		funds   = big.NewInt(1000000000)
  1739  		gspec   = &Genesis{Config: params.TestChainConfig, Alloc: GenesisAlloc{address: {Balance: funds}}}
  1740  		genesis = gspec.MustCommit(gendb)
  1741  	)
  1742  	height := uint64(1024)
  1743  	blocks, receipts := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), gendb, int(height), nil)
  1744  
  1745  	// Import the chain as a ancient-first node and ensure all pointers are updated
  1746  	frdir := t.TempDir()
  1747  
  1748  	ancientDb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
  1749  	if err != nil {
  1750  		t.Fatalf("failed to create temp freezer db: %v", err)
  1751  	}
  1752  	defer ancientDb.Close()
  1753  	gspec.MustCommit(ancientDb)
  1754  	ancient, _ := NewBlockChain(ancientDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1755  
  1756  	headers := make([]*types.Header, len(blocks))
  1757  	for i, block := range blocks {
  1758  		headers[i] = block.Header()
  1759  	}
  1760  	if n, err := ancient.InsertHeaderChain(headers, 1); err != nil {
  1761  		t.Fatalf("failed to insert header %d: %v", n, err)
  1762  	}
  1763  	if n, err := ancient.InsertReceiptChain(blocks, receipts, uint64(3*len(blocks)/4)); err != nil {
  1764  		t.Fatalf("failed to insert receipt %d: %v", n, err)
  1765  	}
  1766  	rawdb.WriteLastPivotNumber(ancientDb, blocks[len(blocks)-1].NumberU64()) // Force fast sync behavior
  1767  	ancient.Stop()
  1768  
  1769  	// Destroy head fast block manually
  1770  	midBlock := blocks[len(blocks)/2]
  1771  	rawdb.WriteHeadFastBlockHash(ancientDb, midBlock.Hash())
  1772  
  1773  	// Reopen broken blockchain again
  1774  	ancient, _ = NewBlockChain(ancientDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1775  	defer ancient.Stop()
  1776  	if num := ancient.CurrentBlock().NumberU64(); num != 0 {
  1777  		t.Errorf("head block mismatch: have #%v, want #%v", num, 0)
  1778  	}
  1779  	if num := ancient.CurrentFastBlock().NumberU64(); num != midBlock.NumberU64() {
  1780  		t.Errorf("head fast-block mismatch: have #%v, want #%v", num, midBlock.NumberU64())
  1781  	}
  1782  	if num := ancient.CurrentHeader().Number.Uint64(); num != midBlock.NumberU64() {
  1783  		t.Errorf("head header mismatch: have #%v, want #%v", num, midBlock.NumberU64())
  1784  	}
  1785  }
  1786  
  1787  // This test checks that InsertReceiptChain will roll back correctly when attempting to insert a side chain.
  1788  func TestInsertReceiptChainRollback(t *testing.T) {
  1789  	// Generate forked chain. The returned BlockChain object is used to process the side chain blocks.
  1790  	tmpChain, sideblocks, canonblocks, err := getLongAndShortChains()
  1791  	if err != nil {
  1792  		t.Fatal(err)
  1793  	}
  1794  	defer tmpChain.Stop()
  1795  	// Get the side chain receipts.
  1796  	if _, err := tmpChain.InsertChain(sideblocks); err != nil {
  1797  		t.Fatal("processing side chain failed:", err)
  1798  	}
  1799  	t.Log("sidechain head:", tmpChain.CurrentBlock().Number(), tmpChain.CurrentBlock().Hash())
  1800  	sidechainReceipts := make([]types.Receipts, len(sideblocks))
  1801  	for i, block := range sideblocks {
  1802  		sidechainReceipts[i] = tmpChain.GetReceiptsByHash(block.Hash())
  1803  	}
  1804  	// Get the canon chain receipts.
  1805  	if _, err := tmpChain.InsertChain(canonblocks); err != nil {
  1806  		t.Fatal("processing canon chain failed:", err)
  1807  	}
  1808  	t.Log("canon head:", tmpChain.CurrentBlock().Number(), tmpChain.CurrentBlock().Hash())
  1809  	canonReceipts := make([]types.Receipts, len(canonblocks))
  1810  	for i, block := range canonblocks {
  1811  		canonReceipts[i] = tmpChain.GetReceiptsByHash(block.Hash())
  1812  	}
  1813  
  1814  	// Set up a BlockChain that uses the ancient store.
  1815  	frdir := t.TempDir()
  1816  	ancientDb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
  1817  	if err != nil {
  1818  		t.Fatalf("failed to create temp freezer db: %v", err)
  1819  	}
  1820  	defer ancientDb.Close()
  1821  	gspec := Genesis{Config: params.AllEthashProtocolChanges}
  1822  	gspec.MustCommit(ancientDb)
  1823  	ancientChain, _ := NewBlockChain(ancientDb, nil, gspec.Config, ethash.NewFaker(), vm.Config{}, nil, nil)
  1824  	defer ancientChain.Stop()
  1825  
  1826  	// Import the canonical header chain.
  1827  	canonHeaders := make([]*types.Header, len(canonblocks))
  1828  	for i, block := range canonblocks {
  1829  		canonHeaders[i] = block.Header()
  1830  	}
  1831  	if _, err = ancientChain.InsertHeaderChain(canonHeaders, 1); err != nil {
  1832  		t.Fatal("can't import canon headers:", err)
  1833  	}
  1834  
  1835  	// Try to insert blocks/receipts of the side chain.
  1836  	_, err = ancientChain.InsertReceiptChain(sideblocks, sidechainReceipts, uint64(len(sideblocks)))
  1837  	if err == nil {
  1838  		t.Fatal("expected error from InsertReceiptChain.")
  1839  	}
  1840  	if ancientChain.CurrentFastBlock().NumberU64() != 0 {
  1841  		t.Fatalf("failed to rollback ancient data, want %d, have %d", 0, ancientChain.CurrentFastBlock().NumberU64())
  1842  	}
  1843  	if frozen, err := ancientChain.db.Ancients(); err != nil || frozen != 1 {
  1844  		t.Fatalf("failed to truncate ancient data, frozen index is %d", frozen)
  1845  	}
  1846  
  1847  	// Insert blocks/receipts of the canonical chain.
  1848  	_, err = ancientChain.InsertReceiptChain(canonblocks, canonReceipts, uint64(len(canonblocks)))
  1849  	if err != nil {
  1850  		t.Fatalf("can't import canon chain receipts: %v", err)
  1851  	}
  1852  	if ancientChain.CurrentFastBlock().NumberU64() != canonblocks[len(canonblocks)-1].NumberU64() {
  1853  		t.Fatalf("failed to insert ancient recept chain after rollback")
  1854  	}
  1855  	if frozen, _ := ancientChain.db.Ancients(); frozen != uint64(len(canonblocks))+1 {
  1856  		t.Fatalf("wrong ancients count %d", frozen)
  1857  	}
  1858  }
  1859  
  1860  // Tests that importing a very large side fork, which is larger than the canon chain,
  1861  // but where the difficulty per block is kept low: this means that it will not
  1862  // overtake the 'canon' chain until after it's passed canon by about 200 blocks.
  1863  //
  1864  // Details at:
  1865  //  - https://github.com/ethereum/go-ethereum/issues/18977
  1866  //  - https://github.com/ethereum/go-ethereum/pull/18988
  1867  func TestLowDiffLongChain(t *testing.T) {
  1868  	// Generate a canonical chain to act as the main dataset
  1869  	engine := ethash.NewFaker()
  1870  	db := rawdb.NewMemoryDatabase()
  1871  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  1872  
  1873  	// We must use a pretty long chain to ensure that the fork doesn't overtake us
  1874  	// until after at least 128 blocks post tip
  1875  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 6*TriesInMemory, func(i int, b *BlockGen) {
  1876  		b.SetCoinbase(common.Address{1})
  1877  		b.OffsetTime(-9)
  1878  	})
  1879  
  1880  	// Import the canonical chain
  1881  	diskdb := rawdb.NewMemoryDatabase()
  1882  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(diskdb)
  1883  
  1884  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  1885  	if err != nil {
  1886  		t.Fatalf("failed to create tester chain: %v", err)
  1887  	}
  1888  	if n, err := chain.InsertChain(blocks); err != nil {
  1889  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  1890  	}
  1891  	// Generate fork chain, starting from an early block
  1892  	parent := blocks[10]
  1893  	fork, _ := GenerateChain(params.TestChainConfig, parent, engine, db, 8*TriesInMemory, func(i int, b *BlockGen) {
  1894  		b.SetCoinbase(common.Address{2})
  1895  	})
  1896  
  1897  	// And now import the fork
  1898  	if i, err := chain.InsertChain(fork); err != nil {
  1899  		t.Fatalf("block %d: failed to insert into chain: %v", i, err)
  1900  	}
  1901  	head := chain.CurrentBlock()
  1902  	if got := fork[len(fork)-1].Hash(); got != head.Hash() {
  1903  		t.Fatalf("head wrong, expected %x got %x", head.Hash(), got)
  1904  	}
  1905  	// Sanity check that all the canonical numbers are present
  1906  	header := chain.CurrentHeader()
  1907  	for number := head.NumberU64(); number > 0; number-- {
  1908  		if hash := chain.GetHeaderByNumber(number).Hash(); hash != header.Hash() {
  1909  			t.Fatalf("header %d: canonical hash mismatch: have %x, want %x", number, hash, header.Hash())
  1910  		}
  1911  		header = chain.GetHeader(header.ParentHash, number-1)
  1912  	}
  1913  }
  1914  
  1915  // Tests that importing a sidechain (S), where
  1916  // - S is sidechain, containing blocks [Sn...Sm]
  1917  // - C is canon chain, containing blocks [G..Cn..Cm]
  1918  // - A common ancestor is placed at prune-point + blocksBetweenCommonAncestorAndPruneblock
  1919  // - The sidechain S is prepended with numCanonBlocksInSidechain blocks from the canon chain
  1920  //
  1921  // The mergePoint can be these values:
  1922  // -1: the transition won't happen
  1923  // 0:  the transition happens since genesis
  1924  // 1:  the transition happens after some chain segments
  1925  func testSideImport(t *testing.T, numCanonBlocksInSidechain, blocksBetweenCommonAncestorAndPruneblock int, mergePoint int) {
  1926  	// Copy the TestChainConfig so we can modify it during tests
  1927  	chainConfig := *params.TestChainConfig
  1928  	// Generate a canonical chain to act as the main dataset
  1929  	var (
  1930  		merger    = consensus.NewMerger(rawdb.NewMemoryDatabase())
  1931  		genEngine = beacon.New(ethash.NewFaker())
  1932  		runEngine = beacon.New(ethash.NewFaker())
  1933  		db        = rawdb.NewMemoryDatabase()
  1934  
  1935  		key, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  1936  		addr   = crypto.PubkeyToAddress(key.PublicKey)
  1937  		nonce  = uint64(0)
  1938  
  1939  		gspec = &Genesis{
  1940  			Config:  &chainConfig,
  1941  			Alloc:   GenesisAlloc{addr: {Balance: big.NewInt(math.MaxInt64)}},
  1942  			BaseFee: big.NewInt(params.InitialBaseFee),
  1943  		}
  1944  		signer  = types.LatestSigner(gspec.Config)
  1945  		genesis = gspec.MustCommit(db)
  1946  	)
  1947  	// Generate and import the canonical chain
  1948  	diskdb := rawdb.NewMemoryDatabase()
  1949  	gspec.MustCommit(diskdb)
  1950  	chain, err := NewBlockChain(diskdb, nil, &chainConfig, runEngine, vm.Config{}, nil, nil)
  1951  	if err != nil {
  1952  		t.Fatalf("failed to create tester chain: %v", err)
  1953  	}
  1954  	// Activate the transition since genesis if required
  1955  	if mergePoint == 0 {
  1956  		merger.ReachTTD()
  1957  		merger.FinalizePoS()
  1958  
  1959  		// Set the terminal total difficulty in the config
  1960  		gspec.Config.TerminalTotalDifficulty = big.NewInt(0)
  1961  	}
  1962  	blocks, _ := GenerateChain(&chainConfig, genesis, genEngine, db, 2*TriesInMemory, func(i int, gen *BlockGen) {
  1963  		tx, err := types.SignTx(types.NewTransaction(nonce, common.HexToAddress("deadbeef"), big.NewInt(100), 21000, big.NewInt(int64(i+1)*params.GWei), nil), signer, key)
  1964  		if err != nil {
  1965  			t.Fatalf("failed to create tx: %v", err)
  1966  		}
  1967  		gen.AddTx(tx)
  1968  		nonce++
  1969  	})
  1970  	if n, err := chain.InsertChain(blocks); err != nil {
  1971  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  1972  	}
  1973  
  1974  	lastPrunedIndex := len(blocks) - TriesInMemory - 1
  1975  	lastPrunedBlock := blocks[lastPrunedIndex]
  1976  	firstNonPrunedBlock := blocks[len(blocks)-TriesInMemory]
  1977  
  1978  	// Verify pruning of lastPrunedBlock
  1979  	if chain.HasBlockAndState(lastPrunedBlock.Hash(), lastPrunedBlock.NumberU64()) {
  1980  		t.Errorf("Block %d not pruned", lastPrunedBlock.NumberU64())
  1981  	}
  1982  	// Verify firstNonPrunedBlock is not pruned
  1983  	if !chain.HasBlockAndState(firstNonPrunedBlock.Hash(), firstNonPrunedBlock.NumberU64()) {
  1984  		t.Errorf("Block %d pruned", firstNonPrunedBlock.NumberU64())
  1985  	}
  1986  
  1987  	// Activate the transition in the middle of the chain
  1988  	if mergePoint == 1 {
  1989  		merger.ReachTTD()
  1990  		merger.FinalizePoS()
  1991  		// Set the terminal total difficulty in the config
  1992  		gspec.Config.TerminalTotalDifficulty = big.NewInt(int64(len(blocks)))
  1993  	}
  1994  
  1995  	// Generate the sidechain
  1996  	// First block should be a known block, block after should be a pruned block. So
  1997  	// canon(pruned), side, side...
  1998  
  1999  	// Generate fork chain, make it longer than canon
  2000  	parentIndex := lastPrunedIndex + blocksBetweenCommonAncestorAndPruneblock
  2001  	parent := blocks[parentIndex]
  2002  	fork, _ := GenerateChain(&chainConfig, parent, genEngine, db, 2*TriesInMemory, func(i int, b *BlockGen) {
  2003  		b.SetCoinbase(common.Address{2})
  2004  	})
  2005  	// Prepend the parent(s)
  2006  	var sidechain []*types.Block
  2007  	for i := numCanonBlocksInSidechain; i > 0; i-- {
  2008  		sidechain = append(sidechain, blocks[parentIndex+1-i])
  2009  	}
  2010  	sidechain = append(sidechain, fork...)
  2011  	n, err := chain.InsertChain(sidechain)
  2012  	if err != nil {
  2013  		t.Errorf("Got error, %v number %d - %d", err, sidechain[n].NumberU64(), n)
  2014  	}
  2015  	head := chain.CurrentBlock()
  2016  	if got := fork[len(fork)-1].Hash(); got != head.Hash() {
  2017  		t.Fatalf("head wrong, expected %x got %x", head.Hash(), got)
  2018  	}
  2019  }
  2020  
  2021  // Tests that importing a sidechain (S), where
  2022  // - S is sidechain, containing blocks [Sn...Sm]
  2023  // - C is canon chain, containing blocks [G..Cn..Cm]
  2024  // - The common ancestor Cc is pruned
  2025  // - The first block in S: Sn, is == Cn
  2026  // That is: the sidechain for import contains some blocks already present in canon chain.
  2027  // So the blocks are
  2028  // [ Cn, Cn+1, Cc, Sn+3 ... Sm]
  2029  //   ^    ^    ^  pruned
  2030  func TestPrunedImportSide(t *testing.T) {
  2031  	//glogger := log.NewGlogHandler(log.StreamHandler(os.Stdout, log.TerminalFormat(false)))
  2032  	//glogger.Verbosity(3)
  2033  	//log.Root().SetHandler(log.Handler(glogger))
  2034  	testSideImport(t, 3, 3, -1)
  2035  	testSideImport(t, 3, -3, -1)
  2036  	testSideImport(t, 10, 0, -1)
  2037  	testSideImport(t, 1, 10, -1)
  2038  	testSideImport(t, 1, -10, -1)
  2039  }
  2040  
  2041  func TestPrunedImportSideWithMerging(t *testing.T) {
  2042  	//glogger := log.NewGlogHandler(log.StreamHandler(os.Stdout, log.TerminalFormat(false)))
  2043  	//glogger.Verbosity(3)
  2044  	//log.Root().SetHandler(log.Handler(glogger))
  2045  	testSideImport(t, 3, 3, 0)
  2046  	testSideImport(t, 3, -3, 0)
  2047  	testSideImport(t, 10, 0, 0)
  2048  	testSideImport(t, 1, 10, 0)
  2049  	testSideImport(t, 1, -10, 0)
  2050  
  2051  	testSideImport(t, 3, 3, 1)
  2052  	testSideImport(t, 3, -3, 1)
  2053  	testSideImport(t, 10, 0, 1)
  2054  	testSideImport(t, 1, 10, 1)
  2055  	testSideImport(t, 1, -10, 1)
  2056  }
  2057  
  2058  func TestInsertKnownHeaders(t *testing.T)      { testInsertKnownChainData(t, "headers") }
  2059  func TestInsertKnownReceiptChain(t *testing.T) { testInsertKnownChainData(t, "receipts") }
  2060  func TestInsertKnownBlocks(t *testing.T)       { testInsertKnownChainData(t, "blocks") }
  2061  
  2062  func testInsertKnownChainData(t *testing.T, typ string) {
  2063  	engine := ethash.NewFaker()
  2064  
  2065  	db := rawdb.NewMemoryDatabase()
  2066  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  2067  
  2068  	blocks, receipts := GenerateChain(params.TestChainConfig, genesis, engine, db, 32, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  2069  	// A longer chain but total difficulty is lower.
  2070  	blocks2, receipts2 := GenerateChain(params.TestChainConfig, blocks[len(blocks)-1], engine, db, 65, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  2071  	// A shorter chain but total difficulty is higher.
  2072  	blocks3, receipts3 := GenerateChain(params.TestChainConfig, blocks[len(blocks)-1], engine, db, 64, func(i int, b *BlockGen) {
  2073  		b.SetCoinbase(common.Address{1})
  2074  		b.OffsetTime(-9) // A higher difficulty
  2075  	})
  2076  	// Import the shared chain and the original canonical one
  2077  	dir := t.TempDir()
  2078  	chaindb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), dir, "", false)
  2079  	if err != nil {
  2080  		t.Fatalf("failed to create temp freezer db: %v", err)
  2081  	}
  2082  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(chaindb)
  2083  	defer chaindb.Close()
  2084  
  2085  	chain, err := NewBlockChain(chaindb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  2086  	if err != nil {
  2087  		t.Fatalf("failed to create tester chain: %v", err)
  2088  	}
  2089  
  2090  	var (
  2091  		inserter func(blocks []*types.Block, receipts []types.Receipts) error
  2092  		asserter func(t *testing.T, block *types.Block)
  2093  	)
  2094  	if typ == "headers" {
  2095  		inserter = func(blocks []*types.Block, receipts []types.Receipts) error {
  2096  			headers := make([]*types.Header, 0, len(blocks))
  2097  			for _, block := range blocks {
  2098  				headers = append(headers, block.Header())
  2099  			}
  2100  			_, err := chain.InsertHeaderChain(headers, 1)
  2101  			return err
  2102  		}
  2103  		asserter = func(t *testing.T, block *types.Block) {
  2104  			if chain.CurrentHeader().Hash() != block.Hash() {
  2105  				t.Fatalf("current head header mismatch, have %v, want %v", chain.CurrentHeader().Hash().Hex(), block.Hash().Hex())
  2106  			}
  2107  		}
  2108  	} else if typ == "receipts" {
  2109  		inserter = func(blocks []*types.Block, receipts []types.Receipts) error {
  2110  			headers := make([]*types.Header, 0, len(blocks))
  2111  			for _, block := range blocks {
  2112  				headers = append(headers, block.Header())
  2113  			}
  2114  			_, err := chain.InsertHeaderChain(headers, 1)
  2115  			if err != nil {
  2116  				return err
  2117  			}
  2118  			_, err = chain.InsertReceiptChain(blocks, receipts, 0)
  2119  			return err
  2120  		}
  2121  		asserter = func(t *testing.T, block *types.Block) {
  2122  			if chain.CurrentFastBlock().Hash() != block.Hash() {
  2123  				t.Fatalf("current head fast block mismatch, have %v, want %v", chain.CurrentFastBlock().Hash().Hex(), block.Hash().Hex())
  2124  			}
  2125  		}
  2126  	} else {
  2127  		inserter = func(blocks []*types.Block, receipts []types.Receipts) error {
  2128  			_, err := chain.InsertChain(blocks)
  2129  			return err
  2130  		}
  2131  		asserter = func(t *testing.T, block *types.Block) {
  2132  			if chain.CurrentBlock().Hash() != block.Hash() {
  2133  				t.Fatalf("current head block mismatch, have %v, want %v", chain.CurrentBlock().Hash().Hex(), block.Hash().Hex())
  2134  			}
  2135  		}
  2136  	}
  2137  
  2138  	if err := inserter(blocks, receipts); err != nil {
  2139  		t.Fatalf("failed to insert chain data: %v", err)
  2140  	}
  2141  
  2142  	// Reimport the chain data again. All the imported
  2143  	// chain data are regarded "known" data.
  2144  	if err := inserter(blocks, receipts); err != nil {
  2145  		t.Fatalf("failed to insert chain data: %v", err)
  2146  	}
  2147  	asserter(t, blocks[len(blocks)-1])
  2148  
  2149  	// Import a long canonical chain with some known data as prefix.
  2150  	rollback := blocks[len(blocks)/2].NumberU64()
  2151  
  2152  	chain.SetHead(rollback - 1)
  2153  	if err := inserter(append(blocks, blocks2...), append(receipts, receipts2...)); err != nil {
  2154  		t.Fatalf("failed to insert chain data: %v", err)
  2155  	}
  2156  	asserter(t, blocks2[len(blocks2)-1])
  2157  
  2158  	// Import a heavier shorter but higher total difficulty chain with some known data as prefix.
  2159  	if err := inserter(append(blocks, blocks3...), append(receipts, receipts3...)); err != nil {
  2160  		t.Fatalf("failed to insert chain data: %v", err)
  2161  	}
  2162  	asserter(t, blocks3[len(blocks3)-1])
  2163  
  2164  	// Import a longer but lower total difficulty chain with some known data as prefix.
  2165  	if err := inserter(append(blocks, blocks2...), append(receipts, receipts2...)); err != nil {
  2166  		t.Fatalf("failed to insert chain data: %v", err)
  2167  	}
  2168  	// The head shouldn't change.
  2169  	asserter(t, blocks3[len(blocks3)-1])
  2170  
  2171  	// Rollback the heavier chain and re-insert the longer chain again
  2172  	chain.SetHead(rollback - 1)
  2173  	if err := inserter(append(blocks, blocks2...), append(receipts, receipts2...)); err != nil {
  2174  		t.Fatalf("failed to insert chain data: %v", err)
  2175  	}
  2176  	asserter(t, blocks2[len(blocks2)-1])
  2177  }
  2178  
  2179  func TestInsertKnownHeadersWithMerging(t *testing.T) {
  2180  	testInsertKnownChainDataWithMerging(t, "headers", 0)
  2181  }
  2182  func TestInsertKnownReceiptChainWithMerging(t *testing.T) {
  2183  	testInsertKnownChainDataWithMerging(t, "receipts", 0)
  2184  }
  2185  func TestInsertKnownBlocksWithMerging(t *testing.T) {
  2186  	testInsertKnownChainDataWithMerging(t, "blocks", 0)
  2187  }
  2188  func TestInsertKnownHeadersAfterMerging(t *testing.T) {
  2189  	testInsertKnownChainDataWithMerging(t, "headers", 1)
  2190  }
  2191  func TestInsertKnownReceiptChainAfterMerging(t *testing.T) {
  2192  	testInsertKnownChainDataWithMerging(t, "receipts", 1)
  2193  }
  2194  func TestInsertKnownBlocksAfterMerging(t *testing.T) {
  2195  	testInsertKnownChainDataWithMerging(t, "blocks", 1)
  2196  }
  2197  
  2198  // mergeHeight can be assigned in these values:
  2199  // 0: means the merging is applied since genesis
  2200  // 1: means the merging is applied after the first segment
  2201  func testInsertKnownChainDataWithMerging(t *testing.T, typ string, mergeHeight int) {
  2202  	// Copy the TestChainConfig so we can modify it during tests
  2203  	chainConfig := *params.TestChainConfig
  2204  	var (
  2205  		db        = rawdb.NewMemoryDatabase()
  2206  		genesis   = (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee), Config: &chainConfig}).MustCommit(db)
  2207  		runMerger = consensus.NewMerger(db)
  2208  		runEngine = beacon.New(ethash.NewFaker())
  2209  		genEngine = beacon.New(ethash.NewFaker())
  2210  	)
  2211  	applyMerge := func(engine *beacon.Beacon, height int) {
  2212  		if engine != nil {
  2213  			runMerger.FinalizePoS()
  2214  			// Set the terminal total difficulty in the config
  2215  			chainConfig.TerminalTotalDifficulty = big.NewInt(int64(height))
  2216  		}
  2217  	}
  2218  
  2219  	// Apply merging since genesis
  2220  	if mergeHeight == 0 {
  2221  		applyMerge(genEngine, 0)
  2222  	}
  2223  	blocks, receipts := GenerateChain(&chainConfig, genesis, genEngine, db, 32, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  2224  
  2225  	// Apply merging after the first segment
  2226  	if mergeHeight == 1 {
  2227  		applyMerge(genEngine, len(blocks))
  2228  	}
  2229  	// Longer chain and shorter chain
  2230  	blocks2, receipts2 := GenerateChain(&chainConfig, blocks[len(blocks)-1], genEngine, db, 65, func(i int, b *BlockGen) { b.SetCoinbase(common.Address{1}) })
  2231  	blocks3, receipts3 := GenerateChain(&chainConfig, blocks[len(blocks)-1], genEngine, db, 64, func(i int, b *BlockGen) {
  2232  		b.SetCoinbase(common.Address{1})
  2233  		b.OffsetTime(-9) // Time shifted, difficulty shouldn't be changed
  2234  	})
  2235  
  2236  	// Import the shared chain and the original canonical one
  2237  	dir := t.TempDir()
  2238  	chaindb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), dir, "", false)
  2239  	if err != nil {
  2240  		t.Fatalf("failed to create temp freezer db: %v", err)
  2241  	}
  2242  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(chaindb)
  2243  	defer chaindb.Close()
  2244  
  2245  	chain, err := NewBlockChain(chaindb, nil, &chainConfig, runEngine, vm.Config{}, nil, nil)
  2246  	if err != nil {
  2247  		t.Fatalf("failed to create tester chain: %v", err)
  2248  	}
  2249  	var (
  2250  		inserter func(blocks []*types.Block, receipts []types.Receipts) error
  2251  		asserter func(t *testing.T, block *types.Block)
  2252  	)
  2253  	if typ == "headers" {
  2254  		inserter = func(blocks []*types.Block, receipts []types.Receipts) error {
  2255  			headers := make([]*types.Header, 0, len(blocks))
  2256  			for _, block := range blocks {
  2257  				headers = append(headers, block.Header())
  2258  			}
  2259  			_, err := chain.InsertHeaderChain(headers, 1)
  2260  			return err
  2261  		}
  2262  		asserter = func(t *testing.T, block *types.Block) {
  2263  			if chain.CurrentHeader().Hash() != block.Hash() {
  2264  				t.Fatalf("current head header mismatch, have %v, want %v", chain.CurrentHeader().Hash().Hex(), block.Hash().Hex())
  2265  			}
  2266  		}
  2267  	} else if typ == "receipts" {
  2268  		inserter = func(blocks []*types.Block, receipts []types.Receipts) error {
  2269  			headers := make([]*types.Header, 0, len(blocks))
  2270  			for _, block := range blocks {
  2271  				headers = append(headers, block.Header())
  2272  			}
  2273  			_, err := chain.InsertHeaderChain(headers, 1)
  2274  			if err != nil {
  2275  				return err
  2276  			}
  2277  			_, err = chain.InsertReceiptChain(blocks, receipts, 0)
  2278  			return err
  2279  		}
  2280  		asserter = func(t *testing.T, block *types.Block) {
  2281  			if chain.CurrentFastBlock().Hash() != block.Hash() {
  2282  				t.Fatalf("current head fast block mismatch, have %v, want %v", chain.CurrentFastBlock().Hash().Hex(), block.Hash().Hex())
  2283  			}
  2284  		}
  2285  	} else {
  2286  		inserter = func(blocks []*types.Block, receipts []types.Receipts) error {
  2287  			_, err := chain.InsertChain(blocks)
  2288  			return err
  2289  		}
  2290  		asserter = func(t *testing.T, block *types.Block) {
  2291  			if chain.CurrentBlock().Hash() != block.Hash() {
  2292  				t.Fatalf("current head block mismatch, have %v, want %v", chain.CurrentBlock().Hash().Hex(), block.Hash().Hex())
  2293  			}
  2294  		}
  2295  	}
  2296  
  2297  	// Apply merging since genesis if required
  2298  	if mergeHeight == 0 {
  2299  		applyMerge(runEngine, 0)
  2300  	}
  2301  	if err := inserter(blocks, receipts); err != nil {
  2302  		t.Fatalf("failed to insert chain data: %v", err)
  2303  	}
  2304  
  2305  	// Reimport the chain data again. All the imported
  2306  	// chain data are regarded "known" data.
  2307  	if err := inserter(blocks, receipts); err != nil {
  2308  		t.Fatalf("failed to insert chain data: %v", err)
  2309  	}
  2310  	asserter(t, blocks[len(blocks)-1])
  2311  
  2312  	// Import a long canonical chain with some known data as prefix.
  2313  	rollback := blocks[len(blocks)/2].NumberU64()
  2314  	chain.SetHead(rollback - 1)
  2315  	if err := inserter(blocks, receipts); err != nil {
  2316  		t.Fatalf("failed to insert chain data: %v", err)
  2317  	}
  2318  	asserter(t, blocks[len(blocks)-1])
  2319  
  2320  	// Apply merging after the first segment
  2321  	if mergeHeight == 1 {
  2322  		applyMerge(runEngine, len(blocks))
  2323  	}
  2324  
  2325  	// Import a longer chain with some known data as prefix.
  2326  	if err := inserter(append(blocks, blocks2...), append(receipts, receipts2...)); err != nil {
  2327  		t.Fatalf("failed to insert chain data: %v", err)
  2328  	}
  2329  	asserter(t, blocks2[len(blocks2)-1])
  2330  
  2331  	// Import a shorter chain with some known data as prefix.
  2332  	// The reorg is expected since the fork choice rule is
  2333  	// already changed.
  2334  	if err := inserter(append(blocks, blocks3...), append(receipts, receipts3...)); err != nil {
  2335  		t.Fatalf("failed to insert chain data: %v", err)
  2336  	}
  2337  	// The head shouldn't change.
  2338  	asserter(t, blocks3[len(blocks3)-1])
  2339  
  2340  	// Reimport the longer chain again, the reorg is still expected
  2341  	chain.SetHead(rollback - 1)
  2342  	if err := inserter(append(blocks, blocks2...), append(receipts, receipts2...)); err != nil {
  2343  		t.Fatalf("failed to insert chain data: %v", err)
  2344  	}
  2345  	asserter(t, blocks2[len(blocks2)-1])
  2346  }
  2347  
  2348  // getLongAndShortChains returns two chains: A is longer, B is heavier.
  2349  func getLongAndShortChains() (bc *BlockChain, longChain []*types.Block, heavyChain []*types.Block, err error) {
  2350  	// Generate a canonical chain to act as the main dataset
  2351  	engine := ethash.NewFaker()
  2352  	db := rawdb.NewMemoryDatabase()
  2353  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  2354  
  2355  	// Generate and import the canonical chain,
  2356  	// Offset the time, to keep the difficulty low
  2357  	longChain, _ = GenerateChain(params.TestChainConfig, genesis, engine, db, 80, func(i int, b *BlockGen) {
  2358  		b.SetCoinbase(common.Address{1})
  2359  	})
  2360  	diskdb := rawdb.NewMemoryDatabase()
  2361  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(diskdb)
  2362  
  2363  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  2364  	if err != nil {
  2365  		return nil, nil, nil, fmt.Errorf("failed to create tester chain: %v", err)
  2366  	}
  2367  
  2368  	// Generate fork chain, make it shorter than canon, with common ancestor pretty early
  2369  	parentIndex := 3
  2370  	parent := longChain[parentIndex]
  2371  	heavyChainExt, _ := GenerateChain(params.TestChainConfig, parent, engine, db, 75, func(i int, b *BlockGen) {
  2372  		b.SetCoinbase(common.Address{2})
  2373  		b.OffsetTime(-9)
  2374  	})
  2375  	heavyChain = append(heavyChain, longChain[:parentIndex+1]...)
  2376  	heavyChain = append(heavyChain, heavyChainExt...)
  2377  
  2378  	// Verify that the test is sane
  2379  	var (
  2380  		longerTd  = new(big.Int)
  2381  		shorterTd = new(big.Int)
  2382  	)
  2383  	for index, b := range longChain {
  2384  		longerTd.Add(longerTd, b.Difficulty())
  2385  		if index <= parentIndex {
  2386  			shorterTd.Add(shorterTd, b.Difficulty())
  2387  		}
  2388  	}
  2389  	for _, b := range heavyChain {
  2390  		shorterTd.Add(shorterTd, b.Difficulty())
  2391  	}
  2392  	if shorterTd.Cmp(longerTd) <= 0 {
  2393  		return nil, nil, nil, fmt.Errorf("Test is moot, heavyChain td (%v) must be larger than canon td (%v)", shorterTd, longerTd)
  2394  	}
  2395  	longerNum := longChain[len(longChain)-1].NumberU64()
  2396  	shorterNum := heavyChain[len(heavyChain)-1].NumberU64()
  2397  	if shorterNum >= longerNum {
  2398  		return nil, nil, nil, fmt.Errorf("Test is moot, heavyChain num (%v) must be lower than canon num (%v)", shorterNum, longerNum)
  2399  	}
  2400  	return chain, longChain, heavyChain, nil
  2401  }
  2402  
  2403  // TestReorgToShorterRemovesCanonMapping tests that if we
  2404  // 1. Have a chain [0 ... N .. X]
  2405  // 2. Reorg to shorter but heavier chain [0 ... N ... Y]
  2406  // 3. Then there should be no canon mapping for the block at height X
  2407  // 4. The forked block should still be retrievable by hash
  2408  func TestReorgToShorterRemovesCanonMapping(t *testing.T) {
  2409  	chain, canonblocks, sideblocks, err := getLongAndShortChains()
  2410  	if err != nil {
  2411  		t.Fatal(err)
  2412  	}
  2413  	if n, err := chain.InsertChain(canonblocks); err != nil {
  2414  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  2415  	}
  2416  	canonNum := chain.CurrentBlock().NumberU64()
  2417  	canonHash := chain.CurrentBlock().Hash()
  2418  	_, err = chain.InsertChain(sideblocks)
  2419  	if err != nil {
  2420  		t.Errorf("Got error, %v", err)
  2421  	}
  2422  	head := chain.CurrentBlock()
  2423  	if got := sideblocks[len(sideblocks)-1].Hash(); got != head.Hash() {
  2424  		t.Fatalf("head wrong, expected %x got %x", head.Hash(), got)
  2425  	}
  2426  	// We have now inserted a sidechain.
  2427  	if blockByNum := chain.GetBlockByNumber(canonNum); blockByNum != nil {
  2428  		t.Errorf("expected block to be gone: %v", blockByNum.NumberU64())
  2429  	}
  2430  	if headerByNum := chain.GetHeaderByNumber(canonNum); headerByNum != nil {
  2431  		t.Errorf("expected header to be gone: %v", headerByNum.Number.Uint64())
  2432  	}
  2433  	if blockByHash := chain.GetBlockByHash(canonHash); blockByHash == nil {
  2434  		t.Errorf("expected block to be present: %x", blockByHash.Hash())
  2435  	}
  2436  	if headerByHash := chain.GetHeaderByHash(canonHash); headerByHash == nil {
  2437  		t.Errorf("expected header to be present: %x", headerByHash.Hash())
  2438  	}
  2439  }
  2440  
  2441  // TestReorgToShorterRemovesCanonMappingHeaderChain is the same scenario
  2442  // as TestReorgToShorterRemovesCanonMapping, but applied on headerchain
  2443  // imports -- that is, for fast sync
  2444  func TestReorgToShorterRemovesCanonMappingHeaderChain(t *testing.T) {
  2445  	chain, canonblocks, sideblocks, err := getLongAndShortChains()
  2446  	if err != nil {
  2447  		t.Fatal(err)
  2448  	}
  2449  	// Convert into headers
  2450  	canonHeaders := make([]*types.Header, len(canonblocks))
  2451  	for i, block := range canonblocks {
  2452  		canonHeaders[i] = block.Header()
  2453  	}
  2454  	if n, err := chain.InsertHeaderChain(canonHeaders, 0); err != nil {
  2455  		t.Fatalf("header %d: failed to insert into chain: %v", n, err)
  2456  	}
  2457  	canonNum := chain.CurrentHeader().Number.Uint64()
  2458  	canonHash := chain.CurrentBlock().Hash()
  2459  	sideHeaders := make([]*types.Header, len(sideblocks))
  2460  	for i, block := range sideblocks {
  2461  		sideHeaders[i] = block.Header()
  2462  	}
  2463  	if n, err := chain.InsertHeaderChain(sideHeaders, 0); err != nil {
  2464  		t.Fatalf("header %d: failed to insert into chain: %v", n, err)
  2465  	}
  2466  	head := chain.CurrentHeader()
  2467  	if got := sideblocks[len(sideblocks)-1].Hash(); got != head.Hash() {
  2468  		t.Fatalf("head wrong, expected %x got %x", head.Hash(), got)
  2469  	}
  2470  	// We have now inserted a sidechain.
  2471  	if blockByNum := chain.GetBlockByNumber(canonNum); blockByNum != nil {
  2472  		t.Errorf("expected block to be gone: %v", blockByNum.NumberU64())
  2473  	}
  2474  	if headerByNum := chain.GetHeaderByNumber(canonNum); headerByNum != nil {
  2475  		t.Errorf("expected header to be gone: %v", headerByNum.Number.Uint64())
  2476  	}
  2477  	if blockByHash := chain.GetBlockByHash(canonHash); blockByHash == nil {
  2478  		t.Errorf("expected block to be present: %x", blockByHash.Hash())
  2479  	}
  2480  	if headerByHash := chain.GetHeaderByHash(canonHash); headerByHash == nil {
  2481  		t.Errorf("expected header to be present: %x", headerByHash.Hash())
  2482  	}
  2483  }
  2484  
  2485  func TestTransactionIndices(t *testing.T) {
  2486  	// Configure and generate a sample block chain
  2487  	var (
  2488  		gendb   = rawdb.NewMemoryDatabase()
  2489  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  2490  		address = crypto.PubkeyToAddress(key.PublicKey)
  2491  		funds   = big.NewInt(100000000000000000)
  2492  		gspec   = &Genesis{
  2493  			Config:  params.TestChainConfig,
  2494  			Alloc:   GenesisAlloc{address: {Balance: funds}},
  2495  			BaseFee: big.NewInt(params.InitialBaseFee),
  2496  		}
  2497  		genesis = gspec.MustCommit(gendb)
  2498  		signer  = types.LatestSigner(gspec.Config)
  2499  	)
  2500  	height := uint64(128)
  2501  	blocks, receipts := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), gendb, int(height), func(i int, block *BlockGen) {
  2502  		tx, err := types.SignTx(types.NewTransaction(block.TxNonce(address), common.Address{0x00}, big.NewInt(1000), params.TxGas, block.header.BaseFee, nil), signer, key)
  2503  		if err != nil {
  2504  			panic(err)
  2505  		}
  2506  		block.AddTx(tx)
  2507  	})
  2508  	blocks2, _ := GenerateChain(gspec.Config, blocks[len(blocks)-1], ethash.NewFaker(), gendb, 10, nil)
  2509  
  2510  	check := func(tail *uint64, chain *BlockChain) {
  2511  		stored := rawdb.ReadTxIndexTail(chain.db)
  2512  		if tail == nil && stored != nil {
  2513  			t.Fatalf("Oldest indexded block mismatch, want nil, have %d", *stored)
  2514  		}
  2515  		if tail != nil && *stored != *tail {
  2516  			t.Fatalf("Oldest indexded block mismatch, want %d, have %d", *tail, *stored)
  2517  		}
  2518  		if tail != nil {
  2519  			for i := *tail; i <= chain.CurrentBlock().NumberU64(); i++ {
  2520  				block := rawdb.ReadBlock(chain.db, rawdb.ReadCanonicalHash(chain.db, i), i)
  2521  				if block.Transactions().Len() == 0 {
  2522  					continue
  2523  				}
  2524  				for _, tx := range block.Transactions() {
  2525  					if index := rawdb.ReadTxLookupEntry(chain.db, tx.Hash()); index == nil {
  2526  						t.Fatalf("Miss transaction indice, number %d hash %s", i, tx.Hash().Hex())
  2527  					}
  2528  				}
  2529  			}
  2530  			for i := uint64(0); i < *tail; i++ {
  2531  				block := rawdb.ReadBlock(chain.db, rawdb.ReadCanonicalHash(chain.db, i), i)
  2532  				if block.Transactions().Len() == 0 {
  2533  					continue
  2534  				}
  2535  				for _, tx := range block.Transactions() {
  2536  					if index := rawdb.ReadTxLookupEntry(chain.db, tx.Hash()); index != nil {
  2537  						t.Fatalf("Transaction indice should be deleted, number %d hash %s", i, tx.Hash().Hex())
  2538  					}
  2539  				}
  2540  			}
  2541  		}
  2542  	}
  2543  	frdir := t.TempDir()
  2544  	ancientDb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
  2545  	if err != nil {
  2546  		t.Fatalf("failed to create temp freezer db: %v", err)
  2547  	}
  2548  	gspec.MustCommit(ancientDb)
  2549  
  2550  	// Import all blocks into ancient db
  2551  	l := uint64(0)
  2552  	chain, err := NewBlockChain(ancientDb, nil, params.TestChainConfig, ethash.NewFaker(), vm.Config{}, nil, &l)
  2553  	if err != nil {
  2554  		t.Fatalf("failed to create tester chain: %v", err)
  2555  	}
  2556  	headers := make([]*types.Header, len(blocks))
  2557  	for i, block := range blocks {
  2558  		headers[i] = block.Header()
  2559  	}
  2560  	if n, err := chain.InsertHeaderChain(headers, 0); err != nil {
  2561  		t.Fatalf("failed to insert header %d: %v", n, err)
  2562  	}
  2563  	if n, err := chain.InsertReceiptChain(blocks, receipts, 128); err != nil {
  2564  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  2565  	}
  2566  	chain.Stop()
  2567  	ancientDb.Close()
  2568  
  2569  	// Init block chain with external ancients, check all needed indices has been indexed.
  2570  	limit := []uint64{0, 32, 64, 128}
  2571  	for _, l := range limit {
  2572  		ancientDb, err = rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
  2573  		if err != nil {
  2574  			t.Fatalf("failed to create temp freezer db: %v", err)
  2575  		}
  2576  		gspec.MustCommit(ancientDb)
  2577  		l := l
  2578  		chain, err = NewBlockChain(ancientDb, nil, params.TestChainConfig, ethash.NewFaker(), vm.Config{}, nil, &l)
  2579  		if err != nil {
  2580  			t.Fatalf("failed to create tester chain: %v", err)
  2581  		}
  2582  		time.Sleep(50 * time.Millisecond) // Wait for indices initialisation
  2583  		var tail uint64
  2584  		if l != 0 {
  2585  			tail = uint64(128) - l + 1
  2586  		}
  2587  		check(&tail, chain)
  2588  		chain.Stop()
  2589  		ancientDb.Close()
  2590  	}
  2591  
  2592  	// Reconstruct a block chain which only reserves HEAD-64 tx indices
  2593  	ancientDb, err = rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
  2594  	if err != nil {
  2595  		t.Fatalf("failed to create temp freezer db: %v", err)
  2596  	}
  2597  	defer ancientDb.Close()
  2598  	gspec.MustCommit(ancientDb)
  2599  
  2600  	limit = []uint64{0, 64 /* drop stale */, 32 /* shorten history */, 64 /* extend history */, 0 /* restore all */}
  2601  	tails := []uint64{0, 67 /* 130 - 64 + 1 */, 100 /* 131 - 32 + 1 */, 69 /* 132 - 64 + 1 */, 0}
  2602  	for i, l := range limit {
  2603  		l := l
  2604  		chain, err = NewBlockChain(ancientDb, nil, params.TestChainConfig, ethash.NewFaker(), vm.Config{}, nil, &l)
  2605  		if err != nil {
  2606  			t.Fatalf("failed to create tester chain: %v", err)
  2607  		}
  2608  		chain.InsertChain(blocks2[i : i+1]) // Feed chain a higher block to trigger indices updater.
  2609  		time.Sleep(50 * time.Millisecond)   // Wait for indices initialisation
  2610  		check(&tails[i], chain)
  2611  		chain.Stop()
  2612  	}
  2613  }
  2614  
  2615  func TestSkipStaleTxIndicesInSnapSync(t *testing.T) {
  2616  	// Configure and generate a sample block chain
  2617  	var (
  2618  		gendb   = rawdb.NewMemoryDatabase()
  2619  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  2620  		address = crypto.PubkeyToAddress(key.PublicKey)
  2621  		funds   = big.NewInt(100000000000000000)
  2622  		gspec   = &Genesis{Config: params.TestChainConfig, Alloc: GenesisAlloc{address: {Balance: funds}}}
  2623  		genesis = gspec.MustCommit(gendb)
  2624  		signer  = types.LatestSigner(gspec.Config)
  2625  	)
  2626  	height := uint64(128)
  2627  	blocks, receipts := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), gendb, int(height), func(i int, block *BlockGen) {
  2628  		tx, err := types.SignTx(types.NewTransaction(block.TxNonce(address), common.Address{0x00}, big.NewInt(1000), params.TxGas, block.header.BaseFee, nil), signer, key)
  2629  		if err != nil {
  2630  			panic(err)
  2631  		}
  2632  		block.AddTx(tx)
  2633  	})
  2634  
  2635  	check := func(tail *uint64, chain *BlockChain) {
  2636  		stored := rawdb.ReadTxIndexTail(chain.db)
  2637  		if tail == nil && stored != nil {
  2638  			t.Fatalf("Oldest indexded block mismatch, want nil, have %d", *stored)
  2639  		}
  2640  		if tail != nil && *stored != *tail {
  2641  			t.Fatalf("Oldest indexded block mismatch, want %d, have %d", *tail, *stored)
  2642  		}
  2643  		if tail != nil {
  2644  			for i := *tail; i <= chain.CurrentBlock().NumberU64(); i++ {
  2645  				block := rawdb.ReadBlock(chain.db, rawdb.ReadCanonicalHash(chain.db, i), i)
  2646  				if block.Transactions().Len() == 0 {
  2647  					continue
  2648  				}
  2649  				for _, tx := range block.Transactions() {
  2650  					if index := rawdb.ReadTxLookupEntry(chain.db, tx.Hash()); index == nil {
  2651  						t.Fatalf("Miss transaction indice, number %d hash %s", i, tx.Hash().Hex())
  2652  					}
  2653  				}
  2654  			}
  2655  			for i := uint64(0); i < *tail; i++ {
  2656  				block := rawdb.ReadBlock(chain.db, rawdb.ReadCanonicalHash(chain.db, i), i)
  2657  				if block.Transactions().Len() == 0 {
  2658  					continue
  2659  				}
  2660  				for _, tx := range block.Transactions() {
  2661  					if index := rawdb.ReadTxLookupEntry(chain.db, tx.Hash()); index != nil {
  2662  						t.Fatalf("Transaction indice should be deleted, number %d hash %s", i, tx.Hash().Hex())
  2663  					}
  2664  				}
  2665  			}
  2666  		}
  2667  	}
  2668  
  2669  	frdir := t.TempDir()
  2670  	ancientDb, err := rawdb.NewDatabaseWithFreezer(rawdb.NewMemoryDatabase(), frdir, "", false)
  2671  	if err != nil {
  2672  		t.Fatalf("failed to create temp freezer db: %v", err)
  2673  	}
  2674  	defer ancientDb.Close()
  2675  	gspec.MustCommit(ancientDb)
  2676  
  2677  	// Import all blocks into ancient db, only HEAD-32 indices are kept.
  2678  	l := uint64(32)
  2679  	chain, err := NewBlockChain(ancientDb, nil, params.TestChainConfig, ethash.NewFaker(), vm.Config{}, nil, &l)
  2680  	if err != nil {
  2681  		t.Fatalf("failed to create tester chain: %v", err)
  2682  	}
  2683  	headers := make([]*types.Header, len(blocks))
  2684  	for i, block := range blocks {
  2685  		headers[i] = block.Header()
  2686  	}
  2687  	if n, err := chain.InsertHeaderChain(headers, 0); err != nil {
  2688  		t.Fatalf("failed to insert header %d: %v", n, err)
  2689  	}
  2690  	// The indices before ancient-N(32) should be ignored. After that all blocks should be indexed.
  2691  	if n, err := chain.InsertReceiptChain(blocks, receipts, 64); err != nil {
  2692  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  2693  	}
  2694  	tail := uint64(32)
  2695  	check(&tail, chain)
  2696  }
  2697  
  2698  // Benchmarks large blocks with value transfers to non-existing accounts
  2699  func benchmarkLargeNumberOfValueToNonexisting(b *testing.B, numTxs, numBlocks int, recipientFn func(uint64) common.Address, dataFn func(uint64) []byte) {
  2700  	var (
  2701  		signer          = types.HomesteadSigner{}
  2702  		testBankKey, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  2703  		testBankAddress = crypto.PubkeyToAddress(testBankKey.PublicKey)
  2704  		bankFunds       = big.NewInt(100000000000000000)
  2705  		gspec           = Genesis{
  2706  			Config: params.TestChainConfig,
  2707  			Alloc: GenesisAlloc{
  2708  				testBankAddress: {Balance: bankFunds},
  2709  				common.HexToAddress("0xc0de"): {
  2710  					Code:    []byte{0x60, 0x01, 0x50},
  2711  					Balance: big.NewInt(0),
  2712  				}, // push 1, pop
  2713  			},
  2714  			GasLimit: 100e6, // 100 M
  2715  		}
  2716  	)
  2717  	// Generate the original common chain segment and the two competing forks
  2718  	engine := ethash.NewFaker()
  2719  	db := rawdb.NewMemoryDatabase()
  2720  	genesis := gspec.MustCommit(db)
  2721  
  2722  	blockGenerator := func(i int, block *BlockGen) {
  2723  		block.SetCoinbase(common.Address{1})
  2724  		for txi := 0; txi < numTxs; txi++ {
  2725  			uniq := uint64(i*numTxs + txi)
  2726  			recipient := recipientFn(uniq)
  2727  			tx, err := types.SignTx(types.NewTransaction(uniq, recipient, big.NewInt(1), params.TxGas, block.header.BaseFee, nil), signer, testBankKey)
  2728  			if err != nil {
  2729  				b.Error(err)
  2730  			}
  2731  			block.AddTx(tx)
  2732  		}
  2733  	}
  2734  
  2735  	shared, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, numBlocks, blockGenerator)
  2736  	b.StopTimer()
  2737  	b.ResetTimer()
  2738  	for i := 0; i < b.N; i++ {
  2739  		// Import the shared chain and the original canonical one
  2740  		diskdb := rawdb.NewMemoryDatabase()
  2741  		gspec.MustCommit(diskdb)
  2742  
  2743  		chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  2744  		if err != nil {
  2745  			b.Fatalf("failed to create tester chain: %v", err)
  2746  		}
  2747  		b.StartTimer()
  2748  		if _, err := chain.InsertChain(shared); err != nil {
  2749  			b.Fatalf("failed to insert shared chain: %v", err)
  2750  		}
  2751  		b.StopTimer()
  2752  		if got := chain.CurrentBlock().Transactions().Len(); got != numTxs*numBlocks {
  2753  			b.Fatalf("Transactions were not included, expected %d, got %d", numTxs*numBlocks, got)
  2754  		}
  2755  	}
  2756  }
  2757  
  2758  func BenchmarkBlockChain_1x1000ValueTransferToNonexisting(b *testing.B) {
  2759  	var (
  2760  		numTxs    = 1000
  2761  		numBlocks = 1
  2762  	)
  2763  	recipientFn := func(nonce uint64) common.Address {
  2764  		return common.BigToAddress(new(big.Int).SetUint64(1337 + nonce))
  2765  	}
  2766  	dataFn := func(nonce uint64) []byte {
  2767  		return nil
  2768  	}
  2769  	benchmarkLargeNumberOfValueToNonexisting(b, numTxs, numBlocks, recipientFn, dataFn)
  2770  }
  2771  
  2772  func BenchmarkBlockChain_1x1000ValueTransferToExisting(b *testing.B) {
  2773  	var (
  2774  		numTxs    = 1000
  2775  		numBlocks = 1
  2776  	)
  2777  	b.StopTimer()
  2778  	b.ResetTimer()
  2779  
  2780  	recipientFn := func(nonce uint64) common.Address {
  2781  		return common.BigToAddress(new(big.Int).SetUint64(1337))
  2782  	}
  2783  	dataFn := func(nonce uint64) []byte {
  2784  		return nil
  2785  	}
  2786  	benchmarkLargeNumberOfValueToNonexisting(b, numTxs, numBlocks, recipientFn, dataFn)
  2787  }
  2788  
  2789  func BenchmarkBlockChain_1x1000Executions(b *testing.B) {
  2790  	var (
  2791  		numTxs    = 1000
  2792  		numBlocks = 1
  2793  	)
  2794  	b.StopTimer()
  2795  	b.ResetTimer()
  2796  
  2797  	recipientFn := func(nonce uint64) common.Address {
  2798  		return common.BigToAddress(new(big.Int).SetUint64(0xc0de))
  2799  	}
  2800  	dataFn := func(nonce uint64) []byte {
  2801  		return nil
  2802  	}
  2803  	benchmarkLargeNumberOfValueToNonexisting(b, numTxs, numBlocks, recipientFn, dataFn)
  2804  }
  2805  
  2806  // Tests that importing a some old blocks, where all blocks are before the
  2807  // pruning point.
  2808  // This internally leads to a sidechain import, since the blocks trigger an
  2809  // ErrPrunedAncestor error.
  2810  // This may e.g. happen if
  2811  //   1. Downloader rollbacks a batch of inserted blocks and exits
  2812  //   2. Downloader starts to sync again
  2813  //   3. The blocks fetched are all known and canonical blocks
  2814  func TestSideImportPrunedBlocks(t *testing.T) {
  2815  	// Generate a canonical chain to act as the main dataset
  2816  	engine := ethash.NewFaker()
  2817  	db := rawdb.NewMemoryDatabase()
  2818  	genesis := (&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(db)
  2819  
  2820  	// Generate and import the canonical chain
  2821  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 2*TriesInMemory, nil)
  2822  	diskdb := rawdb.NewMemoryDatabase()
  2823  
  2824  	(&Genesis{BaseFee: big.NewInt(params.InitialBaseFee)}).MustCommit(diskdb)
  2825  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  2826  	if err != nil {
  2827  		t.Fatalf("failed to create tester chain: %v", err)
  2828  	}
  2829  	if n, err := chain.InsertChain(blocks); err != nil {
  2830  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  2831  	}
  2832  
  2833  	lastPrunedIndex := len(blocks) - TriesInMemory - 1
  2834  	lastPrunedBlock := blocks[lastPrunedIndex]
  2835  
  2836  	// Verify pruning of lastPrunedBlock
  2837  	if chain.HasBlockAndState(lastPrunedBlock.Hash(), lastPrunedBlock.NumberU64()) {
  2838  		t.Errorf("Block %d not pruned", lastPrunedBlock.NumberU64())
  2839  	}
  2840  	firstNonPrunedBlock := blocks[len(blocks)-TriesInMemory]
  2841  	// Verify firstNonPrunedBlock is not pruned
  2842  	if !chain.HasBlockAndState(firstNonPrunedBlock.Hash(), firstNonPrunedBlock.NumberU64()) {
  2843  		t.Errorf("Block %d pruned", firstNonPrunedBlock.NumberU64())
  2844  	}
  2845  	// Now re-import some old blocks
  2846  	blockToReimport := blocks[5:8]
  2847  	_, err = chain.InsertChain(blockToReimport)
  2848  	if err != nil {
  2849  		t.Errorf("Got error, %v", err)
  2850  	}
  2851  }
  2852  
  2853  // TestDeleteCreateRevert tests a weird state transition corner case that we hit
  2854  // while changing the internals of statedb. The workflow is that a contract is
  2855  // self destructed, then in a followup transaction (but same block) it's created
  2856  // again and the transaction reverted.
  2857  //
  2858  // The original statedb implementation flushed dirty objects to the tries after
  2859  // each transaction, so this works ok. The rework accumulated writes in memory
  2860  // first, but the journal wiped the entire state object on create-revert.
  2861  func TestDeleteCreateRevert(t *testing.T) {
  2862  	var (
  2863  		aa = common.HexToAddress("0x000000000000000000000000000000000000aaaa")
  2864  		bb = common.HexToAddress("0x000000000000000000000000000000000000bbbb")
  2865  		// Generate a canonical chain to act as the main dataset
  2866  		engine = ethash.NewFaker()
  2867  		db     = rawdb.NewMemoryDatabase()
  2868  
  2869  		// A sender who makes transactions, has some funds
  2870  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  2871  		address = crypto.PubkeyToAddress(key.PublicKey)
  2872  		funds   = big.NewInt(100000000000000000)
  2873  		gspec   = &Genesis{
  2874  			Config: params.TestChainConfig,
  2875  			Alloc: GenesisAlloc{
  2876  				address: {Balance: funds},
  2877  				// The address 0xAAAAA selfdestructs if called
  2878  				aa: {
  2879  					// Code needs to just selfdestruct
  2880  					Code:    []byte{byte(vm.PC), byte(vm.SELFDESTRUCT)},
  2881  					Nonce:   1,
  2882  					Balance: big.NewInt(0),
  2883  				},
  2884  				// The address 0xBBBB send 1 wei to 0xAAAA, then reverts
  2885  				bb: {
  2886  					Code: []byte{
  2887  						byte(vm.PC),          // [0]
  2888  						byte(vm.DUP1),        // [0,0]
  2889  						byte(vm.DUP1),        // [0,0,0]
  2890  						byte(vm.DUP1),        // [0,0,0,0]
  2891  						byte(vm.PUSH1), 0x01, // [0,0,0,0,1] (value)
  2892  						byte(vm.PUSH2), 0xaa, 0xaa, // [0,0,0,0,1, 0xaaaa]
  2893  						byte(vm.GAS),
  2894  						byte(vm.CALL),
  2895  						byte(vm.REVERT),
  2896  					},
  2897  					Balance: big.NewInt(1),
  2898  				},
  2899  			},
  2900  		}
  2901  		genesis = gspec.MustCommit(db)
  2902  	)
  2903  
  2904  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 1, func(i int, b *BlockGen) {
  2905  		b.SetCoinbase(common.Address{1})
  2906  		// One transaction to AAAA
  2907  		tx, _ := types.SignTx(types.NewTransaction(0, aa,
  2908  			big.NewInt(0), 50000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  2909  		b.AddTx(tx)
  2910  		// One transaction to BBBB
  2911  		tx, _ = types.SignTx(types.NewTransaction(1, bb,
  2912  			big.NewInt(0), 100000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  2913  		b.AddTx(tx)
  2914  	})
  2915  	// Import the canonical chain
  2916  	diskdb := rawdb.NewMemoryDatabase()
  2917  	gspec.MustCommit(diskdb)
  2918  
  2919  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  2920  	if err != nil {
  2921  		t.Fatalf("failed to create tester chain: %v", err)
  2922  	}
  2923  	if n, err := chain.InsertChain(blocks); err != nil {
  2924  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  2925  	}
  2926  }
  2927  
  2928  // TestDeleteRecreateSlots tests a state-transition that contains both deletion
  2929  // and recreation of contract state.
  2930  // Contract A exists, has slots 1 and 2 set
  2931  // Tx 1: Selfdestruct A
  2932  // Tx 2: Re-create A, set slots 3 and 4
  2933  // Expected outcome is that _all_ slots are cleared from A, due to the selfdestruct,
  2934  // and then the new slots exist
  2935  func TestDeleteRecreateSlots(t *testing.T) {
  2936  	var (
  2937  		// Generate a canonical chain to act as the main dataset
  2938  		engine = ethash.NewFaker()
  2939  		db     = rawdb.NewMemoryDatabase()
  2940  		// A sender who makes transactions, has some funds
  2941  		key, _    = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  2942  		address   = crypto.PubkeyToAddress(key.PublicKey)
  2943  		funds     = big.NewInt(1000000000000000)
  2944  		bb        = common.HexToAddress("0x000000000000000000000000000000000000bbbb")
  2945  		aaStorage = make(map[common.Hash]common.Hash)          // Initial storage in AA
  2946  		aaCode    = []byte{byte(vm.PC), byte(vm.SELFDESTRUCT)} // Code for AA (simple selfdestruct)
  2947  	)
  2948  	// Populate two slots
  2949  	aaStorage[common.HexToHash("01")] = common.HexToHash("01")
  2950  	aaStorage[common.HexToHash("02")] = common.HexToHash("02")
  2951  
  2952  	// The bb-code needs to CREATE2 the aa contract. It consists of
  2953  	// both initcode and deployment code
  2954  	// initcode:
  2955  	// 1. Set slots 3=3, 4=4,
  2956  	// 2. Return aaCode
  2957  
  2958  	initCode := []byte{
  2959  		byte(vm.PUSH1), 0x3, // value
  2960  		byte(vm.PUSH1), 0x3, // location
  2961  		byte(vm.SSTORE),     // Set slot[3] = 3
  2962  		byte(vm.PUSH1), 0x4, // value
  2963  		byte(vm.PUSH1), 0x4, // location
  2964  		byte(vm.SSTORE), // Set slot[4] = 4
  2965  		// Slots are set, now return the code
  2966  		byte(vm.PUSH2), byte(vm.PC), byte(vm.SELFDESTRUCT), // Push code on stack
  2967  		byte(vm.PUSH1), 0x0, // memory start on stack
  2968  		byte(vm.MSTORE),
  2969  		// Code is now in memory.
  2970  		byte(vm.PUSH1), 0x2, // size
  2971  		byte(vm.PUSH1), byte(32 - 2), // offset
  2972  		byte(vm.RETURN),
  2973  	}
  2974  	if l := len(initCode); l > 32 {
  2975  		t.Fatalf("init code is too long for a pushx, need a more elaborate deployer")
  2976  	}
  2977  	bbCode := []byte{
  2978  		// Push initcode onto stack
  2979  		byte(vm.PUSH1) + byte(len(initCode)-1)}
  2980  	bbCode = append(bbCode, initCode...)
  2981  	bbCode = append(bbCode, []byte{
  2982  		byte(vm.PUSH1), 0x0, // memory start on stack
  2983  		byte(vm.MSTORE),
  2984  		byte(vm.PUSH1), 0x00, // salt
  2985  		byte(vm.PUSH1), byte(len(initCode)), // size
  2986  		byte(vm.PUSH1), byte(32 - len(initCode)), // offset
  2987  		byte(vm.PUSH1), 0x00, // endowment
  2988  		byte(vm.CREATE2),
  2989  	}...)
  2990  
  2991  	initHash := crypto.Keccak256Hash(initCode)
  2992  	aa := crypto.CreateAddress2(bb, [32]byte{}, initHash[:])
  2993  	t.Logf("Destination address: %x\n", aa)
  2994  
  2995  	gspec := &Genesis{
  2996  		Config: params.TestChainConfig,
  2997  		Alloc: GenesisAlloc{
  2998  			address: {Balance: funds},
  2999  			// The address 0xAAAAA selfdestructs if called
  3000  			aa: {
  3001  				// Code needs to just selfdestruct
  3002  				Code:    aaCode,
  3003  				Nonce:   1,
  3004  				Balance: big.NewInt(0),
  3005  				Storage: aaStorage,
  3006  			},
  3007  			// The contract BB recreates AA
  3008  			bb: {
  3009  				Code:    bbCode,
  3010  				Balance: big.NewInt(1),
  3011  			},
  3012  		},
  3013  	}
  3014  	genesis := gspec.MustCommit(db)
  3015  
  3016  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 1, func(i int, b *BlockGen) {
  3017  		b.SetCoinbase(common.Address{1})
  3018  		// One transaction to AA, to kill it
  3019  		tx, _ := types.SignTx(types.NewTransaction(0, aa,
  3020  			big.NewInt(0), 50000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3021  		b.AddTx(tx)
  3022  		// One transaction to BB, to recreate AA
  3023  		tx, _ = types.SignTx(types.NewTransaction(1, bb,
  3024  			big.NewInt(0), 100000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3025  		b.AddTx(tx)
  3026  	})
  3027  	// Import the canonical chain
  3028  	diskdb := rawdb.NewMemoryDatabase()
  3029  	gspec.MustCommit(diskdb)
  3030  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{
  3031  		Debug:  true,
  3032  		Tracer: logger.NewJSONLogger(nil, os.Stdout),
  3033  	}, nil, nil)
  3034  	if err != nil {
  3035  		t.Fatalf("failed to create tester chain: %v", err)
  3036  	}
  3037  	if n, err := chain.InsertChain(blocks); err != nil {
  3038  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3039  	}
  3040  	statedb, _ := chain.State()
  3041  
  3042  	// If all is correct, then slot 1 and 2 are zero
  3043  	if got, exp := statedb.GetState(aa, common.HexToHash("01")), (common.Hash{}); got != exp {
  3044  		t.Errorf("got %x exp %x", got, exp)
  3045  	}
  3046  	if got, exp := statedb.GetState(aa, common.HexToHash("02")), (common.Hash{}); got != exp {
  3047  		t.Errorf("got %x exp %x", got, exp)
  3048  	}
  3049  	// Also, 3 and 4 should be set
  3050  	if got, exp := statedb.GetState(aa, common.HexToHash("03")), common.HexToHash("03"); got != exp {
  3051  		t.Fatalf("got %x exp %x", got, exp)
  3052  	}
  3053  	if got, exp := statedb.GetState(aa, common.HexToHash("04")), common.HexToHash("04"); got != exp {
  3054  		t.Fatalf("got %x exp %x", got, exp)
  3055  	}
  3056  }
  3057  
  3058  // TestDeleteRecreateAccount tests a state-transition that contains deletion of a
  3059  // contract with storage, and a recreate of the same contract via a
  3060  // regular value-transfer
  3061  // Expected outcome is that _all_ slots are cleared from A
  3062  func TestDeleteRecreateAccount(t *testing.T) {
  3063  	var (
  3064  		// Generate a canonical chain to act as the main dataset
  3065  		engine = ethash.NewFaker()
  3066  		db     = rawdb.NewMemoryDatabase()
  3067  		// A sender who makes transactions, has some funds
  3068  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  3069  		address = crypto.PubkeyToAddress(key.PublicKey)
  3070  		funds   = big.NewInt(1000000000000000)
  3071  
  3072  		aa        = common.HexToAddress("0x7217d81b76bdd8707601e959454e3d776aee5f43")
  3073  		aaStorage = make(map[common.Hash]common.Hash)          // Initial storage in AA
  3074  		aaCode    = []byte{byte(vm.PC), byte(vm.SELFDESTRUCT)} // Code for AA (simple selfdestruct)
  3075  	)
  3076  	// Populate two slots
  3077  	aaStorage[common.HexToHash("01")] = common.HexToHash("01")
  3078  	aaStorage[common.HexToHash("02")] = common.HexToHash("02")
  3079  
  3080  	gspec := &Genesis{
  3081  		Config: params.TestChainConfig,
  3082  		Alloc: GenesisAlloc{
  3083  			address: {Balance: funds},
  3084  			// The address 0xAAAAA selfdestructs if called
  3085  			aa: {
  3086  				// Code needs to just selfdestruct
  3087  				Code:    aaCode,
  3088  				Nonce:   1,
  3089  				Balance: big.NewInt(0),
  3090  				Storage: aaStorage,
  3091  			},
  3092  		},
  3093  	}
  3094  	genesis := gspec.MustCommit(db)
  3095  
  3096  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 1, func(i int, b *BlockGen) {
  3097  		b.SetCoinbase(common.Address{1})
  3098  		// One transaction to AA, to kill it
  3099  		tx, _ := types.SignTx(types.NewTransaction(0, aa,
  3100  			big.NewInt(0), 50000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3101  		b.AddTx(tx)
  3102  		// One transaction to AA, to recreate it (but without storage
  3103  		tx, _ = types.SignTx(types.NewTransaction(1, aa,
  3104  			big.NewInt(1), 100000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3105  		b.AddTx(tx)
  3106  	})
  3107  	// Import the canonical chain
  3108  	diskdb := rawdb.NewMemoryDatabase()
  3109  	gspec.MustCommit(diskdb)
  3110  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{
  3111  		Debug:  true,
  3112  		Tracer: logger.NewJSONLogger(nil, os.Stdout),
  3113  	}, nil, nil)
  3114  	if err != nil {
  3115  		t.Fatalf("failed to create tester chain: %v", err)
  3116  	}
  3117  	if n, err := chain.InsertChain(blocks); err != nil {
  3118  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3119  	}
  3120  	statedb, _ := chain.State()
  3121  
  3122  	// If all is correct, then both slots are zero
  3123  	if got, exp := statedb.GetState(aa, common.HexToHash("01")), (common.Hash{}); got != exp {
  3124  		t.Errorf("got %x exp %x", got, exp)
  3125  	}
  3126  	if got, exp := statedb.GetState(aa, common.HexToHash("02")), (common.Hash{}); got != exp {
  3127  		t.Errorf("got %x exp %x", got, exp)
  3128  	}
  3129  }
  3130  
  3131  // TestDeleteRecreateSlotsAcrossManyBlocks tests multiple state-transition that contains both deletion
  3132  // and recreation of contract state.
  3133  // Contract A exists, has slots 1 and 2 set
  3134  // Tx 1: Selfdestruct A
  3135  // Tx 2: Re-create A, set slots 3 and 4
  3136  // Expected outcome is that _all_ slots are cleared from A, due to the selfdestruct,
  3137  // and then the new slots exist
  3138  func TestDeleteRecreateSlotsAcrossManyBlocks(t *testing.T) {
  3139  	var (
  3140  		// Generate a canonical chain to act as the main dataset
  3141  		engine = ethash.NewFaker()
  3142  		db     = rawdb.NewMemoryDatabase()
  3143  		// A sender who makes transactions, has some funds
  3144  		key, _    = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  3145  		address   = crypto.PubkeyToAddress(key.PublicKey)
  3146  		funds     = big.NewInt(1000000000000000)
  3147  		bb        = common.HexToAddress("0x000000000000000000000000000000000000bbbb")
  3148  		aaStorage = make(map[common.Hash]common.Hash)          // Initial storage in AA
  3149  		aaCode    = []byte{byte(vm.PC), byte(vm.SELFDESTRUCT)} // Code for AA (simple selfdestruct)
  3150  	)
  3151  	// Populate two slots
  3152  	aaStorage[common.HexToHash("01")] = common.HexToHash("01")
  3153  	aaStorage[common.HexToHash("02")] = common.HexToHash("02")
  3154  
  3155  	// The bb-code needs to CREATE2 the aa contract. It consists of
  3156  	// both initcode and deployment code
  3157  	// initcode:
  3158  	// 1. Set slots 3=blocknum+1, 4=4,
  3159  	// 2. Return aaCode
  3160  
  3161  	initCode := []byte{
  3162  		byte(vm.PUSH1), 0x1, //
  3163  		byte(vm.NUMBER),     // value = number + 1
  3164  		byte(vm.ADD),        //
  3165  		byte(vm.PUSH1), 0x3, // location
  3166  		byte(vm.SSTORE),     // Set slot[3] = number + 1
  3167  		byte(vm.PUSH1), 0x4, // value
  3168  		byte(vm.PUSH1), 0x4, // location
  3169  		byte(vm.SSTORE), // Set slot[4] = 4
  3170  		// Slots are set, now return the code
  3171  		byte(vm.PUSH2), byte(vm.PC), byte(vm.SELFDESTRUCT), // Push code on stack
  3172  		byte(vm.PUSH1), 0x0, // memory start on stack
  3173  		byte(vm.MSTORE),
  3174  		// Code is now in memory.
  3175  		byte(vm.PUSH1), 0x2, // size
  3176  		byte(vm.PUSH1), byte(32 - 2), // offset
  3177  		byte(vm.RETURN),
  3178  	}
  3179  	if l := len(initCode); l > 32 {
  3180  		t.Fatalf("init code is too long for a pushx, need a more elaborate deployer")
  3181  	}
  3182  	bbCode := []byte{
  3183  		// Push initcode onto stack
  3184  		byte(vm.PUSH1) + byte(len(initCode)-1)}
  3185  	bbCode = append(bbCode, initCode...)
  3186  	bbCode = append(bbCode, []byte{
  3187  		byte(vm.PUSH1), 0x0, // memory start on stack
  3188  		byte(vm.MSTORE),
  3189  		byte(vm.PUSH1), 0x00, // salt
  3190  		byte(vm.PUSH1), byte(len(initCode)), // size
  3191  		byte(vm.PUSH1), byte(32 - len(initCode)), // offset
  3192  		byte(vm.PUSH1), 0x00, // endowment
  3193  		byte(vm.CREATE2),
  3194  	}...)
  3195  
  3196  	initHash := crypto.Keccak256Hash(initCode)
  3197  	aa := crypto.CreateAddress2(bb, [32]byte{}, initHash[:])
  3198  	t.Logf("Destination address: %x\n", aa)
  3199  	gspec := &Genesis{
  3200  		Config: params.TestChainConfig,
  3201  		Alloc: GenesisAlloc{
  3202  			address: {Balance: funds},
  3203  			// The address 0xAAAAA selfdestructs if called
  3204  			aa: {
  3205  				// Code needs to just selfdestruct
  3206  				Code:    aaCode,
  3207  				Nonce:   1,
  3208  				Balance: big.NewInt(0),
  3209  				Storage: aaStorage,
  3210  			},
  3211  			// The contract BB recreates AA
  3212  			bb: {
  3213  				Code:    bbCode,
  3214  				Balance: big.NewInt(1),
  3215  			},
  3216  		},
  3217  	}
  3218  	genesis := gspec.MustCommit(db)
  3219  	var nonce uint64
  3220  
  3221  	type expectation struct {
  3222  		exist    bool
  3223  		blocknum int
  3224  		values   map[int]int
  3225  	}
  3226  	var current = &expectation{
  3227  		exist:    true, // exists in genesis
  3228  		blocknum: 0,
  3229  		values:   map[int]int{1: 1, 2: 2},
  3230  	}
  3231  	var expectations []*expectation
  3232  	var newDestruct = func(e *expectation, b *BlockGen) *types.Transaction {
  3233  		tx, _ := types.SignTx(types.NewTransaction(nonce, aa,
  3234  			big.NewInt(0), 50000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3235  		nonce++
  3236  		if e.exist {
  3237  			e.exist = false
  3238  			e.values = nil
  3239  		}
  3240  		t.Logf("block %d; adding destruct\n", e.blocknum)
  3241  		return tx
  3242  	}
  3243  	var newResurrect = func(e *expectation, b *BlockGen) *types.Transaction {
  3244  		tx, _ := types.SignTx(types.NewTransaction(nonce, bb,
  3245  			big.NewInt(0), 100000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3246  		nonce++
  3247  		if !e.exist {
  3248  			e.exist = true
  3249  			e.values = map[int]int{3: e.blocknum + 1, 4: 4}
  3250  		}
  3251  		t.Logf("block %d; adding resurrect\n", e.blocknum)
  3252  		return tx
  3253  	}
  3254  
  3255  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 150, func(i int, b *BlockGen) {
  3256  		var exp = new(expectation)
  3257  		exp.blocknum = i + 1
  3258  		exp.values = make(map[int]int)
  3259  		for k, v := range current.values {
  3260  			exp.values[k] = v
  3261  		}
  3262  		exp.exist = current.exist
  3263  
  3264  		b.SetCoinbase(common.Address{1})
  3265  		if i%2 == 0 {
  3266  			b.AddTx(newDestruct(exp, b))
  3267  		}
  3268  		if i%3 == 0 {
  3269  			b.AddTx(newResurrect(exp, b))
  3270  		}
  3271  		if i%5 == 0 {
  3272  			b.AddTx(newDestruct(exp, b))
  3273  		}
  3274  		if i%7 == 0 {
  3275  			b.AddTx(newResurrect(exp, b))
  3276  		}
  3277  		expectations = append(expectations, exp)
  3278  		current = exp
  3279  	})
  3280  	// Import the canonical chain
  3281  	diskdb := rawdb.NewMemoryDatabase()
  3282  	gspec.MustCommit(diskdb)
  3283  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{
  3284  		//Debug:  true,
  3285  		//Tracer: vm.NewJSONLogger(nil, os.Stdout),
  3286  	}, nil, nil)
  3287  	if err != nil {
  3288  		t.Fatalf("failed to create tester chain: %v", err)
  3289  	}
  3290  	var asHash = func(num int) common.Hash {
  3291  		return common.BytesToHash([]byte{byte(num)})
  3292  	}
  3293  	for i, block := range blocks {
  3294  		blockNum := i + 1
  3295  		if n, err := chain.InsertChain([]*types.Block{block}); err != nil {
  3296  			t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3297  		}
  3298  		statedb, _ := chain.State()
  3299  		// If all is correct, then slot 1 and 2 are zero
  3300  		if got, exp := statedb.GetState(aa, common.HexToHash("01")), (common.Hash{}); got != exp {
  3301  			t.Errorf("block %d, got %x exp %x", blockNum, got, exp)
  3302  		}
  3303  		if got, exp := statedb.GetState(aa, common.HexToHash("02")), (common.Hash{}); got != exp {
  3304  			t.Errorf("block %d, got %x exp %x", blockNum, got, exp)
  3305  		}
  3306  		exp := expectations[i]
  3307  		if exp.exist {
  3308  			if !statedb.Exist(aa) {
  3309  				t.Fatalf("block %d, expected %v to exist, it did not", blockNum, aa)
  3310  			}
  3311  			for slot, val := range exp.values {
  3312  				if gotValue, expValue := statedb.GetState(aa, asHash(slot)), asHash(val); gotValue != expValue {
  3313  					t.Fatalf("block %d, slot %d, got %x exp %x", blockNum, slot, gotValue, expValue)
  3314  				}
  3315  			}
  3316  		} else {
  3317  			if statedb.Exist(aa) {
  3318  				t.Fatalf("block %d, expected %v to not exist, it did", blockNum, aa)
  3319  			}
  3320  		}
  3321  	}
  3322  }
  3323  
  3324  // TestInitThenFailCreateContract tests a pretty notorious case that happened
  3325  // on mainnet over blocks 7338108, 7338110 and 7338115.
  3326  // - Block 7338108: address e771789f5cccac282f23bb7add5690e1f6ca467c is initiated
  3327  //   with 0.001 ether (thus created but no code)
  3328  // - Block 7338110: a CREATE2 is attempted. The CREATE2 would deploy code on
  3329  //   the same address e771789f5cccac282f23bb7add5690e1f6ca467c. However, the
  3330  //   deployment fails due to OOG during initcode execution
  3331  // - Block 7338115: another tx checks the balance of
  3332  //   e771789f5cccac282f23bb7add5690e1f6ca467c, and the snapshotter returned it as
  3333  //   zero.
  3334  //
  3335  // The problem being that the snapshotter maintains a destructset, and adds items
  3336  // to the destructset in case something is created "onto" an existing item.
  3337  // We need to either roll back the snapDestructs, or not place it into snapDestructs
  3338  // in the first place.
  3339  //
  3340  func TestInitThenFailCreateContract(t *testing.T) {
  3341  	var (
  3342  		// Generate a canonical chain to act as the main dataset
  3343  		engine = ethash.NewFaker()
  3344  		db     = rawdb.NewMemoryDatabase()
  3345  		// A sender who makes transactions, has some funds
  3346  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  3347  		address = crypto.PubkeyToAddress(key.PublicKey)
  3348  		funds   = big.NewInt(1000000000000000)
  3349  		bb      = common.HexToAddress("0x000000000000000000000000000000000000bbbb")
  3350  	)
  3351  
  3352  	// The bb-code needs to CREATE2 the aa contract. It consists of
  3353  	// both initcode and deployment code
  3354  	// initcode:
  3355  	// 1. If blocknum < 1, error out (e.g invalid opcode)
  3356  	// 2. else, return a snippet of code
  3357  	initCode := []byte{
  3358  		byte(vm.PUSH1), 0x1, // y (2)
  3359  		byte(vm.NUMBER), // x (number)
  3360  		byte(vm.GT),     // x > y?
  3361  		byte(vm.PUSH1), byte(0x8),
  3362  		byte(vm.JUMPI), // jump to label if number > 2
  3363  		byte(0xFE),     // illegal opcode
  3364  		byte(vm.JUMPDEST),
  3365  		byte(vm.PUSH1), 0x2, // size
  3366  		byte(vm.PUSH1), 0x0, // offset
  3367  		byte(vm.RETURN), // return 2 bytes of zero-code
  3368  	}
  3369  	if l := len(initCode); l > 32 {
  3370  		t.Fatalf("init code is too long for a pushx, need a more elaborate deployer")
  3371  	}
  3372  	bbCode := []byte{
  3373  		// Push initcode onto stack
  3374  		byte(vm.PUSH1) + byte(len(initCode)-1)}
  3375  	bbCode = append(bbCode, initCode...)
  3376  	bbCode = append(bbCode, []byte{
  3377  		byte(vm.PUSH1), 0x0, // memory start on stack
  3378  		byte(vm.MSTORE),
  3379  		byte(vm.PUSH1), 0x00, // salt
  3380  		byte(vm.PUSH1), byte(len(initCode)), // size
  3381  		byte(vm.PUSH1), byte(32 - len(initCode)), // offset
  3382  		byte(vm.PUSH1), 0x00, // endowment
  3383  		byte(vm.CREATE2),
  3384  	}...)
  3385  
  3386  	initHash := crypto.Keccak256Hash(initCode)
  3387  	aa := crypto.CreateAddress2(bb, [32]byte{}, initHash[:])
  3388  	t.Logf("Destination address: %x\n", aa)
  3389  
  3390  	gspec := &Genesis{
  3391  		Config: params.TestChainConfig,
  3392  		Alloc: GenesisAlloc{
  3393  			address: {Balance: funds},
  3394  			// The address aa has some funds
  3395  			aa: {Balance: big.NewInt(100000)},
  3396  			// The contract BB tries to create code onto AA
  3397  			bb: {
  3398  				Code:    bbCode,
  3399  				Balance: big.NewInt(1),
  3400  			},
  3401  		},
  3402  	}
  3403  	genesis := gspec.MustCommit(db)
  3404  	nonce := uint64(0)
  3405  	blocks, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 4, func(i int, b *BlockGen) {
  3406  		b.SetCoinbase(common.Address{1})
  3407  		// One transaction to BB
  3408  		tx, _ := types.SignTx(types.NewTransaction(nonce, bb,
  3409  			big.NewInt(0), 100000, b.header.BaseFee, nil), types.HomesteadSigner{}, key)
  3410  		b.AddTx(tx)
  3411  		nonce++
  3412  	})
  3413  
  3414  	// Import the canonical chain
  3415  	diskdb := rawdb.NewMemoryDatabase()
  3416  	gspec.MustCommit(diskdb)
  3417  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{
  3418  		//Debug:  true,
  3419  		//Tracer: vm.NewJSONLogger(nil, os.Stdout),
  3420  	}, nil, nil)
  3421  	if err != nil {
  3422  		t.Fatalf("failed to create tester chain: %v", err)
  3423  	}
  3424  	statedb, _ := chain.State()
  3425  	if got, exp := statedb.GetBalance(aa), big.NewInt(100000); got.Cmp(exp) != 0 {
  3426  		t.Fatalf("Genesis err, got %v exp %v", got, exp)
  3427  	}
  3428  	// First block tries to create, but fails
  3429  	{
  3430  		block := blocks[0]
  3431  		if _, err := chain.InsertChain([]*types.Block{blocks[0]}); err != nil {
  3432  			t.Fatalf("block %d: failed to insert into chain: %v", block.NumberU64(), err)
  3433  		}
  3434  		statedb, _ = chain.State()
  3435  		if got, exp := statedb.GetBalance(aa), big.NewInt(100000); got.Cmp(exp) != 0 {
  3436  			t.Fatalf("block %d: got %v exp %v", block.NumberU64(), got, exp)
  3437  		}
  3438  	}
  3439  	// Import the rest of the blocks
  3440  	for _, block := range blocks[1:] {
  3441  		if _, err := chain.InsertChain([]*types.Block{block}); err != nil {
  3442  			t.Fatalf("block %d: failed to insert into chain: %v", block.NumberU64(), err)
  3443  		}
  3444  	}
  3445  }
  3446  
  3447  // TestEIP2718Transition tests that an EIP-2718 transaction will be accepted
  3448  // after the fork block has passed. This is verified by sending an EIP-2930
  3449  // access list transaction, which specifies a single slot access, and then
  3450  // checking that the gas usage of a hot SLOAD and a cold SLOAD are calculated
  3451  // correctly.
  3452  func TestEIP2718Transition(t *testing.T) {
  3453  	var (
  3454  		aa = common.HexToAddress("0x000000000000000000000000000000000000aaaa")
  3455  
  3456  		// Generate a canonical chain to act as the main dataset
  3457  		engine = ethash.NewFaker()
  3458  		db     = rawdb.NewMemoryDatabase()
  3459  
  3460  		// A sender who makes transactions, has some funds
  3461  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  3462  		address = crypto.PubkeyToAddress(key.PublicKey)
  3463  		funds   = big.NewInt(1000000000000000)
  3464  		gspec   = &Genesis{
  3465  			Config: params.TestChainConfig,
  3466  			Alloc: GenesisAlloc{
  3467  				address: {Balance: funds},
  3468  				// The address 0xAAAA sloads 0x00 and 0x01
  3469  				aa: {
  3470  					Code: []byte{
  3471  						byte(vm.PC),
  3472  						byte(vm.PC),
  3473  						byte(vm.SLOAD),
  3474  						byte(vm.SLOAD),
  3475  					},
  3476  					Nonce:   0,
  3477  					Balance: big.NewInt(0),
  3478  				},
  3479  			},
  3480  		}
  3481  		genesis = gspec.MustCommit(db)
  3482  	)
  3483  
  3484  	blocks, _ := GenerateChain(gspec.Config, genesis, engine, db, 1, func(i int, b *BlockGen) {
  3485  		b.SetCoinbase(common.Address{1})
  3486  
  3487  		// One transaction to 0xAAAA
  3488  		signer := types.LatestSigner(gspec.Config)
  3489  		tx, _ := types.SignNewTx(key, signer, &types.AccessListTx{
  3490  			ChainID:  gspec.Config.ChainID,
  3491  			Nonce:    0,
  3492  			To:       &aa,
  3493  			Gas:      30000,
  3494  			GasPrice: b.header.BaseFee,
  3495  			AccessList: types.AccessList{{
  3496  				Address:     aa,
  3497  				StorageKeys: []common.Hash{{0}},
  3498  			}},
  3499  		})
  3500  		b.AddTx(tx)
  3501  	})
  3502  
  3503  	// Import the canonical chain
  3504  	diskdb := rawdb.NewMemoryDatabase()
  3505  	gspec.MustCommit(diskdb)
  3506  
  3507  	chain, err := NewBlockChain(diskdb, nil, gspec.Config, engine, vm.Config{}, nil, nil)
  3508  	if err != nil {
  3509  		t.Fatalf("failed to create tester chain: %v", err)
  3510  	}
  3511  	if n, err := chain.InsertChain(blocks); err != nil {
  3512  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3513  	}
  3514  
  3515  	block := chain.GetBlockByNumber(1)
  3516  
  3517  	// Expected gas is intrinsic + 2 * pc + hot load + cold load, since only one load is in the access list
  3518  	expected := params.TxGas + params.TxAccessListAddressGas + params.TxAccessListStorageKeyGas +
  3519  		vm.GasQuickStep*2 + params.WarmStorageReadCostEIP2929 + params.ColdSloadCostEIP2929
  3520  	if block.GasUsed() != expected {
  3521  		t.Fatalf("incorrect amount of gas spent: expected %d, got %d", expected, block.GasUsed())
  3522  	}
  3523  }
  3524  
  3525  // TestEIP1559Transition tests the following:
  3526  //
  3527  // 1. A transaction whose gasFeeCap is greater than the baseFee is valid.
  3528  // 2. Gas accounting for access lists on EIP-1559 transactions is correct.
  3529  // 3. Only the transaction's tip will be received by the coinbase.
  3530  // 4. The transaction sender pays for both the tip and baseFee.
  3531  // 5. The coinbase receives only the partially realized tip when
  3532  //    gasFeeCap - gasTipCap < baseFee.
  3533  // 6. Legacy transaction behave as expected (e.g. gasPrice = gasFeeCap = gasTipCap).
  3534  func TestEIP1559Transition(t *testing.T) {
  3535  	var (
  3536  		aa = common.HexToAddress("0x000000000000000000000000000000000000aaaa")
  3537  
  3538  		// Generate a canonical chain to act as the main dataset
  3539  		engine = ethash.NewFaker()
  3540  		db     = rawdb.NewMemoryDatabase()
  3541  
  3542  		// A sender who makes transactions, has some funds
  3543  		key1, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  3544  		key2, _ = crypto.HexToECDSA("8a1f9a8f95be41cd7ccb6168179afb4504aefe388d1e14474d32c45c72ce7b7a")
  3545  		addr1   = crypto.PubkeyToAddress(key1.PublicKey)
  3546  		addr2   = crypto.PubkeyToAddress(key2.PublicKey)
  3547  		funds   = new(big.Int).Mul(common.Big1, big.NewInt(params.Ether))
  3548  		gspec   = &Genesis{
  3549  			Config: params.AllEthashProtocolChanges,
  3550  			Alloc: GenesisAlloc{
  3551  				addr1: {Balance: funds},
  3552  				addr2: {Balance: funds},
  3553  				// The address 0xAAAA sloads 0x00 and 0x01
  3554  				aa: {
  3555  					Code: []byte{
  3556  						byte(vm.PC),
  3557  						byte(vm.PC),
  3558  						byte(vm.SLOAD),
  3559  						byte(vm.SLOAD),
  3560  					},
  3561  					Nonce:   0,
  3562  					Balance: big.NewInt(0),
  3563  				},
  3564  			},
  3565  		}
  3566  	)
  3567  
  3568  	gspec.Config.BerlinBlock = common.Big0
  3569  	gspec.Config.LondonBlock = common.Big0
  3570  	genesis := gspec.MustCommit(db)
  3571  	signer := types.LatestSigner(gspec.Config)
  3572  
  3573  	blocks, _ := GenerateChain(gspec.Config, genesis, engine, db, 1, func(i int, b *BlockGen) {
  3574  		b.SetCoinbase(common.Address{1})
  3575  
  3576  		// One transaction to 0xAAAA
  3577  		accesses := types.AccessList{types.AccessTuple{
  3578  			Address:     aa,
  3579  			StorageKeys: []common.Hash{{0}},
  3580  		}}
  3581  
  3582  		txdata := &types.DynamicFeeTx{
  3583  			ChainID:    gspec.Config.ChainID,
  3584  			Nonce:      0,
  3585  			To:         &aa,
  3586  			Gas:        30000,
  3587  			GasFeeCap:  newGwei(5),
  3588  			GasTipCap:  big.NewInt(2),
  3589  			AccessList: accesses,
  3590  			Data:       []byte{},
  3591  		}
  3592  		tx := types.NewTx(txdata)
  3593  		tx, _ = types.SignTx(tx, signer, key1)
  3594  
  3595  		b.AddTx(tx)
  3596  	})
  3597  
  3598  	diskdb := rawdb.NewMemoryDatabase()
  3599  	gspec.MustCommit(diskdb)
  3600  
  3601  	chain, err := NewBlockChain(diskdb, nil, gspec.Config, engine, vm.Config{}, nil, nil)
  3602  	if err != nil {
  3603  		t.Fatalf("failed to create tester chain: %v", err)
  3604  	}
  3605  	if n, err := chain.InsertChain(blocks); err != nil {
  3606  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3607  	}
  3608  
  3609  	block := chain.GetBlockByNumber(1)
  3610  
  3611  	// 1+2: Ensure EIP-1559 access lists are accounted for via gas usage.
  3612  	expectedGas := params.TxGas + params.TxAccessListAddressGas + params.TxAccessListStorageKeyGas +
  3613  		vm.GasQuickStep*2 + params.WarmStorageReadCostEIP2929 + params.ColdSloadCostEIP2929
  3614  	if block.GasUsed() != expectedGas {
  3615  		t.Fatalf("incorrect amount of gas spent: expected %d, got %d", expectedGas, block.GasUsed())
  3616  	}
  3617  
  3618  	state, _ := chain.State()
  3619  
  3620  	// 3: Ensure that miner received only the tx's tip.
  3621  	actual := state.GetBalance(block.Coinbase())
  3622  	expected := new(big.Int).Add(
  3623  		new(big.Int).SetUint64(block.GasUsed()*block.Transactions()[0].GasTipCap().Uint64()),
  3624  		ethash.ConstantinopleBlockReward,
  3625  	)
  3626  	if actual.Cmp(expected) != 0 {
  3627  		t.Fatalf("miner balance incorrect: expected %d, got %d", expected, actual)
  3628  	}
  3629  
  3630  	// 4: Ensure the tx sender paid for the gasUsed * (tip + block baseFee).
  3631  	actual = new(big.Int).Sub(funds, state.GetBalance(addr1))
  3632  	expected = new(big.Int).SetUint64(block.GasUsed() * (block.Transactions()[0].GasTipCap().Uint64() + block.BaseFee().Uint64()))
  3633  	if actual.Cmp(expected) != 0 {
  3634  		t.Fatalf("sender balance incorrect: expected %d, got %d", expected, actual)
  3635  	}
  3636  
  3637  	blocks, _ = GenerateChain(gspec.Config, block, engine, db, 1, func(i int, b *BlockGen) {
  3638  		b.SetCoinbase(common.Address{2})
  3639  
  3640  		txdata := &types.LegacyTx{
  3641  			Nonce:    0,
  3642  			To:       &aa,
  3643  			Gas:      30000,
  3644  			GasPrice: newGwei(5),
  3645  		}
  3646  		tx := types.NewTx(txdata)
  3647  		tx, _ = types.SignTx(tx, signer, key2)
  3648  
  3649  		b.AddTx(tx)
  3650  	})
  3651  
  3652  	if n, err := chain.InsertChain(blocks); err != nil {
  3653  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3654  	}
  3655  
  3656  	block = chain.GetBlockByNumber(2)
  3657  	state, _ = chain.State()
  3658  	effectiveTip := block.Transactions()[0].GasTipCap().Uint64() - block.BaseFee().Uint64()
  3659  
  3660  	// 6+5: Ensure that miner received only the tx's effective tip.
  3661  	actual = state.GetBalance(block.Coinbase())
  3662  	expected = new(big.Int).Add(
  3663  		new(big.Int).SetUint64(block.GasUsed()*effectiveTip),
  3664  		ethash.ConstantinopleBlockReward,
  3665  	)
  3666  	if actual.Cmp(expected) != 0 {
  3667  		t.Fatalf("miner balance incorrect: expected %d, got %d", expected, actual)
  3668  	}
  3669  
  3670  	// 4: Ensure the tx sender paid for the gasUsed * (effectiveTip + block baseFee).
  3671  	actual = new(big.Int).Sub(funds, state.GetBalance(addr2))
  3672  	expected = new(big.Int).SetUint64(block.GasUsed() * (effectiveTip + block.BaseFee().Uint64()))
  3673  	if actual.Cmp(expected) != 0 {
  3674  		t.Fatalf("sender balance incorrect: expected %d, got %d", expected, actual)
  3675  	}
  3676  }
  3677  
  3678  // Tests the scenario the chain is requested to another point with the missing state.
  3679  // It expects the state is recovered and all relevant chain markers are set correctly.
  3680  func TestSetCanonical(t *testing.T) {
  3681  	//log.Root().SetHandler(log.LvlFilterHandler(log.LvlDebug, log.StreamHandler(os.Stderr, log.TerminalFormat(true))))
  3682  
  3683  	var (
  3684  		db      = rawdb.NewMemoryDatabase()
  3685  		key, _  = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
  3686  		address = crypto.PubkeyToAddress(key.PublicKey)
  3687  		funds   = big.NewInt(100000000000000000)
  3688  		gspec   = &Genesis{
  3689  			Config:  params.TestChainConfig,
  3690  			Alloc:   GenesisAlloc{address: {Balance: funds}},
  3691  			BaseFee: big.NewInt(params.InitialBaseFee),
  3692  		}
  3693  		genesis = gspec.MustCommit(db)
  3694  		signer  = types.LatestSigner(gspec.Config)
  3695  		engine  = ethash.NewFaker()
  3696  	)
  3697  	// Generate and import the canonical chain
  3698  	canon, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 2*TriesInMemory, func(i int, gen *BlockGen) {
  3699  		tx, err := types.SignTx(types.NewTransaction(gen.TxNonce(address), common.Address{0x00}, big.NewInt(1000), params.TxGas, gen.header.BaseFee, nil), signer, key)
  3700  		if err != nil {
  3701  			panic(err)
  3702  		}
  3703  		gen.AddTx(tx)
  3704  	})
  3705  	diskdb := rawdb.NewMemoryDatabase()
  3706  	gspec.MustCommit(diskdb)
  3707  
  3708  	chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  3709  	if err != nil {
  3710  		t.Fatalf("failed to create tester chain: %v", err)
  3711  	}
  3712  	if n, err := chain.InsertChain(canon); err != nil {
  3713  		t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3714  	}
  3715  
  3716  	// Generate the side chain and import them
  3717  	side, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, 2*TriesInMemory, func(i int, gen *BlockGen) {
  3718  		tx, err := types.SignTx(types.NewTransaction(gen.TxNonce(address), common.Address{0x00}, big.NewInt(1), params.TxGas, gen.header.BaseFee, nil), signer, key)
  3719  		if err != nil {
  3720  			panic(err)
  3721  		}
  3722  		gen.AddTx(tx)
  3723  	})
  3724  	for _, block := range side {
  3725  		err := chain.InsertBlockWithoutSetHead(block)
  3726  		if err != nil {
  3727  			t.Fatalf("Failed to insert into chain: %v", err)
  3728  		}
  3729  	}
  3730  	for _, block := range side {
  3731  		got := chain.GetBlockByHash(block.Hash())
  3732  		if got == nil {
  3733  			t.Fatalf("Lost the inserted block")
  3734  		}
  3735  	}
  3736  
  3737  	// Set the chain head to the side chain, ensure all the relevant markers are updated.
  3738  	verify := func(head *types.Block) {
  3739  		if chain.CurrentBlock().Hash() != head.Hash() {
  3740  			t.Fatalf("Unexpected block hash, want %x, got %x", head.Hash(), chain.CurrentBlock().Hash())
  3741  		}
  3742  		if chain.CurrentFastBlock().Hash() != head.Hash() {
  3743  			t.Fatalf("Unexpected fast block hash, want %x, got %x", head.Hash(), chain.CurrentFastBlock().Hash())
  3744  		}
  3745  		if chain.CurrentHeader().Hash() != head.Hash() {
  3746  			t.Fatalf("Unexpected head header, want %x, got %x", head.Hash(), chain.CurrentHeader().Hash())
  3747  		}
  3748  		if !chain.HasState(head.Root()) {
  3749  			t.Fatalf("Lost block state %v %x", head.Number(), head.Hash())
  3750  		}
  3751  	}
  3752  	chain.SetCanonical(side[len(side)-1])
  3753  	verify(side[len(side)-1])
  3754  
  3755  	// Reset the chain head to original chain
  3756  	chain.SetCanonical(canon[TriesInMemory-1])
  3757  	verify(canon[TriesInMemory-1])
  3758  }
  3759  
  3760  // TestCanonicalHashMarker tests all the canonical hash markers are updated/deleted
  3761  // correctly in case reorg is called.
  3762  func TestCanonicalHashMarker(t *testing.T) {
  3763  	var cases = []struct {
  3764  		forkA int
  3765  		forkB int
  3766  	}{
  3767  		// ForkA: 10 blocks
  3768  		// ForkB: 1 blocks
  3769  		//
  3770  		// reorged:
  3771  		//      markers [2, 10] should be deleted
  3772  		//      markers [1] should be updated
  3773  		{10, 1},
  3774  
  3775  		// ForkA: 10 blocks
  3776  		// ForkB: 2 blocks
  3777  		//
  3778  		// reorged:
  3779  		//      markers [3, 10] should be deleted
  3780  		//      markers [1, 2] should be updated
  3781  		{10, 2},
  3782  
  3783  		// ForkA: 10 blocks
  3784  		// ForkB: 10 blocks
  3785  		//
  3786  		// reorged:
  3787  		//      markers [1, 10] should be updated
  3788  		{10, 10},
  3789  
  3790  		// ForkA: 10 blocks
  3791  		// ForkB: 11 blocks
  3792  		//
  3793  		// reorged:
  3794  		//      markers [1, 11] should be updated
  3795  		{10, 11},
  3796  	}
  3797  	for _, c := range cases {
  3798  		var (
  3799  			db    = rawdb.NewMemoryDatabase()
  3800  			gspec = &Genesis{
  3801  				Config:  params.TestChainConfig,
  3802  				Alloc:   GenesisAlloc{},
  3803  				BaseFee: big.NewInt(params.InitialBaseFee),
  3804  			}
  3805  			genesis = gspec.MustCommit(db)
  3806  			engine  = ethash.NewFaker()
  3807  		)
  3808  		forkA, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, c.forkA, func(i int, gen *BlockGen) {})
  3809  		forkB, _ := GenerateChain(params.TestChainConfig, genesis, engine, db, c.forkB, func(i int, gen *BlockGen) {})
  3810  
  3811  		// Initialize test chain
  3812  		diskdb := rawdb.NewMemoryDatabase()
  3813  		gspec.MustCommit(diskdb)
  3814  		chain, err := NewBlockChain(diskdb, nil, params.TestChainConfig, engine, vm.Config{}, nil, nil)
  3815  		if err != nil {
  3816  			t.Fatalf("failed to create tester chain: %v", err)
  3817  		}
  3818  		// Insert forkA and forkB, the canonical should on forkA still
  3819  		if n, err := chain.InsertChain(forkA); err != nil {
  3820  			t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3821  		}
  3822  		if n, err := chain.InsertChain(forkB); err != nil {
  3823  			t.Fatalf("block %d: failed to insert into chain: %v", n, err)
  3824  		}
  3825  
  3826  		verify := func(head *types.Block) {
  3827  			if chain.CurrentBlock().Hash() != head.Hash() {
  3828  				t.Fatalf("Unexpected block hash, want %x, got %x", head.Hash(), chain.CurrentBlock().Hash())
  3829  			}
  3830  			if chain.CurrentFastBlock().Hash() != head.Hash() {
  3831  				t.Fatalf("Unexpected fast block hash, want %x, got %x", head.Hash(), chain.CurrentFastBlock().Hash())
  3832  			}
  3833  			if chain.CurrentHeader().Hash() != head.Hash() {
  3834  				t.Fatalf("Unexpected head header, want %x, got %x", head.Hash(), chain.CurrentHeader().Hash())
  3835  			}
  3836  			if !chain.HasState(head.Root()) {
  3837  				t.Fatalf("Lost block state %v %x", head.Number(), head.Hash())
  3838  			}
  3839  		}
  3840  
  3841  		// Switch canonical chain to forkB if necessary
  3842  		if len(forkA) < len(forkB) {
  3843  			verify(forkB[len(forkB)-1])
  3844  		} else {
  3845  			verify(forkA[len(forkA)-1])
  3846  			chain.SetCanonical(forkB[len(forkB)-1])
  3847  			verify(forkB[len(forkB)-1])
  3848  		}
  3849  
  3850  		// Ensure all hash markers are updated correctly
  3851  		for i := 0; i < len(forkB); i++ {
  3852  			block := forkB[i]
  3853  			hash := chain.GetCanonicalHash(block.NumberU64())
  3854  			if hash != block.Hash() {
  3855  				t.Fatalf("Unexpected canonical hash %d", block.NumberU64())
  3856  			}
  3857  		}
  3858  		if c.forkA > c.forkB {
  3859  			for i := uint64(c.forkB) + 1; i <= uint64(c.forkA); i++ {
  3860  				hash := chain.GetCanonicalHash(i)
  3861  				if hash != (common.Hash{}) {
  3862  					t.Fatalf("Unexpected canonical hash %d", i)
  3863  				}
  3864  			}
  3865  		}
  3866  	}
  3867  }