Skip to content

Commit 23c1b46

Browse files
authored
Merge pull request #2092 from TheBlueMatt/2023-03-find-route-id
Correct `outbound_payment` route-fetch calls to pass the hash + ID
2 parents 36834b3 + 10e6978 commit 23c1b46

File tree

1 file changed

+32
-31
lines changed

1 file changed

+32
-31
lines changed

lightning/src/ln/outbound_payment.rs

+32-31
Original file line numberDiff line numberDiff line change
@@ -231,7 +231,7 @@ pub enum Retry {
231231
///
232232
/// Each attempt may be multiple HTLCs along multiple paths if the router decides to split up a
233233
/// retry, and may retry multiple failed HTLCs at once if they failed around the same time and
234-
/// were retried along a route from a single call to [`Router::find_route`].
234+
/// were retried along a route from a single call to [`Router::find_route_with_id`].
235235
Attempts(usize),
236236
#[cfg(not(feature = "no-std"))]
237237
/// Time elapsed before abandoning retries for a payment. At least one attempt at payment is made;
@@ -531,9 +531,9 @@ impl OutboundPayments {
531531
let mut retry_id_route_params = None;
532532
for (pmt_id, pmt) in outbounds.iter_mut() {
533533
if pmt.is_auto_retryable_now() {
534-
if let PendingOutboundPayment::Retryable { pending_amt_msat, total_msat, payment_params: Some(params), .. } = pmt {
534+
if let PendingOutboundPayment::Retryable { pending_amt_msat, total_msat, payment_params: Some(params), payment_hash, .. } = pmt {
535535
if pending_amt_msat < total_msat {
536-
retry_id_route_params = Some((*pmt_id, RouteParameters {
536+
retry_id_route_params = Some((*payment_hash, *pmt_id, RouteParameters {
537537
final_value_msat: *total_msat - *pending_amt_msat,
538538
payment_params: params.clone(),
539539
}));
@@ -543,8 +543,8 @@ impl OutboundPayments {
543543
}
544544
}
545545
core::mem::drop(outbounds);
546-
if let Some((payment_id, route_params)) = retry_id_route_params {
547-
self.retry_payment_internal(payment_id, route_params, router, first_hops(), &inflight_htlcs, entropy_source, node_signer, best_block_height, logger, pending_events, &send_payment_along_path)
546+
if let Some((payment_hash, payment_id, route_params)) = retry_id_route_params {
547+
self.retry_payment_internal(payment_hash, payment_id, route_params, router, first_hops(), &inflight_htlcs, entropy_source, node_signer, best_block_height, logger, pending_events, &send_payment_along_path)
548548
} else { break }
549549
}
550550

@@ -597,9 +597,10 @@ impl OutboundPayments {
597597
}
598598
}
599599

600-
let route = router.find_route(
600+
let route = router.find_route_with_id(
601601
&node_signer.get_node_id(Recipient::Node).unwrap(), &route_params,
602-
Some(&first_hops.iter().collect::<Vec<_>>()), &inflight_htlcs()
602+
Some(&first_hops.iter().collect::<Vec<_>>()), &inflight_htlcs(),
603+
payment_hash, payment_id,
603604
).map_err(|_| RetryableSendFailure::RouteNotFound)?;
604605

605606
let onion_session_privs = self.add_new_pending_payment(payment_hash, *payment_secret,
@@ -617,10 +618,10 @@ impl OutboundPayments {
617618
}
618619

619620
fn retry_payment_internal<R: Deref, NS: Deref, ES: Deref, IH, SP, L: Deref>(
620-
&self, payment_id: PaymentId, route_params: RouteParameters, router: &R,
621-
first_hops: Vec<ChannelDetails>, inflight_htlcs: &IH, entropy_source: &ES, node_signer: &NS,
622-
best_block_height: u32, logger: &L, pending_events: &Mutex<Vec<events::Event>>,
623-
send_payment_along_path: &SP,
621+
&self, payment_hash: PaymentHash, payment_id: PaymentId, route_params: RouteParameters,
622+
router: &R, first_hops: Vec<ChannelDetails>, inflight_htlcs: &IH, entropy_source: &ES,
623+
node_signer: &NS, best_block_height: u32, logger: &L,
624+
pending_events: &Mutex<Vec<events::Event>>, send_payment_along_path: &SP,
624625
)
625626
where
626627
R::Target: Router,
@@ -639,9 +640,10 @@ impl OutboundPayments {
639640
}
640641
}
641642

642-
let route = match router.find_route(
643+
let route = match router.find_route_with_id(
643644
&node_signer.get_node_id(Recipient::Node).unwrap(), &route_params,
644-
Some(&first_hops.iter().collect::<Vec<_>>()), &inflight_htlcs()
645+
Some(&first_hops.iter().collect::<Vec<_>>()), &inflight_htlcs(),
646+
payment_hash, payment_id,
645647
) {
646648
Ok(route) => route,
647649
Err(e) => {
@@ -665,32 +667,31 @@ impl OutboundPayments {
665667
}
666668

667669
macro_rules! abandon_with_entry {
668-
($payment_id: expr, $payment_hash: expr, $payment: expr, $pending_events: expr) => {
670+
($payment: expr) => {
669671
if $payment.get_mut().mark_abandoned().is_ok() && $payment.get().remaining_parts() == 0 {
670-
$pending_events.lock().unwrap().push(events::Event::PaymentFailed {
671-
payment_id: $payment_id,
672-
payment_hash: $payment_hash,
672+
pending_events.lock().unwrap().push(events::Event::PaymentFailed {
673+
payment_id,
674+
payment_hash,
673675
});
674676
$payment.remove();
675677
}
676678
}
677679
}
678-
let (total_msat, payment_hash, payment_secret, keysend_preimage) = {
680+
let (total_msat, payment_secret, keysend_preimage) = {
679681
let mut outbounds = self.pending_outbound_payments.lock().unwrap();
680682
match outbounds.entry(payment_id) {
681683
hash_map::Entry::Occupied(mut payment) => {
682684
let res = match payment.get() {
683685
PendingOutboundPayment::Retryable {
684-
total_msat, payment_hash, keysend_preimage, payment_secret, pending_amt_msat, ..
686+
total_msat, keysend_preimage, payment_secret, pending_amt_msat, ..
685687
} => {
686688
let retry_amt_msat: u64 = route.paths.iter().map(|path| path.last().unwrap().fee_msat).sum();
687689
if retry_amt_msat + *pending_amt_msat > *total_msat * (100 + RETRY_OVERFLOW_PERCENTAGE) / 100 {
688690
log_error!(logger, "retry_amt_msat of {} will put pending_amt_msat (currently: {}) more than 10% over total_payment_amt_msat of {}", retry_amt_msat, pending_amt_msat, total_msat);
689-
let payment_hash = *payment_hash;
690-
abandon_with_entry!(payment_id, payment_hash, payment, pending_events);
691+
abandon_with_entry!(payment);
691692
return
692693
}
693-
(*total_msat, *payment_hash, *payment_secret, *keysend_preimage)
694+
(*total_msat, *payment_secret, *keysend_preimage)
694695
},
695696
PendingOutboundPayment::Legacy { .. } => {
696697
log_error!(logger, "Unable to retry payments that were initially sent on LDK versions prior to 0.0.102");
@@ -707,7 +708,7 @@ impl OutboundPayments {
707708
};
708709
if !payment.get().is_retryable_now() {
709710
log_error!(logger, "Retries exhausted for payment id {}", log_bytes!(payment_id.0));
710-
abandon_with_entry!(payment_id, res.1, payment, pending_events);
711+
abandon_with_entry!(payment);
711712
return
712713
}
713714
payment.get_mut().increment_attempts();
@@ -749,14 +750,14 @@ impl OutboundPayments {
749750
match err {
750751
PaymentSendFailure::AllFailedResendSafe(errs) => {
751752
Self::push_path_failed_evs_and_scids(payment_id, payment_hash, &mut route_params, route.paths, errs.into_iter().map(|e| Err(e)), pending_events);
752-
self.retry_payment_internal(payment_id, route_params, router, first_hops, inflight_htlcs, entropy_source, node_signer, best_block_height, logger, pending_events, send_payment_along_path);
753+
self.retry_payment_internal(payment_hash, payment_id, route_params, router, first_hops, inflight_htlcs, entropy_source, node_signer, best_block_height, logger, pending_events, send_payment_along_path);
753754
},
754755
PaymentSendFailure::PartialFailure { failed_paths_retry: Some(mut retry), results, .. } => {
755756
Self::push_path_failed_evs_and_scids(payment_id, payment_hash, &mut retry, route.paths, results.into_iter(), pending_events);
756757
// Some paths were sent, even if we failed to send the full MPP value our recipient may
757758
// misbehave and claim the funds, at which point we have to consider the payment sent, so
758759
// return `Ok()` here, ignoring any retry errors.
759-
self.retry_payment_internal(payment_id, retry, router, first_hops, inflight_htlcs, entropy_source, node_signer, best_block_height, logger, pending_events, send_payment_along_path);
760+
self.retry_payment_internal(payment_hash, payment_id, retry, router, first_hops, inflight_htlcs, entropy_source, node_signer, best_block_height, logger, pending_events, send_payment_along_path);
760761
},
761762
PaymentSendFailure::PartialFailure { failed_paths_retry: None, .. } => {
762763
// This may happen if we send a payment and some paths fail, but only due to a temporary
@@ -1384,9 +1385,9 @@ mod tests {
13841385
&Route { paths: vec![], payment_params: None }, Some(Retry::Attempts(1)),
13851386
Some(expired_route_params.payment_params.clone()), &&keys_manager, 0).unwrap();
13861387
outbound_payments.retry_payment_internal(
1387-
PaymentId([0; 32]), expired_route_params, &&router, vec![], &|| InFlightHtlcs::new(),
1388-
&&keys_manager, &&keys_manager, 0, &&logger, &pending_events,
1389-
&|_, _, _, _, _, _, _, _, _| Ok(()));
1388+
PaymentHash([0; 32]), PaymentId([0; 32]), expired_route_params, &&router, vec![],
1389+
&|| InFlightHtlcs::new(), &&keys_manager, &&keys_manager, 0, &&logger,
1390+
&pending_events, &|_, _, _, _, _, _, _, _, _| Ok(()));
13901391
let events = pending_events.lock().unwrap();
13911392
assert_eq!(events.len(), 1);
13921393
if let Event::PaymentFailed { .. } = events[0] { } else { panic!("Unexpected event"); }
@@ -1428,9 +1429,9 @@ mod tests {
14281429
&Route { paths: vec![], payment_params: None }, Some(Retry::Attempts(1)),
14291430
Some(route_params.payment_params.clone()), &&keys_manager, 0).unwrap();
14301431
outbound_payments.retry_payment_internal(
1431-
PaymentId([0; 32]), route_params, &&router, vec![], &|| InFlightHtlcs::new(),
1432-
&&keys_manager, &&keys_manager, 0, &&logger, &pending_events,
1433-
&|_, _, _, _, _, _, _, _, _| Ok(()));
1432+
PaymentHash([0; 32]), PaymentId([0; 32]), route_params, &&router, vec![],
1433+
&|| InFlightHtlcs::new(), &&keys_manager, &&keys_manager, 0, &&logger,
1434+
&pending_events, &|_, _, _, _, _, _, _, _, _| Ok(()));
14341435
let events = pending_events.lock().unwrap();
14351436
assert_eq!(events.len(), 1);
14361437
if let Event::PaymentFailed { .. } = events[0] { } else { panic!("Unexpected event"); }

0 commit comments

Comments
 (0)