@@ -1404,13 +1404,12 @@ bool CConnman::InactivityCheck(const CNode& node) const
1404
1404
return false ;
1405
1405
}
1406
1406
1407
- bool CConnman::GenerateSelectSet (const std::vector<CNode*>& nodes,
1408
- std::set<SOCKET>& recv_set,
1409
- std::set<SOCKET>& send_set,
1410
- std::set<SOCKET>& error_set)
1407
+ Sock::EventsPerSock CConnman::GenerateWaitSockets (Span<CNode* const > nodes)
1411
1408
{
1409
+ Sock::EventsPerSock events_per_sock;
1410
+
1412
1411
for (const ListenSocket& hListenSocket : vhListenSocket) {
1413
- recv_set. insert (hListenSocket.sock -> Get () );
1412
+ events_per_sock. emplace (hListenSocket.sock , Sock::Events{Sock::RECV} );
1414
1413
}
1415
1414
1416
1415
for (CNode* pnode : nodes) {
@@ -1437,172 +1436,49 @@ bool CConnman::GenerateSelectSet(const std::vector<CNode*>& nodes,
1437
1436
continue ;
1438
1437
}
1439
1438
1440
- error_set. insert (pnode-> m_sock -> Get ()) ;
1439
+ Sock::Event requested{ 0 } ;
1441
1440
if (select_send) {
1442
- send_set.insert (pnode->m_sock ->Get ());
1443
- continue ;
1444
- }
1445
- if (select_recv) {
1446
- recv_set.insert (pnode->m_sock ->Get ());
1447
- }
1448
- }
1449
-
1450
- return !recv_set.empty () || !send_set.empty () || !error_set.empty ();
1451
- }
1452
-
1453
- #ifdef USE_POLL
1454
- void CConnman::SocketEvents (const std::vector<CNode*>& nodes,
1455
- std::set<SOCKET>& recv_set,
1456
- std::set<SOCKET>& send_set,
1457
- std::set<SOCKET>& error_set)
1458
- {
1459
- std::set<SOCKET> recv_select_set, send_select_set, error_select_set;
1460
- if (!GenerateSelectSet (nodes, recv_select_set, send_select_set, error_select_set)) {
1461
- interruptNet.sleep_for (std::chrono::milliseconds (SELECT_TIMEOUT_MILLISECONDS));
1462
- return ;
1463
- }
1464
-
1465
- std::unordered_map<SOCKET, struct pollfd > pollfds;
1466
- for (SOCKET socket_id : recv_select_set) {
1467
- pollfds[socket_id].fd = socket_id;
1468
- pollfds[socket_id].events |= POLLIN;
1469
- }
1470
-
1471
- for (SOCKET socket_id : send_select_set) {
1472
- pollfds[socket_id].fd = socket_id;
1473
- pollfds[socket_id].events |= POLLOUT;
1474
- }
1475
-
1476
- for (SOCKET socket_id : error_select_set) {
1477
- pollfds[socket_id].fd = socket_id;
1478
- // These flags are ignored, but we set them for clarity
1479
- pollfds[socket_id].events |= POLLERR|POLLHUP;
1480
- }
1481
-
1482
- std::vector<struct pollfd > vpollfds;
1483
- vpollfds.reserve (pollfds.size ());
1484
- for (auto it : pollfds) {
1485
- vpollfds.push_back (std::move (it.second ));
1486
- }
1487
-
1488
- if (poll (vpollfds.data (), vpollfds.size (), SELECT_TIMEOUT_MILLISECONDS) < 0 ) return ;
1489
-
1490
- if (interruptNet) return ;
1491
-
1492
- for (struct pollfd pollfd_entry : vpollfds) {
1493
- if (pollfd_entry.revents & POLLIN) recv_set.insert (pollfd_entry.fd );
1494
- if (pollfd_entry.revents & POLLOUT) send_set.insert (pollfd_entry.fd );
1495
- if (pollfd_entry.revents & (POLLERR|POLLHUP)) error_set.insert (pollfd_entry.fd );
1496
- }
1497
- }
1498
- #else
1499
- void CConnman::SocketEvents (const std::vector<CNode*>& nodes,
1500
- std::set<SOCKET>& recv_set,
1501
- std::set<SOCKET>& send_set,
1502
- std::set<SOCKET>& error_set)
1503
- {
1504
- std::set<SOCKET> recv_select_set, send_select_set, error_select_set;
1505
- if (!GenerateSelectSet (nodes, recv_select_set, send_select_set, error_select_set)) {
1506
- interruptNet.sleep_for (std::chrono::milliseconds (SELECT_TIMEOUT_MILLISECONDS));
1507
- return ;
1508
- }
1509
-
1510
- //
1511
- // Find which sockets have data to receive
1512
- //
1513
- struct timeval timeout;
1514
- timeout.tv_sec = 0 ;
1515
- timeout.tv_usec = SELECT_TIMEOUT_MILLISECONDS * 1000 ; // frequency to poll pnode->vSend
1516
-
1517
- fd_set fdsetRecv;
1518
- fd_set fdsetSend;
1519
- fd_set fdsetError;
1520
- FD_ZERO (&fdsetRecv);
1521
- FD_ZERO (&fdsetSend);
1522
- FD_ZERO (&fdsetError);
1523
- SOCKET hSocketMax = 0 ;
1524
-
1525
- for (SOCKET hSocket : recv_select_set) {
1526
- FD_SET (hSocket, &fdsetRecv);
1527
- hSocketMax = std::max (hSocketMax, hSocket);
1528
- }
1529
-
1530
- for (SOCKET hSocket : send_select_set) {
1531
- FD_SET (hSocket, &fdsetSend);
1532
- hSocketMax = std::max (hSocketMax, hSocket);
1533
- }
1534
-
1535
- for (SOCKET hSocket : error_select_set) {
1536
- FD_SET (hSocket, &fdsetError);
1537
- hSocketMax = std::max (hSocketMax, hSocket);
1538
- }
1539
-
1540
- int nSelect = select (hSocketMax + 1 , &fdsetRecv, &fdsetSend, &fdsetError, &timeout);
1541
-
1542
- if (interruptNet)
1543
- return ;
1544
-
1545
- if (nSelect == SOCKET_ERROR)
1546
- {
1547
- int nErr = WSAGetLastError ();
1548
- LogPrintf (" socket select error %s\n " , NetworkErrorString (nErr));
1549
- for (unsigned int i = 0 ; i <= hSocketMax; i++)
1550
- FD_SET (i, &fdsetRecv);
1551
- FD_ZERO (&fdsetSend);
1552
- FD_ZERO (&fdsetError);
1553
- if (!interruptNet.sleep_for (std::chrono::milliseconds (SELECT_TIMEOUT_MILLISECONDS)))
1554
- return ;
1555
- }
1556
-
1557
- for (SOCKET hSocket : recv_select_set) {
1558
- if (FD_ISSET (hSocket, &fdsetRecv)) {
1559
- recv_set.insert (hSocket);
1441
+ requested = Sock::SEND;
1442
+ } else if (select_recv) {
1443
+ requested = Sock::RECV;
1560
1444
}
1561
- }
1562
1445
1563
- for (SOCKET hSocket : send_select_set) {
1564
- if (FD_ISSET (hSocket, &fdsetSend)) {
1565
- send_set.insert (hSocket);
1566
- }
1446
+ events_per_sock.emplace (pnode->m_sock , Sock::Events{requested});
1567
1447
}
1568
1448
1569
- for (SOCKET hSocket : error_select_set) {
1570
- if (FD_ISSET (hSocket, &fdsetError)) {
1571
- error_set.insert (hSocket);
1572
- }
1573
- }
1449
+ return events_per_sock;
1574
1450
}
1575
- #endif
1576
1451
1577
1452
void CConnman::SocketHandler ()
1578
1453
{
1579
1454
AssertLockNotHeld (m_total_bytes_sent_mutex);
1580
1455
1581
- std::set<SOCKET> recv_set;
1582
- std::set<SOCKET> send_set;
1583
- std::set<SOCKET> error_set;
1456
+ Sock::EventsPerSock events_per_sock;
1584
1457
1585
1458
{
1586
1459
const NodesSnapshot snap{*this , /* shuffle=*/ false };
1587
1460
1461
+ const auto timeout = std::chrono::milliseconds (SELECT_TIMEOUT_MILLISECONDS);
1462
+
1588
1463
// Check for the readiness of the already connected sockets and the
1589
1464
// listening sockets in one call ("readiness" as in poll(2) or
1590
1465
// select(2)). If none are ready, wait for a short while and return
1591
1466
// empty sets.
1592
- SocketEvents (snap.Nodes (), recv_set, send_set, error_set);
1467
+ events_per_sock = GenerateWaitSockets (snap.Nodes ());
1468
+ if (events_per_sock.empty () || !events_per_sock.begin ()->first ->WaitMany (timeout, events_per_sock)) {
1469
+ interruptNet.sleep_for (timeout);
1470
+ }
1593
1471
1594
1472
// Service (send/receive) each of the already connected nodes.
1595
- SocketHandlerConnected (snap.Nodes (), recv_set, send_set, error_set );
1473
+ SocketHandlerConnected (snap.Nodes (), events_per_sock );
1596
1474
}
1597
1475
1598
1476
// Accept new connections from listening sockets.
1599
- SocketHandlerListening (recv_set );
1477
+ SocketHandlerListening (events_per_sock );
1600
1478
}
1601
1479
1602
1480
void CConnman::SocketHandlerConnected (const std::vector<CNode*>& nodes,
1603
- const std::set<SOCKET>& recv_set,
1604
- const std::set<SOCKET>& send_set,
1605
- const std::set<SOCKET>& error_set)
1481
+ const Sock::EventsPerSock& events_per_sock)
1606
1482
{
1607
1483
AssertLockNotHeld (m_total_bytes_sent_mutex);
1608
1484
@@ -1621,9 +1497,12 @@ void CConnman::SocketHandlerConnected(const std::vector<CNode*>& nodes,
1621
1497
if (!pnode->m_sock ) {
1622
1498
continue ;
1623
1499
}
1624
- recvSet = recv_set.count (pnode->m_sock ->Get ()) > 0 ;
1625
- sendSet = send_set.count (pnode->m_sock ->Get ()) > 0 ;
1626
- errorSet = error_set.count (pnode->m_sock ->Get ()) > 0 ;
1500
+ const auto it = events_per_sock.find (pnode->m_sock );
1501
+ if (it != events_per_sock.end ()) {
1502
+ recvSet = it->second .occurred & Sock::RECV;
1503
+ sendSet = it->second .occurred & Sock::SEND;
1504
+ errorSet = it->second .occurred & Sock::ERR;
1505
+ }
1627
1506
}
1628
1507
if (recvSet || errorSet)
1629
1508
{
@@ -1693,13 +1572,14 @@ void CConnman::SocketHandlerConnected(const std::vector<CNode*>& nodes,
1693
1572
}
1694
1573
}
1695
1574
1696
- void CConnman::SocketHandlerListening (const std::set<SOCKET>& recv_set )
1575
+ void CConnman::SocketHandlerListening (const Sock::EventsPerSock& events_per_sock )
1697
1576
{
1698
1577
for (const ListenSocket& listen_socket : vhListenSocket) {
1699
1578
if (interruptNet) {
1700
1579
return ;
1701
1580
}
1702
- if (recv_set.count (listen_socket.sock ->Get ()) > 0 ) {
1581
+ const auto it = events_per_sock.find (listen_socket.sock );
1582
+ if (it != events_per_sock.end () && it->second .occurred & Sock::RECV) {
1703
1583
AcceptConnection (listen_socket);
1704
1584
}
1705
1585
}
0 commit comments