From 54476e829fb83b9894c84691ec68d8417f336ffe Mon Sep 17 00:00:00 2001 From: Zhang Song Date: Thu, 10 Apr 2025 11:11:15 +0800 Subject: [PATCH] crimson/os/seastore: move BtreeNodeMapping::is_viewable_by_trans to CachedExtent Signed-off-by: Zhang Song --- .../os/seastore/btree/btree_range_pin.h | 27 +--------- src/crimson/os/seastore/cached_extent.cc | 51 +++++++++++++++++++ src/crimson/os/seastore/cached_extent.h | 21 ++++++++ src/crimson/os/seastore/transaction.h | 7 ++- 4 files changed, 79 insertions(+), 27 deletions(-) diff --git a/src/crimson/os/seastore/btree/btree_range_pin.h b/src/crimson/os/seastore/btree/btree_range_pin.h index 1106aeccab620..bfc0e8e548048 100644 --- a/src/crimson/os/seastore/btree/btree_range_pin.h +++ b/src/crimson/os/seastore/btree/btree_range_pin.h @@ -173,34 +173,9 @@ public: return parent->has_been_invalidated(); } - bool is_unviewable_by_trans(CachedExtent& extent, Transaction &t) const { - if (!extent.is_valid()) { - return true; - } - if (extent.is_pending()) { - assert(extent.is_pending_in_trans(t.get_trans_id())); - return false; - } - auto &pendings = extent.mutation_pending_extents; - auto trans_id = t.get_trans_id(); - bool unviewable = (pendings.find(trans_id, trans_spec_view_t::cmp_t()) != - pendings.end()); - if (!unviewable) { - auto &trans = extent.retired_transactions; - unviewable = (trans.find(trans_id, trans_spec_view_t::cmp_t()) != - trans.end()); - assert(unviewable == - t.is_stable_extent_retired(extent.get_paddr(), extent.get_length())); - } - return unviewable; - } - bool is_parent_viewable() const final { ceph_assert(parent); - if (!parent->is_valid()) { - return false; - } - return !is_unviewable_by_trans(*parent, ctx.trans); + return parent->is_viewable_by_trans(ctx.trans).first; } bool is_parent_valid() const final { ceph_assert(parent); diff --git a/src/crimson/os/seastore/cached_extent.cc b/src/crimson/os/seastore/cached_extent.cc index d96500736de62..23e221392df2d 100644 --- a/src/crimson/os/seastore/cached_extent.cc +++ b/src/crimson/os/seastore/cached_extent.cc @@ -110,6 +110,57 @@ void LogicalCachedExtent::maybe_set_intermediate_laddr(LBAMapping &mapping) { : mapping.get_key(); } +std::pair +CachedExtent::is_viewable_by_trans(Transaction &t) { + if (!is_valid()) { + return std::make_pair(false, viewable_state_t::invalid); + } + + auto trans_id = t.get_trans_id(); + if (is_pending()) { + ceph_assert(is_pending_in_trans(trans_id)); + return std::make_pair(true, viewable_state_t::pending); + } + + // shared by multiple transactions + assert(t.is_in_read_set(this)); + assert(is_stable_written()); + + auto cmp = trans_spec_view_t::cmp_t(); + if (mutation_pending_extents.find(trans_id, cmp) != + mutation_pending_extents.end()) { + return std::make_pair(false, viewable_state_t::stable_become_pending); + } + + if (retired_transactions.find(trans_id, cmp) != + retired_transactions.end()) { + assert(t.is_stable_extent_retired(get_paddr(), get_length())); + return std::make_pair(false, viewable_state_t::stable_become_retired); + } + + return std::make_pair(true, viewable_state_t::stable); +} + +std::ostream &operator<<( + std::ostream &out, + CachedExtent::viewable_state_t state) +{ + switch(state) { + case CachedExtent::viewable_state_t::stable: + return out << "stable"; + case CachedExtent::viewable_state_t::pending: + return out << "pending"; + case CachedExtent::viewable_state_t::invalid: + return out << "invalid"; + case CachedExtent::viewable_state_t::stable_become_retired: + return out << "stable_become_retired"; + case CachedExtent::viewable_state_t::stable_become_pending: + return out << "stable_become_pending"; + default: + __builtin_unreachable(); + } +} + bool BufferSpace::is_range_loaded(extent_len_t offset, extent_len_t length) const { assert(length > 0); diff --git a/src/crimson/os/seastore/cached_extent.h b/src/crimson/os/seastore/cached_extent.h index d4f9111d4008c..24d442fbdc9f1 100644 --- a/src/crimson/os/seastore/cached_extent.h +++ b/src/crimson/os/seastore/cached_extent.h @@ -789,6 +789,25 @@ public: return is_pending() && pending_for_transaction == id; } + enum class viewable_state_t { + stable, // viewable + pending, // viewable + invalid, // unviewable + stable_become_retired, // unviewable + stable_become_pending, // unviewable + }; + + /** + * is_viewable_by_trans + * + * Check if this extent is still viewable by transaction t. + * + * Precondition: *this was previously visible to t, which indicates + * this extent is either in the read set of t or created(pending) by t. + */ + std::pair + is_viewable_by_trans(Transaction &t); + private: template friend class read_set_item_t; @@ -1102,6 +1121,7 @@ protected: }; std::ostream &operator<<(std::ostream &, CachedExtent::extent_state_t); +std::ostream &operator<<(std::ostream &, CachedExtent::viewable_state_t); std::ostream &operator<<(std::ostream &, const CachedExtent&); /// Compare extents by paddr @@ -1542,5 +1562,6 @@ using lextent_list_t = addr_extent_list_base_t< #if FMT_VERSION >= 90000 template <> struct fmt::formatter : fmt::ostream_formatter {}; +template <> struct fmt::formatter : fmt::ostream_formatter {}; template <> struct fmt::formatter : fmt::ostream_formatter {}; #endif diff --git a/src/crimson/os/seastore/transaction.h b/src/crimson/os/seastore/transaction.h index cc0bf09f24c72..c6e4545bfa832 100644 --- a/src/crimson/os/seastore/transaction.h +++ b/src/crimson/os/seastore/transaction.h @@ -166,6 +166,10 @@ public: return do_add_to_read_set(ref); } + bool is_in_read_set(CachedExtentRef extent) const { + return lookup_read_set(extent).first; + } + void add_to_read_set(CachedExtentRef ref) { assert(ref->get_paddr().is_absolute() || ref->get_paddr().is_root()); @@ -594,7 +598,8 @@ private: } } - auto lookup_read_set(CachedExtentRef ref) const { + auto lookup_read_set(CachedExtentRef ref) const + -> std::pair::const_iterator> { assert(ref->is_valid()); assert(!is_weak()); auto it = ref->read_transactions.lower_bound( -- 2.39.5