From a19d5fbcae5bd39eaa72a6883898f895b868d66c Mon Sep 17 00:00:00 2001 From: t-bast Date: Wed, 11 Aug 2021 09:34:47 +0200 Subject: [PATCH 1/4] Peers need to check each other's dust limit Since HTLCs below this amount will not appear in the commitment tx, they are effectively converted to miner fees. The peer could use this to grief you by broadcasting its commitment once it contains a lot of dust HTLCs. Fixes #696 --- 02-peer-protocol.md | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/02-peer-protocol.md b/02-peer-protocol.md index b869f02a4..b781122d7 100644 --- a/02-peer-protocol.md +++ b/02-peer-protocol.md @@ -259,6 +259,7 @@ The receiving node MAY fail the channel if: - it considers `channel_reserve_satoshis` too large. - it considers `max_accepted_htlcs` too small. - it considers `dust_limit_satoshis` too small and plans to rely on the sending node publishing its commitment transaction in the event of a data loss (see [message-retransmission](02-peer-protocol.md#message-retransmission)). + - it considers `dust_limit_satoshis` too large. The receiving node MUST fail the channel if: - the `chain_hash` value is set to a hash of a chain that is unknown to the receiver. @@ -279,7 +280,7 @@ The receiving node MUST NOT: #### Rationale -The requirement for `funding_satoshis` to be less than 2^24 satoshi was a temporary self-imposed limit while implementations were not yet considered stable, it can be lifted by advertising `option_support_large_channel`. +The requirement for `funding_satoshis` to be less than 2^24 satoshi was a temporary self-imposed limit while implementations were not yet considered stable, it can be lifted by advertising `option_support_large_channel`. The *channel reserve* is specified by the peer's `channel_reserve_satoshis`: 1% of the channel total is suggested. Each side of a channel maintains this reserve so it always has something to lose if it were to try to broadcast an old, revoked commitment transaction. Initially, this reserve may not be met, as only one side has funds; but the protocol ensures that there is always progress toward meeting this reserve, and once met, it is maintained. @@ -295,6 +296,10 @@ would be eliminated as dust. The similar requirements in `accept_channel` ensure that both sides' `channel_reserve_satoshis` are above both `dust_limit_satoshis`. +The receiver should not accept large `dust_limit_satoshis`, as this could be +used in griefing attacks, where the peer publishes its commitment with a lot +of dust htlcs, which effectively become miner fees. + Details for how to handle a channel failure can be found in [BOLT 5:Failing a Channel](05-onchain.md#failing-a-channel). ### The `accept_channel` Message @@ -353,7 +358,6 @@ The receiver: - if `channel_type` is set, and `channel_type` was set in `open_channel`, and they are not equal types: - MUST reject the channel. - Other fields have the same requirements as their counterparts in `open_channel`. ### The `funding_created` Message From 7e3dce42cbe4fa4592320db6a4e06c26bb99122b Mon Sep 17 00:00:00 2001 From: t-bast Date: Wed, 18 Aug 2021 14:12:50 +0200 Subject: [PATCH 2/4] Add network dust thresholds As implemented in Bitcoin Core's default relay policy. --- 03-transactions.md | 108 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 108 insertions(+) diff --git a/03-transactions.md b/03-transactions.md index 29ce25552..22fb16fee 100644 --- a/03-transactions.md +++ b/03-transactions.md @@ -21,6 +21,8 @@ This details the exact format of on-chain transactions, which both sides need to * [Fees](#fees) * [Fee Calculation](#fee-calculation) * [Fee Payment](#fee-payment) + * [Dust Limits](#dust-limits) + * [Commitment Transaction Construction](#commitment-transaction-construction) * [Keys](#keys) * [Key Derivation](#key-derivation) * [`localpubkey`, `remotepubkey`, `local_htlcpubkey`, `remote_htlcpubkey`, `local_delayedpubkey`, and `remote_delayedpubkey` Derivation](#localpubkey-remotepubkey-local_htlcpubkey-remote_htlcpubkey-local_delayedpubkey-and-remote_delayedpubkey-derivation) @@ -484,6 +486,112 @@ A node: - if the resulting fee rate is too low: - MAY fail the channel. +## Dust Limits + +The `dust_limit_satoshis` parameter is used to configure the threshold below +which nodes will not produce on-chain transaction outputs. + +There is no consensus rule in Bitcoin that makes outputs below dust thresholds +invalid or unspendable, but policy rules in popular implementations will prevent +relaying transactions that contain such outputs. + +Bitcoin Core defines the following dust thresholds: + +- pay to pubkey hash (p2pkh): 546 satoshis +- pay to script hash (p2sh): 540 satoshis +- pay to witness pubkey hash (p2wpkh): 294 satoshis +- pay to witness script hash (p2wsh): 330 satoshis +- unknown segwit versions: 354 satoshis + +The rationale of this calculation (implemented [here](https://github.com/bitcoin/bitcoin/blob/0.21/src/policy/policy.cpp)) +is explained in the following sections. + +In all these sections, the calculations are done with a feerate of 3000 sat/kB +as per Bitcoin Core's implementation. + +### Pay to pubkey hash (p2pkh) + +A p2pkh output is 34 bytes: + +- 8 bytes for the output amount +- 1 byte for the script length +- 25 bytes for the script (`OP_DUP` `OP_HASH160` `20` 20-bytes `OP_EQUALVERIFY` `OP_CHECKSIG`) + +A p2pkh input is at least 148 bytes: + +- 36 bytes for the previous output (32 bytes hash + 4 bytes index) +- 1 byte for the script sig length +- 4 bytes for the sequence +- 107 bytes for the script sig: + - 1 byte for the items count + - 1 byte for the signature length + - 71 bytes for the signature + - 1 byte for the public key length + - 33 bytes for the public key + +The p2pkh dust threshold is then `(34 + 148) * 3000 / 1000 = 546 satoshis` + +### Pay to script hash (p2sh) + +A p2sh output is 32 bytes: + +- 8 bytes for the output amount +- 1 byte for the script length +- 23 bytes for the script (`OP_HASH160` `20` 20-bytes `OP_EQUAL`) + +A p2sh input doesn't have a fixed size, since it depends on the underlying +script, so we use 148 bytes as a lower bound. + +The p2sh dust threshold is then `(32 + 148) * 3000 / 1000 = 540 satoshis` + +### Pay to witness pubkey hash (p2wpkh) + +A p2wpkh output is 31 bytes: + +- 8 bytes for the output amount +- 1 byte for the script length +- 22 bytes for the script (`OP_0` `20` 20-bytes) + +A p2wpkh input is at least 67 bytes (depending on the signature length): + +- 36 bytes for the previous output (32 bytes hash + 4 bytes index) +- 1 byte for the script sig length +- 4 bytes for the sequence +- 26 bytes for the witness (with the 75% segwit discount applied): + - 1 byte for the items count + - 1 byte for the signature length + - 71 bytes for the signature + - 1 byte for the public key length + - 33 bytes for the public key + +The p2wpkh dust threshold is then `(31 + 67) * 3000 / 1000 = 294 satoshis` + +### Pay to witness script hash (p2wsh) + +A p2wsh output is 43 bytes: + +- 8 bytes for the output amount +- 1 byte for the script length +- 34 bytes for the script (`OP_0` `32` 32-bytes) + +A p2wsh input doesn't have a fixed size, since it depends on the underlying +script, so we use 67 bytes as a lower bound. + +The p2wsh dust threshold is then `(43 + 67) * 3000 / 1000 = 330 satoshis` + +### Unknown segwit versions + +Unknown segwit outputs are at most 51 bytes: + +- 8 bytes for the output amount +- 1 byte for the script length +- 42 bytes for the script (`OP_1` through `OP_16` inclusive, followed by a single push of 2 to 40 bytes) + +The input doesn't have a fixed size, since it depends on the underlying +script, so we use 67 bytes as a lower bound. + +The unknown segwit version dust threshold is then `(51 + 67) * 3000 / 1000 = 354 satoshis` + ## Commitment Transaction Construction This section ties the previous sections together to detail the From 9ff138715dea52858f6bdeb1b3d2f208a74157c5 Mon Sep 17 00:00:00 2001 From: t-bast Date: Tue, 14 Sep 2021 16:34:03 +0200 Subject: [PATCH 3/4] Drop non-segwit support in shutdown This allows dust limit to go as low as 354 sats without creating relay issues with default node policies. We add a requirement that dust limit cannot be lower than 354 sats. This ensures implementers don't have to figure this subtlety on their own. --- 02-peer-protocol.md | 29 +++++++++++++++++++---------- 1 file changed, 19 insertions(+), 10 deletions(-) diff --git a/02-peer-protocol.md b/02-peer-protocol.md index b781122d7..28a32ff45 100644 --- a/02-peer-protocol.md +++ b/02-peer-protocol.md @@ -258,7 +258,6 @@ The receiving node MAY fail the channel if: - it considers `max_htlc_value_in_flight_msat` too small. - it considers `channel_reserve_satoshis` too large. - it considers `max_accepted_htlcs` too small. - - it considers `dust_limit_satoshis` too small and plans to rely on the sending node publishing its commitment transaction in the event of a data loss (see [message-retransmission](02-peer-protocol.md#message-retransmission)). - it considers `dust_limit_satoshis` too large. The receiving node MUST fail the channel if: @@ -270,6 +269,7 @@ The receiving node MUST fail the channel if: - `funding_pubkey`, `revocation_basepoint`, `htlc_basepoint`, `payment_basepoint`, or `delayed_payment_basepoint` are not valid secp256k1 pubkeys in compressed format. - `dust_limit_satoshis` is greater than `channel_reserve_satoshis`. + - `dust_limit_satoshis` is smaller than `354 satoshis` (see [BOLT 3](03-transactions.md#dust-limits)). - the funder's amount for the initial commitment transaction is not sufficient for full [fee payment](03-transactions.md#fee-payment). - both `to_local` and `to_remote` amounts for the initial commitment transaction are less than or equal to `channel_reserve_satoshis` (see [BOLT 3](03-transactions.md#commitment-transaction-outputs)). - `funding_satoshis` is greater than or equal to 2^24 and the receiver does not support `option_support_large_channel`. @@ -547,12 +547,9 @@ A sending node: - MUST send the same value in `scriptpubkey`. - MUST set `scriptpubkey` in one of the following forms: - 1. `OP_DUP` `OP_HASH160` `20` 20-bytes `OP_EQUALVERIFY` `OP_CHECKSIG` - (pay to pubkey hash), OR - 2. `OP_HASH160` `20` 20-bytes `OP_EQUAL` (pay to script hash), OR - 3. `OP_0` `20` 20-bytes (version 0 pay to witness pubkey hash), OR - 4. `OP_0` `32` 32-bytes (version 0 pay to witness script hash), OR - 5. if (and only if) `option_shutdown_anysegwit` is negotiated: + 1. `OP_0` `20` 20-bytes (version 0 pay to witness pubkey hash), OR + 2. `OP_0` `32` 32-bytes (version 0 pay to witness script hash), OR + 3. if (and only if) `option_shutdown_anysegwit` is negotiated: * `OP_1` through `OP_16` inclusive, followed by a single push of 2 to 40 bytes (witness program versions 1 through 16) @@ -580,9 +577,11 @@ may immediately begin closing negotiation, so we ban further updates to the commitment transaction (in particular, `update_fee` would be possible otherwise). -The `scriptpubkey` forms include only standard forms accepted by the -Bitcoin network, which ensures the resulting transaction will -propagate to miners. +The `scriptpubkey` forms include only standard segwit forms accepted by +the Bitcoin network, which ensures the resulting transaction will +propagate to miners. However old nodes may send non-segwit scripts, which +may be accepted for backwards-compatibility (with a caveat to force-close +if this output doesn't meet dust relay requirements). The `option_upfront_shutdown_script` feature means that the node wanted to pre-commit to `shutdown_scriptpubkey` in case it was @@ -678,6 +677,10 @@ The receiving node: - MUST propose a value "strictly between" the received `fee_satoshis` and its previously-sent `fee_satoshis`. +The receiving node: + - if one of the outputs in the closing transaction is below the dust limit for its `scriptpubkey` (see [BOLT 3](03-transactions.md#dust-limits)): + - MUST fail the channel + #### Rationale When `fee_range` is not provided, the "strictly between" requirement ensures @@ -694,6 +697,12 @@ to have a maximum feerate. It may want a minimum feerate, however, to ensure that the transaction propagates. It can always use CPFP later to speed up confirmation if necessary, so that minimum should be low. +It may happen that the closing transaction doesn't meet bitcoin's default relay +policies (e.g. when using a non-segwit shutdown script for an output below 546 +satoshis, which is possible if `dust_limit_satoshis` is below 546 satoshis). +No funds are at risk when that happens, but the channel must be force-closed as +the closing transaction will likely never reach miners. + ## Normal Operation Once both nodes have exchanged `funding_locked` (and optionally [`announcement_signatures`](07-routing-gossip.md#the-announcement_signatures-message)), the channel can be used to make payments via Hashed Time Locked Contracts. From dff76b23e81a42184e861d7d7b996a81e578f206 Mon Sep 17 00:00:00 2001 From: t-bast Date: Wed, 22 Sep 2021 08:54:25 +0200 Subject: [PATCH 4/4] fixup! Add network dust thresholds --- 03-transactions.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/03-transactions.md b/03-transactions.md index 22fb16fee..af6590fd3 100644 --- a/03-transactions.md +++ b/03-transactions.md @@ -520,8 +520,8 @@ A p2pkh output is 34 bytes: A p2pkh input is at least 148 bytes: - 36 bytes for the previous output (32 bytes hash + 4 bytes index) -- 1 byte for the script sig length - 4 bytes for the sequence +- 1 byte for the script sig length - 107 bytes for the script sig: - 1 byte for the items count - 1 byte for the signature length @@ -555,9 +555,9 @@ A p2wpkh output is 31 bytes: A p2wpkh input is at least 67 bytes (depending on the signature length): - 36 bytes for the previous output (32 bytes hash + 4 bytes index) -- 1 byte for the script sig length - 4 bytes for the sequence -- 26 bytes for the witness (with the 75% segwit discount applied): +- 1 byte for the script sig length +- 26 bytes for the witness (rounded down from 26.75, with the 75% segwit discount applied): - 1 byte for the items count - 1 byte for the signature length - 71 bytes for the signature