]> git.bitcoin.ninja Git - rust-lightning/commitdiff
Allow htlc_satisfies_config to override the amount to forward
authorMatt Corallo <git@bluematt.me>
Mon, 9 Jan 2023 18:42:34 +0000 (18:42 +0000)
committerMatt Corallo <git@bluematt.me>
Mon, 9 Jan 2023 18:42:34 +0000 (18:42 +0000)
This allows us to calculate implicit fees before forwarding.

lightning/src/ln/channel.rs
lightning/src/ln/channelmanager.rs

index 29f1a30a6de4a8a04d6638251faf77a348a49fe5..583a98ec6310a016d605426d8281cc9d02ad1e42 100644 (file)
@@ -4724,7 +4724,7 @@ impl<Signer: Sign> Channel<Signer> {
 
        fn internal_htlc_satisfies_config(
                &self, htlc: &msgs::UpdateAddHTLC, amt_to_forward: u64, outgoing_cltv_value: u32, config: &ChannelConfig,
-       ) -> Result<(), (&'static str, u16)> {
+       ) -> Result<u64, (&'static str, u16)> {
                let fee = amt_to_forward.checked_mul(config.forwarding_fee_proportional_millionths as u64)
                        .and_then(|prop_fee| (prop_fee / 1000000).checked_add(config.forwarding_fee_base_msat as u64));
                if fee.is_none() || htlc.amount_msat < fee.unwrap() ||
@@ -4740,15 +4740,17 @@ impl<Signer: Sign> Channel<Signer> {
                                0x1000 | 13, // incorrect_cltv_expiry
                        ));
                }
-               Ok(())
+               Ok(amt_to_forward)
        }
 
        /// Determines whether the parameters of an incoming HTLC to be forwarded satisfy the channel's
        /// [`ChannelConfig`]. This first looks at the channel's current [`ChannelConfig`], and if
        /// unsuccessful, falls back to the previous one if one exists.
+       ///
+       /// Returns the amount we should actually forward to our counterparty.
        pub fn htlc_satisfies_config(
                &self, htlc: &msgs::UpdateAddHTLC, amt_to_forward: u64, outgoing_cltv_value: u32,
-       ) -> Result<(), (&'static str, u16)> {
+       ) -> Result<u64, (&'static str, u16)> {
                self.internal_htlc_satisfies_config(&htlc, amt_to_forward, outgoing_cltv_value, &self.config())
                        .or_else(|err| {
                                if let Some(prev_config) = self.prev_config() {
index a17332225bbe8103776ce50b49afcae6723f4cfb..a39ca1e20c2fb3052253ac5ba7fc8b3f52c9eca7 100644 (file)
@@ -2014,7 +2014,7 @@ where
                        },
                };
 
-               let pending_forward_info = match next_hop {
+               let mut pending_forward_info = match next_hop {
                        onion_utils::Hop::Receive(next_hop_data) => {
                                // OUR PAYMENT!
                                match self.construct_recv_pending_htlc_info(next_hop_data, shared_secret, msg.payment_hash, msg.amount_msat, msg.cltv_expiry, None) {
@@ -2058,7 +2058,7 @@ where
                        }
                };
 
-               if let &PendingHTLCStatus::Forward(PendingHTLCInfo { ref routing, ref outgoing_amt_msat, ref outgoing_cltv_value, .. }) = &pending_forward_info {
+               if let &mut PendingHTLCStatus::Forward(PendingHTLCInfo { ref routing, ref mut outgoing_amt_msat, ref outgoing_cltv_value, .. }) = &mut pending_forward_info {
                        // If short_channel_id is 0 here, we'll reject the HTLC as there cannot be a channel
                        // with a short_channel_id of 0. This is important as various things later assume
                        // short_channel_id is non-0 in any ::Forward.
@@ -2115,8 +2115,9 @@ where
                                                if *outgoing_amt_msat < chan.get_counterparty_htlc_minimum_msat() { // amount_below_minimum
                                                        break Some(("HTLC amount was below the htlc_minimum_msat", 0x1000 | 11, chan_update_opt));
                                                }
-                                               if let Err((err, code)) = chan.htlc_satisfies_config(&msg, *outgoing_amt_msat, *outgoing_cltv_value) {
-                                                       break Some((err, code, chan_update_opt));
+                                               match chan.htlc_satisfies_config(&msg, *outgoing_amt_msat, *outgoing_cltv_value) {
+                                                       Err((err, code)) => break Some((err, code, chan_update_opt)),
+                                                       Ok(amt_to_forward_msat) => *outgoing_amt_msat = amt_to_forward_msat,
                                                }
                                                chan_update_opt
                                        } else {