]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
test: snapshot stress test rbd-mirror image sync
authorJason Dillaman <dillaman@redhat.com>
Wed, 4 May 2016 02:53:52 +0000 (22:53 -0400)
committerJason Dillaman <dillaman@redhat.com>
Tue, 10 May 2016 17:43:52 +0000 (13:43 -0400)
Signed-off-by: Jason Dillaman <dillaman@redhat.com>
(cherry picked from commit 468287bd182fa0cd02f7551ad6d729ff67ab1a22)

src/test/rbd_mirror/test_ImageSync.cc

index 5e6b0a9d310156436f4a1641b86f2a8f34ed9122..5b80f970d888333c5eb5a6396764a0f5ec57c96a 100644 (file)
@@ -2,12 +2,15 @@
 // vim: ts=8 sw=2 smarttab
 
 #include "test/rbd_mirror/test_fixture.h"
+#include "include/stringify.h"
 #include "include/rbd/librbd.hpp"
 #include "journal/Journaler.h"
 #include "librbd/AioImageRequestWQ.h"
 #include "librbd/ExclusiveLock.h"
 #include "librbd/ImageCtx.h"
 #include "librbd/ImageState.h"
+#include "librbd/internal.h"
+#include "librbd/Operations.h"
 #include "librbd/journal/Types.h"
 #include "tools/rbd_mirror/ImageSync.h"
 #include "tools/rbd_mirror/Threads.h"
@@ -22,6 +25,7 @@ namespace {
 
 void scribble(librbd::ImageCtx *image_ctx, int num_ops, size_t max_size)
 {
+  max_size = MIN(image_ctx->size, max_size);
   for (int i=0; i<num_ops; i++) {
     uint64_t off = rand() % (image_ctx->size - max_size + 1);
     uint64_t len = 1 + rand() % max_size;
@@ -34,6 +38,9 @@ void scribble(librbd::ImageCtx *image_ctx, int num_ops, size_t max_size)
                                                            str.c_str(), 0));
     }
   }
+
+  RWLock::RLocker owner_locker(image_ctx->owner_lock);
+  ASSERT_EQ(0, image_ctx->flush());
 }
 
 } // anonymous namespace
@@ -105,10 +112,6 @@ TEST_F(TestImageSync, Empty) {
 
 TEST_F(TestImageSync, Simple) {
   scribble(m_remote_image_ctx, 10, 102400);
-  {
-    RWLock::RLocker owner_locker(m_remote_image_ctx->owner_lock);
-    ASSERT_EQ(0, m_remote_image_ctx->flush());
-  }
 
   C_SaferCond ctx;
   ImageSync<> *request = create_request(&ctx);
@@ -132,5 +135,76 @@ TEST_F(TestImageSync, Simple) {
   }
 }
 
+TEST_F(TestImageSync, SnapshotStress) {
+  std::list<std::string> snap_names;
+
+  const int num_snaps = 4;
+  for (int idx = 0; idx <= num_snaps; ++idx) {
+    scribble(m_remote_image_ctx, 10, 102400);
+
+    librbd::NoOpProgressContext no_op_progress_ctx;
+    uint64_t size = 1 + rand() % m_image_size;
+    ASSERT_EQ(0, m_remote_image_ctx->operations->resize(size,
+                                                        no_op_progress_ctx));
+    ASSERT_EQ(0, m_remote_image_ctx->state->refresh());
+
+    if (idx < num_snaps) {
+      snap_names.push_back("snap" + stringify(idx + 1));
+      ASSERT_EQ(0, create_snap(m_remote_image_ctx, snap_names.back().c_str(),
+                               nullptr));
+    } else {
+      snap_names.push_back("");
+    }
+  }
+
+  C_SaferCond ctx;
+  ImageSync<> *request = create_request(&ctx);
+  request->start();
+  ASSERT_EQ(0, ctx.wait());
+
+  int64_t object_size = std::min<int64_t>(
+    m_remote_image_ctx->size, 1 << m_remote_image_ctx->order);
+  bufferlist read_remote_bl;
+  read_remote_bl.append(std::string(object_size, '1'));
+  bufferlist read_local_bl;
+  read_local_bl.append(std::string(object_size, '1'));
+
+  for (auto &snap_name : snap_names) {
+    uint64_t remote_size;
+    {
+      C_SaferCond ctx;
+      m_remote_image_ctx->state->snap_set(snap_name, &ctx);
+      ASSERT_EQ(0, ctx.wait());
+
+      RWLock::RLocker remote_snap_locker(m_remote_image_ctx->snap_lock);
+      remote_size = m_remote_image_ctx->get_image_size(
+        m_remote_image_ctx->snap_id);
+    }
+
+    uint64_t local_size;
+    {
+      C_SaferCond ctx;
+      m_local_image_ctx->state->snap_set(snap_name, &ctx);
+      ASSERT_EQ(0, ctx.wait());
+
+      RWLock::RLocker snap_locker(m_local_image_ctx->snap_lock);
+      local_size = m_local_image_ctx->get_image_size(
+        m_local_image_ctx->snap_id);
+      ASSERT_FALSE(m_local_image_ctx->test_flags(RBD_FLAG_OBJECT_MAP_INVALID,
+                                                 m_local_image_ctx->snap_lock));
+    }
+
+    ASSERT_EQ(remote_size, local_size);
+
+    for (uint64_t offset = 0; offset < remote_size; offset += object_size) {
+      ASSERT_LE(0, m_remote_image_ctx->aio_work_queue->read(
+                     offset, object_size, read_remote_bl.c_str(), 0));
+      ASSERT_LE(0, m_local_image_ctx->aio_work_queue->read(
+                     offset, object_size, read_local_bl.c_str(), 0));
+      ASSERT_TRUE(read_remote_bl.contents_equal(read_local_bl));
+    }
+  }
+}
+
 } // namespace mirror
 } // namespace rbd