@@ -475,6 +475,9 @@ where L::Target: Logger {
475475 network_graph : G ,
476476 logger : L ,
477477 channel_liquidities : HashMap < u64 , ChannelLiquidity > ,
478+ /// The last time we were given via a [`ScoreUpdate`] method. This does not imply that we've
479+ /// decayed every liquidity bound up to that time.
480+ last_duration_since_epoch : Duration ,
478481}
479482
480483/// Parameters for configuring [`ProbabilisticScorer`].
@@ -637,6 +640,22 @@ pub struct ProbabilisticScoringFeeParameters {
637640 ///
638641 /// Default value: false
639642 pub linear_success_probability : bool ,
643+
644+ /// In order to ensure we have knowledge for as many paths as possible, when probing it makes
645+ /// sense to bias away from channels for which we have very recent data.
646+ ///
647+ /// This value is a penalty that is applied based on the last time that we updated the bounds
648+ /// on the available liquidity in a channel. The specified value is the maximum penalty that
649+ /// will be applied.
650+ ///
651+ /// It obviously does not make sense to assign a non-0 value here unless you are using the
652+ /// pathfinding result for background probing.
653+ ///
654+ /// Specifically, the following penalty is applied
655+ /// `probing_diversity_penalty_msat * max(0, (86400 - current time + last update))^2 / 86400^2` is
656+ ///
657+ /// Default value: 0
658+ pub probing_diversity_penalty_msat : u64 ,
640659}
641660
642661impl Default for ProbabilisticScoringFeeParameters {
@@ -652,6 +671,7 @@ impl Default for ProbabilisticScoringFeeParameters {
652671 historical_liquidity_penalty_multiplier_msat : 10_000 ,
653672 historical_liquidity_penalty_amount_multiplier_msat : 64 ,
654673 linear_success_probability : false ,
674+ probing_diversity_penalty_msat : 0 ,
655675 }
656676 }
657677}
@@ -706,6 +726,7 @@ impl ProbabilisticScoringFeeParameters {
706726 anti_probing_penalty_msat : 0 ,
707727 considered_impossible_penalty_msat : 0 ,
708728 linear_success_probability : true ,
729+ probing_diversity_penalty_msat : 0 ,
709730 }
710731 }
711732}
@@ -823,6 +844,7 @@ impl<G: Deref<Target = NetworkGraph<L>>, L: Deref> ProbabilisticScorer<G, L> whe
823844 network_graph,
824845 logger,
825846 channel_liquidities : new_hash_map ( ) ,
847+ last_duration_since_epoch : Duration :: from_secs ( 0 ) ,
826848 }
827849 }
828850
@@ -1141,7 +1163,7 @@ DirectedChannelLiquidity< L, HT, T> {
11411163 /// Returns a liquidity penalty for routing the given HTLC `amount_msat` through the channel in
11421164 /// this direction.
11431165 fn penalty_msat (
1144- & self , amount_msat : u64 , inflight_htlc_msat : u64 ,
1166+ & self , amount_msat : u64 , inflight_htlc_msat : u64 , last_duration_since_epoch : Duration ,
11451167 score_params : & ProbabilisticScoringFeeParameters ,
11461168 ) -> u64 {
11471169 let total_inflight_amount_msat = amount_msat. saturating_add ( inflight_htlc_msat) ;
@@ -1216,6 +1238,13 @@ DirectedChannelLiquidity< L, HT, T> {
12161238 }
12171239 }
12181240
1241+ if score_params. probing_diversity_penalty_msat != 0 {
1242+ let time_since_update = last_duration_since_epoch. saturating_sub ( * self . last_updated ) ;
1243+ let mul = Duration :: from_secs ( 60 * 60 * 24 ) . saturating_sub ( time_since_update) . as_secs ( ) ;
1244+ let penalty = score_params. probing_diversity_penalty_msat . saturating_mul ( mul * mul) ;
1245+ res = res. saturating_add ( penalty / ( ( 60 * 60 * 24 ) * ( 60 * 60 * 24 ) ) ) ;
1246+ }
1247+
12191248 res
12201249 }
12211250
@@ -1365,11 +1394,12 @@ impl<G: Deref<Target = NetworkGraph<L>>, L: Deref> ScoreLookUp for Probabilistic
13651394 }
13661395
13671396 let capacity_msat = usage. effective_capacity . as_msat ( ) ;
1397+ let time = self . last_duration_since_epoch ;
13681398 self . channel_liquidities
13691399 . get ( scid)
13701400 . unwrap_or ( & ChannelLiquidity :: new ( Duration :: ZERO ) )
13711401 . as_directed ( & source, & target, capacity_msat)
1372- . penalty_msat ( usage. amount_msat , usage. inflight_htlc_msat , score_params)
1402+ . penalty_msat ( usage. amount_msat , usage. inflight_htlc_msat , time , score_params)
13731403 . saturating_add ( anti_probing_penalty_msat)
13741404 . saturating_add ( base_penalty_msat)
13751405 }
@@ -1415,6 +1445,7 @@ impl<G: Deref<Target = NetworkGraph<L>>, L: Deref> ScoreUpdate for Probabilistic
14151445 }
14161446 if at_failed_channel { break ; }
14171447 }
1448+ self . last_duration_since_epoch = duration_since_epoch;
14181449 }
14191450
14201451 fn payment_path_successful ( & mut self , path : & Path , duration_since_epoch : Duration ) {
@@ -1442,6 +1473,7 @@ impl<G: Deref<Target = NetworkGraph<L>>, L: Deref> ScoreUpdate for Probabilistic
14421473 hop. short_channel_id) ;
14431474 }
14441475 }
1476+ self . last_duration_since_epoch = duration_since_epoch;
14451477 }
14461478
14471479 fn probe_failed ( & mut self , path : & Path , short_channel_id : u64 , duration_since_epoch : Duration ) {
@@ -1473,6 +1505,7 @@ impl<G: Deref<Target = NetworkGraph<L>>, L: Deref> ScoreUpdate for Probabilistic
14731505 liquidity. min_liquidity_offset_msat != 0 || liquidity. max_liquidity_offset_msat != 0 ||
14741506 liquidity. liquidity_history . has_datapoints ( )
14751507 } ) ;
1508+ self . last_duration_since_epoch = duration_since_epoch;
14761509 }
14771510}
14781511
@@ -1906,15 +1939,20 @@ ReadableArgs<(ProbabilisticScoringDecayParameters, G, L)> for ProbabilisticScore
19061939 r : & mut R , args : ( ProbabilisticScoringDecayParameters , G , L )
19071940 ) -> Result < Self , DecodeError > {
19081941 let ( decay_params, network_graph, logger) = args;
1909- let mut channel_liquidities = new_hash_map ( ) ;
1942+ let mut channel_liquidities: HashMap < u64 , ChannelLiquidity > = new_hash_map ( ) ;
19101943 read_tlv_fields ! ( r, {
19111944 ( 0 , channel_liquidities, required) ,
19121945 } ) ;
1946+ let mut last_duration_since_epoch = Duration :: from_secs ( 0 ) ;
1947+ for ( _, liq) in channel_liquidities. iter ( ) {
1948+ last_duration_since_epoch = cmp:: max ( last_duration_since_epoch, liq. last_updated ) ;
1949+ }
19131950 Ok ( Self {
19141951 decay_params,
19151952 network_graph,
19161953 logger,
19171954 channel_liquidities,
1955+ last_duration_since_epoch,
19181956 } )
19191957 }
19201958}
0 commit comments