]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
librbd: add copy_with_progress API
authorColin Patrick McCabe <cmccabe@alumni.cmu.edu>
Mon, 29 Aug 2011 23:43:33 +0000 (16:43 -0700)
committerColin Patrick McCabe <cmccabe@alumni.cmu.edu>
Mon, 29 Aug 2011 23:57:23 +0000 (16:57 -0700)
Signed-off-by: Colin McCabe <colin.mccabe@dreamhost.com>
src/include/rbd/librbd.h
src/include/rbd/librbd.hpp
src/librbd.cc

index 412e290260806116c5c595aa52df1cd58c3559b1..a143edab50e512568c78c567d744eb68340ccb16 100644 (file)
@@ -37,6 +37,9 @@ extern "C" {
 typedef void *rbd_snap_t;
 typedef void *rbd_image_t;
 
+typedef void (*librbd_copy_progress_fn_t)(uint64_t offset, uint64_t src_size,
+                                        void *data);
+
 typedef struct {
   uint64_t id;
   uint64_t size;
@@ -69,6 +72,8 @@ int rbd_close(rbd_image_t image);
 int rbd_resize(rbd_image_t image, uint64_t size);
 int rbd_stat(rbd_image_t image, rbd_image_info_t *info, size_t infosize);
 int rbd_copy(rbd_image_t image, rados_ioctx_t dest_io_ctx, const char *destname);
+int rbd_copy_with_progress(rbd_image_t image, rados_ioctx_t dest_p,
+           const char *destname, librbd_copy_progress_fn_t fn, void *data);
 
 /* snapshots */
 int rbd_snap_list(rbd_image_t image, rbd_snap_info_t *snaps, int *max_snaps);
index 01ff4f4dc885e2f6bb22e0c7f5165c761adf0f5d..a48676e65095f9b614028a3a24d42270e6eb491f 100644 (file)
@@ -32,6 +32,8 @@ namespace librbd {
   typedef void *image_ctx_t;
   typedef void *completion_t;
   typedef void (*callback_t)(completion_t cb, void *arg);
+  typedef void (*copy_progress_fn_t)(uint64_t offset, uint64_t src_size,
+                                    void *data);
 
   typedef struct {
     uint64_t id;
@@ -79,6 +81,8 @@ public:
   int resize(uint64_t size);
   int stat(image_info_t &info, size_t infosize);
   int copy(IoCtx& dest_io_ctx, const char *destname);
+  int copy_with_progress(IoCtx& dest_io_ctx, const char *destname,
+           copy_progress_fn_t fn, void *data);
 
   /* snapshots */
   int snap_list(std::vector<snap_info_t>& snaps);
index 2c2ef94384a378f27b2a71aa24a7e06214000994..289b10b7b9283e7a100d96243a61d80fb9f349cd 100644 (file)
@@ -1012,17 +1012,32 @@ int snap_rollback(ImageCtx *ictx, const char *snap_name)
   return 0;
 }
 
-int do_copy_extent(uint64_t offset, size_t len, const char *buf, void *destictx)
-{
-  if (buf)
-    return write((ImageCtx *)destictx, offset, len, buf);
-  else
-    return 0;  /* do nothing for holes */
+struct CopyProgressCtx {
+  ImageCtx *destictx;
+  uint64_t src_size;
+  copy_progress_fn_t fn;
+  void *data;
+};
+
+int do_copy_extent(uint64_t offset, size_t len, const char *buf, void *data)
+{
+  CopyProgressCtx *cp = reinterpret_cast<CopyProgressCtx*>(data);
+  if (buf) {
+    int ret = write(cp->destictx, offset, len, buf);
+    if (ret) {
+      return ret;
+    }
+  }
+  if (cp->fn)
+    cp->fn(offset, cp->src_size, cp->data);
+  return 0;
 }
 
-int copy(ImageCtx& ictx, IoCtx& dest_md_ctx, const char *destname)
+int copy(ImageCtx& ictx, IoCtx& dest_md_ctx, const char *destname,
+        copy_progress_fn_t fn, void *data)
 {
   CephContext *cct = dest_md_ctx.cct();
+  CopyProgressCtx cp;
 
   uint64_t src_size = ictx.get_image_size();
 
@@ -1033,15 +1048,21 @@ int copy(ImageCtx& ictx, IoCtx& dest_md_ctx, const char *destname)
     return r;
   }
 
-  ImageCtx *destictx = new librbd::ImageCtx(destname, dest_md_ctx);
-  r = open_image(dest_md_ctx, destictx, destname, NULL);
+  cp.destictx = new librbd::ImageCtx(destname, dest_md_ctx);
+  cp.src_size = src_size;
+  cp.fn = fn;
+  cp.data = data;
+  r = open_image(dest_md_ctx, cp.destictx, destname, NULL);
   if (r < 0) {
     lderr(cct) << "failed to read newly created header" << dendl;
     return r;
   }
 
-  r = read_iterate(&ictx, 0, src_size, do_copy_extent, destictx);
-  close_image(destictx);
+  r = read_iterate(&ictx, 0, src_size, do_copy_extent, &cp);
+  if ((r >= 0) && (cp.fn)) {
+    cp.fn(cp.src_size, cp.src_size, cp.data);
+  }
+  close_image(cp.destictx);
   return r;
 }
 
@@ -1556,7 +1577,15 @@ int Image::stat(image_info_t& info, size_t infosize)
 int Image::copy(IoCtx& dest_io_ctx, const char *destname)
 {
   ImageCtx *ictx = (ImageCtx *)ctx;
-  int r = librbd::copy(*ictx, dest_io_ctx, destname);
+  int r = librbd::copy(*ictx, dest_io_ctx, destname, NULL, NULL);
+  return r;
+}
+
+int Image::copy_with_progress(IoCtx& dest_io_ctx, const char *destname,
+                             copy_progress_fn_t fn, void *data)
+{
+  ImageCtx *ictx = (ImageCtx *)ctx;
+  int r = librbd::copy(*ictx, dest_io_ctx, destname, fn, data);
   return r;
 }
 
@@ -1694,7 +1723,16 @@ extern "C" int rbd_copy(rbd_image_t image, rados_ioctx_t dest_p, const char *des
   librbd::ImageCtx *ictx = (librbd::ImageCtx *)image;
   librados::IoCtx dest_io_ctx;
   librados::IoCtx::from_rados_ioctx_t(dest_p, dest_io_ctx);
-  return librbd::copy(*ictx, dest_io_ctx, destname);
+  return librbd::copy(*ictx, dest_io_ctx, destname, NULL, NULL);
+}
+
+extern "C" int rbd_copy_with_progress(rbd_image_t image, rados_ioctx_t dest_p,
+             const char *destname, librbd_copy_progress_fn_t fn, void *data)
+{
+  librbd::ImageCtx *ictx = (librbd::ImageCtx *)image;
+  librados::IoCtx dest_io_ctx;
+  librados::IoCtx::from_rados_ioctx_t(dest_p, dest_io_ctx);
+  return librbd::copy(*ictx, dest_io_ctx, destname, fn, data);
 }
 
 extern "C" int rbd_rename(rados_ioctx_t src_p, const char *srcname, const char *destname)