lightningd: fix up BOLT references.

Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
Rusty Russell
2018-06-17 19:43:44 +09:30
committed by Christian Decker
parent ce4eef6943
commit e549bc6ecf
10 changed files with 185 additions and 147 deletions

View File

@@ -143,20 +143,21 @@ static void fail_out_htlc(struct htlc_out *hout, const char *localfail)
/* BOLT #4:
*
* * `amt_to_forward` - The amount in milli-satoshi to forward to the next
* (outgoing) hop specified within the routing information.
* * `amt_to_forward`: The amount, in millisatoshis, to forward to the next
* receiving peer specified within the routing information.
*
* This value MUST factor in the computed fee for this particular hop. When
* processing an incoming Sphinx packet along with the HTLC message it's
* encapsulated within, if the following inequality doesn't hold, then the
* HTLC should be rejected as it indicates a prior node in the path has
* deviated from the specified parameters:
* This value amount MUST include the origin node's computed _fee_ for the
* receiving peer. When processing an incoming Sphinx packet and the HTLC
* message that it is encapsulated within, if the following inequality
* doesn't hold, then the HTLC should be rejected as it would indicate that
* a prior hop has deviated from the specified parameters:
*
* incoming_htlc_amt - fee >= amt_to_forward
* incoming_htlc_amt - fee >= amt_to_forward
*
* Where `fee` is calculated according to the receiving node's advertised fee
* schema as described in [BOLT 7](https://github.com/lightningnetwork/lightning-rfc/blob/master/07-routing-gossip.md#htlc-fees), or 0 if this node is the
* final hop.
* Where `fee` is either calculated according to the receiving peer's
* advertised fee schema (as described in [BOLT
* #7](07-routing-gossip.md#htlc-fees)) or is 0, if the processing node is
* the final node.
*/
static bool check_amount(struct htlc_in *hin,
u64 amt_to_forward, u64 amt_in_htlc, u64 fee)
@@ -171,21 +172,22 @@ static bool check_amount(struct htlc_in *hin,
/* BOLT #4:
*
* * `outgoing_cltv_value` - The CLTV value that the _outgoing_ HTLC carrying
* * `outgoing_cltv_value`: The CLTV value that the _outgoing_ HTLC carrying
* the packet should have.
*
* cltv_expiry - cltv_expiry_delta >= outgoing_cltv_value
*
* Inclusion of this field allows a node to both authenticate the information
* specified by the original sender and the parameters of the HTLC forwarded,
* and ensure the original sender is using the current `cltv_expiry_delta` value.
* If there is no next hop, `cltv_expiry_delta` is zero.
* If the values don't correspond, then the HTLC should be failed+rejected as
* this indicates the incoming node has tampered with the intended HTLC
* values, or the origin has an obsolete `cltv_expiry_delta` value.
* The node MUST be consistent in responding to an unexpected
* `outgoing_cltv_value` whether it is the final hop or not, to avoid
* leaking that information.
* Inclusion of this field allows a hop to both authenticate the
* information specified by the origin node, and the parameters of the
* HTLC forwarded, and ensure the origin node is using the current
* `cltv_expiry_delta` value. If there is no next hop,
* `cltv_expiry_delta` is 0. If the values don't correspond, then the
* HTLC should be failed and rejected, as this indicates that either a
* forwarding node has tampered with the intended HTLC values or that the
* origin node has an obsolete `cltv_expiry_delta` value. The hop MUST be
* consistent in responding to an unexpected `outgoing_cltv_value`,
* whether it is the final node or not, to avoid leaking its position in
* the route.
*/
static bool check_cltv(struct htlc_in *hin,
u32 cltv_expiry, u32 outgoing_cltv_value, u32 delta)
@@ -241,13 +243,12 @@ static void handle_localpay(struct htlc_in *hin,
struct lightningd *ld = hin->key.channel->peer->ld;
/* BOLT #4:
*
* If the `amt_to_forward` is higher than `incoming_htlc_amt` of
* the HTLC at the final hop:
*
* 1. type: 19 (`final_incorrect_htlc_amount`)
* 2. data:
* * [`4`:`incoming_htlc_amt`]
*
* The amount in the HTLC doesn't match the value in the onion.
*/
if (!check_amount(hin, amt_to_forward, hin->msatoshi, 0)) {
failcode = WIRE_FINAL_INCORRECT_HTLC_AMOUNT;
@@ -255,13 +256,12 @@ static void handle_localpay(struct htlc_in *hin,
}
/* BOLT #4:
*
* If the `outgoing_cltv_value` does not match the `cltv_expiry` of
* the HTLC at the final hop:
*
* 1. type: 18 (`final_incorrect_cltv_expiry`)
* 2. data:
* * [`4`:`cltv_expiry`]
* * [`4`:`cltv_expiry`]
*
* The CLTV expiry in the HTLC doesn't match the value in the onion.
*/
if (!check_cltv(hin, cltv_expiry, outgoing_cltv_value, 0)) {
failcode = WIRE_FINAL_INCORRECT_CLTV_EXPIRY;
@@ -276,13 +276,17 @@ static void handle_localpay(struct htlc_in *hin,
/* BOLT #4:
*
* If the amount paid is less than the amount expected, the final node
* MUST fail the HTLC. If the amount paid is more than twice the
* amount expected, the final node SHOULD fail the HTLC. This allows
* the sender to reduce information leakage by altering the amount,
* without allowing accidental gross overpayment:
*
* 1. type: PERM|16 (`incorrect_payment_amount`)
* An _intermediate hop_ MUST NOT, but the _final node_:
*...
* - if the amount paid is less than the amount expected:
* - MUST fail the HTLC.
*...
* - if the amount paid is more than twice the amount expected:
* - SHOULD fail the HTLC.
* - SHOULD return an `incorrect_payment_amount` error.
* - Note: this allows the origin node to reduce information
* leakage by altering the amount while not allowing for
* accidental gross overpayment.
*/
if (details.msatoshi != NULL && hin->msatoshi < *details.msatoshi) {
failcode = WIRE_INCORRECT_PAYMENT_AMOUNT;
@@ -294,7 +298,9 @@ static void handle_localpay(struct htlc_in *hin,
/* BOLT #4:
*
* If the `cltv_expiry` is too low, the final node MUST fail the HTLC:
* - if the `cltv_expiry` value is unreasonably near the present:
* - MUST fail the HTLC.
* - MUST return a `final_expiry_too_soon` error.
*/
if (get_block_height(ld->topology) + ld->config.cltv_final
> cltv_expiry) {
@@ -444,10 +450,9 @@ static void forward_htlc(struct htlc_in *hin,
/* BOLT #7:
*
* The node creating `channel_update` SHOULD accept HTLCs which pay a
* fee equal or greater than:
*
* fee_base_msat + amount_msat * fee_proportional_millionths / 1000000
* The origin node:
* - SHOULD accept HTLCs that pay a fee equal to or greater than:
* - fee_base_msat + ( amount_msat * fee_proportional_millionths / 1000000 )
*/
if (mul_overflows_u64(amt_to_forward,
ld->config.fee_per_satoshi)) {
@@ -469,9 +474,10 @@ static void forward_htlc(struct htlc_in *hin,
/* BOLT #2:
*
* A node MUST estimate a timeout deadline for each HTLC it offers. A
* node MUST NOT offer an HTLC with a timeout deadline before its
* `cltv_expiry`
* An offering node:
* - MUST estimate a timeout deadline for each HTLC it offers.
* - MUST NOT offer an HTLC with a timeout deadline before its
* `cltv_expiry`.
*/
/* In our case, G = 1, so we need to expire it one after it's expiration.
* But never offer an expired HTLC; that's dumb. */
@@ -486,9 +492,8 @@ static void forward_htlc(struct htlc_in *hin,
/* BOLT #4:
*
* If the `cltv_expiry` is unreasonably far, we can also report an error:
*
* 1. type: 21 (`expiry_too_far`)
* - if the `cltv_expiry` is unreasonably far in the future:
* - return an `expiry_too_far` error.
*/
if (get_block_height(ld->topology)
+ ld->config.locktime_max < outgoing_cltv_value) {
@@ -587,8 +592,8 @@ static bool peer_accepted_htlc(struct channel *channel,
#endif
/* BOLT #2:
*
* A sending node SHOULD fail to route any HTLC added after it
* sent `shutdown`. */
* - SHOULD fail to route any HTLC added after it has sent `shutdown`.
*/
if (channel->state == CHANNELD_SHUTTING_DOWN) {
*failcode = WIRE_PERMANENT_CHANNEL_FAILURE;
goto out;
@@ -596,9 +601,11 @@ static bool peer_accepted_htlc(struct channel *channel,
/* BOLT #2:
*
* A node MUST estimate a fulfillment deadline for each HTLC it is
* attempting to fulfill. A node MUST fail (and not forward) an HTLC
* whose fulfillment deadline is already past
* A fulfilling node:
* - for each HTLC it is attempting to fulfill:
* - MUST estimate a fulfillment deadline.
* - MUST fail (and not forward) an HTLC whose fulfillment deadline is
* already past.
*/
/* Our deadline is half the cltv_delta we insist on, so this check is
* a subset of the cltv check done in handle_localpay and
@@ -1290,8 +1297,9 @@ void peer_got_revoke(struct channel *channel, const u8 *msg)
/* BOLT #2:
*
* A receiving node MAY fail if the `per_commitment_secret` was not
* generated by the protocol in [BOLT #3]
* - if the `per_commitment_secret` was not generated by the protocol
* in [BOLT #3](03-transactions.md#per-commitment-secret-requirements):
* - MAY fail the channel.
*/
if (!wallet_shachain_add_hash(ld->wallet,
&channel->their_shachain,
@@ -1491,9 +1499,9 @@ void free_htlcs(struct lightningd *ld, const struct channel *channel)
/* BOLT #2:
*
* For HTLCs we offer: the timeout deadline when we have to fail the channel
* and time it out on-chain. This is `G` blocks after the HTLC
* `cltv_expiry`; 1 block is reasonable.
* 2. the deadline for offered HTLCs: the deadline after which the channel has
* to be failed and timed out on-chain. This is `G` blocks after the HTLC's
* `cltv_expiry`: 1 block is reasonable.
*/
static u32 htlc_out_deadline(const struct htlc_out *hout)
{
@@ -1502,10 +1510,10 @@ static u32 htlc_out_deadline(const struct htlc_out *hout)
/* BOLT #2:
*
* For HTLCs we accept and have a preimage: the fulfillment deadline when we
* have to fail the channel and fulfill the HTLC onchain before its
* `cltv_expiry`. This is steps 4-7 above, which means a deadline of `2R+G+S`
* blocks before `cltv_expiry`; 7 blocks is reasonable.
* 3. the deadline for received HTLCs this node has fulfilled: the deadline
* after which the channel has to be failed and the HTLC fulfilled on-chain
* before its `cltv_expiry`. See steps 4-7 above, which imply a deadline of
* `2R+G+S` blocks before `cltv_expiry`: 7 blocks is reasonable.
*/
/* We approximate this, by using half the cltv_expiry_delta (3R+2G+2S),
* rounded up. */
@@ -1521,9 +1529,9 @@ void htlcs_notify_new_block(struct lightningd *ld, u32 height)
/* BOLT #2:
*
* A node ... MUST fail the channel if an HTLC which it offered is in
* either node's current commitment transaction past this timeout
* deadline.
* - if an HTLC which it offered is in either node's current
* commitment transaction, AND is past this timeout deadline:
* - MUST fail the channel.
*/
/* FIXME: use db to look this up in one go (earliest deadline per-peer) */
do {
@@ -1561,10 +1569,12 @@ void htlcs_notify_new_block(struct lightningd *ld, u32 height)
/* BOLT #2:
*
* A node MUST estimate a fulfillment deadline for each HTLC it is
* attempting to fulfill. A node ... MUST fail the connection if a
* HTLC it has fulfilled is in either node's current commitment
* transaction past this fulfillment deadline.
* - for each HTLC it is attempting to fulfill:
* - MUST estimate a fulfillment deadline.
*...
* - if an HTLC it has fulfilled is in either node's current commitment
* transaction, AND is past this fulfillment deadline:
* - MUST fail the connection.
*/
do {
struct htlc_in *hin;