]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/commitdiff
mon/OSDMonitor: convert removed_snaps on first mimic map
authorSage Weil <sage@redhat.com>
Mon, 16 Oct 2017 03:03:11 +0000 (22:03 -0500)
committerSage Weil <sage@redhat.com>
Sat, 2 Dec 2017 03:26:49 +0000 (21:26 -0600)
On the first mimic map, consider previously removed_snaps to be removed
in that epoch (since we don't easily know when it happened).

Signed-off-by: Sage Weil <sage@redhat.com>
src/mon/OSDMonitor.cc
src/osd/PG.cc
src/osd/PG.h

index 4c214ea29b3dc76f992bba28b8d4a69f7f8a6136..c441a02f6123bce7e1dfcdbd90327b2dd0adb45d 100644 (file)
@@ -1127,6 +1127,70 @@ void OSDMonitor::encode_pending(MonitorDBStore::TransactionRef t)
                        << "required " << ceph_release_name(mv);
       pending_inc.new_require_min_compat_client = mv;
     }
+
+    // upgrade to mimic?
+    if (osdmap.require_osd_release < CEPH_RELEASE_MIMIC &&
+       tmp.require_osd_release >= CEPH_RELEASE_MIMIC) {
+      dout(10) << __func__ << " first mimic epoch" << dendl;
+      // record this epoch as the deletion for all legacy removed_snaps
+      for (auto& p : tmp.get_pools()) {
+       // update every pool
+       if (pending_inc.new_pools.count(p.first) == 0) {
+         pending_inc.new_pools[p.first] = p.second;
+       }
+       auto& pi = pending_inc.new_pools[p.first];
+       if (pi.snap_seq == 0) {
+         // no snaps on this pool
+         continue;
+       }
+       if ((pi.flags & (pg_pool_t::FLAG_SELFMANAGED_SNAPS |
+                        pg_pool_t::FLAG_POOL_SNAPS)) == 0) {
+         if (!pi.removed_snaps.empty()) {
+           pi.flags |= pg_pool_t::FLAG_SELFMANAGED_SNAPS;
+         } else {
+           pi.flags |= pg_pool_t::FLAG_POOL_SNAPS;
+         }
+       }
+
+       // Make all previously removed snaps appear to be removed in this
+       // epoch.  this populates removed_snaps_queue.  The OSD will subtract
+       // off its purged_snaps, as before, and this set will shrink over the
+       // following epochs as the purged snaps are reported back through the
+       // mgr.
+       OSDMap::snap_interval_set_t removed;
+       if (!p.second.removed_snaps.empty()) {
+         // different flavor of interval_set :(
+         for (auto q = p.second.removed_snaps.begin();
+              q != p.second.removed_snaps.end();
+              ++q) {
+           removed.insert(q.get_start(), q.get_len());
+         }
+       } else {
+         for (snapid_t s = 1; s <= pi.get_snap_seq(); s = s + 1) {
+           if (pi.snaps.count(s) == 0) {
+             removed.insert(s);
+           }
+         }
+       }
+       pending_inc.new_removed_snaps[p.first].union_of(removed);
+
+       dout(10) << __func__ << " converting pool " << p.first
+                << " with " << p.second.removed_snaps.size()
+                << " legacy removed_snaps" << dendl;
+       string k = make_snap_epoch_key(p.first, pending_inc.epoch);
+       bufferlist v;
+       ::encode(p.second.removed_snaps, v);
+       t->put(OSD_SNAP_PREFIX, k, v);
+       for (auto q = p.second.removed_snaps.begin();
+            q != p.second.removed_snaps.end();
+            ++q) {
+         bufferlist v;
+         string k = make_snap_key_value(p.first, q.get_start(),
+                                        q.get_len(), pending_inc.epoch, &v);
+         t->put(OSD_SNAP_PREFIX, k, v);
+       }
+      }
+    }
   }
 
   // tell me about it
index 5adcfcf4e27eb70569688bc56d2e92c888fbf27c..a2cfc99cecdf88e9460c24305b9d1893432eea0f 100644 (file)
@@ -354,7 +354,8 @@ PG::PG(OSDService *o, OSDMapRef curmap,
   peer_features(CEPH_FEATURES_SUPPORTED_DEFAULT),
   acting_features(CEPH_FEATURES_SUPPORTED_DEFAULT),
   upacting_features(CEPH_FEATURES_SUPPORTED_DEFAULT),
-  last_epoch(0)
+  last_epoch(0),
+  last_require_osd_release(curmap->require_osd_release)
 {
 #ifdef PG_DEBUG_REFS
   osd->add_pgid(p, this);
@@ -5955,6 +5956,7 @@ void PG::handle_advance_map(
     on_pool_change();
     update_store_with_options();
   }
+  last_require_osd_release = osdmap->require_osd_release;
 }
 
 void PG::handle_activate_map(RecoveryCtx *rctx)
@@ -7317,14 +7319,28 @@ boost::statechart::result PG::RecoveryState::Active::react(const AdvMap& advmap)
          decltype(pg->snap_trimq) added, overlap;
          added.insert(j.first, j.second);
          overlap.intersection_of(pg->snap_trimq, added);
-         lderr(pg->cct) << __func__ << " removed_snaps already contains "
-                        << overlap << dendl;
-         bad = true;
+         if (pg->last_require_osd_release < CEPH_RELEASE_MIMIC) {
+           lderr(pg->cct) << __func__ << " removed_snaps already contains "
+                          << overlap << ", but this is the first mimic+ osdmap,"
+                          << " so it's expected" << dendl;
+         } else {
+           lderr(pg->cct) << __func__ << " removed_snaps already contains "
+                          << overlap << dendl;
+           bad = true;
+         }
          pg->snap_trimq.union_of(added);
        } else {
          pg->snap_trimq.insert(j.first, j.second);
        }
       }
+      if (pg->last_require_osd_release < CEPH_RELEASE_MIMIC) {
+       // at upgrade, we report *all* previously removed snaps as removed in
+       // the first mimic epoch.  remove the ones we previously divined were
+       // removed (and subsequently purged) from the trimq.
+       lderr(pg->cct) << __func__ << " first mimic map, filtering purged_snaps"
+                      << " from new removed_snaps" << dendl;
+       pg->snap_trimq.subtract(pg->info.purged_snaps);
+      }
       ldout(pg->cct,10) << __func__ << " new removed_snaps " << i->second
                        << ", snap_trimq now " << pg->snap_trimq << dendl;
       assert(!bad || !pg->cct->_conf->osd_debug_verify_cached_snaps);
index 73632fa9654b42c508c3bacc929e4a94c815d70b..c260a9b444ebdcc2e8cd7a766ec59bac2abf895d 100644 (file)
@@ -2630,6 +2630,9 @@ protected:
 
   epoch_t last_epoch;
 
+  /// most recently consumed osdmap's require_osd_version
+  unsigned last_require_osd_release = 0;
+
 protected:
   void reset_min_peer_features() {
     peer_features = CEPH_FEATURES_SUPPORTED_DEFAULT;