]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/commitdiff
mds: properly invalidate past child snaprealms
authorYan, Zheng <zyan@redhat.com>
Mon, 18 May 2015 09:25:58 +0000 (17:25 +0800)
committerYan, Zheng <zyan@redhat.com>
Tue, 19 May 2015 07:47:17 +0000 (15:47 +0800)
After updating an existing snapshot or deleting an old snapshot,
we should invalidate past child snaprealms' cached snap set and
snap context.

Signed-off-by: Yan, Zheng <zyan@redhat.com>
src/mds/MDCache.cc
src/mds/Server.cc
src/mds/SnapRealm.cc
src/mds/SnapRealm.h

index fbcbbb7c53ae0a45c9886b23b0f26f6971bf971d..809144a2e8d394debda58e652afdac92dd1e9391 100644 (file)
@@ -9013,6 +9013,7 @@ void MDCache::do_realm_invalidate_and_update_notify(CInode *in, int snapop, bool
   bufferlist snapbl;
   in->snaprealm->build_snap_trace(snapbl);
 
+  set<SnapRealm*> past_children;
   map<client_t, MClientSnap*> updates;
   list<SnapRealm*> q;
   q.push_back(in->snaprealm);
@@ -9037,6 +9038,13 @@ void MDCache::do_realm_invalidate_and_update_notify(CInode *in, int snapop, bool
       }
     }
 
+    if (snapop == CEPH_SNAP_OP_UPDATE || snapop == CEPH_SNAP_OP_DESTROY) {
+      for (set<SnapRealm*>::iterator p = realm->open_past_children.begin();
+          p != realm->open_past_children.end();
+          ++p)
+       past_children.insert(*p);
+    }
+
     // notify for active children, too.
     dout(10) << " " << realm << " open_children are " << realm->open_children << dendl;
     for (set<SnapRealm*>::iterator p = realm->open_children.begin();
@@ -9047,6 +9055,43 @@ void MDCache::do_realm_invalidate_and_update_notify(CInode *in, int snapop, bool
 
   if (!nosend)
     send_snaps(updates);
+
+  // notify past children and their descendants if we update/delete old snapshots
+  for (set<SnapRealm*>::iterator p = past_children.begin();
+       p !=  past_children.end();
+       ++p)
+    q.push_back(*p);
+
+  while (!q.empty()) {
+    SnapRealm *realm = q.front();
+    q.pop_front();
+
+    realm->invalidate_cached_snaps();
+
+    for (set<SnapRealm*>::iterator p = realm->open_children.begin();
+        p != realm->open_children.end();
+        ++p) {
+      if (past_children.count(*p) == 0)
+       q.push_back(*p);
+    }
+
+    for (set<SnapRealm*>::iterator p = realm->open_past_children.begin();
+        p != realm->open_past_children.end();
+        ++p) {
+      if (past_children.count(*p) == 0) {
+       q.push_back(*p);
+       past_children.insert(*p);
+      }
+    }
+  }
+
+  if (snapop == CEPH_SNAP_OP_DESTROY) {
+    // eval stray inodes if we delete snapshot from their past ancestor snaprealm
+    for (set<SnapRealm*>::iterator p = past_children.begin();
+       p != past_children.end();
+       ++p)
+      maybe_eval_stray((*p)->inode, true);
+  }
 }
 
 void MDCache::_snaprealm_create_finish(MDRequestRef& mdr, MutationRef& mut, CInode *in)
index 39a4465aa3318b55a02653a990cff6751c2e73d6..12de267e9e2c0354b7326b1e6944f593c378daa5 100644 (file)
@@ -8061,7 +8061,7 @@ void Server::_renamesnap_finish(MDRequestRef& mdr, CInode *diri, snapid_t snapid
 
   dout(10) << "snaprealm now " << *diri->snaprealm << dendl;
 
-  mdcache->do_realm_invalidate_and_update_notify(diri, CEPH_SNAP_OP_CREATE, true);
+  mdcache->do_realm_invalidate_and_update_notify(diri, CEPH_SNAP_OP_UPDATE, true);
 
   // yay
   mdr->in[0] = diri;
index 14af91f8f704ea0a4d29a6f0c567ab382b72a7cd..60d417514e4c711a62a550e2c3e8131bbf4f943e 100644 (file)
@@ -61,6 +61,7 @@ ostream& operator<<(ostream& out, const SnapRealm& realm)
 void SnapRealm::add_open_past_parent(SnapRealm *parent)
 {
   open_past_parents[parent->inode->ino()] = parent;
+  parent->open_past_children.insert(this);
   parent->inode->get(CInode::PIN_PASTSNAPPARENT);
 }
 
@@ -174,8 +175,10 @@ void SnapRealm::close_parents()
 {
   for (map<inodeno_t,SnapRealm*>::iterator p = open_past_parents.begin();
        p != open_past_parents.end();
-       ++p)
+       ++p) {
     p->second->inode->put(CInode::PIN_PASTSNAPPARENT);
+    p->second->open_past_children.erase(this);
+  }
   open_past_parents.clear();
 }
 
index cd0de824d255deac8492419183086838cba07a99..ad55adc017237797228395f176882e46d8a398eb 100644 (file)
@@ -35,6 +35,7 @@ struct SnapRealm {
   SnapRealm *parent;
   set<SnapRealm*> open_children;    // active children that are currently open
   map<inodeno_t,SnapRealm*> open_past_parents;  // these are explicitly pinned.
+  set<SnapRealm*> open_past_children;  // past children who has pinned me
 
   // cache
   snapid_t cached_seq;           // max seq over self and all past+present parents.