Skip to content

Commit 7c25fb0

Browse files
author
Antoine Riard
committed
-f Add HOLDER_DUST_LIMIT_SATOSHIS
1 parent 944cdaf commit 7c25fb0

File tree

4 files changed

+19
-31
lines changed

4 files changed

+19
-31
lines changed

fuzz/src/full_stack.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -347,7 +347,6 @@ pub fn do_test(data: &[u8], logger: &Arc<dyn Logger>) {
347347
let mut config = UserConfig::default();
348348
config.channel_options.fee_proportional_millionths = slice_to_be32(get_slice!(4));
349349
config.channel_options.announced_channel = get_slice!(1)[0] != 0;
350-
config.peer_channel_config_limits.min_dust_limit_satoshis = 0;
351350
let network = Network::Bitcoin;
352351
let genesis_hash = genesis_block(network).block_hash();
353352
let params = ChainParameters {

lightning/src/ln/channel.rs

Lines changed: 18 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -429,7 +429,6 @@ pub const OUR_MAX_HTLCS: u16 = 50; //TODO
429429
/// really allow for this, so instead we're stuck closing it out at that point.
430430
const UNCONF_THRESHOLD: u32 = 6;
431431
const SPENDING_INPUT_FOR_A_OUTPUT_WEIGHT: u64 = 79; // prevout: 36, nSequence: 4, script len: 1, witness lengths: (3+1)/4, sig: 73/4, if-selector: 1, redeemScript: (6 ops + 2*33 pubkeys + 1*2 delay)/4
432-
const B_OUTPUT_PLUS_SPENDING_INPUT_WEIGHT: u64 = 104; // prevout: 40, nSequence: 4, script len: 1, witness lengths: 3/4, sig: 73/4, pubkey: 33/4, output: 31 (TODO: Wrong? Useless?)
433432

434433
#[cfg(not(test))]
435434
const COMMITMENT_TX_BASE_WEIGHT: u64 = 724;
@@ -454,6 +453,12 @@ pub const MAX_FUNDING_SATOSHIS: u64 = 1 << 24;
454453
/// upper bound to avoid negotiation conflicts with other implementations.
455454
pub const MAX_DUST_LIMIT_SATOSHIS: u64 = 2 * 330;
456455

456+
/// A typical p2wsh output is 43 bytes big to which Core's `GetDustThreshold()` sums up a minimal
457+
/// spend of 67 bytes (even if a p2wsh witnessScript might be *effectively* smaller), `dustRelayFee`
458+
/// is set to 3000sat/kb, thus 110 * 3000 / 1000 = 330. Per-protocol rules, all time-sensitive outputs
459+
/// are p2wsh, a value of 330 sats is the lower bound desired to ensure good propagation of transactions.
460+
pub const HOLDER_DUST_LIMIT_SATOSHIS: u64 = 330;
461+
457462
/// Used to return a simple Error back to ChannelManager. Will get converted to a
458463
/// msgs::ErrorAction::SendErrorMessage or msgs::ErrorAction::IgnoreError as appropriate with our
459464
/// channel_id in ChannelManager.
@@ -497,10 +502,6 @@ impl<Signer: Sign> Channel<Signer> {
497502
cmp::min(channel_value_satoshis, cmp::max(q, 1000)) //TODO
498503
}
499504

500-
fn derive_holder_dust_limit_satoshis(at_open_background_feerate: u32) -> u64 {
501-
cmp::max(at_open_background_feerate as u64 * B_OUTPUT_PLUS_SPENDING_INPUT_WEIGHT / 1000, 546) //TODO
502-
}
503-
504505
// Constructors:
505506
pub fn new_outbound<K: Deref, F: Deref>(fee_estimator: &F, keys_provider: &K, counterparty_node_id: PublicKey, channel_value_satoshis: u64, push_msat: u64, user_id: u64, config: &UserConfig) -> Result<Channel<Signer>, APIError>
506507
where K::Target: KeysInterface<Signer = Signer>,
@@ -521,7 +522,7 @@ impl<Signer: Sign> Channel<Signer> {
521522
return Err(APIError::APIMisuseError {err: format!("Configured with an unreasonable our_to_self_delay ({}) putting user funds at risks", holder_selected_contest_delay)});
522523
}
523524
let background_feerate = fee_estimator.get_est_sat_per_1000_weight(ConfirmationTarget::Background);
524-
if Channel::<Signer>::get_holder_selected_channel_reserve_satoshis(channel_value_satoshis) < Channel::<Signer>::derive_holder_dust_limit_satoshis(background_feerate) {
525+
if Channel::<Signer>::get_holder_selected_channel_reserve_satoshis(channel_value_satoshis) < HOLDER_DUST_LIMIT_SATOSHIS {
525526
return Err(APIError::FeeRateTooHigh{err: format!("Not enough reserve above dust limit can be found at current fee rate({})", background_feerate), feerate: background_feerate});
526527
}
527528

@@ -579,7 +580,7 @@ impl<Signer: Sign> Channel<Signer> {
579580

580581
feerate_per_kw: feerate,
581582
counterparty_dust_limit_satoshis: 0,
582-
holder_dust_limit_satoshis: Channel::<Signer>::derive_holder_dust_limit_satoshis(background_feerate),
583+
holder_dust_limit_satoshis: HOLDER_DUST_LIMIT_SATOSHIS,
583584
counterparty_max_htlc_value_in_flight_msat: 0,
584585
counterparty_selected_channel_reserve_satoshis: 0,
585586
counterparty_htlc_minimum_msat: 0,
@@ -697,8 +698,8 @@ impl<Signer: Sign> Channel<Signer> {
697698
if msg.max_accepted_htlcs < config.peer_channel_config_limits.min_max_accepted_htlcs {
698699
return Err(ChannelError::Close(format!("max_accepted_htlcs ({}) is less than the user specified limit ({})", msg.max_accepted_htlcs, config.peer_channel_config_limits.min_max_accepted_htlcs)));
699700
}
700-
if msg.dust_limit_satoshis < config.peer_channel_config_limits.min_dust_limit_satoshis {
701-
return Err(ChannelError::Close(format!("dust_limit_satoshis ({}) is less than the user specified limit ({})", msg.dust_limit_satoshis, config.peer_channel_config_limits.min_dust_limit_satoshis)));
701+
if msg.dust_limit_satoshis < HOLDER_DUST_LIMIT_SATOSHIS {
702+
return Err(ChannelError::Close(format!("dust_limit_satoshis ({}) is less than the user specified limit ({})", msg.dust_limit_satoshis, HOLDER_DUST_LIMIT_SATOSHIS)));
702703
}
703704
if msg.dust_limit_satoshis > MAX_DUST_LIMIT_SATOSHIS {
704705
return Err(ChannelError::Close(format!("dust_limit_satoshis ({}) is greater than the implementation limit ({})", msg.dust_limit_satoshis, MAX_DUST_LIMIT_SATOSHIS)));
@@ -717,13 +718,12 @@ impl<Signer: Sign> Channel<Signer> {
717718

718719
let background_feerate = fee_estimator.get_est_sat_per_1000_weight(ConfirmationTarget::Background);
719720

720-
let holder_dust_limit_satoshis = Channel::<Signer>::derive_holder_dust_limit_satoshis(background_feerate);
721721
let holder_selected_channel_reserve_satoshis = Channel::<Signer>::get_holder_selected_channel_reserve_satoshis(msg.funding_satoshis);
722-
if holder_selected_channel_reserve_satoshis < holder_dust_limit_satoshis {
723-
return Err(ChannelError::Close(format!("Suitable channel reserve not found. remote_channel_reserve was ({}). dust_limit_satoshis is ({}).", holder_selected_channel_reserve_satoshis, holder_dust_limit_satoshis)));
722+
if holder_selected_channel_reserve_satoshis < HOLDER_DUST_LIMIT_SATOSHIS {
723+
return Err(ChannelError::Close(format!("Suitable channel reserve not found. remote_channel_reserve was ({}). dust_limit_satoshis is ({}).", holder_selected_channel_reserve_satoshis, HOLDER_DUST_LIMIT_SATOSHIS)));
724724
}
725-
if msg.channel_reserve_satoshis < holder_dust_limit_satoshis {
726-
return Err(ChannelError::Close(format!("channel_reserve_satoshis ({}) is smaller than our dust limit ({})", msg.channel_reserve_satoshis, holder_dust_limit_satoshis)));
725+
if msg.channel_reserve_satoshis < HOLDER_DUST_LIMIT_SATOSHIS {
726+
return Err(ChannelError::Close(format!("channel_reserve_satoshis ({}) is smaller than our dust limit ({})", msg.channel_reserve_satoshis, HOLDER_DUST_LIMIT_SATOSHIS)));
727727
}
728728
if holder_selected_channel_reserve_satoshis < msg.dust_limit_satoshis {
729729
return Err(ChannelError::Close(format!("Dust limit ({}) too high for the channel reserve we require the remote to keep ({})", msg.dust_limit_satoshis, holder_selected_channel_reserve_satoshis)));
@@ -815,7 +815,7 @@ impl<Signer: Sign> Channel<Signer> {
815815
feerate_per_kw: msg.feerate_per_kw,
816816
channel_value_satoshis: msg.funding_satoshis,
817817
counterparty_dust_limit_satoshis: msg.dust_limit_satoshis,
818-
holder_dust_limit_satoshis,
818+
holder_dust_limit_satoshis: HOLDER_DUST_LIMIT_SATOSHIS,
819819
counterparty_max_htlc_value_in_flight_msat: cmp::min(msg.max_htlc_value_in_flight_msat, msg.funding_satoshis * 1000),
820820
counterparty_selected_channel_reserve_satoshis: msg.channel_reserve_satoshis,
821821
counterparty_htlc_minimum_msat: msg.htlc_minimum_msat,
@@ -1436,8 +1436,8 @@ impl<Signer: Sign> Channel<Signer> {
14361436
if msg.max_accepted_htlcs < config.peer_channel_config_limits.min_max_accepted_htlcs {
14371437
return Err(ChannelError::Close(format!("max_accepted_htlcs ({}) is less than the user specified limit ({})", msg.max_accepted_htlcs, config.peer_channel_config_limits.min_max_accepted_htlcs)));
14381438
}
1439-
if msg.dust_limit_satoshis < config.peer_channel_config_limits.min_dust_limit_satoshis {
1440-
return Err(ChannelError::Close(format!("dust_limit_satoshis ({}) is less than the user specified limit ({})", msg.dust_limit_satoshis, config.peer_channel_config_limits.min_dust_limit_satoshis)));
1439+
if msg.dust_limit_satoshis < HOLDER_DUST_LIMIT_SATOSHIS {
1440+
return Err(ChannelError::Close(format!("dust_limit_satoshis ({}) is less than the user specified limit ({})", msg.dust_limit_satoshis, HOLDER_DUST_LIMIT_SATOSHIS)));
14411441
}
14421442
if msg.dust_limit_satoshis > MAX_DUST_LIMIT_SATOSHIS {
14431443
return Err(ChannelError::Close(format!("dust_limit_satoshis ({}) is greater than the implementation limit ({})", msg.dust_limit_satoshis, MAX_DUST_LIMIT_SATOSHIS)));
@@ -4818,14 +4818,14 @@ mod tests {
48184818
// Create Node B's channel by receiving Node A's open_channel message
48194819
// Make sure A's dust limit is as we expect.
48204820
let open_channel_msg = node_a_chan.get_open_channel(genesis_block(network).header.block_hash());
4821-
assert_eq!(open_channel_msg.dust_limit_satoshis, 1560);
48224821
let node_b_node_id = PublicKey::from_secret_key(&secp_ctx, &SecretKey::from_slice(&[7; 32]).unwrap());
48234822
let node_b_chan = Channel::<EnforcingSigner>::new_from_req(&&feeest, &&keys_provider, node_b_node_id, InitFeatures::known(), &open_channel_msg, 7, &config).unwrap();
48244823

48254824
// Node B --> Node A: accept channel, explicitly setting B's dust limit.
48264825
let mut accept_channel_msg = node_b_chan.get_accept_channel();
48274826
accept_channel_msg.dust_limit_satoshis = 546;
48284827
node_a_chan.accept_channel(&accept_channel_msg, &config, InitFeatures::known()).unwrap();
4828+
node_a_chan.holder_dust_limit_satoshis = 1560;
48294829

48304830
// Put some inbound and outbound HTLCs in A's channel.
48314831
let htlc_amount_msat = 11_092_000; // put an amount below A's effective dust limit but above B's.

lightning/src/ln/functional_tests.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1793,7 +1793,7 @@ fn test_chan_reserve_dust_inbound_htlcs_outbound_chan() {
17931793
// transaction fee with 0 HTLCs (183 sats)).
17941794
create_announced_chan_between_nodes_with_value(&nodes, 0, 1, 100000, 98817000, InitFeatures::known(), InitFeatures::known());
17951795

1796-
let dust_amt = 546000; // Dust amount
1796+
let dust_amt = 329000; // Dust amount
17971797
// In the previous code, routing this dust payment would cause nodes[0] to perceive a channel
17981798
// reserve violation even though it's a dust HTLC and therefore shouldn't count towards the
17991799
// commitment transaction fee.

lightning/src/util/config.rs

Lines changed: 0 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -95,16 +95,6 @@ pub struct ChannelHandshakeLimits {
9595
///
9696
/// Default value: 0.
9797
pub min_max_accepted_htlcs: u16,
98-
/// Outputs below a certain value will not be added to on-chain transactions. The dust value is
99-
/// required to always be higher than this value so this only applies to HTLC outputs (and
100-
/// potentially to-self outputs before any payments have been made).
101-
/// Thus, HTLCs below this amount plus HTLC transaction fees are not enforceable on-chain.
102-
/// This setting allows you to set a minimum dust limit for their commitment transactions,
103-
/// reflecting the reality that tiny outputs are not considered standard transactions and will
104-
/// not propagate through the Bitcoin network.
105-
///
106-
/// Default value: 546, the current dust limit on the Bitcoin network.
107-
pub min_dust_limit_satoshis: u64,
10898
/// Before a channel is usable the funding transaction will need to be confirmed by at least a
10999
/// certain number of blocks, specified by the node which is not the funder (as the funder can
110100
/// assume they aren't going to double-spend themselves).
@@ -136,7 +126,6 @@ impl Default for ChannelHandshakeLimits {
136126
min_max_htlc_value_in_flight_msat: 0,
137127
max_channel_reserve_satoshis: <u64>::max_value(),
138128
min_max_accepted_htlcs: 0,
139-
min_dust_limit_satoshis: 546,
140129
max_minimum_depth: 144,
141130
force_announced_channel_preference: true,
142131
their_to_self_delay: MAX_LOCAL_BREAKDOWN_TIMEOUT,

0 commit comments

Comments
 (0)