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.
19 #include <miniupnpc/miniwget.h>
20 #include <miniupnpc/miniupnpc.h>
21 #include <miniupnpc/upnpcommands.h>
22 #include <miniupnpc/upnperrors.h>
26 using namespace boost;
28 static const int MAX_OUTBOUND_CONNECTIONS = 8;
30 void ThreadMessageHandler2(void* parg);
31 void ThreadSocketHandler2(void* parg);
32 void ThreadOpenConnections2(void* parg);
33 void ThreadOpenAddedConnections2(void* parg);
35 void ThreadMapPort2(void* parg);
37 void ThreadDNSAddressSeed2(void* parg);
38 bool OpenNetworkConnection(const CAddress& addrConnect);
43 // Global state variables
46 bool fAllowDNS = 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;
55 vector<CNode*> vNodes;
56 CCriticalSection cs_vNodes;
57 map<CInv, CDataStream> mapRelay;
58 deque<pair<int64, CInv> > vRelayExpiration;
59 CCriticalSection cs_mapRelay;
60 map<CInv, int64> mapAlreadyAskedFor;
63 set<CNetAddr> setservAddNodeAddresses;
64 CCriticalSection cs_setservAddNodeAddresses;
68 unsigned short GetListenPort()
70 return (unsigned short)(GetArg("-port", GetDefaultPort()));
73 void CNode::PushGetBlocks(CBlockIndex* pindexBegin, uint256 hashEnd)
75 // Filter out duplicate requests
76 if (pindexBegin == pindexLastGetBlocksBegin && hashEnd == hashLastGetBlocksEnd)
78 pindexLastGetBlocksBegin = pindexBegin;
79 hashLastGetBlocksEnd = hashEnd;
81 PushMessage("getblocks", CBlockLocator(pindexBegin), hashEnd);
86 bool RecvLine(SOCKET hSocket, string& strLine)
92 int nBytes = recv(hSocket, &c, 1, 0);
100 if (strLine.size() >= 9000)
103 else if (nBytes <= 0)
109 int nErr = WSAGetLastError();
110 if (nErr == WSAEMSGSIZE)
112 if (nErr == WSAEWOULDBLOCK || nErr == WSAEINTR || nErr == WSAEINPROGRESS)
118 if (!strLine.empty())
123 printf("socket closed\n");
129 int nErr = WSAGetLastError();
130 printf("recv failed: %d\n", nErr);
139 bool GetMyExternalIP2(const CService& addrConnect, const char* pszGet, const char* pszKeyword, CNetAddr& ipRet)
142 if (!ConnectSocket(addrConnect, hSocket))
143 return error("GetMyExternalIP() : connection to %s failed", addrConnect.ToString().c_str());
145 send(hSocket, pszGet, strlen(pszGet), MSG_NOSIGNAL);
148 while (RecvLine(hSocket, strLine))
150 if (strLine.empty()) // HTTP response is separated from headers by blank line
154 if (!RecvLine(hSocket, strLine))
156 closesocket(hSocket);
159 if (pszKeyword == NULL)
161 if (strLine.find(pszKeyword) != -1)
163 strLine = strLine.substr(strLine.find(pszKeyword) + strlen(pszKeyword));
167 closesocket(hSocket);
168 if (strLine.find("<") != -1)
169 strLine = strLine.substr(0, strLine.find("<"));
170 strLine = strLine.substr(strspn(strLine.c_str(), " \t\n\r"));
171 while (strLine.size() > 0 && isspace(strLine[strLine.size()-1]))
172 strLine.resize(strLine.size()-1);
173 CService addr(strLine,0,true);
174 printf("GetMyExternalIP() received [%s] %s\n", strLine.c_str(), addr.ToString().c_str());
175 if (!addr.IsValid() || !addr.IsRoutable())
181 closesocket(hSocket);
182 return error("GetMyExternalIP() : connection closed");
185 // We now get our external IP from the IRC server first and only use this as a backup
186 bool GetMyExternalIP(CNetAddr& ipRet)
188 CService addrConnect;
190 const char* pszKeyword;
192 if (fNoListen||fUseProxy)
195 for (int nLookup = 0; nLookup <= 1; nLookup++)
196 for (int nHost = 1; nHost <= 2; nHost++)
198 // We should be phasing out our use of sites like these. If we need
199 // replacements, we should ask for volunteers to put this simple
200 // php file on their webserver that prints the client IP:
201 // <?php echo $_SERVER["REMOTE_ADDR"]; ?>
204 addrConnect = CService("91.198.22.70",80); // checkip.dyndns.org
208 CService addrIP("checkip.dyndns.org", 80, true);
209 if (addrIP.IsValid())
210 addrConnect = addrIP;
213 pszGet = "GET / HTTP/1.1\r\n"
214 "Host: checkip.dyndns.org\r\n"
215 "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
216 "Connection: close\r\n"
219 pszKeyword = "Address:";
223 addrConnect = CService("74.208.43.192", 80); // www.showmyip.com
227 CService addrIP("www.showmyip.com", 80, true);
228 if (addrIP.IsValid())
229 addrConnect = addrIP;
232 pszGet = "GET /simple/ HTTP/1.1\r\n"
233 "Host: www.showmyip.com\r\n"
234 "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
235 "Connection: close\r\n"
238 pszKeyword = NULL; // Returns just IP address
241 if (GetMyExternalIP2(addrConnect, pszGet, pszKeyword, ipRet))
248 void ThreadGetMyExternalIP(void* parg)
250 // Wait for IRC to get it first
251 if (GetBoolArg("-irc", false))
253 for (int i = 0; i < 2 * 60; i++)
256 if (fGotExternalIP || fShutdown)
261 // Fallback in case IRC fails to get it
262 if (GetMyExternalIP(addrLocalHost))
264 printf("GetMyExternalIP() returned %s\n", addrLocalHost.ToStringIP().c_str());
265 if (addrLocalHost.IsRoutable())
267 // If we already connected to a few before we had our IP, go back and addr them.
268 // setAddrKnown automatically filters any duplicate sends.
269 CAddress addr(addrLocalHost);
270 addr.nTime = GetAdjustedTime();
271 CRITICAL_BLOCK(cs_vNodes)
272 BOOST_FOREACH(CNode* pnode, vNodes)
273 pnode->PushAddress(addr);
282 void AddressCurrentlyConnected(const CService& addr)
284 addrman.Connected(addr);
291 void AbandonRequests(void (*fn)(void*, CDataStream&), void* param1)
293 // If the dialog might get closed before the reply comes back,
294 // call this in the destructor so it doesn't get called after it's deleted.
295 CRITICAL_BLOCK(cs_vNodes)
297 BOOST_FOREACH(CNode* pnode, vNodes)
299 CRITICAL_BLOCK(pnode->cs_mapRequests)
301 for (map<uint256, CRequestTracker>::iterator mi = pnode->mapRequests.begin(); mi != pnode->mapRequests.end();)
303 CRequestTracker& tracker = (*mi).second;
304 if (tracker.fn == fn && tracker.param1 == param1)
305 pnode->mapRequests.erase(mi++);
321 // Subscription methods for the broadcast and subscription system.
322 // Channel numbers are message numbers, i.e. MSG_TABLE and MSG_PRODUCT.
324 // The subscription system uses a meet-in-the-middle strategy.
325 // With 100,000 nodes, if senders broadcast to 1000 random nodes and receivers
326 // subscribe to 1000 random nodes, 99.995% (1 - 0.99^1000) of messages will get through.
329 bool AnySubscribed(unsigned int nChannel)
331 if (pnodeLocalHost->IsSubscribed(nChannel))
333 CRITICAL_BLOCK(cs_vNodes)
334 BOOST_FOREACH(CNode* pnode, vNodes)
335 if (pnode->IsSubscribed(nChannel))
340 bool CNode::IsSubscribed(unsigned int nChannel)
342 if (nChannel >= vfSubscribe.size())
344 return vfSubscribe[nChannel];
347 void CNode::Subscribe(unsigned int nChannel, unsigned int nHops)
349 if (nChannel >= vfSubscribe.size())
352 if (!AnySubscribed(nChannel))
355 CRITICAL_BLOCK(cs_vNodes)
356 BOOST_FOREACH(CNode* pnode, vNodes)
358 pnode->PushMessage("subscribe", nChannel, nHops);
361 vfSubscribe[nChannel] = true;
364 void CNode::CancelSubscribe(unsigned int nChannel)
366 if (nChannel >= vfSubscribe.size())
369 // Prevent from relaying cancel if wasn't subscribed
370 if (!vfSubscribe[nChannel])
372 vfSubscribe[nChannel] = false;
374 if (!AnySubscribed(nChannel))
376 // Relay subscription cancel
377 CRITICAL_BLOCK(cs_vNodes)
378 BOOST_FOREACH(CNode* pnode, vNodes)
380 pnode->PushMessage("sub-cancel", nChannel);
392 CNode* FindNode(const CNetAddr& ip)
394 CRITICAL_BLOCK(cs_vNodes)
396 BOOST_FOREACH(CNode* pnode, vNodes)
397 if ((CNetAddr)pnode->addr == ip)
403 CNode* FindNode(const CService& addr)
405 CRITICAL_BLOCK(cs_vNodes)
407 BOOST_FOREACH(CNode* pnode, vNodes)
408 if ((CService)pnode->addr == addr)
414 CNode* ConnectNode(CAddress addrConnect, int64 nTimeout)
416 if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost)
419 // Look for an existing connection
420 CNode* pnode = FindNode((CService)addrConnect);
424 pnode->AddRef(nTimeout);
431 printf("trying connection %s lastseen=%.1fhrs\n",
432 addrConnect.ToString().c_str(),
433 (double)(addrConnect.nTime - GetAdjustedTime())/3600.0);
435 addrman.Attempt(addrConnect);
439 if (ConnectSocket(addrConnect, hSocket))
442 printf("connected %s\n", addrConnect.ToString().c_str());
444 // Set to nonblocking
447 if (ioctlsocket(hSocket, FIONBIO, &nOne) == SOCKET_ERROR)
448 printf("ConnectSocket() : ioctlsocket nonblocking setting failed, error %d\n", WSAGetLastError());
450 if (fcntl(hSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
451 printf("ConnectSocket() : fcntl nonblocking setting failed, error %d\n", errno);
455 CNode* pnode = new CNode(hSocket, addrConnect, false);
457 pnode->AddRef(nTimeout);
460 CRITICAL_BLOCK(cs_vNodes)
461 vNodes.push_back(pnode);
463 pnode->nTimeConnected = GetTime();
472 void CNode::CloseSocketDisconnect()
475 if (hSocket != INVALID_SOCKET)
478 printf("%s ", DateTimeStrFormat("%x %H:%M:%S", GetTime()).c_str());
479 printf("disconnecting node %s\n", addr.ToString().c_str());
480 closesocket(hSocket);
481 hSocket = INVALID_SOCKET;
485 void CNode::Cleanup()
487 // All of a nodes broadcasts and subscriptions are automatically torn down
488 // when it goes down, so a node has to stay up to keep its broadcast going.
490 // Cancel subscriptions
491 for (unsigned int nChannel = 0; nChannel < vfSubscribe.size(); nChannel++)
492 if (vfSubscribe[nChannel])
493 CancelSubscribe(nChannel);
497 void CNode::PushVersion()
499 /// when NTP implemented, change to just nTime = GetAdjustedTime()
500 int64 nTime = (fInbound ? GetAdjustedTime() : GetTime());
501 CAddress addrYou = (fUseProxy ? CAddress(CService("0.0.0.0",0)) : addr);
502 CAddress addrMe = (fUseProxy || !addrLocalHost.IsRoutable() ? CAddress(CService("0.0.0.0",0)) : addrLocalHost);
503 RAND_bytes((unsigned char*)&nLocalHostNonce, sizeof(nLocalHostNonce));
504 PushMessage("version", PROTOCOL_VERSION, nLocalServices, nTime, addrYou, addrMe,
505 nLocalHostNonce, FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<string>()), nBestHeight);
512 std::map<CNetAddr, int64> CNode::setBanned;
513 CCriticalSection CNode::cs_setBanned;
515 void CNode::ClearBanned()
520 bool CNode::IsBanned(CNetAddr ip)
522 bool fResult = false;
523 CRITICAL_BLOCK(cs_setBanned)
525 std::map<CNetAddr, int64>::iterator i = setBanned.find(ip);
526 if (i != setBanned.end())
528 int64 t = (*i).second;
536 bool CNode::Misbehaving(int howmuch)
540 printf("Warning: local node %s misbehaving\n", addr.ToString().c_str());
544 nMisbehavior += howmuch;
545 if (nMisbehavior >= GetArg("-banscore", 100))
547 int64 banTime = GetTime()+GetArg("-bantime", 60*60*24); // Default 24-hour ban
548 CRITICAL_BLOCK(cs_setBanned)
549 if (setBanned[addr] < banTime)
550 setBanned[addr] = banTime;
551 CloseSocketDisconnect();
552 printf("Disconnected %s for misbehavior (score=%d)\n", addr.ToString().c_str(), nMisbehavior);
569 void ThreadSocketHandler(void* parg)
571 IMPLEMENT_RANDOMIZE_STACK(ThreadSocketHandler(parg));
574 vnThreadsRunning[THREAD_SOCKETHANDLER]++;
575 ThreadSocketHandler2(parg);
576 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
578 catch (std::exception& e) {
579 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
580 PrintException(&e, "ThreadSocketHandler()");
582 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
583 throw; // support pthread_cancel()
585 printf("ThreadSocketHandler exiting\n");
588 void ThreadSocketHandler2(void* parg)
590 printf("ThreadSocketHandler started\n");
591 list<CNode*> vNodesDisconnected;
592 int nPrevNodeCount = 0;
599 CRITICAL_BLOCK(cs_vNodes)
601 // Disconnect unused nodes
602 vector<CNode*> vNodesCopy = vNodes;
603 BOOST_FOREACH(CNode* pnode, vNodesCopy)
605 if (pnode->fDisconnect ||
606 (pnode->GetRefCount() <= 0 && pnode->vRecv.empty() && pnode->vSend.empty()))
608 // remove from vNodes
609 vNodes.erase(remove(vNodes.begin(), vNodes.end(), pnode), vNodes.end());
611 // close socket and cleanup
612 pnode->CloseSocketDisconnect();
615 // hold in disconnected pool until all refs are released
616 pnode->nReleaseTime = max(pnode->nReleaseTime, GetTime() + 15 * 60);
617 if (pnode->fNetworkNode || pnode->fInbound)
619 vNodesDisconnected.push_back(pnode);
623 // Delete disconnected nodes
624 list<CNode*> vNodesDisconnectedCopy = vNodesDisconnected;
625 BOOST_FOREACH(CNode* pnode, vNodesDisconnectedCopy)
627 // wait until threads are done using it
628 if (pnode->GetRefCount() <= 0)
630 bool fDelete = false;
631 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
632 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
633 TRY_CRITICAL_BLOCK(pnode->cs_mapRequests)
634 TRY_CRITICAL_BLOCK(pnode->cs_inventory)
638 vNodesDisconnected.remove(pnode);
644 if (vNodes.size() != nPrevNodeCount)
646 nPrevNodeCount = vNodes.size();
652 // Find which sockets have data to receive
654 struct timeval timeout;
656 timeout.tv_usec = 50000; // frequency to poll pnode->vSend
663 FD_ZERO(&fdsetError);
664 SOCKET hSocketMax = 0;
666 if(hListenSocket != INVALID_SOCKET)
667 FD_SET(hListenSocket, &fdsetRecv);
668 hSocketMax = max(hSocketMax, hListenSocket);
669 CRITICAL_BLOCK(cs_vNodes)
671 BOOST_FOREACH(CNode* pnode, vNodes)
673 if (pnode->hSocket == INVALID_SOCKET)
675 FD_SET(pnode->hSocket, &fdsetRecv);
676 FD_SET(pnode->hSocket, &fdsetError);
677 hSocketMax = max(hSocketMax, pnode->hSocket);
678 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
679 if (!pnode->vSend.empty())
680 FD_SET(pnode->hSocket, &fdsetSend);
684 vnThreadsRunning[THREAD_SOCKETHANDLER]--;
685 int nSelect = select(hSocketMax + 1, &fdsetRecv, &fdsetSend, &fdsetError, &timeout);
686 vnThreadsRunning[THREAD_SOCKETHANDLER]++;
689 if (nSelect == SOCKET_ERROR)
691 int nErr = WSAGetLastError();
694 printf("socket select error %d\n", nErr);
695 for (int i = 0; i <= hSocketMax; i++)
696 FD_SET(i, &fdsetRecv);
699 FD_ZERO(&fdsetError);
700 Sleep(timeout.tv_usec/1000);
705 // Accept new connections
707 if (hListenSocket != INVALID_SOCKET && FD_ISSET(hListenSocket, &fdsetRecv))
709 struct sockaddr_in sockaddr;
710 socklen_t len = sizeof(sockaddr);
711 SOCKET hSocket = accept(hListenSocket, (struct sockaddr*)&sockaddr, &len);
715 if (hSocket != INVALID_SOCKET)
716 addr = CAddress(sockaddr);
718 CRITICAL_BLOCK(cs_vNodes)
719 BOOST_FOREACH(CNode* pnode, vNodes)
723 if (hSocket == INVALID_SOCKET)
725 if (WSAGetLastError() != WSAEWOULDBLOCK)
726 printf("socket error accept failed: %d\n", WSAGetLastError());
728 else if (nInbound >= GetArg("-maxconnections", 125) - MAX_OUTBOUND_CONNECTIONS)
730 CRITICAL_BLOCK(cs_setservAddNodeAddresses)
731 if (!setservAddNodeAddresses.count(addr))
732 closesocket(hSocket);
734 else if (CNode::IsBanned(addr))
736 printf("connetion from %s dropped (banned)\n", addr.ToString().c_str());
737 closesocket(hSocket);
741 printf("accepted connection %s\n", addr.ToString().c_str());
742 CNode* pnode = new CNode(hSocket, addr, true);
744 CRITICAL_BLOCK(cs_vNodes)
745 vNodes.push_back(pnode);
751 // Service each socket
753 vector<CNode*> vNodesCopy;
754 CRITICAL_BLOCK(cs_vNodes)
757 BOOST_FOREACH(CNode* pnode, vNodesCopy)
760 BOOST_FOREACH(CNode* pnode, vNodesCopy)
768 if (pnode->hSocket == INVALID_SOCKET)
770 if (FD_ISSET(pnode->hSocket, &fdsetRecv) || FD_ISSET(pnode->hSocket, &fdsetError))
772 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
774 CDataStream& vRecv = pnode->vRecv;
775 unsigned int nPos = vRecv.size();
777 if (nPos > ReceiveBufferSize()) {
778 if (!pnode->fDisconnect)
779 printf("socket recv flood control disconnect (%d bytes)\n", vRecv.size());
780 pnode->CloseSocketDisconnect();
783 // typical socket buffer is 8K-64K
784 char pchBuf[0x10000];
785 int nBytes = recv(pnode->hSocket, pchBuf, sizeof(pchBuf), MSG_DONTWAIT);
788 vRecv.resize(nPos + nBytes);
789 memcpy(&vRecv[nPos], pchBuf, nBytes);
790 pnode->nLastRecv = GetTime();
792 else if (nBytes == 0)
794 // socket closed gracefully
795 if (!pnode->fDisconnect)
796 printf("socket closed\n");
797 pnode->CloseSocketDisconnect();
802 int nErr = WSAGetLastError();
803 if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
805 if (!pnode->fDisconnect)
806 printf("socket recv error %d\n", nErr);
807 pnode->CloseSocketDisconnect();
817 if (pnode->hSocket == INVALID_SOCKET)
819 if (FD_ISSET(pnode->hSocket, &fdsetSend))
821 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
823 CDataStream& vSend = pnode->vSend;
826 int nBytes = send(pnode->hSocket, &vSend[0], vSend.size(), MSG_NOSIGNAL | MSG_DONTWAIT);
829 vSend.erase(vSend.begin(), vSend.begin() + nBytes);
830 pnode->nLastSend = GetTime();
835 int nErr = WSAGetLastError();
836 if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
838 printf("socket send error %d\n", nErr);
839 pnode->CloseSocketDisconnect();
842 if (vSend.size() > SendBufferSize()) {
843 if (!pnode->fDisconnect)
844 printf("socket send flood control disconnect (%d bytes)\n", vSend.size());
845 pnode->CloseSocketDisconnect();
852 // Inactivity checking
854 if (pnode->vSend.empty())
855 pnode->nLastSendEmpty = GetTime();
856 if (GetTime() - pnode->nTimeConnected > 60)
858 if (pnode->nLastRecv == 0 || pnode->nLastSend == 0)
860 printf("socket no message in first 60 seconds, %d %d\n", pnode->nLastRecv != 0, pnode->nLastSend != 0);
861 pnode->fDisconnect = true;
863 else if (GetTime() - pnode->nLastSend > 90*60 && GetTime() - pnode->nLastSendEmpty > 90*60)
865 printf("socket not sending\n");
866 pnode->fDisconnect = true;
868 else if (GetTime() - pnode->nLastRecv > 90*60)
870 printf("socket inactivity timeout\n");
871 pnode->fDisconnect = true;
875 CRITICAL_BLOCK(cs_vNodes)
877 BOOST_FOREACH(CNode* pnode, vNodesCopy)
894 void ThreadMapPort(void* parg)
896 IMPLEMENT_RANDOMIZE_STACK(ThreadMapPort(parg));
899 vnThreadsRunning[THREAD_UPNP]++;
900 ThreadMapPort2(parg);
901 vnThreadsRunning[THREAD_UPNP]--;
903 catch (std::exception& e) {
904 vnThreadsRunning[THREAD_UPNP]--;
905 PrintException(&e, "ThreadMapPort()");
907 vnThreadsRunning[THREAD_UPNP]--;
908 PrintException(NULL, "ThreadMapPort()");
910 printf("ThreadMapPort exiting\n");
913 void ThreadMapPort2(void* parg)
915 printf("ThreadMapPort started\n");
918 sprintf(port, "%d", GetListenPort());
920 const char * multicastif = 0;
921 const char * minissdpdpath = 0;
922 struct UPNPDev * devlist = 0;
925 #ifndef UPNPDISCOVER_SUCCESS
927 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0);
931 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0, 0, &error);
934 struct UPNPUrls urls;
935 struct IGDdatas data;
938 r = UPNP_GetValidIGD(devlist, &urls, &data, lanaddr, sizeof(lanaddr));
941 if (!addrLocalHost.IsRoutable())
943 char externalIPAddress[40];
944 r = UPNP_GetExternalIPAddress(urls.controlURL, data.first.servicetype, externalIPAddress);
945 if(r != UPNPCOMMAND_SUCCESS)
946 printf("UPnP: GetExternalIPAddress() returned %d\n", r);
949 if(externalIPAddress[0])
951 printf("UPnP: ExternalIPAddress = %s\n", externalIPAddress);
952 CAddress addrExternalFromUPnP(CService(externalIPAddress, 0), nLocalServices);
953 if (addrExternalFromUPnP.IsRoutable())
954 addrLocalHost = addrExternalFromUPnP;
957 printf("UPnP: GetExternalIPAddress failed.\n");
961 string strDesc = "Bitcoin " + FormatFullVersion();
962 #ifndef UPNPDISCOVER_SUCCESS
964 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
965 port, port, lanaddr, strDesc.c_str(), "TCP", 0);
968 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
969 port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
972 if(r!=UPNPCOMMAND_SUCCESS)
973 printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
974 port, port, lanaddr, r, strupnperror(r));
976 printf("UPnP Port Mapping successful.\n");
979 if (fShutdown || !fUseUPnP)
981 r = UPNP_DeletePortMapping(urls.controlURL, data.first.servicetype, port, "TCP", 0);
982 printf("UPNP_DeletePortMapping() returned : %d\n", r);
983 freeUPNPDevlist(devlist); devlist = 0;
987 if (i % 600 == 0) // Refresh every 20 minutes
989 #ifndef UPNPDISCOVER_SUCCESS
991 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
992 port, port, lanaddr, strDesc.c_str(), "TCP", 0);
995 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
996 port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
999 if(r!=UPNPCOMMAND_SUCCESS)
1000 printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
1001 port, port, lanaddr, r, strupnperror(r));
1003 printf("UPnP Port Mapping successful.\n");;
1009 printf("No valid UPnP IGDs found\n");
1010 freeUPNPDevlist(devlist); devlist = 0;
1012 FreeUPNPUrls(&urls);
1014 if (fShutdown || !fUseUPnP)
1021 void MapPort(bool fMapPort)
1023 if (fUseUPnP != fMapPort)
1025 fUseUPnP = fMapPort;
1026 WriteSetting("fUseUPnP", fUseUPnP);
1028 if (fUseUPnP && vnThreadsRunning[THREAD_UPNP] < 1)
1030 if (!CreateThread(ThreadMapPort, NULL))
1031 printf("Error: ThreadMapPort(ThreadMapPort) failed\n");
1035 void MapPort(bool /* unused fMapPort */)
1037 // Intentionally left blank.
1050 // Each pair gives a source name and a seed name.
1051 // The first name is used as information source for addrman.
1052 // The second name should resolve to a list of seed addresses.
1053 static const char *strDNSSeed[][2] = {
1054 {"xf2.org", "bitseed.xf2.org"},
1055 {"bluematt.me", "dnsseed.bluematt.me"},
1056 {"bitcoin.sipa.be", "seed.bitcoin.sipa.be"},
1057 {"dashjr.org", "dnsseed.bitcoin.dashjr.org"},
1060 void ThreadDNSAddressSeed(void* parg)
1062 IMPLEMENT_RANDOMIZE_STACK(ThreadDNSAddressSeed(parg));
1065 vnThreadsRunning[THREAD_DNSSEED]++;
1066 ThreadDNSAddressSeed2(parg);
1067 vnThreadsRunning[THREAD_DNSSEED]--;
1069 catch (std::exception& e) {
1070 vnThreadsRunning[THREAD_DNSSEED]--;
1071 PrintException(&e, "ThreadDNSAddressSeed()");
1073 vnThreadsRunning[THREAD_DNSSEED]--;
1074 throw; // support pthread_cancel()
1076 printf("ThreadDNSAddressSeed exiting\n");
1079 void ThreadDNSAddressSeed2(void* parg)
1081 printf("ThreadDNSAddressSeed started\n");
1086 printf("Loading addresses from DNS seeds (could take a while)\n");
1088 for (int seed_idx = 0; seed_idx < ARRAYLEN(strDNSSeed); seed_idx++) {
1089 vector<CNetAddr> vaddr;
1090 vector<CAddress> vAdd;
1091 if (LookupHost(strDNSSeed[seed_idx][1], vaddr))
1093 BOOST_FOREACH(CNetAddr& ip, vaddr)
1095 CAddress addr = CAddress(CService(ip, GetDefaultPort()));
1097 vAdd.push_back(addr);
1101 addrman.Add(vAdd, CNetAddr(strDNSSeed[seed_idx][0], true));
1105 printf("%d addresses found from DNS seeds\n", found);
1119 unsigned int pnSeed[] =
1121 0x959bd347, 0xf8de42b2, 0x73bc0518, 0xea6edc50, 0x21b00a4d, 0xc725b43d, 0xd665464d, 0x1a2a770e,
1122 0x27c93946, 0x65b2fa46, 0xb80ae255, 0x66b3b446, 0xb1877a3e, 0x6ee89e3e, 0xc3175b40, 0x2a01a83c,
1123 0x95b1363a, 0xa079ad3d, 0xe6ca801f, 0x027f4f4a, 0x34f7f03a, 0xf790f04a, 0x16ca801f, 0x2f4d5e40,
1124 0x3a4d5e40, 0xc43a322e, 0xc8159753, 0x14d4724c, 0x7919a118, 0xe0bdb34e, 0x68a16b2e, 0xff64b44d,
1125 0x6099115b, 0x9b57b05b, 0x7bd1b4ad, 0xdf95944f, 0x29d2b73d, 0xafa8db79, 0xe247ba41, 0x24078348,
1126 0xf722f03c, 0x33567ebc, 0xace64ed4, 0x984d3932, 0xb5f34e55, 0x27b7024d, 0x94579247, 0x8894042e,
1127 0x9357d34c, 0x1063c24b, 0xcaa228b1, 0xa3c5a8b2, 0x5dc64857, 0xa2c23643, 0xa8369a54, 0x31203077,
1128 0x00707c5c, 0x09fc0b3a, 0x272e9e2e, 0xf80f043e, 0x9449ca3e, 0x5512c33e, 0xd106b555, 0xe8024157,
1129 0xe288ec29, 0xc79c5461, 0xafb63932, 0xdb02ab4b, 0x0e512777, 0x8a145a4c, 0xb201ff4f, 0x5e09314b,
1130 0xcd9bfbcd, 0x1c023765, 0x4394e75c, 0xa728bd4d, 0x65331552, 0xa98420b1, 0x89ecf559, 0x6e80801f,
1131 0xf404f118, 0xefd62b51, 0x05918346, 0x9b186d5f, 0xacabab46, 0xf912e255, 0xc188ea62, 0xcc55734e,
1132 0xc668064d, 0xd77a4558, 0x46201c55, 0xf17dfc80, 0xf7142f2e, 0x87bfb718, 0x8aa54fb2, 0xc451d518,
1133 0xc4ae8831, 0x8dd44d55, 0x5bbd206c, 0x64536b5d, 0x5c667e60, 0x3b064242, 0xfe963a42, 0xa28e6dc8,
1134 0xe8a9604a, 0xc989464e, 0xd124a659, 0x50065140, 0xa44dfe5e, 0x1079e655, 0x3fb986d5, 0x47895b18,
1135 0x7d3ce4ad, 0x4561ba50, 0x296eec62, 0x255b41ad, 0xaed35ec9, 0x55556f12, 0xc7d3154d, 0x3297b65d,
1136 0x8930121f, 0xabf42e4e, 0x4a29e044, 0x1212685d, 0x676c1e40, 0xce009744, 0x383a8948, 0xa2dbd0ad,
1137 0xecc2564d, 0x07dbc252, 0x887ee24b, 0x5171644c, 0x6bb798c1, 0x847f495d, 0x4cbb7145, 0x3bb81c32,
1138 0x45eb262e, 0xc8015a4e, 0x250a361b, 0xf694f946, 0xd64a183e, 0xd4f1dd59, 0x8f20ffd4, 0x51d9e55c,
1139 0x09521763, 0x5e02002e, 0x32c8074d, 0xe685762e, 0x8290b0bc, 0x762a922e, 0xfc5ee754, 0x83a24829,
1140 0x775b224d, 0x6295bb4d, 0x38ec0555, 0xbffbba50, 0xe5560260, 0x86b16a7c, 0xd372234e, 0x49a3c24b,
1141 0x2f6a171f, 0x4d75ed60, 0xae94115b, 0xcb543744, 0x63080c59, 0x3f9c724c, 0xc977ce18, 0x532efb18,
1142 0x69dc3b2e, 0x5f94d929, 0x1732bb4d, 0x9c814b4d, 0xe6b3762e, 0xc024f662, 0x8face35b, 0x6b5b044d,
1143 0x798c7b57, 0x79a6b44c, 0x067d3057, 0xf9e94e5f, 0x91cbe15b, 0x71405eb2, 0x2662234e, 0xcbcc4a6d,
1144 0xbf69d54b, 0xa79b4e55, 0xec6d3e51, 0x7c0b3c02, 0x60f83653, 0x24c1e15c, 0x1110b62e, 0x10350f59,
1145 0xa56f1d55, 0x3509e7a9, 0xeb128354, 0x14268e2e, 0x934e28bc, 0x8e32692e, 0x8331a21f, 0x3e633932,
1146 0xc812b12e, 0xc684bf2e, 0x80112d2e, 0xe0ddc96c, 0xc630ca4a, 0x5c09b3b2, 0x0b580518, 0xc8e9d54b,
1147 0xd169aa43, 0x17d0d655, 0x1d029963, 0x7ff87559, 0xcb701f1f, 0x6fa3e85d, 0xe45e9a54, 0xf05d1802,
1148 0x44d03b2e, 0x837b692e, 0xccd4354e, 0x3d6da13c, 0x3423084d, 0xf707c34a, 0x55f6db3a, 0xad26e442,
1149 0x6233a21f, 0x09e80e59, 0x8caeb54d, 0xbe870941, 0xb407d20e, 0x20b51018, 0x56fb152e, 0x460d2a4e,
1150 0xbb9a2946, 0x560eb12e, 0xed83dd29, 0xd6724f53, 0xa50aafb8, 0x451346d9, 0x88348e2e, 0x7312fead,
1151 0x8ecaf96f, 0x1bda4e5f, 0xf1671e40, 0x3c8c3e3b, 0x4716324d, 0xdde24ede, 0xf98cd17d, 0xa91d4644,
1152 0x28124eb2, 0x147d5129, 0xd022042e, 0x61733d3b, 0xad0d5e02, 0x8ce2932e, 0xe5c18502, 0x549c1e32,
1153 0x9685801f, 0x86e217ad, 0xd948214b, 0x4110f462, 0x3a2e894e, 0xbd35492e, 0x87e0d558, 0x64b8ef7d,
1154 0x7c3eb962, 0x72a84b3e, 0x7cd667c9, 0x28370a2e, 0x4bc60e7b, 0x6fc1ec60, 0x14a6983f, 0x86739a4b,
1155 0x46954e5f, 0x32e2e15c, 0x2e9326cf, 0xe5801c5e, 0x379607b2, 0x32151145, 0xf0e39744, 0xacb54c55,
1156 0xa37dfb60, 0x83b55cc9, 0x388f7ca5, 0x15034f5f, 0x3e94965b, 0x68e0ffad, 0x35280f59, 0x8fe190cf,
1157 0x7c6ba5b2, 0xa5e9db43, 0x4ee1fc60, 0xd9d94e5f, 0x04040677, 0x0ea9b35e, 0x5961f14f, 0x67fda063,
1158 0xa48a5a31, 0xc6524e55, 0x283d325e, 0x3f37515f, 0x96b94b3e, 0xacce620e, 0x6481cc5b, 0xa4a06d4b,
1159 0x9e95d2d9, 0xe40c03d5, 0xc2f4514b, 0xb79aad44, 0xf64be843, 0xb2064070, 0xfca00455, 0x429dfa4e,
1160 0x2323f173, 0xeda4185e, 0xabd5227d, 0x9efd4d58, 0xb1104758, 0x4811e955, 0xbd9ab355, 0xe921f44b,
1161 0x9f166dce, 0x09e279b2, 0xe0c9ac7b, 0x7901a5ad, 0xa145d4b0, 0x79104671, 0xec31e35a, 0x4fe0b555,
1162 0xc7d9cbad, 0xad057f55, 0xe94cc759, 0x7fe0b043, 0xe4529f2e, 0x0d4dd4b2, 0x9f11a54d, 0x031e2e4e,
1163 0xe6014f5f, 0x11d1ca6c, 0x26bd7f61, 0xeb86854f, 0x4d347b57, 0x116bbe2e, 0xdba7234e, 0x7bcbfd2e,
1164 0x174dd4b2, 0x6686762e, 0xb089ba50, 0xc6258246, 0x087e767b, 0xc4a8cb4a, 0x595dba50, 0x7f0ae502,
1165 0x7b1dbd5a, 0xa0603492, 0x57d1af4b, 0x9e21ffd4, 0x6393064d, 0x7407376e, 0xe484762e, 0x122a4e53,
1166 0x4a37aa43, 0x3888a6be, 0xee77864e, 0x039c8dd5, 0x688d89af, 0x0e988f62, 0x08218246, 0xfc2f8246,
1167 0xd1d97040, 0xd64cd4b2, 0x5ae4a6b8, 0x7d0de9bc, 0x8d304d61, 0x06c5c672, 0xa4c8bd4d, 0xe0fd373b,
1168 0x575ebe4d, 0x72d26277, 0x55570f55, 0x77b154d9, 0xe214293a, 0xfc740f4b, 0xfe3f6a57, 0xa9c55f02,
1169 0xae4054db, 0x2394d918, 0xb511b24a, 0xb8741ab2, 0x0758e65e, 0xc7b5795b, 0xb0a30a4c, 0xaf7f170c,
1170 0xf3b4762e, 0x8179576d, 0x738a1581, 0x4b95b64c, 0x9829b618, 0x1bea932e, 0x7bdeaa4b, 0xcb5e0281,
1171 0x65618f54, 0x0658474b, 0x27066acf, 0x40556d65, 0x7d204d53, 0xf28bc244, 0xdce23455, 0xadc0ff54,
1172 0x3863c948, 0xcee34e5f, 0xdeb85e02, 0x2ed17a61, 0x6a7b094d, 0x7f0cfc40, 0x59603f54, 0x3220afbc,
1173 0xb5dfd962, 0x125d21c0, 0x13f8d243, 0xacfefb4e, 0x86c2c147, 0x3d8bbd59, 0xbd02a21f, 0x2593042e,
1174 0xc6a17a7c, 0x28925861, 0xb487ed44, 0xb5f4fd6d, 0x90c28a45, 0x5a14f74d, 0x43d71b4c, 0x728ebb5d,
1175 0x885bf950, 0x08134dd0, 0x38ec046e, 0xc575684b, 0x50082d2e, 0xa2f47757, 0x270f86ae, 0xf3ff6462,
1176 0x10ed3f4e, 0x4b58d462, 0xe01ce23e, 0x8c5b092e, 0x63e52f4e, 0x22c1e85d, 0xa908f54e, 0x8591624f,
1177 0x2c0fb94e, 0xa280ba3c, 0xb6f41b4c, 0x24f9aa47, 0x27201647, 0x3a3ea6dc, 0xa14fc3be, 0x3c34bdd5,
1178 0x5b8d4f5b, 0xaadeaf4b, 0xc71cab50, 0x15697a4c, 0x9a1a734c, 0x2a037d81, 0x2590bd59, 0x48ec2741,
1179 0x53489c5b, 0x7f00314b, 0x2170d362, 0xf2e92542, 0x42c10b44, 0x98f0f118, 0x883a3456, 0x099a932e,
1180 0xea38f7bc, 0x644e9247, 0xbb61b62e, 0x30e0863d, 0x5f51be54, 0x207215c7, 0x5f306c45, 0xaa7f3932,
1181 0x98da7d45, 0x4e339b59, 0x2e411581, 0xa808f618, 0xad2c0c59, 0x54476741, 0x09e99fd1, 0x5db8f752,
1182 0xc16df8bd, 0x1dd4b44f, 0x106edf2e, 0x9e15c180, 0x2ad6b56f, 0x633a5332, 0xff33787c, 0x077cb545,
1183 0x6610be6d, 0x75aad2c4, 0x72fb4d5b, 0xe81e0f59, 0x576f6332, 0x47333373, 0x351ed783, 0x2d90fb50,
1184 0x8d5e0f6c, 0x5b27a552, 0xdb293ebb, 0xe55ef950, 0x4b133ad8, 0x75df975a, 0x7b6a8740, 0xa899464b,
1185 0xfab15161, 0x10f8b64d, 0xd055ea4d, 0xee8e146b, 0x4b14afb8, 0x4bc1c44a, 0x9b961dcc, 0xd111ff43,
1186 0xfca0b745, 0xc800e412, 0x0afad9d1, 0xf751c350, 0xf9f0cccf, 0xa290a545, 0x8ef13763, 0x7ec70d59,
1187 0x2b066acf, 0x65496c45, 0xade02c1b, 0xae6eb077, 0x92c1e65b, 0xc064e6a9, 0xc649e56d, 0x5287a243,
1188 0x36de4f5b, 0x5b1df6ad, 0x65c39a59, 0xdba805b2, 0x20067aa8, 0x6457e56d, 0x3cee26cf, 0xfd3ff26d,
1189 0x04f86d4a, 0x06b8e048, 0xa93bcd5c, 0x91135852, 0xbe90a643, 0x8fa0094d, 0x06d8215f, 0x2677094d,
1190 0xd735685c, 0x164a00c9, 0x5209ac5f, 0xa9564c5c, 0x3b504f5f, 0xcc826bd0, 0x4615042e, 0x5fe13b4a,
1191 0x8c81b86d, 0x879ab68c, 0x1de564b8, 0x434487d8, 0x2dcb1b63, 0x82ab524a, 0xb0676abb, 0xa13d9c62,
1192 0xdbb5b86d, 0x5b7f4b59, 0xaddfb44d, 0xad773532, 0x3997054c, 0x72cebd89, 0xb194544c, 0xc5b8046e,
1193 0x6e1adeb2, 0xaa5abb51, 0xefb54b44, 0x15efc54f, 0xe9f1bc4d, 0x5f401b6c, 0x97f018ad, 0xc82f9252,
1194 0x2cdc762e, 0x8e52e56d, 0x1827175e, 0x9b7d7d80, 0xb2ad6845, 0x51065140, 0x71180a18, 0x5b27006c,
1195 0x0621e255, 0x721cbe58, 0x670c0cb8, 0xf8bd715d, 0xe0bdc5d9, 0xed843501, 0x4b84554d, 0x7f1a18bc,
1196 0x53bcaf47, 0x5729d35f, 0xf0dda246, 0x22382bd0, 0x4d641fb0, 0x316afcde, 0x50a22f1f, 0x73608046,
1197 0xc461d84a, 0xb2dbe247,
1200 void DumpAddresses()
1203 adb.WriteAddrman(addrman);
1206 void ThreadDumpAddress2(void* parg)
1208 vnThreadsRunning[THREAD_DUMPADDRESS]++;
1212 vnThreadsRunning[THREAD_DUMPADDRESS]--;
1214 vnThreadsRunning[THREAD_DUMPADDRESS]++;
1216 vnThreadsRunning[THREAD_DUMPADDRESS]--;
1219 void ThreadDumpAddress(void* parg)
1221 IMPLEMENT_RANDOMIZE_STACK(ThreadDumpAddress(parg));
1224 ThreadDumpAddress2(parg);
1226 catch (std::exception& e) {
1227 PrintException(&e, "ThreadDumpAddress()");
1229 printf("ThreadDumpAddress exiting\n");
1232 void ThreadOpenConnections(void* parg)
1234 IMPLEMENT_RANDOMIZE_STACK(ThreadOpenConnections(parg));
1237 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1238 ThreadOpenConnections2(parg);
1239 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1241 catch (std::exception& e) {
1242 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1243 PrintException(&e, "ThreadOpenConnections()");
1245 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1246 PrintException(NULL, "ThreadOpenConnections()");
1248 printf("ThreadOpenConnections exiting\n");
1251 void ThreadOpenConnections2(void* parg)
1253 printf("ThreadOpenConnections started\n");
1255 // Connect to specific addresses
1256 if (mapArgs.count("-connect"))
1258 for (int64 nLoop = 0;; nLoop++)
1260 BOOST_FOREACH(string strAddr, mapMultiArgs["-connect"])
1262 CAddress addr(CService(strAddr, GetDefaultPort(), fAllowDNS));
1264 OpenNetworkConnection(addr);
1265 for (int i = 0; i < 10 && i < nLoop; i++)
1275 // Initiate network connections
1276 int64 nStart = GetTime();
1281 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1283 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1287 // Limit outbound connections
1291 CRITICAL_BLOCK(cs_vNodes)
1292 BOOST_FOREACH(CNode* pnode, vNodes)
1293 if (!pnode->fInbound)
1295 int nMaxOutboundConnections = MAX_OUTBOUND_CONNECTIONS;
1296 nMaxOutboundConnections = min(nMaxOutboundConnections, (int)GetArg("-maxconnections", 125));
1297 if (nOutbound < nMaxOutboundConnections)
1299 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1301 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1306 bool fAddSeeds = false;
1308 // Add seed nodes if IRC isn't working
1309 bool fTOR = (fUseProxy && addrProxy.GetPort() == 9050);
1310 if (addrman.size()==0 && (GetTime() - nStart > 60 || fTOR) && !fTestNet)
1312 std::vector<CAddress> vAdd;
1313 for (int i = 0; i < ARRAYLEN(pnSeed); i++)
1315 // It'll only connect to one or two seed nodes because once it connects,
1316 // it'll get a pile of addresses with newer timestamps.
1317 // Seed nodes are given a random 'last seen time' of between one and two
1319 const int64 nOneWeek = 7*24*60*60;
1321 memcpy(&ip, &pnSeed[i], sizeof(ip));
1322 CAddress addr(CService(ip, GetDefaultPort()));
1323 addr.nTime = GetTime()-GetRand(nOneWeek)-nOneWeek;
1324 vAdd.push_back(addr);
1326 addrman.Add(vAdd, CNetAddr("127.0.0.1"));
1330 // Choose an address to connect to based on most recently seen
1332 CAddress addrConnect;
1333 int64 nBest = std::numeric_limits<int64>::min();
1335 // Only connect to one address per a.b.?.? range.
1336 // Do this here so we don't have to critsect vNodes inside mapAddresses critsect.
1337 set<vector<unsigned char> > setConnected;
1338 CRITICAL_BLOCK(cs_vNodes)
1339 BOOST_FOREACH(CNode* pnode, vNodes)
1340 setConnected.insert(pnode->addr.GetGroup());
1342 int64 nANow = GetAdjustedTime();
1347 // use an nUnkBias between 10 (no outgoing connections) and 90 (8 outgoing connections)
1348 CAddress addr = addrman.Select(10 + min(nOutbound,8)*10);
1350 // if we selected an invalid address, restart
1351 if (!addr.IsIPv4() || !addr.IsValid() || setConnected.count(addr.GetGroup()) || addr == addrLocalHost)
1356 // only consider very recently tried nodes after 30 failed attempts
1357 if (nANow - addr.nLastTry < 600 && nTries < 30)
1360 // do not allow non-default ports, unless after 50 invalid addresses selected already
1361 if (addr.GetPort() != GetDefaultPort() && nTries < 50)
1368 if (addrConnect.IsValid())
1369 OpenNetworkConnection(addrConnect);
1373 void ThreadOpenAddedConnections(void* parg)
1375 IMPLEMENT_RANDOMIZE_STACK(ThreadOpenAddedConnections(parg));
1378 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]++;
1379 ThreadOpenAddedConnections2(parg);
1380 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1382 catch (std::exception& e) {
1383 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1384 PrintException(&e, "ThreadOpenAddedConnections()");
1386 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1387 PrintException(NULL, "ThreadOpenAddedConnections()");
1389 printf("ThreadOpenAddedConnections exiting\n");
1392 void ThreadOpenAddedConnections2(void* parg)
1394 printf("ThreadOpenAddedConnections started\n");
1396 if (mapArgs.count("-addnode") == 0)
1399 vector<vector<CService> > vservAddressesToAdd(0);
1400 BOOST_FOREACH(string& strAddNode, mapMultiArgs["-addnode"])
1402 vector<CService> vservNode(0);
1403 if(Lookup(strAddNode.c_str(), vservNode, GetDefaultPort(), fAllowDNS, 0))
1405 vservAddressesToAdd.push_back(vservNode);
1406 CRITICAL_BLOCK(cs_setservAddNodeAddresses)
1407 BOOST_FOREACH(CService& serv, vservNode)
1408 setservAddNodeAddresses.insert(serv);
1413 vector<vector<CService> > vservConnectAddresses = vservAddressesToAdd;
1414 // Attempt to connect to each IP for each addnode entry until at least one is successful per addnode entry
1415 // (keeping in mind that addnode entries can have many IPs if fAllowDNS)
1416 CRITICAL_BLOCK(cs_vNodes)
1417 BOOST_FOREACH(CNode* pnode, vNodes)
1418 for (vector<vector<CService> >::iterator it = vservConnectAddresses.begin(); it != vservConnectAddresses.end(); it++)
1419 BOOST_FOREACH(CService& addrNode, *(it))
1420 if (pnode->addr == addrNode)
1422 it = vservConnectAddresses.erase(it);
1426 BOOST_FOREACH(vector<CService>& vserv, vservConnectAddresses)
1428 OpenNetworkConnection(CAddress(*(vserv.begin())));
1435 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1436 Sleep(120000); // Retry every 2 minutes
1437 vnThreadsRunning[THREAD_ADDEDCONNECTIONS]++;
1443 bool OpenNetworkConnection(const CAddress& addrConnect)
1446 // Initiate outbound network connection
1450 if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost || !addrConnect.IsIPv4() ||
1451 FindNode((CNetAddr)addrConnect) || CNode::IsBanned(addrConnect))
1454 vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1455 CNode* pnode = ConnectNode(addrConnect);
1456 vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1461 pnode->fNetworkNode = true;
1473 void ThreadMessageHandler(void* parg)
1475 IMPLEMENT_RANDOMIZE_STACK(ThreadMessageHandler(parg));
1478 vnThreadsRunning[THREAD_MESSAGEHANDLER]++;
1479 ThreadMessageHandler2(parg);
1480 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1482 catch (std::exception& e) {
1483 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1484 PrintException(&e, "ThreadMessageHandler()");
1486 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1487 PrintException(NULL, "ThreadMessageHandler()");
1489 printf("ThreadMessageHandler exiting\n");
1492 void ThreadMessageHandler2(void* parg)
1494 printf("ThreadMessageHandler started\n");
1495 SetThreadPriority(THREAD_PRIORITY_BELOW_NORMAL);
1498 vector<CNode*> vNodesCopy;
1499 CRITICAL_BLOCK(cs_vNodes)
1501 vNodesCopy = vNodes;
1502 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1506 // Poll the connected nodes for messages
1507 CNode* pnodeTrickle = NULL;
1508 if (!vNodesCopy.empty())
1509 pnodeTrickle = vNodesCopy[GetRand(vNodesCopy.size())];
1510 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1513 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
1514 ProcessMessages(pnode);
1519 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
1520 SendMessages(pnode, pnode == pnodeTrickle);
1525 CRITICAL_BLOCK(cs_vNodes)
1527 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1531 // Wait and allow messages to bunch up.
1532 // Reduce vnThreadsRunning so StopNode has permission to exit while
1533 // we're sleeping, but we must always check fShutdown after doing this.
1534 vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1536 if (fRequestShutdown)
1538 vnThreadsRunning[THREAD_MESSAGEHANDLER]++;
1549 bool BindListenPort(string& strError)
1553 addrLocalHost.SetPort(GetListenPort());
1556 // Initialize Windows Sockets
1558 int ret = WSAStartup(MAKEWORD(2,2), &wsadata);
1559 if (ret != NO_ERROR)
1561 strError = strprintf("Error: TCP/IP socket library failed to start (WSAStartup returned error %d)", ret);
1562 printf("%s\n", strError.c_str());
1567 // Create socket for listening for incoming connections
1568 hListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
1569 if (hListenSocket == INVALID_SOCKET)
1571 strError = strprintf("Error: Couldn't open socket for incoming connections (socket returned error %d)", WSAGetLastError());
1572 printf("%s\n", strError.c_str());
1577 // Different way of disabling SIGPIPE on BSD
1578 setsockopt(hListenSocket, SOL_SOCKET, SO_NOSIGPIPE, (void*)&nOne, sizeof(int));
1582 // Allow binding if the port is still in TIME_WAIT state after
1583 // the program was closed and restarted. Not an issue on windows.
1584 setsockopt(hListenSocket, SOL_SOCKET, SO_REUSEADDR, (void*)&nOne, sizeof(int));
1588 // Set to nonblocking, incoming connections will also inherit this
1589 if (ioctlsocket(hListenSocket, FIONBIO, (u_long*)&nOne) == SOCKET_ERROR)
1591 if (fcntl(hListenSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
1594 strError = strprintf("Error: Couldn't set properties on socket for incoming connections (error %d)", WSAGetLastError());
1595 printf("%s\n", strError.c_str());
1599 // The sockaddr_in structure specifies the address family,
1600 // IP address, and port for the socket that is being bound
1601 struct sockaddr_in sockaddr;
1602 memset(&sockaddr, 0, sizeof(sockaddr));
1603 sockaddr.sin_family = AF_INET;
1604 sockaddr.sin_addr.s_addr = INADDR_ANY; // bind to all IPs on this computer
1605 sockaddr.sin_port = htons(GetListenPort());
1606 if (::bind(hListenSocket, (struct sockaddr*)&sockaddr, sizeof(sockaddr)) == SOCKET_ERROR)
1608 int nErr = WSAGetLastError();
1609 if (nErr == WSAEADDRINUSE)
1610 strError = strprintf(_("Unable to bind to port %d on this computer. Bitcoin is probably already running."), ntohs(sockaddr.sin_port));
1612 strError = strprintf("Error: Unable to bind to port %d on this computer (bind returned error %d)", ntohs(sockaddr.sin_port), nErr);
1613 printf("%s\n", strError.c_str());
1616 printf("Bound to port %d\n", ntohs(sockaddr.sin_port));
1618 // Listen for incoming connections
1619 if (listen(hListenSocket, SOMAXCONN) == SOCKET_ERROR)
1621 strError = strprintf("Error: Listening for incoming connections failed (listen returned error %d)", WSAGetLastError());
1622 printf("%s\n", strError.c_str());
1629 void StartNode(void* parg)
1631 if (pnodeLocalHost == NULL)
1632 pnodeLocalHost = new CNode(INVALID_SOCKET, CAddress(CService("127.0.0.1", 0), nLocalServices));
1635 // Get local host ip
1636 char pszHostName[1000] = "";
1637 if (gethostname(pszHostName, sizeof(pszHostName)) != SOCKET_ERROR)
1639 vector<CNetAddr> vaddr;
1640 if (LookupHost(pszHostName, vaddr))
1641 BOOST_FOREACH (const CNetAddr &addr, vaddr)
1642 if (!addr.IsLocal())
1644 addrLocalHost.SetIP(addr);
1649 // Get local host ip
1650 struct ifaddrs* myaddrs;
1651 if (getifaddrs(&myaddrs) == 0)
1653 for (struct ifaddrs* ifa = myaddrs; ifa != NULL; ifa = ifa->ifa_next)
1655 if (ifa->ifa_addr == NULL) continue;
1656 if ((ifa->ifa_flags & IFF_UP) == 0) continue;
1657 if (strcmp(ifa->ifa_name, "lo") == 0) continue;
1658 if (strcmp(ifa->ifa_name, "lo0") == 0) continue;
1660 if (ifa->ifa_addr->sa_family == AF_INET)
1662 struct sockaddr_in* s4 = (struct sockaddr_in*)(ifa->ifa_addr);
1663 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s4->sin_addr), pszIP, sizeof(pszIP)) != NULL)
1664 printf("ipv4 %s: %s\n", ifa->ifa_name, pszIP);
1666 // Take the first IP that isn't loopback 127.x.x.x
1667 CAddress addr(CService(s4->sin_addr, GetListenPort()), nLocalServices);
1668 if (addr.IsValid() && !addr.IsLocal())
1670 addrLocalHost = addr;
1674 else if (ifa->ifa_addr->sa_family == AF_INET6)
1676 struct sockaddr_in6* s6 = (struct sockaddr_in6*)(ifa->ifa_addr);
1677 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s6->sin6_addr), pszIP, sizeof(pszIP)) != NULL)
1678 printf("ipv6 %s: %s\n", ifa->ifa_name, pszIP);
1681 freeifaddrs(myaddrs);
1684 printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1686 if (fUseProxy || mapArgs.count("-connect") || fNoListen)
1688 // Proxies can't take incoming connections
1689 addrLocalHost.SetIP(CNetAddr("0.0.0.0"));
1690 printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1694 CreateThread(ThreadGetMyExternalIP, NULL);
1701 if (!GetBoolArg("-dnsseed", true))
1702 printf("DNS seeding disabled\n");
1704 if (!CreateThread(ThreadDNSAddressSeed, NULL))
1705 printf("Error: CreateThread(ThreadDNSAddressSeed) failed\n");
1707 // Map ports with UPnP
1711 // Get addresses from IRC and advertise ours
1712 if (!CreateThread(ThreadIRCSeed, NULL))
1713 printf("Error: CreateThread(ThreadIRCSeed) failed\n");
1715 // Send and receive from sockets, accept connections
1716 if (!CreateThread(ThreadSocketHandler, NULL))
1717 printf("Error: CreateThread(ThreadSocketHandler) failed\n");
1719 // Initiate outbound connections from -addnode
1720 if (!CreateThread(ThreadOpenAddedConnections, NULL))
1721 printf("Error: CreateThread(ThreadOpenAddedConnections) failed\n");
1723 // Initiate outbound connections
1724 if (!CreateThread(ThreadOpenConnections, NULL))
1725 printf("Error: CreateThread(ThreadOpenConnections) failed\n");
1728 if (!CreateThread(ThreadMessageHandler, NULL))
1729 printf("Error: CreateThread(ThreadMessageHandler) failed\n");
1731 // Dump network addresses
1732 if (!CreateThread(ThreadDumpAddress, NULL))
1733 printf("Error; CreateThread(ThreadDumpAddress) failed\n");
1735 // Generate coins in the background
1736 GenerateBitcoins(fGenerateBitcoins, pwalletMain);
1741 printf("StopNode()\n");
1743 nTransactionsUpdated++;
1744 int64 nStart = GetTime();
1747 int nThreadsRunning = 0;
1748 for (int n = 0; n < THREAD_MAX; n++)
1749 nThreadsRunning += vnThreadsRunning[n];
1750 if (nThreadsRunning == 0)
1752 if (GetTime() - nStart > 20)
1756 if (vnThreadsRunning[THREAD_SOCKETHANDLER] > 0) printf("ThreadSocketHandler still running\n");
1757 if (vnThreadsRunning[THREAD_OPENCONNECTIONS] > 0) printf("ThreadOpenConnections still running\n");
1758 if (vnThreadsRunning[THREAD_MESSAGEHANDLER] > 0) printf("ThreadMessageHandler still running\n");
1759 if (vnThreadsRunning[THREAD_MINER] > 0) printf("ThreadBitcoinMiner still running\n");
1760 if (vnThreadsRunning[THREAD_RPCSERVER] > 0) printf("ThreadRPCServer still running\n");
1761 if (fHaveUPnP && vnThreadsRunning[THREAD_UPNP] > 0) printf("ThreadMapPort still running\n");
1762 if (vnThreadsRunning[THREAD_DNSSEED] > 0) printf("ThreadDNSAddressSeed still running\n");
1763 if (vnThreadsRunning[THREAD_ADDEDCONNECTIONS] > 0) printf("ThreadOpenAddedConnections still running\n");
1764 if (vnThreadsRunning[THREAD_DUMPADDRESS] > 0) printf("ThreadDumpAddresses still running\n");
1765 while (vnThreadsRunning[THREAD_MESSAGEHANDLER] > 0 || vnThreadsRunning[THREAD_RPCSERVER] > 0)
1781 BOOST_FOREACH(CNode* pnode, vNodes)
1782 if (pnode->hSocket != INVALID_SOCKET)
1783 closesocket(pnode->hSocket);
1784 if (hListenSocket != INVALID_SOCKET)
1785 if (closesocket(hListenSocket) == SOCKET_ERROR)
1786 printf("closesocket(hListenSocket) failed with error %d\n", WSAGetLastError());
1789 // Shutdown Windows Sockets
1794 instance_of_cnetcleanup;