blockchain

package
v0.0.0-...-e4b14ae Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Dec 12, 2018 License: LGPL-3.0 Imports: 22 Imported by: 0

Documentation

Index

Examples

Constants

This section is empty.

Variables

View Source
var (
	// ErrKnownBlock is returned when a block to import is already known locally.
	ErrKnownBlock = errors.New("block already known")

	// ErrBlacklistedHash is returned if a block to import is on the blacklist.
	ErrBlacklistedHash = errors.New("blacklisted hash")

	// ErrNonceTooHigh is returned if the nonce of a transaction is higher than the
	// next one expected based on the local chain.
	ErrNonceTooHigh = errors.New("nonce too high")
)
View Source
var ErrNoGenesis = errors.New("Genesis not found in chain")

Functions

func GenerateChain

func GenerateChain(config *params.ChainConfig, parent *types.Block, engine consensus.Engine, db database.Database, n int, gen func(int, *BlockGen)) []*types.Block

GenerateChain creates a chain of n blocks. The first block's parent will be the provided parent. db is used to store intermediate states and should contain the parent's state trie.

The generator function is called with a new block generator for every block. Any transactions and uncles added to the generator become part of the block. If gen is nil, the blocks will be empty and their coinbase will be the zero address.

Blocks created by GenerateChain do not contain valid proof of work values. Inserting them into BlockChain requires use of FakePow or a similar non-validating proof of work implementation.

Example
var (
	key1, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291")
	key2, _ = crypto.HexToECDSA("8a1f9a8f95be41cd7ccb6168179afb4504aefe388d1e14474d32c45c72ce7b7a")
	key3, _ = crypto.HexToECDSA("49a7b37aa6f6645917e7b807e9d1c00d4fa71f18343b0d4122a4d2df64dd6fee")
	addr1   = crypto.PubkeyToAddress(key1.PublicKey)
	addr2   = crypto.PubkeyToAddress(key2.PublicKey)
	addr3   = crypto.PubkeyToAddress(key3.PublicKey)
	db      = ethdb.NewMemDatabase()
)

// Ensure that key1 has some funds in the genesis block.
gspec := &Genesis{
	Config: &params.ChainConfig{HomesteadBlock: new(big.Int)},
	Alloc:  GenesisAlloc{addr1: {Balance: big.NewInt(1000000)}},
}
genesis := gspec.MustCommit(db)

// This call generates a chain of 5 blocks. The function runs for
// each block and adds different features to gen based on the
// block index.
signer := types.HomesteadSigner{}
chain, _ := GenerateChain(gspec.Config, genesis, ethash.NewFaker(), db, 5, func(i int, gen *BlockGen) {
	switch i {
	case 0:
		// In block 1, addr1 sends addr2 some ether.
		tx, _ := types.SignTx(types.NewTransaction(gen.TxNonce(addr1), addr2, big.NewInt(10000), params.TxGas, nil, nil), signer, key1)
		gen.AddTx(tx)
	case 1:
		// In block 2, addr1 sends some more ether to addr2.
		// addr2 passes it on to addr3.
		tx1, _ := types.SignTx(types.NewTransaction(gen.TxNonce(addr1), addr2, big.NewInt(1000), params.TxGas, nil, nil), signer, key1)
		tx2, _ := types.SignTx(types.NewTransaction(gen.TxNonce(addr2), addr3, big.NewInt(1000), params.TxGas, nil, nil), signer, key2)
		gen.AddTx(tx1)
		gen.AddTx(tx2)
	case 2:
		// Block 3 is empty but was mined by addr3.
		gen.SetCoinbase(addr3)
		gen.SetExtra([]byte("yeehaw"))
	case 3:
		// Block 4 includes blocks 2 and 3 as uncle headers (with modified extra data).
		b2 := gen.PrevBlock(1).Header()
		b2.Extra = []byte("foo")
		gen.AddUncle(b2)
		b3 := gen.PrevBlock(2).Header()
		b3.Extra = []byte("foo")
		gen.AddUncle(b3)
	}
})

// Import the chain. This runs all block validation rules.
blockchain, _ := NewBlockChain(db, nil, gspec.Config, ethash.NewFaker(), vm.Config{})
defer blockchain.Stop()

if i, err := blockchain.InsertChain(chain); err != nil {
	fmt.Printf("insert error (block %d): %v\n", chain[i].NumberU64(), err)
	return
}

state, _ := blockchain.State()
fmt.Printf("last block: #%d\n", blockchain.CurrentBlock().Number())
fmt.Println("balance of addr1:", state.GetBalance(addr1))
fmt.Println("balance of addr2:", state.GetBalance(addr2))
fmt.Println("balance of addr3:", state.GetBalance(addr3))
Output:
last block: #5
balance of addr1: 989000
balance of addr2: 10000
balance of addr3: 19687500000000001000

func GenesisBlockForTesting

func GenesisBlockForTesting(db database.Database) *types.Block

func SetupGenesisBlock

func SetupGenesisBlock(db database.Database, genesis *Genesis) (*params.ChainConfig, common.Hash, error)

Types

type BlockChain

type BlockChain struct {
	// contains filtered or unexported fields
}

func NewBlockChain

func NewBlockChain(db database.Database, engine consensus.Engine, config *params.ChainConfig) (*BlockChain, error)

NewBlockChain returns a fully initialised block chain using information available in the database.

func (*BlockChain) BadBlocks

func (bc *BlockChain) BadBlocks() []*types.Block

BadBlocks returns a list of the last 'bad blocks' that the client has seen on the network

func (*BlockChain) Config

func (bc *BlockChain) Config() *params.ChainConfig

Config retrieves the blockchain's chain configuration.

func (*BlockChain) CurrentBlock

func (bc *BlockChain) CurrentBlock() *types.Block

CurrentBlock retrieves the current head block of the canonical chain. The block is retrieved from the blockchain's internal cache.

func (*BlockChain) CurrentFastBlock

func (bc *BlockChain) CurrentFastBlock() *types.Block

CurrentFastBlock retrieves the current fast-sync head block of the canonical chain. The block is retrieved from the blockchain's internal cache.

func (*BlockChain) CurrentHeader

func (bc *BlockChain) CurrentHeader() *types.Header

CurrentHeader retrieves the current head header of the canonical chain. The header is retrieved from the HeaderChain's internal cache.

func (*BlockChain) FastSyncCommitHead

func (bc *BlockChain) FastSyncCommitHead(hash common.Hash) error

FastSyncCommitHead sets the current head block to the one defined by the hash irrelevant what the chain contents were prior.

func (*BlockChain) Genesis

func (bc *BlockChain) Genesis() *types.Block

Genesis retrieves the chain's genesis block.

func (*BlockChain) GetAncestor

func (bc *BlockChain) GetAncestor(hash common.Hash, number, ancestor uint64, maxNonCanonical *uint64) (common.Hash, uint64)

GetAncestor retrieves the Nth ancestor of a given block. It assumes that either the given block or a close ancestor of it is canonical. maxNonCanonical points to a downwards counter limiting the number of blocks to be individually checked before we reach the canonical chain.

Note: ancestor == 0 returns the same block, 1 returns its parent and so on.

func (*BlockChain) GetBlock

func (bc *BlockChain) GetBlock(hash common.Hash, number uint64) *types.Block

GetBlock retrieves a block from the database by hash and number, caching it if found.

func (*BlockChain) GetBlockByHash

func (bc *BlockChain) GetBlockByHash(hash common.Hash) *types.Block

GetBlockByHash retrieves a block from the database by hash, caching it if found.

func (*BlockChain) GetBlockByNumber

func (bc *BlockChain) GetBlockByNumber(number uint64) *types.Block

GetBlockByNumber retrieves a block from the database by number.

func (*BlockChain) GetBodyRLP

func (bc *BlockChain) GetBodyRLP(hash common.Hash) rlp.RawValue

GetBodyRLP retrieves a block body in RLP encoding from the database by hash, caching it if found.

func (*BlockChain) GetHeader

func (bc *BlockChain) GetHeader(hash common.Hash, number uint64) *types.Header

GetHeader retrieves a block header from the database by hash and number, caching it if found.

func (*BlockChain) GetHeaderByHash

func (bc *BlockChain) GetHeaderByHash(hash common.Hash) *types.Header

GetHeaderByHash retrieves a block header from the database by hash, caching it if found.

func (*BlockChain) GetHeaderByNumber

func (bc *BlockChain) GetHeaderByNumber(number uint64) *types.Header

GetHeaderByNumber retrieves a block header from the database by number, caching it (associated with its hash) if found.

func (*BlockChain) GetTd

func (bc *BlockChain) GetTd(hash common.Hash, number uint64) *big.Int

GetTd retrieves a block's total difficulty in the canonical chain from the database by hash and number, caching it if found.

func (*BlockChain) GetTdByHash

func (bc *BlockChain) GetTdByHash(hash common.Hash) *big.Int

GetTdByHash retrieves a block's total difficulty in the canonical chain from the database by hash, caching it if found.

func (*BlockChain) HasBlock

func (bc *BlockChain) HasBlock(hash common.Hash, number uint64) bool

HasBlock checks if a block is fully present in the database or not.

func (*BlockChain) HasHeader

func (bc *BlockChain) HasHeader(hash common.Hash, number uint64) bool

HasHeader checks if a block header is present in the database or not, caching it if present.

func (*BlockChain) InsertChain

func (bc *BlockChain) InsertChain(chain types.Blocks) (int, error)

InsertChain attempts to insert the given batch of blocks in to the canonical chain. If an error is returned it will return the index number of the failing block as well an error describing what went wrong.

func (*BlockChain) InsertHeaderChain

func (bc *BlockChain) InsertHeaderChain(chain []*types.Header, checkFreq int) (int, error)

InsertHeaderChain attempts to insert the given header chain in to the local chain, possibly creating a reorg. If an error is returned, it will return the index number of the failing header as well an error describing what went wrong.

The verify parameter can be used to fine tune whether nonce verification should be done or not. The reason behind the optional check is because some of the header retrieval mechanisms already need to verify nonces, as well as because nonces can be verified sparsely, not needing to check each.

func (*BlockChain) PostChainEvents

func (bc *BlockChain) PostChainEvents(events []interface{})

PostChainEvents iterates over the events generated by a chain insertion and posts them into the event feed.

func (*BlockChain) Reset

func (bc *BlockChain) Reset() error

Reset purges the entire blockchain, restoring it to its genesis state.

func (*BlockChain) ResetWithGenesisBlock

func (bc *BlockChain) ResetWithGenesisBlock(genesis *types.Block) error

ResetWithGenesisBlock purges the entire blockchain, restoring it to the specified genesis state.

func (*BlockChain) Rollback

func (bc *BlockChain) Rollback(chain []common.Hash)

Rollback is designed to remove a chain of links from the database that aren't certain enough to be valid.

func (*BlockChain) SetHead

func (bc *BlockChain) SetHead(head uint64) error

SetHead rewinds the local chain to a new head. In the case of headers, everything above the new head will be deleted and the new one set. In the case of blocks though, the head may be further rewound if block bodies are missing (non-archive nodes after a fast sync).

func (*BlockChain) SetValidator

func (bc *BlockChain) SetValidator(validator Validator)

SetValidator sets the validator which is used to validate incoming blocks.

func (*BlockChain) Stop

func (bc *BlockChain) Stop()

Stop stops the blockchain service. If any imports are currently in progress it will abort them using the procInterrupt.

func (*BlockChain) SubscribeChainHeadEvent

func (bc *BlockChain) SubscribeChainHeadEvent(ch chan<- core.ChainHeadEvent) event.Subscription

SubscribeChainHeadEvent registers a subscription of ChainHeadEvent.

func (*BlockChain) Validator

func (bc *BlockChain) Validator() Validator

Validator returns the current validator.

func (*BlockChain) WriteBlock

func (bc *BlockChain) WriteBlock(block *types.Block)

WriteBlock writes the block to the database.

type BlockGen

type BlockGen struct {
	// contains filtered or unexported fields
}

BlockGen creates blocks for testing. See GenerateChain for a detailed explanation.

func (*BlockGen) AddTx

func (b *BlockGen) AddTx(tx *types.Transaction)

AddTx adds a transaction to the generated block. If no coinbase has been set, the block's coinbase is set to the zero address.

AddTx panics if the transaction cannot be executed. In addition to the protocol-imposed limitations (gas limit, etc.), there are some further limitations on the content of transactions that can be added. Notably, contract code relying on the BLOCKHASH instruction will panic during execution.

func (*BlockGen) AddTxWithChain

func (b *BlockGen) AddTxWithChain(bc *BlockChain, tx *types.Transaction)

AddTxWithChain adds a transaction to the generated block. If no coinbase has been set, the block's coinbase is set to the zero address.

AddTxWithChain panics if the transaction cannot be executed. In addition to the protocol-imposed limitations (gas limit, etc.), there are some further limitations on the content of transactions that can be added. If contract code relies on the BLOCKHASH instruction, the block in chain will be returned.

func (*BlockGen) Number

func (b *BlockGen) Number() *big.Int

Number returns the block number of the block being generated.

func (*BlockGen) OffsetTime

func (b *BlockGen) OffsetTime(seconds int64)

OffsetTime modifies the time instance of a block, implicitly changing its associated difficulty. It's useful to test scenarios where forking is not tied to chain length directly.

func (*BlockGen) PrevBlock

func (b *BlockGen) PrevBlock(index int) *types.Block

PrevBlock returns a previously generated block by number. It panics if num is greater or equal to the number of the block being generated. For index -1, PrevBlock returns the parent block given to GenerateChain.

func (*BlockGen) SetCoinbase

func (b *BlockGen) SetCoinbase(addr common.Address)

SetCoinbase sets the coinbase of the generated block. It can be called at most once.

func (*BlockGen) SetExtra

func (b *BlockGen) SetExtra(data []byte)

SetExtra sets the extra data field of the generated block.

type BlockValidator

type BlockValidator struct {
	// contains filtered or unexported fields
}

BlockValidator is responsible for validating block headers and processed state.

func NewBlockValidator

func NewBlockValidator(blockchain *BlockChain, engine consensus.Engine) *BlockValidator

NewBlockValidator returns a new block validator which is safe for re-use

func (*BlockValidator) ValidateBody

func (v *BlockValidator) ValidateBody(block *types.Block) error

ValidateBody verifies the the block header's transaction.

type DeleteCallback

type DeleteCallback func(rawdb.DatabaseDeleter, common.Hash, uint64)

DeleteCallback is a callback function that is called by SetHead before each header is deleted.

type Genesis

type Genesis struct {
	Config     *params.ChainConfig `json:"config"`
	Nonce      uint64              `json:"nonce"`
	Timestamp  uint64              `json:"timestamp"`
	ExtraData  []byte              `json:"extraData"`
	Difficulty *big.Int            `json:"difficulty" gencodec:"required"`
	Coinbase   common.Address      `json:"coinbase"`

	// These fields are used for consensus tests. Please don't use them
	// in actual genesis blocks.
	Number     uint64      `json:"number"`
	ParentHash common.Hash `json:"parentHash"`
}

Genesis specifies the header fields, state of a genesis block.

func DefaultGenesisBlock

func DefaultGenesisBlock() *Genesis

DefaultGenesisBlock returns main net genesis block.

func (*Genesis) Commit

func (g *Genesis) Commit(db database.Database) (*types.Block, error)

Commit writes the block and state of a genesis specification to the database.

func (*Genesis) MustCommit

func (g *Genesis) MustCommit(db database.Database) *types.Block

func (*Genesis) ToBlock

func (g *Genesis) ToBlock() *types.Block

ToBlock creates the genesis block.

type GenesisMismatchError

type GenesisMismatchError struct {
	Stored, New common.Hash
}

GenesisMismatchError is raised when trying to overwrite an existing genesis block with an incompatible one.

func (*GenesisMismatchError) Error

func (e *GenesisMismatchError) Error() string

type HeaderChain

type HeaderChain struct {
	// contains filtered or unexported fields
}

HeaderChain implements the basic block header chain logic that is shared by core.BlockChain and light.LightChain. It is not usable in itself, only as a part of either structure.

func NewHeaderChain

func NewHeaderChain(chainDb database.Database, engine consensus.Engine, procInterrupt func() bool) (*HeaderChain, error)

NewHeaderChain creates a new HeaderChain structure.

func (*HeaderChain) CurrentHeader

func (hc *HeaderChain) CurrentHeader() *types.Header

CurrentHeader retrieves the current head header of the canonical chain. The header is retrieved from the HeaderChain's internal cache.

func (*HeaderChain) GetAncestor

func (hc *HeaderChain) GetAncestor(hash common.Hash, number, ancestor uint64, maxNonCanonical *uint64) (common.Hash, uint64)

GetAncestor retrieves the Nth ancestor of a given block. It assumes that either the given block or a close ancestor of it is canonical. maxNonCanonical points to a downwards counter limiting the number of blocks to be individually checked before we reach the canonical chain.

Note: ancestor == 0 returns the same block, 1 returns its parent and so on.

func (*HeaderChain) GetBlock

func (hc *HeaderChain) GetBlock(hash common.Hash, number uint64) *types.Block

func (*HeaderChain) GetBlockHashesFromHash

func (hc *HeaderChain) GetBlockHashesFromHash(hash common.Hash, max uint64) []common.Hash

GetBlockHashesFromHash retrieves a number of block hashes starting at a given hash, fetching towards the genesis block.

func (*HeaderChain) GetBlockNumber

func (hc *HeaderChain) GetBlockNumber(hash common.Hash) *uint64

GetBlockNumber retrieves the block number belonging to the given hash from the cache or database

func (*HeaderChain) GetHeader

func (hc *HeaderChain) GetHeader(hash common.Hash, number uint64) *types.Header

GetHeader retrieves a block header from the database by hash and number, caching it if found.

func (*HeaderChain) GetHeaderByHash

func (hc *HeaderChain) GetHeaderByHash(hash common.Hash) *types.Header

GetHeaderByHash retrieves a block header from the database by hash.

func (*HeaderChain) GetHeaderByNumber

func (hc *HeaderChain) GetHeaderByNumber(number uint64) *types.Header

GetHeaderByNumber retrieves a block header from the database by number.

func (*HeaderChain) GetTd

func (hc *HeaderChain) GetTd(hash common.Hash, number uint64) *big.Int

GetTd retrieves a block's total difficulty in the canonical chain from the database by hash and number, caching it if found.

func (*HeaderChain) GetTdByHash

func (hc *HeaderChain) GetTdByHash(hash common.Hash) *big.Int

GetTdByHash retrieves a block's total difficulty in the canonical chain from the database by hash, caching it if found.

func (*HeaderChain) HasHeader

func (hc *HeaderChain) HasHeader(hash common.Hash, number uint64) bool

HasHeader checks if a block header is present in the database or not.

func (*HeaderChain) InsertHeaderChain

func (hc *HeaderChain) InsertHeaderChain(chain []*types.Header, writeHeader WhCallback, start time.Time) (int, error)

InsertHeaderChain attempts to insert the given header chain in to the local chain, possibly creating a reorg. If an error is returned, it will return the index number of the failing header as well an error describing what went wrong.

The verify parameter can be used to fine tune whether nonce verification should be done or not. The reason behind the optional check is because some of the header retrieval mechanisms already need to verfy nonces, as well as because nonces can be verified sparsely, not needing to check each.

func (*HeaderChain) SetCurrentHeader

func (hc *HeaderChain) SetCurrentHeader(head *types.Header)

SetCurrentHeader sets the current head header of the canonical chain.

func (*HeaderChain) SetGenesis

func (hc *HeaderChain) SetGenesis(head *types.Header)

SetGenesis sets a new genesis block header for the chain

func (*HeaderChain) SetHead

func (hc *HeaderChain) SetHead(head uint64, delFn DeleteCallback)

SetHead rewinds the local chain to a new head. Everything above the new head will be deleted and the new one set.

func (*HeaderChain) ValidateHeaderChain

func (hc *HeaderChain) ValidateHeaderChain(chain []*types.Header, checkFreq int) (int, error)

func (*HeaderChain) WriteHeader

func (hc *HeaderChain) WriteHeader(header *types.Header) (status WriteStatus, err error)

WriteHeader writes a header into the local chain, given that its parent is already known. If the total difficulty of the newly inserted header becomes greater than the current known TD, the canonical chain is re-routed.

Note: This method is not concurrent-safe with inserting blocks simultaneously into the chain, as side effects caused by reorganisations cannot be emulated without the real blocks. Hence, writing headers directly should only be done in two scenarios: pure-header mode of operation (light clients), or properly separated header/block phases (non-archive clients).

func (*HeaderChain) WriteTd

func (hc *HeaderChain) WriteTd(hash common.Hash, number uint64, td *big.Int) error

WriteTd stores a block's total difficulty into the database, also caching it along the way.

type Validator

type Validator interface {
	// ValidateBody validates the given block's content.
	ValidateBody(block *types.Block) error
}

Validator is an interface which defines the standard for block validation. It is only responsible for validating block contents, as the header validation is done by the specific consensus engines.

type WhCallback

type WhCallback func(*types.Header) error

WhCallback is a callback function for inserting individual headers. A callback is used for two reasons: first, in a LightChain, status should be processed and light chain events sent, while in a BlockChain this is not necessary since chain events are sent after inserting blocks. Second, the header writes should be protected by the parent chain mutex individually.

type WriteStatus

type WriteStatus byte

WriteStatus status of write

const (
	NonStatTy WriteStatus = iota
	CanonStatTy
	SideStatTy
)

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL