]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
(re)add mechanism for marking objects as lost
authorColin Patrick McCabe <cmccabe@alumni.cmu.edu>
Sat, 20 Nov 2010 03:15:40 +0000 (19:15 -0800)
committerColin Patrick McCabe <cmccabe@alumni.cmu.edu>
Tue, 30 Nov 2010 23:43:44 +0000 (15:43 -0800)
In activate_map, we now mark objects that we know are unfindable as
lost. This relies on the might_have_unfound set introduced earlier.

Signed-off-by: Colin McCabe <colinm@hq.newdream.net>
src/osd/OSD.cc
src/osd/PG.cc
src/osd/PG.h

index c18854d735a72bf36346148aeec025cf59f52afc..419a2d9a28dd41dacdb4e5927c526d2c83aeebe9 100644 (file)
@@ -3079,6 +3079,13 @@ void OSD::activate_map(ObjectStore::Transaction& t, list<Context*>& tfin)
     if (g_conf.osd_check_for_log_corruption)
       pg->check_log_for_corruption(store);
 
+    if (pg->is_primary() &&
+       (pg->missing.num_missing() > pg->missing_loc.size())) {
+      if (pg->all_unfound_are_lost(osdmap)) {
+       pg->mark_all_unfound_as_lost();
+      }
+    }
+
     if (!osdmap->have_pg_pool(pg->info.pgid.pool())) {
       //pool is deleted!
       queue_pg_for_deletion(pg);
index 769bf2d6edad152ca3c981582106fff485abd405..db2d1943c8f42490ffad401963a0f1b0c53e8367 100644 (file)
@@ -974,6 +974,75 @@ bool PG::prior_set_affected(OSDMap *osdmap)
   return false;
 }
 
+/*
+ * Returns true unless there is a non-lost OSD in might_have_unfound.
+ */
+bool PG::all_unfound_are_lost(const OSDMap* osdmap) const
+{
+  assert(is_primary());
+
+  set<int>::const_iterator peer = might_have_unfound.begin();
+  set<int>::const_iterator mend = might_have_unfound.end();
+  for (; peer != mend; ++peer) {
+    const osd_info_t &osd_info(osdmap->get_info(*peer));
+    if (osd_info.lost_at <= osd_info.up_from) {
+      // If there is even one OSD in might_have_unfound that isn't lost, we
+      // still might retrieve our unfound.
+      return false;
+    }
+  }
+  return true;
+}
+
+class CompareSobjectPtrs {
+public:
+  bool operator()(const sobject_t *a, const sobject_t *b) {
+    return *a < *b;
+  }
+};
+
+/* Mark all unfound objects as lost.
+ */
+void PG::mark_all_unfound_as_lost()
+{
+  dout(3) << __func__ << dendl;
+
+  // Find out what to delete
+  map<sobject_t, Missing::item>::iterator m = missing.missing.begin();
+  map<sobject_t, Missing::item>::iterator mend = missing.missing.end();
+  std::set <const sobject_t*, CompareSobjectPtrs> del;
+  for (; m != mend; ++m) {
+    const sobject_t &soid(m->first);
+    if (missing_loc.find(soid) == missing_loc.end()) {
+      del.insert(&m->first);
+      continue;
+    }
+  }
+
+  // Iterate over rmissing, removing elements that point to deleted sobject_t
+  map<eversion_t, sobject_t>::iterator z = missing.rmissing.begin();
+  map<eversion_t, sobject_t>::iterator zend = missing.rmissing.end();
+  std::set <const sobject_t*, CompareSobjectPtrs>::iterator dend = del.end();
+  while (z != zend) {
+    const sobject_t &soid(z->second);
+    if (del.find(&soid) != dend) {
+      missing.rmissing.erase(z++);
+    }
+  }
+
+  // Remove deleted elements from missing.
+  std::set <const sobject_t*, CompareSobjectPtrs>::iterator d = del.begin();
+  while (d != dend) {
+    sobject_t lost_soid(**d);
+
+    // TODO: some kind of bit that we set inside the object store
+    dout(10) << __func__ << ": marked " << lost_soid << " as lost!" << dendl;
+
+    missing.missing.erase(lost_soid);
+    del.erase(d++);
+  }
+}
+
 void PG::clear_prior()
 {
   dout(10) << "clear_prior" << dendl;
@@ -984,7 +1053,6 @@ void PG::clear_prior()
   prior_set_built = false;
 }
 
-
 void PG::build_prior()
 {
   if (1) {
@@ -1607,10 +1675,7 @@ void PG::build_might_have_unfound()
   dout(10) << __func__ << dendl;
 
   // Make sure that we have past intervals.
-  if (info.history.same_acting_since > info.history.last_epoch_started &&
-      (past_intervals.empty() ||
-       past_intervals.begin()->first > info.history.last_epoch_started))
-    generate_past_intervals();
+  generate_past_intervals();
 
   // We need to decide who might have unfound objects that we need
   std::map<epoch_t,Interval>::const_reverse_iterator p = past_intervals.rbegin();
index cd2e068bd3f3bf5678e927848527a515164126f4..6808ec4851cb14f440c6c9a912614e45f31f1499 100644 (file)
@@ -805,6 +805,9 @@ public:
   void clear_prior();
   bool prior_set_affected(OSDMap *map);
 
+  bool all_unfound_are_lost(const OSDMap* osdmap) const;
+  void mark_all_unfound_as_lost();
+
   bool calc_min_last_complete_ondisk() {
     eversion_t min = last_complete_ondisk;
     for (unsigned i=1; i<acting.size(); i++) {