Try to find a connection to evict when the node is full. * Extreme care must be taken to avoid opening the node to attacker * triggered network partitioning. * The strategy used here is to protect a small number of peers * for each of several distinct characteristics which are difficult * to forge. In order to partition a node the attacker must be * simultaneously better at all of
| 1692 | * simultaneously better at all of them than honest peers. |
| 1693 | */ |
| 1694 | bool CConnman::AttemptToEvictConnection() |
| 1695 | { |
| 1696 | AssertLockNotHeld(m_nodes_mutex); |
| 1697 | |
| 1698 | std::vector<NodeEvictionCandidate> vEvictionCandidates; |
| 1699 | { |
| 1700 | |
| 1701 | LOCK(m_nodes_mutex); |
| 1702 | for (const CNode* node : m_nodes) { |
| 1703 | if (node->fDisconnect) |
| 1704 | continue; |
| 1705 | NodeEvictionCandidate candidate{ |
| 1706 | .id = node->GetId(), |
| 1707 | .m_connected = node->m_connected, |
| 1708 | .m_min_ping_time = node->m_min_ping_time, |
| 1709 | .m_last_block_time = node->m_last_block_time, |
| 1710 | .m_last_tx_time = node->m_last_tx_time, |
| 1711 | .fRelevantServices = node->m_has_all_wanted_services, |
| 1712 | .m_relay_txs = node->m_relays_txs.load(), |
| 1713 | .fBloomFilter = node->m_bloom_filter_loaded.load(), |
| 1714 | .nKeyedNetGroup = node->nKeyedNetGroup, |
| 1715 | .prefer_evict = node->m_prefer_evict, |
| 1716 | .m_is_local = node->addr.IsLocal(), |
| 1717 | .m_network = node->ConnectedThroughNetwork(), |
| 1718 | .m_noban = node->HasPermission(NetPermissionFlags::NoBan), |
| 1719 | .m_conn_type = node->m_conn_type, |
| 1720 | }; |
| 1721 | vEvictionCandidates.push_back(candidate); |
| 1722 | } |
| 1723 | } |
| 1724 | const std::optional<NodeId> node_id_to_evict = SelectNodeToEvict(std::move(vEvictionCandidates)); |
| 1725 | if (!node_id_to_evict) { |
| 1726 | return false; |
| 1727 | } |
| 1728 | LOCK(m_nodes_mutex); |
| 1729 | for (CNode* pnode : m_nodes) { |
| 1730 | if (pnode->GetId() == *node_id_to_evict) { |
| 1731 | LogDebug(BCLog::NET, "selected %s connection for eviction, %s", pnode->ConnectionTypeAsString(), pnode->DisconnectMsg()); |
| 1732 | TRACEPOINT(net, evicted_inbound_connection, |
| 1733 | pnode->GetId(), |
| 1734 | pnode->m_addr_name.c_str(), |
| 1735 | pnode->ConnectionTypeAsString().c_str(), |
| 1736 | pnode->ConnectedThroughNetwork(), |
| 1737 | TicksSinceEpoch<std::chrono::seconds>(pnode->m_connected)); |
| 1738 | pnode->fDisconnect = true; |
| 1739 | return true; |
| 1740 | } |
| 1741 | } |
| 1742 | return false; |
| 1743 | } |
| 1744 | |
| 1745 | void CConnman::AcceptConnection(const ListenSocket& hListenSocket) { |
| 1746 | AssertLockNotHeld(m_nodes_mutex); |
nothing calls this directly
no test coverage detected