6 #if defined(HAVE_CONFIG_H)
31 #if HAVE_DECL_GETIFADDRS && HAVE_DECL_FREEIFADDRS
40 #include <miniupnpc/miniupnpc.h>
41 #include <miniupnpc/upnpcommands.h>
42 #include <miniupnpc/upnperrors.h>
45 static_assert(MINIUPNPC_API_VERSION >= 10,
"miniUPnPc API version >= 10 assumed");
50 #include <unordered_map>
58 const char*
const ANCHORS_DATABASE_FILENAME =
"anchors.dat";
61 static constexpr std::chrono::minutes DUMP_PEERS_INTERVAL{15};
64 static constexpr
int DNSSEEDS_TO_QUERY_AT_ONCE = 3;
75 static constexpr std::chrono::seconds DNSSEEDS_DELAY_FEW_PEERS{11};
76 static constexpr std::chrono::minutes DNSSEEDS_DELAY_MANY_PEERS{5};
77 static constexpr
int DNSSEEDS_DELAY_PEER_THRESHOLD = 1000;
80 #define FEELER_SLEEP_WINDOW 1
83 #if !defined(MSG_NOSIGNAL)
84 #define MSG_NOSIGNAL 0
88 #if !defined(MSG_DONTWAIT)
89 #define MSG_DONTWAIT 0
95 BF_EXPLICIT = (1U << 0),
96 BF_REPORT_ERROR = (1U << 1),
101 BF_DONT_ADVERTISE = (1U << 2),
106 static const uint64_t SELECT_TIMEOUT_MILLISECONDS = 50;
110 static const uint64_t RANDOMIZER_ID_NETGROUP = 0x6c0edd8036ef4036ULL;
111 static const uint64_t RANDOMIZER_ID_LOCALHOSTNONCE = 0xd93e69e2bbfa5735ULL;
112 static const uint64_t RANDOMIZER_ID_ADDRCACHE = 0x1cf2e4ddd306dda9ULL;
120 std::map<CNetAddr, LocalServiceInfo> mapLocalHost
GUARDED_BY(cs_mapLocalHost);
127 m_addr_fetches.push_back(strDest);
142 int nBestReachability = -1;
144 LOCK(cs_mapLocalHost);
145 for (
const auto& entry : mapLocalHost)
147 int nScore = entry.second.nScore;
148 int nReachability = entry.first.GetReachabilityFrom(paddrPeer);
149 if (nReachability > nBestReachability || (nReachability == nBestReachability && nScore > nBestScore))
151 addr =
CService(entry.first, entry.second.nPort);
152 nBestReachability = nReachability;
157 return nBestScore >= 0;
161 static std::vector<CAddress> convertSeed6(
const std::vector<SeedSpec6> &vSeedsIn)
167 const int64_t nOneWeek = 7*24*60*60;
168 std::vector<CAddress> vSeedsOut;
169 vSeedsOut.reserve(vSeedsIn.size());
171 for (
const auto& seed_in : vSeedsIn) {
173 memcpy(&ip, seed_in.addr,
sizeof(ip));
176 vSeedsOut.push_back(addr);
191 ret =
CAddress(addr, nLocalServices);
197 static int GetnScore(
const CService& addr)
199 LOCK(cs_mapLocalHost);
200 if (mapLocalHost.count(addr) == 0)
return 0;
201 return mapLocalHost[addr].nScore;
254 LOCK(cs_mapLocalHost);
255 bool fAlready = mapLocalHost.count(addr) > 0;
257 if (!fAlready || nScore >= info.
nScore) {
258 info.
nScore = nScore + (fAlready ? 1 : 0);
273 LOCK(cs_mapLocalHost);
275 mapLocalHost.erase(addr);
282 LOCK(cs_mapLocalHost);
283 vfLimited[net] = !reachable;
288 LOCK(cs_mapLocalHost);
289 return !vfLimited[net];
301 LOCK(cs_mapLocalHost);
302 if (mapLocalHost.count(addr) == 0)
304 mapLocalHost[addr].nScore++;
313 LOCK(cs_mapLocalHost);
314 return mapLocalHost.count(addr) > 0;
320 for (
CNode* pnode : vNodes) {
321 if (static_cast<CNetAddr>(pnode->
addr) == ip) {
331 for (
CNode* pnode : vNodes) {
332 if (subNet.
Match(static_cast<CNetAddr>(pnode->
addr))) {
342 for (
CNode* pnode : vNodes) {
353 for (
CNode* pnode : vNodes) {
354 if (static_cast<CService>(pnode->
addr) == addr) {
369 for (
const CNode* pnode : vNodes) {
380 struct sockaddr_storage sockaddr_bind;
381 socklen_t sockaddr_bind_len =
sizeof(sockaddr_bind);
383 if (!getsockname(sock, (
struct sockaddr*)&sockaddr_bind, &sockaddr_bind_len)) {
384 addr_bind.
SetSockAddr((
const struct sockaddr*)&sockaddr_bind);
396 if (pszDest ==
nullptr) {
404 LogPrintf(
"Failed to open new connection, already connected\n");
411 pszDest ? pszDest : addrConnect.
ToString(),
417 std::vector<CService> resolved;
433 LogPrintf(
"Failed to open new connection, already connected\n");
440 bool connected =
false;
444 bool proxyConnectionFailed =
false;
460 if (!proxyConnectionFailed) {
471 int port = default_port;
473 bool proxyConnectionFailed;
484 CAddress addr_bind = GetBindAddress(hSocket);
521 return "outbound-full-relay";
523 return "block-relay-only";
538 if (addrName.empty()) {
539 addrName = addrNameIn;
551 error(
"Addr local already set for node: %i. Refusing to change from %s to %s",
id, addrLocal.
ToString(), addrLocalIn.
ToString());
553 addrLocal = addrLocalIn;
563 #define X(name) stats.name = name
600 X(mapRecvBytesPerMsgCmd);
618 std::chrono::microseconds ping_wait{0};
620 ping_wait = GetTime<std::chrono::microseconds>() -
m_ping_start.load();
649 const auto time = GetTime<std::chrono::microseconds>();
651 nLastRecv = std::chrono::duration_cast<std::chrono::seconds>(time).
count();
652 nRecvBytes += nBytes;
666 uint32_t out_err_raw_size{0};
671 mapRecvBytesPerMsgCmd.find(NET_MESSAGE_COMMAND_OTHER)->second += out_err_raw_size;
677 mapMsgCmdSize::iterator i = mapRecvBytesPerMsgCmd.find(result->m_command);
678 if (i == mapRecvBytesPerMsgCmd.end())
679 i = mapRecvBytesPerMsgCmd.find(NET_MESSAGE_COMMAND_OTHER);
680 assert(i != mapRecvBytesPerMsgCmd.end());
681 i->second += result->m_raw_message_size;
684 vRecvMsg.push_back(std::move(*result));
697 unsigned int nCopy = std::min(nRemaining, nBytes);
710 catch (
const std::exception&) {
736 unsigned int nCopy = std::min(nRemaining, nBytes);
781 out_err_raw_size = msg->m_raw_message_size;
786 out_err_raw_size = msg->m_raw_message_size;
810 auto it = pnode->vSendMsg.begin();
811 size_t nSentSize = 0;
813 while (
it != pnode->vSendMsg.end()) {
814 const auto &data = *
it;
825 pnode->nSendBytes += nBytes;
852 if (
it == pnode->vSendMsg.end()) {
856 pnode->vSendMsg.erase(pnode->vSendMsg.begin(),
it);
860 struct NodeEvictionCandidate
863 int64_t nTimeConnected;
864 int64_t nMinPingUsecTime;
865 int64_t nLastBlockTime;
867 bool fRelevantServices;
870 uint64_t nKeyedNetGroup;
875 static bool ReverseCompareNodeMinPingTime(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b)
877 return a.nMinPingUsecTime > b.nMinPingUsecTime;
880 static bool ReverseCompareNodeTimeConnected(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b)
882 return a.nTimeConnected > b.nTimeConnected;
885 static bool CompareLocalHostTimeConnected(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b)
887 if (a.m_is_local != b.m_is_local)
return b.m_is_local;
888 return a.nTimeConnected > b.nTimeConnected;
891 static bool CompareNetGroupKeyed(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b) {
892 return a.nKeyedNetGroup < b.nKeyedNetGroup;
895 static bool CompareNodeBlockTime(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b)
898 if (a.nLastBlockTime != b.nLastBlockTime)
return a.nLastBlockTime < b.nLastBlockTime;
899 if (a.fRelevantServices != b.fRelevantServices)
return b.fRelevantServices;
900 return a.nTimeConnected > b.nTimeConnected;
903 static bool CompareNodeTXTime(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b)
906 if (a.nLastTXTime != b.nLastTXTime)
return a.nLastTXTime < b.nLastTXTime;
907 if (a.fRelayTxes != b.fRelayTxes)
return b.fRelayTxes;
908 if (a.fBloomFilter != b.fBloomFilter)
return a.fBloomFilter;
909 return a.nTimeConnected > b.nTimeConnected;
913 static bool CompareNodeBlockRelayOnlyTime(
const NodeEvictionCandidate &a,
const NodeEvictionCandidate &b)
915 if (a.fRelayTxes != b.fRelayTxes)
return a.fRelayTxes;
916 if (a.nLastBlockTime != b.nLastBlockTime)
return a.nLastBlockTime < b.nLastBlockTime;
917 if (a.fRelevantServices != b.fRelevantServices)
return b.fRelevantServices;
918 return a.nTimeConnected > b.nTimeConnected;
922 template<
typename T,
typename Comparator>
923 static void EraseLastKElements(std::vector<T> &elements, Comparator comparator,
size_t k)
925 std::sort(elements.begin(), elements.end(), comparator);
926 size_t eraseSize = std::min(k, elements.size());
927 elements.erase(elements.end() - eraseSize, elements.end());
940 std::vector<NodeEvictionCandidate> vEvictionCandidates;
944 for (
const CNode* node : vNodes) {
947 if (!node->IsInboundConn())
949 if (node->fDisconnect)
951 bool peer_relay_txes =
false;
952 bool peer_filter_not_null =
false;
953 if (node->m_tx_relay !=
nullptr) {
954 LOCK(node->m_tx_relay->cs_filter);
955 peer_relay_txes = node->m_tx_relay->fRelayTxes;
956 peer_filter_not_null = node->m_tx_relay->pfilter !=
nullptr;
958 NodeEvictionCandidate candidate = {node->GetId(), node->nTimeConnected, node->nMinPingUsecTime,
959 node->nLastBlockTime, node->nLastTXTime,
961 peer_relay_txes, peer_filter_not_null, node->nKeyedNetGroup,
962 node->m_prefer_evict, node->addr.IsLocal()};
963 vEvictionCandidates.push_back(candidate);
971 EraseLastKElements(vEvictionCandidates, CompareNetGroupKeyed, 4);
974 EraseLastKElements(vEvictionCandidates, ReverseCompareNodeMinPingTime, 8);
977 EraseLastKElements(vEvictionCandidates, CompareNodeTXTime, 4);
979 std::sort(vEvictionCandidates.begin(), vEvictionCandidates.end(), CompareNodeBlockRelayOnlyTime);
980 size_t erase_size = std::min(
size_t(8), vEvictionCandidates.size());
981 vEvictionCandidates.erase(std::remove_if(vEvictionCandidates.end() - erase_size, vEvictionCandidates.end(), [](NodeEvictionCandidate
const &n) {
return !n.fRelayTxes && n.fRelevantServices; }), vEvictionCandidates.end());
985 EraseLastKElements(vEvictionCandidates, CompareNodeBlockTime, 4);
992 size_t initial_size = vEvictionCandidates.size();
993 size_t total_protect_size = initial_size / 2;
996 std::sort(vEvictionCandidates.begin(), vEvictionCandidates.end(), CompareLocalHostTimeConnected);
997 size_t local_erase_size = total_protect_size / 2;
998 vEvictionCandidates.erase(std::remove_if(vEvictionCandidates.end() - local_erase_size, vEvictionCandidates.end(), [](NodeEvictionCandidate
const &n) {
return n.m_is_local; }), vEvictionCandidates.end());
1001 total_protect_size -= initial_size - vEvictionCandidates.size();
1002 EraseLastKElements(vEvictionCandidates, ReverseCompareNodeTimeConnected, total_protect_size);
1004 if (vEvictionCandidates.empty())
return false;
1009 if (std::any_of(vEvictionCandidates.begin(),vEvictionCandidates.end(),[](NodeEvictionCandidate
const &n){
return n.prefer_evict;})) {
1010 vEvictionCandidates.erase(std::remove_if(vEvictionCandidates.begin(),vEvictionCandidates.end(),
1011 [](NodeEvictionCandidate
const &n){
return !n.prefer_evict;}),vEvictionCandidates.end());
1016 uint64_t naMostConnections;
1017 unsigned int nMostConnections = 0;
1018 int64_t nMostConnectionsTime = 0;
1019 std::map<uint64_t, std::vector<NodeEvictionCandidate> > mapNetGroupNodes;
1020 for (
const NodeEvictionCandidate &node : vEvictionCandidates) {
1021 std::vector<NodeEvictionCandidate> &group = mapNetGroupNodes[node.nKeyedNetGroup];
1022 group.push_back(node);
1023 int64_t grouptime = group[0].nTimeConnected;
1025 if (group.size() > nMostConnections || (group.size() == nMostConnections && grouptime > nMostConnectionsTime)) {
1026 nMostConnections = group.size();
1027 nMostConnectionsTime = grouptime;
1028 naMostConnections = node.nKeyedNetGroup;
1033 vEvictionCandidates = std::move(mapNetGroupNodes[naMostConnections]);
1036 NodeId evicted = vEvictionCandidates.front().id;
1038 for (
CNode* pnode : vNodes) {
1039 if (pnode->
GetId() == evicted) {
1048 struct sockaddr_storage sockaddr;
1049 socklen_t len =
sizeof(sockaddr);
1050 SOCKET hSocket = accept(hListenSocket.socket, (
struct sockaddr*)&sockaddr, &len);
1053 int nMaxInbound = nMaxConnections - m_max_outbound;
1056 if (!addr.
SetSockAddr((
const struct sockaddr*)&sockaddr)) {
1057 LogPrintf(
"Warning: Unknown socket family\n");
1062 hListenSocket.AddSocketPermissionFlags(permissionFlags);
1063 AddWhitelistPermissionFlags(permissionFlags, addr);
1064 bool legacyWhitelisted =
false;
1071 legacyWhitelisted =
true;
1076 for (
const CNode* pnode : vNodes) {
1089 if (!fNetworkActive) {
1090 LogPrintf(
"connection from %s dropped: not accepting new connections\n", addr.
ToString());
1097 LogPrintf(
"connection from %s dropped: non-selectable socket\n", addr.
ToString());
1107 bool banned = m_banman && m_banman->IsBanned(addr);
1116 bool discouraged = m_banman && m_banman->IsDiscouraged(addr);
1124 if (nInbound >= nMaxInbound)
1126 if (!AttemptToEvictConnection()) {
1128 LogPrint(
BCLog::NET,
"failed to find an eviction candidate - connection dropped (full)\n");
1134 NodeId id = GetNewNodeId();
1135 uint64_t nonce = GetDeterministicRandomizer(RANDOMIZER_ID_LOCALHOSTNONCE).Write(
id).Finalize();
1136 CAddress addr_bind = GetBindAddress(hSocket);
1143 const bool inbound_onion = std::find(m_onion_binds.begin(), m_onion_binds.end(), addr_bind) != m_onion_binds.end();
1144 CNode* pnode =
new CNode(
id, nodeServices, GetBestHeight(), hSocket, addr, CalculateKeyedNetGroup(addr), nonce, addr_bind,
"",
ConnectionType::INBOUND, inbound_onion);
1150 m_msgproc->InitializeNode(pnode);
1156 vNodes.push_back(pnode);
1168 if (!fNetworkActive) {
1170 for (
CNode* pnode : vNodes) {
1179 std::vector<CNode*> vNodesCopy = vNodes;
1180 for (
CNode* pnode : vNodesCopy)
1185 vNodes.erase(
remove(vNodes.begin(), vNodes.end(), pnode), vNodes.end());
1195 vNodesDisconnected.push_back(pnode);
1201 std::list<CNode*> vNodesDisconnectedCopy = vNodesDisconnected;
1202 for (
CNode* pnode : vNodesDisconnectedCopy)
1206 bool fDelete =
false;
1214 vNodesDisconnected.remove(pnode);
1227 vNodesSize = vNodes.size();
1229 if(vNodesSize != nPrevNodeCount) {
1230 nPrevNodeCount = vNodesSize;
1232 clientInterface->NotifyNumConnectionsChanged(vNodesSize);
1271 for (
const ListenSocket& hListenSocket : vhListenSocket) {
1272 recv_set.insert(hListenSocket.socket);
1277 for (
CNode* pnode : vNodes)
1294 select_send = !pnode->vSendMsg.empty();
1301 error_set.insert(pnode->hSocket);
1303 send_set.insert(pnode->hSocket);
1307 recv_set.insert(pnode->hSocket);
1312 return !recv_set.empty() || !send_set.empty() || !error_set.empty();
1316 void CConnman::SocketEvents(std::set<SOCKET> &recv_set, std::set<SOCKET> &send_set, std::set<SOCKET> &error_set)
1318 std::set<SOCKET> recv_select_set, send_select_set, error_select_set;
1319 if (!GenerateSelectSet(recv_select_set, send_select_set, error_select_set)) {
1320 interruptNet.sleep_for(std::chrono::milliseconds(SELECT_TIMEOUT_MILLISECONDS));
1324 std::unordered_map<SOCKET, struct pollfd> pollfds;
1325 for (
SOCKET socket_id : recv_select_set) {
1326 pollfds[socket_id].fd = socket_id;
1327 pollfds[socket_id].events |= POLLIN;
1330 for (
SOCKET socket_id : send_select_set) {
1331 pollfds[socket_id].fd = socket_id;
1332 pollfds[socket_id].events |= POLLOUT;
1335 for (
SOCKET socket_id : error_select_set) {
1336 pollfds[socket_id].fd = socket_id;
1338 pollfds[socket_id].events |= POLLERR|POLLHUP;
1341 std::vector<struct pollfd> vpollfds;
1342 vpollfds.reserve(pollfds.size());
1343 for (
auto it : pollfds) {
1344 vpollfds.push_back(std::move(
it.second));
1347 if (poll(vpollfds.data(), vpollfds.size(), SELECT_TIMEOUT_MILLISECONDS) < 0)
return;
1349 if (interruptNet)
return;
1351 for (
struct pollfd pollfd_entry : vpollfds) {
1352 if (pollfd_entry.revents & POLLIN) recv_set.insert(pollfd_entry.fd);
1353 if (pollfd_entry.revents & POLLOUT) send_set.insert(pollfd_entry.fd);
1354 if (pollfd_entry.revents & (POLLERR|POLLHUP)) error_set.insert(pollfd_entry.fd);
1358 void CConnman::SocketEvents(std::set<SOCKET> &recv_set, std::set<SOCKET> &send_set, std::set<SOCKET> &error_set)
1360 std::set<SOCKET> recv_select_set, send_select_set, error_select_set;
1361 if (!GenerateSelectSet(recv_select_set, send_select_set, error_select_set)) {
1362 interruptNet.sleep_for(std::chrono::milliseconds(SELECT_TIMEOUT_MILLISECONDS));
1369 struct timeval timeout;
1371 timeout.tv_usec = SELECT_TIMEOUT_MILLISECONDS * 1000;
1376 FD_ZERO(&fdsetRecv);
1377 FD_ZERO(&fdsetSend);
1378 FD_ZERO(&fdsetError);
1381 for (
SOCKET hSocket : recv_select_set) {
1382 FD_SET(hSocket, &fdsetRecv);
1383 hSocketMax = std::max(hSocketMax, hSocket);
1386 for (
SOCKET hSocket : send_select_set) {
1387 FD_SET(hSocket, &fdsetSend);
1388 hSocketMax = std::max(hSocketMax, hSocket);
1391 for (
SOCKET hSocket : error_select_set) {
1392 FD_SET(hSocket, &fdsetError);
1393 hSocketMax = std::max(hSocketMax, hSocket);
1396 int nSelect = select(hSocketMax + 1, &fdsetRecv, &fdsetSend, &fdsetError, &timeout);
1405 for (
unsigned int i = 0; i <= hSocketMax; i++)
1406 FD_SET(i, &fdsetRecv);
1407 FD_ZERO(&fdsetSend);
1408 FD_ZERO(&fdsetError);
1409 if (!interruptNet.sleep_for(std::chrono::milliseconds(SELECT_TIMEOUT_MILLISECONDS)))
1413 for (
SOCKET hSocket : recv_select_set) {
1414 if (FD_ISSET(hSocket, &fdsetRecv)) {
1415 recv_set.insert(hSocket);
1419 for (
SOCKET hSocket : send_select_set) {
1420 if (FD_ISSET(hSocket, &fdsetSend)) {
1421 send_set.insert(hSocket);
1425 for (
SOCKET hSocket : error_select_set) {
1426 if (FD_ISSET(hSocket, &fdsetError)) {
1427 error_set.insert(hSocket);
1435 std::set<SOCKET> recv_set, send_set, error_set;
1436 SocketEvents(recv_set, send_set, error_set);
1438 if (interruptNet)
return;
1443 for (
const ListenSocket& hListenSocket : vhListenSocket)
1445 if (hListenSocket.socket !=
INVALID_SOCKET && recv_set.count(hListenSocket.socket) > 0)
1447 AcceptConnection(hListenSocket);
1454 std::vector<CNode*> vNodesCopy;
1457 vNodesCopy = vNodes;
1458 for (
CNode* pnode : vNodesCopy)
1461 for (
CNode* pnode : vNodesCopy)
1469 bool recvSet =
false;
1470 bool sendSet =
false;
1471 bool errorSet =
false;
1476 recvSet = recv_set.count(pnode->hSocket) > 0;
1477 sendSet = send_set.count(pnode->hSocket) > 0;
1478 errorSet = error_set.count(pnode->hSocket) > 0;
1480 if (recvSet || errorSet)
1483 char pchBuf[0x10000];
1489 nBytes = recv(pnode->hSocket, pchBuf,
sizeof(pchBuf),
MSG_DONTWAIT);
1493 bool notify =
false;
1496 RecordBytesRecv(nBytes);
1498 size_t nSizeAdded = 0;
1503 nSizeAdded +=
it->m_raw_message_size;
1507 pnode->vProcessMsg.splice(pnode->vProcessMsg.end(), pnode->
vRecvMsg, pnode->
vRecvMsg.begin(),
it);
1511 WakeMessageHandler();
1514 else if (nBytes == 0)
1522 else if (nBytes < 0)
1542 size_t nBytes = SocketSendData(pnode);
1544 RecordBytesSent(nBytes);
1548 InactivityCheck(pnode);
1552 for (
CNode* pnode : vNodesCopy)
1559 while (!interruptNet)
1571 fMsgProcWake =
true;
1573 condMsgProc.notify_one();
1583 static std::thread g_upnp_thread;
1584 static void ThreadMapPort()
1587 const char * multicastif =
nullptr;
1588 const char * minissdpdpath =
nullptr;
1589 struct UPNPDev * devlist =
nullptr;
1593 #if MINIUPNPC_API_VERSION < 14
1594 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0, 0, &error);
1596 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0, 0, 2, &error);
1599 struct UPNPUrls urls;
1600 struct IGDdatas data;
1603 r = UPNP_GetValidIGD(devlist, &urls, &data, lanaddr,
sizeof(lanaddr));
1607 char externalIPAddress[40];
1608 r = UPNP_GetExternalIPAddress(urls.controlURL, data.first.servicetype, externalIPAddress);
1609 if (r != UPNPCOMMAND_SUCCESS) {
1610 LogPrintf(
"UPnP: GetExternalIPAddress() returned %d\n", r);
1612 if (externalIPAddress[0]) {
1614 if (
LookupHost(externalIPAddress, resolved,
false)) {
1619 LogPrintf(
"UPnP: GetExternalIPAddress failed.\n");
1627 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype, port.c_str(), port.c_str(), lanaddr, strDesc.c_str(),
"TCP", 0,
"0");
1629 if (r != UPNPCOMMAND_SUCCESS) {
1630 LogPrintf(
"AddPortMapping(%s, %s, %s) failed with code %d (%s)\n", port, port, lanaddr, r, strupnperror(r));
1632 LogPrintf(
"UPnP Port Mapping successful.\n");
1634 }
while (g_upnp_interrupt.
sleep_for(std::chrono::minutes(20)));
1636 r = UPNP_DeletePortMapping(urls.controlURL, data.first.servicetype, port.c_str(),
"TCP", 0);
1637 LogPrintf(
"UPNP_DeletePortMapping() returned: %d\n", r);
1638 freeUPNPDevlist(devlist); devlist =
nullptr;
1639 FreeUPNPUrls(&urls);
1641 LogPrintf(
"No valid UPnP IGDs found\n");
1642 freeUPNPDevlist(devlist); devlist =
nullptr;
1644 FreeUPNPUrls(&urls);
1650 if (!g_upnp_thread.joinable()) {
1651 assert(!g_upnp_interrupt);
1652 g_upnp_thread = std::thread((std::bind(&
TraceThread<
void (*)()>,
"upnp", &ThreadMapPort)));
1658 if(g_upnp_thread.joinable()) {
1665 if(g_upnp_thread.joinable()) {
1666 g_upnp_thread.join();
1667 g_upnp_interrupt.
reset();
1695 Shuffle(seeds.begin(), seeds.end(), rng);
1696 int seeds_right_now = 0;
1701 seeds_right_now = seeds.size();
1702 }
else if (addrman.size() == 0) {
1706 seeds_right_now = seeds.size();
1721 const std::chrono::seconds seeds_wait_time = (addrman.size() >= DNSSEEDS_DELAY_PEER_THRESHOLD ? DNSSEEDS_DELAY_MANY_PEERS : DNSSEEDS_DELAY_FEW_PEERS);
1723 for (
const std::string& seed : seeds) {
1724 if (seeds_right_now == 0) {
1725 seeds_right_now += DNSSEEDS_TO_QUERY_AT_ONCE;
1727 if (addrman.size() > 0) {
1728 LogPrintf(
"Waiting %d seconds before querying DNS seeds.\n", seeds_wait_time.count());
1729 std::chrono::seconds to_wait = seeds_wait_time;
1730 while (to_wait.count() > 0) {
1734 std::chrono::seconds w = std::min(DNSSEEDS_DELAY_FEW_PEERS, to_wait);
1735 if (!interruptNet.sleep_for(w))
return;
1741 for (
const CNode* pnode : vNodes) {
1745 if (nRelevant >= 2) {
1747 LogPrintf(
"%d addresses found from DNS seeds\n", found);
1748 LogPrintf(
"P2P peers available. Finished DNS seeding.\n");
1750 LogPrintf(
"P2P peers available. Skipped DNS seeding.\n");
1758 if (interruptNet)
return;
1761 if (!fNetworkActive) {
1762 LogPrintf(
"Waiting for network to be reactivated before querying DNS seeds.\n");
1764 if (!interruptNet.sleep_for(std::chrono::seconds{1}))
return;
1765 }
while (!fNetworkActive);
1768 LogPrintf(
"Loading addresses from DNS seed %s\n", seed);
1772 std::vector<CNetAddr> vIPs;
1773 std::vector<CAddress> vAdd;
1775 std::string host =
strprintf(
"x%x.%s", requiredServiceBits, seed);
1780 unsigned int nMaxIPs = 256;
1783 int nOneDay = 24*3600;
1786 vAdd.push_back(addr);
1789 addrman.Add(vAdd, resolveSource);
1798 LogPrintf(
"%d addresses found from DNS seeds\n", found);
1814 std::string strDest;
1816 LOCK(m_addr_fetches_mutex);
1817 if (m_addr_fetches.empty())
1819 strDest = m_addr_fetches.front();
1820 m_addr_fetches.pop_front();
1831 return m_try_another_outbound_peer;
1836 m_try_another_outbound_peer = flag;
1837 LogPrint(
BCLog::NET,
"net: setting try another outbound peer=%s\n", flag ?
"true" :
"false");
1851 for (
const CNode* pnode : vNodes) {
1857 return std::max(nOutbound - m_max_outbound_full_relay - m_max_outbound_block_relay, 0);
1863 if (!connect.empty())
1865 for (int64_t nLoop = 0;; nLoop++)
1868 for (
const std::string& strAddr : connect)
1872 for (
int i = 0; i < 10 && i < nLoop; i++)
1874 if (!interruptNet.sleep_for(std::chrono::milliseconds(500)))
1878 if (!interruptNet.sleep_for(std::chrono::milliseconds(500)))
1888 while (!interruptNet)
1892 if (!interruptNet.sleep_for(std::chrono::milliseconds(500)))
1903 if (addrman.size() == 0 && (
GetTime() - nStart > 60)) {
1904 static bool done =
false;
1906 LogPrintf(
"Adding fixed seed nodes as DNS doesn't seem to be available.\n");
1909 addrman.Add(convertSeed6(
Params().FixedSeeds()), local);
1920 int nOutboundFullRelay = 0;
1921 int nOutboundBlockRelay = 0;
1922 std::set<std::vector<unsigned char> > setConnected;
1926 for (
const CNode* pnode : vNodes) {
1943 setConnected.insert(pnode->
addr.
GetGroup(addrman.m_asmap));
1950 bool anchor =
false;
1951 bool fFeeler =
false;
1963 if (!m_anchors.empty() && (nOutboundBlockRelay < m_max_outbound_block_relay)) {
1966 }
else if (nOutboundFullRelay < m_max_outbound_full_relay) {
1968 }
else if (nOutboundBlockRelay < m_max_outbound_block_relay) {
1970 }
else if (GetTryNewOutboundPeer()) {
1972 }
else if (nTime > nNextFeeler) {
1981 addrman.ResolveCollisions();
1985 while (!interruptNet)
1987 if (anchor && !m_anchors.empty()) {
1988 const CAddress addr = m_anchors.back();
1989 m_anchors.pop_back();
1992 setConnected.count(addr.
GetGroup(addrman.m_asmap)))
continue;
2010 addr = addrman.SelectTriedCollision();
2015 addr = addrman.Select(
true);
2016 }
else if (AlreadyConnectedToAddress(addr)) {
2024 addr = addrman.Select(
true);
2028 addr = addrman.Select();
2032 if (!fFeeler && setConnected.count(addr.
GetGroup(addrman.m_asmap))) {
2045 if (nANow - addr.
nLastTry < 600 && nTries < 30)
2074 if (!interruptNet.sleep_for(std::chrono::milliseconds(randsleep)))
2079 OpenNetworkConnection(addrConnect, (
int)setConnected.size() >= std::min(nMaxConnections - 1, 2), &grant,
nullptr, conn_type);
2086 std::vector<CAddress> ret;
2088 for (
const CNode* pnode : vNodes) {
2090 ret.push_back(pnode->
addr);
2099 std::vector<AddedNodeInfo> ret;
2101 std::list<std::string> lAddresses(0);
2103 LOCK(cs_vAddedNodes);
2104 ret.reserve(vAddedNodes.size());
2105 std::copy(vAddedNodes.cbegin(), vAddedNodes.cend(), std::back_inserter(lAddresses));
2110 std::map<CService, bool> mapConnected;
2111 std::map<std::string, std::pair<bool, CService>> mapConnectedByName;
2114 for (
const CNode* pnode : vNodes) {
2119 if (!addrName.empty()) {
2120 mapConnectedByName[std::move(addrName)] = std::make_pair(pnode->
IsInboundConn(),
static_cast<const CService&
>(pnode->
addr));
2125 for (
const std::string& strAddNode : lAddresses) {
2128 if (service.IsValid()) {
2130 auto it = mapConnected.find(service);
2131 if (
it != mapConnected.end()) {
2132 addedNode.resolvedAddress = service;
2133 addedNode.fConnected =
true;
2134 addedNode.fInbound =
it->second;
2138 auto it = mapConnectedByName.find(strAddNode);
2139 if (
it != mapConnectedByName.end()) {
2140 addedNode.resolvedAddress =
it->second.second;
2141 addedNode.fConnected =
true;
2142 addedNode.fInbound =
it->second.first;
2145 ret.emplace_back(std::move(addedNode));
2156 std::vector<AddedNodeInfo> vInfo = GetAddedNodeInfo();
2159 if (!info.fConnected) {
2160 if (!grant.TryAcquire()) {
2168 if (!interruptNet.sleep_for(std::chrono::milliseconds(500)))
2173 if (!interruptNet.sleep_for(std::chrono::seconds(tried ? 60 : 2)))
2189 if (!fNetworkActive) {
2193 bool banned_or_discouraged = m_banman && (m_banman->IsDiscouraged(addrConnect) || m_banman->IsBanned(addrConnect));
2194 if (
IsLocal(addrConnect) || banned_or_discouraged || AlreadyConnectedToAddress(addrConnect)) {
2197 }
else if (FindNode(std::string(pszDest)))
2200 CNode* pnode = ConnectNode(addrConnect, pszDest, fCountFailure, conn_type);
2207 m_msgproc->InitializeNode(pnode);
2210 vNodes.push_back(pnode);
2216 while (!flagInterruptMsgProc)
2218 std::vector<CNode*> vNodesCopy;
2221 vNodesCopy = vNodes;
2222 for (
CNode* pnode : vNodesCopy) {
2227 bool fMoreWork =
false;
2229 for (
CNode* pnode : vNodesCopy)
2235 bool fMoreNodeWork = m_msgproc->ProcessMessages(pnode, flagInterruptMsgProc);
2236 fMoreWork |= (fMoreNodeWork && !pnode->
fPauseSend);
2237 if (flagInterruptMsgProc)
2242 m_msgproc->SendMessages(pnode);
2245 if (flagInterruptMsgProc)
2251 for (
CNode* pnode : vNodesCopy)
2257 condMsgProc.wait_until(lock, std::chrono::steady_clock::now() + std::chrono::milliseconds(100), [
this]()
EXCLUSIVE_LOCKS_REQUIRED(mutexMsgProc) {
return fMsgProcWake; });
2259 fMsgProcWake =
false;
2268 struct sockaddr_storage sockaddr;
2269 socklen_t len =
sizeof(sockaddr);
2270 if (!addrBind.
GetSockAddr((
struct sockaddr*)&sockaddr, &len))
2287 setsockopt(hListenSocket, SOL_SOCKET, SO_REUSEADDR, (
sockopt_arg_type)&nOne,
sizeof(
int));
2293 setsockopt(hListenSocket, IPPROTO_IPV6, IPV6_V6ONLY, (
sockopt_arg_type)&nOne,
sizeof(
int));
2296 int nProtLevel = PROTECTION_LEVEL_UNRESTRICTED;
2297 setsockopt(hListenSocket, IPPROTO_IPV6, IPV6_PROTECTION_LEVEL, (
const char*)&nProtLevel,
sizeof(
int));
2301 if (::bind(hListenSocket, (
struct sockaddr*)&sockaddr, len) ==
SOCKET_ERROR)
2323 vhListenSocket.push_back(ListenSocket(hListenSocket, permissions));
2334 char pszHostName[256] =
"";
2335 if (gethostname(pszHostName,
sizeof(pszHostName)) !=
SOCKET_ERROR)
2337 std::vector<CNetAddr> vaddr;
2347 #elif (HAVE_DECL_GETIFADDRS && HAVE_DECL_FREEIFADDRS)
2349 struct ifaddrs* myaddrs;
2350 if (getifaddrs(&myaddrs) == 0)
2352 for (
struct ifaddrs* ifa = myaddrs; ifa !=
nullptr; ifa = ifa->ifa_next)
2354 if (ifa->ifa_addr ==
nullptr)
continue;
2355 if ((ifa->ifa_flags & IFF_UP) == 0)
continue;
2356 if (strcmp(ifa->ifa_name,
"lo") == 0)
continue;
2357 if (strcmp(ifa->ifa_name,
"lo0") == 0)
continue;
2358 if (ifa->ifa_addr->sa_family == AF_INET)
2360 struct sockaddr_in* s4 = (
struct sockaddr_in*)(ifa->ifa_addr);
2365 else if (ifa->ifa_addr->sa_family == AF_INET6)
2367 struct sockaddr_in6* s6 = (
struct sockaddr_in6*)(ifa->ifa_addr);
2373 freeifaddrs(myaddrs);
2380 LogPrintf(
"%s: %s\n", __func__, active);
2382 if (fNetworkActive == active) {
2386 fNetworkActive = active;
2388 uiInterface.NotifyNetworkActiveChanged(fNetworkActive);
2392 : nSeed0(nSeed0In), nSeed1(nSeed1In)
2394 SetTryNewOutboundPeer(
false);
2396 Options connOptions;
2398 SetNetworkActive(network_active);
2403 return nLastNodeId.fetch_add(1, std::memory_order_relaxed);
2418 if (addr.
IsRoutable() && fDiscover && !(flags & BF_DONT_ADVERTISE) && !(permissions &
PF_NOBAN)) {
2426 const std::vector<CService>& binds,
2427 const std::vector<NetWhitebindPermissions>& whiteBinds,
2428 const std::vector<CService>& onion_binds)
2430 bool fBound =
false;
2431 for (
const auto& addrBind : binds) {
2434 for (
const auto& addrBind : whiteBinds) {
2435 fBound |=
Bind(addrBind.m_service, (BF_EXPLICIT | BF_REPORT_ERROR), addrBind.m_flags);
2437 if (binds.empty() && whiteBinds.empty()) {
2438 struct in_addr inaddr_any;
2439 inaddr_any.s_addr = htonl(INADDR_ANY);
2440 struct in6_addr inaddr6_any = IN6ADDR_ANY_INIT;
2445 for (
const auto& addr_bind : onion_binds) {
2458 nTotalBytesRecv = 0;
2462 nTotalBytesSent = 0;
2463 nMaxOutboundTotalBytesSentInCycle = 0;
2464 nMaxOutboundCycleStartTime = 0;
2467 if (fListen && !
InitBinds(connOptions.vBinds, connOptions.vWhiteBinds, connOptions.onion_binds)) {
2470 _(
"Failed to listen on any port. Use -listen=0 if you want this."),
2476 for (
const auto& strDest : connOptions.vSeedNodes) {
2491 LogPrintf(
"Invalid or missing peers.dat; recreating\n");
2502 LogPrintf(
"%i block-relay-only anchors will be tried for connections.\n",
m_anchors.size());
2505 uiInterface.InitMessage(
_(
"Starting network threads...").translated);
2528 fMsgProcWake =
false;
2542 if (connOptions.m_use_addrman_outgoing && !connOptions.m_specified_outgoing.empty()) {
2545 _(
"Cannot provide specific connections and have addrman find outgoing connections at the same."),
2550 if (connOptions.m_use_addrman_outgoing || !connOptions.m_specified_outgoing.empty())
2575 static CNetCleanup instance_of_cnetcleanup;
2633 for (
CNode* pnode : vNodes)
2635 for (ListenSocket& hListenSocket : vhListenSocket)
2641 for (
CNode* pnode : vNodes) {
2648 vNodesDisconnected.clear();
2649 vhListenSocket.clear();
2657 bool fUpdateConnectionTime =
false;
2659 if (fUpdateConnectionTime) {
2683 return addrman.
Add(vAddr, addrFrom, nTimePenalty);
2688 std::vector<CAddress> addresses =
addrman.
GetAddr(max_addresses, max_pct);
2690 addresses.erase(std::remove_if(addresses.begin(), addresses.end(),
2701 auto local_socket_bytes = GetBindAddress(socket).GetAddrBytes();
2704 .Write(local_socket_bytes.data(), local_socket_bytes.size())
2706 const auto current_time = GetTime<std::chrono::microseconds>();
2708 CachedAddrResponse& cache_entry = r.first->second;
2709 if (cache_entry.m_cache_entry_expiration < current_time) {
2710 cache_entry.m_addrs_response_cache =
GetAddresses(max_addresses, max_pct);
2735 cache_entry.m_cache_entry_expiration = current_time + std::chrono::hours(21) +
GetRandMillis(std::chrono::hours(6));
2737 return cache_entry.m_addrs_response_cache;
2743 for (
const std::string&
it : vAddedNodes) {
2744 if (strNode ==
it)
return false;
2747 vAddedNodes.push_back(strNode);
2754 for(std::vector<std::string>::iterator
it = vAddedNodes.begin();
it != vAddedNodes.end(); ++
it) {
2755 if (strNode == *
it) {
2756 vAddedNodes.erase(
it);
2767 return vNodes.size();
2770 for (
const auto& pnode : vNodes) {
2783 vstats.reserve(vNodes.size());
2784 for (
CNode* pnode : vNodes) {
2785 vstats.emplace_back();
2802 bool disconnected =
false;
2804 for (
CNode* pnode : vNodes) {
2807 disconnected =
true;
2810 return disconnected;
2821 for(
CNode* pnode : vNodes) {
2822 if (
id == pnode->
GetId()) {
2833 nTotalBytesRecv += bytes;
2839 nTotalBytesSent += bytes;
2842 if (nMaxOutboundCycleStartTime + nMaxOutboundTimeframe < now)
2845 nMaxOutboundCycleStartTime = now;
2846 nMaxOutboundTotalBytesSentInCycle = 0;
2850 nMaxOutboundTotalBytesSentInCycle += bytes;
2856 nMaxOutboundLimit = limit;
2862 return nMaxOutboundLimit;
2868 return nMaxOutboundTimeframe;
2874 if (nMaxOutboundLimit == 0)
2877 if (nMaxOutboundCycleStartTime == 0)
2878 return nMaxOutboundTimeframe;
2880 uint64_t cycleEndTime = nMaxOutboundCycleStartTime + nMaxOutboundTimeframe;
2882 return (cycleEndTime < now) ? 0 : cycleEndTime -
GetTime();
2888 if (nMaxOutboundTimeframe != timeframe)
2892 nMaxOutboundCycleStartTime =
GetTime();
2894 nMaxOutboundTimeframe = timeframe;
2900 if (nMaxOutboundLimit == 0)
2903 if (historicalBlockServingLimit)
2908 if (buffer >= nMaxOutboundLimit || nMaxOutboundTotalBytesSentInCycle >= nMaxOutboundLimit - buffer)
2911 else if (nMaxOutboundTotalBytesSentInCycle >= nMaxOutboundLimit)
2920 if (nMaxOutboundLimit == 0)
2923 return (nMaxOutboundTotalBytesSentInCycle >= nMaxOutboundLimit) ? 0 : nMaxOutboundLimit - nMaxOutboundTotalBytesSentInCycle;
2929 return nTotalBytesRecv;
2935 return nTotalBytesSent;
2945 nBestHeight.store(height, std::memory_order_release);
2950 return nBestHeight.load(std::memory_order_acquire);
2955 CNode::CNode(
NodeId idIn,
ServiceFlags nLocalServicesIn,
int nMyStartingHeightIn,
SOCKET hSocketIn,
const CAddress& addrIn, uint64_t nKeyedNetGroupIn, uint64_t nLocalHostNonceIn,
const CAddress& addrBindIn,
const std::string& addrNameIn,
ConnectionType conn_type_in,
bool inbound_onion)
2958 addrBind(addrBindIn),
2959 nKeyedNetGroup(nKeyedNetGroupIn),
2964 nLocalHostNonce(nLocalHostNonceIn),
2965 m_conn_type(conn_type_in),
2966 nLocalServices(nLocalServicesIn),
2967 nMyStartingHeight(nMyStartingHeightIn),
2968 m_inbound_onion(inbound_onion)
2970 hSocket = hSocketIn;
2971 addrName = addrNameIn ==
"" ? addr.ToStringIPPort() : addrNameIn;
2974 m_tx_relay = MakeUnique<TxRelay>();
2977 if (RelayAddrsWithConn()) {
2978 m_addr_known = MakeUnique<CRollingBloomFilter>(5000, 0.001);
2982 mapRecvBytesPerMsgCmd[msg] = 0;
3007 size_t nMessageSize = msg.
data.size();
3011 std::vector<unsigned char> serializedHeader;
3012 pnode->
m_serializer->prepareForTransport(msg, serializedHeader);
3013 size_t nTotalSize = nMessageSize + serializedHeader.size();
3015 size_t nBytesSent = 0;
3018 bool optimisticSend(pnode->vSendMsg.empty());
3026 pnode->vSendMsg.push_back(std::move(serializedHeader));
3028 pnode->vSendMsg.push_back(std::move(msg.
data));
3031 if (optimisticSend ==
true)
3040 CNode* found =
nullptr;
3042 for (
auto&& pnode : vNodes) {
3043 if(pnode->
GetId() == id) {
3064 return now + (int64_t)(log1p(
GetRand(1ULL << 48) * -0.0000000000000035527136788 ) * average_interval_seconds * -1000000.0 + 0.5);
std::atomic< bool > flagInterruptMsgProc
void copyStats(CNodeStats &stats, const std::vector< bool > &m_asmap)
std::string SanitizeString(const std::string &str, int rule)
Remove unsafe chars.
static const int MAX_BLOCK_RELAY_ONLY_CONNECTIONS
Maximum number of block-relay-only outgoing connections.
std::atomic< uint64_t > nPingNonceSent
void RandAddEvent(const uint32_t event_info) noexcept
Gathers entropy from the low bits of the time at which events occur.
bool IsReachable(enum Network net)
void MoveTo(CSemaphoreGrant &grant)
std::atomic_bool fPauseSend
Access to the (IP) address database (peers.dat)
uint64_t GetRand(uint64_t nMax) noexcept
Generate a uniform random integer in the range [0..range).
void ThreadOpenAddedConnections()
bool sleep_for(std::chrono::milliseconds rel_time)
static const unsigned int MAX_PROTOCOL_MESSAGE_LENGTH
Maximum length of incoming protocol messages (no message over 4 MB is currently acceptable).
int GetCommonVersion() const
bool ConnectSocketDirectly(const CService &addrConnect, const SOCKET &hSocket, int nTimeout, bool manual_connection)
Try to connect to the specified service on the specified socket.
CService LookupNumeric(const std::string &name, int portDefault)
Resolve a service string with a numeric IP to its first corresponding service.
uint64_t CalculateKeyedNetGroup(const CAddress &ad) const
uint64_t GetLocalNonce() const
static void AddFlag(NetPermissionFlags &flags, NetPermissionFlags f)
ServiceFlags
nServices flags
void Finalize(Span< unsigned char > output)
std::unique_ptr< TransportSerializer > m_serializer
#define LogPrint(category,...)
unsigned int GetReceiveFloodSize() const
void Attempt(const CService &addr, bool fCountFailure, int64_t nTime=GetAdjustedTime())
Mark an entry as connection attempted to.
A set of addresses that represent the hash of a string or FQDN.
We open manual connections to addresses that users explicitly inputted via the addnode RPC...
CNode * FindNode(const CNetAddr &ip)
CSipHasher & Write(uint64_t data)
Hash a 64-bit integer worth of data It is treated as if this was the little-endian interpretation of ...
#define TRY_LOCK(cs, name)
Dummy value to indicate the number of NET_* constants.
void scheduleEvery(Function f, std::chrono::milliseconds delta)
Repeat f until the scheduler is stopped.
static bool IsSelectableSocket(const SOCKET &s)
std::atomic< int > nBestHeight
void SetIP(const CNetAddr &ip)
void WakeMessageHandler()
bool Bind(const CService &addr, unsigned int flags, NetPermissionFlags permissions)
static bool NodeFullyConnected(const CNode *pnode)
void SetServices(const CService &addr, ServiceFlags nServices)
bool GetBoolArg(const std::string &strArg, bool fDefault) const
Return boolean argument or default value.
void SocketEvents(std::set< SOCKET > &recv_set, std::set< SOCKET > &send_set, std::set< SOCKET > &error_set)
const std::string NET_MESSAGE_COMMAND_OTHER
ServiceFlags GetLocalServices() const
Used to convey which local services we are offering peers during node connection. ...
int64_t GetTimeMillis()
Returns the system time (not mockable)
static const bool DEFAULT_FORCEDNSSEED
bool SeenLocal(const CService &addr)
bool ReceiveMsgBytes(const char *pch, unsigned int nBytes, bool &complete)
mapMsgCmdSize mapSendBytesPerMsgCmd
std::string ToStringIP() const
int64_t count_microseconds(std::chrono::microseconds t)
std::vector< CAddress > GetAddresses(size_t max_addresses, size_t max_pct)
static void ClearFlag(NetPermissionFlags &flags, NetPermissionFlags f)
std::vector< unsigned char > data
static void LogPrintf(const char *fmt, const Args &...args)
const ConnectionType m_conn_type
bilingual_str Untranslated(std::string original)
Mark a bilingual_str as untranslated.
std::vector< NetWhitelistPermissions > vWhitelistedRange
const std::vector< std::string > & DNSSeeds() const
Return the list of hostnames to look up for DNS seeds.
constexpr auto GetRandMillis
std::string ToStringIPPort() const
void resize(size_type n, value_type c=0)
bool GetNameProxy(proxyType &nameProxyOut)
uint32_t GetMappedAS(const std::vector< bool > &asmap) const
bool AlreadyConnectedToAddress(const CAddress &addr)
Determine whether we're already connected to a given address, in order to avoid initiating duplicate ...
bool GetTryNewOutboundPeer()
#define FEELER_SLEEP_WINDOW
std::atomic< int64_t > m_next_send_inv_to_incoming
RAII-style semaphore lock.
uint64_t GetMaxOutboundTarget()
static const int BIP0031_VERSION
BIP 0031, pong message, is enabled for all versions AFTER this one.
void PushMessage(CNode *pnode, CSerializedNetMsg &&msg)
int readHeader(const char *pch, unsigned int nBytes)
bool BindListenPort(const CService &bindAddr, bilingual_str &strError, NetPermissionFlags permissions)
RecursiveMutex cs_vProcessMsg
void SetMaxOutboundTimeframe(uint64_t timeframe)
set the timeframe for the max outbound target
RecursiveMutex cs_addrName
CService GetAddrLocal() const
static auto & nullopt
Substitute for C++17 std::nullopt.
NetEventsInterface * m_msgproc
void AdvertiseLocal(CNode *pnode)
void SetTryNewOutboundPeer(bool flag)
std::unique_ptr< TransportDeserializer > m_deserializer
void ThreadSocketHandler()
std::vector< CAddress > GetCurrentBlockRelayOnlyConns() const
Return vector of current BLOCK_RELAY peers.
bool IsBlockOnlyConn() const
size_t GetNodeCount(NumConnections num)
bool Add(const CAddress &addr, const CNetAddr &source, int64_t nTimePenalty=0)
Add a single address.
bool Match(const CNetAddr &addr) const
std::atomic< int > nStartingHeight
void PushAddress(const CAddress &_addr, FastRandomContext &insecure_rand)
static const int FEELER_INTERVAL
Run the feeler connection loop once every 2 minutes or 120 seconds.
static const int TIMEOUT_INTERVAL
Time after which to disconnect, after waiting for a ping response (or inactivity).
int64_t GetSystemTimeInSeconds()
Returns the system time (not mockable)
#define WSAGetLastError()
std::list< CNetMessage > vRecvMsg
void DumpAnchors(const fs::path &anchors_db_path, const std::vector< CAddress > &anchors)
Dump the anchor IP address database (anchors.dat)
void NotifyNumConnectionsChanged()
void SetMaxOutboundTarget(uint64_t limit)
set the max outbound target in bytes
void RecordBytesSent(uint64_t bytes)
std::map< uint64_t, CachedAddrResponse > m_addr_response_caches
Addr responses stored in different caches per (network, local socket) prevent cross-network node iden...
std::atomic< ServiceFlags > nServices
void SetAddrLocal(const CService &addrLocalIn)
May not be called more than once.
uint64_t GetMaxOutboundTimeframe()
bool ConnectThroughProxy(const proxyType &proxy, const std::string &strDest, int port, const SOCKET &hSocket, int nTimeout, bool &outProxyConnectionFailed)
Connect to a specified destination service through a SOCKS5 proxy by first connecting to the SOCKS5 p...
bool ForNode(NodeId id, std::function< bool(CNode *pnode)> func)
RecursiveMutex cs_sendProcessing
ServiceFlags nLocalServices
Services this instance offers.
bool DisconnectNode(const std::string &node)
bool Lookup(const std::string &name, std::vector< CService > &vAddr, int portDefault, bool fAllowLookup, unsigned int nMaxSolutions)
Resolve a service string to its corresponding service.
std::atomic< int64_t > nLastSend
void RecordBytesRecv(uint64_t bytes)
bool IsDiscouraged(const CNetAddr &net_addr)
Return whether net_addr is discouraged.
int readData(const char *pch, unsigned int nBytes)
size_t size() const
Return the number of (unique) addresses in all tables.
const uint256 & GetMessageHash() const
std::atomic< int64_t > nPingUsecTime
uint64_t randbits(int bits) noexcept
Generate a random (bits)-bit integer.
std::atomic< int64_t > nMinPingUsecTime
Extended statistics about a CAddress.
bool error(const char *fmt, const Args &...args)
void CloseSocketDisconnect()
uint64_t GetOutboundTargetBytesLeft()
response the bytes left in the current max outbound cycle in case of no limit, it will always respons...
bool IsInboundConn() const
bool Write(const CAddrMan &addr)
void AddAddrFetch(const std::string &strDest)
bool GetLocal(CService &addr, const CNetAddr *paddrPeer=nullptr)
bool AddNode(const std::string &node)
std::condition_variable condMsgProc
bool IsFullOutboundConn() const
RecursiveMutex cs_vAddedNodes
uint64_t GetMaxOutboundTimeLeftInCycle()
response the time in second left in the current max outbound cycle in case of no limit, it will always response 0
void OpenNetworkConnection(const CAddress &addrConnect, bool fCountFailure, CSemaphoreGrant *grantOutbound, const char *strDest, ConnectionType conn_type)
void InactivityCheck(CNode *pnode)
std::atomic< int64_t > nLastRecv
int GetDefaultPort() const
const uint64_t nSeed0
SipHasher seeds for deterministic randomness.
static bool HasAllDesirableServiceFlags(ServiceFlags services)
A shortcut for (services & GetDesirableServiceFlags(services)) == GetDesirableServiceFlags(services)...
std::thread threadOpenAddedConnections
std::vector< CAddress > ReadAnchors(const fs::path &anchors_db_path)
Read the anchor IP address database (anchors.dat)
RecursiveMutex m_addr_fetches_mutex
bool IsPeerAddrLocalGood(CNode *pnode)
bilingual_str _(const char *psz)
Translation function.
static const int INIT_PROTO_VERSION
initial proto version, to be increased after version/verack negotiation
A combination of a network address (CNetAddr) and a (TCP) port.
int64_t PoissonNextSendInbound(int64_t now, int average_interval_seconds)
Attempts to obfuscate tx time through exponentially distributed emitting.
bool OutboundTargetReached(bool historicalBlockServingLimit)
check if the outbound target is reached if param historicalBlockServingLimit is set true...
const fs::path & GetDataDir(bool fNetSpecific)
std::unique_ptr< CSemaphore > semOutbound
void ThreadOpenConnections(std::vector< std::string > connect)
std::thread threadMessageHandler
static bool HasFlag(const NetPermissionFlags &flags, NetPermissionFlags f)
uint64_t Finalize() const
Compute the 64-bit SipHash-2-4 of the data written so far.
virtual void FinalizeNode(const CNode &node, bool &update_connection_time)=0
A CService with information about it as peer.
bool Start(CScheduler &scheduler, const Options &options)
void MaybeSetAddrName(const std::string &addrNameIn)
Sets the addrName only if it was not previously set.
const std::vector< std::string > & getAllNetMessageTypes()
uint64_t GetTotalBytesRecv()
RecursiveMutex cs_mapLocalHost
std::string ToString() const
void SetNetworkActive(bool active)
#define WAIT_LOCK(cs, name)
const CMessageHeader::MessageStartChars & MessageStart() const
CClientUIInterface * clientInterface
void GetNodeStats(std::vector< CNodeStats > &vstats)
const bool m_inbound_onion
Whether this peer connected via our Tor onion service.
bool AddNewAddresses(const std::vector< CAddress > &vAddr, const CAddress &addrFrom, int64_t nTimePenalty=0)
std::atomic_bool fDisconnect
bool InitBinds(const std::vector< CService > &binds, const std::vector< NetWhitebindPermissions > &whiteBinds, const std::vector< CService > &onion_binds)
void TraceThread(const char *name, Callable func)
ServiceFlags GetLocalServices() const
bool CloseSocket(SOCKET &hSocket)
Close socket and set hSocket to INVALID_SOCKET.
void prepareForTransport(CSerializedNetMsg &msg, std::vector< unsigned char > &header) override
static constexpr size_t MAX_BLOCK_RELAY_ONLY_ANCHORS
Maximum number of block-relay-only anchor connections.
#define WITH_LOCK(cs, code)
Run code while locking a mutex.
std::string FormatFullVersion()
static bool MayHaveUsefulAddressDB(ServiceFlags services)
Checks if a peer with the given service flags may be capable of having a robust address-storage DB...
std::string HexStr(const Span< const uint8_t > s)
Convert a span of bytes to a lower-case hexadecimal string.
Inbound connections are those initiated by a peer.
void DeleteNode(CNode *pnode)
bool CheckIncomingNonce(uint64_t nonce)
static uint32_t ReadLE32(const unsigned char *ptr)
bool Complete() const override
const int64_t nTimeConnected
std::vector< unsigned char > GetGroup(const std::vector< bool > &asmap) const
Get the canonical identifier of our network group.
int64_t GetTimeMicros()
Returns the system time (not mockable)
std::atomic< NodeId > nLastNodeId
bool RemoveAddedNode(const std::string &node)
bool LookupHost(const std::string &name, std::vector< CNetAddr > &vIP, unsigned int nMaxSolutions, bool fAllowLookup)
Resolve a host string to its corresponding network addresses.
std::list< CNode * > vNodesDisconnected
void RemoveLocal(const CService &addr)
void Shuffle(I first, I last, R &&rng)
More efficient than using std::shuffle on a FastRandomContext.
#define EXCLUSIVE_LOCKS_REQUIRED(...)
static const bool DEFAULT_WHITELISTFORCERELAY
Default for -whitelistforcerelay.
std::string GetAddrName() const
BanMan * m_banman
Pointer to this node's banman.
std::atomic< int64_t > nLastTXTime
UNIX epoch time of the last transaction received from this peer that we had not yet seen (e...
void AddWhitelistPermissionFlags(NetPermissionFlags &flags, const CNetAddr &addr) const
int GetBestHeight() const
std::thread threadOpenConnections
bool AttemptToEvictConnection()
ConnectionType
Different types of connections to a peer.
bool IsOutboundOrBlockRelayConn() const
CNode(NodeId id, ServiceFlags nLocalServicesIn, int nMyStartingHeightIn, SOCKET hSocketIn, const CAddress &addrIn, uint64_t nKeyedNetGroupIn, uint64_t nLocalHostNonceIn, const CAddress &addrBindIn, const std::string &addrNameIn, ConnectionType conn_type_in, bool inbound_onion=false)
const CChainParams & Params()
Return the currently selected parameters.
CSemaphoreGrant grantOutbound
bool SetSocketNoDelay(const SOCKET &hSocket)
Set the TCP_NODELAY flag on a socket.
const CChainParams & m_chain_params
void * memcpy(void *a, const void *b, size_t c)
std::string GetArg(const std::string &strArg, const std::string &strDefault) const
Return string argument or default value.
Feeler connections are short-lived connections made to check that a node is alive.
NetPermissionFlags m_permissionFlags
bool fAddressesInitialized
std::thread threadDNSAddressSeed
int64_t GetAdjustedTime()
ServiceFlags GetDesirableServiceFlags(ServiceFlags services)
Gets the set of service flags which are "desirable" for a given peer.
int64_t PoissonNextSend(int64_t now, int average_interval_seconds)
Return a timestamp in the future (in microseconds) for exponentially distributed events.
std::string ConnectionTypeAsString() const
void SetBestHeight(int height)
SOCKET CreateSocket(const CService &addrConnect)
Try to create a socket file descriptor with specific properties in the communications domain (address...
Network GetNetClass() const
std::atomic< int64_t > nTimeOffset
std::vector< CAddress > GetAddr(size_t max_addresses, size_t max_pct)
Return a bunch of addresses, selected at random.
std::atomic_bool fSuccessfullyConnected
static constexpr uint64_t MAX_SIZE
The maximum size of a serialized object in bytes or number of elements (for eg vectors) when the size...
std::string m_conn_type_string
void ThreadMessageHandler()
These are the default connections that we use to connect with the network.
std::atomic< int > nVersion
void InterruptSocks5(bool interrupt)
unsigned int nSendBufferMaxSize
static const bool DEFAULT_BLOCKSONLY
Default for blocks only.
std::vector< bool > m_asmap
bool GetProxy(enum Network net, proxyType &proxyInfoOut)
static const unsigned int MAX_BLOCK_SERIALIZED_SIZE
The maximum allowed size for a serialized block, in bytes (only for buffer size limits) ...
int GetExtraOutboundCount()
std::string NetworkErrorString(int err)
Return readable error string for a network error code.
CSipHasher GetDeterministicRandomizer(uint64_t id) const
Get a unique deterministic randomizer.
Network ConnectedThroughNetwork() const
Get network the peer connected through.
static const bool DEFAULT_WHITELISTRELAY
Default for -whitelistrelay.
void Good(const CService &addr, bool test_before_evict=true, int64_t nTime=GetAdjustedTime())
Mark an entry as accessible.
CNode * ConnectNode(CAddress addrConnect, const char *pszDest, bool fCountFailure, ConnectionType conn_type)
bool IsBanned(const CNetAddr &net_addr)
Return whether net_addr is banned.
std::string ToString() const
void SetServices(const CService &addr, ServiceFlags nServices)
uint64_t GetTotalBytesSent()
bool GenerateSelectSet(std::set< SOCKET > &recv_set, std::set< SOCKET > &send_set, std::set< SOCKET > &error_set)
void AcceptConnection(const ListenSocket &hListenSocket)
A Span is an object that can refer to a contiguous sequence of objects.
std::string strSubVersion
Subversion as sent to the P2P network in version messages.
CClientUIInterface uiInterface
std::string GetNetworkName(enum Network net)
void MarkAddressGood(const CAddress &addr)
uint256 Hash(const T &in1)
Compute the 256-bit hash of an object.
boost::optional< T > Optional
Substitute for C++17 std::optional.
Information about a peer.
bool SetSockAddr(const struct sockaddr *paddr)
std::thread threadSocketHandler
Simple class for background tasks that should be run periodically or once "after a while"...
We use block-relay-only connections to help prevent against partition attacks.
RecursiveMutex cs_totalBytesRecv
void SetReachable(enum Network net, bool reachable)
Mark a network as reachable or unreachable (no automatic connects to it)
bool SetInternal(const std::string &name)
Create an "internal" address that represents a name or FQDN.
CConnman(uint64_t seed0, uint64_t seed1, bool network_active=true)
RecursiveMutex cs_addrLocal
bool IsManualConn() const
std::vector< CAddress > m_anchors
Addresses that were saved during the previous clean shutdown.
AddrFetch connections are short lived connections used to solicit addresses from peers.
void Connected(const CService &addr, int64_t nTime=GetAdjustedTime())
Mark an entry as currently-connected-to.
int64_t GetTime()
Return system time (or mocked time, if set)
std::atomic_bool fPauseRecv
std::unique_ptr< CSemaphore > semAddnode
void Init(const Options &connOptions)
CThreadInterrupt interruptNet
static void NotifyNumConnectionsChanged(ClientModel *clientmodel, int newNumConnections)
int GetRandInt(int nMax) noexcept
CAddress GetLocalAddress(const CNetAddr *paddrPeer, ServiceFlags nLocalServices)
bool AddLocal(const CService &addr, int nScore=LOCAL_NONE)
std::atomic< int64_t > nLastBlockTime
UNIX epoch time of the last block received from this peer that we had not yet seen (e...
bool IsLocal(const CService &addr)
size_t SocketSendData(CNode *pnode) const
CHash256 & Write(Span< const unsigned char > input)
uint64_t randrange(uint64_t range) noexcept
Generate a random integer in the range [0..range).
bool Read(CAddrMan &addr)
bool GetSockAddr(struct sockaddr *paddr, socklen_t *addrlen) const
Obtain the IPv4/6 socket address this represents.
RecursiveMutex cs_hSocket
bool m_use_addrman_outgoing
int64_t nLastTry
last try whatsoever by us (memory only)
std::vector< AddedNodeInfo > GetAddedNodeInfo()
std::atomic< std::chrono::microseconds > m_ping_start
When the last ping was sent, or 0 if no ping was ever sent.
RecursiveMutex cs_totalBytesSent
unsigned int nReceiveFloodSize
Optional< CNetMessage > GetMessage(std::chrono::microseconds time, uint32_t &out_err_raw_size) override
std::unique_ptr< TxRelay > m_tx_relay
void SplitHostPort(std::string in, int &portOut, std::string &hostOut)
void ThreadDNSAddressSeed()
enum Network GetNetwork() const
Addresses from these networks are not publicly routable on the global Internet.