Update License in File Headers
[novacoin.git] / src / net.cpp
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 COPYING or http://www.opensource.org/licenses/mit-license.php.
5
6 #include "headers.h"
7 #include "irc.h"
8 #include "db.h"
9 #include "net.h"
10 #include "init.h"
11 #include "strlcpy.h"
12 #include "addrman.h"
13
14 #ifdef WIN32
15 #include <string.h>
16 #else
17 #include <netinet/in.h>
18 #endif
19
20 #ifdef USE_UPNP
21 #include <miniupnpc/miniwget.h>
22 #include <miniupnpc/miniupnpc.h>
23 #include <miniupnpc/upnpcommands.h>
24 #include <miniupnpc/upnperrors.h>
25 #endif
26
27 using namespace std;
28 using namespace boost;
29
30 static const int MAX_OUTBOUND_CONNECTIONS = 8;
31
32 void ThreadMessageHandler2(void* parg);
33 void ThreadSocketHandler2(void* parg);
34 void ThreadOpenConnections2(void* parg);
35 void ThreadOpenAddedConnections2(void* parg);
36 #ifdef USE_UPNP
37 void ThreadMapPort2(void* parg);
38 #endif
39 void ThreadDNSAddressSeed2(void* parg);
40 bool OpenNetworkConnection(const CAddress& addrConnect);
41
42
43
44 //
45 // Global state variables
46 //
47 bool fClient = false;
48 bool fAllowDNS = false;
49 static bool fUseUPnP = false;
50 uint64 nLocalServices = (fClient ? 0 : NODE_NETWORK);
51 CAddress addrLocalHost(CService("0.0.0.0", 0), nLocalServices);
52 static CNode* pnodeLocalHost = NULL;
53 uint64 nLocalHostNonce = 0;
54 array<int, THREAD_MAX> vnThreadsRunning;
55 static SOCKET hListenSocket = INVALID_SOCKET;
56 CAddrMan addrman;
57
58 vector<CNode*> vNodes;
59 CCriticalSection cs_vNodes;
60 map<CInv, CDataStream> mapRelay;
61 deque<pair<int64, CInv> > vRelayExpiration;
62 CCriticalSection cs_mapRelay;
63 map<CInv, int64> mapAlreadyAskedFor;
64
65
66 set<CNetAddr> setservAddNodeAddresses;
67 CCriticalSection cs_setservAddNodeAddresses;
68
69
70
71 unsigned short GetListenPort()
72 {
73     return (unsigned short)(GetArg("-port", GetDefaultPort()));
74 }
75
76 void CNode::PushGetBlocks(CBlockIndex* pindexBegin, uint256 hashEnd)
77 {
78     // Filter out duplicate requests
79     if (pindexBegin == pindexLastGetBlocksBegin && hashEnd == hashLastGetBlocksEnd)
80         return;
81     pindexLastGetBlocksBegin = pindexBegin;
82     hashLastGetBlocksEnd = hashEnd;
83
84     PushMessage("getblocks", CBlockLocator(pindexBegin), hashEnd);
85 }
86
87
88
89 bool RecvLine(SOCKET hSocket, string& strLine)
90 {
91     strLine = "";
92     loop
93     {
94         char c;
95         int nBytes = recv(hSocket, &c, 1, 0);
96         if (nBytes > 0)
97         {
98             if (c == '\n')
99                 continue;
100             if (c == '\r')
101                 return true;
102             strLine += c;
103             if (strLine.size() >= 9000)
104                 return true;
105         }
106         else if (nBytes <= 0)
107         {
108             if (fShutdown)
109                 return false;
110             if (nBytes < 0)
111             {
112                 int nErr = WSAGetLastError();
113                 if (nErr == WSAEMSGSIZE)
114                     continue;
115                 if (nErr == WSAEWOULDBLOCK || nErr == WSAEINTR || nErr == WSAEINPROGRESS)
116                 {
117                     Sleep(10);
118                     continue;
119                 }
120             }
121             if (!strLine.empty())
122                 return true;
123             if (nBytes == 0)
124             {
125                 // socket closed
126                 printf("socket closed\n");
127                 return false;
128             }
129             else
130             {
131                 // socket error
132                 int nErr = WSAGetLastError();
133                 printf("recv failed: %d\n", nErr);
134                 return false;
135             }
136         }
137     }
138 }
139
140
141
142 bool GetMyExternalIP2(const CService& addrConnect, const char* pszGet, const char* pszKeyword, CNetAddr& ipRet)
143 {
144     SOCKET hSocket;
145     if (!ConnectSocket(addrConnect, hSocket))
146         return error("GetMyExternalIP() : connection to %s failed", addrConnect.ToString().c_str());
147
148     send(hSocket, pszGet, strlen(pszGet), MSG_NOSIGNAL);
149
150     string strLine;
151     while (RecvLine(hSocket, strLine))
152     {
153         if (strLine.empty()) // HTTP response is separated from headers by blank line
154         {
155             loop
156             {
157                 if (!RecvLine(hSocket, strLine))
158                 {
159                     closesocket(hSocket);
160                     return false;
161                 }
162                 if (pszKeyword == NULL)
163                     break;
164                 if (strLine.find(pszKeyword) != string::npos)
165                 {
166                     strLine = strLine.substr(strLine.find(pszKeyword) + strlen(pszKeyword));
167                     break;
168                 }
169             }
170             closesocket(hSocket);
171             if (strLine.find("<") != string::npos)
172                 strLine = strLine.substr(0, strLine.find("<"));
173             strLine = strLine.substr(strspn(strLine.c_str(), " \t\n\r"));
174             while (strLine.size() > 0 && isspace(strLine[strLine.size()-1]))
175                 strLine.resize(strLine.size()-1);
176             CService addr(strLine,0,true);
177             printf("GetMyExternalIP() received [%s] %s\n", strLine.c_str(), addr.ToString().c_str());
178             if (!addr.IsValid() || !addr.IsRoutable())
179                 return false;
180             ipRet.SetIP(addr);
181             return true;
182         }
183     }
184     closesocket(hSocket);
185     return error("GetMyExternalIP() : connection closed");
186 }
187
188 // We now get our external IP from the IRC server first and only use this as a backup
189 bool GetMyExternalIP(CNetAddr& ipRet)
190 {
191     CService addrConnect;
192     const char* pszGet;
193     const char* pszKeyword;
194
195     if (fNoListen||fUseProxy)
196         return false;
197
198     for (int nLookup = 0; nLookup <= 1; nLookup++)
199     for (int nHost = 1; nHost <= 2; nHost++)
200     {
201         // We should be phasing out our use of sites like these.  If we need
202         // replacements, we should ask for volunteers to put this simple
203         // php file on their webserver that prints the client IP:
204         //  <?php echo $_SERVER["REMOTE_ADDR"]; ?>
205         if (nHost == 1)
206         {
207             addrConnect = CService("91.198.22.70",80); // checkip.dyndns.org
208
209             if (nLookup == 1)
210             {
211                 CService addrIP("checkip.dyndns.org", 80, true);
212                 if (addrIP.IsValid())
213                     addrConnect = addrIP;
214             }
215
216             pszGet = "GET / HTTP/1.1\r\n"
217                      "Host: checkip.dyndns.org\r\n"
218                      "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
219                      "Connection: close\r\n"
220                      "\r\n";
221
222             pszKeyword = "Address:";
223         }
224         else if (nHost == 2)
225         {
226             addrConnect = CService("74.208.43.192", 80); // www.showmyip.com
227
228             if (nLookup == 1)
229             {
230                 CService addrIP("www.showmyip.com", 80, true);
231                 if (addrIP.IsValid())
232                     addrConnect = addrIP;
233             }
234
235             pszGet = "GET /simple/ HTTP/1.1\r\n"
236                      "Host: www.showmyip.com\r\n"
237                      "User-Agent: Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1)\r\n"
238                      "Connection: close\r\n"
239                      "\r\n";
240
241             pszKeyword = NULL; // Returns just IP address
242         }
243
244         if (GetMyExternalIP2(addrConnect, pszGet, pszKeyword, ipRet))
245             return true;
246     }
247
248     return false;
249 }
250
251 void ThreadGetMyExternalIP(void* parg)
252 {
253     // Wait for IRC to get it first
254     if (GetBoolArg("-irc", false))
255     {
256         for (int i = 0; i < 2 * 60; i++)
257         {
258             Sleep(1000);
259             if (fGotExternalIP || fShutdown)
260                 return;
261         }
262     }
263
264     // Fallback in case IRC fails to get it
265     if (GetMyExternalIP(addrLocalHost))
266     {
267         printf("GetMyExternalIP() returned %s\n", addrLocalHost.ToStringIP().c_str());
268         if (addrLocalHost.IsRoutable())
269         {
270             // If we already connected to a few before we had our IP, go back and addr them.
271             // setAddrKnown automatically filters any duplicate sends.
272             CAddress addr(addrLocalHost);
273             addr.nTime = GetAdjustedTime();
274             CRITICAL_BLOCK(cs_vNodes)
275                 BOOST_FOREACH(CNode* pnode, vNodes)
276                     pnode->PushAddress(addr);
277         }
278     }
279 }
280
281
282
283
284
285 void AddressCurrentlyConnected(const CService& addr)
286 {
287     addrman.Connected(addr);
288 }
289
290
291
292
293
294 void AbandonRequests(void (*fn)(void*, CDataStream&), void* param1)
295 {
296     // If the dialog might get closed before the reply comes back,
297     // call this in the destructor so it doesn't get called after it's deleted.
298     CRITICAL_BLOCK(cs_vNodes)
299     {
300         BOOST_FOREACH(CNode* pnode, vNodes)
301         {
302             CRITICAL_BLOCK(pnode->cs_mapRequests)
303             {
304                 for (map<uint256, CRequestTracker>::iterator mi = pnode->mapRequests.begin(); mi != pnode->mapRequests.end();)
305                 {
306                     CRequestTracker& tracker = (*mi).second;
307                     if (tracker.fn == fn && tracker.param1 == param1)
308                         pnode->mapRequests.erase(mi++);
309                     else
310                         mi++;
311                 }
312             }
313         }
314     }
315 }
316
317
318
319
320
321
322
323 //
324 // Subscription methods for the broadcast and subscription system.
325 // Channel numbers are message numbers, i.e. MSG_TABLE and MSG_PRODUCT.
326 //
327 // The subscription system uses a meet-in-the-middle strategy.
328 // With 100,000 nodes, if senders broadcast to 1000 random nodes and receivers
329 // subscribe to 1000 random nodes, 99.995% (1 - 0.99^1000) of messages will get through.
330 //
331
332 bool AnySubscribed(unsigned int nChannel)
333 {
334     if (pnodeLocalHost->IsSubscribed(nChannel))
335         return true;
336     CRITICAL_BLOCK(cs_vNodes)
337         BOOST_FOREACH(CNode* pnode, vNodes)
338             if (pnode->IsSubscribed(nChannel))
339                 return true;
340     return false;
341 }
342
343 bool CNode::IsSubscribed(unsigned int nChannel)
344 {
345     if (nChannel >= vfSubscribe.size())
346         return false;
347     return vfSubscribe[nChannel];
348 }
349
350 void CNode::Subscribe(unsigned int nChannel, unsigned int nHops)
351 {
352     if (nChannel >= vfSubscribe.size())
353         return;
354
355     if (!AnySubscribed(nChannel))
356     {
357         // Relay subscribe
358         CRITICAL_BLOCK(cs_vNodes)
359             BOOST_FOREACH(CNode* pnode, vNodes)
360                 if (pnode != this)
361                     pnode->PushMessage("subscribe", nChannel, nHops);
362     }
363
364     vfSubscribe[nChannel] = true;
365 }
366
367 void CNode::CancelSubscribe(unsigned int nChannel)
368 {
369     if (nChannel >= vfSubscribe.size())
370         return;
371
372     // Prevent from relaying cancel if wasn't subscribed
373     if (!vfSubscribe[nChannel])
374         return;
375     vfSubscribe[nChannel] = false;
376
377     if (!AnySubscribed(nChannel))
378     {
379         // Relay subscription cancel
380         CRITICAL_BLOCK(cs_vNodes)
381             BOOST_FOREACH(CNode* pnode, vNodes)
382                 if (pnode != this)
383                     pnode->PushMessage("sub-cancel", nChannel);
384     }
385 }
386
387
388
389
390
391
392
393
394
395 CNode* FindNode(const CNetAddr& ip)
396 {
397     CRITICAL_BLOCK(cs_vNodes)
398     {
399         BOOST_FOREACH(CNode* pnode, vNodes)
400             if ((CNetAddr)pnode->addr == ip)
401                 return (pnode);
402     }
403     return NULL;
404 }
405
406 CNode* FindNode(const CService& addr)
407 {
408     CRITICAL_BLOCK(cs_vNodes)
409     {
410         BOOST_FOREACH(CNode* pnode, vNodes)
411             if ((CService)pnode->addr == addr)
412                 return (pnode);
413     }
414     return NULL;
415 }
416
417 CNode* ConnectNode(CAddress addrConnect, int64 nTimeout)
418 {
419     if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost)
420         return NULL;
421
422     // Look for an existing connection
423     CNode* pnode = FindNode((CService)addrConnect);
424     if (pnode)
425     {
426         if (nTimeout != 0)
427             pnode->AddRef(nTimeout);
428         else
429             pnode->AddRef();
430         return pnode;
431     }
432
433     /// debug print
434     printf("trying connection %s lastseen=%.1fhrs\n",
435         addrConnect.ToString().c_str(),
436         (double)(addrConnect.nTime - GetAdjustedTime())/3600.0);
437
438     addrman.Attempt(addrConnect);
439
440     // Connect
441     SOCKET hSocket;
442     if (ConnectSocket(addrConnect, hSocket))
443     {
444         /// debug print
445         printf("connected %s\n", addrConnect.ToString().c_str());
446
447         // Set to nonblocking
448 #ifdef WIN32
449         u_long nOne = 1;
450         if (ioctlsocket(hSocket, FIONBIO, &nOne) == SOCKET_ERROR)
451             printf("ConnectSocket() : ioctlsocket nonblocking setting failed, error %d\n", WSAGetLastError());
452 #else
453         if (fcntl(hSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
454             printf("ConnectSocket() : fcntl nonblocking setting failed, error %d\n", errno);
455 #endif
456
457         // Add node
458         CNode* pnode = new CNode(hSocket, addrConnect, false);
459         if (nTimeout != 0)
460             pnode->AddRef(nTimeout);
461         else
462             pnode->AddRef();
463         CRITICAL_BLOCK(cs_vNodes)
464             vNodes.push_back(pnode);
465
466         pnode->nTimeConnected = GetTime();
467         return pnode;
468     }
469     else
470     {
471         return NULL;
472     }
473 }
474
475 void CNode::CloseSocketDisconnect()
476 {
477     fDisconnect = true;
478     if (hSocket != INVALID_SOCKET)
479     {
480         if (fDebug)
481             printf("%s ", DateTimeStrFormat("%x %H:%M:%S", GetTime()).c_str());
482         printf("disconnecting node %s\n", addr.ToString().c_str());
483         closesocket(hSocket);
484         hSocket = INVALID_SOCKET;
485         vRecv.clear();
486     }
487 }
488
489 void CNode::Cleanup()
490 {
491     // All of a nodes broadcasts and subscriptions are automatically torn down
492     // when it goes down, so a node has to stay up to keep its broadcast going.
493
494     // Cancel subscriptions
495     for (unsigned int nChannel = 0; nChannel < vfSubscribe.size(); nChannel++)
496         if (vfSubscribe[nChannel])
497             CancelSubscribe(nChannel);
498 }
499
500
501 void CNode::PushVersion()
502 {
503     /// when NTP implemented, change to just nTime = GetAdjustedTime()
504     int64 nTime = (fInbound ? GetAdjustedTime() : GetTime());
505     CAddress addrYou = (fUseProxy ? CAddress(CService("0.0.0.0",0)) : addr);
506     CAddress addrMe = (fUseProxy || !addrLocalHost.IsRoutable() ? CAddress(CService("0.0.0.0",0)) : addrLocalHost);
507     RAND_bytes((unsigned char*)&nLocalHostNonce, sizeof(nLocalHostNonce));
508     PushMessage("version", PROTOCOL_VERSION, nLocalServices, nTime, addrYou, addrMe,
509                 nLocalHostNonce, FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<string>()), nBestHeight);
510 }
511
512
513
514
515
516 std::map<CNetAddr, int64> CNode::setBanned;
517 CCriticalSection CNode::cs_setBanned;
518
519 void CNode::ClearBanned()
520 {
521     setBanned.clear();
522 }
523
524 bool CNode::IsBanned(CNetAddr ip)
525 {
526     bool fResult = false;
527     CRITICAL_BLOCK(cs_setBanned)
528     {
529         std::map<CNetAddr, int64>::iterator i = setBanned.find(ip);
530         if (i != setBanned.end())
531         {
532             int64 t = (*i).second;
533             if (GetTime() < t)
534                 fResult = true;
535         }
536     }
537     return fResult;
538 }
539
540 bool CNode::Misbehaving(int howmuch)
541 {
542     if (addr.IsLocal())
543     {
544         printf("Warning: local node %s misbehaving\n", addr.ToString().c_str());
545         return false;
546     }
547
548     nMisbehavior += howmuch;
549     if (nMisbehavior >= GetArg("-banscore", 100))
550     {
551         int64 banTime = GetTime()+GetArg("-bantime", 60*60*24);  // Default 24-hour ban
552         CRITICAL_BLOCK(cs_setBanned)
553             if (setBanned[addr] < banTime)
554                 setBanned[addr] = banTime;
555         CloseSocketDisconnect();
556         printf("Disconnected %s for misbehavior (score=%d)\n", addr.ToString().c_str(), nMisbehavior);
557         return true;
558     }
559     return false;
560 }
561
562
563
564
565
566
567
568
569
570
571
572
573 void ThreadSocketHandler(void* parg)
574 {
575     IMPLEMENT_RANDOMIZE_STACK(ThreadSocketHandler(parg));
576     try
577     {
578         vnThreadsRunning[THREAD_SOCKETHANDLER]++;
579         ThreadSocketHandler2(parg);
580         vnThreadsRunning[THREAD_SOCKETHANDLER]--;
581     }
582     catch (std::exception& e) {
583         vnThreadsRunning[THREAD_SOCKETHANDLER]--;
584         PrintException(&e, "ThreadSocketHandler()");
585     } catch (...) {
586         vnThreadsRunning[THREAD_SOCKETHANDLER]--;
587         throw; // support pthread_cancel()
588     }
589     printf("ThreadSocketHandler exiting\n");
590 }
591
592 void ThreadSocketHandler2(void* parg)
593 {
594     printf("ThreadSocketHandler started\n");
595     list<CNode*> vNodesDisconnected;
596     int nPrevNodeCount = 0;
597
598     loop
599     {
600         //
601         // Disconnect nodes
602         //
603         CRITICAL_BLOCK(cs_vNodes)
604         {
605             // Disconnect unused nodes
606             vector<CNode*> vNodesCopy = vNodes;
607             BOOST_FOREACH(CNode* pnode, vNodesCopy)
608             {
609                 if (pnode->fDisconnect ||
610                     (pnode->GetRefCount() <= 0 && pnode->vRecv.empty() && pnode->vSend.empty()))
611                 {
612                     // remove from vNodes
613                     vNodes.erase(remove(vNodes.begin(), vNodes.end(), pnode), vNodes.end());
614
615                     // close socket and cleanup
616                     pnode->CloseSocketDisconnect();
617                     pnode->Cleanup();
618
619                     // hold in disconnected pool until all refs are released
620                     pnode->nReleaseTime = max(pnode->nReleaseTime, GetTime() + 15 * 60);
621                     if (pnode->fNetworkNode || pnode->fInbound)
622                         pnode->Release();
623                     vNodesDisconnected.push_back(pnode);
624                 }
625             }
626
627             // Delete disconnected nodes
628             list<CNode*> vNodesDisconnectedCopy = vNodesDisconnected;
629             BOOST_FOREACH(CNode* pnode, vNodesDisconnectedCopy)
630             {
631                 // wait until threads are done using it
632                 if (pnode->GetRefCount() <= 0)
633                 {
634                     bool fDelete = false;
635                     TRY_CRITICAL_BLOCK(pnode->cs_vSend)
636                      TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
637                       TRY_CRITICAL_BLOCK(pnode->cs_mapRequests)
638                        TRY_CRITICAL_BLOCK(pnode->cs_inventory)
639                         fDelete = true;
640                     if (fDelete)
641                     {
642                         vNodesDisconnected.remove(pnode);
643                         delete pnode;
644                     }
645                 }
646             }
647         }
648         if (vNodes.size() != nPrevNodeCount)
649         {
650             nPrevNodeCount = vNodes.size();
651             MainFrameRepaint();
652         }
653
654
655         //
656         // Find which sockets have data to receive
657         //
658         struct timeval timeout;
659         timeout.tv_sec  = 0;
660         timeout.tv_usec = 50000; // frequency to poll pnode->vSend
661
662         fd_set fdsetRecv;
663         fd_set fdsetSend;
664         fd_set fdsetError;
665         FD_ZERO(&fdsetRecv);
666         FD_ZERO(&fdsetSend);
667         FD_ZERO(&fdsetError);
668         SOCKET hSocketMax = 0;
669
670         if(hListenSocket != INVALID_SOCKET)
671             FD_SET(hListenSocket, &fdsetRecv);
672         hSocketMax = max(hSocketMax, hListenSocket);
673         CRITICAL_BLOCK(cs_vNodes)
674         {
675             BOOST_FOREACH(CNode* pnode, vNodes)
676             {
677                 if (pnode->hSocket == INVALID_SOCKET)
678                     continue;
679                 FD_SET(pnode->hSocket, &fdsetRecv);
680                 FD_SET(pnode->hSocket, &fdsetError);
681                 hSocketMax = max(hSocketMax, pnode->hSocket);
682                 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
683                     if (!pnode->vSend.empty())
684                         FD_SET(pnode->hSocket, &fdsetSend);
685             }
686         }
687
688         vnThreadsRunning[THREAD_SOCKETHANDLER]--;
689         int nSelect = select(hSocketMax + 1, &fdsetRecv, &fdsetSend, &fdsetError, &timeout);
690         vnThreadsRunning[THREAD_SOCKETHANDLER]++;
691         if (fShutdown)
692             return;
693         if (nSelect == SOCKET_ERROR)
694         {
695             int nErr = WSAGetLastError();
696             if (hSocketMax > -1)
697             {
698                 printf("socket select error %d\n", nErr);
699                 for (unsigned int i = 0; i <= hSocketMax; i++)
700                     FD_SET(i, &fdsetRecv);
701             }
702             FD_ZERO(&fdsetSend);
703             FD_ZERO(&fdsetError);
704             Sleep(timeout.tv_usec/1000);
705         }
706
707
708         //
709         // Accept new connections
710         //
711         if (hListenSocket != INVALID_SOCKET && FD_ISSET(hListenSocket, &fdsetRecv))
712         {
713             struct sockaddr_in sockaddr;
714             socklen_t len = sizeof(sockaddr);
715             SOCKET hSocket = accept(hListenSocket, (struct sockaddr*)&sockaddr, &len);
716             CAddress addr;
717             int nInbound = 0;
718
719             if (hSocket != INVALID_SOCKET)
720                 addr = CAddress(sockaddr);
721
722             CRITICAL_BLOCK(cs_vNodes)
723                 BOOST_FOREACH(CNode* pnode, vNodes)
724                 if (pnode->fInbound)
725                     nInbound++;
726
727             if (hSocket == INVALID_SOCKET)
728             {
729                 if (WSAGetLastError() != WSAEWOULDBLOCK)
730                     printf("socket error accept failed: %d\n", WSAGetLastError());
731             }
732             else if (nInbound >= GetArg("-maxconnections", 125) - MAX_OUTBOUND_CONNECTIONS)
733             {
734                 CRITICAL_BLOCK(cs_setservAddNodeAddresses)
735                     if (!setservAddNodeAddresses.count(addr))
736                         closesocket(hSocket);
737             }
738             else if (CNode::IsBanned(addr))
739             {
740                 printf("connection from %s dropped (banned)\n", addr.ToString().c_str());
741                 closesocket(hSocket);
742             }
743             else
744             {
745                 printf("accepted connection %s\n", addr.ToString().c_str());
746                 CNode* pnode = new CNode(hSocket, addr, true);
747                 pnode->AddRef();
748                 CRITICAL_BLOCK(cs_vNodes)
749                     vNodes.push_back(pnode);
750             }
751         }
752
753
754         //
755         // Service each socket
756         //
757         vector<CNode*> vNodesCopy;
758         CRITICAL_BLOCK(cs_vNodes)
759         {
760             vNodesCopy = vNodes;
761             BOOST_FOREACH(CNode* pnode, vNodesCopy)
762                 pnode->AddRef();
763         }
764         BOOST_FOREACH(CNode* pnode, vNodesCopy)
765         {
766             if (fShutdown)
767                 return;
768
769             //
770             // Receive
771             //
772             if (pnode->hSocket == INVALID_SOCKET)
773                 continue;
774             if (FD_ISSET(pnode->hSocket, &fdsetRecv) || FD_ISSET(pnode->hSocket, &fdsetError))
775             {
776                 TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
777                 {
778                     CDataStream& vRecv = pnode->vRecv;
779                     unsigned int nPos = vRecv.size();
780
781                     if (nPos > ReceiveBufferSize()) {
782                         if (!pnode->fDisconnect)
783                             printf("socket recv flood control disconnect (%d bytes)\n", vRecv.size());
784                         pnode->CloseSocketDisconnect();
785                     }
786                     else {
787                         // typical socket buffer is 8K-64K
788                         char pchBuf[0x10000];
789                         int nBytes = recv(pnode->hSocket, pchBuf, sizeof(pchBuf), MSG_DONTWAIT);
790                         if (nBytes > 0)
791                         {
792                             vRecv.resize(nPos + nBytes);
793                             memcpy(&vRecv[nPos], pchBuf, nBytes);
794                             pnode->nLastRecv = GetTime();
795                         }
796                         else if (nBytes == 0)
797                         {
798                             // socket closed gracefully
799                             if (!pnode->fDisconnect)
800                                 printf("socket closed\n");
801                             pnode->CloseSocketDisconnect();
802                         }
803                         else if (nBytes < 0)
804                         {
805                             // error
806                             int nErr = WSAGetLastError();
807                             if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
808                             {
809                                 if (!pnode->fDisconnect)
810                                     printf("socket recv error %d\n", nErr);
811                                 pnode->CloseSocketDisconnect();
812                             }
813                         }
814                     }
815                 }
816             }
817
818             //
819             // Send
820             //
821             if (pnode->hSocket == INVALID_SOCKET)
822                 continue;
823             if (FD_ISSET(pnode->hSocket, &fdsetSend))
824             {
825                 TRY_CRITICAL_BLOCK(pnode->cs_vSend)
826                 {
827                     CDataStream& vSend = pnode->vSend;
828                     if (!vSend.empty())
829                     {
830                         int nBytes = send(pnode->hSocket, &vSend[0], vSend.size(), MSG_NOSIGNAL | MSG_DONTWAIT);
831                         if (nBytes > 0)
832                         {
833                             vSend.erase(vSend.begin(), vSend.begin() + nBytes);
834                             pnode->nLastSend = GetTime();
835                         }
836                         else if (nBytes < 0)
837                         {
838                             // error
839                             int nErr = WSAGetLastError();
840                             if (nErr != WSAEWOULDBLOCK && nErr != WSAEMSGSIZE && nErr != WSAEINTR && nErr != WSAEINPROGRESS)
841                             {
842                                 printf("socket send error %d\n", nErr);
843                                 pnode->CloseSocketDisconnect();
844                             }
845                         }
846                         if (vSend.size() > SendBufferSize()) {
847                             if (!pnode->fDisconnect)
848                                 printf("socket send flood control disconnect (%d bytes)\n", vSend.size());
849                             pnode->CloseSocketDisconnect();
850                         }
851                     }
852                 }
853             }
854
855             //
856             // Inactivity checking
857             //
858             if (pnode->vSend.empty())
859                 pnode->nLastSendEmpty = GetTime();
860             if (GetTime() - pnode->nTimeConnected > 60)
861             {
862                 if (pnode->nLastRecv == 0 || pnode->nLastSend == 0)
863                 {
864                     printf("socket no message in first 60 seconds, %d %d\n", pnode->nLastRecv != 0, pnode->nLastSend != 0);
865                     pnode->fDisconnect = true;
866                 }
867                 else if (GetTime() - pnode->nLastSend > 90*60 && GetTime() - pnode->nLastSendEmpty > 90*60)
868                 {
869                     printf("socket not sending\n");
870                     pnode->fDisconnect = true;
871                 }
872                 else if (GetTime() - pnode->nLastRecv > 90*60)
873                 {
874                     printf("socket inactivity timeout\n");
875                     pnode->fDisconnect = true;
876                 }
877             }
878         }
879         CRITICAL_BLOCK(cs_vNodes)
880         {
881             BOOST_FOREACH(CNode* pnode, vNodesCopy)
882                 pnode->Release();
883         }
884
885         Sleep(10);
886     }
887 }
888
889
890
891
892
893
894
895
896
897 #ifdef USE_UPNP
898 void ThreadMapPort(void* parg)
899 {
900     IMPLEMENT_RANDOMIZE_STACK(ThreadMapPort(parg));
901     try
902     {
903         vnThreadsRunning[THREAD_UPNP]++;
904         ThreadMapPort2(parg);
905         vnThreadsRunning[THREAD_UPNP]--;
906     }
907     catch (std::exception& e) {
908         vnThreadsRunning[THREAD_UPNP]--;
909         PrintException(&e, "ThreadMapPort()");
910     } catch (...) {
911         vnThreadsRunning[THREAD_UPNP]--;
912         PrintException(NULL, "ThreadMapPort()");
913     }
914     printf("ThreadMapPort exiting\n");
915 }
916
917 void ThreadMapPort2(void* parg)
918 {
919     printf("ThreadMapPort started\n");
920
921     char port[6];
922     sprintf(port, "%d", GetListenPort());
923
924     const char * multicastif = 0;
925     const char * minissdpdpath = 0;
926     struct UPNPDev * devlist = 0;
927     char lanaddr[64];
928
929 #ifndef UPNPDISCOVER_SUCCESS
930     /* miniupnpc 1.5 */
931     devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0);
932 #else
933     /* miniupnpc 1.6 */
934     int error = 0;
935     devlist = upnpDiscover(2000, multicastif, minissdpdpath, 0, 0, &error);
936 #endif
937
938     struct UPNPUrls urls;
939     struct IGDdatas data;
940     int r;
941
942     r = UPNP_GetValidIGD(devlist, &urls, &data, lanaddr, sizeof(lanaddr));
943     if (r == 1)
944     {
945         if (!addrLocalHost.IsRoutable())
946         {
947             char externalIPAddress[40];
948             r = UPNP_GetExternalIPAddress(urls.controlURL, data.first.servicetype, externalIPAddress);
949             if(r != UPNPCOMMAND_SUCCESS)
950                 printf("UPnP: GetExternalIPAddress() returned %d\n", r);
951             else
952             {
953                 if(externalIPAddress[0])
954                 {
955                     printf("UPnP: ExternalIPAddress = %s\n", externalIPAddress);
956                     CAddress addrExternalFromUPnP(CService(externalIPAddress, 0), nLocalServices);
957                     if (addrExternalFromUPnP.IsRoutable())
958                         addrLocalHost = addrExternalFromUPnP;
959                 }
960                 else
961                     printf("UPnP: GetExternalIPAddress failed.\n");
962             }
963         }
964
965         string strDesc = "Bitcoin " + FormatFullVersion();
966 #ifndef UPNPDISCOVER_SUCCESS
967         /* miniupnpc 1.5 */
968         r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
969                             port, port, lanaddr, strDesc.c_str(), "TCP", 0);
970 #else
971         /* miniupnpc 1.6 */
972         r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
973                             port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
974 #endif
975
976         if(r!=UPNPCOMMAND_SUCCESS)
977             printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
978                 port, port, lanaddr, r, strupnperror(r));
979         else
980             printf("UPnP Port Mapping successful.\n");
981         int i = 1;
982         loop {
983             if (fShutdown || !fUseUPnP)
984             {
985                 r = UPNP_DeletePortMapping(urls.controlURL, data.first.servicetype, port, "TCP", 0);
986                 printf("UPNP_DeletePortMapping() returned : %d\n", r);
987                 freeUPNPDevlist(devlist); devlist = 0;
988                 FreeUPNPUrls(&urls);
989                 return;
990             }
991             if (i % 600 == 0) // Refresh every 20 minutes
992             {
993 #ifndef UPNPDISCOVER_SUCCESS
994                 /* miniupnpc 1.5 */
995                 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
996                                     port, port, lanaddr, strDesc.c_str(), "TCP", 0);
997 #else
998                 /* miniupnpc 1.6 */
999                 r = UPNP_AddPortMapping(urls.controlURL, data.first.servicetype,
1000                                     port, port, lanaddr, strDesc.c_str(), "TCP", 0, "0");
1001 #endif
1002
1003                 if(r!=UPNPCOMMAND_SUCCESS)
1004                     printf("AddPortMapping(%s, %s, %s) failed with code %d (%s)\n",
1005                         port, port, lanaddr, r, strupnperror(r));
1006                 else
1007                     printf("UPnP Port Mapping successful.\n");;
1008             }
1009             Sleep(2000);
1010             i++;
1011         }
1012     } else {
1013         printf("No valid UPnP IGDs found\n");
1014         freeUPNPDevlist(devlist); devlist = 0;
1015         if (r != 0)
1016             FreeUPNPUrls(&urls);
1017         loop {
1018             if (fShutdown || !fUseUPnP)
1019                 return;
1020             Sleep(2000);
1021         }
1022     }
1023 }
1024
1025 void MapPort(bool fMapPort)
1026 {
1027     if (fUseUPnP != fMapPort)
1028     {
1029         fUseUPnP = fMapPort;
1030     }
1031     if (fUseUPnP && vnThreadsRunning[THREAD_UPNP] < 1)
1032     {
1033         if (!CreateThread(ThreadMapPort, NULL))
1034             printf("Error: ThreadMapPort(ThreadMapPort) failed\n");
1035     }
1036 }
1037 #else
1038 void MapPort(bool /* unused fMapPort */)
1039 {
1040     // Intentionally left blank.
1041 }
1042 #endif
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052 // DNS seeds
1053 // Each pair gives a source name and a seed name.
1054 // The first name is used as information source for addrman.
1055 // The second name should resolve to a list of seed addresses.
1056 static const char *strDNSSeed[][2] = {
1057     {"xf2.org", "bitseed.xf2.org"},
1058     {"bluematt.me", "dnsseed.bluematt.me"},
1059     {"bitcoin.sipa.be", "seed.bitcoin.sipa.be"},
1060     {"dashjr.org", "dnsseed.bitcoin.dashjr.org"},
1061 };
1062
1063 void ThreadDNSAddressSeed(void* parg)
1064 {
1065     IMPLEMENT_RANDOMIZE_STACK(ThreadDNSAddressSeed(parg));
1066     try
1067     {
1068         vnThreadsRunning[THREAD_DNSSEED]++;
1069         ThreadDNSAddressSeed2(parg);
1070         vnThreadsRunning[THREAD_DNSSEED]--;
1071     }
1072     catch (std::exception& e) {
1073         vnThreadsRunning[THREAD_DNSSEED]--;
1074         PrintException(&e, "ThreadDNSAddressSeed()");
1075     } catch (...) {
1076         vnThreadsRunning[THREAD_DNSSEED]--;
1077         throw; // support pthread_cancel()
1078     }
1079     printf("ThreadDNSAddressSeed exiting\n");
1080 }
1081
1082 void ThreadDNSAddressSeed2(void* parg)
1083 {
1084     printf("ThreadDNSAddressSeed started\n");
1085     int found = 0;
1086
1087     if (!fTestNet)
1088     {
1089         printf("Loading addresses from DNS seeds (could take a while)\n");
1090
1091         for (unsigned int seed_idx = 0; seed_idx < ARRAYLEN(strDNSSeed); seed_idx++) {
1092             vector<CNetAddr> vaddr;
1093             vector<CAddress> vAdd;
1094             if (LookupHost(strDNSSeed[seed_idx][1], vaddr))
1095             {
1096                 BOOST_FOREACH(CNetAddr& ip, vaddr)
1097                 {
1098                     int nOneDay = 24*3600;
1099                     CAddress addr = CAddress(CService(ip, GetDefaultPort()));
1100                     addr.nTime = GetTime() - 3*nOneDay - GetRand(4*nOneDay); // use a random age between 3 and 7 days old
1101                     vAdd.push_back(addr);
1102                     found++;
1103                 }
1104             }
1105             addrman.Add(vAdd, CNetAddr(strDNSSeed[seed_idx][0], true));
1106         }
1107     }
1108
1109     printf("%d addresses found from DNS seeds\n", found);
1110 }
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123 unsigned int pnSeed[] =
1124 {
1125     0x959bd347, 0xf8de42b2, 0x73bc0518, 0xea6edc50, 0x21b00a4d, 0xc725b43d, 0xd665464d, 0x1a2a770e,
1126     0x27c93946, 0x65b2fa46, 0xb80ae255, 0x66b3b446, 0xb1877a3e, 0x6ee89e3e, 0xc3175b40, 0x2a01a83c,
1127     0x95b1363a, 0xa079ad3d, 0xe6ca801f, 0x027f4f4a, 0x34f7f03a, 0xf790f04a, 0x16ca801f, 0x2f4d5e40,
1128     0x3a4d5e40, 0xc43a322e, 0xc8159753, 0x14d4724c, 0x7919a118, 0xe0bdb34e, 0x68a16b2e, 0xff64b44d,
1129     0x6099115b, 0x9b57b05b, 0x7bd1b4ad, 0xdf95944f, 0x29d2b73d, 0xafa8db79, 0xe247ba41, 0x24078348,
1130     0xf722f03c, 0x33567ebc, 0xace64ed4, 0x984d3932, 0xb5f34e55, 0x27b7024d, 0x94579247, 0x8894042e,
1131     0x9357d34c, 0x1063c24b, 0xcaa228b1, 0xa3c5a8b2, 0x5dc64857, 0xa2c23643, 0xa8369a54, 0x31203077,
1132     0x00707c5c, 0x09fc0b3a, 0x272e9e2e, 0xf80f043e, 0x9449ca3e, 0x5512c33e, 0xd106b555, 0xe8024157,
1133     0xe288ec29, 0xc79c5461, 0xafb63932, 0xdb02ab4b, 0x0e512777, 0x8a145a4c, 0xb201ff4f, 0x5e09314b,
1134     0xcd9bfbcd, 0x1c023765, 0x4394e75c, 0xa728bd4d, 0x65331552, 0xa98420b1, 0x89ecf559, 0x6e80801f,
1135     0xf404f118, 0xefd62b51, 0x05918346, 0x9b186d5f, 0xacabab46, 0xf912e255, 0xc188ea62, 0xcc55734e,
1136     0xc668064d, 0xd77a4558, 0x46201c55, 0xf17dfc80, 0xf7142f2e, 0x87bfb718, 0x8aa54fb2, 0xc451d518,
1137     0xc4ae8831, 0x8dd44d55, 0x5bbd206c, 0x64536b5d, 0x5c667e60, 0x3b064242, 0xfe963a42, 0xa28e6dc8,
1138     0xe8a9604a, 0xc989464e, 0xd124a659, 0x50065140, 0xa44dfe5e, 0x1079e655, 0x3fb986d5, 0x47895b18,
1139     0x7d3ce4ad, 0x4561ba50, 0x296eec62, 0x255b41ad, 0xaed35ec9, 0x55556f12, 0xc7d3154d, 0x3297b65d,
1140     0x8930121f, 0xabf42e4e, 0x4a29e044, 0x1212685d, 0x676c1e40, 0xce009744, 0x383a8948, 0xa2dbd0ad,
1141     0xecc2564d, 0x07dbc252, 0x887ee24b, 0x5171644c, 0x6bb798c1, 0x847f495d, 0x4cbb7145, 0x3bb81c32,
1142     0x45eb262e, 0xc8015a4e, 0x250a361b, 0xf694f946, 0xd64a183e, 0xd4f1dd59, 0x8f20ffd4, 0x51d9e55c,
1143     0x09521763, 0x5e02002e, 0x32c8074d, 0xe685762e, 0x8290b0bc, 0x762a922e, 0xfc5ee754, 0x83a24829,
1144     0x775b224d, 0x6295bb4d, 0x38ec0555, 0xbffbba50, 0xe5560260, 0x86b16a7c, 0xd372234e, 0x49a3c24b,
1145     0x2f6a171f, 0x4d75ed60, 0xae94115b, 0xcb543744, 0x63080c59, 0x3f9c724c, 0xc977ce18, 0x532efb18,
1146     0x69dc3b2e, 0x5f94d929, 0x1732bb4d, 0x9c814b4d, 0xe6b3762e, 0xc024f662, 0x8face35b, 0x6b5b044d,
1147     0x798c7b57, 0x79a6b44c, 0x067d3057, 0xf9e94e5f, 0x91cbe15b, 0x71405eb2, 0x2662234e, 0xcbcc4a6d,
1148     0xbf69d54b, 0xa79b4e55, 0xec6d3e51, 0x7c0b3c02, 0x60f83653, 0x24c1e15c, 0x1110b62e, 0x10350f59,
1149     0xa56f1d55, 0x3509e7a9, 0xeb128354, 0x14268e2e, 0x934e28bc, 0x8e32692e, 0x8331a21f, 0x3e633932,
1150     0xc812b12e, 0xc684bf2e, 0x80112d2e, 0xe0ddc96c, 0xc630ca4a, 0x5c09b3b2, 0x0b580518, 0xc8e9d54b,
1151     0xd169aa43, 0x17d0d655, 0x1d029963, 0x7ff87559, 0xcb701f1f, 0x6fa3e85d, 0xe45e9a54, 0xf05d1802,
1152     0x44d03b2e, 0x837b692e, 0xccd4354e, 0x3d6da13c, 0x3423084d, 0xf707c34a, 0x55f6db3a, 0xad26e442,
1153     0x6233a21f, 0x09e80e59, 0x8caeb54d, 0xbe870941, 0xb407d20e, 0x20b51018, 0x56fb152e, 0x460d2a4e,
1154     0xbb9a2946, 0x560eb12e, 0xed83dd29, 0xd6724f53, 0xa50aafb8, 0x451346d9, 0x88348e2e, 0x7312fead,
1155     0x8ecaf96f, 0x1bda4e5f, 0xf1671e40, 0x3c8c3e3b, 0x4716324d, 0xdde24ede, 0xf98cd17d, 0xa91d4644,
1156     0x28124eb2, 0x147d5129, 0xd022042e, 0x61733d3b, 0xad0d5e02, 0x8ce2932e, 0xe5c18502, 0x549c1e32,
1157     0x9685801f, 0x86e217ad, 0xd948214b, 0x4110f462, 0x3a2e894e, 0xbd35492e, 0x87e0d558, 0x64b8ef7d,
1158     0x7c3eb962, 0x72a84b3e, 0x7cd667c9, 0x28370a2e, 0x4bc60e7b, 0x6fc1ec60, 0x14a6983f, 0x86739a4b,
1159     0x46954e5f, 0x32e2e15c, 0x2e9326cf, 0xe5801c5e, 0x379607b2, 0x32151145, 0xf0e39744, 0xacb54c55,
1160     0xa37dfb60, 0x83b55cc9, 0x388f7ca5, 0x15034f5f, 0x3e94965b, 0x68e0ffad, 0x35280f59, 0x8fe190cf,
1161     0x7c6ba5b2, 0xa5e9db43, 0x4ee1fc60, 0xd9d94e5f, 0x04040677, 0x0ea9b35e, 0x5961f14f, 0x67fda063,
1162     0xa48a5a31, 0xc6524e55, 0x283d325e, 0x3f37515f, 0x96b94b3e, 0xacce620e, 0x6481cc5b, 0xa4a06d4b,
1163     0x9e95d2d9, 0xe40c03d5, 0xc2f4514b, 0xb79aad44, 0xf64be843, 0xb2064070, 0xfca00455, 0x429dfa4e,
1164     0x2323f173, 0xeda4185e, 0xabd5227d, 0x9efd4d58, 0xb1104758, 0x4811e955, 0xbd9ab355, 0xe921f44b,
1165     0x9f166dce, 0x09e279b2, 0xe0c9ac7b, 0x7901a5ad, 0xa145d4b0, 0x79104671, 0xec31e35a, 0x4fe0b555,
1166     0xc7d9cbad, 0xad057f55, 0xe94cc759, 0x7fe0b043, 0xe4529f2e, 0x0d4dd4b2, 0x9f11a54d, 0x031e2e4e,
1167     0xe6014f5f, 0x11d1ca6c, 0x26bd7f61, 0xeb86854f, 0x4d347b57, 0x116bbe2e, 0xdba7234e, 0x7bcbfd2e,
1168     0x174dd4b2, 0x6686762e, 0xb089ba50, 0xc6258246, 0x087e767b, 0xc4a8cb4a, 0x595dba50, 0x7f0ae502,
1169     0x7b1dbd5a, 0xa0603492, 0x57d1af4b, 0x9e21ffd4, 0x6393064d, 0x7407376e, 0xe484762e, 0x122a4e53,
1170     0x4a37aa43, 0x3888a6be, 0xee77864e, 0x039c8dd5, 0x688d89af, 0x0e988f62, 0x08218246, 0xfc2f8246,
1171     0xd1d97040, 0xd64cd4b2, 0x5ae4a6b8, 0x7d0de9bc, 0x8d304d61, 0x06c5c672, 0xa4c8bd4d, 0xe0fd373b,
1172     0x575ebe4d, 0x72d26277, 0x55570f55, 0x77b154d9, 0xe214293a, 0xfc740f4b, 0xfe3f6a57, 0xa9c55f02,
1173     0xae4054db, 0x2394d918, 0xb511b24a, 0xb8741ab2, 0x0758e65e, 0xc7b5795b, 0xb0a30a4c, 0xaf7f170c,
1174     0xf3b4762e, 0x8179576d, 0x738a1581, 0x4b95b64c, 0x9829b618, 0x1bea932e, 0x7bdeaa4b, 0xcb5e0281,
1175     0x65618f54, 0x0658474b, 0x27066acf, 0x40556d65, 0x7d204d53, 0xf28bc244, 0xdce23455, 0xadc0ff54,
1176     0x3863c948, 0xcee34e5f, 0xdeb85e02, 0x2ed17a61, 0x6a7b094d, 0x7f0cfc40, 0x59603f54, 0x3220afbc,
1177     0xb5dfd962, 0x125d21c0, 0x13f8d243, 0xacfefb4e, 0x86c2c147, 0x3d8bbd59, 0xbd02a21f, 0x2593042e,
1178     0xc6a17a7c, 0x28925861, 0xb487ed44, 0xb5f4fd6d, 0x90c28a45, 0x5a14f74d, 0x43d71b4c, 0x728ebb5d,
1179     0x885bf950, 0x08134dd0, 0x38ec046e, 0xc575684b, 0x50082d2e, 0xa2f47757, 0x270f86ae, 0xf3ff6462,
1180     0x10ed3f4e, 0x4b58d462, 0xe01ce23e, 0x8c5b092e, 0x63e52f4e, 0x22c1e85d, 0xa908f54e, 0x8591624f,
1181     0x2c0fb94e, 0xa280ba3c, 0xb6f41b4c, 0x24f9aa47, 0x27201647, 0x3a3ea6dc, 0xa14fc3be, 0x3c34bdd5,
1182     0x5b8d4f5b, 0xaadeaf4b, 0xc71cab50, 0x15697a4c, 0x9a1a734c, 0x2a037d81, 0x2590bd59, 0x48ec2741,
1183     0x53489c5b, 0x7f00314b, 0x2170d362, 0xf2e92542, 0x42c10b44, 0x98f0f118, 0x883a3456, 0x099a932e,
1184     0xea38f7bc, 0x644e9247, 0xbb61b62e, 0x30e0863d, 0x5f51be54, 0x207215c7, 0x5f306c45, 0xaa7f3932,
1185     0x98da7d45, 0x4e339b59, 0x2e411581, 0xa808f618, 0xad2c0c59, 0x54476741, 0x09e99fd1, 0x5db8f752,
1186     0xc16df8bd, 0x1dd4b44f, 0x106edf2e, 0x9e15c180, 0x2ad6b56f, 0x633a5332, 0xff33787c, 0x077cb545,
1187     0x6610be6d, 0x75aad2c4, 0x72fb4d5b, 0xe81e0f59, 0x576f6332, 0x47333373, 0x351ed783, 0x2d90fb50,
1188     0x8d5e0f6c, 0x5b27a552, 0xdb293ebb, 0xe55ef950, 0x4b133ad8, 0x75df975a, 0x7b6a8740, 0xa899464b,
1189     0xfab15161, 0x10f8b64d, 0xd055ea4d, 0xee8e146b, 0x4b14afb8, 0x4bc1c44a, 0x9b961dcc, 0xd111ff43,
1190     0xfca0b745, 0xc800e412, 0x0afad9d1, 0xf751c350, 0xf9f0cccf, 0xa290a545, 0x8ef13763, 0x7ec70d59,
1191     0x2b066acf, 0x65496c45, 0xade02c1b, 0xae6eb077, 0x92c1e65b, 0xc064e6a9, 0xc649e56d, 0x5287a243,
1192     0x36de4f5b, 0x5b1df6ad, 0x65c39a59, 0xdba805b2, 0x20067aa8, 0x6457e56d, 0x3cee26cf, 0xfd3ff26d,
1193     0x04f86d4a, 0x06b8e048, 0xa93bcd5c, 0x91135852, 0xbe90a643, 0x8fa0094d, 0x06d8215f, 0x2677094d,
1194     0xd735685c, 0x164a00c9, 0x5209ac5f, 0xa9564c5c, 0x3b504f5f, 0xcc826bd0, 0x4615042e, 0x5fe13b4a,
1195     0x8c81b86d, 0x879ab68c, 0x1de564b8, 0x434487d8, 0x2dcb1b63, 0x82ab524a, 0xb0676abb, 0xa13d9c62,
1196     0xdbb5b86d, 0x5b7f4b59, 0xaddfb44d, 0xad773532, 0x3997054c, 0x72cebd89, 0xb194544c, 0xc5b8046e,
1197     0x6e1adeb2, 0xaa5abb51, 0xefb54b44, 0x15efc54f, 0xe9f1bc4d, 0x5f401b6c, 0x97f018ad, 0xc82f9252,
1198     0x2cdc762e, 0x8e52e56d, 0x1827175e, 0x9b7d7d80, 0xb2ad6845, 0x51065140, 0x71180a18, 0x5b27006c,
1199     0x0621e255, 0x721cbe58, 0x670c0cb8, 0xf8bd715d, 0xe0bdc5d9, 0xed843501, 0x4b84554d, 0x7f1a18bc,
1200     0x53bcaf47, 0x5729d35f, 0xf0dda246, 0x22382bd0, 0x4d641fb0, 0x316afcde, 0x50a22f1f, 0x73608046,
1201     0xc461d84a, 0xb2dbe247,
1202 };
1203
1204 void DumpAddresses()
1205 {
1206     CAddrDB adb;
1207     adb.WriteAddrman(addrman);
1208 }
1209
1210 void ThreadDumpAddress2(void* parg)
1211 {
1212     vnThreadsRunning[THREAD_DUMPADDRESS]++;
1213     while (!fShutdown)
1214     {
1215         DumpAddresses();
1216         vnThreadsRunning[THREAD_DUMPADDRESS]--;
1217         Sleep(100000);
1218         vnThreadsRunning[THREAD_DUMPADDRESS]++;
1219     }
1220     vnThreadsRunning[THREAD_DUMPADDRESS]--;
1221 }
1222
1223 void ThreadDumpAddress(void* parg)
1224 {
1225     IMPLEMENT_RANDOMIZE_STACK(ThreadDumpAddress(parg));
1226     try
1227     {
1228         ThreadDumpAddress2(parg);
1229     }
1230     catch (std::exception& e) {
1231         PrintException(&e, "ThreadDumpAddress()");
1232     }
1233     printf("ThreadDumpAddress exiting\n");
1234 }
1235
1236 void ThreadOpenConnections(void* parg)
1237 {
1238     IMPLEMENT_RANDOMIZE_STACK(ThreadOpenConnections(parg));
1239     try
1240     {
1241         vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1242         ThreadOpenConnections2(parg);
1243         vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1244     }
1245     catch (std::exception& e) {
1246         vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1247         PrintException(&e, "ThreadOpenConnections()");
1248     } catch (...) {
1249         vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1250         PrintException(NULL, "ThreadOpenConnections()");
1251     }
1252     printf("ThreadOpenConnections exiting\n");
1253 }
1254
1255 void ThreadOpenConnections2(void* parg)
1256 {
1257     printf("ThreadOpenConnections started\n");
1258
1259     // Connect to specific addresses
1260     if (mapArgs.count("-connect"))
1261     {
1262         for (int64 nLoop = 0;; nLoop++)
1263         {
1264             BOOST_FOREACH(string strAddr, mapMultiArgs["-connect"])
1265             {
1266                 CAddress addr(CService(strAddr, GetDefaultPort(), fAllowDNS));
1267                 if (addr.IsValid())
1268                     OpenNetworkConnection(addr);
1269                 for (int i = 0; i < 10 && i < nLoop; i++)
1270                 {
1271                     Sleep(500);
1272                     if (fShutdown)
1273                         return;
1274                 }
1275             }
1276         }
1277     }
1278
1279     // Initiate network connections
1280     int64 nStart = GetTime();
1281     loop
1282     {
1283         int nOutbound = 0;
1284
1285         vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1286         Sleep(500);
1287         vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1288         if (fShutdown)
1289             return;
1290
1291         // Limit outbound connections
1292         loop
1293         {
1294             nOutbound = 0;
1295             CRITICAL_BLOCK(cs_vNodes)
1296                 BOOST_FOREACH(CNode* pnode, vNodes)
1297                     if (!pnode->fInbound)
1298                         nOutbound++;
1299             int nMaxOutboundConnections = MAX_OUTBOUND_CONNECTIONS;
1300             nMaxOutboundConnections = min(nMaxOutboundConnections, (int)GetArg("-maxconnections", 125));
1301             if (nOutbound < nMaxOutboundConnections)
1302                 break;
1303             vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1304             Sleep(2000);
1305             vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1306             if (fShutdown)
1307                 return;
1308         }
1309
1310         // Add seed nodes if IRC isn't working
1311         bool fTOR = (fUseProxy && addrProxy.GetPort() == 9050);
1312         if (addrman.size()==0 && (GetTime() - nStart > 60 || fTOR) && !fTestNet)
1313         {
1314             std::vector<CAddress> vAdd;
1315             for (unsigned int i = 0; i < ARRAYLEN(pnSeed); i++)
1316             {
1317                 // It'll only connect to one or two seed nodes because once it connects,
1318                 // it'll get a pile of addresses with newer timestamps.
1319                 // Seed nodes are given a random 'last seen time' of between one and two
1320                 // weeks ago.
1321                 const int64 nOneWeek = 7*24*60*60;
1322                 struct in_addr ip;
1323                 memcpy(&ip, &pnSeed[i], sizeof(ip));
1324                 CAddress addr(CService(ip, GetDefaultPort()));
1325                 addr.nTime = GetTime()-GetRand(nOneWeek)-nOneWeek;
1326                 vAdd.push_back(addr);
1327             }
1328             addrman.Add(vAdd, CNetAddr("127.0.0.1"));
1329         }
1330
1331         //
1332         // Choose an address to connect to based on most recently seen
1333         //
1334         CAddress addrConnect;
1335
1336         // Only connect to one address per a.b.?.? range.
1337         // Do this here so we don't have to critsect vNodes inside mapAddresses critsect.
1338         set<vector<unsigned char> > setConnected;
1339         CRITICAL_BLOCK(cs_vNodes)
1340             BOOST_FOREACH(CNode* pnode, vNodes)
1341                 setConnected.insert(pnode->addr.GetGroup());
1342
1343         int64 nANow = GetAdjustedTime();
1344
1345         int nTries = 0;
1346         loop
1347         {
1348             // use an nUnkBias between 10 (no outgoing connections) and 90 (8 outgoing connections)
1349             CAddress addr = addrman.Select(10 + min(nOutbound,8)*10);
1350
1351             // if we selected an invalid address, restart
1352             if (!addr.IsIPv4() || !addr.IsValid() || setConnected.count(addr.GetGroup()) || addr == addrLocalHost)
1353                 break;
1354
1355             nTries++;
1356
1357             // only consider very recently tried nodes after 30 failed attempts
1358             if (nANow - addr.nLastTry < 600 && nTries < 30)
1359                 continue;
1360
1361             // do not allow non-default ports, unless after 50 invalid addresses selected already
1362             if (addr.GetPort() != GetDefaultPort() && nTries < 50)
1363                 continue;
1364
1365             addrConnect = addr;
1366             break;
1367         }
1368
1369         if (addrConnect.IsValid())
1370             OpenNetworkConnection(addrConnect);
1371     }
1372 }
1373
1374 void ThreadOpenAddedConnections(void* parg)
1375 {
1376     IMPLEMENT_RANDOMIZE_STACK(ThreadOpenAddedConnections(parg));
1377     try
1378     {
1379         vnThreadsRunning[THREAD_ADDEDCONNECTIONS]++;
1380         ThreadOpenAddedConnections2(parg);
1381         vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1382     }
1383     catch (std::exception& e) {
1384         vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1385         PrintException(&e, "ThreadOpenAddedConnections()");
1386     } catch (...) {
1387         vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1388         PrintException(NULL, "ThreadOpenAddedConnections()");
1389     }
1390     printf("ThreadOpenAddedConnections exiting\n");
1391 }
1392
1393 void ThreadOpenAddedConnections2(void* parg)
1394 {
1395     printf("ThreadOpenAddedConnections started\n");
1396
1397     if (mapArgs.count("-addnode") == 0)
1398         return;
1399
1400     vector<vector<CService> > vservAddressesToAdd(0);
1401     BOOST_FOREACH(string& strAddNode, mapMultiArgs["-addnode"])
1402     {
1403         vector<CService> vservNode(0);
1404         if(Lookup(strAddNode.c_str(), vservNode, GetDefaultPort(), fAllowDNS, 0))
1405         {
1406             vservAddressesToAdd.push_back(vservNode);
1407             CRITICAL_BLOCK(cs_setservAddNodeAddresses)
1408                 BOOST_FOREACH(CService& serv, vservNode)
1409                     setservAddNodeAddresses.insert(serv);
1410         }
1411     }
1412     loop
1413     {
1414         vector<vector<CService> > vservConnectAddresses = vservAddressesToAdd;
1415         // Attempt to connect to each IP for each addnode entry until at least one is successful per addnode entry
1416         // (keeping in mind that addnode entries can have many IPs if fAllowDNS)
1417         CRITICAL_BLOCK(cs_vNodes)
1418             BOOST_FOREACH(CNode* pnode, vNodes)
1419                 for (vector<vector<CService> >::iterator it = vservConnectAddresses.begin(); it != vservConnectAddresses.end(); it++)
1420                     BOOST_FOREACH(CService& addrNode, *(it))
1421                         if (pnode->addr == addrNode)
1422                         {
1423                             it = vservConnectAddresses.erase(it);
1424                             it--;
1425                             break;
1426                         }
1427         BOOST_FOREACH(vector<CService>& vserv, vservConnectAddresses)
1428         {
1429             OpenNetworkConnection(CAddress(*(vserv.begin())));
1430             Sleep(500);
1431             if (fShutdown)
1432                 return;
1433         }
1434         if (fShutdown)
1435             return;
1436         vnThreadsRunning[THREAD_ADDEDCONNECTIONS]--;
1437         Sleep(120000); // Retry every 2 minutes
1438         vnThreadsRunning[THREAD_ADDEDCONNECTIONS]++;
1439         if (fShutdown)
1440             return;
1441     }
1442 }
1443
1444 bool OpenNetworkConnection(const CAddress& addrConnect)
1445 {
1446     //
1447     // Initiate outbound network connection
1448     //
1449     if (fShutdown)
1450         return false;
1451     if ((CNetAddr)addrConnect == (CNetAddr)addrLocalHost || !addrConnect.IsIPv4() ||
1452         FindNode((CNetAddr)addrConnect) || CNode::IsBanned(addrConnect))
1453         return false;
1454
1455     vnThreadsRunning[THREAD_OPENCONNECTIONS]--;
1456     CNode* pnode = ConnectNode(addrConnect);
1457     vnThreadsRunning[THREAD_OPENCONNECTIONS]++;
1458     if (fShutdown)
1459         return false;
1460     if (!pnode)
1461         return false;
1462     pnode->fNetworkNode = true;
1463
1464     return true;
1465 }
1466
1467
1468
1469
1470
1471
1472
1473
1474 void ThreadMessageHandler(void* parg)
1475 {
1476     IMPLEMENT_RANDOMIZE_STACK(ThreadMessageHandler(parg));
1477     try
1478     {
1479         vnThreadsRunning[THREAD_MESSAGEHANDLER]++;
1480         ThreadMessageHandler2(parg);
1481         vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1482     }
1483     catch (std::exception& e) {
1484         vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1485         PrintException(&e, "ThreadMessageHandler()");
1486     } catch (...) {
1487         vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1488         PrintException(NULL, "ThreadMessageHandler()");
1489     }
1490     printf("ThreadMessageHandler exiting\n");
1491 }
1492
1493 void ThreadMessageHandler2(void* parg)
1494 {
1495     printf("ThreadMessageHandler started\n");
1496     SetThreadPriority(THREAD_PRIORITY_BELOW_NORMAL);
1497     while (!fShutdown)
1498     {
1499         vector<CNode*> vNodesCopy;
1500         CRITICAL_BLOCK(cs_vNodes)
1501         {
1502             vNodesCopy = vNodes;
1503             BOOST_FOREACH(CNode* pnode, vNodesCopy)
1504                 pnode->AddRef();
1505         }
1506
1507         // Poll the connected nodes for messages
1508         CNode* pnodeTrickle = NULL;
1509         if (!vNodesCopy.empty())
1510             pnodeTrickle = vNodesCopy[GetRand(vNodesCopy.size())];
1511         BOOST_FOREACH(CNode* pnode, vNodesCopy)
1512         {
1513             // Receive messages
1514             TRY_CRITICAL_BLOCK(pnode->cs_vRecv)
1515                 ProcessMessages(pnode);
1516             if (fShutdown)
1517                 return;
1518
1519             // Send messages
1520             TRY_CRITICAL_BLOCK(pnode->cs_vSend)
1521                 SendMessages(pnode, pnode == pnodeTrickle);
1522             if (fShutdown)
1523                 return;
1524         }
1525
1526         CRITICAL_BLOCK(cs_vNodes)
1527         {
1528             BOOST_FOREACH(CNode* pnode, vNodesCopy)
1529                 pnode->Release();
1530         }
1531
1532         // Wait and allow messages to bunch up.
1533         // Reduce vnThreadsRunning so StopNode has permission to exit while
1534         // we're sleeping, but we must always check fShutdown after doing this.
1535         vnThreadsRunning[THREAD_MESSAGEHANDLER]--;
1536         Sleep(100);
1537         if (fRequestShutdown)
1538             Shutdown(NULL);
1539         vnThreadsRunning[THREAD_MESSAGEHANDLER]++;
1540         if (fShutdown)
1541             return;
1542     }
1543 }
1544
1545
1546
1547
1548
1549
1550 bool BindListenPort(string& strError)
1551 {
1552     strError = "";
1553     int nOne = 1;
1554     addrLocalHost.SetPort(GetListenPort());
1555
1556 #ifdef WIN32
1557     // Initialize Windows Sockets
1558     WSADATA wsadata;
1559     int ret = WSAStartup(MAKEWORD(2,2), &wsadata);
1560     if (ret != NO_ERROR)
1561     {
1562         strError = strprintf("Error: TCP/IP socket library failed to start (WSAStartup returned error %d)", ret);
1563         printf("%s\n", strError.c_str());
1564         return false;
1565     }
1566 #endif
1567
1568     // Create socket for listening for incoming connections
1569     hListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
1570     if (hListenSocket == INVALID_SOCKET)
1571     {
1572         strError = strprintf("Error: Couldn't open socket for incoming connections (socket returned error %d)", WSAGetLastError());
1573         printf("%s\n", strError.c_str());
1574         return false;
1575     }
1576
1577 #ifdef SO_NOSIGPIPE
1578     // Different way of disabling SIGPIPE on BSD
1579     setsockopt(hListenSocket, SOL_SOCKET, SO_NOSIGPIPE, (void*)&nOne, sizeof(int));
1580 #endif
1581
1582 #ifndef WIN32
1583     // Allow binding if the port is still in TIME_WAIT state after
1584     // the program was closed and restarted.  Not an issue on windows.
1585     setsockopt(hListenSocket, SOL_SOCKET, SO_REUSEADDR, (void*)&nOne, sizeof(int));
1586 #endif
1587
1588 #ifdef WIN32
1589     // Set to nonblocking, incoming connections will also inherit this
1590     if (ioctlsocket(hListenSocket, FIONBIO, (u_long*)&nOne) == SOCKET_ERROR)
1591 #else
1592     if (fcntl(hListenSocket, F_SETFL, O_NONBLOCK) == SOCKET_ERROR)
1593 #endif
1594     {
1595         strError = strprintf("Error: Couldn't set properties on socket for incoming connections (error %d)", WSAGetLastError());
1596         printf("%s\n", strError.c_str());
1597         return false;
1598     }
1599
1600     // The sockaddr_in structure specifies the address family,
1601     // IP address, and port for the socket that is being bound
1602     struct sockaddr_in sockaddr;
1603     memset(&sockaddr, 0, sizeof(sockaddr));
1604     sockaddr.sin_family = AF_INET;
1605     sockaddr.sin_addr.s_addr = INADDR_ANY; // bind to all IPs on this computer
1606     sockaddr.sin_port = htons(GetListenPort());
1607     if (::bind(hListenSocket, (struct sockaddr*)&sockaddr, sizeof(sockaddr)) == SOCKET_ERROR)
1608     {
1609         int nErr = WSAGetLastError();
1610         if (nErr == WSAEADDRINUSE)
1611             strError = strprintf(_("Unable to bind to port %d on this computer.  Bitcoin is probably already running."), ntohs(sockaddr.sin_port));
1612         else
1613             strError = strprintf("Error: Unable to bind to port %d on this computer (bind returned error %d)", ntohs(sockaddr.sin_port), nErr);
1614         printf("%s\n", strError.c_str());
1615         return false;
1616     }
1617     printf("Bound to port %d\n", ntohs(sockaddr.sin_port));
1618
1619     // Listen for incoming connections
1620     if (listen(hListenSocket, SOMAXCONN) == SOCKET_ERROR)
1621     {
1622         strError = strprintf("Error: Listening for incoming connections failed (listen returned error %d)", WSAGetLastError());
1623         printf("%s\n", strError.c_str());
1624         return false;
1625     }
1626
1627     return true;
1628 }
1629
1630 void StartNode(void* parg)
1631 {
1632 #ifdef USE_UPNP
1633 #if USE_UPNP
1634     fUseUPnP = GetBoolArg("-upnp", true);
1635 #else
1636     fUseUPnP = GetBoolArg("-upnp", false);
1637 #endif
1638 #endif
1639
1640     if (pnodeLocalHost == NULL)
1641         pnodeLocalHost = new CNode(INVALID_SOCKET, CAddress(CService("127.0.0.1", 0), nLocalServices));
1642
1643 #ifdef WIN32
1644     // Get local host ip
1645     char pszHostName[1000] = "";
1646     if (gethostname(pszHostName, sizeof(pszHostName)) != SOCKET_ERROR)
1647     {
1648         vector<CNetAddr> vaddr;
1649         if (LookupHost(pszHostName, vaddr))
1650             BOOST_FOREACH (const CNetAddr &addr, vaddr)
1651                 if (!addr.IsLocal())
1652                 {
1653                     addrLocalHost.SetIP(addr);
1654                     break;
1655                 }
1656     }
1657 #else
1658     // Get local host ip
1659     struct ifaddrs* myaddrs;
1660     if (getifaddrs(&myaddrs) == 0)
1661     {
1662         for (struct ifaddrs* ifa = myaddrs; ifa != NULL; ifa = ifa->ifa_next)
1663         {
1664             if (ifa->ifa_addr == NULL) continue;
1665             if ((ifa->ifa_flags & IFF_UP) == 0) continue;
1666             if (strcmp(ifa->ifa_name, "lo") == 0) continue;
1667             if (strcmp(ifa->ifa_name, "lo0") == 0) continue;
1668             char pszIP[100];
1669             if (ifa->ifa_addr->sa_family == AF_INET)
1670             {
1671                 struct sockaddr_in* s4 = (struct sockaddr_in*)(ifa->ifa_addr);
1672                 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s4->sin_addr), pszIP, sizeof(pszIP)) != NULL)
1673                     printf("ipv4 %s: %s\n", ifa->ifa_name, pszIP);
1674
1675                 // Take the first IP that isn't loopback 127.x.x.x
1676                 CAddress addr(CService(s4->sin_addr, GetListenPort()), nLocalServices);
1677                 if (addr.IsValid() && !addr.IsLocal())
1678                 {
1679                     addrLocalHost = addr;
1680                     break;
1681                 }
1682             }
1683             else if (ifa->ifa_addr->sa_family == AF_INET6)
1684             {
1685                 struct sockaddr_in6* s6 = (struct sockaddr_in6*)(ifa->ifa_addr);
1686                 if (inet_ntop(ifa->ifa_addr->sa_family, (void*)&(s6->sin6_addr), pszIP, sizeof(pszIP)) != NULL)
1687                     printf("ipv6 %s: %s\n", ifa->ifa_name, pszIP);
1688             }
1689         }
1690         freeifaddrs(myaddrs);
1691     }
1692 #endif
1693     printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1694
1695     if (fUseProxy || mapArgs.count("-connect") || fNoListen)
1696     {
1697         // Proxies can't take incoming connections
1698         addrLocalHost.SetIP(CNetAddr("0.0.0.0"));
1699         printf("addrLocalHost = %s\n", addrLocalHost.ToString().c_str());
1700     }
1701     else
1702     {
1703         CreateThread(ThreadGetMyExternalIP, NULL);
1704     }
1705
1706     //
1707     // Start threads
1708     //
1709
1710     if (!GetBoolArg("-dnsseed", true))
1711         printf("DNS seeding disabled\n");
1712     else
1713         if (!CreateThread(ThreadDNSAddressSeed, NULL))
1714             printf("Error: CreateThread(ThreadDNSAddressSeed) failed\n");
1715
1716     // Map ports with UPnP
1717     if (fHaveUPnP)
1718         MapPort(fUseUPnP);
1719
1720     // Get addresses from IRC and advertise ours
1721     if (!CreateThread(ThreadIRCSeed, NULL))
1722         printf("Error: CreateThread(ThreadIRCSeed) failed\n");
1723
1724     // Send and receive from sockets, accept connections
1725     if (!CreateThread(ThreadSocketHandler, NULL))
1726         printf("Error: CreateThread(ThreadSocketHandler) failed\n");
1727
1728     // Initiate outbound connections from -addnode
1729     if (!CreateThread(ThreadOpenAddedConnections, NULL))
1730         printf("Error: CreateThread(ThreadOpenAddedConnections) failed\n");
1731
1732     // Initiate outbound connections
1733     if (!CreateThread(ThreadOpenConnections, NULL))
1734         printf("Error: CreateThread(ThreadOpenConnections) failed\n");
1735
1736     // Process messages
1737     if (!CreateThread(ThreadMessageHandler, NULL))
1738         printf("Error: CreateThread(ThreadMessageHandler) failed\n");
1739
1740     // Dump network addresses
1741     if (!CreateThread(ThreadDumpAddress, NULL))
1742         printf("Error; CreateThread(ThreadDumpAddress) failed\n");
1743
1744     // Generate coins in the background
1745     GenerateBitcoins(GetBoolArg("-gen", false), pwalletMain);
1746 }
1747
1748 bool StopNode()
1749 {
1750     printf("StopNode()\n");
1751     fShutdown = true;
1752     nTransactionsUpdated++;
1753     int64 nStart = GetTime();
1754     do
1755     {
1756         int nThreadsRunning = 0;
1757         for (int n = 0; n < THREAD_MAX; n++)
1758             nThreadsRunning += vnThreadsRunning[n];
1759         if (nThreadsRunning == 0)
1760             break;
1761         if (GetTime() - nStart > 20)
1762             break;
1763         Sleep(20);
1764     } while(true);
1765     if (vnThreadsRunning[THREAD_SOCKETHANDLER] > 0) printf("ThreadSocketHandler still running\n");
1766     if (vnThreadsRunning[THREAD_OPENCONNECTIONS] > 0) printf("ThreadOpenConnections still running\n");
1767     if (vnThreadsRunning[THREAD_MESSAGEHANDLER] > 0) printf("ThreadMessageHandler still running\n");
1768     if (vnThreadsRunning[THREAD_MINER] > 0) printf("ThreadBitcoinMiner still running\n");
1769     if (vnThreadsRunning[THREAD_RPCSERVER] > 0) printf("ThreadRPCServer still running\n");
1770     if (fHaveUPnP && vnThreadsRunning[THREAD_UPNP] > 0) printf("ThreadMapPort still running\n");
1771     if (vnThreadsRunning[THREAD_DNSSEED] > 0) printf("ThreadDNSAddressSeed still running\n");
1772     if (vnThreadsRunning[THREAD_ADDEDCONNECTIONS] > 0) printf("ThreadOpenAddedConnections still running\n");
1773     if (vnThreadsRunning[THREAD_DUMPADDRESS] > 0) printf("ThreadDumpAddresses still running\n");
1774     while (vnThreadsRunning[THREAD_MESSAGEHANDLER] > 0 || vnThreadsRunning[THREAD_RPCSERVER] > 0)
1775         Sleep(20);
1776     Sleep(50);
1777     DumpAddresses();
1778     return true;
1779 }
1780
1781 class CNetCleanup
1782 {
1783 public:
1784     CNetCleanup()
1785     {
1786     }
1787     ~CNetCleanup()
1788     {
1789         // Close sockets
1790         BOOST_FOREACH(CNode* pnode, vNodes)
1791             if (pnode->hSocket != INVALID_SOCKET)
1792                 closesocket(pnode->hSocket);
1793         if (hListenSocket != INVALID_SOCKET)
1794             if (closesocket(hListenSocket) == SOCKET_ERROR)
1795                 printf("closesocket(hListenSocket) failed with error %d\n", WSAGetLastError());
1796
1797 #ifdef WIN32
1798         // Shutdown Windows Sockets
1799         WSACleanup();
1800 #endif
1801     }
1802 }
1803 instance_of_cnetcleanup;