Skip to content

Commit 207479f

Browse files
Don't remove failed payments when all paths fail
This is because we want the ability to retry completely failed payments. Upcoming commits will remove these payments on timeout to prevent DoS issues Also test that this removal allows retrying single-path payments
1 parent 8db9c50 commit 207479f

File tree

2 files changed

+53
-4
lines changed

2 files changed

+53
-4
lines changed

lightning/src/ln/channelmanager.rs

-4
Original file line numberDiff line numberDiff line change
@@ -3008,9 +3008,6 @@ impl<Signer: Sign, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref> ChannelMana
30083008
error_data: None,
30093009
}
30103010
);
3011-
if payment.get().remaining_parts() == 0 {
3012-
payment.remove();
3013-
}
30143011
}
30153012
} else {
30163013
log_trace!(self.logger, "Received duplicative fail for HTLC with payment_hash {}", log_bytes!(payment_hash.0));
@@ -3048,7 +3045,6 @@ impl<Signer: Sign, M: Deref, T: Deref, K: Deref, F: Deref, L: Deref> ChannelMana
30483045
}
30493046
if sessions.get().remaining_parts() == 0 {
30503047
all_paths_failed = true;
3051-
sessions.remove();
30523048
}
30533049
} else {
30543050
log_trace!(self.logger, "Received duplicative fail for HTLC with payment_hash {}", log_bytes!(payment_hash.0));

lightning/src/ln/functional_tests.rs

+53
Original file line numberDiff line numberDiff line change
@@ -4273,6 +4273,59 @@ fn mpp_retry() {
42734273
claim_payment_along_route(&nodes[0], &[&[&nodes[1], &nodes[3]], &[&nodes[2], &nodes[3]]], false, payment_preimage);
42744274
}
42754275

4276+
#[test]
4277+
fn retry_single_path_payment() {
4278+
let chanmon_cfgs = create_chanmon_cfgs(3);
4279+
let node_cfgs = create_node_cfgs(3, &chanmon_cfgs);
4280+
let node_chanmgrs = create_node_chanmgrs(3, &node_cfgs, &[None, None, None]);
4281+
let mut nodes = create_network(3, &node_cfgs, &node_chanmgrs);
4282+
4283+
let _chan_0 = create_announced_chan_between_nodes(&nodes, 0, 1, InitFeatures::known(), InitFeatures::known());
4284+
let _chan_1 = create_announced_chan_between_nodes(&nodes, 2, 1, InitFeatures::known(), InitFeatures::known());
4285+
// Rebalance to find a route
4286+
send_payment(&nodes[2], &vec!(&nodes[1])[..], 3_000_000);
4287+
4288+
let logger = test_utils::TestLogger::new();
4289+
let (payment_preimage, payment_hash, payment_secret) = get_payment_preimage_hash!(nodes[2]);
4290+
let net_graph_msg_handler = &nodes[0].net_graph_msg_handler;
4291+
let route = get_route(&nodes[0].node.get_our_node_id(), &net_graph_msg_handler.network_graph, &nodes[2].node.get_our_node_id(), Some(InvoiceFeatures::known()), None, &Vec::new(), 100_000, TEST_FINAL_CLTV, &logger).unwrap();
4292+
4293+
// Rebalance so that the first hop fails.
4294+
send_payment(&nodes[1], &vec!(&nodes[2])[..], 2_000_000);
4295+
4296+
// Make sure the payment fails on the first hop.
4297+
let payment_id = nodes[0].node.send_payment(&route, payment_hash, &Some(payment_secret)).unwrap();
4298+
check_added_monitors!(nodes[0], 1);
4299+
let mut events = nodes[0].node.get_and_clear_pending_msg_events();
4300+
assert_eq!(events.len(), 1);
4301+
let mut payment_event = SendEvent::from_event(events.pop().unwrap());
4302+
nodes[1].node.handle_update_add_htlc(&nodes[0].node.get_our_node_id(), &payment_event.msgs[0]);
4303+
check_added_monitors!(nodes[1], 0);
4304+
commitment_signed_dance!(nodes[1], nodes[0], payment_event.commitment_msg, false);
4305+
expect_pending_htlcs_forwardable!(nodes[1]);
4306+
expect_pending_htlcs_forwardable!(&nodes[1]);
4307+
let htlc_updates = get_htlc_update_msgs!(nodes[1], nodes[0].node.get_our_node_id());
4308+
assert!(htlc_updates.update_add_htlcs.is_empty());
4309+
assert_eq!(htlc_updates.update_fail_htlcs.len(), 1);
4310+
assert!(htlc_updates.update_fulfill_htlcs.is_empty());
4311+
assert!(htlc_updates.update_fail_malformed_htlcs.is_empty());
4312+
check_added_monitors!(nodes[1], 1);
4313+
nodes[0].node.handle_update_fail_htlc(&nodes[1].node.get_our_node_id(), &htlc_updates.update_fail_htlcs[0]);
4314+
commitment_signed_dance!(nodes[0], nodes[1], htlc_updates.commitment_signed, false);
4315+
expect_payment_failed!(nodes[0], payment_hash, false);
4316+
4317+
// Rebalance the channel so the retry succeeds.
4318+
send_payment(&nodes[2], &vec!(&nodes[1])[..], 3_000_000);
4319+
4320+
// Retry the payment and make sure it succeeds.
4321+
nodes[0].node.retry_payment(&route, payment_id).unwrap();
4322+
check_added_monitors!(nodes[0], 1);
4323+
let mut events = nodes[0].node.get_and_clear_pending_msg_events();
4324+
assert_eq!(events.len(), 1);
4325+
pass_along_path(&nodes[0], &[&nodes[1], &nodes[2]], 100_000, payment_hash, Some(payment_secret), events.pop().unwrap(), true, None);
4326+
claim_payment_along_route(&nodes[0], &[&[&nodes[1], &nodes[2]]], false, payment_preimage);
4327+
}
4328+
42764329
#[test]
42774330
fn test_dup_htlc_onchain_fails_on_reload() {
42784331
// When a Channel is closed, any outbound HTLCs which were relayed through it are simply

0 commit comments

Comments
 (0)