]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
mds: fix open on snapped files
authorSage Weil <sage@newdream.net>
Fri, 3 Apr 2009 20:05:49 +0000 (13:05 -0700)
committerSage Weil <sage@newdream.net>
Fri, 3 Apr 2009 20:06:27 +0000 (13:06 -0700)
rdlock the filelock to make sure we get the snapped metadata.  Also
make sure the filelock is SYNC so that the data ends up on disk.
(On the auth mds, we may rdlock by going to LOCK state.)

src/mds/Locker.h
src/mds/Server.cc

index 3efed871d31dfec5b1c8ad47d5e5bb1256c037dc..d48ea39d007facf38d58172ceb36c9f0c6ef2e58 100644 (file)
@@ -108,7 +108,9 @@ protected:
   void simple_eval(SimpleLock *lock);
   void handle_simple_lock(SimpleLock *lock, MLock *m);
 
+public:
   bool simple_sync(SimpleLock *lock);
+protected:
   void simple_lock(SimpleLock *lock);
   void simple_xlock(SimpleLock *lock);
 
index 0998f0742a4ff62170ecc306bb1e139f6be0d84c..d05647e040875856e9085ecdb816120fde7fc70d 100644 (file)
@@ -4854,15 +4854,28 @@ void Server::handle_client_open(MDRequest *mdr)
     }
   } 
 
-  // rdlock filelock if snapped.
-  //  this makes us wait for writers to flushsnaps, ensuring we get accurate metadata.
+  // sync filelock if snapped.
+  //  this makes us wait for writers to flushsnaps, ensuring we get accurate metadata,
+  //  and that data itself is flushed so that we can read the snapped data off disk.
   if (mdr->ref_snapid != CEPH_NOSNAP && !cur->is_dir()) {
+    // first rdlock.
     set<SimpleLock*> rdlocks = mdr->rdlocks;
     set<SimpleLock*> wrlocks = mdr->wrlocks;
     set<SimpleLock*> xlocks = mdr->xlocks;
     rdlocks.insert(&cur->filelock);
     if (!mds->locker->acquire_locks(mdr, rdlocks, wrlocks, xlocks))
       return;
+
+    // sure sure we ended up in the SYNC state
+    if (cur->filelock.is_stable() && cur->filelock.get_state() != LOCK_SYNC) {
+      assert(cur->is_auth());
+      mds->locker->simple_sync(&cur->filelock);
+    }
+    if (!cur->filelock.is_stable()) {
+      dout(10) << " waiting for filelock to stabilize on " << *cur << dendl;
+      cur->filelock.add_waiter(SimpleLock::WAIT_STABLE, new C_MDS_RetryRequest(mdcache, mdr));
+      return;
+    }
   }