evidence

package
v0.34.0-rc2 Latest Latest
Warning

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

Go to latest
Published: Jul 30, 2020 License: Apache-2.0 Imports: 14 Imported by: 0

Documentation

Overview

Package evidence handles all evidence storage and gossiping from detection to block proposal. For the different types of evidence refer to the `evidence.go` file in the types package or https://github.com/tendermint/spec/blob/master/spec/consensus/light-client/accountability.md.

Gossiping

The core functionality begins with the evidence reactor (see reactor. go) which operates both the sending and receiving of evidence.

The `Receive` function takes a list of evidence and does the following:

1. Breaks it down into individual evidence if it is `Composite Evidence` (see types/evidence.go#ConflictingHeadersEvidence)

2. Checks that it does not already have the evidence stored

3. Verifies the evidence against the node's state (see state/validation.go#VerifyEvidence)

4. Stores the evidence to a db and a concurrent list

The gossiping of evidence is initiated when a peer is added which starts a go routine to broadcast currently uncommitted evidence at intervals of 60 seconds (set by the by broadcastEvidenceIntervalS). It uses a concurrent list to store the evidence and before sending verifies that each evidence is still valid in the sense that it has not exceeded the max evidence age and height (see types/params.go#EvidenceParams).

Three are four buckets that evidence can be stored in: Pending, Committed, Awaiting and POLC's.

1. Pending is awaiting to be committed (evidence is usually broadcasted then)

2. Committed is for those already on the block and is to ensure that evidence isn't submitted twice

3. AwaitingTrial primarily refers to PotentialAmnesiaEvidence which must wait for a trial period before being ready to be submitted (see docs/architecture/adr-056)

4. POLC's store all the ProofOfLockChanges that the node has done as part of consensus. To change lock is to vote for a different block in a later round. The consensus module calls `AddPOLC()` to add to this bucket.

All evidence is proto encoded to disk.

Proposing

When a new block is being proposed (in state/execution.go#CreateProposalBlock), `PendingEvidence(maxNum)` is called to send up to the maxNum number of uncommitted evidence, from the evidence store, prioritized in order of age. All evidence is checked for expiration.

When a node receives evidence in a block it will use the evidence module as a cache first to see if it has already verified the evidence before trying to verify it again.

Once the proposed evidence is submitted, the evidence is marked as committed and is moved from the broadcasted set to the committed set. As a result it is also removed from the concurrent list so that it is no longer gossiped.

Minor Functionality

As all evidence (including POLC's) are bounded by an expiration date, those that exceed this are no longer needed and hence pruned. Currently, only committed evidence in which a marker to the height that the evidence was committed and hence very small is saved. All updates are made from the `Update(block, state)` function which should be called when a new block is committed.

Index

Constants

View Source
const (
	EvidenceChannel = byte(0x38)
)

Variables

This section is empty.

Functions

This section is empty.

Types

type ErrInvalidEvidence added in v0.33.4

type ErrInvalidEvidence struct {
	Reason error
}

ErrInvalidEvidence returns when evidence failed to validate

func (ErrInvalidEvidence) Error added in v0.33.4

func (e ErrInvalidEvidence) Error() string

type PeerState

type PeerState interface {
	GetHeight() int64
}

PeerState describes the state of a peer.

type Pool added in v0.33.0

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

Pool maintains a pool of valid evidence to be broadcasted and committed

func NewPool added in v0.33.0

func NewPool(stateDB, evidenceDB dbm.DB, blockStore *store.BlockStore) (*Pool, error)

Creates a new pool. If using an existing evidence store, it will add all pending evidence to the concurrent list.

func (*Pool) AddEvidence added in v0.33.0

func (evpool *Pool) AddEvidence(evidence types.Evidence) error

AddEvidence checks the evidence is valid and adds it to the pool. If evidence is composite (ConflictingHeadersEvidence), it will be broken up into smaller pieces.

func (*Pool) AddPOLC

func (evpool *Pool) AddPOLC(polc *types.ProofOfLockChange) error

AddPOLC adds a proof of lock change to the evidence database that may be needed in the future to verify votes

func (*Pool) AllPendingEvidence

func (evpool *Pool) AllPendingEvidence() []types.Evidence

AllPendingEvidence returns all evidence ready to be proposed and committed.

func (*Pool) EvidenceFront added in v0.33.0

func (evpool *Pool) EvidenceFront() *clist.CElement

EvidenceFront goes to the first evidence in the clist

func (*Pool) EvidenceWaitChan added in v0.33.0

func (evpool *Pool) EvidenceWaitChan() <-chan struct{}

EvidenceWaitChan is a channel that closes once the first evidence in the list is there. i.e Front is not nil

func (*Pool) Has

func (evpool *Pool) Has(evidence types.Evidence) bool

Has checks whether the evidence exists either pending or already committed

func (*Pool) Header

func (evpool *Pool) Header(height int64) *types.Header

Header gets the header from the block store at a specified height. Is used for validation of LunaticValidatorEvidence

func (*Pool) IsCommitted added in v0.33.0

func (evpool *Pool) IsCommitted(evidence types.Evidence) bool

IsCommitted returns true if we have already seen this exact evidence and it is already marked as committed.

func (*Pool) IsEvidenceExpired

func (evpool *Pool) IsEvidenceExpired(evidence types.Evidence) bool

IsEvidenceExpired checks whether evidence is past the maximum age where it can be used

func (*Pool) IsExpired

func (evpool *Pool) IsExpired(height int64, time time.Time) bool

IsExpired checks whether evidence or a polc is expired by checking whether a height and time is older than set by the evidence consensus parameters

func (*Pool) IsOnTrial

func (evpool *Pool) IsOnTrial(evidence types.Evidence) bool

IsOnTrial checks whether a piece of evidence is in the awaiting bucket. Only Potential Amnesia Evidence is stored here.

func (*Pool) IsPending

func (evpool *Pool) IsPending(evidence types.Evidence) bool

IsPending checks whether the evidence is already pending. DB errors are passed to the logger.

func (*Pool) MarkEvidenceAsCommitted added in v0.33.0

func (evpool *Pool) MarkEvidenceAsCommitted(height int64, evidence []types.Evidence)

MarkEvidenceAsCommitted marks all the evidence as committed and removes it from the queue.

func (*Pool) PendingEvidence added in v0.33.0

func (evpool *Pool) PendingEvidence(maxNum uint32) []types.Evidence

PendingEvidence is used primarily as part of block proposal and returns up to maxNum of uncommitted evidence. If maxNum is -1, all evidence is returned. Pending evidence is prioritized based on time.

func (*Pool) RetrievePOLC

func (evpool *Pool) RetrievePOLC(height int64, round int32) (*types.ProofOfLockChange, error)

RetrievePOLC attempts to find a polc at the given height and round, if not there than exist returns false, all database errors are automatically logged

func (*Pool) SetLogger added in v0.33.0

func (evpool *Pool) SetLogger(l log.Logger)

SetLogger sets the Logger.

func (*Pool) State added in v0.33.0

func (evpool *Pool) State() sm.State

State returns the current state of the evpool.

func (*Pool) Update added in v0.33.0

func (evpool *Pool) Update(block *types.Block, state sm.State)

Update uses the latest block & state to update its copy of the state, validator to last height map and calls MarkEvidenceAsCommitted.

func (*Pool) ValidatorLastHeight

func (evpool *Pool) ValidatorLastHeight(address []byte) int64

ValidatorLastHeight returns the last height of the validator w/ the given address. 0 - if address never was a validator or was such a long time ago (> ConsensusParams.Evidence.MaxAgeDuration && > ConsensusParams.Evidence.MaxAgeNumBlocks).

type Reactor added in v0.33.0

type Reactor struct {
	p2p.BaseReactor
	// contains filtered or unexported fields
}

Reactor handles evpool evidence broadcasting amongst peers.

func NewReactor added in v0.33.0

func NewReactor(evpool *Pool) *Reactor

NewReactor returns a new Reactor with the given config and evpool.

func (*Reactor) AddPeer added in v0.33.0

func (evR *Reactor) AddPeer(peer p2p.Peer)

AddPeer implements Reactor.

func (*Reactor) GetChannels added in v0.33.0

func (evR *Reactor) GetChannels() []*p2p.ChannelDescriptor

GetChannels implements Reactor. It returns the list of channels for this reactor.

func (*Reactor) Receive added in v0.33.0

func (evR *Reactor) Receive(chID byte, src p2p.Peer, msgBytes []byte)

Receive implements Reactor. It adds any received evidence to the evpool.

func (*Reactor) SetEventBus added in v0.33.0

func (evR *Reactor) SetEventBus(b *types.EventBus)

SetEventBus implements events.Eventable.

func (*Reactor) SetLogger added in v0.33.0

func (evR *Reactor) SetLogger(l log.Logger)

SetLogger sets the Logger on the reactor and the underlying Evidence.

Jump to

Keyboard shortcuts

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