block.go 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151
  1. package dgn
  2. import (
  3. "encoding/binary"
  4. "github.com/ethereum/go-ethereum/common"
  5. "github.com/ethereum/go-ethereum/core/types"
  6. "github.com/ethereum/go-ethereum/rlp"
  7. "golang.org/x/crypto/sha3"
  8. "math/big"
  9. "sync/atomic"
  10. "time"
  11. )
  12. type BHeader struct {
  13. ParentHash common.Hash `json:"parentHash" gencodec:"required"`
  14. UncleHash common.Hash `json:"sha3Uncles" gencodec:"required"`
  15. Coinbase common.Address `json:"miner" gencodec:"required"`
  16. Root common.Hash `json:"stateRoot" gencodec:"required"`
  17. TxHash common.Hash `json:"transactionsRoot" gencodec:"required"`
  18. ReceiptHash common.Hash `json:"receiptsRoot" gencodec:"required"`
  19. Bloom types.Bloom `json:"logsBloom" gencodec:"required"`
  20. Difficulty *big.Int `json:"difficulty" gencodec:"required"`
  21. Number *big.Int `json:"number" gencodec:"required"`
  22. GasLimit uint64 `json:"gasLimit" gencodec:"required"`
  23. GasUsed uint64 `json:"gasUsed" gencodec:"required"`
  24. Time uint64 `json:"timestamp" gencodec:"required"`
  25. Extra []byte `json:"extraData" gencodec:"required"`
  26. Election []byte `json:"election" gencodec:"required"`
  27. MixDigest common.Hash `json:"mixHash"`
  28. Nonce types.BlockNonce `json:"nonce"`
  29. // Signature values
  30. V *big.Int `json:"v" gencodec:"required"`
  31. R *big.Int `json:"r" gencodec:"required"`
  32. S *big.Int `json:"s" gencodec:"required"`
  33. }
  34. // Hash returns the block hash of the header, which is simply the keccak256 hash of its
  35. // RLP encoding.
  36. func (h *BHeader) Hash() common.Hash {
  37. return rlpHash(h)
  38. }
  39. func rlpHash(x interface{}) (h common.Hash) {
  40. hw := sha3.NewLegacyKeccak256()
  41. rlp.Encode(hw, x)
  42. hw.Sum(h[:0])
  43. return h
  44. }
  45. // Block represents an entire block in the Ethereum blockchain.
  46. type Block struct {
  47. header *BHeader
  48. uncles []*BHeader
  49. transactions types.Transactions
  50. // caches
  51. hash atomic.Value
  52. size atomic.Value
  53. // Td is used by package core to store the total difficulty
  54. // of the chain up to and including the block.
  55. td *big.Int
  56. // These fields are used by package eth to track
  57. // inter-peer block relay.
  58. ReceivedAt time.Time
  59. ReceivedFrom interface{}
  60. }
  61. func (b *Block) Uncles() []*BHeader { return b.uncles }
  62. func (b *Block) Transactions() types.Transactions { return b.transactions }
  63. func (b *Block) Transaction(hash common.Hash) *types.Transaction {
  64. for _, transaction := range b.transactions {
  65. if transaction.Hash() == hash {
  66. return transaction
  67. }
  68. }
  69. return nil
  70. }
  71. func (b *Block) Number() *big.Int { return new(big.Int).Set(b.header.Number) }
  72. func (b *Block) GasLimit() uint64 { return b.header.GasLimit }
  73. func (b *Block) GasUsed() uint64 { return b.header.GasUsed }
  74. func (b *Block) Difficulty() *big.Int { return new(big.Int).Set(b.header.Difficulty) }
  75. func (b *Block) Time() uint64 { return b.header.Time }
  76. func (b *Block) NumberU64() uint64 { return b.header.Number.Uint64() }
  77. func (b *Block) MixDigest() common.Hash { return b.header.MixDigest }
  78. func (b *Block) Nonce() uint64 { return binary.BigEndian.Uint64(b.header.Nonce[:]) }
  79. func (b *Block) Bloom() types.Bloom { return b.header.Bloom }
  80. func (b *Block) Coinbase() common.Address { return b.header.Coinbase }
  81. func (b *Block) Root() common.Hash { return b.header.Root }
  82. func (b *Block) ParentHash() common.Hash { return b.header.ParentHash }
  83. func (b *Block) TxHash() common.Hash { return b.header.TxHash }
  84. func (b *Block) ReceiptHash() common.Hash { return b.header.ReceiptHash }
  85. func (b *Block) UncleHash() common.Hash { return b.header.UncleHash }
  86. func (b *Block) Extra() []byte { return common.CopyBytes(b.header.Extra) }
  87. // WithBody returns a new block with the given transaction and uncle contents.
  88. func (b *Block) WithBody(transactions []*types.Transaction, uncles []*BHeader) *Block {
  89. block := &Block{
  90. header: CopyHeader(b.header),
  91. transactions: make([]*types.Transaction, len(transactions)),
  92. uncles: make([]*BHeader, len(uncles)),
  93. }
  94. copy(block.transactions, transactions)
  95. for i := range uncles {
  96. block.uncles[i] = CopyHeader(uncles[i])
  97. }
  98. return block
  99. }
  100. // Hash returns the keccak256 hash of b's header.
  101. // The hash is computed on the first call and cached thereafter.
  102. func (b *Block) Hash() common.Hash {
  103. if hash := b.hash.Load(); hash != nil {
  104. return hash.(common.Hash)
  105. }
  106. v := b.header.Hash()
  107. b.hash.Store(v)
  108. return v
  109. }
  110. // CopyHeader creates a deep copy of a block header to prevent side effects from
  111. // modifying a header variable.
  112. func CopyHeader(h *BHeader) *BHeader {
  113. cpy := *h
  114. if cpy.Difficulty = new(big.Int); h.Difficulty != nil {
  115. cpy.Difficulty.Set(h.Difficulty)
  116. }
  117. if cpy.Number = new(big.Int); h.Number != nil {
  118. cpy.Number.Set(h.Number)
  119. }
  120. if len(h.Extra) > 0 {
  121. cpy.Extra = make([]byte, len(h.Extra))
  122. copy(cpy.Extra, h.Extra)
  123. }
  124. return &cpy
  125. }
  126. func NewBlockWithHeader(header *BHeader) *Block {
  127. return &Block{header: CopyHeader(header)}
  128. }