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.
17 class CAccountingEntry;
21 class CDiskBlockIndex;
29 extern unsigned int nWalletDBUpdated;
32 extern void DBFlush(bool fShutdown);
33 void ThreadFlushWalletDB(void* parg);
34 bool BackupWallet(const CWallet& wallet, const std::string& strDest);
37 /** RAII class that provides access to a Berkeley database */
43 std::vector<DbTxn*> vTxn;
46 explicit CDB(const char* pszFile, const char* pszMode="r+");
52 void operator=(const CDB&);
55 template<typename K, typename T>
56 bool Read(const K& key, T& value)
62 CDataStream ssKey(SER_DISK);
65 Dbt datKey(&ssKey[0], ssKey.size());
69 datValue.set_flags(DB_DBT_MALLOC);
70 int ret = pdb->get(GetTxn(), &datKey, &datValue, 0);
71 memset(datKey.get_data(), 0, datKey.get_size());
72 if (datValue.get_data() == NULL)
77 CDataStream ssValue((char*)datValue.get_data(), (char*)datValue.get_data() + datValue.get_size(), SER_DISK);
80 catch (std::exception &e) {
84 // Clear and free memory
85 memset(datValue.get_data(), 0, datValue.get_size());
86 free(datValue.get_data());
90 template<typename K, typename T>
91 bool Write(const K& key, const T& value, bool fOverwrite=true)
96 assert(!"Write called on database in read-only mode");
99 CDataStream ssKey(SER_DISK);
102 Dbt datKey(&ssKey[0], ssKey.size());
105 CDataStream ssValue(SER_DISK);
106 ssValue.reserve(10000);
108 Dbt datValue(&ssValue[0], ssValue.size());
111 int ret = pdb->put(GetTxn(), &datKey, &datValue, (fOverwrite ? 0 : DB_NOOVERWRITE));
113 // Clear memory in case it was a private key
114 memset(datKey.get_data(), 0, datKey.get_size());
115 memset(datValue.get_data(), 0, datValue.get_size());
120 bool Erase(const K& key)
125 assert(!"Erase called on database in read-only mode");
128 CDataStream ssKey(SER_DISK);
131 Dbt datKey(&ssKey[0], ssKey.size());
134 int ret = pdb->del(GetTxn(), &datKey, 0);
137 memset(datKey.get_data(), 0, datKey.get_size());
138 return (ret == 0 || ret == DB_NOTFOUND);
142 bool Exists(const K& key)
148 CDataStream ssKey(SER_DISK);
151 Dbt datKey(&ssKey[0], ssKey.size());
154 int ret = pdb->exists(GetTxn(), &datKey, 0);
157 memset(datKey.get_data(), 0, datKey.get_size());
166 int ret = pdb->cursor(NULL, &pcursor, 0);
172 int ReadAtCursor(Dbc* pcursor, CDataStream& ssKey, CDataStream& ssValue, unsigned int fFlags=DB_NEXT)
176 if (fFlags == DB_SET || fFlags == DB_SET_RANGE || fFlags == DB_GET_BOTH || fFlags == DB_GET_BOTH_RANGE)
178 datKey.set_data(&ssKey[0]);
179 datKey.set_size(ssKey.size());
182 if (fFlags == DB_GET_BOTH || fFlags == DB_GET_BOTH_RANGE)
184 datValue.set_data(&ssValue[0]);
185 datValue.set_size(ssValue.size());
187 datKey.set_flags(DB_DBT_MALLOC);
188 datValue.set_flags(DB_DBT_MALLOC);
189 int ret = pcursor->get(&datKey, &datValue, fFlags);
192 else if (datKey.get_data() == NULL || datValue.get_data() == NULL)
195 // Convert to streams
196 ssKey.SetType(SER_DISK);
198 ssKey.write((char*)datKey.get_data(), datKey.get_size());
199 ssValue.SetType(SER_DISK);
201 ssValue.write((char*)datValue.get_data(), datValue.get_size());
203 // Clear and free memory
204 memset(datKey.get_data(), 0, datKey.get_size());
205 memset(datValue.get_data(), 0, datValue.get_size());
206 free(datKey.get_data());
207 free(datValue.get_data());
225 int ret = dbenv.txn_begin(GetTxn(), &ptxn, DB_TXN_NOSYNC);
226 if (!ptxn || ret != 0)
228 vTxn.push_back(ptxn);
238 int ret = vTxn.back()->commit(0);
249 int ret = vTxn.back()->abort();
254 bool ReadVersion(int& nVersion)
257 return Read(std::string("version"), nVersion);
260 bool WriteVersion(int nVersion)
262 return Write(std::string("version"), nVersion);
265 bool static Rewrite(const std::string& strFile, const char* pszSkip = NULL);
274 /** Access to the transaction database (blkindex.dat) */
275 class CTxDB : public CDB
278 CTxDB(const char* pszMode="r+") : CDB("blkindex.dat", pszMode) { }
281 void operator=(const CTxDB&);
283 bool ReadTxIndex(uint256 hash, CTxIndex& txindex);
284 bool UpdateTxIndex(uint256 hash, const CTxIndex& txindex);
285 bool AddTxIndex(const CTransaction& tx, const CDiskTxPos& pos, int nHeight);
286 bool EraseTxIndex(const CTransaction& tx);
287 bool ContainsTx(uint256 hash);
288 bool ReadOwnerTxes(uint160 hash160, int nHeight, std::vector<CTransaction>& vtx);
289 bool ReadDiskTx(uint256 hash, CTransaction& tx, CTxIndex& txindex);
290 bool ReadDiskTx(uint256 hash, CTransaction& tx);
291 bool ReadDiskTx(COutPoint outpoint, CTransaction& tx, CTxIndex& txindex);
292 bool ReadDiskTx(COutPoint outpoint, CTransaction& tx);
293 bool WriteBlockIndex(const CDiskBlockIndex& blockindex);
294 bool EraseBlockIndex(uint256 hash);
295 bool ReadHashBestChain(uint256& hashBestChain);
296 bool WriteHashBestChain(uint256 hashBestChain);
297 bool ReadBestInvalidWork(CBigNum& bnBestInvalidWork);
298 bool WriteBestInvalidWork(CBigNum bnBestInvalidWork);
299 bool LoadBlockIndex();
305 /** Access to the (IP) address database (addr.dat) */
306 class CAddrDB : public CDB
309 CAddrDB(const char* pszMode="r+") : CDB("addr.dat", pszMode) { }
311 CAddrDB(const CAddrDB&);
312 void operator=(const CAddrDB&);
314 bool WriteAddrman(const CAddrMan& addr);
315 bool LoadAddresses();
318 bool LoadAddresses();
321 /** A key pool entry */
326 std::vector<unsigned char> vchPubKey;
333 CKeyPool(const std::vector<unsigned char>& vchPubKeyIn)
336 vchPubKey = vchPubKeyIn;
341 if (!(nType & SER_GETHASH))
344 READWRITE(vchPubKey);
350 /** Error statuses for the wallet database */
360 /** Access to the wallet database (wallet.dat) */
361 class CWalletDB : public CDB
364 CWalletDB(std::string strFilename, const char* pszMode="r+") : CDB(strFilename.c_str(), pszMode)
368 CWalletDB(const CWalletDB&);
369 void operator=(const CWalletDB&);
371 bool ReadName(const std::string& strAddress, std::string& strName)
374 return Read(std::make_pair(std::string("name"), strAddress), strName);
377 bool WriteName(const std::string& strAddress, const std::string& strName);
379 bool EraseName(const std::string& strAddress);
381 bool ReadTx(uint256 hash, CWalletTx& wtx)
383 return Read(std::make_pair(std::string("tx"), hash), wtx);
386 bool WriteTx(uint256 hash, const CWalletTx& wtx)
389 return Write(std::make_pair(std::string("tx"), hash), wtx);
392 bool EraseTx(uint256 hash)
395 return Erase(std::make_pair(std::string("tx"), hash));
398 bool ReadKey(const std::vector<unsigned char>& vchPubKey, CPrivKey& vchPrivKey)
401 return Read(std::make_pair(std::string("key"), vchPubKey), vchPrivKey);
404 bool WriteKey(const std::vector<unsigned char>& vchPubKey, const CPrivKey& vchPrivKey)
407 return Write(std::make_pair(std::string("key"), vchPubKey), vchPrivKey, false);
410 bool WriteCryptedKey(const std::vector<unsigned char>& vchPubKey, const std::vector<unsigned char>& vchCryptedSecret, bool fEraseUnencryptedKey = true)
413 if (!Write(std::make_pair(std::string("ckey"), vchPubKey), vchCryptedSecret, false))
415 if (fEraseUnencryptedKey)
417 Erase(std::make_pair(std::string("key"), vchPubKey));
418 Erase(std::make_pair(std::string("wkey"), vchPubKey));
423 bool WriteMasterKey(unsigned int nID, const CMasterKey& kMasterKey)
426 return Write(std::make_pair(std::string("mkey"), nID), kMasterKey, true);
429 // Support for BIP 0013 : see https://en.bitcoin.it/wiki/BIP_0013
430 bool ReadCScript(const uint160 &hash, CScript& redeemScript)
432 redeemScript.clear();
433 return Read(std::make_pair(std::string("cscript"), hash), redeemScript);
436 bool WriteCScript(const uint160& hash, const CScript& redeemScript)
439 return Write(std::make_pair(std::string("cscript"), hash), redeemScript, false);
442 bool WriteBestBlock(const CBlockLocator& locator)
445 return Write(std::string("bestblock"), locator);
448 bool ReadBestBlock(CBlockLocator& locator)
450 return Read(std::string("bestblock"), locator);
453 bool ReadDefaultKey(std::vector<unsigned char>& vchPubKey)
456 return Read(std::string("defaultkey"), vchPubKey);
459 bool WriteDefaultKey(const std::vector<unsigned char>& vchPubKey)
462 return Write(std::string("defaultkey"), vchPubKey);
465 bool ReadPool(int64 nPool, CKeyPool& keypool)
467 return Read(std::make_pair(std::string("pool"), nPool), keypool);
470 bool WritePool(int64 nPool, const CKeyPool& keypool)
473 return Write(std::make_pair(std::string("pool"), nPool), keypool);
476 bool ErasePool(int64 nPool)
479 return Erase(std::make_pair(std::string("pool"), nPool));
482 // Settings are no longer stored in wallet.dat; these are
483 // used only for backwards compatibility:
485 bool ReadSetting(const std::string& strKey, T& value)
487 return Read(std::make_pair(std::string("setting"), strKey), value);
490 bool WriteSetting(const std::string& strKey, const T& value)
493 return Write(std::make_pair(std::string("setting"), strKey), value);
495 bool EraseSetting(const std::string& strKey)
498 return Erase(std::make_pair(std::string("setting"), strKey));
501 bool WriteMinVersion(int nVersion)
503 return Write(std::string("minversion"), nVersion);
506 bool ReadAccount(const std::string& strAccount, CAccount& account);
507 bool WriteAccount(const std::string& strAccount, const CAccount& account);
508 bool WriteAccountingEntry(const CAccountingEntry& acentry);
509 int64 GetAccountCreditDebit(const std::string& strAccount);
510 void ListAccountCreditDebit(const std::string& strAccount, std::list<CAccountingEntry>& acentries);
512 int LoadWallet(CWallet* pwallet);