diff --git a/src/coins.cpp b/src/coins.cpp index e5deef34348..2eadfde95d6 100644 --- a/src/coins.cpp +++ b/src/coins.cpp @@ -14,22 +14,6 @@ TRACEPOINT_SEMAPHORE(utxocache, add); TRACEPOINT_SEMAPHORE(utxocache, spent); TRACEPOINT_SEMAPHORE(utxocache, uncache); -std::optional CCoinsView::GetCoin(const COutPoint& outpoint) const { return std::nullopt; } -std::optional CCoinsView::PeekCoin(const COutPoint& outpoint) const { return GetCoin(outpoint); } -uint256 CCoinsView::GetBestBlock() const { return uint256(); } -std::vector CCoinsView::GetHeadBlocks() const { return std::vector(); } -void CCoinsView::BatchWrite(CoinsViewCacheCursor& cursor, const uint256& block_hash) -{ - for (auto it{cursor.Begin()}; it != cursor.End(); it = cursor.NextAndMaybeErase(*it)) { } -} - -std::unique_ptr CCoinsView::Cursor() const { return nullptr; } - -bool CCoinsView::HaveCoin(const COutPoint& outpoint) const -{ - return GetCoin(outpoint).has_value(); -} - CCoinsViewBacked::CCoinsViewBacked(CCoinsView* in_view) : base(in_view) { } std::optional CCoinsViewBacked::GetCoin(const COutPoint& outpoint) const { return base->GetCoin(outpoint); } std::optional CCoinsViewBacked::PeekCoin(const COutPoint& outpoint) const { return base->PeekCoin(outpoint); } diff --git a/src/coins.h b/src/coins.h index 876c5ed8b20..c18f7e10f93 100644 --- a/src/coins.h +++ b/src/coins.h @@ -303,43 +303,43 @@ private: bool m_will_erase; }; -/** Abstract view on the open txout dataset. */ +/** Pure abstract view on the open txout dataset. */ class CCoinsView { public: + //! As we use CCoinsViews polymorphically, have a virtual destructor + virtual ~CCoinsView() = default; + //! Retrieve the Coin (unspent transaction output) for a given outpoint. //! May populate the cache. Use PeekCoin() to perform a non-caching lookup. - virtual std::optional GetCoin(const COutPoint& outpoint) const; + virtual std::optional GetCoin(const COutPoint& outpoint) const = 0; //! Retrieve the Coin (unspent transaction output) for a given outpoint, without caching results. //! Does not populate the cache. Use GetCoin() to cache the result. - virtual std::optional PeekCoin(const COutPoint& outpoint) const; + virtual std::optional PeekCoin(const COutPoint& outpoint) const = 0; //! Just check whether a given outpoint is unspent. //! May populate the cache. Use PeekCoin() to perform a non-caching lookup. - virtual bool HaveCoin(const COutPoint& outpoint) const; + virtual bool HaveCoin(const COutPoint& outpoint) const = 0; //! Retrieve the block hash whose state this CCoinsView currently represents - virtual uint256 GetBestBlock() const; + virtual uint256 GetBestBlock() const = 0; //! Retrieve the range of blocks that may have been only partially written. //! If the database is in a consistent state, the result is the empty vector. //! Otherwise, a two-element vector is returned consisting of the new and //! the old block hash, in that order. - virtual std::vector GetHeadBlocks() const; + virtual std::vector GetHeadBlocks() const = 0; //! Do a bulk modification (multiple Coin changes + BestBlock change). //! The passed cursor is used to iterate through the coins. - virtual void BatchWrite(CoinsViewCacheCursor& cursor, const uint256& block_hash); + virtual void BatchWrite(CoinsViewCacheCursor& cursor, const uint256& block_hash) = 0; - //! Get a cursor to iterate over the whole state - virtual std::unique_ptr Cursor() const; + //! Get a cursor to iterate over the whole state. Implementations may return nullptr. + virtual std::unique_ptr Cursor() const = 0; - //! As we use CCoinsViews polymorphically, have a virtual destructor - virtual ~CCoinsView() = default; - - //! Estimate database size (0 if not implemented) - virtual size_t EstimateSize() const { return 0; } + //! Estimate database size + virtual size_t EstimateSize() const = 0; }; /** Noop coins view. */ @@ -353,6 +353,18 @@ public: CoinsViewEmpty(const CoinsViewEmpty&) = delete; CoinsViewEmpty& operator=(const CoinsViewEmpty&) = delete; + + std::optional GetCoin(const COutPoint&) const override { return {}; } + std::optional PeekCoin(const COutPoint& outpoint) const override { return GetCoin(outpoint); } + bool HaveCoin(const COutPoint& outpoint) const override { return !!GetCoin(outpoint); } + uint256 GetBestBlock() const override { return {}; } + std::vector GetHeadBlocks() const override { return {}; } + void BatchWrite(CoinsViewCacheCursor& cursor, const uint256&) override + { + for (auto it{cursor.Begin()}; it != cursor.End(); it = cursor.NextAndMaybeErase(*it)) { } + } + std::unique_ptr Cursor() const override { return {}; } + size_t EstimateSize() const override { return 0; } }; /** CCoinsView backed by another CCoinsView */ diff --git a/src/test/fuzz/coinscache_sim.cpp b/src/test/fuzz/coinscache_sim.cpp index 238281321f5..9d41a6c058b 100644 --- a/src/test/fuzz/coinscache_sim.cpp +++ b/src/test/fuzz/coinscache_sim.cpp @@ -247,7 +247,7 @@ FUZZ_TARGET(coinscache_sim) CallOneOf( provider, - [&]() { // GetCoin + [&]() { // PeekCoin/GetCoin uint32_t outpointidx = provider.ConsumeIntegralInRange(0, NUM_OUTPOINTS - 1); // Look up in simulation data. auto sim = lookup(outpointidx); diff --git a/src/txdb.cpp b/src/txdb.cpp index 592b739ba96..a098faa44bc 100644 --- a/src/txdb.cpp +++ b/src/txdb.cpp @@ -78,6 +78,11 @@ std::optional CCoinsViewDB::GetCoin(const COutPoint& outpoint) const return std::nullopt; } +std::optional CCoinsViewDB::PeekCoin(const COutPoint& outpoint) const +{ + return GetCoin(outpoint); +} + bool CCoinsViewDB::HaveCoin(const COutPoint& outpoint) const { return m_db->Exists(CoinEntry(&outpoint)); diff --git a/src/txdb.h b/src/txdb.h index 70618ef547d..b19b312a4b6 100644 --- a/src/txdb.h +++ b/src/txdb.h @@ -41,6 +41,7 @@ public: explicit CCoinsViewDB(DBParams db_params, CoinsViewOptions options); std::optional GetCoin(const COutPoint& outpoint) const override; + std::optional PeekCoin(const COutPoint& outpoint) const override; bool HaveCoin(const COutPoint& outpoint) const override; uint256 GetBestBlock() const override; std::vector GetHeadBlocks() const override; diff --git a/src/txmempool.h b/src/txmempool.h index d172c78e860..c4723f89155 100644 --- a/src/txmempool.h +++ b/src/txmempool.h @@ -768,7 +768,7 @@ protected: public: CCoinsViewMemPool(CCoinsView* baseIn, const CTxMemPool& mempoolIn); /** GetCoin, returning whether it exists and is not spent. Also updates m_non_base_coins if the - * coin is not fetched from base. */ + * coin is not fetched from base. May populate the base view on cache misses. */ std::optional GetCoin(const COutPoint& outpoint) const override; /** Add the coins created by this transaction. These coins are only temporarily stored in * m_temp_added and cannot be flushed to the back end. Only used for package validation. */