[index] Move disk IO logic from GetTransaction to TxIndex::FindTx.

This commit is contained in:
Jim Posen 2018-03-30 00:39:08 -07:00
parent e0a3b80033
commit a03f804f2a
3 changed files with 32 additions and 25 deletions

View file

@ -254,9 +254,30 @@ bool TxIndex::BlockUntilSyncedToCurrentChain()
return true; return true;
} }
bool TxIndex::FindTx(const uint256& txid, CDiskTxPos& pos) const bool TxIndex::FindTx(const uint256& tx_hash, uint256& block_hash, CTransactionRef& tx) const
{ {
return m_db->ReadTxPos(txid, pos); CDiskTxPos postx;
if (!m_db->ReadTxPos(tx_hash, postx)) {
return false;
}
CAutoFile file(OpenBlockFile(postx, true), SER_DISK, CLIENT_VERSION);
if (file.IsNull()) {
return error("%s: OpenBlockFile failed", __func__);
}
CBlockHeader header;
try {
file >> header;
fseek(file.Get(), postx.nTxOffset, SEEK_CUR);
file >> tx;
} catch (const std::exception& e) {
return error("%s: Deserialize or I/O error - %s", __func__, e.what());
}
if (tx->GetHash() != tx_hash) {
return error("%s: txid mismatch", __func__);
}
block_hash = header.GetHash();
return true;
} }
void TxIndex::Interrupt() void TxIndex::Interrupt()

View file

@ -6,6 +6,7 @@
#define BITCOIN_INDEX_TXINDEX_H #define BITCOIN_INDEX_TXINDEX_H
#include <primitives/block.h> #include <primitives/block.h>
#include <primitives/transaction.h>
#include <threadinterrupt.h> #include <threadinterrupt.h>
#include <txdb.h> #include <txdb.h>
#include <uint256.h> #include <uint256.h>
@ -69,8 +70,13 @@ public:
/// up from far behind, this method does not block and immediately returns false. /// up from far behind, this method does not block and immediately returns false.
bool BlockUntilSyncedToCurrentChain(); bool BlockUntilSyncedToCurrentChain();
/// Look up the on-disk location of a transaction by hash. /// Look up a transaction by hash.
bool FindTx(const uint256& txid, CDiskTxPos& pos) const; ///
/// @param[in] tx_hash The hash of the transaction to be returned.
/// @param[out] block_hash The hash of the block the transaction is found in.
/// @param[out] tx The transaction itself.
/// @return true if transaction is found, false otherwise
bool FindTx(const uint256& tx_hash, uint256& block_hash, CTransactionRef& tx) const;
void Interrupt(); void Interrupt();

View file

@ -1029,27 +1029,7 @@ bool GetTransaction(const uint256& hash, CTransactionRef& txOut, const Consensus
} }
if (g_txindex) { if (g_txindex) {
CDiskTxPos postx; return g_txindex->FindTx(hash, hashBlock, txOut);
if (g_txindex->FindTx(hash, postx)) {
CAutoFile file(OpenBlockFile(postx, true), SER_DISK, CLIENT_VERSION);
if (file.IsNull())
return error("%s: OpenBlockFile failed", __func__);
CBlockHeader header;
try {
file >> header;
fseek(file.Get(), postx.nTxOffset, SEEK_CUR);
file >> txOut;
} catch (const std::exception& e) {
return error("%s: Deserialize or I/O error - %s", __func__, e.what());
}
hashBlock = header.GetHash();
if (txOut->GetHash() != hash)
return error("%s: txid mismatch", __func__);
return true;
}
// transaction not found in index, nothing more can be done
return false;
} }
if (fAllowSlow) { // use coin database to locate block that contains transaction, and scan it if (fAllowSlow) { // use coin database to locate block that contains transaction, and scan it