From 863f64bee9f19882178245500fea4abcaff62755 Mon Sep 17 00:00:00 2001 From: Matt Corallo Date: Sat, 13 Nov 2021 21:28:49 +0000 Subject: [PATCH] XXX: BAD WIP --- lightning/src/ln/channel.rs | 22 +++++++++++++++++++++- lightning/src/ln/channelmanager.rs | 17 ++++++++++++++++- 2 files changed, 37 insertions(+), 2 deletions(-) diff --git a/lightning/src/ln/channel.rs b/lightning/src/ln/channel.rs index bda7d3411..746222506 100644 --- a/lightning/src/ln/channel.rs +++ b/lightning/src/ln/channel.rs @@ -2430,7 +2430,10 @@ panic!(); fn check_state_for_htlc_msg(&self) -> Result<(), ChannelError> { if (self.channel_state & (ChannelState::ChannelFunded as u32)) != (ChannelState::ChannelFunded as u32) { - return Err(ChannelError::Close("Got HTLC message when channel was not in an operational state".to_owned())); + let early_funding_locked_state = ChannelState::FundingSent as u32 | ChannelState::OurFundingLocked as u32; + if self.channel_state & early_funding_locked_state != early_funding_locked_state { + return Err(ChannelError::Close("Got HTLC message when channel was not in an operational state".to_owned())); + } } if self.channel_state & (ChannelState::PeerDisconnected as u32) == ChannelState::PeerDisconnected as u32 { return Err(ChannelError::Close("Peer sent HTLC message when we needed a channel_reestablish".to_owned())); @@ -4282,6 +4285,7 @@ panic!(); /// Returns true if this channel is fully established and not known to be closing. /// Allowed in any state (including after shutdown) + #[inline] pub fn is_usable(&self) -> bool { let mask = ChannelState::ChannelFunded as u32 | BOTH_SIDES_SHUTDOWN_MASK; (self.channel_state & mask) == (ChannelState::ChannelFunded as u32) && !self.monitor_pending_funding_locked @@ -4290,10 +4294,26 @@ panic!(); /// Returns true if this channel is currently available for use. This is a superset of /// is_usable() and considers things like the channel being temporarily disabled. /// Allowed in any state (including after shutdown) + #[inline] pub fn is_live(&self) -> bool { self.is_usable() && (self.channel_state & (ChannelState::PeerDisconnected as u32) == 0) } + /// Returns true if this channel is currently available for receiving inbound payments *to us*. + /// This may be true even if [`is_usable`] (or [`is_live`]) is *not* true, if our counterparty + /// is willing to forward payments to us with 0 confirmations on the funding transaction. + /// Note that payments received on this channel MUST NOT be forwarded unless we've marked the + /// channel trusted or [`is_usable`] is also true. + /// Allowed in any state (including after shutdown) + pub fn is_receivable(&self) -> bool { + let non_live_state_reqd = ChannelState::TheirFundingLocked as u32 | ChannelState::ChannelState::FundingSent as u32; + self.is_live() || ( + (self.channel_state & BOTH_SIDES_SHUTDOWN_MASK) == 0 && + (self.channel_state & ChannelState::PeerDisconnected as u32) == 0 && + (self.channel_state & non_live_state_reqd) == non_live_state_reqd + ) + } + /// Returns true if this channel has been marked as awaiting a monitor update to move forward. /// Allowed in any state (including after shutdown) pub fn is_awaiting_monitor_update(&self) -> bool { diff --git a/lightning/src/ln/channelmanager.rs b/lightning/src/ln/channelmanager.rs index b1ea5b2ea..60eb5605b 100644 --- a/lightning/src/ln/channelmanager.rs +++ b/lightning/src/ln/channelmanager.rs @@ -1274,6 +1274,7 @@ pub struct ChannelDetails { /// /// This is a strict superset of `is_funding_locked`. pub is_usable: bool, + pub is_receivable: bool, /// True if this channel is (or will be) publicly-announced. pub is_public: bool, } @@ -1828,7 +1829,8 @@ impl ChannelMana force_close_spend_delay: channel.get_counterparty_selected_contest_delay(), is_outbound: channel.is_outbound(), is_funding_locked: channel.is_usable(), - is_usable: channel.is_live(), + is_outbound_usable: channel.is_live(), + is_inbound_usable: channel.is_live(), is_public: channel.should_announce(), }); } @@ -1861,6 +1863,19 @@ impl ChannelMana self.list_channels_with_filter(|&(_, ref channel)| channel.is_live()) } + /// Gets the list of channels on which we can receive a payment to us, in random order. Useful + /// to generate a list of route hints when generating an invoice. + /// + /// These are guaranteed to have their [`ChannelDetails::is_receivable`] value set to true, see the + /// documentation for [`ChannelDetails::is_receivable`] for more info on exactly what the criteria + /// are. + pub fn list_receivable_channels(&self) -> Vec { + // Note we use is_live here instead of usable which leads to somewhat confused + // internal/external nomenclature, but that's ok cause that's probably what the user + // really wanted anyway. + self.list_channels_with_filter(|&(_, ref channel)| channel.is_receivable()) + } + /// Helper function that issues the channel close events fn issue_channel_close_events(&self, channel: &Channel, closure_reason: ClosureReason) { let mut pending_events_lock = self.pending_events.lock().unwrap(); -- 2.39.5