Skip to content

Commit 202ad2f

Browse files
committed
f simplify disconnection logic a good bit with more utils
1 parent e3dd8fd commit 202ad2f

File tree

1 file changed

+41
-37
lines changed

1 file changed

+41
-37
lines changed

lightning/src/ln/channelmanager.rs

Lines changed: 41 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -4266,28 +4266,35 @@ where
42664266
Ok(())
42674267
}
42684268

4269+
fn unfunded_channel_count(
4270+
peer: &PeerState<<SP::Target as SignerProvider>::Signer>, best_block_height: u32
4271+
) -> usize {
4272+
let mut num_unfunded_channels = 0;
4273+
for (_, chan) in peer.channel_by_id.iter() {
4274+
if !chan.is_outbound() && chan.minimum_depth().unwrap_or(1) != 0 &&
4275+
chan.get_funding_tx_confirmations(best_block_height) == 0
4276+
{
4277+
num_unfunded_channels += 1;
4278+
}
4279+
}
4280+
num_unfunded_channels
4281+
}
4282+
42694283
/// Gets the number of peers which match the given filter which do not have any funded,
42704284
/// outbound, or 0-conf channels.
42714285
///
42724286
/// The filter is called for each peer and provided with the number of unfunded, inbound, and
42734287
/// non-0-conf channels we have with the peer.
42744288
fn peers_without_funded_channels<Filter>(&self, mut filter: Filter) -> usize
4275-
where Filter: FnMut(&PublicKey, &PeerState<<SP::Target as SignerProvider>::Signer>, usize) -> bool {
4289+
where Filter: FnMut(&PeerState<<SP::Target as SignerProvider>::Signer>) -> bool {
42764290
let mut peers_without_funded_channels = 0;
42774291
let best_block_height = self.best_block.read().unwrap().height();
42784292
{
42794293
let peer_state_lock = self.per_peer_state.read().unwrap();
4280-
for (node_id, peer_mtx) in peer_state_lock.iter() {
4294+
for (_, peer_mtx) in peer_state_lock.iter() {
42814295
let peer = peer_mtx.lock().unwrap();
4282-
let mut num_unfunded_channels = 0;
4283-
for (_, chan) in peer.channel_by_id.iter() {
4284-
if !chan.is_outbound() && chan.minimum_depth().unwrap_or(1) != 0 &&
4285-
chan.get_funding_tx_confirmations(best_block_height) == 0
4286-
{
4287-
num_unfunded_channels += 1;
4288-
}
4289-
}
4290-
if !filter(node_id, &*peer, num_unfunded_channels) { continue; }
4296+
if !filter(&*peer) { continue; }
4297+
let num_unfunded_channels = Self::unfunded_channel_count(&peer, best_block_height);
42914298
if num_unfunded_channels == peer.channel_by_id.len() {
42924299
peers_without_funded_channels += 1;
42934300
}
@@ -4319,21 +4326,16 @@ where
43194326
// Get the number of peers with channels, but without funded ones. We don't care too much
43204327
// about peers that never open a channel, so we filter by peers that have at least one
43214328
// channel, and then limit the number of those with unfunded channels.
4322-
let mut this_node_unfunded_channels = 0;
4323-
let peers_without_funded_channels = self.peers_without_funded_channels(
4324-
|node_id, node, unfunded_channels| {
4325-
if node_id == counterparty_node_id {
4326-
this_node_unfunded_channels = unfunded_channels;
4327-
}
4328-
!node.channel_by_id.is_empty()
4329-
});
4330-
if this_node_unfunded_channels >= MAX_UNFUNDED_CHANS_PER_PEER {
4329+
let peers_without_funded_channels = self.peers_without_funded_channels(|node| !node.channel_by_id.is_empty());
4330+
let mut peer_state_lock = peer_state_mutex_opt.unwrap().lock().unwrap();
4331+
let peer_state = &mut *peer_state_lock;
4332+
4333+
let best_block_height = self.best_block.read().unwrap().height();
4334+
if Self::unfunded_channel_count(peer_state, best_block_height) >= MAX_UNFUNDED_CHANS_PER_PEER {
43314335
return Err(MsgHandleErrInternal::send_err_msg_no_close(
43324336
format!("Refusing more than {} unfunded channels.", MAX_UNFUNDED_CHANS_PER_PEER),
43334337
msg.temporary_channel_id.clone()));
43344338
}
4335-
let mut peer_state_lock = peer_state_mutex_opt.unwrap().lock().unwrap();
4336-
let peer_state = &mut *peer_state_lock;
43374339
// If this peer already has some channels, a new channel won't increase our number of peers
43384340
// with unfunded channels, so as long as we aren't over the maximum number of unfunded
43394341
// channels per-peer we can accept channels from a peer with existing ones.
@@ -4345,7 +4347,7 @@ where
43454347

43464348
let mut channel = match Channel::new_from_req(&self.fee_estimator, &self.entropy_source, &self.signer_provider,
43474349
counterparty_node_id.clone(), &self.channel_type_features(), &peer_state.latest_features, msg, user_channel_id,
4348-
&self.default_configuration, self.best_block.read().unwrap().height(), &self.logger, outbound_scid_alias)
4350+
&self.default_configuration, best_block_height, &self.logger, outbound_scid_alias)
43494351
{
43504352
Err(e) => {
43514353
self.outbound_scid_aliases.lock().unwrap().remove(&outbound_scid_alias);
@@ -6299,25 +6301,19 @@ where
62996301
let _persistence_guard = PersistenceNotifierGuard::notify_on_drop(&self.total_consistency_lock, &self.persistence_notifier);
63006302

63016303
// If we have too many peers connected which don't have funded channels, disconnect the
6302-
// peer immediately. If we have a bunch of unfunded channels taking up space in memory for
6303-
// disconnected peers, we still let new peers connect, but we'll reject new channels from
6304-
// them.
6305-
let mut this_peer_has_funded_channels = false;
6306-
let connected_peers_without_funded_channels = self.peers_without_funded_channels(
6307-
|node_id, node, num_unfunded_channels| {
6308-
if node_id == counterparty_node_id && num_unfunded_channels != node.channel_by_id.len() {
6309-
this_peer_has_funded_channels = true;
6310-
}
6311-
node.is_connected
6312-
});
6313-
if inbound && !this_peer_has_funded_channels && connected_peers_without_funded_channels >= MAX_NO_CHANNEL_PEERS {
6314-
return Err(());
6315-
}
6304+
// peer immediately (as long as it doesn't have funded channels). If we have a bunch of
6305+
// unfunded channels taking up space in memory for disconnected peers, we still let new
6306+
// peers connect, but we'll reject new channels from them.
6307+
let connected_peers_without_funded_channels = self.peers_without_funded_channels(|node| node.is_connected);
6308+
let inbound_peer_limited = inbound && connected_peers_without_funded_channels >= MAX_NO_CHANNEL_PEERS;
63166309

63176310
{
63186311
let mut peer_state_lock = self.per_peer_state.write().unwrap();
63196312
match peer_state_lock.entry(counterparty_node_id.clone()) {
63206313
hash_map::Entry::Vacant(e) => {
6314+
if inbound_peer_limited {
6315+
return Err(());
6316+
}
63216317
e.insert(Mutex::new(PeerState {
63226318
channel_by_id: HashMap::new(),
63236319
latest_features: init_msg.features.clone(),
@@ -6328,6 +6324,14 @@ where
63286324
hash_map::Entry::Occupied(e) => {
63296325
let mut peer_state = e.get().lock().unwrap();
63306326
peer_state.latest_features = init_msg.features.clone();
6327+
6328+
let best_block_height = self.best_block.read().unwrap().height();
6329+
if Self::unfunded_channel_count(&*peer_state, best_block_height) ==
6330+
peer_state.channel_by_id.len() && inbound_peer_limited
6331+
{
6332+
return Err(());
6333+
}
6334+
63316335
debug_assert!(!peer_state.is_connected, "A peer shouldn't be connected twice");
63326336
peer_state.is_connected = true;
63336337
},

0 commit comments

Comments
 (0)