1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2011 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);
33 void ThreadMapPort2(void* parg);
35 void ThreadDNSAddressSeed2(void* parg);
36 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, 10> 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;
67 unsigned short GetListenPort()
69 return (unsigned short)(GetArg("-port", GetDefaultPort()));
72 void CNode::PushGetBlocks(CBlockIndex* pindexBegin, uint256 hashEnd)
74 // Filter out duplicate requests
75 if (pindexBegin == pindexLastGetBlocksBegin && hashEnd == hashLastGetBlocksEnd)
77 pindexLastGetBlocksBegin = pindexBegin;
78 hashLastGetBlocksEnd = hashEnd;
80 PushMessage("getblocks", CBlockLocator(pindexBegin), hashEnd);
87 bool GetMyExternalIP2(const CService& addrConnect, const char* pszGet, const char* pszKeyword, CNetAddr& ipRet)
90 if (!ConnectSocket(addrConnect, hSocket))
91 return error("GetMyExternalIP() : connection to %s failed", addrConnect.ToString().c_str());
93 send(hSocket, pszGet, strlen(pszGet), MSG_NOSIGNAL);
96 while (RecvLine(hSocket, strLine))
98 if (strLine.empty()) // HTTP response is separated from headers by blank line
102 if (!RecvLine(hSocket, strLine))
104 closesocket(hSocket);
107 if (pszKeyword == NULL)
109 if (strLine.find(pszKeyword) != -1)
111 strLine = strLine.substr(strLine.find(pszKeyword) + strlen(pszKeyword));
115 closesocket(hSocket);
116 if (strLine.find("<") != -1)
117 strLine = strLine.substr(0, strLine.find("<"));
118 strLine = strLine.substr(strspn(strLine.c_str(), " \t\n\r"));
119 while (strLine.size() > 0 && isspace(strLine[strLine.size()-1]))
120 strLine.resize(strLine.size()-1);
121 CService addr(strLine,0,true);
122 printf("GetMyExternalIP() received [%s] %s\n", strLine.c_str(), addr.ToString().c_str());
123 if (!addr.IsValid() || !addr.IsRoutable())
129 closesocket(hSocket);
130 return error("GetMyExternalIP() : connection closed");
133 // We now get our external IP from the IRC server first and only use this as a backup
134 bool GetMyExternalIP(CNetAddr& ipRet)
136 CAddress addrConnect;
138 const char* pszKeyword;
143 for (int nLookup = 0; nLookup <= 1; nLookup++)
144 for (int nHost = 1; nHost <= 2; nHost++)
146 // We should be phasing out our use of sites like these. If we need
147 // replacements, we should ask for volunteers to put this simple
148 // php file on their webserver that prints the client IP:
149 // <?php echo $_SERVER["REMOTE_ADDR"]; ?>
152 addrConnect = CAddress("91.198.22.70",80); // checkip.dyndns.org
156 CService addrIP("checkip.dyndns.org", 80, true);
157 if (addrIP.IsValid())
158 addrConnect = addrIP;
161 pszGet = "GET / HTTP/1.1\r\n"
162 "Host: checkip.dyndns.org\r\n"
163 "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
164 "Connection: close\r\n"
167 pszKeyword = "Address:";
171 addrConnect = CAddress("74.208.43.192", 80); // www.showmyip.com
175 CService addrIP("www.showmyip.com", 80, true);
176 if (addrIP.IsValid())
177 addrConnect = addrIP;
180 pszGet = "GET /simple/ HTTP/1.1\r\n"
181 "Host: www.showmyip.com\r\n"
182 "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
183 "Connection: close\r\n"
186 pszKeyword = NULL; // Returns just IP address
189 if (GetMyExternalIP2(addrConnect, pszGet, pszKeyword, ipRet))
196 void ThreadGetMyExternalIP(void* parg)
198 // Wait for IRC to get it first
199 if (!GetBoolArg("-noirc"))
201 for (int i = 0; i < 2 * 60; i++)
204 if (fGotExternalIP || fShutdown)
209 // Fallback in case IRC fails to get it
210 if (GetMyExternalIP(addrLocalHost))
212 printf("GetMyExternalIP() returned %s\n", addrLocalHost.ToStringIP().c_str());
213 if (addrLocalHost.IsRoutable())
215 // If we already connected to a few before we had our IP, go back and addr them.
216 // setAddrKnown automatically filters any duplicate sends.
217 CAddress addr(addrLocalHost);
218 addr.nTime = GetAdjustedTime();
219 CRITICAL_BLOCK(cs_vNodes)
220 BOOST_FOREACH(CNode* pnode, vNodes)
221 pnode->PushAddress(addr);
230 bool AddAddress(CAddress addr, int64 nTimePenalty, CAddrDB *pAddrDB)
232 if (!addr.IsRoutable())
234 if ((CService)addr == (CService)addrLocalHost)
236 addr.nTime = max((int64)0, (int64)addr.nTime - nTimePenalty);
237 bool fUpdated = false;
239 CAddress addrFound = addr;
241 CRITICAL_BLOCK(cs_mapAddresses)
243 map<vector<unsigned char>, CAddress>::iterator it = mapAddresses.find(addr.GetKey());
244 if (it == mapAddresses.end())
247 printf("AddAddress(%s)\n", addr.ToString().c_str());
248 mapAddresses.insert(make_pair(addr.GetKey(), addr));
254 addrFound = (*it).second;
255 if ((addrFound.nServices | addr.nServices) != addrFound.nServices)
257 // Services have been added
258 addrFound.nServices |= addr.nServices;
261 bool fCurrentlyOnline = (GetAdjustedTime() - addr.nTime < 24 * 60 * 60);
262 int64 nUpdateInterval = (fCurrentlyOnline ? 60 * 60 : 24 * 60 * 60);
263 if (addrFound.nTime < addr.nTime - nUpdateInterval)
265 // Periodically update most recently seen time
266 addrFound.nTime = addr.nTime;
271 // There is a nasty deadlock bug if this is done inside the cs_mapAddresses
273 // Thread 1: begin db transaction (locks inside-db-mutex)
274 // then AddAddress (locks cs_mapAddresses)
275 // Thread 2: AddAddress (locks cs_mapAddresses)
276 // ... then db operation hangs waiting for inside-db-mutex
280 pAddrDB->WriteAddress(addrFound);
282 CAddrDB().WriteAddress(addrFound);
287 void AddressCurrentlyConnected(const CService& addr)
289 CAddress *paddrFound = NULL;
291 CRITICAL_BLOCK(cs_mapAddresses)
293 // Only if it's been published already
294 map<vector<unsigned char>, CAddress>::iterator it = mapAddresses.find(addr.GetKey());
295 if (it != mapAddresses.end())
296 paddrFound = &(*it).second;
301 int64 nUpdateInterval = 20 * 60;
302 if (paddrFound->nTime < GetAdjustedTime() - nUpdateInterval)
304 // Periodically update most recently seen time
305 paddrFound->nTime = GetAdjustedTime();
307 addrdb.WriteAddress(*paddrFound);
316 void AbandonRequests(void (*fn)(void*, CDataStream&), void* param1)
318 // If the dialog might get closed before the reply comes back,
319 // call this in the destructor so it doesn't get called after it's deleted.
320 CRITICAL_BLOCK(cs_vNodes)
322 BOOST_FOREACH(CNode* pnode, vNodes)
324 CRITICAL_BLOCK(pnode->cs_mapRequests)
326 for (map<uint256, CRequestTracker>::iterator mi = pnode->mapRequests.begin(); mi != pnode->mapRequests.end();)
328 CRequestTracker& tracker = (*mi).second;
329 if (tracker.fn == fn && tracker.param1 == param1)
330 pnode->mapRequests.erase(mi++);
346 // Subscription methods for the broadcast and subscription system.
347 // Channel numbers are message numbers, i.e. MSG_TABLE and MSG_PRODUCT.
349 // The subscription system uses a meet-in-the-middle strategy.
350 // With 100,000 nodes, if senders broadcast to 1000 random nodes and receivers
351 // subscribe to 1000 random nodes, 99.995% (1 - 0.99^1000) of messages will get through.
354 bool AnySubscribed(unsigned int nChannel)
356 if (pnodeLocalHost->IsSubscribed(nChannel))
358 CRITICAL_BLOCK(cs_vNodes)
359 BOOST_FOREACH(CNode* pnode, vNodes)
360 if (pnode->IsSubscribed(nChannel))
365 bool CNode::IsSubscribed(unsigned int nChannel)
367 if (nChannel >= vfSubscribe.size())
369 return vfSubscribe[nChannel];
372 void CNode::Subscribe(unsigned int nChannel, unsigned int nHops)
374 if (nChannel >= vfSubscribe.size())
377 if (!AnySubscribed(nChannel))
380 CRITICAL_BLOCK(cs_vNodes)
381 BOOST_FOREACH(CNode* pnode, vNodes)
383 pnode->PushMessage("subscribe", nChannel, nHops);
386 vfSubscribe[nChannel] = true;
389 void CNode::CancelSubscribe(unsigned int nChannel)
391 if (nChannel >= vfSubscribe.size())
394 // Prevent from relaying cancel if wasn't subscribed
395 if (!vfSubscribe[nChannel])
397 vfSubscribe[nChannel] = false;
399 if (!AnySubscribed(nChannel))
401 // Relay subscription cancel
402 CRITICAL_BLOCK(cs_vNodes)
403 BOOST_FOREACH(CNode* pnode, vNodes)
405 pnode->PushMessage("sub-cancel", nChannel);
417 CNode* FindNode(const CNetAddr& ip)
419 CRITICAL_BLOCK(cs_vNodes)
421 BOOST_FOREACH(CNode* pnode, vNodes)
422 if ((CNetAddr)pnode->addr == ip)
428 CNode* FindNode(const CService& addr)
430 CRITICAL_BLOCK(cs_vNodes)
432 BOOST_FOREACH(CNode* pnode, vNodes)
433 if ((CService)pnode->addr == addr)
439 CNode* ConnectNode(CAddress addrConnect, int64 nTimeout)
441 if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost)
444 // Look for an existing connection
445 CNode* pnode = FindNode((CService)addrConnect);
449 pnode->AddRef(nTimeout);
456 printf("trying connection %s lastseen=%.1fhrs lasttry=%.1fhrs\n",
457 addrConnect.ToString().c_str(),
458 (double)(addrConnect.nTime - GetAdjustedTime())/3600.0,
459 (double)(addrConnect.nLastTry - GetAdjustedTime())/3600.0);
461 CRITICAL_BLOCK(cs_mapAddresses)
462 mapAddresses[addrConnect.GetKey()].nLastTry = GetAdjustedTime();
466 if (ConnectSocket(addrConnect, hSocket))
469 printf("connected %s\n", addrConnect.ToString().c_str());
471 // Set to nonblocking
474 if (ioctlsocket(hSocket, FIONBIO, &nOne) == SOCKET_ERROR)
475 printf("ConnectSocket() : ioctlsocket nonblocking setting failed, error %d\n", WSAGetLastError());
477 if (fcntl(hSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
478 printf("ConnectSocket() : fcntl nonblocking setting failed, error %d\n", errno);
482 CNode* pnode = new CNode(hSocket, addrConnect, false);
484 pnode->AddRef(nTimeout);
487 CRITICAL_BLOCK(cs_vNodes)
488 vNodes.push_back(pnode);
490 pnode->nTimeConnected = GetTime();
499 void CNode::CloseSocketDisconnect()
502 if (hSocket != INVALID_SOCKET)
505 printf("%s ", DateTimeStrFormat("%x %H:%M:%S", GetTime()).c_str());
506 printf("disconnecting node %s\n", addr.ToString().c_str());
507 closesocket(hSocket);
508 hSocket = INVALID_SOCKET;
512 void CNode::Cleanup()
514 // All of a nodes broadcasts and subscriptions are automatically torn down
515 // when it goes down, so a node has to stay up to keep its broadcast going.
517 // Cancel subscriptions
518 for (unsigned int nChannel = 0; nChannel < vfSubscribe.size(); nChannel++)
519 if (vfSubscribe[nChannel])
520 CancelSubscribe(nChannel);
524 void CNode::PushVersion()
526 /// when NTP implemented, change to just nTime = GetAdjustedTime()
527 int64 nTime = (fInbound ? GetAdjustedTime() : GetTime());
528 CAddress addrYou = (fUseProxy ? CAddress("0.0.0.0") : addr);
529 CAddress addrMe = (fUseProxy ? CAddress("0.0.0.0") : addrLocalHost);
530 RAND_bytes((unsigned char*)&nLocalHostNonce, sizeof(nLocalHostNonce));
531 PushMessage("version", PROTOCOL_VERSION, nLocalServices, nTime, addrYou, addrMe,
532 nLocalHostNonce, FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<string>()), nBestHeight);
539 std::map<CNetAddr, int64> CNode::setBanned;
540 CCriticalSection CNode::cs_setBanned;
542 void CNode::ClearBanned()
547 bool CNode::IsBanned(CNetAddr ip)
549 bool fResult = false;
550 CRITICAL_BLOCK(cs_setBanned)
552 std::map<CNetAddr, int64>::iterator i = setBanned.find(ip);
553 if (i != setBanned.end())
555 int64 t = (*i).second;
563 bool CNode::Misbehaving(int howmuch)
567 printf("Warning: local node %s misbehaving\n", addr.ToString().c_str());
571 nMisbehavior += howmuch;
572 if (nMisbehavior >= GetArg("-banscore", 100))
574 int64 banTime = GetTime()+GetArg("-bantime", 60*60*24); // Default 24-hour ban
575 CRITICAL_BLOCK(cs_setBanned)
576 if (setBanned[addr] < banTime)
577 setBanned[addr] = banTime;
578 CloseSocketDisconnect();
579 printf("Disconnected %s for misbehavior (score=%d)\n", addr.ToString().c_str(), nMisbehavior);
596 void ThreadSocketHandler(void* parg)
598 IMPLEMENT_RANDOMIZE_STACK(ThreadSocketHandler(parg));
601 vnThreadsRunning[0]++;
602 ThreadSocketHandler2(parg);
603 vnThreadsRunning[0]--;
605 catch (std::exception& e) {
606 vnThreadsRunning[0]--;
607 PrintException(&e, "ThreadSocketHandler()");
609 vnThreadsRunning[0]--;
610 throw; // support pthread_cancel()
612 printf("ThreadSocketHandler exiting\n");
615 void ThreadSocketHandler2(void* parg)
617 printf("ThreadSocketHandler started\n");
618 list<CNode*> vNodesDisconnected;
619 int nPrevNodeCount = 0;
626 CRITICAL_BLOCK(cs_vNodes)
628 // Disconnect unused nodes
629 vector<CNode*> vNodesCopy = vNodes;
630 BOOST_FOREACH(CNode* pnode, vNodesCopy)
632 if (pnode->fDisconnect ||
633 (pnode->GetRefCount() <= 0 && pnode->vRecv.empty() && pnode->vSend.empty()))
635 // remove from vNodes
636 vNodes.erase(remove(vNodes.begin(), vNodes.end(), pnode), vNodes.end());
638 // close socket and cleanup
639 pnode->CloseSocketDisconnect();
642 // hold in disconnected pool until all refs are released
643 pnode->nReleaseTime = max(pnode->nReleaseTime, GetTime() + 15 * 60);
644 if (pnode->fNetworkNode || pnode->fInbound)
646 vNodesDisconnected.push_back(pnode);
650 // Delete disconnected nodes
651 list<CNode*> vNodesDisconnectedCopy = vNodesDisconnected;
652 BOOST_FOREACH(CNode* pnode, vNodesDisconnectedCopy)
654 // wait until threads are done using it
655 if (pnode->GetRefCount() <= 0)
657 bool fDelete = false;
658 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
659 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
660 TRY_CRITICAL_BLOCK(pnode->cs_mapRequests)
661 TRY_CRITICAL_BLOCK(pnode->cs_inventory)
665 vNodesDisconnected.remove(pnode);
671 if (vNodes.size() != nPrevNodeCount)
673 nPrevNodeCount = vNodes.size();
679 // Find which sockets have data to receive
681 struct timeval timeout;
683 timeout.tv_usec = 50000; // frequency to poll pnode->vSend
690 FD_ZERO(&fdsetError);
691 SOCKET hSocketMax = 0;
693 if(hListenSocket != INVALID_SOCKET)
694 FD_SET(hListenSocket, &fdsetRecv);
695 hSocketMax = max(hSocketMax, hListenSocket);
696 CRITICAL_BLOCK(cs_vNodes)
698 BOOST_FOREACH(CNode* pnode, vNodes)
700 if (pnode->hSocket == INVALID_SOCKET)
702 FD_SET(pnode->hSocket, &fdsetRecv);
703 FD_SET(pnode->hSocket, &fdsetError);
704 hSocketMax = max(hSocketMax, pnode->hSocket);
705 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
706 if (!pnode->vSend.empty())
707 FD_SET(pnode->hSocket, &fdsetSend);
711 vnThreadsRunning[0]--;
712 int nSelect = select(hSocketMax + 1, &fdsetRecv, &fdsetSend, &fdsetError, &timeout);
713 vnThreadsRunning[0]++;
716 if (nSelect == SOCKET_ERROR)
718 int nErr = WSAGetLastError();
721 printf("socket select error %d\n", nErr);
722 for (int i = 0; i <= hSocketMax; i++)
723 FD_SET(i, &fdsetRecv);
726 FD_ZERO(&fdsetError);
727 Sleep(timeout.tv_usec/1000);
732 // Accept new connections
734 if (hListenSocket != INVALID_SOCKET && FD_ISSET(hListenSocket, &fdsetRecv))
736 struct sockaddr_in sockaddr;
737 socklen_t len = sizeof(sockaddr);
738 SOCKET hSocket = accept(hListenSocket, (struct sockaddr*)&sockaddr, &len);
739 CAddress addr(sockaddr);
742 CRITICAL_BLOCK(cs_vNodes)
743 BOOST_FOREACH(CNode* pnode, vNodes)
746 if (hSocket == INVALID_SOCKET)
748 if (WSAGetLastError() != WSAEWOULDBLOCK)
749 printf("socket error accept failed: %d\n", WSAGetLastError());
751 else if (nInbound >= GetArg("-maxconnections", 125) - MAX_OUTBOUND_CONNECTIONS)
753 closesocket(hSocket);
755 else if (CNode::IsBanned(addr))
757 printf("connetion from %s dropped (banned)\n", addr.ToString().c_str());
758 closesocket(hSocket);
762 printf("accepted connection %s\n", addr.ToString().c_str());
763 CNode* pnode = new CNode(hSocket, addr, true);
765 CRITICAL_BLOCK(cs_vNodes)
766 vNodes.push_back(pnode);
772 // Service each socket
774 vector<CNode*> vNodesCopy;
775 CRITICAL_BLOCK(cs_vNodes)
778 BOOST_FOREACH(CNode* pnode, vNodesCopy)
781 BOOST_FOREACH(CNode* pnode, vNodesCopy)
789 if (pnode->hSocket == INVALID_SOCKET)
791 if (FD_ISSET(pnode->hSocket, &fdsetRecv) || FD_ISSET(pnode->hSocket, &fdsetError))
793 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
795 CDataStream& vRecv = pnode->vRecv;
796 unsigned int nPos = vRecv.size();
798 if (nPos > ReceiveBufferSize()) {
799 if (!pnode->fDisconnect)
800 printf("socket recv flood control disconnect (%d bytes)\n", vRecv.size());
801 pnode->CloseSocketDisconnect();
804 // typical socket buffer is 8K-64K
805 char pchBuf[0x10000];
806 int nBytes = recv(pnode->hSocket, pchBuf, sizeof(pchBuf), MSG_DONTWAIT);
809 vRecv.resize(nPos + nBytes);
810 memcpy(&vRecv[nPos], pchBuf, nBytes);
811 pnode->nLastRecv = GetTime();
813 else if (nBytes == 0)
815 // socket closed gracefully
816 if (!pnode->fDisconnect)
817 printf("socket closed\n");
818 pnode->CloseSocketDisconnect();
823 int nErr = WSAGetLastError();
824 if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
826 if (!pnode->fDisconnect)
827 printf("socket recv error %d\n", nErr);
828 pnode->CloseSocketDisconnect();
838 if (pnode->hSocket == INVALID_SOCKET)
840 if (FD_ISSET(pnode->hSocket, &fdsetSend))
842 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
844 CDataStream& vSend = pnode->vSend;
847 int nBytes = send(pnode->hSocket, &vSend[0], vSend.size(), MSG_NOSIGNAL | MSG_DONTWAIT);
850 vSend.erase(vSend.begin(), vSend.begin() + nBytes);
851 pnode->nLastSend = GetTime();
856 int nErr = WSAGetLastError();
857 if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
859 printf("socket send error %d\n", nErr);
860 pnode->CloseSocketDisconnect();
863 if (vSend.size() > SendBufferSize()) {
864 if (!pnode->fDisconnect)
865 printf("socket send flood control disconnect (%d bytes)\n", vSend.size());
866 pnode->CloseSocketDisconnect();
873 // Inactivity checking
875 if (pnode->vSend.empty())
876 pnode->nLastSendEmpty = GetTime();
877 if (GetTime() - pnode->nTimeConnected > 60)
879 if (pnode->nLastRecv == 0 || pnode->nLastSend == 0)
881 printf("socket no message in first 60 seconds, %d %d\n", pnode->nLastRecv != 0, pnode->nLastSend != 0);
882 pnode->fDisconnect = true;
884 else if (GetTime() - pnode->nLastSend > 90*60 && GetTime() - pnode->nLastSendEmpty > 90*60)
886 printf("socket not sending\n");
887 pnode->fDisconnect = true;
889 else if (GetTime() - pnode->nLastRecv > 90*60)
891 printf("socket inactivity timeout\n");
892 pnode->fDisconnect = true;
896 CRITICAL_BLOCK(cs_vNodes)
898 BOOST_FOREACH(CNode* pnode, vNodesCopy)
915 void ThreadMapPort(void* parg)
917 IMPLEMENT_RANDOMIZE_STACK(ThreadMapPort(parg));
920 vnThreadsRunning[5]++;
921 ThreadMapPort2(parg);
922 vnThreadsRunning[5]--;
924 catch (std::exception& e) {
925 vnThreadsRunning[5]--;
926 PrintException(&e, "ThreadMapPort()");
928 vnThreadsRunning[5]--;
929 PrintException(NULL, "ThreadMapPort()");
931 printf("ThreadMapPort exiting\n");
934 void ThreadMapPort2(void* parg)
936 printf("ThreadMapPort started\n");
939 sprintf(port, "%d", GetListenPort());
941 const char * multicastif = 0;
942 const char * minissdpdpath = 0;
943 struct UPNPDev * devlist = 0;
946 #ifndef UPNPDISCOVER_SUCCESS
948 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0);
952 devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0, 0, &error);
955 struct UPNPUrls urls;
956 struct IGDdatas data;
959 r = UPNP_GetValidIGD(devlist, &urls, &data, lanaddr, sizeof(lanaddr));
962 string strDesc = "Bitcoin " + FormatFullVersion();
963 #ifndef UPNPDISCOVER_SUCCESS
965 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
966 port, port, lanaddr, strDesc.c_str(), "TCP", 0);
969 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
970 port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
973 if(r!=UPNPCOMMAND_SUCCESS)
974 printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
975 port, port, lanaddr, r, strupnperror(r));
977 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;
990 printf("No valid UPnP IGDs found\n");
991 freeUPNPDevlist(devlist); devlist = 0;
995 if (fShutdown || !fUseUPnP)
1002 void MapPort(bool fMapPort)
1004 if (fUseUPnP != fMapPort)
1006 fUseUPnP = fMapPort;
1007 WriteSetting("fUseUPnP", fUseUPnP);
1009 if (fUseUPnP && vnThreadsRunning[5] < 1)
1011 if (!CreateThread(ThreadMapPort, NULL))
1012 printf("Error: ThreadMapPort(ThreadMapPort) failed\n");
1016 void MapPort(bool /* unused fMapPort */)
1018 // Intentionally left blank.
1031 static const char *strDNSSeed[] = {
1033 "dnsseed.bluematt.me",
1034 "seed.bitcoin.sipa.be",
1035 "dnsseed.bitcoin.dashjr.org",
1038 void ThreadDNSAddressSeed(void* parg)
1040 IMPLEMENT_RANDOMIZE_STACK(ThreadDNSAddressSeed(parg));
1043 vnThreadsRunning[6]++;
1044 ThreadDNSAddressSeed2(parg);
1045 vnThreadsRunning[6]--;
1047 catch (std::exception& e) {
1048 vnThreadsRunning[6]--;
1049 PrintException(&e, "ThreadDNSAddressSeed()");
1051 vnThreadsRunning[6]--;
1052 throw; // support pthread_cancel()
1054 printf("ThreadDNSAddressSeed exiting\n");
1057 void ThreadDNSAddressSeed2(void* parg)
1059 printf("ThreadDNSAddressSeed started\n");
1064 printf("Loading addresses from DNS seeds (could take a while)\n");
1066 for (int seed_idx = 0; seed_idx < ARRAYLEN(strDNSSeed); seed_idx++) {
1067 vector<CNetAddr> vaddr;
1068 if (LookupHost(strDNSSeed[seed_idx], vaddr))
1072 BOOST_FOREACH (CNetAddr& ip, vaddr)
1074 if (ip.IsRoutable())
1076 CAddress addr(CService(ip, GetDefaultPort()), NODE_NETWORK);
1078 AddAddress(addr, 0, &addrDB);
1082 addrDB.TxnCommit(); // Save addresses (it's ok if this fails)
1087 printf("%d addresses found from DNS seeds\n", found);
1101 unsigned int pnSeed[] =
1103 0x6884ac63, 0x3ffecead, 0x2919b953, 0x0942fe50, 0x7a1d922e, 0xcdd6734a, 0x953a5bb6, 0x2c46922e,
1104 0xe2a5f143, 0xaa39103a, 0xa06afa5c, 0x135ffd59, 0xe8e82863, 0xf61ef029, 0xf75f042e, 0x2b363532,
1105 0x29b2df42, 0x16b1f64e, 0xd46e281b, 0x5280bf58, 0x60372229, 0x1be58e4f, 0xa8496f45, 0x1fb1a057,
1106 0x756b3844, 0x3bb79445, 0x0b375518, 0xcccb0102, 0xb682bf2e, 0x46431c02, 0x3a81073a, 0xa3771f1f,
1107 0x213a121f, 0x85dc2c1b, 0x56b4323b, 0xb34e8945, 0x3c40b33d, 0xfa276418, 0x1f818d29, 0xebe1e344,
1108 0xf6160a18, 0xf4fa384a, 0x34b09558, 0xb882b543, 0xe3ce2253, 0x6abf56d8, 0xe91b1155, 0x688ee6ad,
1109 0x2efc6058, 0x4792cd47, 0x0c32f757, 0x4c813a46, 0x8c93644a, 0x37507444, 0x813ad218, 0xdac06d4a,
1110 0xe4c63e4b, 0x21a1ea3c, 0x8d88556f, 0x30e9173a, 0x041f681b, 0xdc77ba50, 0xc0072753, 0xceddd44f,
1111 0x052d1743, 0xe3c77a4a, 0x13981c3a, 0x5685d918, 0x3c0e4e70, 0x3e56fb54, 0xb676ae0c, 0xac93c859,
1112 0x22279f43, 0x975a4542, 0xe527f071, 0xea162f2e, 0x3c65a32e, 0x5be5713b, 0x961ec418, 0xb202922e,
1113 0x5ef7be50, 0xce49f53e, 0x05803b47, 0x8463b055, 0x78576153, 0x3ec2ae3a, 0x4bbd7118, 0xafcee043,
1114 0x56a3e8ba, 0x6174de4d, 0x8d01ba4b, 0xc9af564e, 0xdbc9c547, 0xa627474d, 0xdada9244, 0xd3b3083a,
1115 0x523e071f, 0xd6b96f18, 0xbd527c46, 0xdf2bbb4d, 0xd37b4a4b, 0x3a6a2158, 0xc064b055, 0x18a8e055,
1116 0xec4dae3b, 0x0540416c, 0x475b4fbe, 0x064803b2, 0x48e9f062, 0x2898524b, 0xd315ff43, 0xf786d247,
1117 0xc7ea2f3e, 0xc087f043, 0xc163354b, 0x8250284d, 0xed300029, 0xbf36e05c, 0x8eb3ae4c, 0xe7aa623e,
1118 0x7ced0274, 0xdd362c1b, 0x362b995a, 0xca26b629, 0x3fc41618, 0xb97b364e, 0xa05b8729, 0x0f5e3c43,
1119 0xdf942618, 0x6aeb9b5b, 0xbf04762e, 0xfaaeb118, 0x87579958, 0x76520044, 0xc2660c5b, 0x628b201b,
1120 0xf193932e, 0x1c0ad045, 0xff908346, 0x8da9d4da, 0xed201c1f, 0xa47a2b1b, 0x330007d4, 0x8ba1ed47,
1121 0xb2f02d44, 0x7db62c1b, 0x781c454b, 0xc0300029, 0xb7062a45, 0x88b52e3a, 0x78dd6b63, 0x1cb9b718,
1122 0x5d358e47, 0x59912c3b, 0x79607544, 0x5197f759, 0xc023be48, 0xd1013743, 0x0f354057, 0x8e3aac3b,
1123 0x4114693e, 0x22316318, 0xe27dda50, 0x878eac3b, 0x4948a21f, 0x5db7f24c, 0x8ccb6157, 0x26a5de18,
1124 0x0a11bd43, 0x27bb1e41, 0x60a7a951, 0x3e16b35e, 0x07888b53, 0x5648a853, 0x0149fe50, 0xd070a34f,
1125 0x6454c96d, 0xd6e54758, 0xa96dc152, 0x65447861, 0xf6bdf95e, 0x10400202, 0x2c29d483, 0x18174732,
1126 0x1d840618, 0x12e61818, 0x089d3f3c, 0x917e931f, 0xd1b0c90e, 0x25bd3c42, 0xeb05775b, 0x7d550c59,
1127 0x6cfacb01, 0xe4224444, 0xa41dd943, 0x0f5aa643, 0x5e33731b, 0x81036d50, 0x6f46a0d1, 0x7731be43,
1128 0x14840e18, 0xf1e8d059, 0x661d2b1f, 0x40a3201b, 0x9407b843, 0xedf0254d, 0x7bd1a5bc, 0x073dbe51,
1129 0xe864a97b, 0x2efd947b, 0xb9ca0e45, 0x4e2113ad, 0xcc305731, 0xd39ca63c, 0x733df918, 0xda172b1f,
1130 0xaa03b34d, 0x7230fd4d, 0xf1ce6e3a, 0x2e9fab43, 0xa4010750, 0xa928bd18, 0x6809be42, 0xb19de348,
1131 0xff956270, 0x0d795f51, 0xd2dec247, 0x6df5774b, 0xbac11f79, 0xdfb05c75, 0x887683d8, 0xa1e83632,
1132 0x2c0f7671, 0x28bcb65d, 0xac2a7545, 0x3eebfc60, 0x304ad7c4, 0xa215a462, 0xc86f0f58, 0xcfb92ebe,
1133 0x5e23ed82, 0xf506184b, 0xec0f19b7, 0x060c59ad, 0x86ee3174, 0x85380774, 0xa199a562, 0x02b507ae,
1134 0x33eb2163, 0xf2112b1f, 0xb702ba50, 0x131b9618, 0x90ccd04a, 0x08f3273b, 0xecb61718, 0x64b8b44d,
1135 0x182bf4dc, 0xc7b68286, 0x6e318d5f, 0xfdb03654, 0xb3272e54, 0xe014ad4b, 0x274e4a31, 0x7806375c,
1136 0xbc34a748, 0x1b5ad94a, 0x6b54d10e, 0x73e2ae6e, 0x5529d483, 0x8455a76d, 0x99c13f47, 0x1d811741,
1137 0xa9782a78, 0x0b00464d, 0x7266ea50, 0x532dab46, 0x33e1413e, 0x780d0c18, 0x0fb0854e, 0x03370155,
1138 0x2693042e, 0xfa3d824a, 0x2bb1681b, 0x37ea2a18, 0x7fb8414b, 0x32e0713b, 0xacf38d3f, 0xa282716f,
1139 0xb1a09d7b, 0xa04b764b, 0x83c94d18, 0x05ee4c6d, 0x0e795f51, 0x46984352, 0xf80fc247, 0x3fccb946,
1140 0xd7ae244b, 0x0a8e0a4c, 0x57b141bc, 0x3647bed1, 0x1431b052, 0x803a8bbb, 0xfc69056b, 0xf5991862,
1141 0x14963b2e, 0xd35d5dda, 0xc6c73574, 0xc8f1405b, 0x0ca4224d, 0xecd36071, 0xa9461754, 0xe7a0ed72,
1142 0x559e8346, 0x1c9beec1, 0xc786ea4a, 0x9561b44d, 0x9788074d, 0x1a69934f, 0x23c5614c, 0x07c79d4b,
1143 0xc7ee52db, 0xc72df351, 0xcb135e44, 0xa0988346, 0xc211fc4c, 0x87dec34b, 0x1381074d, 0x04a65cb7,
1144 0x4409083a, 0x4a407a4c, 0x92b8d37d, 0xacf50b4d, 0xa58aa5bc, 0x448f801f, 0x9c83762e, 0x6fd5734a,
1145 0xfe2d454b, 0x84144c55, 0x05190e4c, 0xb2151448, 0x63867a3e, 0x16099018, 0x9c010d3c, 0x962d8f3d,
1146 0xd51ee453, 0x9d86801f, 0x68e87b47, 0x6bf7bb73, 0x5fc7910e, 0x10d90118, 0x3db04442, 0x729d3e4b,
1147 0xc397d842, 0x57bb15ad, 0x72f31f4e, 0xc9380043, 0x2bb24e18, 0xd9b8ab50, 0xb786801f, 0xf4dc4847,
1148 0x85f4bb51, 0x4435995b, 0x5ba07e40, 0x2c57392e, 0x3628124b, 0x9839b64b, 0x6fe8b24d, 0xaddce847,
1149 0x75260e45, 0x0c572a43, 0xfea21902, 0xb9f9742e, 0x5a70d443, 0x8fc5910e, 0x868d4744, 0x56245e02,
1150 0xd7eb5f02, 0x35c12c1b, 0x4373034b, 0x8786554c, 0xa6facf18, 0x4b11a31f, 0x3570664e, 0x5a64bc42,
1151 0x0b03983f, 0x8f457e4c, 0x0fd874c3, 0xb6cf31b2, 0x2bbc2d4e, 0x146ca5b2, 0x9d00b150, 0x048a4153,
1152 0xca4dcd43, 0xc1607cca, 0x8234cf57, 0x9c7daead, 0x3dc07658, 0xea5c6e4c, 0xf1a0084e, 0x16d2ee53,
1153 0x1b849418, 0xfe913a47, 0x1e988f62, 0x208b644c, 0xc55ee980, 0xbdbce747, 0xf59a384e, 0x0f56091b,
1154 0x7417b745, 0x0c37344e, 0x2c62ab47, 0xf8533a4d, 0x8030084d, 0x76b93c4b, 0xda6ea0ad, 0x3c54f618,
1155 0x63b0de1f, 0x7370d858, 0x1a70bb4c, 0xdda63b2e, 0x60b2ba50, 0x1ba7d048, 0xbe1b2c1b, 0xabea5747,
1156 0x29ad2e4d, 0xe8cd7642, 0x66c80e18, 0x138bf34a, 0xc6145e44, 0x2586794c, 0x07bc5478, 0x0da0b14d,
1157 0x8f95354e, 0x9eb11c62, 0xa1545e46, 0x2e7a2602, 0x408c9c3d, 0x59065d55, 0xf51d1a4c, 0x3bbc6a4e,
1158 0xc71b2a2e, 0xcdaaa545, 0x17d659d0, 0x5202e7ad, 0xf1b68445, 0x93375961, 0xbd88a043, 0x066ad655,
1159 0x890f6318, 0x7b7dca47, 0x99bdd662, 0x3bb4fc53, 0x1231efdc, 0xc0a99444, 0x96bbea47, 0x61ed8748,
1160 0x27dfa73b, 0x8d4d1754, 0x3460042e, 0x551f0c4c, 0x8d0e0718, 0x162ddc53, 0x53231718, 0x1ecd65d0,
1161 0x944d28bc, 0x3b79d058, 0xaff97fbc, 0x4860006c, 0xc101c90e, 0xace41743, 0xa5975d4c, 0x5cc2703e,
1162 0xb55a4450, 0x02d18840, 0xee2765ae, 0xd6012fd5, 0x24c94d7d, 0x8c6eec47, 0x7520ba5d, 0x9e15e460,
1163 0x8510b04c, 0x75ec3847, 0x1dfa6661, 0xe172b3ad, 0x5744c90e, 0x52a0a152, 0x8d6fad18, 0x67b74b6d,
1164 0x93a089b2, 0x0f3ac5d5, 0xe5de1855, 0x43d25747, 0x4bad804a, 0x55b408d8, 0x60a36441, 0xf553e860,
1165 0xdb2fa2c8, 0x03152b32, 0xdd27a7d5, 0x3116a8b8, 0x0a1d708c, 0xeee2f13c, 0x6acf436f, 0xce6eb4ca,
1166 0x101cd3d9, 0x1c48a6b8, 0xe57d6f44, 0x93dcf562,
1171 void ThreadOpenConnections(void* parg)
1173 IMPLEMENT_RANDOMIZE_STACK(ThreadOpenConnections(parg));
1176 vnThreadsRunning[1]++;
1177 ThreadOpenConnections2(parg);
1178 vnThreadsRunning[1]--;
1180 catch (std::exception& e) {
1181 vnThreadsRunning[1]--;
1182 PrintException(&e, "ThreadOpenConnections()");
1184 vnThreadsRunning[1]--;
1185 PrintException(NULL, "ThreadOpenConnections()");
1187 printf("ThreadOpenConnections exiting\n");
1190 void ThreadOpenConnections2(void* parg)
1192 printf("ThreadOpenConnections started\n");
1194 // Connect to specific addresses
1195 if (mapArgs.count("-connect"))
1197 for (int64 nLoop = 0;; nLoop++)
1199 BOOST_FOREACH(string strAddr, mapMultiArgs["-connect"])
1201 CAddress addr(strAddr, fAllowDNS);
1203 OpenNetworkConnection(addr);
1204 for (int i = 0; i < 10 && i < nLoop; i++)
1214 // Connect to manually added nodes first
1215 if (mapArgs.count("-addnode"))
1217 BOOST_FOREACH(string strAddr, mapMultiArgs["-addnode"])
1219 CAddress addr(strAddr, fAllowDNS);
1222 OpenNetworkConnection(addr);
1230 // Initiate network connections
1231 int64 nStart = GetTime();
1234 // Limit outbound connections
1235 vnThreadsRunning[1]--;
1240 CRITICAL_BLOCK(cs_vNodes)
1241 BOOST_FOREACH(CNode* pnode, vNodes)
1242 if (!pnode->fInbound)
1244 int nMaxOutboundConnections = MAX_OUTBOUND_CONNECTIONS;
1245 nMaxOutboundConnections = min(nMaxOutboundConnections, (int)GetArg("-maxconnections", 125));
1246 if (nOutbound < nMaxOutboundConnections)
1252 vnThreadsRunning[1]++;
1256 bool fAddSeeds = false;
1258 CRITICAL_BLOCK(cs_mapAddresses)
1260 // Add seed nodes if IRC isn't working
1261 bool fTOR = (fUseProxy && addrProxy.GetPort() == 9050);
1262 if (mapAddresses.empty() && (GetTime() - nStart > 60 || fTOR) && !fTestNet)
1268 for (int i = 0; i < ARRAYLEN(pnSeed); i++)
1270 // It'll only connect to one or two seed nodes because once it connects,
1271 // it'll get a pile of addresses with newer timestamps.
1272 // Seed nodes are given a random 'last seen time' of between one and two
1274 const int64 nOneWeek = 7*24*60*60;
1276 memcpy(&ip, &pnSeed[i], sizeof(ip));
1277 CAddress addr(CService(ip, GetDefaultPort()));
1278 addr.nTime = GetTime()-GetRand(nOneWeek)-nOneWeek;
1284 // Choose an address to connect to based on most recently seen
1286 CAddress addrConnect;
1287 int64 nBest = std::numeric_limits<int64>::min();
1289 // Only connect to one address per a.b.?.? range.
1290 // Do this here so we don't have to critsect vNodes inside mapAddresses critsect.
1291 set<vector<unsigned char> > setConnected;
1292 CRITICAL_BLOCK(cs_vNodes)
1293 BOOST_FOREACH(CNode* pnode, vNodes)
1294 setConnected.insert(pnode->addr.GetGroup());
1296 int64 nANow = GetAdjustedTime();
1298 CRITICAL_BLOCK(cs_mapAddresses)
1300 BOOST_FOREACH(const PAIRTYPE(vector<unsigned char>, CAddress)& item, mapAddresses)
1302 const CAddress& addr = item.second;
1303 if (!addr.IsIPv4() || !addr.IsValid() || setConnected.count(addr.GetGroup()))
1305 int64 nSinceLastSeen = nANow - addr.nTime;
1306 int64 nSinceLastTry = nANow - addr.nLastTry;
1308 // Randomize the order in a deterministic way, putting the standard port first
1309 int64 nRandomizer = (uint64)(nStart * 4951 + addr.nLastTry * 9567851 + addr.GetHash()) % (2 * 60 * 60);
1310 if (addr.GetPort() != GetDefaultPort())
1311 nRandomizer += 2 * 60 * 60;
1313 // Last seen Base retry frequency
1322 // 365 days 93 hours
1323 int64 nDelay = (int64)(3600.0 * sqrt(fabs((double)nSinceLastSeen) / 3600.0) + nRandomizer);
1325 // Fast reconnect for one hour after last seen
1326 if (nSinceLastSeen < 60 * 60)
1329 // Limit retry frequency
1330 if (nSinceLastTry < nDelay)
1333 // If we have IRC, we'll be notified when they first come online,
1334 // and again every 24 hours by the refresh broadcast.
1335 if (nGotIRCAddresses > 0 && vNodes.size() >= 2 && nSinceLastSeen > 24 * 60 * 60)
1338 // Only try the old stuff if we don't have enough connections
1339 if (vNodes.size() >= 8 && nSinceLastSeen > 24 * 60 * 60)
1342 // If multiple addresses are ready, prioritize by time since
1343 // last seen and time since last tried.
1344 int64 nScore = min(nSinceLastTry, (int64)24 * 60 * 60) - nSinceLastSeen - nRandomizer;
1353 if (addrConnect.IsValid())
1354 OpenNetworkConnection(addrConnect);
1358 bool OpenNetworkConnection(const CAddress& addrConnect)
1361 // Initiate outbound network connection
1365 if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost || !addrConnect.IsIPv4() ||
1366 FindNode((CNetAddr)addrConnect) || CNode::IsBanned(addrConnect))
1369 vnThreadsRunning[1]--;
1370 CNode* pnode = ConnectNode(addrConnect);
1371 vnThreadsRunning[1]++;
1376 pnode->fNetworkNode = true;
1388 void ThreadMessageHandler(void* parg)
1390 IMPLEMENT_RANDOMIZE_STACK(ThreadMessageHandler(parg));
1393 vnThreadsRunning[2]++;
1394 ThreadMessageHandler2(parg);
1395 vnThreadsRunning[2]--;
1397 catch (std::exception& e) {
1398 vnThreadsRunning[2]--;
1399 PrintException(&e, "ThreadMessageHandler()");
1401 vnThreadsRunning[2]--;
1402 PrintException(NULL, "ThreadMessageHandler()");
1404 printf("ThreadMessageHandler exiting\n");
1407 void ThreadMessageHandler2(void* parg)
1409 printf("ThreadMessageHandler started\n");
1410 SetThreadPriority(THREAD_PRIORITY_BELOW_NORMAL);
1413 vector<CNode*> vNodesCopy;
1414 CRITICAL_BLOCK(cs_vNodes)
1416 vNodesCopy = vNodes;
1417 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1421 // Poll the connected nodes for messages
1422 CNode* pnodeTrickle = NULL;
1423 if (!vNodesCopy.empty())
1424 pnodeTrickle = vNodesCopy[GetRand(vNodesCopy.size())];
1425 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1428 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
1429 ProcessMessages(pnode);
1434 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
1435 SendMessages(pnode, pnode == pnodeTrickle);
1440 CRITICAL_BLOCK(cs_vNodes)
1442 BOOST_FOREACH(CNode* pnode, vNodesCopy)
1446 // Wait and allow messages to bunch up.
1447 // Reduce vnThreadsRunning so StopNode has permission to exit while
1448 // we're sleeping, but we must always check fShutdown after doing this.
1449 vnThreadsRunning[2]--;
1451 if (fRequestShutdown)
1453 vnThreadsRunning[2]++;
1464 bool BindListenPort(string& strError)
1468 addrLocalHost.SetPort(GetListenPort());
1471 // Initialize Windows Sockets
1473 int ret = WSAStartup(MAKEWORD(2,2), &wsadata);
1474 if (ret != NO_ERROR)
1476 strError = strprintf("Error: TCP/IP socket library failed to start (WSAStartup returned error %d)", ret);
1477 printf("%s\n", strError.c_str());
1482 // Create socket for listening for incoming connections
1483 hListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
1484 if (hListenSocket == INVALID_SOCKET)
1486 strError = strprintf("Error: Couldn't open socket for incoming connections (socket returned error %d)", WSAGetLastError());
1487 printf("%s\n", strError.c_str());
1492 // Different way of disabling SIGPIPE on BSD
1493 setsockopt(hListenSocket, SOL_SOCKET, SO_NOSIGPIPE, (void*)&nOne, sizeof(int));
1497 // Allow binding if the port is still in TIME_WAIT state after
1498 // the program was closed and restarted. Not an issue on windows.
1499 setsockopt(hListenSocket, SOL_SOCKET, SO_REUSEADDR, (void*)&nOne, sizeof(int));
1503 // Set to nonblocking, incoming connections will also inherit this
1504 if (ioctlsocket(hListenSocket, FIONBIO, (u_long*)&nOne) == SOCKET_ERROR)
1506 if (fcntl(hListenSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
1509 strError = strprintf("Error: Couldn't set properties on socket for incoming connections (error %d)", WSAGetLastError());
1510 printf("%s\n", strError.c_str());
1514 // The sockaddr_in structure specifies the address family,
1515 // IP address, and port for the socket that is being bound
1516 struct sockaddr_in sockaddr;
1517 memset(&sockaddr, 0, sizeof(sockaddr));
1518 sockaddr.sin_family = AF_INET;
1519 sockaddr.sin_addr.s_addr = INADDR_ANY; // bind to all IPs on this computer
1520 sockaddr.sin_port = htons(GetListenPort());
1521 if (::bind(hListenSocket, (struct sockaddr*)&sockaddr, sizeof(sockaddr)) == SOCKET_ERROR)
1523 int nErr = WSAGetLastError();
1524 if (nErr == WSAEADDRINUSE)
1525 strError = strprintf(_("Unable to bind to port %d on this computer. Bitcoin is probably already running."), ntohs(sockaddr.sin_port));
1527 strError = strprintf("Error: Unable to bind to port %d on this computer (bind returned error %d)", ntohs(sockaddr.sin_port), nErr);
1528 printf("%s\n", strError.c_str());
1531 printf("Bound to port %d\n", ntohs(sockaddr.sin_port));
1533 // Listen for incoming connections
1534 if (listen(hListenSocket, SOMAXCONN) == SOCKET_ERROR)
1536 strError = strprintf("Error: Listening for incoming connections failed (listen returned error %d)", WSAGetLastError());
1537 printf("%s\n", strError.c_str());
1544 void StartNode(void* parg)
1546 if (pnodeLocalHost == NULL)
1547 pnodeLocalHost = new CNode(INVALID_SOCKET, CAddress(CService("127.0.0.1", 0), nLocalServices));
1550 // Get local host ip
1551 char pszHostName[1000] = "";
1552 if (gethostname(pszHostName, sizeof(pszHostName)) != SOCKET_ERROR)
1554 vector<CNetAddr> vaddr;
1555 if (LookupHost(pszHostName, vaddr))
1556 BOOST_FOREACH (const CNetAddr &addr, vaddr)
1557 if (!addr.IsLocal())
1559 addrLocalHost.SetIP(addr);
1564 // Get local host ip
1565 struct ifaddrs* myaddrs;
1566 if (getifaddrs(&myaddrs) == 0)
1568 for (struct ifaddrs* ifa = myaddrs; ifa != NULL; ifa = ifa->ifa_next)
1570 if (ifa->ifa_addr == NULL) continue;
1571 if ((ifa->ifa_flags & IFF_UP) == 0) continue;
1572 if (strcmp(ifa->ifa_name, "lo") == 0) continue;
1573 if (strcmp(ifa->ifa_name, "lo0") == 0) continue;
1575 if (ifa->ifa_addr->sa_family == AF_INET)
1577 struct sockaddr_in* s4 = (struct sockaddr_in*)(ifa->ifa_addr);
1578 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s4->sin_addr), pszIP, sizeof(pszIP)) != NULL)
1579 printf("ipv4 %s: %s\n", ifa->ifa_name, pszIP);
1581 // Take the first IP that isn't loopback 127.x.x.x
1582 CAddress addr(CService(s4->sin_addr, GetListenPort()), nLocalServices);
1583 if (addr.IsValid() && !addr.IsLocal())
1585 addrLocalHost = addr;
1589 else if (ifa->ifa_addr->sa_family == AF_INET6)
1591 struct sockaddr_in6* s6 = (struct sockaddr_in6*)(ifa->ifa_addr);
1592 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s6->sin6_addr), pszIP, sizeof(pszIP)) != NULL)
1593 printf("ipv6 %s: %s\n", ifa->ifa_name, pszIP);
1596 freeifaddrs(myaddrs);
1599 printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1601 if (fUseProxy || mapArgs.count("-connect") || fNoListen)
1603 // Proxies can't take incoming connections
1604 addrLocalHost.SetIP(CNetAddr("0.0.0.0"));
1605 printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1609 CreateThread(ThreadGetMyExternalIP, NULL);
1616 if (GetBoolArg("-nodnsseed"))
1617 printf("DNS seeding disabled\n");
1619 if (!CreateThread(ThreadDNSAddressSeed, NULL))
1620 printf("Error: CreateThread(ThreadDNSAddressSeed) failed\n");
1622 // Map ports with UPnP
1626 // Get addresses from IRC and advertise ours
1627 if (!CreateThread(ThreadIRCSeed, NULL))
1628 printf("Error: CreateThread(ThreadIRCSeed) failed\n");
1630 // Send and receive from sockets, accept connections
1631 if (!CreateThread(ThreadSocketHandler, NULL))
1632 printf("Error: CreateThread(ThreadSocketHandler) failed\n");
1634 // Initiate outbound connections
1635 if (!CreateThread(ThreadOpenConnections, NULL))
1636 printf("Error: CreateThread(ThreadOpenConnections) failed\n");
1639 if (!CreateThread(ThreadMessageHandler, NULL))
1640 printf("Error: CreateThread(ThreadMessageHandler) failed\n");
1642 // Generate coins in the background
1643 GenerateBitcoins(fGenerateBitcoins, pwalletMain);
1648 printf("StopNode()\n");
1650 nTransactionsUpdated++;
1651 int64 nStart = GetTime();
1652 while (vnThreadsRunning[0] > 0 || vnThreadsRunning[2] > 0 || vnThreadsRunning[3] > 0 || vnThreadsRunning[4] > 0
1654 || vnThreadsRunning[5] > 0
1658 if (GetTime() - nStart > 20)
1662 if (vnThreadsRunning[0] > 0) printf("ThreadSocketHandler still running\n");
1663 if (vnThreadsRunning[1] > 0) printf("ThreadOpenConnections still running\n");
1664 if (vnThreadsRunning[2] > 0) printf("ThreadMessageHandler still running\n");
1665 if (vnThreadsRunning[3] > 0) printf("ThreadBitcoinMiner still running\n");
1666 if (vnThreadsRunning[4] > 0) printf("ThreadRPCServer still running\n");
1667 if (fHaveUPnP && vnThreadsRunning[5] > 0) printf("ThreadMapPort still running\n");
1668 if (vnThreadsRunning[6] > 0) printf("ThreadDNSAddressSeed still running\n");
1669 while (vnThreadsRunning[2] > 0 || vnThreadsRunning[4] > 0)
1685 BOOST_FOREACH(CNode* pnode, vNodes)
1686 if (pnode->hSocket != INVALID_SOCKET)
1687 closesocket(pnode->hSocket);
1688 if (hListenSocket != INVALID_SOCKET)
1689 if (closesocket(hListenSocket) == SOCKET_ERROR)
1690 printf("closesocket(hListenSocket) failed with error %d\n", WSAGetLastError());
1693 // Shutdown Windows Sockets
1698 instance_of_cnetcleanup;