raw
experimental-genesis    1 //  /****************************\
experimental-genesis 2 // * EXPERIMENTAL BRANCH. *
experimental-genesis 3 // * FOR LABORATORY USE ONLY. *
experimental-genesis 4 // ********************************
experimental-genesis 5 // ************
experimental-genesis 6 // **************
experimental-genesis 7 // ****************
experimental-genesis 8 // **** **** ****
experimental-genesis 9 // *** *** ***
experimental-genesis 10 // *** *** ***
experimental-genesis 11 // *** * * **
experimental-genesis 12 // ******** ********
experimental-genesis 13 // ******* ******
experimental-genesis 14 // *** **
experimental-genesis 15 // * ******* **
experimental-genesis 16 // ** * * * * *
experimental-genesis 17 // ** * * ***
experimental-genesis 18 // **** * * * * ****
experimental-genesis 19 // **** *** * * ** ***
experimental-genesis 20 // **** ********* ******
experimental-genesis 21 // ******* ***** *******
experimental-genesis 22 // ********* ****** **
experimental-genesis 23 // ** ****** ******
experimental-genesis 24 // ** ******* **
experimental-genesis 25 // ** ******* ***
experimental-genesis 26 // **** ******** ************
experimental-genesis 27 // ************ ************
experimental-genesis 28 // ******** *******
experimental-genesis 29 // ****** ****
experimental-genesis 30 // *** ***
experimental-genesis 31 // ********************************
experimental-genesis 32 // Copyright (c) 2009-2010 Satoshi Nakamoto
experimental-genesis 33 // Copyright (c) 2009-2012 The Bitcoin developers
experimental-genesis 34 // Distributed under the MIT/X11 software license, see the accompanying
experimental-genesis 35 // file license.txt or http://www.opensource.org/licenses/mit-license.php.
experimental-genesis 36 #ifndef BITCOIN_WALLET_H
experimental-genesis 37 #define BITCOIN_WALLET_H
experimental-genesis 38
experimental-genesis 39 #include "bignum.h"
experimental-genesis 40 #include "key.h"
experimental-genesis 41 #include "script.h"
experimental-genesis 42
experimental-genesis 43 class CWalletTx;
experimental-genesis 44 class CReserveKey;
experimental-genesis 45 class CWalletDB;
experimental-genesis 46
experimental-genesis 47 // A CWallet is an extension of a keystore, which also maintains a set of
experimental-genesis 48 // transactions and balances, and provides the ability to create new
experimental-genesis 49 // transactions
experimental-genesis 50 class CWallet : public CCryptoKeyStore
experimental-genesis 51 {
experimental-genesis 52 private:
experimental-genesis 53 bool SelectCoinsMinConf(int64 nTargetValue, int nConfMine, int nConfTheirs, std::set<std::pair<const CWalletTx*,unsigned int> >& setCoinsRet, int64& nValueRet) const;
experimental-genesis 54 bool SelectCoins(int64 nTargetValue, std::set<std::pair<const CWalletTx*,unsigned int> >& setCoinsRet, int64& nValueRet) const;
experimental-genesis 55
experimental-genesis 56 CWalletDB *pwalletdbEncryption;
experimental-genesis 57
experimental-genesis 58 public:
experimental-genesis 59 mutable CCriticalSection cs_wallet;
experimental-genesis 60
experimental-genesis 61 bool fFileBacked;
experimental-genesis 62 std::string strWalletFile;
experimental-genesis 63
experimental-genesis 64 std::set<int64> setKeyPool;
experimental-genesis 65
experimental-genesis 66 typedef std::map<unsigned int, CMasterKey> MasterKeyMap;
experimental-genesis 67 MasterKeyMap mapMasterKeys;
experimental-genesis 68 unsigned int nMasterKeyMaxID;
experimental-genesis 69
experimental-genesis 70 CWallet()
experimental-genesis 71 {
experimental-genesis 72 fFileBacked = false;
experimental-genesis 73 nMasterKeyMaxID = 0;
experimental-genesis 74 pwalletdbEncryption = NULL;
experimental-genesis 75 }
experimental-genesis 76 CWallet(std::string strWalletFileIn)
experimental-genesis 77 {
experimental-genesis 78 strWalletFile = strWalletFileIn;
experimental-genesis 79 fFileBacked = true;
experimental-genesis 80 nMasterKeyMaxID = 0;
experimental-genesis 81 pwalletdbEncryption = NULL;
experimental-genesis 82 }
experimental-genesis 83
experimental-genesis 84 std::map<uint256, CWalletTx> mapWallet;
experimental-genesis 85 std::vector<uint256> vWalletUpdated;
experimental-genesis 86
experimental-genesis 87 std::map<uint256, int> mapRequestCount;
experimental-genesis 88
experimental-genesis 89 std::map<CBitcoinAddress, std::string> mapAddressBook;
experimental-genesis 90
experimental-genesis 91 std::vector<unsigned char> vchDefaultKey;
experimental-genesis 92
experimental-genesis 93 // keystore implementation
experimental-genesis 94 // Adds a key to the store, and saves it to disk.
experimental-genesis 95 bool AddKey(const CKey& key);
experimental-genesis 96 // Adds a key to the store, without saving it to disk (used by LoadWallet)
experimental-genesis 97 bool LoadKey(const CKey& key) { return CCryptoKeyStore::AddKey(key); }
experimental-genesis 98
experimental-genesis 99 // Adds an encrypted key to the store, and saves it to disk.
experimental-genesis 100 bool AddCryptedKey(const std::vector<unsigned char> &vchPubKey, const std::vector<unsigned char> &vchCryptedSecret);
experimental-genesis 101 // Adds an encrypted key to the store, without saving it to disk (used by LoadWallet)
experimental-genesis 102 bool LoadCryptedKey(const std::vector<unsigned char> &vchPubKey, const std::vector<unsigned char> &vchCryptedSecret) { return CCryptoKeyStore::AddCryptedKey(vchPubKey, vchCryptedSecret); }
experimental-genesis 103
experimental-genesis 104 bool Unlock(const SecureString& strWalletPassphrase);
experimental-genesis 105 bool ChangeWalletPassphrase(const SecureString& strOldWalletPassphrase, const SecureString& strNewWalletPassphrase);
experimental-genesis 106 bool EncryptWallet(const SecureString& strWalletPassphrase);
experimental-genesis 107
experimental-genesis 108 bool AddToWallet(const CWalletTx& wtxIn);
experimental-genesis 109 bool AddToWalletIfInvolvingMe(const CTransaction& tx, const CBlock* pblock, bool fUpdate = false);
experimental-genesis 110 bool EraseFromWallet(uint256 hash);
experimental-genesis 111 void WalletUpdateSpent(const CTransaction& prevout);
experimental-genesis 112 int ScanForWalletTransactions(CBlockIndex* pindexStart, bool fUpdate = false);
experimental-genesis 113 void ReacceptWalletTransactions();
experimental-genesis 114 void ResendWalletTransactions();
experimental-genesis 115 int64 GetBalance() const;
experimental-genesis 116 int64 GetUnconfirmedBalance() const;
experimental-genesis 117 bool CreateTransaction(const std::vector<std::pair<CScript, int64> >& vecSend, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRet);
experimental-genesis 118 bool CreateTransaction(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRet);
experimental-genesis 119 bool CommitTransaction(CWalletTx& wtxNew, CReserveKey& reservekey);
experimental-genesis 120 std::string SendMoney(CScript scriptPubKey, int64 nValue, CWalletTx& wtxNew, bool fAskFee=false);
experimental-genesis 121 std::string SendMoneyToBitcoinAddress(const CBitcoinAddress& address, int64 nValue, CWalletTx& wtxNew, bool fAskFee=false);
experimental-genesis 122
experimental-genesis 123 bool NewKeyPool();
experimental-genesis 124 bool TopUpKeyPool();
experimental-genesis 125 void ReserveKeyFromKeyPool(int64& nIndex, CKeyPool& keypool);
experimental-genesis 126 void KeepKey(int64 nIndex);
experimental-genesis 127 void ReturnKey(int64 nIndex);
experimental-genesis 128 bool GetKeyFromPool(std::vector<unsigned char> &key, bool fAllowReuse=true);
experimental-genesis 129 int64 GetOldestKeyPoolTime();
experimental-genesis 130
experimental-genesis 131 bool IsMine(const CTxIn& txin) const;
experimental-genesis 132 int64 GetDebit(const CTxIn& txin) const;
experimental-genesis 133 bool IsMine(const CTxOut& txout) const
experimental-genesis 134 {
experimental-genesis 135 return ::IsMine(*this, txout.scriptPubKey);
experimental-genesis 136 }
experimental-genesis 137 int64 GetCredit(const CTxOut& txout) const
experimental-genesis 138 {
experimental-genesis 139 if (!MoneyRange(txout.nValue))
experimental-genesis 140 throw std::runtime_error("CWallet::GetCredit() : value out of range");
experimental-genesis 141 return (IsMine(txout) ? txout.nValue : 0);
experimental-genesis 142 }
experimental-genesis 143 bool IsChange(const CTxOut& txout) const
experimental-genesis 144 {
experimental-genesis 145 CBitcoinAddress address;
experimental-genesis 146 if (ExtractAddress(txout.scriptPubKey, this, address))
experimental-genesis 147 CRITICAL_BLOCK(cs_wallet)
experimental-genesis 148 if (!mapAddressBook.count(address))
experimental-genesis 149 return true;
experimental-genesis 150 return false;
experimental-genesis 151 }
experimental-genesis 152 int64 GetChange(const CTxOut& txout) const
experimental-genesis 153 {
experimental-genesis 154 if (!MoneyRange(txout.nValue))
experimental-genesis 155 throw std::runtime_error("CWallet::GetChange() : value out of range");
experimental-genesis 156 return (IsChange(txout) ? txout.nValue : 0);
experimental-genesis 157 }
experimental-genesis 158 bool IsMine(const CTransaction& tx) const
experimental-genesis 159 {
experimental-genesis 160 BOOST_FOREACH(const CTxOut& txout, tx.vout)
experimental-genesis 161 if (IsMine(txout))
experimental-genesis 162 return true;
experimental-genesis 163 return false;
experimental-genesis 164 }
experimental-genesis 165 bool IsFromMe(const CTransaction& tx) const
experimental-genesis 166 {
experimental-genesis 167 return (GetDebit(tx) > 0);
experimental-genesis 168 }
experimental-genesis 169 int64 GetDebit(const CTransaction& tx) const
experimental-genesis 170 {
experimental-genesis 171 int64 nDebit = 0;
experimental-genesis 172 BOOST_FOREACH(const CTxIn& txin, tx.vin)
experimental-genesis 173 {
experimental-genesis 174 nDebit += GetDebit(txin);
experimental-genesis 175 if (!MoneyRange(nDebit))
experimental-genesis 176 throw std::runtime_error("CWallet::GetDebit() : value out of range");
experimental-genesis 177 }
experimental-genesis 178 return nDebit;
experimental-genesis 179 }
experimental-genesis 180 int64 GetCredit(const CTransaction& tx) const
experimental-genesis 181 {
experimental-genesis 182 int64 nCredit = 0;
experimental-genesis 183 BOOST_FOREACH(const CTxOut& txout, tx.vout)
experimental-genesis 184 {
experimental-genesis 185 nCredit += GetCredit(txout);
experimental-genesis 186 if (!MoneyRange(nCredit))
experimental-genesis 187 throw std::runtime_error("CWallet::GetCredit() : value out of range");
experimental-genesis 188 }
experimental-genesis 189 return nCredit;
experimental-genesis 190 }
experimental-genesis 191 int64 GetChange(const CTransaction& tx) const
experimental-genesis 192 {
experimental-genesis 193 int64 nChange = 0;
experimental-genesis 194 BOOST_FOREACH(const CTxOut& txout, tx.vout)
experimental-genesis 195 {
experimental-genesis 196 nChange += GetChange(txout);
experimental-genesis 197 if (!MoneyRange(nChange))
experimental-genesis 198 throw std::runtime_error("CWallet::GetChange() : value out of range");
experimental-genesis 199 }
experimental-genesis 200 return nChange;
experimental-genesis 201 }
experimental-genesis 202 void SetBestChain(const CBlockLocator& loc)
experimental-genesis 203 {
experimental-genesis 204 CWalletDB walletdb(strWalletFile);
experimental-genesis 205 walletdb.WriteBestBlock(loc);
experimental-genesis 206 }
experimental-genesis 207
experimental-genesis 208 int LoadWallet(bool& fFirstRunRet);
experimental-genesis 209 // bool BackupWallet(const std::string& strDest);
experimental-genesis 210
experimental-genesis 211 bool SetAddressBookName(const CBitcoinAddress& address, const std::string& strName);
experimental-genesis 212
experimental-genesis 213 bool DelAddressBookName(const CBitcoinAddress& address);
experimental-genesis 214
experimental-genesis 215 void UpdatedTransaction(const uint256 &hashTx)
experimental-genesis 216 {
experimental-genesis 217 CRITICAL_BLOCK(cs_wallet)
experimental-genesis 218 vWalletUpdated.push_back(hashTx);
experimental-genesis 219 }
experimental-genesis 220
experimental-genesis 221 void PrintWallet(const CBlock& block);
experimental-genesis 222
experimental-genesis 223 void Inventory(const uint256 &hash)
experimental-genesis 224 {
experimental-genesis 225 CRITICAL_BLOCK(cs_wallet)
experimental-genesis 226 {
experimental-genesis 227 std::map<uint256, int>::iterator mi = mapRequestCount.find(hash);
experimental-genesis 228 if (mi != mapRequestCount.end())
experimental-genesis 229 (*mi).second++;
experimental-genesis 230 }
experimental-genesis 231 }
experimental-genesis 232
experimental-genesis 233 int GetKeyPoolSize()
experimental-genesis 234 {
experimental-genesis 235 return setKeyPool.size();
experimental-genesis 236 }
experimental-genesis 237
experimental-genesis 238 bool GetTransaction(const uint256 &hashTx, CWalletTx& wtx);
experimental-genesis 239
experimental-genesis 240 bool SetDefaultKey(const std::vector<unsigned char> &vchPubKey);
experimental-genesis 241 };
experimental-genesis 242
experimental-genesis 243
experimental-genesis 244 class CReserveKey
experimental-genesis 245 {
experimental-genesis 246 protected:
experimental-genesis 247 CWallet* pwallet;
experimental-genesis 248 int64 nIndex;
experimental-genesis 249 std::vector<unsigned char> vchPubKey;
experimental-genesis 250 public:
experimental-genesis 251 CReserveKey(CWallet* pwalletIn)
experimental-genesis 252 {
experimental-genesis 253 nIndex = -1;
experimental-genesis 254 pwallet = pwalletIn;
experimental-genesis 255 }
experimental-genesis 256
experimental-genesis 257 ~CReserveKey()
experimental-genesis 258 {
experimental-genesis 259 if (!fShutdown)
experimental-genesis 260 ReturnKey();
experimental-genesis 261 }
experimental-genesis 262
experimental-genesis 263 void ReturnKey();
experimental-genesis 264 std::vector<unsigned char> GetReservedKey();
experimental-genesis 265 void KeepKey();
experimental-genesis 266 };
experimental-genesis 267
experimental-genesis 268
experimental-genesis 269 //
experimental-genesis 270 // A transaction with a bunch of additional info that only the owner cares
experimental-genesis 271 // about. It includes any unrecorded transactions needed to link it back
experimental-genesis 272 // to the block chain.
experimental-genesis 273 //
experimental-genesis 274 class CWalletTx : public CMerkleTx
experimental-genesis 275 {
experimental-genesis 276 public:
experimental-genesis 277 const CWallet* pwallet;
experimental-genesis 278
experimental-genesis 279 std::vector<CMerkleTx> vtxPrev;
experimental-genesis 280 std::map<std::string, std::string> mapValue;
experimental-genesis 281 std::vector<std::pair<std::string, std::string> > vOrderForm;
experimental-genesis 282 unsigned int fTimeReceivedIsTxTime;
experimental-genesis 283 unsigned int nTimeReceived; // time received by this node
experimental-genesis 284 char fFromMe;
experimental-genesis 285 std::string strFromAccount;
experimental-genesis 286 std::vector<char> vfSpent; // which outputs are already spent
experimental-genesis 287
experimental-genesis 288 // memory only
experimental-genesis 289 mutable char fDebitCached;
experimental-genesis 290 mutable char fCreditCached;
experimental-genesis 291 mutable char fAvailableCreditCached;
experimental-genesis 292 mutable char fChangeCached;
experimental-genesis 293 mutable int64 nDebitCached;
experimental-genesis 294 mutable int64 nCreditCached;
experimental-genesis 295 mutable int64 nAvailableCreditCached;
experimental-genesis 296 mutable int64 nChangeCached;
experimental-genesis 297
experimental-genesis 298 // memory only UI hints
experimental-genesis 299 mutable unsigned int nTimeDisplayed;
experimental-genesis 300 mutable int nLinesDisplayed;
experimental-genesis 301 mutable char fConfirmedDisplayed;
experimental-genesis 302
experimental-genesis 303 CWalletTx()
experimental-genesis 304 {
experimental-genesis 305 Init(NULL);
experimental-genesis 306 }
experimental-genesis 307
experimental-genesis 308 CWalletTx(const CWallet* pwalletIn)
experimental-genesis 309 {
experimental-genesis 310 Init(pwalletIn);
experimental-genesis 311 }
experimental-genesis 312
experimental-genesis 313 CWalletTx(const CWallet* pwalletIn, const CMerkleTx& txIn) : CMerkleTx(txIn)
experimental-genesis 314 {
experimental-genesis 315 Init(pwalletIn);
experimental-genesis 316 }
experimental-genesis 317
experimental-genesis 318 CWalletTx(const CWallet* pwalletIn, const CTransaction& txIn) : CMerkleTx(txIn)
experimental-genesis 319 {
experimental-genesis 320 Init(pwalletIn);
experimental-genesis 321 }
experimental-genesis 322
experimental-genesis 323 void Init(const CWallet* pwalletIn)
experimental-genesis 324 {
experimental-genesis 325 pwallet = pwalletIn;
experimental-genesis 326 vtxPrev.clear();
experimental-genesis 327 mapValue.clear();
experimental-genesis 328 vOrderForm.clear();
experimental-genesis 329 fTimeReceivedIsTxTime = false;
experimental-genesis 330 nTimeReceived = 0;
experimental-genesis 331 fFromMe = false;
experimental-genesis 332 strFromAccount.clear();
experimental-genesis 333 vfSpent.clear();
experimental-genesis 334 fDebitCached = false;
experimental-genesis 335 fCreditCached = false;
experimental-genesis 336 fAvailableCreditCached = false;
experimental-genesis 337 fChangeCached = false;
experimental-genesis 338 nDebitCached = 0;
experimental-genesis 339 nCreditCached = 0;
experimental-genesis 340 nAvailableCreditCached = 0;
experimental-genesis 341 nChangeCached = 0;
experimental-genesis 342 nTimeDisplayed = 0;
experimental-genesis 343 nLinesDisplayed = 0;
experimental-genesis 344 fConfirmedDisplayed = false;
experimental-genesis 345 }
experimental-genesis 346
experimental-genesis 347 IMPLEMENT_SERIALIZE
experimental-genesis 348 (
experimental-genesis 349 CWalletTx* pthis = const_cast<CWalletTx*>(this);
experimental-genesis 350 if (fRead)
experimental-genesis 351 pthis->Init(NULL);
experimental-genesis 352 char fSpent = false;
experimental-genesis 353
experimental-genesis 354 if (!fRead)
experimental-genesis 355 {
experimental-genesis 356 pthis->mapValue["fromaccount"] = pthis->strFromAccount;
experimental-genesis 357
experimental-genesis 358 std::string str;
experimental-genesis 359 BOOST_FOREACH(char f, vfSpent)
experimental-genesis 360 {
experimental-genesis 361 str += (f ? '1' : '0');
experimental-genesis 362 if (f)
experimental-genesis 363 fSpent = true;
experimental-genesis 364 }
experimental-genesis 365 pthis->mapValue["spent"] = str;
experimental-genesis 366 }
experimental-genesis 367
experimental-genesis 368 nSerSize += SerReadWrite(s, *(CMerkleTx*)this, nType, nVersion,ser_action);
experimental-genesis 369 READWRITE(vtxPrev);
experimental-genesis 370 READWRITE(mapValue);
experimental-genesis 371 READWRITE(vOrderForm);
experimental-genesis 372 READWRITE(fTimeReceivedIsTxTime);
experimental-genesis 373 READWRITE(nTimeReceived);
experimental-genesis 374 READWRITE(fFromMe);
experimental-genesis 375 READWRITE(fSpent);
experimental-genesis 376
experimental-genesis 377 if (fRead)
experimental-genesis 378 {
experimental-genesis 379 pthis->strFromAccount = pthis->mapValue["fromaccount"];
experimental-genesis 380
experimental-genesis 381 if (mapValue.count("spent"))
experimental-genesis 382 BOOST_FOREACH(char c, pthis->mapValue["spent"])
experimental-genesis 383 pthis->vfSpent.push_back(c != '0');
experimental-genesis 384 else
experimental-genesis 385 pthis->vfSpent.assign(vout.size(), fSpent);
experimental-genesis 386 }
experimental-genesis 387
experimental-genesis 388 pthis->mapValue.erase("fromaccount");
experimental-genesis 389 pthis->mapValue.erase("version");
experimental-genesis 390 pthis->mapValue.erase("spent");
experimental-genesis 391 )
experimental-genesis 392
experimental-genesis 393 // marks certain txout's as spent
experimental-genesis 394 // returns true if any update took place
experimental-genesis 395 bool UpdateSpent(const std::vector<char>& vfNewSpent)
experimental-genesis 396 {
experimental-genesis 397 bool fReturn = false;
experimental-genesis 398 for (int i=0; i < vfNewSpent.size(); i++)
experimental-genesis 399 {
experimental-genesis 400 if (i == vfSpent.size())
experimental-genesis 401 break;
experimental-genesis 402
experimental-genesis 403 if (vfNewSpent[i] && !vfSpent[i])
experimental-genesis 404 {
experimental-genesis 405 vfSpent[i] = true;
experimental-genesis 406 fReturn = true;
experimental-genesis 407 fAvailableCreditCached = false;
experimental-genesis 408 }
experimental-genesis 409 }
experimental-genesis 410 return fReturn;
experimental-genesis 411 }
experimental-genesis 412
experimental-genesis 413 // make sure balances are recalculated
experimental-genesis 414 void MarkDirty()
experimental-genesis 415 {
experimental-genesis 416 fCreditCached = false;
experimental-genesis 417 fAvailableCreditCached = false;
experimental-genesis 418 fDebitCached = false;
experimental-genesis 419 fChangeCached = false;
experimental-genesis 420 }
experimental-genesis 421
experimental-genesis 422 void MarkSpent(unsigned int nOut)
experimental-genesis 423 {
experimental-genesis 424 if (nOut >= vout.size())
experimental-genesis 425 throw std::runtime_error("CWalletTx::MarkSpent() : nOut out of range");
experimental-genesis 426 vfSpent.resize(vout.size());
experimental-genesis 427 if (!vfSpent[nOut])
experimental-genesis 428 {
experimental-genesis 429 vfSpent[nOut] = true;
experimental-genesis 430 fAvailableCreditCached = false;
experimental-genesis 431 }
experimental-genesis 432 }
experimental-genesis 433
experimental-genesis 434 bool IsSpent(unsigned int nOut) const
experimental-genesis 435 {
experimental-genesis 436 if (nOut >= vout.size())
experimental-genesis 437 throw std::runtime_error("CWalletTx::IsSpent() : nOut out of range");
experimental-genesis 438 if (nOut >= vfSpent.size())
experimental-genesis 439 return false;
experimental-genesis 440 return (!!vfSpent[nOut]);
experimental-genesis 441 }
experimental-genesis 442
experimental-genesis 443 int64 GetDebit() const
experimental-genesis 444 {
experimental-genesis 445 if (vin.empty())
experimental-genesis 446 return 0;
experimental-genesis 447 if (fDebitCached)
experimental-genesis 448 return nDebitCached;
experimental-genesis 449 nDebitCached = pwallet->GetDebit(*this);
experimental-genesis 450 fDebitCached = true;
experimental-genesis 451 return nDebitCached;
experimental-genesis 452 }
experimental-genesis 453
experimental-genesis 454 int64 GetCredit(bool fUseCache=true) const
experimental-genesis 455 {
experimental-genesis 456 // Must wait until coinbase is safely deep enough in the chain before valuing it
experimental-genesis 457 if (IsCoinBase() && GetBlocksToMaturity() > 0)
experimental-genesis 458 return 0;
experimental-genesis 459
experimental-genesis 460 // GetBalance can assume transactions in mapWallet won't change
experimental-genesis 461 if (fUseCache && fCreditCached)
experimental-genesis 462 return nCreditCached;
experimental-genesis 463 nCreditCached = pwallet->GetCredit(*this);
experimental-genesis 464 fCreditCached = true;
experimental-genesis 465 return nCreditCached;
experimental-genesis 466 }
experimental-genesis 467
experimental-genesis 468 int64 GetAvailableCredit(bool fUseCache=true) const
experimental-genesis 469 {
experimental-genesis 470 // Must wait until coinbase is safely deep enough in the chain before valuing it
experimental-genesis 471 if (IsCoinBase() && GetBlocksToMaturity() > 0)
experimental-genesis 472 return 0;
experimental-genesis 473
experimental-genesis 474 if (fUseCache && fAvailableCreditCached)
experimental-genesis 475 return nAvailableCreditCached;
experimental-genesis 476
experimental-genesis 477 int64 nCredit = 0;
experimental-genesis 478 for (int i = 0; i < vout.size(); i++)
experimental-genesis 479 {
experimental-genesis 480 if (!IsSpent(i))
experimental-genesis 481 {
experimental-genesis 482 const CTxOut &txout = vout[i];
experimental-genesis 483 nCredit += pwallet->GetCredit(txout);
experimental-genesis 484 if (!MoneyRange(nCredit))
experimental-genesis 485 throw std::runtime_error("CWalletTx::GetAvailableCredit() : value out of range");
experimental-genesis 486 }
experimental-genesis 487 }
experimental-genesis 488
experimental-genesis 489 nAvailableCreditCached = nCredit;
experimental-genesis 490 fAvailableCreditCached = true;
experimental-genesis 491 return nCredit;
experimental-genesis 492 }
experimental-genesis 493
experimental-genesis 494
experimental-genesis 495 int64 GetChange() const
experimental-genesis 496 {
experimental-genesis 497 if (fChangeCached)
experimental-genesis 498 return nChangeCached;
experimental-genesis 499 nChangeCached = pwallet->GetChange(*this);
experimental-genesis 500 fChangeCached = true;
experimental-genesis 501 return nChangeCached;
experimental-genesis 502 }
experimental-genesis 503
experimental-genesis 504 void GetAmounts(int64& nGeneratedImmature, int64& nGeneratedMature, std::list<std::pair<CBitcoinAddress, int64> >& listReceived,
experimental-genesis 505 std::list<std::pair<CBitcoinAddress, int64> >& listSent, int64& nFee, std::string& strSentAccount) const;
experimental-genesis 506
experimental-genesis 507 void GetAccountAmounts(const std::string& strAccount, int64& nGenerated, int64& nReceived,
experimental-genesis 508 int64& nSent, int64& nFee) const;
experimental-genesis 509
experimental-genesis 510 bool IsFromMe() const
experimental-genesis 511 {
experimental-genesis 512 return (GetDebit() > 0);
experimental-genesis 513 }
experimental-genesis 514
experimental-genesis 515 bool IsConfirmed() const
experimental-genesis 516 {
experimental-genesis 517 // Quick answer in most cases
experimental-genesis 518 if (!IsFinal())
experimental-genesis 519 return false;
experimental-genesis 520 if (GetDepthInMainChain() >= 1)
experimental-genesis 521 return true;
experimental-genesis 522 if (!IsFromMe()) // using wtx's cached debit
experimental-genesis 523 return false;
experimental-genesis 524
experimental-genesis 525 // If no confirmations but it's from us, we can still
experimental-genesis 526 // consider it confirmed if all dependencies are confirmed
experimental-genesis 527 std::map<uint256, const CMerkleTx*> mapPrev;
experimental-genesis 528 std::vector<const CMerkleTx*> vWorkQueue;
experimental-genesis 529 vWorkQueue.reserve(vtxPrev.size()+1);
experimental-genesis 530 vWorkQueue.push_back(this);
experimental-genesis 531 for (int i = 0; i < vWorkQueue.size(); i++)
experimental-genesis 532 {
experimental-genesis 533 const CMerkleTx* ptx = vWorkQueue[i];
experimental-genesis 534
experimental-genesis 535 if (!ptx->IsFinal())
experimental-genesis 536 return false;
experimental-genesis 537 if (ptx->GetDepthInMainChain() >= 1)
experimental-genesis 538 continue;
experimental-genesis 539 if (!pwallet->IsFromMe(*ptx))
experimental-genesis 540 return false;
experimental-genesis 541
experimental-genesis 542 if (mapPrev.empty())
experimental-genesis 543 BOOST_FOREACH(const CMerkleTx& tx, vtxPrev)
experimental-genesis 544 mapPrev[tx.GetHash()] = &tx;
experimental-genesis 545
experimental-genesis 546 BOOST_FOREACH(const CTxIn& txin, ptx->vin)
experimental-genesis 547 {
experimental-genesis 548 if (!mapPrev.count(txin.prevout.hash))
experimental-genesis 549 return false;
experimental-genesis 550 vWorkQueue.push_back(mapPrev[txin.prevout.hash]);
experimental-genesis 551 }
experimental-genesis 552 }
experimental-genesis 553 return true;
experimental-genesis 554 }
experimental-genesis 555
experimental-genesis 556 bool WriteToDisk();
experimental-genesis 557
experimental-genesis 558 int64 GetTxTime() const;
experimental-genesis 559 int GetRequestCount() const;
experimental-genesis 560
experimental-genesis 561 void AddSupportingTransactions(CTxDB& txdb);
experimental-genesis 562
experimental-genesis 563 bool AcceptWalletTransaction(CTxDB& txdb, bool fCheckInputs=true);
experimental-genesis 564 bool AcceptWalletTransaction();
experimental-genesis 565
experimental-genesis 566 void RelayWalletTransaction(CTxDB& txdb);
experimental-genesis 567 void RelayWalletTransaction();
experimental-genesis 568 };
experimental-genesis 569
experimental-genesis 570
experimental-genesis 571 //
experimental-genesis 572 // Private key that includes an expiration date in case it never gets used.
experimental-genesis 573 //
experimental-genesis 574 class CWalletKey
experimental-genesis 575 {
experimental-genesis 576 public:
experimental-genesis 577 CPrivKey vchPrivKey;
experimental-genesis 578 int64 nTimeCreated;
experimental-genesis 579 int64 nTimeExpires;
experimental-genesis 580 std::string strComment;
experimental-genesis 581 //// todo: add something to note what created it (user, getnewaddress, change)
experimental-genesis 582 //// maybe should have a map<string, string> property map
experimental-genesis 583
experimental-genesis 584 CWalletKey(int64 nExpires=0)
experimental-genesis 585 {
experimental-genesis 586 nTimeCreated = (nExpires ? GetTime() : 0);
experimental-genesis 587 nTimeExpires = nExpires;
experimental-genesis 588 }
experimental-genesis 589
experimental-genesis 590 IMPLEMENT_SERIALIZE
experimental-genesis 591 (
experimental-genesis 592 if (!(nType & SER_GETHASH))
experimental-genesis 593 READWRITE(nVersion);
experimental-genesis 594 READWRITE(vchPrivKey);
experimental-genesis 595 READWRITE(nTimeCreated);
experimental-genesis 596 READWRITE(nTimeExpires);
experimental-genesis 597 READWRITE(strComment);
experimental-genesis 598 )
experimental-genesis 599 };
experimental-genesis 600
experimental-genesis 601
experimental-genesis 602
experimental-genesis 603
experimental-genesis 604
experimental-genesis 605
experimental-genesis 606 //
experimental-genesis 607 // Account information.
experimental-genesis 608 // Stored in wallet with key "acc"+string account name
experimental-genesis 609 //
experimental-genesis 610 class CAccount
experimental-genesis 611 {
experimental-genesis 612 public:
experimental-genesis 613 std::vector<unsigned char> vchPubKey;
experimental-genesis 614
experimental-genesis 615 CAccount()
experimental-genesis 616 {
experimental-genesis 617 SetNull();
experimental-genesis 618 }
experimental-genesis 619
experimental-genesis 620 void SetNull()
experimental-genesis 621 {
experimental-genesis 622 vchPubKey.clear();
experimental-genesis 623 }
experimental-genesis 624
experimental-genesis 625 IMPLEMENT_SERIALIZE
experimental-genesis 626 (
experimental-genesis 627 if (!(nType & SER_GETHASH))
experimental-genesis 628 READWRITE(nVersion);
experimental-genesis 629 READWRITE(vchPubKey);
experimental-genesis 630 )
experimental-genesis 631 };
experimental-genesis 632
experimental-genesis 633
experimental-genesis 634
experimental-genesis 635 //
experimental-genesis 636 // Internal transfers.
experimental-genesis 637 // Database key is acentry<account><counter>
experimental-genesis 638 //
experimental-genesis 639 class CAccountingEntry
experimental-genesis 640 {
experimental-genesis 641 public:
experimental-genesis 642 std::string strAccount;
experimental-genesis 643 int64 nCreditDebit;
experimental-genesis 644 int64 nTime;
experimental-genesis 645 std::string strOtherAccount;
experimental-genesis 646 std::string strComment;
experimental-genesis 647
experimental-genesis 648 CAccountingEntry()
experimental-genesis 649 {
experimental-genesis 650 SetNull();
experimental-genesis 651 }
experimental-genesis 652
experimental-genesis 653 void SetNull()
experimental-genesis 654 {
experimental-genesis 655 nCreditDebit = 0;
experimental-genesis 656 nTime = 0;
experimental-genesis 657 strAccount.clear();
experimental-genesis 658 strOtherAccount.clear();
experimental-genesis 659 strComment.clear();
experimental-genesis 660 }
experimental-genesis 661
experimental-genesis 662 IMPLEMENT_SERIALIZE
experimental-genesis 663 (
experimental-genesis 664 if (!(nType & SER_GETHASH))
experimental-genesis 665 READWRITE(nVersion);
experimental-genesis 666 // Note: strAccount is serialized as part of the key, not here.
experimental-genesis 667 READWRITE(nCreditDebit);
experimental-genesis 668 READWRITE(nTime);
experimental-genesis 669 READWRITE(strOtherAccount);
experimental-genesis 670 READWRITE(strComment);
experimental-genesis 671 )
experimental-genesis 672 };
experimental-genesis 673
experimental-genesis 674 bool GetWalletFile(CWallet* pwallet, std::string &strWalletFileOut);
experimental-genesis 675
experimental-genesis 676 #endif