@ -13,7 +13,9 @@ The book is suitable for technical readers with an understanding of the fundamen
## Status
The current status of the book is "RELEASE PREP". See below for status of specific chapters and read the contribution guide to learn how and where to contribute.
The current status of the book is "IN PRODUCTION": ONLY COPY-EDIT CONTRIBUTIONS ARE ACCEPTED.
See below for status of specific chapters and read the contribution guide to learn how and where to contribute.
### Legend
@ -41,14 +43,17 @@ The current status of the book is "RELEASE PREP". See below for status of specif
= Brontide: Lightning's Encrypted Message Transport
[appendix]
[[brontide]]
[[encrypted_message_transport]]
== Lightning's Encrypted Message Transport (Brontide)
== Intro
In this chapter we will review the Lightning Network's _Encrypted Message Transport_, also known as the _Brontide Protocol_, which allows peers to establish end-to-end encrypted communication, authentication and integrity checking.
=== Introduction
Unlike the vanilla Bitcoin P2P network, every node in the Lightning Network is
identified by a unique public key which serves as it identity. By default, this
@ -18,7 +23,7 @@ custom encrypted message transport Lightning uses, commonly referred to as
"Brontide" (more on that later) can be dropped into any context that requires
encrypted communication between two parties.
== The Channel Graph as Decentralized Public Key Infrastructure
=== The Channel Graph as Decentralized Public Key Infrastructure
As we learned in the chapter on multi-hop forwarding, very node has a long-term
identity that is used as the identifier for a vertex during path finding and
@ -48,7 +53,7 @@ Lightning network is able to significantly simply its encrypted transport
protocol as it doesn't need to deal with all the complexities that come along
with TLS, the Transport Layer Security protocol.
== Why Not TLS?
=== Why Not TLS?
Readers familiar with the TLS system may be wondering at this point: why wasn't
TLS used in spite of the drawbacks of the existing PKI system? It is indeed a
@ -80,7 +85,7 @@ to continual scrutiny of the TLS protocol over decades. In a way, the existence
of Noise allows the community to effective "start over", with a more compact,
simplified protocol that retains all the added benefits of TLS.
== The Noise Protocol Framework
=== The Noise Protocol Framework
The Noise Protocol Framework is a modern, extensible, and flexible message
encryption protocol designed by the creators of the Signal protocol. The Signal
@ -114,7 +119,7 @@ Lightning Network, the flavor of Noise use will be referred to from here on as
"Brontide". A brontide is a low billowing noise, similar to what one would hear
during a thunderstorm when very far away.
=== Noise Protocol Handshakes
==== Noise Protocol Handshakes
The Noise protocol is extremely flexible in that it advertises several
handshakes, each with different security and privacy properties for a would be
@ -129,7 +134,7 @@ handshake. Instead, a clever series of Elliptic-Curve Diffie-Hellman (ECDH) and
Message Authentication Code (MAC) checks are used to authenticate the
responder.
=== Handshake Notation & Protocol Flow
==== Handshake Notation & Protocol Flow
Each handshakes typically consist of several steps. At each step some
(possibly) encrypted material is sent to the opposite party, an ECDH (or
@ -148,12 +153,12 @@ refer to a new ephemeral key. ECDH operations between two keys are notated as
the concatenation of two keys. As an example, `ee` represents an ECDH operation
between two ephemeral keys.
== Brontide: Lightning's P2P Encryption
=== Brontide: Lightning's P2P Encryption
=== High-Level Overview
==== High-Level Overview
Using the notation laid out earlier, we can succinctly describe the `Noise_XK`
as follows:
as follows:
```
Noise_XK(s, rs):
<- rs
@ -196,7 +201,7 @@ variant, the ASCII string is hashed into a digest, which is used to initialize
the starting handshake state. In the context of Brontide, the ASCII string
describing the protocol is: `Noise_XK_secp256k1_ChaChaPoly_SHA256`.
=== Brontide: A Handshake in Three Acts
==== Brontide: A Handshake in Three Acts
The handshake portion of Brontide can be see prated into three distinct "acts".
The entire handshake takes 1.5 round trips between the initiator and responder.
@ -229,7 +234,7 @@ functions that will operate on the handshake and messaging state. When
describing the handshake protocol, we'll use these variables in a manner
similar to pseudo-code in order to reduce the verbosity of the explanation of
each step in the protocol. We'll define the _functional_ primitives of the
handshake as:
handshake as:
* `ECDH(k, rk)`: performs an Elliptic-Curve Diffie-Hellman operation using
`k`, which is a valid `secp256k1` private key, and `rk`, which is a valid public key
@ -263,7 +268,7 @@ handshake as:
* `a || b` denotes the concatenation of two byte strings `a` and `b`
==== Handshake Session State Initialization
===== Handshake Session State Initialization
Before starting the handshake process, both sides need to initialize the
starting state that they'll use to advance the handshake process. To start,
@ -295,13 +300,13 @@ does indeed know the public key of the responder.
| `node_alias` | A 32-byte fixed-length byte slice. | When decoding, reject if contents are not a valid UTF-8 string.
| `channel_id` | A 32-byte fixed-length byte slice that maps an outpoint to a 32 byte value. | Given an outpoint, one can convert it to a `channel_id` by taking the txid of the outpoint and XOR'ing it with the index (interpreted as the lower 2 bytes).
| `short_chan_id` | An unsigned 64-bit integer (`uint64`) | Composed of the block height (24 bits), transaction index (24 bits), and output index (16 bits) packed into 8 bytes.
| `milli_satoshi` | An unsigned 64-bit integer (`uint64`) | Represents 1000th of a satoshi.
| `satoshi` | An unsigned 64-bit integer (`uint64`) | The based unit of bitcoin.
| `satoshi` | An unsigned 64-bit integer (`uint64`) | The based unit of bitcoin.
| `pubkey` | An secp256k1 public key encoded in _compressed_ format, occupying 33 bytes. | Occupies a fixed 33-byte length on the wire.
| High Level Type | Framing | Comment
| `node_alias` | A 32-byte fixed-length byte slice. | When decoding, reject if contents are not a valid UTF-8 string.
| `channel_id` | A 32-byte fixed-length byte slice that maps an outpoint to a 32 byte value. | Given an outpoint, one can convert it to a `channel_id` by taking the txid of the outpoint and XOR'ing it with the index (interpreted as the lower 2 bytes).
| `short_chan_id` | An unsigned 64-bit integer (`uint64`) | Composed of the block height (24 bits), transaction index (24 bits), and output index (16 bits) packed into 8 bytes.
| `milli_satoshi` | An unsigned 64-bit integer (`uint64`) | Represents 1000th of a satoshi.
| `satoshi` | An unsigned 64-bit integer (`uint64`) | The based unit of bitcoin.
| `satoshi` | An unsigned 64-bit integer (`uint64`) | The based unit of bitcoin.
| `pubkey` | An secp256k1 public key encoded in _compressed_ format, occupying 33 bytes. | Occupies a fixed 33-byte length on the wire.
| `sig` | An ECDSA signature of the secp256k1 Elliptic Curve. | Encoded as a _fixed_ 64-byte byte slice, packed as `R \|\| S`
| `uint8` | An 8-bit integer. |
| `uint16` | A 16-bit integer. |
| `uint64` | A 64-bit integer. |
| `[]byte` | A variable length byte slice. | Prefixed with a 16-bit integer denoting the length of the bytes.
| `color_rgb` | RGB color encoding. | Encoded as a series if 8-bit integers.
| `net_addr` | The encoding of a network address. | Encoded with a 1 byte prefix that denotes the type of address, followed by the address body.
| `[]byte` | A variable length byte slice. | Prefixed with a 16-bit integer denoting the length of the bytes.
| `color_rgb` | RGB color encoding. | Encoded as a series if 8-bit integers.
| `net_addr` | The encoding of a network address. | Encoded with a 1 byte prefix that denotes the type of address, followed by the address body.