1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2012 The Bitcoin developers
3 // Distributed under the MIT/X11 software license, see the accompanying
4 // file license.txt or http://www.opensource.org/licenses/mit-license.php.
18 #include <miniupnpc/miniwget.h>
19 #include <miniupnpc/miniupnpc.h>
20 #include <miniupnpc/upnpcommands.h>
21 #include <miniupnpc/upnperrors.h>
25 using namespace boost;
27 static const int MAX_OUTBOUND_CONNECTIONS = 8;
29 void ThreadMessageHandler2(void* parg);
30 void ThreadSocketHandler2(void* parg);
31 void ThreadOpenConnections2(void* parg);
32 void ThreadOpenAddedConnections2(void* parg);
34 void ThreadMapPort2(void* parg);
36 void ThreadDNSAddressSeed2(void* parg);
37 bool OpenNetworkConnection(const CAddress& addrConnect);
42 // Global state variables
45 bool fAllowDNS = false;
46 static bool fUseUPnP = false;
47 uint64 nLocalServices = (fClient ? 0 : NODE_NETWORK);
48 CAddress addrLocalHost(CService("0.0.0.0", 0), nLocalServices);
49 static CNode* pnodeLocalHost = NULL;
50 uint64 nLocalHostNonce = 0;
51 array<int, THREAD_MAX> vnThreadsRunning;
52 static SOCKET hListenSocket = INVALID_SOCKET;
54 vector<CNode*> vNodes;
55 CCriticalSection cs_vNodes;
56 map<vector<unsigned char>, CAddress> mapAddresses;
57 CCriticalSection cs_mapAddresses;
58 map<CInv, CDataStream> mapRelay;
59 deque<pair<int64, CInv> > vRelayExpiration;
60 CCriticalSection cs_mapRelay;
61 map<CInv, int64> mapAlreadyAskedFor;
64 set<CNetAddr> setservAddNodeAddresses;
65 CCriticalSection cs_setservAddNodeAddresses;
69 unsigned short GetListenPort()
71 return (unsigned short)(GetArg("-port", GetDefaultPort()));
74 void CNode::PushGetBlocks(CBlockIndex* pindexBegin, uint256 hashEnd)
76 // Filter out duplicate requests
77 if (pindexBegin == pindexLastGetBlocksBegin && hashEnd == hashLastGetBlocksEnd)
79 pindexLastGetBlocksBegin = pindexBegin;
80 hashLastGetBlocksEnd = hashEnd;
82 PushMessage("getblocks", CBlockLocator(pindexBegin), hashEnd);
87 bool RecvLine(SOCKET hSocket, string& strLine)
93 int nBytes = recv(hSocket, &c, 1, 0);
101 if (strLine.size() >= 9000)
104 else if (nBytes <= 0)
110 int nErr = WSAGetLastError();
111 if (nErr == WSAEMSGSIZE)
113 if (nErr == WSAEWOULDBLOCK || nErr == WSAEINTR || nErr == WSAEINPROGRESS)
119 if (!strLine.empty())
124 printf("socket closed\n");
130 int nErr = WSAGetLastError();
131 printf("recv failed: %d\n", nErr);
140 bool GetMyExternalIP2(const CService& addrConnect, const char* pszGet, const char* pszKeyword, CNetAddr& ipRet)
143 if (!ConnectSocket(addrConnect, hSocket))
144 return error("GetMyExternalIP() : connection to %s failed", addrConnect.ToString().c_str());
146 send(hSocket, pszGet, strlen(pszGet), MSG_NOSIGNAL);
149 while (RecvLine(hSocket, strLine))
151 if (strLine.empty()) // HTTP response is separated from headers by blank line
155 if (!RecvLine(hSocket, strLine))
157 closesocket(hSocket);
160 if (pszKeyword == NULL)
162 if (strLine.find(pszKeyword) != -1)
164 strLine = strLine.substr(strLine.find(pszKeyword) + strlen(pszKeyword));
168 closesocket(hSocket);
169 if (strLine.find("<") != -1)
170 strLine = strLine.substr(0, strLine.find("<"));
171 strLine = strLine.substr(strspn(strLine.c_str(), " \t\n\r"));
172 while (strLine.size() > 0 && isspace(strLine[strLine.size()-1]))
173 strLine.resize(strLine.size()-1);
174 CService addr(strLine,0,true);
175 printf("GetMyExternalIP() received [%s] %s\n", strLine.c_str(), addr.ToString().c_str());
176 if (!addr.IsValid() || !addr.IsRoutable())
182 closesocket(hSocket);
183 return error("GetMyExternalIP() : connection closed");
186 // We now get our external IP from the IRC server first and only use this as a backup
187 bool GetMyExternalIP(CNetAddr& ipRet)
189 CService addrConnect;
191 const char* pszKeyword;
193 if (fNoListen||fUseProxy)
196 for (int nLookup = 0; nLookup <= 1; nLookup++)
197 for (int nHost = 1; nHost <= 2; nHost++)
199 // We should be phasing out our use of sites like these. If we need
200 // replacements, we should ask for volunteers to put this simple
201 // php file on their webserver that prints the client IP:
202 // <?php echo $_SERVER["REMOTE_ADDR"]; ?>
205 addrConnect = CService("91.198.22.70",80); // checkip.dyndns.org
209 CService addrIP("checkip.dyndns.org", 80, true);
210 if (addrIP.IsValid())
211 addrConnect = addrIP;
214 pszGet = "GET / HTTP/1.1\r\n"
215 "Host: checkip.dyndns.org\r\n"
216 "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
217 "Connection: close\r\n"
220 pszKeyword = "Address:";
224 addrConnect = CService("74.208.43.192", 80); // www.showmyip.com
228 CService addrIP("www.showmyip.com", 80, true);
229 if (addrIP.IsValid())
230 addrConnect = addrIP;
233 pszGet = "GET /simple/ HTTP/1.1\r\n"
234 "Host: www.showmyip.com\r\n"
235 "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
236 "Connection: close\r\n"
239 pszKeyword = NULL; // Returns just IP address
242 if (GetMyExternalIP2(addrConnect, pszGet, pszKeyword, ipRet))
249 void ThreadGetMyExternalIP(void* parg)
251 // Wait for IRC to get it first
252 if (GetBoolArg("-irc", false))
254 for (int i = 0; i < 2 * 60; i++)
257 if (fGotExternalIP || fShutdown)
262 // Fallback in case IRC fails to get it
263 if (GetMyExternalIP(addrLocalHost))
265 printf("GetMyExternalIP() returned %s\n", addrLocalHost.ToStringIP().c_str());
266 if (addrLocalHost.IsRoutable())
268 // If we already connected to a few before we had our IP, go back and addr them.
269 // setAddrKnown automatically filters any duplicate sends.
270 CAddress addr(addrLocalHost);
271 addr.nTime = GetAdjustedTime();
272 CRITICAL_BLOCK(cs_vNodes)
273 BOOST_FOREACH(CNode* pnode, vNodes)
274 pnode->PushAddress(addr);
283 bool AddAddress(CAddress addr, int64 nTimePenalty, CAddrDB *pAddrDB)
285 if (!addr.IsRoutable())
287 if ((CService)addr == (CService)addrLocalHost)
289 addr.nTime = max((int64)0, (int64)addr.nTime - nTimePenalty);
290 bool fUpdated = false;
292 CAddress addrFound = addr;
294 CRITICAL_BLOCK(cs_mapAddresses)
296 map<vector<unsigned char>, CAddress>::iterator it = mapAddresses.find(addr.GetKey());
297 if (it == mapAddresses.end())
300 printf("AddAddress(%s)\n", addr.ToString().c_str());
301 mapAddresses.insert(make_pair(addr.GetKey(), addr));
307 addrFound = (*it).second;
308 if ((addrFound.nServices | addr.nServices) != addrFound.nServices)
310 // Services have been added
311 addrFound.nServices |= addr.nServices;
314 bool fCurrentlyOnline = (GetAdjustedTime() - addr.nTime < 24 * 60 * 60);
315 int64 nUpdateInterval = (fCurrentlyOnline ? 60 * 60 : 24 * 60 * 60);
316 if (addrFound.nTime < addr.nTime - nUpdateInterval)
318 // Periodically update most recently seen time
319 addrFound.nTime = addr.nTime;
324 // There is a nasty deadlock bug if this is done inside the cs_mapAddresses
326 // Thread 1: begin db transaction (locks inside-db-mutex)
327 // then AddAddress (locks cs_mapAddresses)
328 // Thread 2: AddAddress (locks cs_mapAddresses)
329 // ... then db operation hangs waiting for inside-db-mutex
333 pAddrDB->WriteAddress(addrFound);
335 CAddrDB().WriteAddress(addrFound);
340 void AddressCurrentlyConnected(const CService& addr)
342 CAddress *paddrFound = NULL;
344 CRITICAL_BLOCK(cs_mapAddresses)
346 // Only if it's been published already
347 map<vector<unsigned char>, CAddress>::iterator it = mapAddresses.find(addr.GetKey());
348 if (it != mapAddresses.end())
349 paddrFound = &(*it).second;
354 int64 nUpdateInterval = 20 * 60;
355 if (paddrFound->nTime < GetAdjustedTime() - nUpdateInterval)
357 // Periodically update most recently seen time
358 paddrFound->nTime = GetAdjustedTime();
360 addrdb.WriteAddress(*paddrFound);
369 void AbandonRequests(void (*fn)(void*, CDataStream&), void* param1)
371 // If the dialog might get closed before the reply comes back,
372 // call this in the destructor so it doesn't get called after it's deleted.
373 CRITICAL_BLOCK(cs_vNodes)
375 BOOST_FOREACH(CNode* pnode, vNodes)
377 CRITICAL_BLOCK(pnode->cs_mapRequests)
379 for (map<uint256, CRequestTracker>::iterator mi = pnode->mapRequests.begin(); mi != pnode->mapRequests.end();)
381 CRequestTracker& tracker = (*mi).second;
382 if (tracker.fn == fn && tracker.param1 == param1)
383 pnode->mapRequests.erase(mi++);
399 // Subscription methods for the broadcast and subscription system.
400 // Channel numbers are message numbers, i.e. MSG_TABLE and MSG_PRODUCT.
402 // The subscription system uses a meet-in-the-middle strategy.
403 // With 100,000 nodes, if senders broadcast to 1000 random nodes and receivers
404 // subscribe to 1000 random nodes, 99.995% (1 - 0.99^1000) of messages will get through.
407 bool AnySubscribed(unsigned int nChannel)
409 if (pnodeLocalHost->IsSubscribed(nChannel))
411 CRITICAL_BLOCK(cs_vNodes)
412 BOOST_FOREACH(CNode* pnode, vNodes)
413 if (pnode->IsSubscribed(nChannel))
418 bool CNode::IsSubscribed(unsigned int nChannel)
420 if (nChannel >= vfSubscribe.size())
422 return vfSubscribe[nChannel];
425 void CNode::Subscribe(unsigned int nChannel, unsigned int nHops)
427 if (nChannel >= vfSubscribe.size())
430 if (!AnySubscribed(nChannel))
433 CRITICAL_BLOCK(cs_vNodes)
434 BOOST_FOREACH(CNode* pnode, vNodes)
436 pnode->PushMessage("subscribe", nChannel, nHops);
439 vfSubscribe[nChannel] = true;
442 void CNode::CancelSubscribe(unsigned int nChannel)
444 if (nChannel >= vfSubscribe.size())
447 // Prevent from relaying cancel if wasn't subscribed
448 if (!vfSubscribe[nChannel])
450 vfSubscribe[nChannel] = false;
452 if (!AnySubscribed(nChannel))
454 // Relay subscription cancel
455 CRITICAL_BLOCK(cs_vNodes)
456 BOOST_FOREACH(CNode* pnode, vNodes)
458 pnode->PushMessage("sub-cancel", nChannel);
470 CNode* FindNode(const CNetAddr& ip)
472 CRITICAL_BLOCK(cs_vNodes)
474 BOOST_FOREACH(CNode* pnode, vNodes)
475 if ((CNetAddr)pnode->addr == ip)
481 CNode* FindNode(const CService& addr)
483 CRITICAL_BLOCK(cs_vNodes)
485 BOOST_FOREACH(CNode* pnode, vNodes)
486 if ((CService)pnode->addr == addr)
492 CNode* ConnectNode(CAddress addrConnect, int64 nTimeout)
494 if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost)
497 // Look for an existing connection
498 CNode* pnode = FindNode((CService)addrConnect);
502 pnode->AddRef(nTimeout);
509 printf("trying connection %s lastseen=%.1fhrs lasttry=%.1fhrs\n",
510 addrConnect.ToString().c_str(),
511 (double)(addrConnect.nTime - GetAdjustedTime())/3600.0,
512 (double)(addrConnect.nLastTry - GetAdjustedTime())/3600.0);
514 CRITICAL_BLOCK(cs_mapAddresses)
515 mapAddresses[addrConnect.GetKey()].nLastTry = GetAdjustedTime();
519 if (ConnectSocket(addrConnect, hSocket))
522 printf("connected %s\n", addrConnect.ToString().c_str());
524 // Set to nonblocking
527 if (ioctlsocket(hSocket, FIONBIO, &nOne) == SOCKET_ERROR)
528 printf("ConnectSocket() : ioctlsocket nonblocking setting failed, error %d\n", WSAGetLastError());
530 if (fcntl(hSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
531 printf("ConnectSocket() : fcntl nonblocking setting failed, error %d\n", errno);
535 CNode* pnode = new CNode(hSocket, addrConnect, false);
537 pnode->AddRef(nTimeout);
540 CRITICAL_BLOCK(cs_vNodes)
541 vNodes.push_back(pnode);
543 pnode->nTimeConnected = GetTime();
552 void CNode::CloseSocketDisconnect()
555 if (hSocket != INVALID_SOCKET)
558 printf("%s ", DateTimeStrFormat("%x %H:%M:%S", GetTime()).c_str());
559 printf("disconnecting node %s\n", addr.ToString().c_str());
560 closesocket(hSocket);
561 hSocket = INVALID_SOCKET;
565 void CNode::Cleanup()
567 // All of a nodes broadcasts and subscriptions are automatically torn down
568 // when it goes down, so a node has to stay up to keep its broadcast going.
570 // Cancel subscriptions
571 for (unsigned int nChannel = 0; nChannel < vfSubscribe.size(); nChannel++)
572 if (vfSubscribe[nChannel])
573 CancelSubscribe(nChannel);
577 void CNode::PushVersion()
579 /// when NTP implemented, change to just nTime = GetAdjustedTime()
580 int64 nTime = (fInbound ? GetAdjustedTime() : GetTime());
581 CAddress addrYou = (fUseProxy ? CAddress(CService("0.0.0.0",0)) : addr);
582 CAddress addrMe = (fUseProxy || !addrLocalHost.IsRoutable() ? CAddress(CService("0.0.0.0",0)) : addrLocalHost);
583 RAND_bytes((unsigned char*)&nLocalHostNonce, sizeof(nLocalHostNonce));
584 PushMessage("version", PROTOCOL_VERSION, nLocalServices, nTime, addrYou, addrMe,
585 nLocalHostNonce, FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<string>()), nBestHeight);
592 std::map<CNetAddr, int64> CNode::setBanned;
593 CCriticalSection CNode::cs_setBanned;
595 void CNode::ClearBanned()
600 bool CNode::IsBanned(CNetAddr ip)
602 bool fResult = false;
603 CRITICAL_BLOCK(cs_setBanned)
605 std::map<CNetAddr, int64>::iterator i = setBanned.find(ip);
606 if (i != setBanned.end())
608 int64 t = (*i).second;
616 bool CNode::Misbehaving(int howmuch)
620 printf("Warning: local node %s misbehaving\n", addr.ToString().c_str());
624 nMisbehavior += howmuch;
625 if (nMisbehavior >= GetArg("-banscore", 100))
627 int64 banTime = GetTime()+GetArg("-bantime", 60*60*24); // Default 24-hour ban
628 CRITICAL_BLOCK(cs_setBanned)
629 if (setBanned[addr] < banTime)
630 setBanned[addr] = banTime;
631 CloseSocketDisconnect();
632 printf("Disconnected %s for misbehavior (score=%d)\n", addr.ToString().c_str(), nMisbehavior);
649 void ThreadSocketHandler(void* parg)
651 IMPLEMENT_RANDOMIZE_STACK(ThreadSocketHandler(parg));
654 vnThreadsRunning[THREAD_SOCKETHANDLER]++;
655 ThreadSocketHandler2(parg);
656 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
658 catch (std::exception& e) {
659 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
660 PrintException(&e, "ThreadSocketHandler()");
662 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
663 throw; // support pthread_cancel()
665 printf("ThreadSocketHandler exiting\n");
668 void ThreadSocketHandler2(void* parg)
670 printf("ThreadSocketHandler started\n");
671 list<CNode*> vNodesDisconnected;
672 int nPrevNodeCount = 0;
679 CRITICAL_BLOCK(cs_vNodes)
681 // Disconnect unused nodes
682 vector<CNode*> vNodesCopy = vNodes;
683 BOOST_FOREACH(CNode* pnode, vNodesCopy)
685 if (pnode->fDisconnect ||
686 (pnode->GetRefCount() <= 0 && pnode->vRecv.empty() && pnode->vSend.empty()))
688 // remove from vNodes
689 vNodes.erase(remove(vNodes.begin(), vNodes.end(), pnode), vNodes.end());
691 // close socket and cleanup
692 pnode->CloseSocketDisconnect();
695 // hold in disconnected pool until all refs are released
696 pnode->nReleaseTime = max(pnode->nReleaseTime, GetTime() + 15 * 60);
697 if (pnode->fNetworkNode || pnode->fInbound)
699 vNodesDisconnected.push_back(pnode);
703 // Delete disconnected nodes
704 list<CNode*> vNodesDisconnectedCopy = vNodesDisconnected;
705 BOOST_FOREACH(CNode* pnode, vNodesDisconnectedCopy)
707 // wait until threads are done using it
708 if (pnode->GetRefCount() <= 0)
710 bool fDelete = false;
711 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
712 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
713 TRY_CRITICAL_BLOCK(pnode->cs_mapRequests)
714 TRY_CRITICAL_BLOCK(pnode->cs_inventory)
718 vNodesDisconnected.remove(pnode);
724 if (vNodes.size() != nPrevNodeCount)
726 nPrevNodeCount = vNodes.size();
732 // Find which sockets have data to receive
734 struct timeval timeout;
736 timeout.tv_usec = 50000; // frequency to poll pnode->vSend
743 FD_ZERO(&fdsetError);
744 SOCKET hSocketMax = 0;
746 if(hListenSocket != INVALID_SOCKET)
747 FD_SET(hListenSocket, &fdsetRecv);
748 hSocketMax = max(hSocketMax, hListenSocket);
749 CRITICAL_BLOCK(cs_vNodes)
751 BOOST_FOREACH(CNode* pnode, vNodes)
753 if (pnode->hSocket == INVALID_SOCKET)
755 FD_SET(pnode->hSocket, &fdsetRecv);
756 FD_SET(pnode->hSocket, &fdsetError);
757 hSocketMax = max(hSocketMax, pnode->hSocket);
758 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
759 if (!pnode->vSend.empty())
760 FD_SET(pnode->hSocket, &fdsetSend);
764 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
765 int nSelect = select(hSocketMax + 1, &fdsetRecv, &fdsetSend, &fdsetError, &timeout);
766 vnThreadsRunning[THREAD_SOCKETHANDLER]++;
769 if (nSelect == SOCKET_ERROR)
771 int nErr = WSAGetLastError();
774 printf("socket select error %d\n", nErr);
775 for (int i = 0; i <= hSocketMax; i++)
776 FD_SET(i, &fdsetRecv);
779 FD_ZERO(&fdsetError);
780 Sleep(timeout.tv_usec/1000);
785 // Accept new connections
787 if (hListenSocket != INVALID_SOCKET && FD_ISSET(hListenSocket, &fdsetRecv))
789 struct sockaddr_in sockaddr;
790 socklen_t len = sizeof(sockaddr);
791 SOCKET hSocket = accept(hListenSocket, (struct sockaddr*)&sockaddr, &len);
795 if (hSocket != INVALID_SOCKET)
796 addr = CAddress(sockaddr);
798 CRITICAL_BLOCK(cs_vNodes)
799 BOOST_FOREACH(CNode* pnode, vNodes)
803 if (hSocket == INVALID_SOCKET)
805 if (WSAGetLastError() != WSAEWOULDBLOCK)
806 printf("socket error accept failed: %d\n", WSAGetLastError());
808 else if (nInbound >= GetArg("-maxconnections", 125) - MAX_OUTBOUND_CONNECTIONS)
810 CRITICAL_BLOCK(cs_setservAddNodeAddresses)
811 if (!setservAddNodeAddresses.count(addr))
812 closesocket(hSocket);
814 else if (CNode::IsBanned(addr))
816 printf("connection from %s dropped (banned)\n", addr.ToString().c_str());
817 closesocket(hSocket);
821 printf("accepted connection %s\n", addr.ToString().c_str());
822 CNode* pnode = new CNode(hSocket, addr, true);
824 CRITICAL_BLOCK(cs_vNodes)
825 vNodes.push_back(pnode);
831 // Service each socket
833 vector<CNode*> vNodesCopy;
834 CRITICAL_BLOCK(cs_vNodes)
837 BOOST_FOREACH(CNode* pnode, vNodesCopy)
840 BOOST_FOREACH(CNode* pnode, vNodesCopy)
848 if (pnode->hSocket == INVALID_SOCKET)
850 if (FD_ISSET(pnode->hSocket, &fdsetRecv) || FD_ISSET(pnode->hSocket, &fdsetError))
852 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
854 CDataStream& vRecv = pnode->vRecv;
855 unsigned int nPos = vRecv.size();
857 if (nPos > ReceiveBufferSize()) {
858 if (!pnode->fDisconnect)
859 printf("socket recv flood control disconnect (%d bytes)\n", vRecv.size());
860 pnode->CloseSocketDisconnect();
863 // typical socket buffer is 8K-64K
864 char pchBuf[0x10000];
865 int nBytes = recv(pnode->hSocket, pchBuf, sizeof(pchBuf), MSG_DONTWAIT);
868 vRecv.resize(nPos + nBytes);
869 memcpy(&vRecv[nPos], pchBuf, nBytes);
870 pnode->nLastRecv = GetTime();
872 else if (nBytes == 0)
874 // socket closed gracefully
875 if (!pnode->fDisconnect)
876 printf("socket closed\n");
877 pnode->CloseSocketDisconnect();
882 int nErr = WSAGetLastError();
883 if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
885 if (!pnode->fDisconnect)
886 printf("socket recv error %d\n", nErr);
887 pnode->CloseSocketDisconnect();
897 if (pnode->hSocket == INVALID_SOCKET)
899 if (FD_ISSET(pnode->hSocket, &fdsetSend))
901 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
903 CDataStream& vSend = pnode->vSend;
906 int nBytes = send(pnode->hSocket, &vSend[0], vSend.size(), MSG_NOSIGNAL | MSG_DONTWAIT);
909 vSend.erase(vSend.begin(), vSend.begin() + nBytes);
910 pnode->nLastSend = GetTime();
915 int nErr = WSAGetLastError();
916 if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
918 printf("socket send error %d\n", nErr);
919 pnode->CloseSocketDisconnect();
922 if (vSend.size() > SendBufferSize()) {
923 if (!pnode->fDisconnect)
924 printf("socket send flood control disconnect (%d bytes)\n", vSend.size());
925 pnode->CloseSocketDisconnect();
932 // Inactivity checking
934 if (pnode->vSend.empty())
935 pnode->nLastSendEmpty = GetTime();
936 if (GetTime() - pnode->nTimeConnected > 60)
938 if (pnode->nLastRecv == 0 || pnode->nLastSend == 0)
940 printf("socket no message in first 60 seconds, %d %d\n", pnode->nLastRecv != 0, pnode->nLastSend != 0);
941 pnode->fDisconnect = true;
943 else if (GetTime() - pnode->nLastSend > 90*60 && GetTime() - pnode->nLastSendEmpty > 90*60)
945 printf("socket not sending\n");
946 pnode->fDisconnect = true;
948 else if (GetTime() - pnode->nLastRecv > 90*60)
950 printf("socket inactivity timeout\n");
951 pnode->fDisconnect = true;
955 CRITICAL_BLOCK(cs_vNodes)
957 BOOST_FOREACH(CNode* pnode, vNodesCopy)
974 void ThreadMapPort(void* parg)
976 IMPLEMENT_RANDOMIZE_STACK(ThreadMapPort(parg));
979 vnThreadsRunning[THREAD_UPNP]++;
980 ThreadMapPort2(parg);
981 vnThreadsRunning[THREAD_UPNP]--;
983 catch (std::exception& e) {
984 vnThreadsRunning[THREAD_UPNP]--;
985 PrintException(&e, "ThreadMapPort()");
987 vnThreadsRunning[THREAD_UPNP]--;
988 PrintException(NULL, "ThreadMapPort()");
990 printf("ThreadMapPort exiting\n");
993 void ThreadMapPort2(void* parg)
995 printf("ThreadMapPort started\n");
998 sprintf(port, "%d", GetListenPort());
1000 const char * multicastif = 0;
1001 const char * minissdpdpath = 0;
1002 struct UPNPDev * devlist = 0;
1005 #ifndef UPNPDISCOVER_SUCCESS
1007 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0);
1011 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0, 0, &error);
1014 struct UPNPUrls urls;
1015 struct IGDdatas data;
1018 r = UPNP_GetValidIGD(devlist, &urls, &data, lanaddr, sizeof(lanaddr));
1021 if (!addrLocalHost.IsRoutable())
1023 char externalIPAddress[40];
1024 r = UPNP_GetExternalIPAddress(urls.controlURL, data.first.servicetype, externalIPAddress);
1025 if(r != UPNPCOMMAND_SUCCESS)
1026 printf("UPnP: GetExternalIPAddress() returned %d\n", r);
1029 if(externalIPAddress[0])
1031 printf("UPnP: ExternalIPAddress = %s\n", externalIPAddress);
1032 CAddress addrExternalFromUPnP(CService(externalIPAddress, 0), nLocalServices);
1033 if (addrExternalFromUPnP.IsRoutable())
1034 addrLocalHost = addrExternalFromUPnP;
1037 printf("UPnP: GetExternalIPAddress failed.\n");
1041 string strDesc = "Bitcoin " + FormatFullVersion();
1042 #ifndef UPNPDISCOVER_SUCCESS
1044 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
1045 port, port, lanaddr, strDesc.c_str(), "TCP", 0);
1048 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
1049 port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
1052 if(r!=UPNPCOMMAND_SUCCESS)
1053 printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
1054 port, port, lanaddr, r, strupnperror(r));
1056 printf("UPnP Port Mapping successful.\n");
1059 if (fShutdown || !fUseUPnP)
1061 r = UPNP_DeletePortMapping(urls.controlURL, data.first.servicetype, port, "TCP", 0);
1062 printf("UPNP_DeletePortMapping() returned : %d\n", r);
1063 freeUPNPDevlist(devlist); devlist = 0;
1064 FreeUPNPUrls(&urls);
1067 if (i % 600 == 0) // Refresh every 20 minutes
1069 #ifndef UPNPDISCOVER_SUCCESS
1071 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
1072 port, port, lanaddr, strDesc.c_str(), "TCP", 0);
1075 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
1076 port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
1079 if(r!=UPNPCOMMAND_SUCCESS)
1080 printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
1081 port, port, lanaddr, r, strupnperror(r));
1083 printf("UPnP Port Mapping successful.\n");;
1089 printf("No valid UPnP IGDs found\n");
1090 freeUPNPDevlist(devlist); devlist = 0;
1092 FreeUPNPUrls(&urls);
1094 if (fShutdown || !fUseUPnP)
1101 void MapPort(bool fMapPort)
1103 if (fUseUPnP != fMapPort)
1105 fUseUPnP = fMapPort;
1107 if (fUseUPnP && vnThreadsRunning[THREAD_UPNP] < 1)
1109 if (!CreateThread(ThreadMapPort, NULL))
1110 printf("Error: ThreadMapPort(ThreadMapPort) failed\n");
1114 void MapPort(bool /* unused fMapPort */)
1116 // Intentionally left blank.
1129 static const char *strDNSSeed[] = {
1131 "dnsseed.bluematt.me",
1132 "seed.bitcoin.sipa.be",
1133 "dnsseed.bitcoin.dashjr.org",
1136 void ThreadDNSAddressSeed(void* parg)
1138 IMPLEMENT_RANDOMIZE_STACK(ThreadDNSAddressSeed(parg));
1141 vnThreadsRunning[THREAD_DNSSEED]++;
1142 ThreadDNSAddressSeed2(parg);
1143 vnThreadsRunning[THREAD_DNSSEED]--;
1145 catch (std::exception& e) {
1146 vnThreadsRunning[THREAD_DNSSEED]--;
1147 PrintException(&e, "ThreadDNSAddressSeed()");
1149 vnThreadsRunning[THREAD_DNSSEED]--;
1150 throw; // support pthread_cancel()
1152 printf("ThreadDNSAddressSeed exiting\n");
1155 void ThreadDNSAddressSeed2(void* parg)
1157 printf("ThreadDNSAddressSeed started\n");
1162 printf("Loading addresses from DNS seeds (could take a while)\n");
1164 for (int seed_idx = 0; seed_idx < ARRAYLEN(strDNSSeed); seed_idx++) {
1165 vector<CNetAddr> vaddr;
1166 if (LookupHost(strDNSSeed[seed_idx], vaddr))
1170 BOOST_FOREACH (CNetAddr& ip, vaddr)
1172 if (ip.IsRoutable())
1174 CAddress addr(CService(ip, GetDefaultPort()), NODE_NETWORK);
1176 AddAddress(addr, 0, &addrDB);
1180 addrDB.TxnCommit(); // Save addresses (it's ok if this fails)
1185 printf("%d addresses found from DNS seeds\n", found);
1199 unsigned int pnSeed[] =
1201 0x959bd347, 0xf8de42b2, 0x73bc0518, 0xea6edc50, 0x21b00a4d, 0xc725b43d, 0xd665464d, 0x1a2a770e,
1202 0x27c93946, 0x65b2fa46, 0xb80ae255, 0x66b3b446, 0xb1877a3e, 0x6ee89e3e, 0xc3175b40, 0x2a01a83c,
1203 0x95b1363a, 0xa079ad3d, 0xe6ca801f, 0x027f4f4a, 0x34f7f03a, 0xf790f04a, 0x16ca801f, 0x2f4d5e40,
1204 0x3a4d5e40, 0xc43a322e, 0xc8159753, 0x14d4724c, 0x7919a118, 0xe0bdb34e, 0x68a16b2e, 0xff64b44d,
1205 0x6099115b, 0x9b57b05b, 0x7bd1b4ad, 0xdf95944f, 0x29d2b73d, 0xafa8db79, 0xe247ba41, 0x24078348,
1206 0xf722f03c, 0x33567ebc, 0xace64ed4, 0x984d3932, 0xb5f34e55, 0x27b7024d, 0x94579247, 0x8894042e,
1207 0x9357d34c, 0x1063c24b, 0xcaa228b1, 0xa3c5a8b2, 0x5dc64857, 0xa2c23643, 0xa8369a54, 0x31203077,
1208 0x00707c5c, 0x09fc0b3a, 0x272e9e2e, 0xf80f043e, 0x9449ca3e, 0x5512c33e, 0xd106b555, 0xe8024157,
1209 0xe288ec29, 0xc79c5461, 0xafb63932, 0xdb02ab4b, 0x0e512777, 0x8a145a4c, 0xb201ff4f, 0x5e09314b,
1210 0xcd9bfbcd, 0x1c023765, 0x4394e75c, 0xa728bd4d, 0x65331552, 0xa98420b1, 0x89ecf559, 0x6e80801f,
1211 0xf404f118, 0xefd62b51, 0x05918346, 0x9b186d5f, 0xacabab46, 0xf912e255, 0xc188ea62, 0xcc55734e,
1212 0xc668064d, 0xd77a4558, 0x46201c55, 0xf17dfc80, 0xf7142f2e, 0x87bfb718, 0x8aa54fb2, 0xc451d518,
1213 0xc4ae8831, 0x8dd44d55, 0x5bbd206c, 0x64536b5d, 0x5c667e60, 0x3b064242, 0xfe963a42, 0xa28e6dc8,
1214 0xe8a9604a, 0xc989464e, 0xd124a659, 0x50065140, 0xa44dfe5e, 0x1079e655, 0x3fb986d5, 0x47895b18,
1215 0x7d3ce4ad, 0x4561ba50, 0x296eec62, 0x255b41ad, 0xaed35ec9, 0x55556f12, 0xc7d3154d, 0x3297b65d,
1216 0x8930121f, 0xabf42e4e, 0x4a29e044, 0x1212685d, 0x676c1e40, 0xce009744, 0x383a8948, 0xa2dbd0ad,
1217 0xecc2564d, 0x07dbc252, 0x887ee24b, 0x5171644c, 0x6bb798c1, 0x847f495d, 0x4cbb7145, 0x3bb81c32,
1218 0x45eb262e, 0xc8015a4e, 0x250a361b, 0xf694f946, 0xd64a183e, 0xd4f1dd59, 0x8f20ffd4, 0x51d9e55c,
1219 0x09521763, 0x5e02002e, 0x32c8074d, 0xe685762e, 0x8290b0bc, 0x762a922e, 0xfc5ee754, 0x83a24829,
1220 0x775b224d, 0x6295bb4d, 0x38ec0555, 0xbffbba50, 0xe5560260, 0x86b16a7c, 0xd372234e, 0x49a3c24b,
1221 0x2f6a171f, 0x4d75ed60, 0xae94115b, 0xcb543744, 0x63080c59, 0x3f9c724c, 0xc977ce18, 0x532efb18,
1222 0x69dc3b2e, 0x5f94d929, 0x1732bb4d, 0x9c814b4d, 0xe6b3762e, 0xc024f662, 0x8face35b, 0x6b5b044d,
1223 0x798c7b57, 0x79a6b44c, 0x067d3057, 0xf9e94e5f, 0x91cbe15b, 0x71405eb2, 0x2662234e, 0xcbcc4a6d,
1224 0xbf69d54b, 0xa79b4e55, 0xec6d3e51, 0x7c0b3c02, 0x60f83653, 0x24c1e15c, 0x1110b62e, 0x10350f59,
1225 0xa56f1d55, 0x3509e7a9, 0xeb128354, 0x14268e2e, 0x934e28bc, 0x8e32692e, 0x8331a21f, 0x3e633932,
1226 0xc812b12e, 0xc684bf2e, 0x80112d2e, 0xe0ddc96c, 0xc630ca4a, 0x5c09b3b2, 0x0b580518, 0xc8e9d54b,
1227 0xd169aa43, 0x17d0d655, 0x1d029963, 0x7ff87559, 0xcb701f1f, 0x6fa3e85d, 0xe45e9a54, 0xf05d1802,
1228 0x44d03b2e, 0x837b692e, 0xccd4354e, 0x3d6da13c, 0x3423084d, 0xf707c34a, 0x55f6db3a, 0xad26e442,
1229 0x6233a21f, 0x09e80e59, 0x8caeb54d, 0xbe870941, 0xb407d20e, 0x20b51018, 0x56fb152e, 0x460d2a4e,
1230 0xbb9a2946, 0x560eb12e, 0xed83dd29, 0xd6724f53, 0xa50aafb8, 0x451346d9, 0x88348e2e, 0x7312fead,
1231 0x8ecaf96f, 0x1bda4e5f, 0xf1671e40, 0x3c8c3e3b, 0x4716324d, 0xdde24ede, 0xf98cd17d, 0xa91d4644,
1232 0x28124eb2, 0x147d5129, 0xd022042e, 0x61733d3b, 0xad0d5e02, 0x8ce2932e, 0xe5c18502, 0x549c1e32,
1233 0x9685801f, 0x86e217ad, 0xd948214b, 0x4110f462, 0x3a2e894e, 0xbd35492e, 0x87e0d558, 0x64b8ef7d,
1234 0x7c3eb962, 0x72a84b3e, 0x7cd667c9, 0x28370a2e, 0x4bc60e7b, 0x6fc1ec60, 0x14a6983f, 0x86739a4b,
1235 0x46954e5f, 0x32e2e15c, 0x2e9326cf, 0xe5801c5e, 0x379607b2, 0x32151145, 0xf0e39744, 0xacb54c55,
1236 0xa37dfb60, 0x83b55cc9, 0x388f7ca5, 0x15034f5f, 0x3e94965b, 0x68e0ffad, 0x35280f59, 0x8fe190cf,
1237 0x7c6ba5b2, 0xa5e9db43, 0x4ee1fc60, 0xd9d94e5f, 0x04040677, 0x0ea9b35e, 0x5961f14f, 0x67fda063,
1238 0xa48a5a31, 0xc6524e55, 0x283d325e, 0x3f37515f, 0x96b94b3e, 0xacce620e, 0x6481cc5b, 0xa4a06d4b,
1239 0x9e95d2d9, 0xe40c03d5, 0xc2f4514b, 0xb79aad44, 0xf64be843, 0xb2064070, 0xfca00455, 0x429dfa4e,
1240 0x2323f173, 0xeda4185e, 0xabd5227d, 0x9efd4d58, 0xb1104758, 0x4811e955, 0xbd9ab355, 0xe921f44b,
1241 0x9f166dce, 0x09e279b2, 0xe0c9ac7b, 0x7901a5ad, 0xa145d4b0, 0x79104671, 0xec31e35a, 0x4fe0b555,
1242 0xc7d9cbad, 0xad057f55, 0xe94cc759, 0x7fe0b043, 0xe4529f2e, 0x0d4dd4b2, 0x9f11a54d, 0x031e2e4e,
1243 0xe6014f5f, 0x11d1ca6c, 0x26bd7f61, 0xeb86854f, 0x4d347b57, 0x116bbe2e, 0xdba7234e, 0x7bcbfd2e,
1244 0x174dd4b2, 0x6686762e, 0xb089ba50, 0xc6258246, 0x087e767b, 0xc4a8cb4a, 0x595dba50, 0x7f0ae502,
1245 0x7b1dbd5a, 0xa0603492, 0x57d1af4b, 0x9e21ffd4, 0x6393064d, 0x7407376e, 0xe484762e, 0x122a4e53,
1246 0x4a37aa43, 0x3888a6be, 0xee77864e, 0x039c8dd5, 0x688d89af, 0x0e988f62, 0x08218246, 0xfc2f8246,
1247 0xd1d97040, 0xd64cd4b2, 0x5ae4a6b8, 0x7d0de9bc, 0x8d304d61, 0x06c5c672, 0xa4c8bd4d, 0xe0fd373b,
1248 0x575ebe4d, 0x72d26277, 0x55570f55, 0x77b154d9, 0xe214293a, 0xfc740f4b, 0xfe3f6a57, 0xa9c55f02,
1249 0xae4054db, 0x2394d918, 0xb511b24a, 0xb8741ab2, 0x0758e65e, 0xc7b5795b, 0xb0a30a4c, 0xaf7f170c,
1250 0xf3b4762e, 0x8179576d, 0x738a1581, 0x4b95b64c, 0x9829b618, 0x1bea932e, 0x7bdeaa4b, 0xcb5e0281,
1251 0x65618f54, 0x0658474b, 0x27066acf, 0x40556d65, 0x7d204d53, 0xf28bc244, 0xdce23455, 0xadc0ff54,
1252 0x3863c948, 0xcee34e5f, 0xdeb85e02, 0x2ed17a61, 0x6a7b094d, 0x7f0cfc40, 0x59603f54, 0x3220afbc,
1253 0xb5dfd962, 0x125d21c0, 0x13f8d243, 0xacfefb4e, 0x86c2c147, 0x3d8bbd59, 0xbd02a21f, 0x2593042e,
1254 0xc6a17a7c, 0x28925861, 0xb487ed44, 0xb5f4fd6d, 0x90c28a45, 0x5a14f74d, 0x43d71b4c, 0x728ebb5d,
1255 0x885bf950, 0x08134dd0, 0x38ec046e, 0xc575684b, 0x50082d2e, 0xa2f47757, 0x270f86ae, 0xf3ff6462,
1256 0x10ed3f4e, 0x4b58d462, 0xe01ce23e, 0x8c5b092e, 0x63e52f4e, 0x22c1e85d, 0xa908f54e, 0x8591624f,
1257 0x2c0fb94e, 0xa280ba3c, 0xb6f41b4c, 0x24f9aa47, 0x27201647, 0x3a3ea6dc, 0xa14fc3be, 0x3c34bdd5,
1258 0x5b8d4f5b, 0xaadeaf4b, 0xc71cab50, 0x15697a4c, 0x9a1a734c, 0x2a037d81, 0x2590bd59, 0x48ec2741,
1259 0x53489c5b, 0x7f00314b, 0x2170d362, 0xf2e92542, 0x42c10b44, 0x98f0f118, 0x883a3456, 0x099a932e,
1260 0xea38f7bc, 0x644e9247, 0xbb61b62e, 0x30e0863d, 0x5f51be54, 0x207215c7, 0x5f306c45, 0xaa7f3932,
1261 0x98da7d45, 0x4e339b59, 0x2e411581, 0xa808f618, 0xad2c0c59, 0x54476741, 0x09e99fd1, 0x5db8f752,
1262 0xc16df8bd, 0x1dd4b44f, 0x106edf2e, 0x9e15c180, 0x2ad6b56f, 0x633a5332, 0xff33787c, 0x077cb545,
1263 0x6610be6d, 0x75aad2c4, 0x72fb4d5b, 0xe81e0f59, 0x576f6332, 0x47333373, 0x351ed783, 0x2d90fb50,
1264 0x8d5e0f6c, 0x5b27a552, 0xdb293ebb, 0xe55ef950, 0x4b133ad8, 0x75df975a, 0x7b6a8740, 0xa899464b,
1265 0xfab15161, 0x10f8b64d, 0xd055ea4d, 0xee8e146b, 0x4b14afb8, 0x4bc1c44a, 0x9b961dcc, 0xd111ff43,
1266 0xfca0b745, 0xc800e412, 0x0afad9d1, 0xf751c350, 0xf9f0cccf, 0xa290a545, 0x8ef13763, 0x7ec70d59,
1267 0x2b066acf, 0x65496c45, 0xade02c1b, 0xae6eb077, 0x92c1e65b, 0xc064e6a9, 0xc649e56d, 0x5287a243,
1268 0x36de4f5b, 0x5b1df6ad, 0x65c39a59, 0xdba805b2, 0x20067aa8, 0x6457e56d, 0x3cee26cf, 0xfd3ff26d,
1269 0x04f86d4a, 0x06b8e048, 0xa93bcd5c, 0x91135852, 0xbe90a643, 0x8fa0094d, 0x06d8215f, 0x2677094d,
1270 0xd735685c, 0x164a00c9, 0x5209ac5f, 0xa9564c5c, 0x3b504f5f, 0xcc826bd0, 0x4615042e, 0x5fe13b4a,
1271 0x8c81b86d, 0x879ab68c, 0x1de564b8, 0x434487d8, 0x2dcb1b63, 0x82ab524a, 0xb0676abb, 0xa13d9c62,
1272 0xdbb5b86d, 0x5b7f4b59, 0xaddfb44d, 0xad773532, 0x3997054c, 0x72cebd89, 0xb194544c, 0xc5b8046e,
1273 0x6e1adeb2, 0xaa5abb51, 0xefb54b44, 0x15efc54f, 0xe9f1bc4d, 0x5f401b6c, 0x97f018ad, 0xc82f9252,
1274 0x2cdc762e, 0x8e52e56d, 0x1827175e, 0x9b7d7d80, 0xb2ad6845, 0x51065140, 0x71180a18, 0x5b27006c,
1275 0x0621e255, 0x721cbe58, 0x670c0cb8, 0xf8bd715d, 0xe0bdc5d9, 0xed843501, 0x4b84554d, 0x7f1a18bc,
1276 0x53bcaf47, 0x5729d35f, 0xf0dda246, 0x22382bd0, 0x4d641fb0, 0x316afcde, 0x50a22f1f, 0x73608046,
1277 0xc461d84a, 0xb2dbe247,
1282 void ThreadOpenConnections(void* parg)
1284 IMPLEMENT_RANDOMIZE_STACK(ThreadOpenConnections(parg));
1287 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1288 ThreadOpenConnections2(parg);
1289 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1291 catch (std::exception& e) {
1292 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1293 PrintException(&e, "ThreadOpenConnections()");
1295 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1296 PrintException(NULL, "ThreadOpenConnections()");
1298 printf("ThreadOpenConnections exiting\n");
1301 void ThreadOpenConnections2(void* parg)
1303 printf("ThreadOpenConnections started\n");
1305 // Connect to specific addresses
1306 if (mapArgs.count("-connect"))
1308 for (int64 nLoop = 0;; nLoop++)
1310 BOOST_FOREACH(string strAddr, mapMultiArgs["-connect"])
1312 CAddress addr(CService(strAddr, GetDefaultPort(), fAllowDNS));
1314 OpenNetworkConnection(addr);
1315 for (int i = 0; i < 10 && i < nLoop; i++)
1325 // Initiate network connections
1326 int64 nStart = GetTime();
1329 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1331 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1335 // Limit outbound connections
1339 CRITICAL_BLOCK(cs_vNodes)
1340 BOOST_FOREACH(CNode* pnode, vNodes)
1341 if (!pnode->fInbound)
1343 int nMaxOutboundConnections = MAX_OUTBOUND_CONNECTIONS;
1344 nMaxOutboundConnections = min(nMaxOutboundConnections, (int)GetArg("-maxconnections", 125));
1345 if (nOutbound < nMaxOutboundConnections)
1347 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1349 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1354 bool fAddSeeds = false;
1356 CRITICAL_BLOCK(cs_mapAddresses)
1358 // Add seed nodes if IRC isn't working
1359 bool fTOR = (fUseProxy && addrProxy.GetPort() == 9050);
1360 if (mapAddresses.empty() && (GetTime() - nStart > 60 || fTOR) && !fTestNet)
1366 for (int i = 0; i < ARRAYLEN(pnSeed); i++)
1368 // It'll only connect to one or two seed nodes because once it connects,
1369 // it'll get a pile of addresses with newer timestamps.
1370 // Seed nodes are given a random 'last seen time' of between one and two
1372 const int64 nOneWeek = 7*24*60*60;
1374 memcpy(&ip, &pnSeed[i], sizeof(ip));
1375 CAddress addr(CService(ip, GetDefaultPort()));
1376 addr.nTime = GetTime()-GetRand(nOneWeek)-nOneWeek;
1382 // Choose an address to connect to based on most recently seen
1384 CAddress addrConnect;
1385 int64 nBest = std::numeric_limits<int64>::min();
1387 // Only connect to one address per a.b.?.? range.
1388 // Do this here so we don't have to critsect vNodes inside mapAddresses critsect.
1389 set<vector<unsigned char> > setConnected;
1390 CRITICAL_BLOCK(cs_vNodes)
1391 BOOST_FOREACH(CNode* pnode, vNodes)
1392 setConnected.insert(pnode->addr.GetGroup());
1394 int64 nANow = GetAdjustedTime();
1396 CRITICAL_BLOCK(cs_mapAddresses)
1398 BOOST_FOREACH(const PAIRTYPE(vector<unsigned char>, CAddress)& item, mapAddresses)
1400 const CAddress& addr = item.second;
1401 if (!addr.IsIPv4() || !addr.IsValid() || setConnected.count(addr.GetGroup()))
1403 int64 nSinceLastSeen = nANow - addr.nTime;
1404 int64 nSinceLastTry = nANow - addr.nLastTry;
1406 // Randomize the order in a deterministic way, putting the standard port first
1407 int64 nRandomizer = (uint64)(nStart * 4951 + addr.nLastTry * 9567851 + addr.GetHash()) % (2 * 60 * 60);
1408 if (addr.GetPort() != GetDefaultPort())
1409 nRandomizer += 2 * 60 * 60;
1411 // Last seen Base retry frequency
1420 // 365 days 93 hours
1421 int64 nDelay = (int64)(3600.0 * sqrt(fabs((double)nSinceLastSeen) / 3600.0) + nRandomizer);
1423 // Fast reconnect for one hour after last seen
1424 if (nSinceLastSeen < 60 * 60)
1427 // Limit retry frequency
1428 if (nSinceLastTry < nDelay)
1431 // If we have IRC, we'll be notified when they first come online,
1432 // and again every 24 hours by the refresh broadcast.
1433 if (nGotIRCAddresses > 0 && vNodes.size() >= 2 && nSinceLastSeen > 24 * 60 * 60)
1436 // Only try the old stuff if we don't have enough connections
1437 if (vNodes.size() >= 8 && nSinceLastSeen > 24 * 60 * 60)
1440 // If multiple addresses are ready, prioritize by time since
1441 // last seen and time since last tried.
1442 int64 nScore = min(nSinceLastTry, (int64)24 * 60 * 60) - nSinceLastSeen - nRandomizer;
1451 if (addrConnect.IsValid())
1452 OpenNetworkConnection(addrConnect);
1456 void ThreadOpenAddedConnections(void* parg)
1458 IMPLEMENT_RANDOMIZE_STACK(ThreadOpenAddedConnections(parg));
1461 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]++;
1462 ThreadOpenAddedConnections2(parg);
1463 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1465 catch (std::exception& e) {
1466 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1467 PrintException(&e, "ThreadOpenAddedConnections()");
1469 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1470 PrintException(NULL, "ThreadOpenAddedConnections()");
1472 printf("ThreadOpenAddedConnections exiting\n");
1475 void ThreadOpenAddedConnections2(void* parg)
1477 printf("ThreadOpenAddedConnections started\n");
1479 if (mapArgs.count("-addnode") == 0)
1482 vector<vector<CService> > vservAddressesToAdd(0);
1483 BOOST_FOREACH(string& strAddNode, mapMultiArgs["-addnode"])
1485 vector<CService> vservNode(0);
1486 if(Lookup(strAddNode.c_str(), vservNode, GetDefaultPort(), fAllowDNS, 0))
1488 vservAddressesToAdd.push_back(vservNode);
1489 CRITICAL_BLOCK(cs_setservAddNodeAddresses)
1490 BOOST_FOREACH(CService& serv, vservNode)
1491 setservAddNodeAddresses.insert(serv);
1496 vector<vector<CService> > vservConnectAddresses = vservAddressesToAdd;
1497 // Attempt to connect to each IP for each addnode entry until at least one is successful per addnode entry
1498 // (keeping in mind that addnode entries can have many IPs if fAllowDNS)
1499 CRITICAL_BLOCK(cs_vNodes)
1500 BOOST_FOREACH(CNode* pnode, vNodes)
1501 for (vector<vector<CService> >::iterator it = vservConnectAddresses.begin(); it != vservConnectAddresses.end(); it++)
1502 BOOST_FOREACH(CService& addrNode, *(it))
1503 if (pnode->addr == addrNode)
1505 it = vservConnectAddresses.erase(it);
1509 BOOST_FOREACH(vector<CService>& vserv, vservConnectAddresses)
1511 OpenNetworkConnection(CAddress(*(vserv.begin())));
1518 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1519 Sleep(120000); // Retry every 2 minutes
1520 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]++;
1526 bool OpenNetworkConnection(const CAddress& addrConnect)
1529 // Initiate outbound network connection
1533 if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost || !addrConnect.IsIPv4() ||
1534 FindNode((CNetAddr)addrConnect) || CNode::IsBanned(addrConnect))
1537 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1538 CNode* pnode = ConnectNode(addrConnect);
1539 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1544 pnode->fNetworkNode = true;
1556 void ThreadMessageHandler(void* parg)
1558 IMPLEMENT_RANDOMIZE_STACK(ThreadMessageHandler(parg));
1561 vnThreadsRunning[THREAD_MESSAGEHANDLER]++;
1562 ThreadMessageHandler2(parg);
1563 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1565 catch (std::exception& e) {
1566 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1567 PrintException(&e, "ThreadMessageHandler()");
1569 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1570 PrintException(NULL, "ThreadMessageHandler()");
1572 printf("ThreadMessageHandler exiting\n");
1575 void ThreadMessageHandler2(void* parg)
1577 printf("ThreadMessageHandler started\n");
1578 SetThreadPriority(THREAD_PRIORITY_BELOW_NORMAL);
1581 vector<CNode*> vNodesCopy;
1582 CRITICAL_BLOCK(cs_vNodes)
1584 vNodesCopy = vNodes;
1585 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1589 // Poll the connected nodes for messages
1590 CNode* pnodeTrickle = NULL;
1591 if (!vNodesCopy.empty())
1592 pnodeTrickle = vNodesCopy[GetRand(vNodesCopy.size())];
1593 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1596 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
1597 ProcessMessages(pnode);
1602 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
1603 SendMessages(pnode, pnode == pnodeTrickle);
1608 CRITICAL_BLOCK(cs_vNodes)
1610 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1614 // Wait and allow messages to bunch up.
1615 // Reduce vnThreadsRunning so StopNode has permission to exit while
1616 // we're sleeping, but we must always check fShutdown after doing this.
1617 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1619 if (fRequestShutdown)
1621 vnThreadsRunning[THREAD_MESSAGEHANDLER]++;
1632 bool BindListenPort(string& strError)
1636 addrLocalHost.SetPort(GetListenPort());
1639 // Initialize Windows Sockets
1641 int ret = WSAStartup(MAKEWORD(2,2), &wsadata);
1642 if (ret != NO_ERROR)
1644 strError = strprintf("Error: TCP/IP socket library failed to start (WSAStartup returned error %d)", ret);
1645 printf("%s\n", strError.c_str());
1650 // Create socket for listening for incoming connections
1651 hListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
1652 if (hListenSocket == INVALID_SOCKET)
1654 strError = strprintf("Error: Couldn't open socket for incoming connections (socket returned error %d)", WSAGetLastError());
1655 printf("%s\n", strError.c_str());
1660 // Different way of disabling SIGPIPE on BSD
1661 setsockopt(hListenSocket, SOL_SOCKET, SO_NOSIGPIPE, (void*)&nOne, sizeof(int));
1665 // Allow binding if the port is still in TIME_WAIT state after
1666 // the program was closed and restarted. Not an issue on windows.
1667 setsockopt(hListenSocket, SOL_SOCKET, SO_REUSEADDR, (void*)&nOne, sizeof(int));
1671 // Set to nonblocking, incoming connections will also inherit this
1672 if (ioctlsocket(hListenSocket, FIONBIO, (u_long*)&nOne) == SOCKET_ERROR)
1674 if (fcntl(hListenSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
1677 strError = strprintf("Error: Couldn't set properties on socket for incoming connections (error %d)", WSAGetLastError());
1678 printf("%s\n", strError.c_str());
1682 // The sockaddr_in structure specifies the address family,
1683 // IP address, and port for the socket that is being bound
1684 struct sockaddr_in sockaddr;
1685 memset(&sockaddr, 0, sizeof(sockaddr));
1686 sockaddr.sin_family = AF_INET;
1687 sockaddr.sin_addr.s_addr = INADDR_ANY; // bind to all IPs on this computer
1688 sockaddr.sin_port = htons(GetListenPort());
1689 if (::bind(hListenSocket, (struct sockaddr*)&sockaddr, sizeof(sockaddr)) == SOCKET_ERROR)
1691 int nErr = WSAGetLastError();
1692 if (nErr == WSAEADDRINUSE)
1693 strError = strprintf(_("Unable to bind to port %d on this computer. Bitcoin is probably already running."), ntohs(sockaddr.sin_port));
1695 strError = strprintf("Error: Unable to bind to port %d on this computer (bind returned error %d)", ntohs(sockaddr.sin_port), nErr);
1696 printf("%s\n", strError.c_str());
1699 printf("Bound to port %d\n", ntohs(sockaddr.sin_port));
1701 // Listen for incoming connections
1702 if (listen(hListenSocket, SOMAXCONN) == SOCKET_ERROR)
1704 strError = strprintf("Error: Listening for incoming connections failed (listen returned error %d)", WSAGetLastError());
1705 printf("%s\n", strError.c_str());
1712 void StartNode(void* parg)
1716 fUseUPnP = GetBoolArg("-upnp", true);
1718 fUseUPnP = GetBoolArg("-upnp", false);
1722 if (pnodeLocalHost == NULL)
1723 pnodeLocalHost = new CNode(INVALID_SOCKET, CAddress(CService("127.0.0.1", 0), nLocalServices));
1726 // Get local host ip
1727 char pszHostName[1000] = "";
1728 if (gethostname(pszHostName, sizeof(pszHostName)) != SOCKET_ERROR)
1730 vector<CNetAddr> vaddr;
1731 if (LookupHost(pszHostName, vaddr))
1732 BOOST_FOREACH (const CNetAddr &addr, vaddr)
1733 if (!addr.IsLocal())
1735 addrLocalHost.SetIP(addr);
1740 // Get local host ip
1741 struct ifaddrs* myaddrs;
1742 if (getifaddrs(&myaddrs) == 0)
1744 for (struct ifaddrs* ifa = myaddrs; ifa != NULL; ifa = ifa->ifa_next)
1746 if (ifa->ifa_addr == NULL) continue;
1747 if ((ifa->ifa_flags & IFF_UP) == 0) continue;
1748 if (strcmp(ifa->ifa_name, "lo") == 0) continue;
1749 if (strcmp(ifa->ifa_name, "lo0") == 0) continue;
1751 if (ifa->ifa_addr->sa_family == AF_INET)
1753 struct sockaddr_in* s4 = (struct sockaddr_in*)(ifa->ifa_addr);
1754 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s4->sin_addr), pszIP, sizeof(pszIP)) != NULL)
1755 printf("ipv4 %s: %s\n", ifa->ifa_name, pszIP);
1757 // Take the first IP that isn't loopback 127.x.x.x
1758 CAddress addr(CService(s4->sin_addr, GetListenPort()), nLocalServices);
1759 if (addr.IsValid() && !addr.IsLocal())
1761 addrLocalHost = addr;
1765 else if (ifa->ifa_addr->sa_family == AF_INET6)
1767 struct sockaddr_in6* s6 = (struct sockaddr_in6*)(ifa->ifa_addr);
1768 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s6->sin6_addr), pszIP, sizeof(pszIP)) != NULL)
1769 printf("ipv6 %s: %s\n", ifa->ifa_name, pszIP);
1772 freeifaddrs(myaddrs);
1775 printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1777 if (fUseProxy || mapArgs.count("-connect") || fNoListen)
1779 // Proxies can't take incoming connections
1780 addrLocalHost.SetIP(CNetAddr("0.0.0.0"));
1781 printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1785 CreateThread(ThreadGetMyExternalIP, NULL);
1792 if (!GetBoolArg("-dnsseed", true))
1793 printf("DNS seeding disabled\n");
1795 if (!CreateThread(ThreadDNSAddressSeed, NULL))
1796 printf("Error: CreateThread(ThreadDNSAddressSeed) failed\n");
1798 // Map ports with UPnP
1802 // Get addresses from IRC and advertise ours
1803 if (!CreateThread(ThreadIRCSeed, NULL))
1804 printf("Error: CreateThread(ThreadIRCSeed) failed\n");
1806 // Send and receive from sockets, accept connections
1807 if (!CreateThread(ThreadSocketHandler, NULL))
1808 printf("Error: CreateThread(ThreadSocketHandler) failed\n");
1810 // Initiate outbound connections from -addnode
1811 if (!CreateThread(ThreadOpenAddedConnections, NULL))
1812 printf("Error: CreateThread(ThreadOpenAddedConnections) failed\n");
1814 // Initiate outbound connections
1815 if (!CreateThread(ThreadOpenConnections, NULL))
1816 printf("Error: CreateThread(ThreadOpenConnections) failed\n");
1819 if (!CreateThread(ThreadMessageHandler, NULL))
1820 printf("Error: CreateThread(ThreadMessageHandler) failed\n");
1822 // Generate coins in the background
1823 GenerateBitcoins(GetBoolArg("-gen", false), pwalletMain);
1828 printf("StopNode()\n");
1830 nTransactionsUpdated++;
1831 int64 nStart = GetTime();
1834 int nThreadsRunning = 0;
1835 for (int n = 0; n < THREAD_MAX; n++)
1836 nThreadsRunning += vnThreadsRunning[n];
1837 if (nThreadsRunning == 0)
1839 if (GetTime() - nStart > 20)
1843 if (vnThreadsRunning[THREAD_SOCKETHANDLER] > 0) printf("ThreadSocketHandler still running\n");
1844 if (vnThreadsRunning[THREAD_OPENCONNECTIONS] > 0) printf("ThreadOpenConnections still running\n");
1845 if (vnThreadsRunning[THREAD_MESSAGEHANDLER] > 0) printf("ThreadMessageHandler still running\n");
1846 if (vnThreadsRunning[THREAD_MINER] > 0) printf("ThreadBitcoinMiner still running\n");
1847 if (vnThreadsRunning[THREAD_RPCSERVER] > 0) printf("ThreadRPCServer still running\n");
1848 if (fHaveUPnP && vnThreadsRunning[THREAD_UPNP] > 0) printf("ThreadMapPort still running\n");
1849 if (vnThreadsRunning[THREAD_DNSSEED] > 0) printf("ThreadDNSAddressSeed still running\n");
1850 if (vnThreadsRunning[THREAD_ADDEDCONNECTIONS] > 0) printf("ThreadOpenAddedConnections still running\n");
1851 while (vnThreadsRunning[THREAD_MESSAGEHANDLER] > 0 || vnThreadsRunning[THREAD_RPCSERVER] > 0)
1867 BOOST_FOREACH(CNode* pnode, vNodes)
1868 if (pnode->hSocket != INVALID_SOCKET)
1869 closesocket(pnode->hSocket);
1870 if (hListenSocket != INVALID_SOCKET)
1871 if (closesocket(hListenSocket) == SOCKET_ERROR)
1872 printf("closesocket(hListenSocket) failed with error %d\n", WSAGetLastError());
1875 // Shutdown Windows Sockets
1880 instance_of_cnetcleanup;