Cleaned up queue section

This commit is contained in:
Ethan Frey 2018-02-13 20:20:22 +01:00 committed by Christopher Goes
parent cc17a3e963
commit 1feb84e272
No known key found for this signature in database
GPG Key ID: E828D98232D328D3
4 changed files with 55 additions and 265 deletions

Binary file not shown.

After

Width:  |  Height:  |  Size: 26 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 26 KiB

View File

@ -12,70 +12,22 @@ To build useful algorithms upon a provable asynchronous messaging primitive, we
Causal ordering means that if _x_ is causally before _y_ on chain A, it must also be on chain B. Many events may happen concurrently (unrelated tx on two different blockchains) with no causality relation, but every transaction on the same chain has a clear causality relation (same as the order in the blockchain).
Message passing implies a causal ordering over multiple chains and these can be important for reasoning on the system. Given _x _
Message passing implies a causal ordering over multiple chains and these can be important for reasoning on the system. Given _x_ → _y_ means _x_ is causally before _y_, and chains A and B, and _a_ ⇒ _b_ means _a_ implies _b_:
<p id="gdcalert18" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert19">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_A:send(msg<sub>i </sub>)_ &#8594; _B:receive(msg<sub>i </sub>)_
_ y_ means _x_ is causally before _y_, and chains A and B, and _a_
_B:receive(msg<sub>i </sub>)_ &#8594; _A:receipt(msg<sub>i </sub>)_
<p id="gdcalert19" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert20">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_A:send(msg<sub>i </sub>)_ &#8594; _A:send(msg<sub>i+1 </sub>)_
_b_ means _a_ implies _b_:
_x_ &#8594; _A:send(msg<sub>i </sub>)_ &#8658;
_x_ &#8594; _B:receive(msg<sub>i </sub>)_
_A:send(msg<sub>i </sub>)_
<p id="gdcalert20" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert21">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_ B:receive(msg<sub>i </sub>)_
_B:receive(msg<sub>i </sub>)_
<p id="gdcalert21" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert22">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_ A:receipt(msg<sub>i </sub>)_
_A:send(msg<sub>i </sub>)_
<p id="gdcalert22" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert23">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_A:send(msg<sub>i+1 </sub>)_
_x_
<p id="gdcalert23" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert24">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_A:send(msg<sub>i </sub>)_
<p id="gdcalert24" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert25">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_x_
<p id="gdcalert25" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert26">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_B:receive(msg<sub>i </sub>)_
_y_
<p id="gdcalert26" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert27">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_B:receive(msg<sub>i </sub>)_
<p id="gdcalert27" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert28">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_y_
<p id="gdcalert28" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert29">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_A:receipt(msg<sub>i </sub>)_
<p id="gdcalert29" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: inline image link here (to images/Cosmos-IBC0.png). Store image on your image server and adjust path/filename if necessary. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert30">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
![alt_text](images/Cosmos-IBC0.png "image_tooltip")
_y_ &#8594; _B:receive(msg<sub>i </sub>)_ &#8658;
_y_ &#8594; _A:receipt(msg<sub>i </sub>)_
![Vector Clock image](https://upload.wikimedia.org/wikipedia/commons/5/55/Vector_Clock.svg)
([https://en.wikipedia.org/wiki/Vector_clock](https://en.wikipedia.org/wiki/Vector_clock))
In this section, we define an efficient implementation of a secure, reliable messaging queue.
@ -88,37 +40,21 @@ We can visualize a queue as a slice pointing into an infinite sized array. It ma
**init**: _q<sub>head</sub> = q<sub>tail</sub> = 0_
**peek **
**peek** &#8658; **m**: _if q<sub>head</sub> = q<sub>tail</sub> { return None } else { return q[q<sub>head</sub>] }_
<p id="gdcalert30" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert31">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
**m**: _if q<sub>head</sub> = q<sub>tail</sub> { return None } else { return q[q<sub>head</sub>] }_
**pop **
<p id="gdcalert31" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert32">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
**m**: _if q<sub>head</sub> = q<sub>tail</sub> { return None } else { q<sub>head</sub>++; return q[q<sub>head</sub>-1] }_
**pop** &#8658; **m**: _if q<sub>head</sub> = q<sub>tail</sub> { return None } else { q<sub>head</sub>++; return q[q<sub>head</sub>-1] }_
**push(m)**: _q[q<sub>tail</sub>] = m; q<sub>tail</sub>++_
**advance(i)**: _q<sub>head</sub> = i; q<sub>tail</sub> = max(q<sub>tail </sub>, i)_
**head **
**head** &#8658; **i**: _q<sub>head</sub>_
<p id="gdcalert32" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert33">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
**i**: _q<sub>head</sub>_
**tail**
<p id="gdcalert33" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert34">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
**i**: _q<sub>tail</sub>_
**tail** &#8658; **i**: _q<sub>tail</sub>_
Based upon this needed functionality, we define a set of keys to be stored in the merkle tree, which allows us to efficiently implement and prove any of the above queries.
**Key:_ (queue name, [head|tail|index])_**
**Key:** _(queue name, [head|tail|index])_
The index is stored as a fixed-length unsigned integer in big endian format, so that the lexicographical order of the byte representation of the key is consistent with their sequence number. This allows us to quickly iterate over the queue, as well as prove the content of a packet (or lack of packet) at a given sequence. _head_ and _tail_ are two special constants that store an integer index, and are chosen such that their serialization cannot collide with any possible index.
@ -132,10 +68,10 @@ As mentioned above, in order for the receiver to unambiguously interpret the mer
The queue name must be unambiguously associated with a given connection to another chain, so an observer can prove if a message was intended for chain A or chain B. In order to do so, upon registration of a connection with a remote chain, we create two queues with different names (prefixes).
* _ibc:<chain id of A>:send_ - all outgoing packets destined to chain A
* _ibc:<chain id of A>:receipt_ - the results of executing the packets received from chain A
* _ibc:<chain id of A>:send_ - all outgoing packets destined to chain A
* _ibc:<chain id of A>:receipt_ - the results of executing the packets received from chain A
These two queues have different purposes and store messages of different types. By parsing the key of a merkle proof, a recipient can uniquely identify which queue, if any, this message belongs to. We now define _k =_ (_remote id, [send|receipt], index)_. This tuple is used to route and verify every message, before the contents of the packet are processed by the appropriate application logic.
These two queues have different purposes and store messages of different types. By parsing the key of a merkle proof, a recipient can uniquely identify which queue, if any, this message belongs to. We now define _k =_ _(remote id, [send|receipt], index)_. This tuple is used to route and verify every message, before the contents of the packet are processed by the appropriate application logic.
### 3.3 Message Contents
@ -151,86 +87,23 @@ _V<sub>receipt</sub> = (result, [success|error code])_
A proper implementation of IBC requires all relevant state to be encapsulated, so that other modules can only interact with it via a fixed API (to be defined in the next sections) rather than directly mutating internal state. This allows the IBC module to provide security guarantees.
Sending an IBC packet involves an application module calling the send method of the IBC module with a packet and a destination chain id. The IBC module must ensure that the destination chain was already properly registered, and that the calling module has permission to write this packet. If so, the IBC module simply pushes the packet to the tail of the _send_ _queue_, which enables all the proofs described above.
Sending an IBC packet involves an application module calling the send method of the IBC module with a packet and a destination chain id. The IBC module must ensure that the destination chain was already properly registered, and that the calling module has permission to write this packet. If so, the IBC module simply pushes the packet to the tail of the _send queue_, which enables all the proofs described above.
The permissioning of which module can write which packet can be defined per type, so this module can maintain any application-level invariants related to this area. Thus, the "coin" module can maintain the constant supply of tokens, while another module can maintain its own invariants, without IBC messages providing a means to escape their encapsulations. The IBC module must associate every supported message type with a particular handler (_f<sub>type</sub>_) and return an error for unsupported types.
_(IBCsend(D, type, data) _
<p id="gdcalert34" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert35">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_ Success)_
<p id="gdcalert35" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert36">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_ push(q<sub>D.send</sub> ,V<sub>send</sub>{type, data})_
_(IBCsend(D, type, data)_ &#8658; _Success)_
&#8658; _push(q<sub>D.send</sub> ,V<sub>send</sub>{type, data})_
We also consider how a given blockchain _A _is expected to receive the packet from a source chain _S_ with a merkle proof, given the current set of trusted headers for that chain, _T<sub>S</sub>_:
_A:IBCreceive(S, M<sub>k,v,h</sub>) _
<p id="gdcalert36" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert37">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_ match_
_q<sub>S.receipt</sub> =_
<p id="gdcalert37" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert38">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
<p id="gdcalert38" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert39">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("unregistered sender"), _
_ k = (_, reciept, _) _
<p id="gdcalert39" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert40">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("must be a send"),_
_ k = (d, _, _) and d _
<p id="gdcalert40" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert41">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_A_
<p id="gdcalert41" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert42">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("sent to a different chain"),_
_ k = (_, send, i) and head(q<sub>S.receipt</sub>) _
<p id="gdcalert42" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert43">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_i_
<p id="gdcalert43" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert44">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("out of order"),_
_ H<sub>h</sub> _
<p id="gdcalert44" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert45">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_T<sub>S</sub> _
<p id="gdcalert45" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert46">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("must submit header for height h"),_
_ valid(H<sub>h</sub> ,M<sub>k,v,h </sub>) = false _
<p id="gdcalert46" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert47">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("invalid merkle proof"),_
_ v = (type, data) _
<p id="gdcalert47" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert48">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_(result, err) :=f<sub>type</sub>(data); push(q<sub>S.receipt </sub>, (result, err)); Success _
_A:IBCreceive(S, M<sub>k,v,h</sub>)_ &#8658; _match_
* _q<sub>S.receipt</sub> =_ &#8709; &#8658; _Error("unregistered sender"),_
* _k = (\_, reciept, \_)_ &#8658; _Error("must be a send"),_
* _k = (d, \_, \_) and d_ &#8800; _A_ &#8658; _Error("sent to a different chain"),_
* _k = (\_, send, i) and head(q<sub>S.receipt</sub>)_ &#8800; _i_ &#8658; _Error("out of order"),_
* _H<sub>h</sub>_ &#8713; _T<sub>S</sub>_ &#8658; _Error("must submit header for height h"),_
* _valid(H<sub>h</sub> ,M<sub>k,v,h </sub>) = false_ &#8658; _Error("invalid merkle proof"),_
* _v = (type, data)_ &#8658; _(result, err) := f<sub>type</sub>(data); push(q<sub>S.receipt </sub>, (result, err)); Success_
Note that this requires not only an valid proof, but also that the proper header as well as all prior messages were previously submitted. This returns success upon accepting a proper message, even if the message execution returned an error (which must then be relayed to the sender).
@ -240,98 +113,22 @@ When we wish to create a transaction that atomically commits or rolls back acros
To do this requires that we not only provable send a message from chain A to chain B, but provably return the result of that message (the receipt) from chain B to chain A. As one noticed above in the implementation of _IBCreceive_, if the valid IBC message was sent from A to B, then the result of executing it, even if it was an error, is stored in _B:q<sub>A.receipt</sub>_. Since the receipts are stored in a queue with the same key construction as the sending queue, we can generate the same set of proofs for them, and perform a similar sequence of steps to handle a receipt coming back to _S_ for a message previously sent to _A_:
_S:IBCreceipt(A, M<sub>k,v,h</sub>) _
<p id="gdcalert48" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert49">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_ match_
_q<sub>A.send</sub> =_
<p id="gdcalert49" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert50">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
<p id="gdcalert50" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert51">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("unregistered sender"), _
_ k = (_, send, _) _
<p id="gdcalert51" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert52">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("must be a recipient"),_
_ k = (d, _, _) and d _
<p id="gdcalert52" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert53">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_S_
<p id="gdcalert53" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert54">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("sent to a different chain"),_
_H<sub>h</sub> _
<p id="gdcalert54" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert55">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_T<sub>A</sub> _
<p id="gdcalert55" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert56">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("must submit header for height h"),_
_ not valid(H<sub>h</sub> ,M<sub>k,v,h </sub>) _
<p id="gdcalert56" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert57">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("invalid merkle proof"),_
_ k = (_, receipt, head|tail)_
<p id="gdcalert57" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert58">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("only accepts message proofs"),_
_ k = (_, receipt, i) and head(q<sub>S.send</sub>) _
<p id="gdcalert58" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert59">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_i_
<p id="gdcalert59" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert60">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_Error("out of order"),_
_ v = (_, error) _
<p id="gdcalert60" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert61">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_(type, data) := pop(q<sub>S.send </sub>); rollback<sub>type</sub>(data); Success_
_ v = (res, success) _
<p id="gdcalert61" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: equation: use MathJax/LaTeX if your publishing platform supports it. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert62">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
_(type, data) := pop(q<sub>S.send </sub>); commit<sub>type</sub>(data, res); Success_
_S:IBCreceipt(A, M<sub>k,v,h</sub>)_ &#8658; _match_
* _q<sub>A.send</sub> =_ &#8709; &#8658; _Error("unregistered sender"), _
* _k = (\_, send, \_)_ &#8658; _Error("must be a recipient"),_
* _k = (d, \_, \_) and d_ &#8800; _S_ &#8658; _Error("sent to a different chain"),_
* _H<sub>h</sub>_ &#8713; _T<sub>A</sub>_ &#8658; _Error("must submit header for height h"),_
* _not valid(H<sub>h </sub>, M<sub>k,v,h </sub>)_ &#8658; _Error("invalid merkle proof"),_
* _k = (\_, receipt, head|tail)_ &#8658; _Error("only accepts message proofs"),_
* _k = (\_, receipt, i) and head(q<sub>S.send</sub>)_ &#8800; _i_ &#8658; _Error("out of order"),_
* _v = (\_, error)_ &#8658; _(type, data) := pop(q<sub>S.send </sub>); rollback<sub>type</sub>(data); Success_
* _v = (res, success)_ &#8658; _(type, data) := pop(q<sub>S.send </sub>); commit<sub>type</sub>(data, res); Success_
This enforces that the receipts are processed in order, to allow some the application to make use of some basic assumptions about ordering. It also removes the message from the send queue, as there is now proof it was processed on the receiving chain and there is no more need to store this information.
![Successful Transaction](images/Receipts.png)
<p id="gdcalert62" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: inline image link here (to images/Cosmos-IBC1.png). Store image on your image server and adjust path/filename if necessary. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert63">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
![alt_text](images/Cosmos-IBC1.png "image_tooltip")
<p id="gdcalert63" ><span style="color: red; font-weight: bold">>>>>> gd2md-html alert: inline image link here (to images/Cosmos-IBC2.png). Store image on your image server and adjust path/filename if necessary. </span><br>(<a href="#">Back to top</a>)(<a href="#gdcalert64">Next alert</a>)<br><span style="color: red; font-weight: bold">>>>>> </span></p>
![alt_text](images/Cosmos-IBC2.png "image_tooltip")
![Rejected Transaction](images/ReceiptError.png)
### 3.6 Relay Process
@ -342,27 +139,19 @@ The relay process must have access to accounts on both chains with sufficient ba
As an example, here is a naive algorithm for relaying send messages from A to B, without error handling. We must also concurrently run the relay of receipts from B back to A, in order to complete the cycle. Note that all reads of variables belonging to a chain imply queries and all function calls imply submitting a transaction to the blockchain.
_while true_
_ pending := tail(A:q<sub>B.send</sub>)_
_ received := tail(B:q<sub>A.receive</sub>)_
_ if pending > received_
_ U<sub>h</sub> := A:latestHeader_
_ B:updateHeader(U<sub>h</sub>)_
_ for i :=received...pending_
_ k := (B, send, i)_
_ packet := A:M<sub>k,v,h</sub>_
_ B:IBCreceive(A, packet)_
_ sleep(desiredLatency)_
```
while true
pending := tail(A:q<sub>B.send</sub>)
received := tail(B:q<sub>A.receive</sub>)
if pending > received
U<sub>h</sub> := A:latestHeader
B:updateHeader(U<sub>h</sub>)
for i :=received...pending
k := (B, send, i)
packet := A:M<sub>k,v,h</sub>
B:IBCreceive(A, packet)
sleep(desiredLatency)
```
Note that updating a header is a costly transaction compared to posting a merkle proof for a known header. Thus, a process could wait until many messages are pending, then submit one header along with multiple merkle proofs, rather than a separate header for each message. This decreases total computation cost (and fees) at the price of additional latency and is a trade-off each relay can dynamically adjust.

View File

@ -10,7 +10,8 @@ This paper specifies the IBC (inter blockchain communication) protocol, which wa
Each chain maintains a local partial order, while inter-chain messages track any cross-chain causality relations. Once two chains have registered a trust relationship, cryptographically provable packets can be securely sent between the chains, using Tendermint's instant finality for quick and efficient transmission.
We currently use this protocol for secure value transfer in the Cosmos Hub, but the protocol can support arbitrary application logic. Details of how Cosmos Hub uses IBC to securely route and transfer value are provided in a separate paper, along with a framework for expressing global invariants. Designing secure communication logic for other types of applications is still an area of research.
We currently use this protocol for secure value transfer in the Cosmos Hub, but the protocol can support arbitrary application logic. Details of how Cosmos Hub uses IBC to securely route and transfer value ar
e provided in a separate paper, along with a framework for expressing global invariants. Designing secure communication logic for other types of applications is still an area of research.
The protocol makes no assumptions of block times or network delays in the transmission of the packets between chains and requires cryptographic proofs for every message, and thus is highly robust in a heterogeneous environment with Byzantine actors. This paper explains the requirements and structure of the Cosmos IBC protocol. It aims to provide enough detail to fully understand and analyze the security of the protocol.