pub struct LightClient {
    pub peer: PeerId,
    pub options: Options,
    /* private fields */
}
Expand description

The light client implements a read operation of a header from the blockchain, by communicating with full nodes. As full nodes may be faulty, it cannot trust the received information, but the light client has to check whether the header it receives coincides with the one generated by Tendermint consensus.

In the Tendermint blockchain, the validator set may change with every new block. The staking and unbonding mechanism induces a security model: starting at time of the header, more than two-thirds of the next validators of a new block are correct for the duration of the trusted period. The fault-tolerant read operation is designed for this security model.

Fields§

§peer: PeerId

The peer id of the peer this client is connected to

§options: Options

Options for this light client

Implementations§

source§

impl LightClient

source

pub fn new( peer: PeerId, options: Options, clock: impl Clock + 'static, scheduler: impl Scheduler + 'static, verifier: impl Verifier + 'static, io: impl Io + 'static ) -> Self

Constructs a new light client

source

pub fn from_boxed( peer: PeerId, options: Options, clock: Box<dyn Clock>, scheduler: Box<dyn Scheduler>, verifier: Box<dyn Verifier>, io: Box<dyn Io> ) -> Self

Constructs a new light client from boxed components

source

pub fn verify_to_highest( &mut self, state: &mut State ) -> Result<LightBlock, Error>

Attempt to update the light client to the highest block of the primary node.

Note: This function delegates the actual work to verify_to_target.

source

pub fn verify_to_target( &self, target_height: Height, state: &mut State ) -> Result<LightBlock, Error>

Update the light client to a block of the primary node at the given height.

This is the main function and uses the following components:

  • The I/O component is called to fetch the next light block. It is the only component that communicates with other nodes.
  • The Verifier component checks whether a header is valid and checks if a new light block should be trusted based on a previously verified light block.
  • When doing forward verification, the Scheduler component decides which height to try to verify next, in case the current block pass verification but cannot be trusted yet.
  • When doing backward verification, the Hasher component is used to determine whether the last_block_id hash of a block matches the hash of the block right below it.
§Implements
  • [LCV-DIST-SAFE.1]
  • [LCV-DIST-LIFE.1]
  • [LCV-PRE-TP.1]
  • [LCV-POST-LS.1]
  • [LCV-INV-TP.1]
§Postcondition
  • The light store contains a light block that corresponds to a block of the blockchain of height target_height [LCV-POST-LS.1]
§Error conditions
  • The light store does not contains a trusted light block within the trusting period [LCV-PRE-TP.1]
  • If the core verification loop invariant is violated [LCV-INV-TP.1]
  • If verification of a light block fails
  • If the fetching a light block from the primary node fails
§Contracts

Post-condition: ret.is_ok() -> trusted_store_contains_block_at_target_height(state.light_store.as_ref(), target_height,)

source

pub fn get_or_fetch_block( &self, height: Height, state: &mut State ) -> Result<(LightBlock, Status), Error>

Look in the light store for a block from the given peer at the given height, which has not previously failed verification (ie. its status is not Failed).

If one cannot be found, fetch the block from the given peer and store it in the light store with Unverified status.

§Postcondition
  • The provider of block that is returned matches the given peer.
§Contracts

Post-condition: ret.as_ref().map(|(lb, _)| lb.provider == self.peer).unwrap_or(true)

source

pub fn get_target_block_or_latest( &mut self, height: Height, state: &mut State ) -> Result<TargetOrLatest, Error>

Get the block at the given height or the latest block from the chain if the given height is lower than the latest height.

Trait Implementations§

source§

impl Debug for LightClient

source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more

Auto Trait Implementations§

Blanket Implementations§

source§

impl<T> Any for T
where T: 'static + ?Sized,

source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
source§

impl<T> Borrow<T> for T
where T: ?Sized,

source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
source§

impl<T> From<T> for T

source§

fn from(t: T) -> T

Returns the argument unchanged.

source§

impl<T> Instrument for T

source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
source§

impl<T, U> Into<U> for T
where U: From<T>,

source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

§

impl<T> Pointable for T

§

const ALIGN: usize = _

The alignment of pointer.
§

type Init = T

The type for initializers.
§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
source§

impl<T> Same for T

§

type Output = T

Should always be Self
source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

§

type Error = Infallible

The type returned in the event of a conversion error.
source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

§

fn vzip(self) -> V

source§

impl<T> WithSubscriber for T

source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more