1313
1414use crate :: chain;
1515use crate :: chain:: { ChannelMonitorUpdateStatus , Confirm , Listen , Watch } ;
16- use crate :: chain:: chaininterface:: LowerBoundedFeeEstimator ;
16+ use crate :: chain:: chaininterface:: { LowerBoundedFeeEstimator , FeeEstimator , ConfirmationTarget } ;
1717use crate :: chain:: channelmonitor;
1818use crate :: chain:: channelmonitor:: { CLTV_CLAIM_BUFFER , LATENCY_GRACE_PERIOD_BLOCKS , ANTI_REORG_DELAY } ;
1919use crate :: chain:: transaction:: OutPoint ;
@@ -9510,7 +9510,7 @@ enum ExposureEvent {
95109510 AtUpdateFeeOutbound ,
95119511}
95129512
9513- fn do_test_max_dust_htlc_exposure ( dust_outbound_balance : bool , exposure_breach_event : ExposureEvent , on_holder_tx : bool ) {
9513+ fn do_test_max_dust_htlc_exposure ( dust_outbound_balance : bool , exposure_breach_event : ExposureEvent , on_holder_tx : bool , multiplier_dust_limit : bool ) {
95149514 // Test that we properly reject dust HTLC violating our `max_dust_htlc_exposure_msat`
95159515 // policy.
95169516 //
@@ -9526,6 +9526,9 @@ fn do_test_max_dust_htlc_exposure(dust_outbound_balance: bool, exposure_breach_e
95269526 let chanmon_cfgs = create_chanmon_cfgs ( 2 ) ;
95279527 let mut config = test_default_channel_config ( ) ;
95289528 config. channel_config . max_dust_htlc_exposure_msat = 5_000_000 ; // default setting value
9529+ // Default test fee estimator rate is 253 sat/kw, so we set the multiplier to 5_000_000 / 253
9530+ // to get roughly the same initial value as the default setting.
9531+ config. channel_config . max_dust_htlc_exposure_multiplier_thousandths = if multiplier_dust_limit { Some ( 5_000_000 / 253 ) } else { None } ;
95299532 let node_cfgs = create_node_cfgs ( 2 , & chanmon_cfgs) ;
95309533 let node_chanmgrs = create_node_chanmgrs ( 2 , & node_cfgs, & [ Some ( config) , None ] ) ;
95319534 let mut nodes = create_network ( 2 , & node_cfgs, & node_chanmgrs) ;
@@ -9575,14 +9578,21 @@ fn do_test_max_dust_htlc_exposure(dust_outbound_balance: bool, exposure_breach_e
95759578 let chan = chan_lock. channel_by_id . get ( & channel_id) . unwrap ( ) ;
95769579 chan. context . get_dust_buffer_feerate ( None ) as u64
95779580 } ;
9581+ let max_dust_htlc_exposure_msat = if multiplier_dust_limit {
9582+ nodes[ 0 ] . fee_estimator . get_est_sat_per_1000_weight ( ConfirmationTarget :: HighPriority ) as u64
9583+ * config. channel_config . max_dust_htlc_exposure_multiplier_thousandths . unwrap ( )
9584+ } else {
9585+ config. channel_config . max_dust_htlc_exposure_msat
9586+ } ;
9587+
95789588 let dust_outbound_htlc_on_holder_tx_msat: u64 = ( dust_buffer_feerate * htlc_timeout_tx_weight ( opt_anchors) / 1000 + open_channel. dust_limit_satoshis - 1 ) * 1000 ;
9579- let dust_outbound_htlc_on_holder_tx: u64 = config . channel_config . max_dust_htlc_exposure_msat / dust_outbound_htlc_on_holder_tx_msat;
9589+ let dust_outbound_htlc_on_holder_tx: u64 = max_dust_htlc_exposure_msat / dust_outbound_htlc_on_holder_tx_msat;
95809590
95819591 let dust_inbound_htlc_on_holder_tx_msat: u64 = ( dust_buffer_feerate * htlc_success_tx_weight ( opt_anchors) / 1000 + open_channel. dust_limit_satoshis - 1 ) * 1000 ;
9582- let dust_inbound_htlc_on_holder_tx: u64 = config . channel_config . max_dust_htlc_exposure_msat / dust_inbound_htlc_on_holder_tx_msat;
9592+ let dust_inbound_htlc_on_holder_tx: u64 = max_dust_htlc_exposure_msat / dust_inbound_htlc_on_holder_tx_msat;
95839593
95849594 let dust_htlc_on_counterparty_tx: u64 = 4 ;
9585- let dust_htlc_on_counterparty_tx_msat: u64 = config . channel_config . max_dust_htlc_exposure_msat / dust_htlc_on_counterparty_tx;
9595+ let dust_htlc_on_counterparty_tx_msat: u64 = max_dust_htlc_exposure_msat / dust_htlc_on_counterparty_tx;
95869596
95879597 if on_holder_tx {
95889598 if dust_outbound_balance {
@@ -9634,7 +9644,7 @@ fn do_test_max_dust_htlc_exposure(dust_outbound_balance: bool, exposure_breach_e
96349644 ) , true , APIError :: ChannelUnavailable { .. } , { } ) ;
96359645 }
96369646 } else if exposure_breach_event == ExposureEvent :: AtHTLCReception {
9637- let ( route, payment_hash, _, payment_secret) = get_route_and_payment_hash ! ( nodes[ 1 ] , nodes[ 0 ] , if on_holder_tx { dust_inbound_htlc_on_holder_tx_msat } else { dust_htlc_on_counterparty_tx_msat + 1 } ) ;
9647+ let ( route, payment_hash, _, payment_secret) = get_route_and_payment_hash ! ( nodes[ 1 ] , nodes[ 0 ] , if on_holder_tx { dust_inbound_htlc_on_holder_tx_msat } else { dust_htlc_on_counterparty_tx_msat + 4 } ) ;
96389648 nodes[ 1 ] . node . send_payment_with_route ( & route, payment_hash,
96399649 RecipientOnionFields :: secret_only ( payment_secret) , PaymentId ( payment_hash. 0 ) ) . unwrap ( ) ;
96409650 check_added_monitors ! ( nodes[ 1 ] , 1 ) ;
@@ -9647,18 +9657,24 @@ fn do_test_max_dust_htlc_exposure(dust_outbound_balance: bool, exposure_breach_e
96479657 // Outbound dust balance: 6399 sats
96489658 let dust_inbound_overflow = dust_inbound_htlc_on_holder_tx_msat * ( dust_inbound_htlc_on_holder_tx + 1 ) ;
96499659 let dust_outbound_overflow = dust_outbound_htlc_on_holder_tx_msat * dust_outbound_htlc_on_holder_tx + dust_inbound_htlc_on_holder_tx_msat;
9650- nodes[ 0 ] . logger . assert_log ( "lightning::ln::channel" . to_string ( ) , format ! ( "Cannot accept value that would put our exposure to dust HTLCs at {} over the limit {} on holder commitment tx" , if dust_outbound_balance { dust_outbound_overflow } else { dust_inbound_overflow } , config . channel_config . max_dust_htlc_exposure_msat) , 1 ) ;
9660+ nodes[ 0 ] . logger . assert_log ( "lightning::ln::channel" . to_string ( ) , format ! ( "Cannot accept value that would put our exposure to dust HTLCs at {} over the limit {} on holder commitment tx" , if dust_outbound_balance { dust_outbound_overflow } else { dust_inbound_overflow } , max_dust_htlc_exposure_msat) , 1 ) ;
96519661 } else {
96529662 // Outbound dust balance: 5200 sats
96539663 nodes[ 0 ] . logger . assert_log ( "lightning::ln::channel" . to_string ( ) ,
96549664 format ! ( "Cannot accept value that would put our exposure to dust HTLCs at {} over the limit {} on counterparty commitment tx" ,
9655- dust_htlc_on_counterparty_tx_msat * ( dust_htlc_on_counterparty_tx - 1 ) + dust_htlc_on_counterparty_tx_msat + 1 ,
9656- config . channel_config . max_dust_htlc_exposure_msat) , 1 ) ;
9665+ dust_htlc_on_counterparty_tx_msat * ( dust_htlc_on_counterparty_tx - 1 ) + dust_htlc_on_counterparty_tx_msat + 4 ,
9666+ max_dust_htlc_exposure_msat) , 1 ) ;
96579667 }
96589668 } else if exposure_breach_event == ExposureEvent :: AtUpdateFeeOutbound {
96599669 route. paths [ 0 ] . hops . last_mut ( ) . unwrap ( ) . fee_msat = 2_500_000 ;
9660- nodes[ 0 ] . node . send_payment_with_route ( & route, payment_hash,
9661- RecipientOnionFields :: secret_only ( payment_secret) , PaymentId ( payment_hash. 0 ) ) . unwrap ( ) ;
9670+ // For the multiplier dust exposure limit, since it scales with feerate,
9671+ // we need to add a lot of HTLCs that will become dust at the new feerate
9672+ // to cross the threshold.
9673+ for _ in 0 ..20 {
9674+ let ( _, payment_hash, payment_secret) = get_payment_preimage_hash ( & nodes[ 1 ] , Some ( 1_000 ) , None ) ;
9675+ nodes[ 0 ] . node . send_payment_with_route ( & route, payment_hash,
9676+ RecipientOnionFields :: secret_only ( payment_secret) , PaymentId ( payment_hash. 0 ) ) . unwrap ( ) ;
9677+ }
96629678 {
96639679 let mut feerate_lock = chanmon_cfgs[ 0 ] . fee_estimator . sat_per_kw . lock ( ) . unwrap ( ) ;
96649680 * feerate_lock = * feerate_lock * 10 ;
@@ -9673,20 +9689,25 @@ fn do_test_max_dust_htlc_exposure(dust_outbound_balance: bool, exposure_breach_e
96739689 added_monitors. clear ( ) ;
96749690}
96759691
9692+ fn do_test_max_dust_htlc_exposure_by_threshold_type ( multiplier_dust_limit : bool ) {
9693+ do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCForward , true , multiplier_dust_limit) ;
9694+ do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCForward , true , multiplier_dust_limit) ;
9695+ do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCReception , true , multiplier_dust_limit) ;
9696+ do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCReception , false , multiplier_dust_limit) ;
9697+ do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCForward , false , multiplier_dust_limit) ;
9698+ do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCReception , false , multiplier_dust_limit) ;
9699+ do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCReception , true , multiplier_dust_limit) ;
9700+ do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCForward , false , multiplier_dust_limit) ;
9701+ do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtUpdateFeeOutbound , true , multiplier_dust_limit) ;
9702+ do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtUpdateFeeOutbound , false , multiplier_dust_limit) ;
9703+ do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtUpdateFeeOutbound , false , multiplier_dust_limit) ;
9704+ do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtUpdateFeeOutbound , true , multiplier_dust_limit) ;
9705+ }
9706+
96769707#[ test]
96779708fn test_max_dust_htlc_exposure ( ) {
9678- do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCForward , true ) ;
9679- do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCForward , true ) ;
9680- do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCReception , true ) ;
9681- do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCReception , false ) ;
9682- do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCForward , false ) ;
9683- do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCReception , false ) ;
9684- do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtHTLCReception , true ) ;
9685- do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtHTLCForward , false ) ;
9686- do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtUpdateFeeOutbound , true ) ;
9687- do_test_max_dust_htlc_exposure ( true , ExposureEvent :: AtUpdateFeeOutbound , false ) ;
9688- do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtUpdateFeeOutbound , false ) ;
9689- do_test_max_dust_htlc_exposure ( false , ExposureEvent :: AtUpdateFeeOutbound , true ) ;
9709+ do_test_max_dust_htlc_exposure_by_threshold_type ( false ) ;
9710+ do_test_max_dust_htlc_exposure_by_threshold_type ( true ) ;
96909711}
96919712
96929713#[ test]
0 commit comments