6c81abad566a16056ccc6751df7579c0e3b0bdbd
[novacoin.git] / src / main.h
1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2012 The Bitcoin developers
3 // Distributed under the MIT/X11 software license, see the accompanying
4 // file license.txt or http://www.opensource.org/licenses/mit-license.php.
5 #ifndef BITCOIN_MAIN_H
6 #define BITCOIN_MAIN_H
7
8 #include "bignum.h"
9 #include "net.h"
10 #include "key.h"
11 #include "script.h"
12 #include "db.h"
13
14 #ifdef WIN32
15 #include <io.h> /* for _commit */
16 #endif
17
18 #include <list>
19
20 class CBlock;
21 class CBlockIndex;
22 class CWalletTx;
23 class CWallet;
24 class CKeyItem;
25 class CReserveKey;
26 class CWalletDB;
27
28 class CAddress;
29 class CInv;
30 class CRequestTracker;
31 class CNode;
32
33 static const int CLIENT_VERSION = 60099;
34 static const bool VERSION_IS_BETA = true;
35 extern const std::string CLIENT_NAME;
36
37 static const unsigned int MAX_BLOCK_SIZE = 1000000;
38 static const unsigned int MAX_BLOCK_SIZE_GEN = MAX_BLOCK_SIZE/2;
39 static const int MAX_BLOCK_SIGOPS = MAX_BLOCK_SIZE/50;
40 static const int MAX_ORPHAN_TRANSACTIONS = MAX_BLOCK_SIZE/100;
41 static const int64 COIN = 100000000;
42 static const int64 CENT = 1000000;
43 static const int64 MIN_TX_FEE = 50000;
44 static const int64 MIN_RELAY_TX_FEE = 10000;
45 static const int64 MAX_MONEY = 21000000 * COIN;
46 inline bool MoneyRange(int64 nValue) { return (nValue >= 0 && nValue <= MAX_MONEY); }
47 static const int COINBASE_MATURITY = 100;
48 // Threshold for nLockTime: below this value it is interpreted as block number, otherwise as UNIX timestamp.
49 static const int LOCKTIME_THRESHOLD = 500000000; // Tue Nov  5 00:53:20 1985 UTC
50 #ifdef USE_UPNP
51 static const int fHaveUPnP = true;
52 #else
53 static const int fHaveUPnP = false;
54 #endif
55
56
57 extern CScript COINBASE_FLAGS;
58
59
60
61
62
63
64 extern CCriticalSection cs_main;
65 extern std::map<uint256, CBlockIndex*> mapBlockIndex;
66 extern uint256 hashGenesisBlock;
67 extern CBlockIndex* pindexGenesisBlock;
68 extern int nBestHeight;
69 extern CBigNum bnBestChainWork;
70 extern CBigNum bnBestInvalidWork;
71 extern uint256 hashBestChain;
72 extern CBlockIndex* pindexBest;
73 extern uint64 nPooledTx;
74 extern unsigned int nTransactionsUpdated;
75 extern uint64 nLastBlockTx;
76 extern uint64 nLastBlockSize;
77 extern const std::string strMessageMagic;
78 extern double dHashesPerSec;
79 extern int64 nHPSTimerStart;
80 extern int64 nTimeBestReceived;
81 extern CCriticalSection cs_setpwalletRegistered;
82 extern std::set<CWallet*> setpwalletRegistered;
83
84 // Settings
85 extern int64 nTransactionFee;
86
87
88
89
90
91 class CReserveKey;
92 class CTxDB;
93 class CTxIndex;
94
95 void RegisterWallet(CWallet* pwalletIn);
96 void UnregisterWallet(CWallet* pwalletIn);
97 bool ProcessBlock(CNode* pfrom, CBlock* pblock);
98 bool CheckDiskSpace(uint64 nAdditionalBytes=0);
99 FILE* OpenBlockFile(unsigned int nFile, unsigned int nBlockPos, const char* pszMode="rb");
100 FILE* AppendBlockFile(unsigned int& nFileRet);
101 bool LoadBlockIndex(bool fAllowNew=true);
102 void PrintBlockTree();
103 bool ProcessMessages(CNode* pfrom);
104 bool SendMessages(CNode* pto, bool fSendTrickle);
105 void GenerateBitcoins(bool fGenerate, CWallet* pwallet);
106 CBlock* CreateNewBlock(CReserveKey& reservekey);
107 void IncrementExtraNonce(CBlock* pblock, CBlockIndex* pindexPrev, unsigned int& nExtraNonce);
108 void FormatHashBuffers(CBlock* pblock, char* pmidstate, char* pdata, char* phash1);
109 bool CheckWork(CBlock* pblock, CWallet& wallet, CReserveKey& reservekey);
110 bool CheckProofOfWork(uint256 hash, unsigned int nBits);
111 unsigned int ComputeMinWork(unsigned int nBase, int64 nTime);
112 int GetNumBlocksOfPeers();
113 bool IsInitialBlockDownload();
114 std::string GetWarnings(std::string strFor);
115
116
117
118
119
120
121
122
123
124
125
126
127 bool GetWalletFile(CWallet* pwallet, std::string &strWalletFileOut);
128
129 /** Position on disk for a particular transaction. */
130 class CDiskTxPos
131 {
132 public:
133     unsigned int nFile;
134     unsigned int nBlockPos;
135     unsigned int nTxPos;
136
137     CDiskTxPos()
138     {
139         SetNull();
140     }
141
142     CDiskTxPos(unsigned int nFileIn, unsigned int nBlockPosIn, unsigned int nTxPosIn)
143     {
144         nFile = nFileIn;
145         nBlockPos = nBlockPosIn;
146         nTxPos = nTxPosIn;
147     }
148
149     IMPLEMENT_SERIALIZE( READWRITE(FLATDATA(*this)); )
150     void SetNull() { nFile = -1; nBlockPos = 0; nTxPos = 0; }
151     bool IsNull() const { return (nFile == -1); }
152
153     friend bool operator==(const CDiskTxPos& a, const CDiskTxPos& b)
154     {
155         return (a.nFile     == b.nFile &&
156                 a.nBlockPos == b.nBlockPos &&
157                 a.nTxPos    == b.nTxPos);
158     }
159
160     friend bool operator!=(const CDiskTxPos& a, const CDiskTxPos& b)
161     {
162         return !(a == b);
163     }
164
165     std::string ToString() const
166     {
167         if (IsNull())
168             return "null";
169         else
170             return strprintf("(nFile=%d, nBlockPos=%d, nTxPos=%d)", nFile, nBlockPos, nTxPos);
171     }
172
173     void print() const
174     {
175         printf("%s", ToString().c_str());
176     }
177 };
178
179
180
181 /** An inpoint - a combination of a transaction and an index n into its vin */
182 class CInPoint
183 {
184 public:
185     CTransaction* ptx;
186     unsigned int n;
187
188     CInPoint() { SetNull(); }
189     CInPoint(CTransaction* ptxIn, unsigned int nIn) { ptx = ptxIn; n = nIn; }
190     void SetNull() { ptx = NULL; n = -1; }
191     bool IsNull() const { return (ptx == NULL && n == -1); }
192 };
193
194
195
196 /** An outpoint - a combination of a transaction hash and an index n into its vout */
197 class COutPoint
198 {
199 public:
200     uint256 hash;
201     unsigned int n;
202
203     COutPoint() { SetNull(); }
204     COutPoint(uint256 hashIn, unsigned int nIn) { hash = hashIn; n = nIn; }
205     IMPLEMENT_SERIALIZE( READWRITE(FLATDATA(*this)); )
206     void SetNull() { hash = 0; n = -1; }
207     bool IsNull() const { return (hash == 0 && n == -1); }
208
209     friend bool operator<(const COutPoint& a, const COutPoint& b)
210     {
211         return (a.hash < b.hash || (a.hash == b.hash && a.n < b.n));
212     }
213
214     friend bool operator==(const COutPoint& a, const COutPoint& b)
215     {
216         return (a.hash == b.hash && a.n == b.n);
217     }
218
219     friend bool operator!=(const COutPoint& a, const COutPoint& b)
220     {
221         return !(a == b);
222     }
223
224     std::string ToString() const
225     {
226         return strprintf("COutPoint(%s, %d)", hash.ToString().substr(0,10).c_str(), n);
227     }
228
229     void print() const
230     {
231         printf("%s\n", ToString().c_str());
232     }
233 };
234
235
236
237
238 /** An input of a transaction.  It contains the location of the previous
239  * transaction's output that it claims and a signature that matches the
240  * output's public key.
241  */
242 class CTxIn
243 {
244 public:
245     COutPoint prevout;
246     CScript scriptSig;
247     unsigned int nSequence;
248
249     CTxIn()
250     {
251         nSequence = std::numeric_limits<unsigned int>::max();
252     }
253
254     explicit CTxIn(COutPoint prevoutIn, CScript scriptSigIn=CScript(), unsigned int nSequenceIn=std::numeric_limits<unsigned int>::max())
255     {
256         prevout = prevoutIn;
257         scriptSig = scriptSigIn;
258         nSequence = nSequenceIn;
259     }
260
261     CTxIn(uint256 hashPrevTx, unsigned int nOut, CScript scriptSigIn=CScript(), unsigned int nSequenceIn=std::numeric_limits<unsigned int>::max())
262     {
263         prevout = COutPoint(hashPrevTx, nOut);
264         scriptSig = scriptSigIn;
265         nSequence = nSequenceIn;
266     }
267
268     IMPLEMENT_SERIALIZE
269     (
270         READWRITE(prevout);
271         READWRITE(scriptSig);
272         READWRITE(nSequence);
273     )
274
275     bool IsFinal() const
276     {
277         return (nSequence == std::numeric_limits<unsigned int>::max());
278     }
279
280     friend bool operator==(const CTxIn& a, const CTxIn& b)
281     {
282         return (a.prevout   == b.prevout &&
283                 a.scriptSig == b.scriptSig &&
284                 a.nSequence == b.nSequence);
285     }
286
287     friend bool operator!=(const CTxIn& a, const CTxIn& b)
288     {
289         return !(a == b);
290     }
291
292     std::string ToString() const
293     {
294         std::string str;
295         str += "CTxIn(";
296         str += prevout.ToString();
297         if (prevout.IsNull())
298             str += strprintf(", coinbase %s", HexStr(scriptSig).c_str());
299         else
300             str += strprintf(", scriptSig=%s", scriptSig.ToString().substr(0,24).c_str());
301         if (nSequence != std::numeric_limits<unsigned int>::max())
302             str += strprintf(", nSequence=%u", nSequence);
303         str += ")";
304         return str;
305     }
306
307     void print() const
308     {
309         printf("%s\n", ToString().c_str());
310     }
311 };
312
313
314
315
316 /** An output of a transaction.  It contains the public key that the next input
317  * must be able to sign with to claim it.
318  */
319 class CTxOut
320 {
321 public:
322     int64 nValue;
323     CScript scriptPubKey;
324
325     CTxOut()
326     {
327         SetNull();
328     }
329
330     CTxOut(int64 nValueIn, CScript scriptPubKeyIn)
331     {
332         nValue = nValueIn;
333         scriptPubKey = scriptPubKeyIn;
334     }
335
336     IMPLEMENT_SERIALIZE
337     (
338         READWRITE(nValue);
339         READWRITE(scriptPubKey);
340     )
341
342     void SetNull()
343     {
344         nValue = -1;
345         scriptPubKey.clear();
346     }
347
348     bool IsNull()
349     {
350         return (nValue == -1);
351     }
352
353     uint256 GetHash() const
354     {
355         return SerializeHash(*this);
356     }
357
358     friend bool operator==(const CTxOut& a, const CTxOut& b)
359     {
360         return (a.nValue       == b.nValue &&
361                 a.scriptPubKey == b.scriptPubKey);
362     }
363
364     friend bool operator!=(const CTxOut& a, const CTxOut& b)
365     {
366         return !(a == b);
367     }
368
369     std::string ToString() const
370     {
371         if (scriptPubKey.size() < 6)
372             return "CTxOut(error)";
373         return strprintf("CTxOut(nValue=%"PRI64d".%08"PRI64d", scriptPubKey=%s)", nValue / COIN, nValue % COIN, scriptPubKey.ToString().substr(0,30).c_str());
374     }
375
376     void print() const
377     {
378         printf("%s\n", ToString().c_str());
379     }
380 };
381
382
383
384
385 enum GetMinFee_mode
386 {
387     GMF_BLOCK,
388     GMF_RELAY,
389     GMF_SEND,
390 };
391
392 typedef std::map<uint256, std::pair<CTxIndex, CTransaction> > MapPrevTx;
393
394 /** The basic transaction that is broadcasted on the network and contained in
395  * blocks.  A transaction can contain multiple inputs and outputs.
396  */
397 class CTransaction
398 {
399 public:
400     int nVersion;
401     std::vector<CTxIn> vin;
402     std::vector<CTxOut> vout;
403     unsigned int nLockTime;
404
405     // Denial-of-service detection:
406     mutable int nDoS;
407     bool DoS(int nDoSIn, bool fIn) const { nDoS += nDoSIn; return fIn; }
408
409     CTransaction()
410     {
411         SetNull();
412     }
413
414     IMPLEMENT_SERIALIZE
415     (
416         READWRITE(this->nVersion);
417         nVersion = this->nVersion;
418         READWRITE(vin);
419         READWRITE(vout);
420         READWRITE(nLockTime);
421     )
422
423     void SetNull()
424     {
425         nVersion = 1;
426         vin.clear();
427         vout.clear();
428         nLockTime = 0;
429         nDoS = 0;  // Denial-of-service prevention
430     }
431
432     bool IsNull() const
433     {
434         return (vin.empty() && vout.empty());
435     }
436
437     uint256 GetHash() const
438     {
439         return SerializeHash(*this);
440     }
441
442     bool IsFinal(int nBlockHeight=0, int64 nBlockTime=0) const
443     {
444         // Time based nLockTime implemented in 0.1.6
445         if (nLockTime == 0)
446             return true;
447         if (nBlockHeight == 0)
448             nBlockHeight = nBestHeight;
449         if (nBlockTime == 0)
450             nBlockTime = GetAdjustedTime();
451         if ((int64)nLockTime < (nLockTime < LOCKTIME_THRESHOLD ? (int64)nBlockHeight : nBlockTime))
452             return true;
453         BOOST_FOREACH(const CTxIn& txin, vin)
454             if (!txin.IsFinal())
455                 return false;
456         return true;
457     }
458
459     bool IsNewerThan(const CTransaction& old) const
460     {
461         if (vin.size() != old.vin.size())
462             return false;
463         for (int i = 0; i < vin.size(); i++)
464             if (vin[i].prevout != old.vin[i].prevout)
465                 return false;
466
467         bool fNewer = false;
468         unsigned int nLowest = std::numeric_limits<unsigned int>::max();
469         for (int i = 0; i < vin.size(); i++)
470         {
471             if (vin[i].nSequence != old.vin[i].nSequence)
472             {
473                 if (vin[i].nSequence <= nLowest)
474                 {
475                     fNewer = false;
476                     nLowest = vin[i].nSequence;
477                 }
478                 if (old.vin[i].nSequence < nLowest)
479                 {
480                     fNewer = true;
481                     nLowest = old.vin[i].nSequence;
482                 }
483             }
484         }
485         return fNewer;
486     }
487
488     bool IsCoinBase() const
489     {
490         return (vin.size() == 1 && vin[0].prevout.IsNull());
491     }
492
493     /** Check for standard transaction types
494         @return True if all outputs (scriptPubKeys) use only standard transaction forms
495     */
496     bool IsStandard() const;
497
498     /** Check for standard transaction types
499         @param[in] mapInputs    Map of previous transactions that have outputs we're spending
500         @return True if all inputs (scriptSigs) use only standard transaction forms
501         @see CTransaction::FetchInputs
502     */
503     bool AreInputsStandard(const MapPrevTx& mapInputs) const;
504
505     /** Count ECDSA signature operations the old-fashioned (pre-0.6) way
506         @return number of sigops this transaction's outputs will produce when spent
507         @see CTransaction::FetchInputs
508     */
509     int GetLegacySigOpCount() const;
510
511     /** Count ECDSA signature operations in pay-to-script-hash inputs.
512
513         @param[in] mapInputs    Map of previous transactions that have outputs we're spending
514         @return maximum number of sigops required to validate this transaction's inputs
515         @see CTransaction::FetchInputs
516      */
517     int GetP2SHSigOpCount(const MapPrevTx& mapInputs) const;
518
519     /** Amount of bitcoins spent by this transaction.
520         @return sum of all outputs (note: does not include fees)
521      */
522     int64 GetValueOut() const
523     {
524         int64 nValueOut = 0;
525         BOOST_FOREACH(const CTxOut& txout, vout)
526         {
527             nValueOut += txout.nValue;
528             if (!MoneyRange(txout.nValue) || !MoneyRange(nValueOut))
529                 throw std::runtime_error("CTransaction::GetValueOut() : value out of range");
530         }
531         return nValueOut;
532     }
533
534     /** Amount of bitcoins coming in to this transaction
535         Note that lightweight clients may not know anything besides the hash of previous transactions,
536         so may not be able to calculate this.
537
538         @param[in] mapInputs    Map of previous transactions that have outputs we're spending
539         @return Sum of value of all inputs (scriptSigs)
540         @see CTransaction::FetchInputs
541      */
542     int64 GetValueIn(const MapPrevTx& mapInputs) const;
543
544     static bool AllowFree(double dPriority)
545     {
546         // Large (in bytes) low-priority (new, small-coin) transactions
547         // need a fee.
548         return dPriority > COIN * 144 / 250;
549     }
550
551     int64 GetMinFee(unsigned int nBlockSize=1, bool fAllowFree=true, enum GetMinFee_mode mode=GMF_BLOCK) const
552     {
553         // Base fee is either MIN_TX_FEE or MIN_RELAY_TX_FEE
554         int64 nBaseFee = (mode == GMF_RELAY) ? MIN_RELAY_TX_FEE : MIN_TX_FEE;
555
556         unsigned int nBytes = ::GetSerializeSize(*this, SER_NETWORK);
557         unsigned int nNewBlockSize = nBlockSize + nBytes;
558         int64 nMinFee = (1 + (int64)nBytes / 1000) * nBaseFee;
559
560         if (fAllowFree)
561         {
562             if (nBlockSize == 1)
563             {
564                 // Transactions under 10K are free
565                 // (about 4500bc if made of 50bc inputs)
566                 if (nBytes < 10000)
567                     nMinFee = 0;
568             }
569             else
570             {
571                 // Free transaction area
572                 if (nNewBlockSize < 27000)
573                     nMinFee = 0;
574             }
575         }
576
577         // To limit dust spam, require MIN_TX_FEE/MIN_RELAY_TX_FEE if any output is less than 0.01
578         if (nMinFee < nBaseFee)
579             BOOST_FOREACH(const CTxOut& txout, vout)
580                 if (txout.nValue < CENT)
581                     nMinFee = nBaseFee;
582
583         // Raise the price as the block approaches full
584         if (nBlockSize != 1 && nNewBlockSize >= MAX_BLOCK_SIZE_GEN/2)
585         {
586             if (nNewBlockSize >= MAX_BLOCK_SIZE_GEN)
587                 return MAX_MONEY;
588             nMinFee *= MAX_BLOCK_SIZE_GEN / (MAX_BLOCK_SIZE_GEN - nNewBlockSize);
589         }
590
591         if (!MoneyRange(nMinFee))
592             nMinFee = MAX_MONEY;
593         return nMinFee;
594     }
595
596
597     bool ReadFromDisk(CDiskTxPos pos, FILE** pfileRet=NULL)
598     {
599         CAutoFile filein = OpenBlockFile(pos.nFile, 0, pfileRet ? "rb+" : "rb");
600         if (!filein)
601             return error("CTransaction::ReadFromDisk() : OpenBlockFile failed");
602
603         // Read transaction
604         if (fseek(filein, pos.nTxPos, SEEK_SET) != 0)
605             return error("CTransaction::ReadFromDisk() : fseek failed");
606         filein >> *this;
607
608         // Return file pointer
609         if (pfileRet)
610         {
611             if (fseek(filein, pos.nTxPos, SEEK_SET) != 0)
612                 return error("CTransaction::ReadFromDisk() : second fseek failed");
613             *pfileRet = filein.release();
614         }
615         return true;
616     }
617
618     friend bool operator==(const CTransaction& a, const CTransaction& b)
619     {
620         return (a.nVersion  == b.nVersion &&
621                 a.vin       == b.vin &&
622                 a.vout      == b.vout &&
623                 a.nLockTime == b.nLockTime);
624     }
625
626     friend bool operator!=(const CTransaction& a, const CTransaction& b)
627     {
628         return !(a == b);
629     }
630
631
632     std::string ToString() const
633     {
634         std::string str;
635         str += strprintf("CTransaction(hash=%s, ver=%d, vin.size=%d, vout.size=%d, nLockTime=%d)\n",
636             GetHash().ToString().substr(0,10).c_str(),
637             nVersion,
638             vin.size(),
639             vout.size(),
640             nLockTime);
641         for (int i = 0; i < vin.size(); i++)
642             str += "    " + vin[i].ToString() + "\n";
643         for (int i = 0; i < vout.size(); i++)
644             str += "    " + vout[i].ToString() + "\n";
645         return str;
646     }
647
648     void print() const
649     {
650         printf("%s", ToString().c_str());
651     }
652
653
654     bool ReadFromDisk(CTxDB& txdb, COutPoint prevout, CTxIndex& txindexRet);
655     bool ReadFromDisk(CTxDB& txdb, COutPoint prevout);
656     bool ReadFromDisk(COutPoint prevout);
657     bool DisconnectInputs(CTxDB& txdb);
658
659     /** Fetch from memory and/or disk. inputsRet keys are transaction hashes.
660
661      @param[in] txdb    Transaction database
662      @param[in] mapTestPool     List of pending changes to the transaction index database
663      @param[in] fBlock  True if being called to add a new best-block to the chain
664      @param[in] fMiner  True if being called by CreateNewBlock
665      @param[out] inputsRet      Pointers to this transaction's inputs
666      @param[out] fInvalid       returns true if transaction is invalid
667      @return    Returns true if all inputs are in txdb or mapTestPool
668      */
669     bool FetchInputs(CTxDB& txdb, const std::map<uint256, CTxIndex>& mapTestPool,
670                      bool fBlock, bool fMiner, MapPrevTx& inputsRet, bool& fInvalid);
671
672     /** Sanity check previous transactions, then, if all checks succeed,
673         mark them as spent by this transaction.
674
675         @param[in] inputs       Previous transactions (from FetchInputs)
676         @param[out] mapTestPool Keeps track of inputs that need to be updated on disk
677         @param[in] posThisTx    Position of this transaction on disk
678         @param[in] pindexBlock
679         @param[in] fBlock       true if called from ConnectBlock
680         @param[in] fMiner       true if called from CreateNewBlock
681         @param[in] fStrictPayToScriptHash       true if fully validating p2sh transactions
682         @return Returns true if all checks succeed
683      */
684     bool ConnectInputs(MapPrevTx inputs,
685                        std::map<uint256, CTxIndex>& mapTestPool, const CDiskTxPos& posThisTx,
686                        const CBlockIndex* pindexBlock, bool fBlock, bool fMiner, bool fStrictPayToScriptHash=true);
687     bool ClientConnectInputs();
688     bool CheckTransaction() const;
689     bool AcceptToMemoryPool(CTxDB& txdb, bool fCheckInputs=true, bool* pfMissingInputs=NULL);
690     bool AcceptToMemoryPool(bool fCheckInputs=true, bool* pfMissingInputs=NULL);
691
692 protected:
693     const CTxOut& GetOutputFor(const CTxIn& input, const MapPrevTx& inputs) const;
694     bool AddToMemoryPoolUnchecked();
695 public:
696     bool RemoveFromMemoryPool();
697 };
698
699
700
701
702
703 /** A transaction with a merkle branch linking it to the block chain. */
704 class CMerkleTx : public CTransaction
705 {
706 public:
707     uint256 hashBlock;
708     std::vector<uint256> vMerkleBranch;
709     int nIndex;
710
711     // memory only
712     mutable char fMerkleVerified;
713
714
715     CMerkleTx()
716     {
717         Init();
718     }
719
720     CMerkleTx(const CTransaction& txIn) : CTransaction(txIn)
721     {
722         Init();
723     }
724
725     void Init()
726     {
727         hashBlock = 0;
728         nIndex = -1;
729         fMerkleVerified = false;
730     }
731
732
733     IMPLEMENT_SERIALIZE
734     (
735         nSerSize += SerReadWrite(s, *(CTransaction*)this, nType, nVersion, ser_action);
736         nVersion = this->nVersion;
737         READWRITE(hashBlock);
738         READWRITE(vMerkleBranch);
739         READWRITE(nIndex);
740     )
741
742
743     int SetMerkleBranch(const CBlock* pblock=NULL);
744     int GetDepthInMainChain(CBlockIndex* &pindexRet) const;
745     int GetDepthInMainChain() const { CBlockIndex *pindexRet; return GetDepthInMainChain(pindexRet); }
746     bool IsInMainChain() const { return GetDepthInMainChain() > 0; }
747     int GetBlocksToMaturity() const;
748     bool AcceptToMemoryPool(CTxDB& txdb, bool fCheckInputs=true);
749     bool AcceptToMemoryPool();
750 };
751
752
753
754
755 /**  A txdb record that contains the disk location of a transaction and the
756  * locations of transactions that spend its outputs.  vSpent is really only
757  * used as a flag, but having the location is very helpful for debugging.
758  */
759 class CTxIndex
760 {
761 public:
762     CDiskTxPos pos;
763     std::vector<CDiskTxPos> vSpent;
764
765     CTxIndex()
766     {
767         SetNull();
768     }
769
770     CTxIndex(const CDiskTxPos& posIn, unsigned int nOutputs)
771     {
772         pos = posIn;
773         vSpent.resize(nOutputs);
774     }
775
776     IMPLEMENT_SERIALIZE
777     (
778         if (!(nType & SER_GETHASH))
779             READWRITE(nVersion);
780         READWRITE(pos);
781         READWRITE(vSpent);
782     )
783
784     void SetNull()
785     {
786         pos.SetNull();
787         vSpent.clear();
788     }
789
790     bool IsNull()
791     {
792         return pos.IsNull();
793     }
794
795     friend bool operator==(const CTxIndex& a, const CTxIndex& b)
796     {
797         return (a.pos    == b.pos &&
798                 a.vSpent == b.vSpent);
799     }
800
801     friend bool operator!=(const CTxIndex& a, const CTxIndex& b)
802     {
803         return !(a == b);
804     }
805     int GetDepthInMainChain() const;
806  
807 };
808
809
810
811
812
813 /** Nodes collect new transactions into a block, hash them into a hash tree,
814  * and scan through nonce values to make the block's hash satisfy proof-of-work
815  * requirements.  When they solve the proof-of-work, they broadcast the block
816  * to everyone and the block is added to the block chain.  The first transaction
817  * in the block is a special one that creates a new coin owned by the creator
818  * of the block.
819  *
820  * Blocks are appended to blk0001.dat files on disk.  Their location on disk
821  * is indexed by CBlockIndex objects in memory.
822  */
823 class CBlock
824 {
825 public:
826     // header
827     int nVersion;
828     uint256 hashPrevBlock;
829     uint256 hashMerkleRoot;
830     unsigned int nTime;
831     unsigned int nBits;
832     unsigned int nNonce;
833
834     // network and disk
835     std::vector<CTransaction> vtx;
836
837     // memory only
838     mutable std::vector<uint256> vMerkleTree;
839
840     // Denial-of-service detection:
841     mutable int nDoS;
842     bool DoS(int nDoSIn, bool fIn) const { nDoS += nDoSIn; return fIn; }
843
844     CBlock()
845     {
846         SetNull();
847     }
848
849     IMPLEMENT_SERIALIZE
850     (
851         READWRITE(this->nVersion);
852         nVersion = this->nVersion;
853         READWRITE(hashPrevBlock);
854         READWRITE(hashMerkleRoot);
855         READWRITE(nTime);
856         READWRITE(nBits);
857         READWRITE(nNonce);
858
859         // ConnectBlock depends on vtx being last so it can calculate offset
860         if (!(nType & (SER_GETHASH|SER_BLOCKHEADERONLY)))
861             READWRITE(vtx);
862         else if (fRead)
863             const_cast<CBlock*>(this)->vtx.clear();
864     )
865
866     void SetNull()
867     {
868         nVersion = 1;
869         hashPrevBlock = 0;
870         hashMerkleRoot = 0;
871         nTime = 0;
872         nBits = 0;
873         nNonce = 0;
874         vtx.clear();
875         vMerkleTree.clear();
876         nDoS = 0;
877     }
878
879     bool IsNull() const
880     {
881         return (nBits == 0);
882     }
883
884     uint256 GetHash() const
885     {
886         return Hash(BEGIN(nVersion), END(nNonce));
887     }
888
889     int64 GetBlockTime() const
890     {
891         return (int64)nTime;
892     }
893
894     void UpdateTime(const CBlockIndex* pindexPrev);
895
896
897     uint256 BuildMerkleTree() const
898     {
899         vMerkleTree.clear();
900         BOOST_FOREACH(const CTransaction& tx, vtx)
901             vMerkleTree.push_back(tx.GetHash());
902         int j = 0;
903         for (int nSize = vtx.size(); nSize > 1; nSize = (nSize + 1) / 2)
904         {
905             for (int i = 0; i < nSize; i += 2)
906             {
907                 int i2 = std::min(i+1, nSize-1);
908                 vMerkleTree.push_back(Hash(BEGIN(vMerkleTree[j+i]),  END(vMerkleTree[j+i]),
909                                            BEGIN(vMerkleTree[j+i2]), END(vMerkleTree[j+i2])));
910             }
911             j += nSize;
912         }
913         return (vMerkleTree.empty() ? 0 : vMerkleTree.back());
914     }
915
916     std::vector<uint256> GetMerkleBranch(int nIndex) const
917     {
918         if (vMerkleTree.empty())
919             BuildMerkleTree();
920         std::vector<uint256> vMerkleBranch;
921         int j = 0;
922         for (int nSize = vtx.size(); nSize > 1; nSize = (nSize + 1) / 2)
923         {
924             int i = std::min(nIndex^1, nSize-1);
925             vMerkleBranch.push_back(vMerkleTree[j+i]);
926             nIndex >>= 1;
927             j += nSize;
928         }
929         return vMerkleBranch;
930     }
931
932     static uint256 CheckMerkleBranch(uint256 hash, const std::vector<uint256>& vMerkleBranch, int nIndex)
933     {
934         if (nIndex == -1)
935             return 0;
936         BOOST_FOREACH(const uint256& otherside, vMerkleBranch)
937         {
938             if (nIndex & 1)
939                 hash = Hash(BEGIN(otherside), END(otherside), BEGIN(hash), END(hash));
940             else
941                 hash = Hash(BEGIN(hash), END(hash), BEGIN(otherside), END(otherside));
942             nIndex >>= 1;
943         }
944         return hash;
945     }
946
947
948     bool WriteToDisk(unsigned int& nFileRet, unsigned int& nBlockPosRet)
949     {
950         // Open history file to append
951         CAutoFile fileout = AppendBlockFile(nFileRet);
952         if (!fileout)
953             return error("CBlock::WriteToDisk() : AppendBlockFile failed");
954
955         // Write index header
956         unsigned int nSize = fileout.GetSerializeSize(*this);
957         fileout << FLATDATA(pchMessageStart) << nSize;
958
959         // Write block
960         nBlockPosRet = ftell(fileout);
961         if (nBlockPosRet == -1)
962             return error("CBlock::WriteToDisk() : ftell failed");
963         fileout << *this;
964
965         // Flush stdio buffers and commit to disk before returning
966         fflush(fileout);
967         if (!IsInitialBlockDownload() || (nBestHeight+1) % 500 == 0)
968         {
969 #ifdef WIN32
970             _commit(_fileno(fileout));
971 #else
972             fsync(fileno(fileout));
973 #endif
974         }
975
976         return true;
977     }
978
979     bool ReadFromDisk(unsigned int nFile, unsigned int nBlockPos, bool fReadTransactions=true)
980     {
981         SetNull();
982
983         // Open history file to read
984         CAutoFile filein = OpenBlockFile(nFile, nBlockPos, "rb");
985         if (!filein)
986             return error("CBlock::ReadFromDisk() : OpenBlockFile failed");
987         if (!fReadTransactions)
988             filein.nType |= SER_BLOCKHEADERONLY;
989
990         // Read block
991         filein >> *this;
992
993         // Check the header
994         if (!CheckProofOfWork(GetHash(), nBits))
995             return error("CBlock::ReadFromDisk() : errors in block header");
996
997         return true;
998     }
999
1000
1001
1002     void print() const
1003     {
1004         printf("CBlock(hash=%s, ver=%d, hashPrevBlock=%s, hashMerkleRoot=%s, nTime=%u, nBits=%08x, nNonce=%u, vtx=%d)\n",
1005             GetHash().ToString().substr(0,20).c_str(),
1006             nVersion,
1007             hashPrevBlock.ToString().substr(0,20).c_str(),
1008             hashMerkleRoot.ToString().substr(0,10).c_str(),
1009             nTime, nBits, nNonce,
1010             vtx.size());
1011         for (int i = 0; i < vtx.size(); i++)
1012         {
1013             printf("  ");
1014             vtx[i].print();
1015         }
1016         printf("  vMerkleTree: ");
1017         for (int i = 0; i < vMerkleTree.size(); i++)
1018             printf("%s ", vMerkleTree[i].ToString().substr(0,10).c_str());
1019         printf("\n");
1020     }
1021
1022
1023     bool DisconnectBlock(CTxDB& txdb, CBlockIndex* pindex);
1024     bool ConnectBlock(CTxDB& txdb, CBlockIndex* pindex);
1025     bool ReadFromDisk(const CBlockIndex* pindex, bool fReadTransactions=true);
1026     bool SetBestChain(CTxDB& txdb, CBlockIndex* pindexNew);
1027     bool AddToBlockIndex(unsigned int nFile, unsigned int nBlockPos);
1028     bool CheckBlock() const;
1029     bool AcceptBlock();
1030
1031 private:
1032     bool SetBestChainInner(CTxDB& txdb, CBlockIndex *pindexNew);
1033 };
1034
1035
1036
1037
1038
1039
1040 /** The block chain is a tree shaped structure starting with the
1041  * genesis block at the root, with each block potentially having multiple
1042  * candidates to be the next block.  pprev and pnext link a path through the
1043  * main/longest chain.  A blockindex may have multiple pprev pointing back
1044  * to it, but pnext will only point forward to the longest branch, or will
1045  * be null if the block is not part of the longest chain.
1046  */
1047 class CBlockIndex
1048 {
1049 public:
1050     const uint256* phashBlock;
1051     CBlockIndex* pprev;
1052     CBlockIndex* pnext;
1053     unsigned int nFile;
1054     unsigned int nBlockPos;
1055     int nHeight;
1056     CBigNum bnChainWork;
1057
1058     // block header
1059     int nVersion;
1060     uint256 hashMerkleRoot;
1061     unsigned int nTime;
1062     unsigned int nBits;
1063     unsigned int nNonce;
1064
1065
1066     CBlockIndex()
1067     {
1068         phashBlock = NULL;
1069         pprev = NULL;
1070         pnext = NULL;
1071         nFile = 0;
1072         nBlockPos = 0;
1073         nHeight = 0;
1074         bnChainWork = 0;
1075
1076         nVersion       = 0;
1077         hashMerkleRoot = 0;
1078         nTime          = 0;
1079         nBits          = 0;
1080         nNonce         = 0;
1081     }
1082
1083     CBlockIndex(unsigned int nFileIn, unsigned int nBlockPosIn, CBlock& block)
1084     {
1085         phashBlock = NULL;
1086         pprev = NULL;
1087         pnext = NULL;
1088         nFile = nFileIn;
1089         nBlockPos = nBlockPosIn;
1090         nHeight = 0;
1091         bnChainWork = 0;
1092
1093         nVersion       = block.nVersion;
1094         hashMerkleRoot = block.hashMerkleRoot;
1095         nTime          = block.nTime;
1096         nBits          = block.nBits;
1097         nNonce         = block.nNonce;
1098     }
1099
1100     CBlock GetBlockHeader() const
1101     {
1102         CBlock block;
1103         block.nVersion       = nVersion;
1104         if (pprev)
1105             block.hashPrevBlock = pprev->GetBlockHash();
1106         block.hashMerkleRoot = hashMerkleRoot;
1107         block.nTime          = nTime;
1108         block.nBits          = nBits;
1109         block.nNonce         = nNonce;
1110         return block;
1111     }
1112
1113     uint256 GetBlockHash() const
1114     {
1115         return *phashBlock;
1116     }
1117
1118     int64 GetBlockTime() const
1119     {
1120         return (int64)nTime;
1121     }
1122
1123     CBigNum GetBlockWork() const
1124     {
1125         CBigNum bnTarget;
1126         bnTarget.SetCompact(nBits);
1127         if (bnTarget <= 0)
1128             return 0;
1129         return (CBigNum(1)<<256) / (bnTarget+1);
1130     }
1131
1132     bool IsInMainChain() const
1133     {
1134         return (pnext || this == pindexBest);
1135     }
1136
1137     bool CheckIndex() const
1138     {
1139         return CheckProofOfWork(GetBlockHash(), nBits);
1140     }
1141
1142     bool EraseBlockFromDisk()
1143     {
1144         // Open history file
1145         CAutoFile fileout = OpenBlockFile(nFile, nBlockPos, "rb+");
1146         if (!fileout)
1147             return false;
1148
1149         // Overwrite with empty null block
1150         CBlock block;
1151         block.SetNull();
1152         fileout << block;
1153
1154         return true;
1155     }
1156
1157     enum { nMedianTimeSpan=11 };
1158
1159     int64 GetMedianTimePast() const
1160     {
1161         int64 pmedian[nMedianTimeSpan];
1162         int64* pbegin = &pmedian[nMedianTimeSpan];
1163         int64* pend = &pmedian[nMedianTimeSpan];
1164
1165         const CBlockIndex* pindex = this;
1166         for (int i = 0; i < nMedianTimeSpan && pindex; i++, pindex = pindex->pprev)
1167             *(--pbegin) = pindex->GetBlockTime();
1168
1169         std::sort(pbegin, pend);
1170         return pbegin[(pend - pbegin)/2];
1171     }
1172
1173     int64 GetMedianTime() const
1174     {
1175         const CBlockIndex* pindex = this;
1176         for (int i = 0; i < nMedianTimeSpan/2; i++)
1177         {
1178             if (!pindex->pnext)
1179                 return GetBlockTime();
1180             pindex = pindex->pnext;
1181         }
1182         return pindex->GetMedianTimePast();
1183     }
1184
1185
1186
1187     std::string ToString() const
1188     {
1189         return strprintf("CBlockIndex(nprev=%08x, pnext=%08x, nFile=%d, nBlockPos=%-6d nHeight=%d, merkle=%s, hashBlock=%s)",
1190             pprev, pnext, nFile, nBlockPos, nHeight,
1191             hashMerkleRoot.ToString().substr(0,10).c_str(),
1192             GetBlockHash().ToString().substr(0,20).c_str());
1193     }
1194
1195     void print() const
1196     {
1197         printf("%s\n", ToString().c_str());
1198     }
1199 };
1200
1201
1202
1203 /** Used to marshal pointers into hashes for db storage. */
1204 class CDiskBlockIndex : public CBlockIndex
1205 {
1206 public:
1207     uint256 hashPrev;
1208     uint256 hashNext;
1209
1210     CDiskBlockIndex()
1211     {
1212         hashPrev = 0;
1213         hashNext = 0;
1214     }
1215
1216     explicit CDiskBlockIndex(CBlockIndex* pindex) : CBlockIndex(*pindex)
1217     {
1218         hashPrev = (pprev ? pprev->GetBlockHash() : 0);
1219         hashNext = (pnext ? pnext->GetBlockHash() : 0);
1220     }
1221
1222     IMPLEMENT_SERIALIZE
1223     (
1224         if (!(nType & SER_GETHASH))
1225             READWRITE(nVersion);
1226
1227         READWRITE(hashNext);
1228         READWRITE(nFile);
1229         READWRITE(nBlockPos);
1230         READWRITE(nHeight);
1231
1232         // block header
1233         READWRITE(this->nVersion);
1234         READWRITE(hashPrev);
1235         READWRITE(hashMerkleRoot);
1236         READWRITE(nTime);
1237         READWRITE(nBits);
1238         READWRITE(nNonce);
1239     )
1240
1241     uint256 GetBlockHash() const
1242     {
1243         CBlock block;
1244         block.nVersion        = nVersion;
1245         block.hashPrevBlock   = hashPrev;
1246         block.hashMerkleRoot  = hashMerkleRoot;
1247         block.nTime           = nTime;
1248         block.nBits           = nBits;
1249         block.nNonce          = nNonce;
1250         return block.GetHash();
1251     }
1252
1253
1254     std::string ToString() const
1255     {
1256         std::string str = "CDiskBlockIndex(";
1257         str += CBlockIndex::ToString();
1258         str += strprintf("\n                hashBlock=%s, hashPrev=%s, hashNext=%s)",
1259             GetBlockHash().ToString().c_str(),
1260             hashPrev.ToString().substr(0,20).c_str(),
1261             hashNext.ToString().substr(0,20).c_str());
1262         return str;
1263     }
1264
1265     void print() const
1266     {
1267         printf("%s\n", ToString().c_str());
1268     }
1269 };
1270
1271
1272
1273
1274
1275
1276
1277
1278 /** Describes a place in the block chain to another node such that if the
1279  * other node doesn't have the same branch, it can find a recent common trunk.
1280  * The further back it is, the further before the fork it may be.
1281  */
1282 class CBlockLocator
1283 {
1284 protected:
1285     std::vector<uint256> vHave;
1286 public:
1287
1288     CBlockLocator()
1289     {
1290     }
1291
1292     explicit CBlockLocator(const CBlockIndex* pindex)
1293     {
1294         Set(pindex);
1295     }
1296
1297     explicit CBlockLocator(uint256 hashBlock)
1298     {
1299         std::map<uint256, CBlockIndex*>::iterator mi = mapBlockIndex.find(hashBlock);
1300         if (mi != mapBlockIndex.end())
1301             Set((*mi).second);
1302     }
1303
1304     CBlockLocator(const std::vector<uint256>& vHaveIn)
1305     {
1306         vHave = vHaveIn;
1307     }
1308
1309     IMPLEMENT_SERIALIZE
1310     (
1311         if (!(nType & SER_GETHASH))
1312             READWRITE(nVersion);
1313         READWRITE(vHave);
1314     )
1315
1316     void SetNull()
1317     {
1318         vHave.clear();
1319     }
1320
1321     bool IsNull()
1322     {
1323         return vHave.empty();
1324     }
1325
1326     void Set(const CBlockIndex* pindex)
1327     {
1328         vHave.clear();
1329         int nStep = 1;
1330         while (pindex)
1331         {
1332             vHave.push_back(pindex->GetBlockHash());
1333
1334             // Exponentially larger steps back
1335             for (int i = 0; pindex && i < nStep; i++)
1336                 pindex = pindex->pprev;
1337             if (vHave.size() > 10)
1338                 nStep *= 2;
1339         }
1340         vHave.push_back(hashGenesisBlock);
1341     }
1342
1343     int GetDistanceBack()
1344     {
1345         // Retrace how far back it was in the sender's branch
1346         int nDistance = 0;
1347         int nStep = 1;
1348         BOOST_FOREACH(const uint256& hash, vHave)
1349         {
1350             std::map<uint256, CBlockIndex*>::iterator mi = mapBlockIndex.find(hash);
1351             if (mi != mapBlockIndex.end())
1352             {
1353                 CBlockIndex* pindex = (*mi).second;
1354                 if (pindex->IsInMainChain())
1355                     return nDistance;
1356             }
1357             nDistance += nStep;
1358             if (nDistance > 10)
1359                 nStep *= 2;
1360         }
1361         return nDistance;
1362     }
1363
1364     CBlockIndex* GetBlockIndex()
1365     {
1366         // Find the first block the caller has in the main chain
1367         BOOST_FOREACH(const uint256& hash, vHave)
1368         {
1369             std::map<uint256, CBlockIndex*>::iterator mi = mapBlockIndex.find(hash);
1370             if (mi != mapBlockIndex.end())
1371             {
1372                 CBlockIndex* pindex = (*mi).second;
1373                 if (pindex->IsInMainChain())
1374                     return pindex;
1375             }
1376         }
1377         return pindexGenesisBlock;
1378     }
1379
1380     uint256 GetBlockHash()
1381     {
1382         // Find the first block the caller has in the main chain
1383         BOOST_FOREACH(const uint256& hash, vHave)
1384         {
1385             std::map<uint256, CBlockIndex*>::iterator mi = mapBlockIndex.find(hash);
1386             if (mi != mapBlockIndex.end())
1387             {
1388                 CBlockIndex* pindex = (*mi).second;
1389                 if (pindex->IsInMainChain())
1390                     return hash;
1391             }
1392         }
1393         return hashGenesisBlock;
1394     }
1395
1396     int GetHeight()
1397     {
1398         CBlockIndex* pindex = GetBlockIndex();
1399         if (!pindex)
1400             return 0;
1401         return pindex->nHeight;
1402     }
1403 };
1404
1405
1406
1407
1408
1409
1410
1411
1412
1413 /** Alerts are for notifying old versions if they become too obsolete and
1414  * need to upgrade.  The message is displayed in the status bar.
1415  * Alert messages are broadcast as a vector of signed data.  Unserializing may
1416  * not read the entire buffer if the alert is for a newer version, but older
1417  * versions can still relay the original data.
1418  */
1419 class CUnsignedAlert
1420 {
1421 public:
1422     int nVersion;
1423     int64 nRelayUntil;      // when newer nodes stop relaying to newer nodes
1424     int64 nExpiration;
1425     int nID;
1426     int nCancel;
1427     std::set<int> setCancel;
1428     int nMinVer;            // lowest version inclusive
1429     int nMaxVer;            // highest version inclusive
1430     std::set<std::string> setSubVer;  // empty matches all
1431     int nPriority;
1432
1433     // Actions
1434     std::string strComment;
1435     std::string strStatusBar;
1436     std::string strReserved;
1437
1438     IMPLEMENT_SERIALIZE
1439     (
1440         READWRITE(this->nVersion);
1441         nVersion = this->nVersion;
1442         READWRITE(nRelayUntil);
1443         READWRITE(nExpiration);
1444         READWRITE(nID);
1445         READWRITE(nCancel);
1446         READWRITE(setCancel);
1447         READWRITE(nMinVer);
1448         READWRITE(nMaxVer);
1449         READWRITE(setSubVer);
1450         READWRITE(nPriority);
1451
1452         READWRITE(strComment);
1453         READWRITE(strStatusBar);
1454         READWRITE(strReserved);
1455     )
1456
1457     void SetNull()
1458     {
1459         nVersion = 1;
1460         nRelayUntil = 0;
1461         nExpiration = 0;
1462         nID = 0;
1463         nCancel = 0;
1464         setCancel.clear();
1465         nMinVer = 0;
1466         nMaxVer = 0;
1467         setSubVer.clear();
1468         nPriority = 0;
1469
1470         strComment.clear();
1471         strStatusBar.clear();
1472         strReserved.clear();
1473     }
1474
1475     std::string ToString() const
1476     {
1477         std::string strSetCancel;
1478         BOOST_FOREACH(int n, setCancel)
1479             strSetCancel += strprintf("%d ", n);
1480         std::string strSetSubVer;
1481         BOOST_FOREACH(std::string str, setSubVer)
1482             strSetSubVer += "\"" + str + "\" ";
1483         return strprintf(
1484                 "CAlert(\n"
1485                 "    nVersion     = %d\n"
1486                 "    nRelayUntil  = %"PRI64d"\n"
1487                 "    nExpiration  = %"PRI64d"\n"
1488                 "    nID          = %d\n"
1489                 "    nCancel      = %d\n"
1490                 "    setCancel    = %s\n"
1491                 "    nMinVer      = %d\n"
1492                 "    nMaxVer      = %d\n"
1493                 "    setSubVer    = %s\n"
1494                 "    nPriority    = %d\n"
1495                 "    strComment   = \"%s\"\n"
1496                 "    strStatusBar = \"%s\"\n"
1497                 ")\n",
1498             nVersion,
1499             nRelayUntil,
1500             nExpiration,
1501             nID,
1502             nCancel,
1503             strSetCancel.c_str(),
1504             nMinVer,
1505             nMaxVer,
1506             strSetSubVer.c_str(),
1507             nPriority,
1508             strComment.c_str(),
1509             strStatusBar.c_str());
1510     }
1511
1512     void print() const
1513     {
1514         printf("%s", ToString().c_str());
1515     }
1516 };
1517
1518 /** An alert is a combination of a serialized CUnsignedAlert and a signature. */
1519 class CAlert : public CUnsignedAlert
1520 {
1521 public:
1522     std::vector<unsigned char> vchMsg;
1523     std::vector<unsigned char> vchSig;
1524
1525     CAlert()
1526     {
1527         SetNull();
1528     }
1529
1530     IMPLEMENT_SERIALIZE
1531     (
1532         READWRITE(vchMsg);
1533         READWRITE(vchSig);
1534     )
1535
1536     void SetNull()
1537     {
1538         CUnsignedAlert::SetNull();
1539         vchMsg.clear();
1540         vchSig.clear();
1541     }
1542
1543     bool IsNull() const
1544     {
1545         return (nExpiration == 0);
1546     }
1547
1548     uint256 GetHash() const
1549     {
1550         return SerializeHash(*this);
1551     }
1552
1553     bool IsInEffect() const
1554     {
1555         return (GetAdjustedTime() < nExpiration);
1556     }
1557
1558     bool Cancels(const CAlert& alert) const
1559     {
1560         if (!IsInEffect())
1561             return false; // this was a no-op before 31403
1562         return (alert.nID <= nCancel || setCancel.count(alert.nID));
1563     }
1564
1565     bool AppliesTo(int nVersion, std::string strSubVerIn) const
1566     {
1567         // TODO: rework for client-version-embedded-in-strSubVer ?
1568         return (IsInEffect() &&
1569                 nMinVer <= nVersion && nVersion <= nMaxVer &&
1570                 (setSubVer.empty() || setSubVer.count(strSubVerIn)));
1571     }
1572
1573     bool AppliesToMe() const
1574     {
1575         return AppliesTo(PROTOCOL_VERSION, FormatSubVersion(CLIENT_NAME, CLIENT_VERSION, std::vector<std::string>()));
1576     }
1577
1578     bool RelayTo(CNode* pnode) const
1579     {
1580         if (!IsInEffect())
1581             return false;
1582         // returns true if wasn't already contained in the set
1583         if (pnode->setKnown.insert(GetHash()).second)
1584         {
1585             if (AppliesTo(pnode->nVersion, pnode->strSubVer) ||
1586                 AppliesToMe() ||
1587                 GetAdjustedTime() < nRelayUntil)
1588             {
1589                 pnode->PushMessage("alert", *this);
1590                 return true;
1591             }
1592         }
1593         return false;
1594     }
1595
1596     bool CheckSignature()
1597     {
1598         CKey key;
1599         if (!key.SetPubKey(ParseHex("04fc9702847840aaf195de8442ebecedf5b095cdbb9bc716bda9110971b28a49e0ead8564ff0db22209e0374782c093bb899692d524e9d6a6956e7c5ecbcd68284")))
1600             return error("CAlert::CheckSignature() : SetPubKey failed");
1601         if (!key.Verify(Hash(vchMsg.begin(), vchMsg.end()), vchSig))
1602             return error("CAlert::CheckSignature() : verify signature failed");
1603
1604         // Now unserialize the data
1605         CDataStream sMsg(vchMsg);
1606         sMsg >> *(CUnsignedAlert*)this;
1607         return true;
1608     }
1609
1610     bool ProcessAlert();
1611 };
1612
1613 #endif