notes about block 1
This commit is contained in:
parent
65cdb07f0c
commit
16227594ef
|
@ -5,7 +5,7 @@ Here we describe the data structures in the Tendermint blockchain and the rules
|
|||
# Data Structures
|
||||
|
||||
The Tendermint blockchains consists of a short list of basic data types:
|
||||
`Block`, `Header`, `Vote`, `BlockID`, and `Signature`.
|
||||
`Block`, `Header`, `Vote`, `BlockID`, `Signature`, and `Evidence`.
|
||||
|
||||
## Block
|
||||
|
||||
|
@ -135,6 +135,10 @@ where `Signature` is the DER encoded signature, ie:
|
|||
0x30 <length of whole message> <0x02> <length of R> <R> 0x2 <length of S> <S>.
|
||||
```
|
||||
|
||||
## Evidence
|
||||
|
||||
TODO
|
||||
|
||||
# Validation
|
||||
|
||||
Here we describe the validation rules for every element in block.
|
||||
|
@ -171,6 +175,8 @@ block.Header.Height > 0
|
|||
block.Header.Height == prevBlock.Header.Height + 1
|
||||
```
|
||||
|
||||
The height is an incrementing integer. The first block has `block.Header.Height == 1`.
|
||||
|
||||
### Time
|
||||
|
||||
The median of the timestamps of the valid votes in the block.LastCommit.
|
||||
|
@ -202,14 +208,18 @@ block.Header.LastCommitHash == SimpleMerkleRoot(block.LastCommit)
|
|||
Simple Merkle root of the votes included in the block.
|
||||
These are the votes that committed the previous block.
|
||||
|
||||
The first block has `block.Header.LastCommitHash == []byte{}`
|
||||
|
||||
### TotalTxs
|
||||
|
||||
```
|
||||
block.Header.TotalTxs == prevBlock.Header.TotalTxs + block.header.NumTxs
|
||||
block.Header.TotalTxs == prevBlock.Header.TotalTxs + block.Header.NumTxs
|
||||
```
|
||||
|
||||
The cumulative sum of all transactions included in this blockchain.
|
||||
|
||||
The first block has `block.Header.TotalTxs = block.Header.NumberTxs`.
|
||||
|
||||
### LastBlockID
|
||||
|
||||
```
|
||||
|
@ -224,6 +234,8 @@ block.HeaderLastBlockID == BlockID{
|
|||
Previous block's BlockID. Note it depends on the ConsensusParams,
|
||||
which are held in the `state` and may be updated by the application.
|
||||
|
||||
The first block has `block.Header.LastBlockID == BlockID{}`.
|
||||
|
||||
### ResultsHash
|
||||
|
||||
```
|
||||
|
@ -232,6 +244,8 @@ block.ResultsHash == SimpleMerkleRoot(app.Results)
|
|||
|
||||
Simple Merkle root of the results of the transactions in the previous block.
|
||||
|
||||
The first block has `block.Header.ResultsHash == []byte{}`.
|
||||
|
||||
### AppHash
|
||||
|
||||
```
|
||||
|
@ -240,6 +254,8 @@ block.AppHash == app.AppHash
|
|||
|
||||
Arbitrary byte array returned by the application after executing and commiting the previous block.
|
||||
|
||||
The first block has `block.Header.AppHash == []byte{}`.
|
||||
|
||||
### ValidatorsHash
|
||||
|
||||
```
|
||||
|
@ -248,7 +264,7 @@ block.ValidatorsHash == SimpleMerkleRoot(state.Validators)
|
|||
|
||||
Simple Merkle root of the current validator set that is committing the block.
|
||||
This can be used to validate the `LastCommit` included in the next block.
|
||||
May be updated by the applicatoin.
|
||||
May be updated by the application.
|
||||
|
||||
### ConsensusParamsHash
|
||||
|
||||
|
@ -261,9 +277,15 @@ May be updated by the application.
|
|||
|
||||
### Proposer
|
||||
|
||||
```
|
||||
block.Header.Proposer in state.Validators
|
||||
```
|
||||
|
||||
Original proposer of the block.
|
||||
|
||||
TODO
|
||||
NOTE: this field can only be further verified by real-time participants in the consensus.
|
||||
This is because the same block can be proposed in multiple rounds for the same height
|
||||
and we do not track the initial round the block was proposed.
|
||||
|
||||
### EvidenceHash
|
||||
|
||||
|
|
|
@ -31,6 +31,8 @@ The length-prefix consists of a single byte and corresponds to the length of the
|
|||
|
||||
Negative integers are encoded by flipping the leading bit of the length-prefix to a `1`.
|
||||
|
||||
Zero is encoded as `0x00`. It is not length-prefixed.
|
||||
|
||||
|
||||
Examples:
|
||||
|
||||
|
@ -40,6 +42,8 @@ encode(uint(70000)) == [0x03, 0x01, 0x11, 0x70]
|
|||
|
||||
encode(int(-6)) == [0xF1, 0x06]
|
||||
encode(int(-70000)) == [0xF3, 0x01, 0x11, 0x70]
|
||||
|
||||
encode(int(0)) == [0x00]
|
||||
```
|
||||
|
||||
### Strings
|
||||
|
@ -47,9 +51,12 @@ encode(int(-70000)) == [0xF3, 0x01, 0x11, 0x70]
|
|||
An encoded string is a length prefix followed by the underlying bytes of the string.
|
||||
The length-prefix is itself encoded as an `int`.
|
||||
|
||||
The empty string is encoded as `0x00`. It is not length-prefixed.
|
||||
|
||||
Examples:
|
||||
|
||||
```
|
||||
encode("") == [0x00]
|
||||
encode("a") == [0x01, 0x01, 0x61]
|
||||
encode("hello") == [0x01, 0x05, 0x68, 0x65, 0x6C, 0x6C, 0x6F]
|
||||
encode("¥") == [0x01, 0x02, 0xC2, 0xA5]
|
||||
|
@ -74,9 +81,12 @@ encode([2]string{"abc", "efg"}) == [0x01, 0x03, 0x61, 0x62, 0x63, 0x01, 0x03, 0x
|
|||
An encoded variable-length array is a length prefix followed by the concatenation of the encoding of its elements.
|
||||
The length-prefix is itself encoded as an `int`.
|
||||
|
||||
An empty slice is encoded as `0x00`. It is not length-prefixed.
|
||||
|
||||
Examples:
|
||||
|
||||
```
|
||||
encode([]int8{}) == [0x00]
|
||||
encode([]int8{1, 2, 3, 4}) == [0x01, 0x04, 0x01, 0x02, 0x03, 0x04]
|
||||
encode([]int16{1, 2, 3, 4}) == [0x01, 0x04, 0x00, 0x01, 0x00, 0x02, 0x00, 0x03, 0x00, 0x04]
|
||||
encode([]int{1, 2, 3, 4}) == [0x01, 0x04, 0x01, 0x01, 0x01, 0x02, 0x01, 0x03, 0x01, 0x4]
|
||||
|
|
|
@ -16,9 +16,11 @@ func main() {
|
|||
Break()
|
||||
encode(uint(6))
|
||||
encode(uint(70000))
|
||||
encode(int(0))
|
||||
encode(int(-6))
|
||||
encode(int(-70000))
|
||||
Break()
|
||||
encode("")
|
||||
encode("a")
|
||||
encode("hello")
|
||||
encode("¥")
|
||||
|
@ -28,6 +30,7 @@ func main() {
|
|||
encode([4]int{1, 2, 3, 4})
|
||||
encode([2]string{"abc", "efg"})
|
||||
Break()
|
||||
encode([]int8{})
|
||||
encode([]int8{1, 2, 3, 4})
|
||||
encode([]int16{1, 2, 3, 4})
|
||||
encode([]int{1, 2, 3, 4})
|
||||
|
|
Loading…
Reference in New Issue