@@ -414,7 +414,10 @@ CNode* CConnman::FindNode(const CService& addr)
414
414
415
415
bool CConnman::AlreadyConnectedToAddress (const CAddress& addr)
416
416
{
417
- return FindNode (static_cast <CNetAddr>(addr)) || FindNode (addr.ToStringIPPort ());
417
+ CNode* found_by_addr = FindNode (static_cast <CNetAddr>(addr));
418
+ CNode* found_by_ip_port = FindNode (addr.ToStringIPPort ());
419
+ return (found_by_addr && !found_by_addr->fDisconnect ) ||
420
+ (found_by_ip_port && !found_by_ip_port->fDisconnect );
418
421
}
419
422
420
423
bool CConnman::CheckIncomingNonce (uint64_t nonce)
@@ -479,8 +482,7 @@ CNode* CConnman::ConnectNode(CAddress addrConnect, const char *pszDest, bool fCo
479
482
480
483
// Look for an existing connection
481
484
CNode* pnode = FindNode (static_cast <CService>(addrConnect));
482
- if (pnode)
483
- {
485
+ if (pnode && !pnode->fDisconnect ) {
484
486
LogPrintf (" Failed to open new connection, already connected\n " );
485
487
return nullptr ;
486
488
}
@@ -506,7 +508,7 @@ CNode* CConnman::ConnectNode(CAddress addrConnect, const char *pszDest, bool fCo
506
508
// In that case, drop the connection that was just created.
507
509
LOCK (m_nodes_mutex);
508
510
CNode* pnode = FindNode (static_cast <CService>(addrConnect));
509
- if (pnode) {
511
+ if (pnode && !pnode-> fDisconnect ) {
510
512
LogPrintf (" Failed to open new connection, already connected\n " );
511
513
return nullptr ;
512
514
}
@@ -1465,6 +1467,16 @@ bool CConnman::ShouldRunInactivityChecks(const CNode& node, std::chrono::seconds
1465
1467
return node.m_connected + m_peer_connect_timeout < now;
1466
1468
}
1467
1469
1470
+ void CConnman::DowngradeToV1Transport (CNode& node)
1471
+ {
1472
+ AssertLockNotHeld (m_total_bytes_sent_mutex);
1473
+ LogPrint (BCLog::NET, " downgrading to v1 transport protocol for peer=%d\n " , node.GetId ());
1474
+ CAddress addr = node.addr ;
1475
+ addr.nServices = ServiceFlags (addr.nServices & ~NODE_P2P_V2);
1476
+ OpenNetworkConnection (addr, false , &node.grantOutbound , addr.ToStringIPPort ().c_str (), node.m_conn_type );
1477
+ node.m_bip324_shared_state ->key_exchange_complete = true ;
1478
+ }
1479
+
1468
1480
bool CConnman::InactivityCheck (const CNode& node) const
1469
1481
{
1470
1482
// Tests that see disconnects after using mocktime can start nodes with a
@@ -1762,6 +1774,14 @@ void CConnman::SocketHandlerConnected(const std::vector<CNode*>& nodes,
1762
1774
LogPrint (BCLog::NET, " socket closed for peer=%d\n " , pnode->GetId ());
1763
1775
}
1764
1776
pnode->CloseSocketDisconnect ();
1777
+
1778
+ // Downgrade if a v2 outbound connection was met with a disconnection before receiving anything
1779
+ if (pnode->PreferV2Conn () &&
1780
+ !pnode->IsInboundConn () &&
1781
+ (pnode->m_bip324_shared_state ->peer_ellswift_buf .empty () &&
1782
+ !pnode->m_bip324_node_state ->keys_derived )) {
1783
+ DowngradeToV1Transport (*pnode);
1784
+ }
1765
1785
} else if (nBytes < 0 ) {
1766
1786
// error
1767
1787
int nErr = WSAGetLastError ();
@@ -1781,7 +1801,17 @@ void CConnman::SocketHandlerConnected(const std::vector<CNode*>& nodes,
1781
1801
if (bytes_sent) RecordBytesSent (bytes_sent);
1782
1802
}
1783
1803
1784
- if (InactivityCheck (*pnode)) pnode->fDisconnect = true ;
1804
+ if (InactivityCheck (*pnode)) {
1805
+ pnode->fDisconnect = true ;
1806
+ // Downgrade if a v2 outbound connection was met with inactivity before receiving anything
1807
+ if (pnode->PreferV2Conn () &&
1808
+ !pnode->IsInboundConn () &&
1809
+ (pnode->m_bip324_shared_state ->peer_ellswift_buf .empty () &&
1810
+ !pnode->m_bip324_node_state ->keys_derived ) &&
1811
+ pnode->m_last_recv .load ().count () == 0 ) {
1812
+ DowngradeToV1Transport (*pnode);
1813
+ }
1814
+ }
1785
1815
}
1786
1816
}
1787
1817
@@ -2427,8 +2457,10 @@ void CConnman::OpenNetworkConnection(const CAddress& addrConnect, bool fCountFai
2427
2457
if (IsLocal (addrConnect) || banned_or_discouraged || AlreadyConnectedToAddress (addrConnect)) {
2428
2458
return ;
2429
2459
}
2430
- } else if (FindNode (std::string (pszDest)))
2431
- return ;
2460
+ } else {
2461
+ auto existing_node = FindNode (std::string (pszDest));
2462
+ if (existing_node && !existing_node->fDisconnect ) return ;
2463
+ }
2432
2464
2433
2465
CNode* pnode = ConnectNode (addrConnect, pszDest, fCountFailure , conn_type);
2434
2466
0 commit comments