]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
librbd/cache/pwl/ssd: remove correct m_blocks_to_log_entries entry
authorFeng Hualong <hualong.feng@intel.com>
Wed, 28 Jul 2021 03:42:44 +0000 (11:42 +0800)
committerDeepika Upadhyay <dupadhya@redhat.com>
Fri, 5 Nov 2021 09:22:02 +0000 (14:52 +0530)
When retiring, m_blocks_to_log_entries doesn't remove
corresponding write_entry (should be `*it` not `entry`)
that will be retired. It leads to read error. And
there should also consider discard entries.

Fixes: https://tracker.ceph.com/issues/52579
Signed-off-by: Feng Hualong <hualong.feng@intel.com>
(cherry picked from commit 01bb75a1056d26ae43832d567087b3d67ab84261)

src/librbd/cache/pwl/ssd/WriteLog.cc

index 91bb659278abb3af24d9073690dc1adc6dfcb97c..b37fd525886124a1a4e01bcb37005f9985c115c6 100644 (file)
@@ -670,8 +670,7 @@ bool WriteLog<I>::retire_entries(const unsigned long int frees_per_tx) {
     first_valid_entry = m_first_valid_entry;
     while (retiring_entries.size() < frees_per_tx && !m_log_entries.empty()) {
       GenericLogEntriesVector retiring_subentries;
-      auto entry = m_log_entries.front();
-      uint64_t control_block_pos = entry->log_entry_index;
+      uint64_t control_block_pos = m_log_entries.front()->log_entry_index;
       uint64_t data_length = 0;
       for (auto it = m_log_entries.begin(); it != m_log_entries.end(); ++it) {
         if (this->can_retire_entry(*it)) {
@@ -708,9 +707,11 @@ bool WriteLog<I>::retire_entries(const unsigned long int frees_per_tx) {
             it != retiring_subentries.end(); it++) {
           ceph_assert(m_log_entries.front() == *it);
           m_log_entries.pop_front();
-          if (entry->is_write_entry()) {
-            auto write_entry = static_pointer_cast<WriteLogEntry>(entry);
-            this->m_blocks_to_log_entries.remove_log_entry(write_entry);
+          if ((*it)->write_bytes() > 0 || (*it)->bytes_dirty() > 0) {
+            auto gen_write_entry = static_pointer_cast<GenericWriteLogEntry>(*it);
+            if (gen_write_entry) {
+                this->m_blocks_to_log_entries.remove_log_entry(gen_write_entry);
+            }
           }
         }