Draft of Functions for Fork detection and Proof of Fork Submisstion
This document collects drafts of function for generating and submitting proof of fork in the IBC contextOn-chain IBC Component
The following is a suggestions to change the function defined in ICS 007
[TAG-IBC-MISBEHAVIOR.1]
- Implementation remark
- Expected precondition
- PoF.TrustedBlock.Header is equal to lightBlock on store with same height
- both traces end with header of same height
- headers are different
- both traces are supported by PoF.TrustedBlock (
supportsdefined in [CMBC-FUNC]), that is, fort = currentTimestamp()(see ICS 024)- supports(PoF.TrustedBlock, PoF.PrimaryTrace[1], t)
- supports(PoF.PrimaryTrace[i], PoF.PrimaryTrace[i+1], t) for 0 < i < length(PoF.PrimaryTrace)
- supports(PoF.TrustedBlock, PoF.SecondaryTrace[1], t)
- supports(PoF.SecondaryTrace[i], PoF.SecondaryTrace[i+1], t) for 0 < i < length(PoF.SecondaryTrace)
- Expected postcondition
- set cs.FrozenHeight to min(cs.FrozenHeight, PoF.TrustedBlock.Header.Height)
- Error condition
- none
The following is a suggestions to add functionality to ICS 002 and 007. I suppose the above is the most efficient way to get the required information. Another option is to subscribe to “header install” events via CosmosSDK
[TAG-IBC-HEIGHTS.1]
- Expected postcondition
- returns all heights h, with from <= h <= to for which the IBC component has a consensus state.
This function can be used if the relayer has no information about the IBC component. This allows late-joining relayers to also participate in fork dection and the generation in proof of fork. Alternatively, we may also postulate that relayers are not responsible to detect forks for heights before they started (and subscribed to the transactions reporting fresh headers being installed at the IBC component).
Relayer
Auxiliary Functions to be implemented in the Light Client
[LCV-LS-FUNC-GET-PREV.1]
- Expected postcondition
- returns a verified LightBlock, whose height is maximal among all
verified lightblocks with height smaller than
height
- returns a verified LightBlock, whose height is maximal among all
verified lightblocks with height smaller than
Relayer Submitting Proof of Fork to the IBC Component
There are two ways the relayer can detect a fork- by the fork detector of one of its lightclients
- be checking the consensus state of the IBC component
commonRoot) and compute a proof of fork
(extendPoF) that the IBC component will accept based on its
knowledge.
The auxiliary functions commonRoot and extendPoF are
defined below.
[TAG-SUBMIT-POF-IBC.1]
- Implementation remark
- Expected precondition
- Expected postcondition
- Error condition
- none
Auxiliary Functions at the Relayer
If the relayer detects a fork, it has to compute a proof of fork that will convince the IBC component. That is it has to compare the relayer’s local lightstore against the lightstore of the IBC component, and find common ancestor lightblocks.
[TAG-COMMON-ROOT.1]
- Expected postcondition
- returns
- a lightBlock b1 from the IBC component, and
- a lightBlock b2 from the local lightStore with height less than lblock.Header.Hight, s.t. b1 supports b2, and
- a lightstore with the blocks downloaded from the ibc component
- returns
[TAG-LS-FUNC-CONNECT.1]
- Expected postcondition
- returns a verified LightBlock from lightStore with height less than h that can be verified by lb in one step.
Once the common root is found, a proof of fork that will be accepted by the IBC component needs to be generated. This is done in the following function.
[TAG-EXTEND-POF.1]
- Implementation remark
- PoF is not sufficient to convince an IBC component, so we extend the proof of fork farther in the past
- Expected postcondition
- returns a newPOF:
- newPoF.TrustedBlock = root
- let prefix =
connector +
lightStore.Subtrace(connector.Header.Height, PoF.TrustedBlock.Header.Height-1) +
PoF.TrustedBlock
- newPoF.PrimaryTrace = prefix + PoF.PrimaryTrace
- newPoF.SecondaryTrace = prefix + PoF.SecondaryTrace
- returns a newPOF:
Detection a fork at the IBC component
The following functions is assumed to be called regularly to check that latest consensus state of the IBC component. Alternatively, this logic can be executed whenever the relayer is informed (via an event) that a new header has been installed.[TAG-HANDLER-DETECT-FORK.1]
- Implementation remark
- we ask the handler for the lastest check. Cross-check with the chain. In case they deviate we generate PoF.
- we assume IBC component is correct. It has verified the consensus state
- Expected precondition
- Expected postcondition