You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

661 lines
18 KiB

10 years ago
10 years ago
7 years ago
10 years ago
10 years ago
7 years ago
7 years ago
7 years ago
10 years ago
10 years ago
7 years ago
7 years ago
11 years ago
7 years ago
7 years ago
7 years ago
7 years ago
  1. package types
  2. import (
  3. "bytes"
  4. "errors"
  5. "fmt"
  6. "strings"
  7. "sync"
  8. "time"
  9. "github.com/tendermint/tendermint/crypto/merkle"
  10. "github.com/tendermint/tendermint/crypto/tmhash"
  11. cmn "github.com/tendermint/tendermint/libs/common"
  12. )
  13. // Block defines the atomic unit of a Tendermint blockchain.
  14. // TODO: add Version byte
  15. type Block struct {
  16. mtx sync.Mutex
  17. Header `json:"header"`
  18. Data `json:"data"`
  19. Evidence EvidenceData `json:"evidence"`
  20. LastCommit *Commit `json:"last_commit"`
  21. }
  22. // MakeBlock returns a new block with an empty header, except what can be
  23. // computed from itself.
  24. // It populates the same set of fields validated by ValidateBasic.
  25. func MakeBlock(height int64, txs []Tx, lastCommit *Commit, evidence []Evidence) *Block {
  26. block := &Block{
  27. Header: Header{
  28. Height: height,
  29. Time: time.Now(),
  30. NumTxs: int64(len(txs)),
  31. },
  32. Data: Data{
  33. Txs: txs,
  34. },
  35. Evidence: EvidenceData{Evidence: evidence},
  36. LastCommit: lastCommit,
  37. }
  38. block.fillHeader()
  39. return block
  40. }
  41. // ValidateBasic performs basic validation that doesn't involve state data.
  42. // It checks the internal consistency of the block.
  43. func (b *Block) ValidateBasic() error {
  44. if b == nil {
  45. return errors.New("Nil blocks are invalid")
  46. }
  47. b.mtx.Lock()
  48. defer b.mtx.Unlock()
  49. newTxs := int64(len(b.Data.Txs))
  50. if b.NumTxs != newTxs {
  51. return fmt.Errorf(
  52. "Wrong Block.Header.NumTxs. Expected %v, got %v",
  53. newTxs,
  54. b.NumTxs,
  55. )
  56. }
  57. if !bytes.Equal(b.LastCommitHash, b.LastCommit.Hash()) {
  58. return fmt.Errorf(
  59. "Wrong Block.Header.LastCommitHash. Expected %v, got %v",
  60. b.LastCommitHash,
  61. b.LastCommit.Hash(),
  62. )
  63. }
  64. if b.Header.Height != 1 {
  65. if err := b.LastCommit.ValidateBasic(); err != nil {
  66. return err
  67. }
  68. }
  69. if !bytes.Equal(b.DataHash, b.Data.Hash()) {
  70. return fmt.Errorf(
  71. "Wrong Block.Header.DataHash. Expected %v, got %v",
  72. b.DataHash,
  73. b.Data.Hash(),
  74. )
  75. }
  76. if !bytes.Equal(b.EvidenceHash, b.Evidence.Hash()) {
  77. return fmt.Errorf(
  78. "Wrong Block.Header.EvidenceHash. Expected %v, got %v",
  79. b.EvidenceHash,
  80. b.Evidence.Hash(),
  81. )
  82. }
  83. return nil
  84. }
  85. // fillHeader fills in any remaining header fields that are a function of the block data
  86. func (b *Block) fillHeader() {
  87. if b.LastCommitHash == nil {
  88. b.LastCommitHash = b.LastCommit.Hash()
  89. }
  90. if b.DataHash == nil {
  91. b.DataHash = b.Data.Hash()
  92. }
  93. if b.EvidenceHash == nil {
  94. b.EvidenceHash = b.Evidence.Hash()
  95. }
  96. }
  97. // Hash computes and returns the block hash.
  98. // If the block is incomplete, block hash is nil for safety.
  99. func (b *Block) Hash() cmn.HexBytes {
  100. if b == nil {
  101. return nil
  102. }
  103. b.mtx.Lock()
  104. defer b.mtx.Unlock()
  105. if b == nil || b.LastCommit == nil {
  106. return nil
  107. }
  108. b.fillHeader()
  109. return b.Header.Hash()
  110. }
  111. // MakePartSet returns a PartSet containing parts of a serialized block.
  112. // This is the form in which the block is gossipped to peers.
  113. // CONTRACT: partSize is greater than zero.
  114. func (b *Block) MakePartSet(partSize int) *PartSet {
  115. if b == nil {
  116. return nil
  117. }
  118. b.mtx.Lock()
  119. defer b.mtx.Unlock()
  120. // We prefix the byte length, so that unmarshaling
  121. // can easily happen via a reader.
  122. bz, err := cdc.MarshalBinary(b)
  123. if err != nil {
  124. panic(err)
  125. }
  126. return NewPartSetFromData(bz, partSize)
  127. }
  128. // HashesTo is a convenience function that checks if a block hashes to the given argument.
  129. // Returns false if the block is nil or the hash is empty.
  130. func (b *Block) HashesTo(hash []byte) bool {
  131. if len(hash) == 0 {
  132. return false
  133. }
  134. if b == nil {
  135. return false
  136. }
  137. return bytes.Equal(b.Hash(), hash)
  138. }
  139. // Size returns size of the block in bytes.
  140. func (b *Block) Size() int {
  141. bz, err := cdc.MarshalBinaryBare(b)
  142. if err != nil {
  143. return 0
  144. }
  145. return len(bz)
  146. }
  147. // String returns a string representation of the block
  148. func (b *Block) String() string {
  149. return b.StringIndented("")
  150. }
  151. // StringIndented returns a string representation of the block
  152. func (b *Block) StringIndented(indent string) string {
  153. if b == nil {
  154. return "nil-Block"
  155. }
  156. return fmt.Sprintf(`Block{
  157. %s %v
  158. %s %v
  159. %s %v
  160. %s %v
  161. %s}#%v`,
  162. indent, b.Header.StringIndented(indent+" "),
  163. indent, b.Data.StringIndented(indent+" "),
  164. indent, b.Evidence.StringIndented(indent+" "),
  165. indent, b.LastCommit.StringIndented(indent+" "),
  166. indent, b.Hash())
  167. }
  168. // StringShort returns a shortened string representation of the block
  169. func (b *Block) StringShort() string {
  170. if b == nil {
  171. return "nil-Block"
  172. }
  173. return fmt.Sprintf("Block#%v", b.Hash())
  174. }
  175. //-----------------------------------------------------------------------------
  176. // Header defines the structure of a Tendermint block header
  177. // TODO: limit header size
  178. // NOTE: changes to the Header should be duplicated in the abci Header
  179. type Header struct {
  180. // basic block info
  181. ChainID string `json:"chain_id"`
  182. Height int64 `json:"height"`
  183. Time time.Time `json:"time"`
  184. NumTxs int64 `json:"num_txs"`
  185. // prev block info
  186. LastBlockID BlockID `json:"last_block_id"`
  187. TotalTxs int64 `json:"total_txs"`
  188. // hashes of block data
  189. LastCommitHash cmn.HexBytes `json:"last_commit_hash"` // commit from validators from the last block
  190. DataHash cmn.HexBytes `json:"data_hash"` // transactions
  191. // hashes from the app output from the prev block
  192. ValidatorsHash cmn.HexBytes `json:"validators_hash"` // validators for the current block
  193. NextValidatorsHash cmn.HexBytes `json:"next_validators_hash"` // validators for the next block
  194. ConsensusHash cmn.HexBytes `json:"consensus_hash"` // consensus params for current block
  195. AppHash cmn.HexBytes `json:"app_hash"` // state after txs from the previous block
  196. LastResultsHash cmn.HexBytes `json:"last_results_hash"` // root hash of all results from the txs from the previous block
  197. // consensus info
  198. EvidenceHash cmn.HexBytes `json:"evidence_hash"` // evidence included in the block
  199. ProposerAddress Address `json:"proposer_address"` // original proposer of the block
  200. }
  201. // Hash returns the hash of the header.
  202. // Returns nil if ValidatorHash is missing,
  203. // since a Header is not valid unless there is
  204. // a ValidatorsHash (corresponding to the validator set).
  205. func (h *Header) Hash() cmn.HexBytes {
  206. if h == nil || len(h.ValidatorsHash) == 0 {
  207. return nil
  208. }
  209. return merkle.SimpleHashFromMap(map[string]merkle.Hasher{
  210. "ChainID": aminoHasher(h.ChainID),
  211. "Height": aminoHasher(h.Height),
  212. "Time": aminoHasher(h.Time),
  213. "NumTxs": aminoHasher(h.NumTxs),
  214. "TotalTxs": aminoHasher(h.TotalTxs),
  215. "LastBlockID": aminoHasher(h.LastBlockID),
  216. "LastCommit": aminoHasher(h.LastCommitHash),
  217. "Data": aminoHasher(h.DataHash),
  218. "Validators": aminoHasher(h.ValidatorsHash),
  219. "NextValidators": aminoHasher(h.NextValidatorsHash),
  220. "App": aminoHasher(h.AppHash),
  221. "Consensus": aminoHasher(h.ConsensusHash),
  222. "Results": aminoHasher(h.LastResultsHash),
  223. "Evidence": aminoHasher(h.EvidenceHash),
  224. "Proposer": aminoHasher(h.ProposerAddress),
  225. })
  226. }
  227. // StringIndented returns a string representation of the header
  228. func (h *Header) StringIndented(indent string) string {
  229. if h == nil {
  230. return "nil-Header"
  231. }
  232. return fmt.Sprintf(`Header{
  233. %s ChainID: %v
  234. %s Height: %v
  235. %s Time: %v
  236. %s NumTxs: %v
  237. %s TotalTxs: %v
  238. %s LastBlockID: %v
  239. %s LastCommit: %v
  240. %s Data: %v
  241. %s Validators: %v
  242. %s NextValidators: %v
  243. %s App: %v
  244. %s Consensus: %v
  245. %s Results: %v
  246. %s Evidence: %v
  247. %s Proposer: %v
  248. %s}#%v`,
  249. indent, h.ChainID,
  250. indent, h.Height,
  251. indent, h.Time,
  252. indent, h.NumTxs,
  253. indent, h.TotalTxs,
  254. indent, h.LastBlockID,
  255. indent, h.LastCommitHash,
  256. indent, h.DataHash,
  257. indent, h.ValidatorsHash,
  258. indent, h.NextValidatorsHash,
  259. indent, h.AppHash,
  260. indent, h.ConsensusHash,
  261. indent, h.LastResultsHash,
  262. indent, h.EvidenceHash,
  263. indent, h.ProposerAddress,
  264. indent, h.Hash())
  265. }
  266. //-------------------------------------
  267. // Commit contains the evidence that a block was committed by a set of validators.
  268. // NOTE: Commit is empty for height 1, but never nil.
  269. type Commit struct {
  270. // NOTE: The Precommits are in order of address to preserve the bonded ValidatorSet order.
  271. // Any peer with a block can gossip precommits by index with a peer without recalculating the
  272. // active ValidatorSet.
  273. BlockID BlockID `json:"block_id"`
  274. Precommits []*Vote `json:"precommits"`
  275. // Volatile
  276. firstPrecommit *Vote
  277. hash cmn.HexBytes
  278. bitArray *cmn.BitArray
  279. }
  280. // FirstPrecommit returns the first non-nil precommit in the commit.
  281. // If all precommits are nil, it returns an empty precommit with height 0.
  282. func (commit *Commit) FirstPrecommit() *Vote {
  283. if len(commit.Precommits) == 0 {
  284. return nil
  285. }
  286. if commit.firstPrecommit != nil {
  287. return commit.firstPrecommit
  288. }
  289. for _, precommit := range commit.Precommits {
  290. if precommit != nil {
  291. commit.firstPrecommit = precommit
  292. return precommit
  293. }
  294. }
  295. return &Vote{
  296. Type: VoteTypePrecommit,
  297. }
  298. }
  299. // Height returns the height of the commit
  300. func (commit *Commit) Height() int64 {
  301. if len(commit.Precommits) == 0 {
  302. return 0
  303. }
  304. return commit.FirstPrecommit().Height
  305. }
  306. // Round returns the round of the commit
  307. func (commit *Commit) Round() int {
  308. if len(commit.Precommits) == 0 {
  309. return 0
  310. }
  311. return commit.FirstPrecommit().Round
  312. }
  313. // Type returns the vote type of the commit, which is always VoteTypePrecommit
  314. func (commit *Commit) Type() byte {
  315. return VoteTypePrecommit
  316. }
  317. // Size returns the number of votes in the commit
  318. func (commit *Commit) Size() int {
  319. if commit == nil {
  320. return 0
  321. }
  322. return len(commit.Precommits)
  323. }
  324. // BitArray returns a BitArray of which validators voted in this commit
  325. func (commit *Commit) BitArray() *cmn.BitArray {
  326. if commit.bitArray == nil {
  327. commit.bitArray = cmn.NewBitArray(len(commit.Precommits))
  328. for i, precommit := range commit.Precommits {
  329. // TODO: need to check the BlockID otherwise we could be counting conflicts,
  330. // not just the one with +2/3 !
  331. commit.bitArray.SetIndex(i, precommit != nil)
  332. }
  333. }
  334. return commit.bitArray
  335. }
  336. // GetByIndex returns the vote corresponding to a given validator index
  337. func (commit *Commit) GetByIndex(index int) *Vote {
  338. return commit.Precommits[index]
  339. }
  340. // IsCommit returns true if there is at least one vote
  341. func (commit *Commit) IsCommit() bool {
  342. return len(commit.Precommits) != 0
  343. }
  344. // ValidateBasic performs basic validation that doesn't involve state data.
  345. // Does not actually check the cryptographic signatures.
  346. func (commit *Commit) ValidateBasic() error {
  347. if commit.BlockID.IsZero() {
  348. return errors.New("Commit cannot be for nil block")
  349. }
  350. if len(commit.Precommits) == 0 {
  351. return errors.New("No precommits in commit")
  352. }
  353. height, round := commit.Height(), commit.Round()
  354. // Validate the precommits.
  355. for _, precommit := range commit.Precommits {
  356. // It's OK for precommits to be missing.
  357. if precommit == nil {
  358. continue
  359. }
  360. // Ensure that all votes are precommits.
  361. if precommit.Type != VoteTypePrecommit {
  362. return fmt.Errorf("Invalid commit vote. Expected precommit, got %v",
  363. precommit.Type)
  364. }
  365. // Ensure that all heights are the same.
  366. if precommit.Height != height {
  367. return fmt.Errorf("Invalid commit precommit height. Expected %v, got %v",
  368. height, precommit.Height)
  369. }
  370. // Ensure that all rounds are the same.
  371. if precommit.Round != round {
  372. return fmt.Errorf("Invalid commit precommit round. Expected %v, got %v",
  373. round, precommit.Round)
  374. }
  375. }
  376. return nil
  377. }
  378. // Hash returns the hash of the commit
  379. func (commit *Commit) Hash() cmn.HexBytes {
  380. if commit == nil {
  381. return nil
  382. }
  383. if commit.hash == nil {
  384. bs := make([]merkle.Hasher, len(commit.Precommits))
  385. for i, precommit := range commit.Precommits {
  386. bs[i] = aminoHasher(precommit)
  387. }
  388. commit.hash = merkle.SimpleHashFromHashers(bs)
  389. }
  390. return commit.hash
  391. }
  392. // StringIndented returns a string representation of the commit
  393. func (commit *Commit) StringIndented(indent string) string {
  394. if commit == nil {
  395. return "nil-Commit"
  396. }
  397. precommitStrings := make([]string, len(commit.Precommits))
  398. for i, precommit := range commit.Precommits {
  399. precommitStrings[i] = precommit.String()
  400. }
  401. return fmt.Sprintf(`Commit{
  402. %s BlockID: %v
  403. %s Precommits:
  404. %s %v
  405. %s}#%v`,
  406. indent, commit.BlockID,
  407. indent,
  408. indent, strings.Join(precommitStrings, "\n"+indent+" "),
  409. indent, commit.hash)
  410. }
  411. //-----------------------------------------------------------------------------
  412. // SignedHeader is a header along with the commits that prove it.
  413. type SignedHeader struct {
  414. *Header `json:"header"`
  415. Commit *Commit `json:"commit"`
  416. }
  417. // ValidateBasic does basic consistency checks and makes sure the header
  418. // and commit are consistent.
  419. //
  420. // NOTE: This does not actually check the cryptographic signatures. Make
  421. // sure to use a Verifier to validate the signatures actually provide a
  422. // significantly strong proof for this header's validity.
  423. func (sh SignedHeader) ValidateBasic(chainID string) error {
  424. // Make sure the header is consistent with the commit.
  425. if sh.Header == nil {
  426. return errors.New("SignedHeader missing header.")
  427. }
  428. if sh.Commit == nil {
  429. return errors.New("SignedHeader missing commit (precommit votes).")
  430. }
  431. // Check ChainID.
  432. if sh.ChainID != chainID {
  433. return fmt.Errorf("Header belongs to another chain '%s' not '%s'",
  434. sh.ChainID, chainID)
  435. }
  436. // Check Height.
  437. if sh.Commit.Height() != sh.Height {
  438. return fmt.Errorf("SignedHeader header and commit height mismatch: %v vs %v",
  439. sh.Height, sh.Commit.Height())
  440. }
  441. // Check Hash.
  442. hhash := sh.Hash()
  443. chash := sh.Commit.BlockID.Hash
  444. if !bytes.Equal(hhash, chash) {
  445. return fmt.Errorf("SignedHeader commit signs block %X, header is block %X",
  446. chash, hhash)
  447. }
  448. // ValidateBasic on the Commit.
  449. err := sh.Commit.ValidateBasic()
  450. if err != nil {
  451. return cmn.ErrorWrap(err, "commit.ValidateBasic failed during SignedHeader.ValidateBasic")
  452. }
  453. return nil
  454. }
  455. func (sh SignedHeader) String() string {
  456. return sh.StringIndented("")
  457. }
  458. // StringIndented returns a string representation of the SignedHeader.
  459. func (sh SignedHeader) StringIndented(indent string) string {
  460. return fmt.Sprintf(`SignedHeader{
  461. %s %v
  462. %s %v
  463. %s}`,
  464. indent, sh.Header.StringIndented(indent+" "),
  465. indent, sh.Commit.StringIndented(indent+" "),
  466. indent)
  467. return ""
  468. }
  469. //-----------------------------------------------------------------------------
  470. // Data contains the set of transactions included in the block
  471. type Data struct {
  472. // Txs that will be applied by state @ block.Height+1.
  473. // NOTE: not all txs here are valid. We're just agreeing on the order first.
  474. // This means that block.AppHash does not include these txs.
  475. Txs Txs `json:"txs"`
  476. // Volatile
  477. hash cmn.HexBytes
  478. }
  479. // Hash returns the hash of the data
  480. func (data *Data) Hash() cmn.HexBytes {
  481. if data == nil {
  482. return (Txs{}).Hash()
  483. }
  484. if data.hash == nil {
  485. data.hash = data.Txs.Hash() // NOTE: leaves of merkle tree are TxIDs
  486. }
  487. return data.hash
  488. }
  489. // StringIndented returns a string representation of the transactions
  490. func (data *Data) StringIndented(indent string) string {
  491. if data == nil {
  492. return "nil-Data"
  493. }
  494. txStrings := make([]string, cmn.MinInt(len(data.Txs), 21))
  495. for i, tx := range data.Txs {
  496. if i == 20 {
  497. txStrings[i] = fmt.Sprintf("... (%v total)", len(data.Txs))
  498. break
  499. }
  500. txStrings[i] = fmt.Sprintf("%X (%d bytes)", tx.Hash(), len(tx))
  501. }
  502. return fmt.Sprintf(`Data{
  503. %s %v
  504. %s}#%v`,
  505. indent, strings.Join(txStrings, "\n"+indent+" "),
  506. indent, data.hash)
  507. }
  508. //-----------------------------------------------------------------------------
  509. // EvidenceData contains any evidence of malicious wrong-doing by validators
  510. type EvidenceData struct {
  511. Evidence EvidenceList `json:"evidence"`
  512. // Volatile
  513. hash cmn.HexBytes
  514. }
  515. // Hash returns the hash of the data.
  516. func (data *EvidenceData) Hash() cmn.HexBytes {
  517. if data.hash == nil {
  518. data.hash = data.Evidence.Hash()
  519. }
  520. return data.hash
  521. }
  522. // StringIndented returns a string representation of the evidence.
  523. func (data *EvidenceData) StringIndented(indent string) string {
  524. if data == nil {
  525. return "nil-Evidence"
  526. }
  527. evStrings := make([]string, cmn.MinInt(len(data.Evidence), 21))
  528. for i, ev := range data.Evidence {
  529. if i == 20 {
  530. evStrings[i] = fmt.Sprintf("... (%v total)", len(data.Evidence))
  531. break
  532. }
  533. evStrings[i] = fmt.Sprintf("Evidence:%v", ev)
  534. }
  535. return fmt.Sprintf(`EvidenceData{
  536. %s %v
  537. %s}#%v`,
  538. indent, strings.Join(evStrings, "\n"+indent+" "),
  539. indent, data.hash)
  540. return ""
  541. }
  542. //--------------------------------------------------------------------------------
  543. // BlockID defines the unique ID of a block as its Hash and its PartSetHeader
  544. type BlockID struct {
  545. Hash cmn.HexBytes `json:"hash"`
  546. PartsHeader PartSetHeader `json:"parts"`
  547. }
  548. // IsZero returns true if this is the BlockID for a nil-block
  549. func (blockID BlockID) IsZero() bool {
  550. return len(blockID.Hash) == 0 && blockID.PartsHeader.IsZero()
  551. }
  552. // Equals returns true if the BlockID matches the given BlockID
  553. func (blockID BlockID) Equals(other BlockID) bool {
  554. return bytes.Equal(blockID.Hash, other.Hash) &&
  555. blockID.PartsHeader.Equals(other.PartsHeader)
  556. }
  557. // Key returns a machine-readable string representation of the BlockID
  558. func (blockID BlockID) Key() string {
  559. bz, err := cdc.MarshalBinaryBare(blockID.PartsHeader)
  560. if err != nil {
  561. panic(err)
  562. }
  563. return string(blockID.Hash) + string(bz)
  564. }
  565. // String returns a human readable string representation of the BlockID
  566. func (blockID BlockID) String() string {
  567. return fmt.Sprintf(`%v:%v`, blockID.Hash, blockID.PartsHeader)
  568. }
  569. //-------------------------------------------------------
  570. type hasher struct {
  571. item interface{}
  572. }
  573. func (h hasher) Hash() []byte {
  574. hasher := tmhash.New()
  575. if h.item != nil && !cmn.IsTypedNil(h.item) && !cmn.IsEmpty(h.item) {
  576. bz, err := cdc.MarshalBinaryBare(h.item)
  577. if err != nil {
  578. panic(err)
  579. }
  580. _, err = hasher.Write(bz)
  581. if err != nil {
  582. panic(err)
  583. }
  584. }
  585. return hasher.Sum(nil)
  586. }
  587. func aminoHash(item interface{}) []byte {
  588. h := hasher{item}
  589. return h.Hash()
  590. }
  591. func aminoHasher(item interface{}) merkle.Hasher {
  592. return hasher{item}
  593. }