-
Notifications
You must be signed in to change notification settings - Fork 282
LLR
Light Lachesis Repeater (LLR) is a non-BFT PoS auxiliary consensus algorithm which is interconnected with the Lachesis aBFT consensus algorithm.
The main purpose of LLR is to allow light stateless syncing, which Lachesis cannot offer.
LLR can be deployed only in conjunction with a BFT consensus algorithm.
Properties of the algorithm:
- LLR consensus finality cannot be overridden, assuming that less than
1/3W
of validators are Byzantine. Lachesis' finality is required to guarantee the property. - LLR consensus liveness cannot be halted if more than
1/3W
of validators are honest and online. Yet, Lachesis liveness is required for LLR liveness, which has a requirement of more than2/3W
of honest and online validators. - LLR and Lachesis share the same validators group in each epoch.
- Archiving finality for a block/epoch using LLR consensus has a complexity of
O(n)
operations and messages, wheren
is a number of validators in an epoch. In a base case scenario, it's proportional to a number of top1/3W+1
validators. - Published LLR doublesign/wrongsign cannot escape slashing unless passed more
than 32768 epochs since the message (
MaxLiableEpochs
) or validator (and his delegators) has withdrawn stake (7 days of delay) or Lachesis is censored. - LLR client must download and verify each epoch, but not necessarily each block. It's possible to download and verify only needed blocks.
- LLR votes are embedded into Lachesis consensus messages (LLR votes don't increase number of signatures to verify for Lachesis clients).
type LlrFullEpochRecord struct {
BlockState BlockState
EpochState EpochState
}
Epoch record contains all necessary information to process Lachesis events and blocks of the epoch, including EVM state root but excluding EVM state. In go-opera, this information is encapsulated into 2 structures - BlockState (updates in every block) and EpochState (updates in every epoch).
LLR depends on the following information from epoch record:
- Validators group of the epoch
- First block number of the epoch
This record is critical for snapsync, which needs it to:
- Obtain state root of a first block in the epoch for EVM state download
- Start Lachesis fullsync after EVM state download is complete
The record has a size of O(n)
, where n
is the number of validators in the epoch.
Epoch record may be processed either if it received 1/3W+1
votes or if it's included into genesis state.
type LlrEpochVote struct {
Epoch idx.Epoch
Vote hash.Hash
}
This message expresses the statement:
- Epoch record of
Epoch
has hash=Vote
Epoch vote for Epoch
is processed with weights pf validators group in Epoch-1
.
Thus, epoch vote may be processed only after epoch record for Epoch-1
was processed.
type LlrFullBlockRecord struct {
Atropos hash.Event
Root hash.Hash
Txs types.Transactions
Receipts []*types.ReceiptForStorage
Time inter.Timestamp
GasUsed uint64
}
Block record contains information about a block, where Root
is a state root after execution of the block.
Block record for block B+N
may be synced before block B
.
Block record may be processed either if it received 1/3W+1
votes or if it's included into genesis state.
type LlrBlockVotes struct {
Start idx.Block
Epoch idx.Epoch
Votes []hash.Hash
}
The message expresses 2 statements:
- Blocks
[Start, Start + len(Votes) - 1]
have the epoch=Epoch
- Blocks
[Start, Start + len(Votes) - 1]
have record hashes as inVotes
The message may contain up to 64 votes.
Start
must be not lower than blocks height in processed epoch record for Epoch
.
Start + len(Votes) - 1
must be smaller than MaxBlocksPerEpoch
+ blocks height in processed epoch record for Epoch
.
Block vote for Epoch
is processed with weights pf validators group in Epoch
.
Thus, block vote may be processed only after epoch record for Epoch
was processed.
- BlockVoteDoublesign [Pair of doublesigned block votes]:
This pair contains different record hashes for the same block from the same validator.
Epoch must be not older than
MaxLiableEpochs
. - WrongBlockVote (Record) [Pair of the same wrongsigned block votes (same record hashes) from different validators]:
"Wrong" means record hash doesn't match to Lachesis' on-chain valuem which is evaluated on-chain during MPs processing of a block.
It requires 2 votes from different validators to prevent slashing due to emitting a wrong vote after a singular hardware/software failure.
Epoch must be not older than
MaxLiableEpochs
. - WrongBlockVote (Epoch) [Pair of the same wrongsigned block votes (same epochs) from different validators]:
"Wrong" means vote's block epoch doesn't match to Lachesis' on-chain value, which is evaluated on-chain during MPs processing of a block.
It requires 2 votes from different validators to prevent slashing due to emitting a wrong vote after a singular hardware/software failure.
Epoch must be not older than
MaxLiableEpochs
. - EpochVoteDoublesign [Pair of doublesigned epoch votes]:
This pair contains different record hashes for the same epoch from the same validator.
Epoch must be not older than
MaxLiableEpochs
. - WrongEpochVote [Pair of the same wrongsigned epoch votes from different validators]:
"Wrong" means record hash doesn't match to Lachesis' on-chain value, which is evaluated on-chain during MPs processing of a block.
It requires 2 votes from different validators to prevent slashing due to emitting a wrong vote after a singular hardware/software failure.
Epoch must be not older than
MaxLiableEpochs
.
Similarly to DAG streams, LLR indexes all messages lexicographically and streams batches of continuous data from peers.
Epoch pack is a container of all epoch votes known by peer for the epoch and an epoch record.
Downloading of all messages (block votes, block records, and epoch votes/record combined into epoch pack) is done in parallel, with the following dependencies:
- Block votes are downloaded from
lowest non-decided block number
untillowest non-decided epoch number
(not including) - Block records are downloaded from
lowest non-downloaded block number
untillowest non-decided block number
(not including) - Epoch packs are downloaded from
min(lowest non-decided epoch, lowest non-downloaded epoch)
untilinfinity
An attacker may buy private keys of either:
- old validators who have already withdrawn stake
- active validators with a condition that misbehaviour will be done only in epochs which are at least
MaxLiableEpochs
old.
This way, the attacker will escape slashing by construction of the attack. Yet, it implies that misbehaviour is done in old epochs, which limits the damage:
- LLR voting is irreversible locally. Even if a different record hash gets more weight, node will continue to accept only the first confirmed record hash. Thus, this attack will affect only nodes that were syncing from scratch the affected epoch during or after the attack.
- Periodically recent epochs get included into new genesis files (more often than
MaxLiableEpochs
). If an attack will breach voting for a past epoch and node is syncing the said epoch for the first time, it won't affect the node if it uses a genesis file where the affected epoch is included into genesis state. - Epoch is allowed to contain no more than
MaxBlocksPerEpoch
blocks. Thus, it won't be possible to breach voting for a recent block by stating that it's a part of an old non-liable epoch.