diff --git a/src/dbwrapper.h b/src/dbwrapper.h --- a/src/dbwrapper.h +++ b/src/dbwrapper.h @@ -222,6 +222,9 @@ bool fWipe = false, bool obfuscate = false); ~CDBWrapper(); + CDBWrapper(const CDBWrapper &) = delete; + CDBWrapper &operator=(const CDBWrapper &) = delete; + template bool Read(const K &key, V &value) const { CDataStream ssKey(SER_DISK, CLIENT_VERSION); ssKey.reserve(DBWRAPPER_PREALLOC_KEY_SIZE); diff --git a/src/txdb.h b/src/txdb.h --- a/src/txdb.h +++ b/src/txdb.h @@ -11,6 +11,7 @@ #include #include #include +#include #include #include @@ -113,11 +114,6 @@ explicit CBlockTreeDB(size_t nCacheSize, bool fMemory = false, bool fWipe = false); -private: - CBlockTreeDB(const CBlockTreeDB &); - void operator=(const CBlockTreeDB &); - -public: bool WriteBatchSync( const std::vector> &fileInfo, int nLastFile, const std::vector &blockinfo); @@ -134,4 +130,32 @@ std::function insertBlockIndex); }; +/** + * Access to the txindex database (indexes/txindex/) + * + * The database stores a block locator of the chain the database is synced to + * so that the TxIndex can efficiently determine the point it last stopped at. + * A locator is used instead of a simple hash of the chain tip because blocks + * and block index entries may not be flushed to disk until after this database + * is updated. + */ +class TxIndexDB : public CDBWrapper { +public: + explicit TxIndexDB(size_t n_cache_size, bool f_memory = false, + bool f_wipe = false); + + /// Read the disk location of the transaction data with the given hash. + /// Returns false if the transaction hash is not indexed. + bool ReadTxPos(const uint256 &txid, CDiskTxPos &pos) const; + + /// Write a batch of transaction positions to the DB. + bool WriteTxs(const std::vector> &v_pos); + + /// Read block locator of the chain that the txindex is in sync with. + bool ReadBestBlock(CBlockLocator &locator) const; + + /// Write block locator of the chain that the txindex is in sync with. + bool WriteBestBlock(const CBlockLocator &locator); +}; + #endif // BITCOIN_TXDB_H diff --git a/src/txdb.cpp b/src/txdb.cpp --- a/src/txdb.cpp +++ b/src/txdb.cpp @@ -454,3 +454,32 @@ LogPrintf("[%s].\n", ShutdownRequested() ? "CANCELLED" : "DONE"); return !ShutdownRequested(); } + +TxIndexDB::TxIndexDB(size_t n_cache_size, bool f_memory, bool f_wipe) + : CDBWrapper(GetDataDir() / "indexes" / "txindex", n_cache_size, f_memory, + f_wipe) {} + +bool TxIndexDB::ReadTxPos(const uint256 &txid, CDiskTxPos &pos) const { + return Read(std::make_pair(DB_TXINDEX, txid), pos); +} + +bool TxIndexDB::WriteTxs( + const std::vector> &v_pos) { + CDBBatch batch(*this); + for (const auto &tuple : v_pos) { + batch.Write(std::make_pair(DB_TXINDEX, tuple.first), tuple.second); + } + return WriteBatch(batch); +} + +bool TxIndexDB::ReadBestBlock(CBlockLocator &locator) const { + bool success = Read(DB_BEST_BLOCK, locator); + if (!success) { + locator.SetNull(); + } + return success; +} + +bool TxIndexDB::WriteBestBlock(const CBlockLocator &locator) { + return Write(DB_BEST_BLOCK, locator); +}