Skip to content

Commit c11009b

Browse files
committed
Update incorrect_payment_amount generation/handling for BOLT uptd
ie dont generate them as they're a really obvious privacy leak. Luckily we were already handling them the same aside from log printing so don't have to touch anything there. I was lazy in updating tests but it only effects log printing, so whatever.
1 parent 0fbe19d commit c11009b

File tree

3 files changed

+25
-33
lines changed

3 files changed

+25
-33
lines changed

src/ln/channelmanager.rs

Lines changed: 20 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -212,16 +212,6 @@ impl MsgHandleErrInternal {
212212
}
213213
}
214214

215-
/// Pass to fail_htlc_backwwards to indicate the reason to fail the payment
216-
/// after a PaymentReceived event.
217-
#[derive(PartialEq)]
218-
pub enum PaymentFailReason {
219-
/// Indicate the preimage for payment_hash is not known after a PaymentReceived event
220-
PreimageUnknown,
221-
/// Indicate the payment amount is incorrect ( received is < expected or > 2*expected ) after a PaymentReceived event
222-
AmountMismatch,
223-
}
224-
225215
/// We hold back HTLCs we intend to relay for a random interval in the range (this, 5*this). This
226216
/// provides some limited amount of privacy. Ideally this would range from somewhere like 1 second
227217
/// to 30 seconds, but people expect lightning to be, you know, kinda fast, sadly. We could
@@ -1532,16 +1522,21 @@ impl ChannelManager {
15321522
events.append(&mut new_events);
15331523
}
15341524

1535-
/// Indicates that the preimage for payment_hash is unknown or the received amount is incorrect after a PaymentReceived event.
1536-
pub fn fail_htlc_backwards(&self, payment_hash: &PaymentHash, reason: PaymentFailReason) -> bool {
1525+
/// Indicates that the preimage for payment_hash is unknown or the received amount is incorrect
1526+
/// after a PaymentReceived event.
1527+
/// expected_value is the value you expected the payment to be for (not the amount it actually
1528+
/// was for from the PaymentReceived event).
1529+
pub fn fail_htlc_backwards(&self, payment_hash: &PaymentHash, expected_value: u64) -> bool {
15371530
let _ = self.total_consistency_lock.read().unwrap();
15381531

15391532
let mut channel_state = Some(self.channel_state.lock().unwrap());
15401533
let removed_source = channel_state.as_mut().unwrap().claimable_htlcs.remove(payment_hash);
15411534
if let Some(mut sources) = removed_source {
15421535
for htlc_with_hash in sources.drain(..) {
15431536
if channel_state.is_none() { channel_state = Some(self.channel_state.lock().unwrap()); }
1544-
self.fail_htlc_backwards_internal(channel_state.take().unwrap(), HTLCSource::PreviousHopData(htlc_with_hash), payment_hash, HTLCFailReason::Reason { failure_code: if reason == PaymentFailReason::PreimageUnknown {0x4000 | 15} else {0x4000 | 16}, data: Vec::new() });
1537+
self.fail_htlc_backwards_internal(channel_state.take().unwrap(),
1538+
HTLCSource::PreviousHopData(htlc_with_hash), payment_hash,
1539+
HTLCFailReason::Reason { failure_code: 0x4000 | 15, data: byte_utils::be64_to_array(expected_value).to_vec() });
15451540
}
15461541
true
15471542
} else { false }
@@ -3366,7 +3361,7 @@ mod tests {
33663361
use chain::keysinterface::{KeysInterface, SpendableOutputDescriptor};
33673362
use chain::keysinterface;
33683363
use ln::channel::{COMMITMENT_TX_BASE_WEIGHT, COMMITMENT_TX_WEIGHT_PER_HTLC};
3369-
use ln::channelmanager::{ChannelManager,ChannelManagerReadArgs,OnionKeys,PaymentFailReason,RAACommitmentOrder, PaymentPreimage, PaymentHash};
3364+
use ln::channelmanager::{ChannelManager,ChannelManagerReadArgs,OnionKeys,RAACommitmentOrder, PaymentPreimage, PaymentHash};
33703365
use ln::channelmonitor::{ChannelMonitor, ChannelMonitorUpdateErr, CLTV_CLAIM_BUFFER, HTLC_FAIL_TIMEOUT_BLOCKS, ManyChannelMonitor};
33713366
use ln::channel::{ACCEPTED_HTLC_SCRIPT_WEIGHT, OFFERED_HTLC_SCRIPT_WEIGHT};
33723367
use ln::router::{Route, RouteHop, Router};
@@ -4224,7 +4219,7 @@ mod tests {
42244219
}
42254220

42264221
fn fail_payment_along_route(origin_node: &Node, expected_route: &[&Node], skip_last: bool, our_payment_hash: PaymentHash) {
4227-
assert!(expected_route.last().unwrap().node.fail_htlc_backwards(&our_payment_hash, PaymentFailReason::PreimageUnknown));
4222+
assert!(expected_route.last().unwrap().node.fail_htlc_backwards(&our_payment_hash, 0));
42284223
check_added_monitors!(expected_route.last().unwrap(), 1);
42294224

42304225
let mut next_msgs: Option<(msgs::UpdateFailHTLC, msgs::CommitmentSigned)> = None;
@@ -6351,7 +6346,7 @@ mod tests {
63516346
// Brodacast legit commitment tx from C on B's chain
63526347
let commitment_tx = nodes[2].node.channel_state.lock().unwrap().by_id.get(&chan_2.2).unwrap().last_local_commitment_txn.clone();
63536348
check_spends!(commitment_tx[0], chan_2.3.clone());
6354-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::PreimageUnknown);
6349+
nodes[2].node.fail_htlc_backwards(&payment_hash, 0);
63556350
{
63566351
let mut added_monitors = nodes[2].chan_monitor.added_monitors.lock().unwrap();
63576352
assert_eq!(added_monitors.len(), 1);
@@ -6536,7 +6531,7 @@ mod tests {
65366531
let (_, second_payment_hash) = route_payment(&nodes[0], &[&nodes[1], &nodes[2]], 3000000);
65376532
let (_, third_payment_hash) = route_payment(&nodes[0], &[&nodes[1], &nodes[2]], 3000000);
65386533

6539-
assert!(nodes[2].node.fail_htlc_backwards(&first_payment_hash, PaymentFailReason::PreimageUnknown));
6534+
assert!(nodes[2].node.fail_htlc_backwards(&first_payment_hash, 0));
65406535
check_added_monitors!(nodes[2], 1);
65416536
let updates = get_htlc_update_msgs!(nodes[2], nodes[1].node.get_our_node_id());
65426537
assert!(updates.update_add_htlcs.is_empty());
@@ -6548,7 +6543,7 @@ mod tests {
65486543
let bs_raa = commitment_signed_dance!(nodes[1], nodes[2], updates.commitment_signed, false, true, false, true);
65496544
// Drop the last RAA from 3 -> 2
65506545

6551-
assert!(nodes[2].node.fail_htlc_backwards(&second_payment_hash, PaymentFailReason::PreimageUnknown));
6546+
assert!(nodes[2].node.fail_htlc_backwards(&second_payment_hash, 0));
65526547
check_added_monitors!(nodes[2], 1);
65536548
let updates = get_htlc_update_msgs!(nodes[2], nodes[1].node.get_our_node_id());
65546549
assert!(updates.update_add_htlcs.is_empty());
@@ -6564,7 +6559,7 @@ mod tests {
65646559
nodes[2].node.handle_revoke_and_ack(&nodes[1].node.get_our_node_id(), &as_raa).unwrap();
65656560
check_added_monitors!(nodes[2], 1);
65666561

6567-
assert!(nodes[2].node.fail_htlc_backwards(&third_payment_hash, PaymentFailReason::PreimageUnknown));
6562+
assert!(nodes[2].node.fail_htlc_backwards(&third_payment_hash, 0));
65686563
check_added_monitors!(nodes[2], 1);
65696564
let updates = get_htlc_update_msgs!(nodes[2], nodes[1].node.get_our_node_id());
65706565
assert!(updates.update_add_htlcs.is_empty());
@@ -8159,7 +8154,7 @@ mod tests {
81598154
let (_, payment_hash_1) = route_payment(&nodes[0], &[&nodes[1], &nodes[2]], 1000000);
81608155

81618156
// Fail the payment backwards, failing the monitor update on nodes[1]'s receipt of the RAA
8162-
assert!(nodes[2].node.fail_htlc_backwards(&payment_hash_1, PaymentFailReason::PreimageUnknown));
8157+
assert!(nodes[2].node.fail_htlc_backwards(&payment_hash_1, 0));
81638158
check_added_monitors!(nodes[2], 1);
81648159

81658160
let updates = get_htlc_update_msgs!(nodes[2], nodes[1].node.get_our_node_id());
@@ -9724,7 +9719,7 @@ mod tests {
97249719
let onion_keys = ChannelManager::construct_onion_keys(&Secp256k1::new(), &route, &session_priv).unwrap();
97259720
msg.reason = ChannelManager::build_first_hop_failure_packet(&onion_keys[1].shared_secret[..], NODE|2, &[0;0]);
97269721
}, ||{
9727-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::PreimageUnknown);
9722+
nodes[2].node.fail_htlc_backwards(&payment_hash, 0);
97289723
}, true, Some(NODE|2), Some(msgs::HTLCFailChannelUpdate::NodeFailure{node_id: route.hops[1].pubkey, is_permanent: false}));
97299724

97309725
// intermediate node failure
@@ -9742,7 +9737,7 @@ mod tests {
97429737
let onion_keys = ChannelManager::construct_onion_keys(&Secp256k1::new(), &route, &session_priv).unwrap();
97439738
msg.reason = ChannelManager::build_first_hop_failure_packet(&onion_keys[1].shared_secret[..], PERM|NODE|2, &[0;0]);
97449739
}, ||{
9745-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::PreimageUnknown);
9740+
nodes[2].node.fail_htlc_backwards(&payment_hash, 0);
97469741
}, false, Some(PERM|NODE|2), Some(msgs::HTLCFailChannelUpdate::NodeFailure{node_id: route.hops[1].pubkey, is_permanent: true}));
97479742

97489743
// intermediate node failure
@@ -9753,7 +9748,7 @@ mod tests {
97539748
let onion_keys = ChannelManager::construct_onion_keys(&Secp256k1::new(), &route, &session_priv).unwrap();
97549749
msg.reason = ChannelManager::build_first_hop_failure_packet(&onion_keys[0].shared_secret[..], PERM|NODE|3, &[0;0]);
97559750
}, ||{
9756-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::PreimageUnknown);
9751+
nodes[2].node.fail_htlc_backwards(&payment_hash, 0);
97579752
}, true, Some(PERM|NODE|3), Some(msgs::HTLCFailChannelUpdate::NodeFailure{node_id: route.hops[0].pubkey, is_permanent: true}));
97589753

97599754
// final node failure
@@ -9762,7 +9757,7 @@ mod tests {
97629757
let onion_keys = ChannelManager::construct_onion_keys(&Secp256k1::new(), &route, &session_priv).unwrap();
97639758
msg.reason = ChannelManager::build_first_hop_failure_packet(&onion_keys[1].shared_secret[..], PERM|NODE|3, &[0;0]);
97649759
}, ||{
9765-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::PreimageUnknown);
9760+
nodes[2].node.fail_htlc_backwards(&payment_hash, 0);
97669761
}, false, Some(PERM|NODE|3), Some(msgs::HTLCFailChannelUpdate::NodeFailure{node_id: route.hops[1].pubkey, is_permanent: true}));
97679762

97689763
run_onion_failure_test("invalid_onion_version", 0, &nodes, &route, &payment_hash, |msg| { msg.onion_routing_packet.version = 1; }, ||{}, true,
@@ -9829,13 +9824,9 @@ mod tests {
98299824
}, ||{}, true, Some(UPDATE|14), Some(msgs::HTLCFailChannelUpdate::ChannelUpdateMessage{msg: ChannelUpdate::dummy()}));
98309825

98319826
run_onion_failure_test("unknown_payment_hash", 2, &nodes, &route, &payment_hash, |_| {}, || {
9832-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::PreimageUnknown);
9827+
nodes[2].node.fail_htlc_backwards(&payment_hash, 0);
98339828
}, false, Some(PERM|15), None);
98349829

9835-
run_onion_failure_test("incorrect_payment_amount", 2, &nodes, &route, &payment_hash, |_| {}, || {
9836-
nodes[2].node.fail_htlc_backwards(&payment_hash, PaymentFailReason::AmountMismatch);
9837-
}, false, Some(PERM|16), None);
9838-
98399830
run_onion_failure_test("final_expiry_too_soon", 1, &nodes, &route, &payment_hash, |msg| {
98409831
let height = msg.cltv_expiry - CLTV_CLAIM_BUFFER - HTLC_FAIL_TIMEOUT_BLOCKS + 1;
98419832
let header = BlockHeader { version: 0x20000000, prev_blockhash: Default::default(), merkle_root: Default::default(), time: 42, bits: 42, nonce: 42 };

src/util/errors.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,7 @@ pub(crate) fn get_onion_error_description(error_code: u16) -> (&'static str, &'s
8484
_c if _c == UPDATE|12 => ("Node indicated the fee amount does not meet the required level", "fee_insufficient"),
8585
_c if _c == UPDATE|13 => ("Node indicated the cltv_expiry does not comply with the cltv_expiry_delta required by the outgoing channel", "incorrect_cltv_expiry"),
8686
_c if _c == UPDATE|14 => ("Node indicated the CLTV expiry too close to the current block height for safe handling", "expiry_too_soon"),
87-
_c if _c == PERM|15 => ("The final node indicated the payment hash is unknown", "unknown_payment_hash"),
87+
_c if _c == PERM|15 => ("The final node indicated the payment hash is unknown or amount is incorrect", "incorrect_or_unknown_payment_details"),
8888
_c if _c == PERM|16 => ("The final node indicated the payment amount is incorrect", "incorrect_payment_amount"),
8989
_c if _c == 17 => ("The final node indicated the CLTV expiry is too close to the current block height for safe handling", "final_expiry_too_soon"),
9090
_c if _c == 18 => ("The final node indicated the CLTV expiry in the HTLC does not match the value in the onion", "final_incorrect_cltv_expiry"),

src/util/events.rs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -54,14 +54,15 @@ pub enum Event {
5454
/// Indicates we've received money! Just gotta dig out that payment preimage and feed it to
5555
/// ChannelManager::claim_funds to get it....
5656
/// Note that if the preimage is not known or the amount paid is incorrect, you must call
57-
/// ChannelManager::fail_htlc_backwards with PaymentFailReason::PreimageUnknown or
58-
/// PaymentFailReason::AmountMismatch, respectively, to free up resources for this HTLC.
57+
/// ChannelManager::fail_htlc_backwards to free up resources for this HTLC.
5958
/// The amount paid should be considered 'incorrect' when it is less than or more than twice
6059
/// the amount expected.
6160
PaymentReceived {
6261
/// The hash for which the preimage should be handed to the ChannelManager.
6362
payment_hash: PaymentHash,
64-
/// The value, in thousandths of a satoshi, that this payment is for.
63+
/// The value, in thousandths of a satoshi, that this payment is for. Note that you must
64+
/// compare this to the expected value before accepting the payment (as otherwise you are
65+
/// providing proof-of-payment for less than the value you expected!).
6566
amt: u64,
6667
},
6768
/// Indicates an outbound payment we made succeeded (ie it made it all the way to its target

0 commit comments

Comments
 (0)