]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
rgw: fail operation when trying to clone to the same shadow
authorYehuda Sadeh <yehuda@hq.newdream.net>
Sat, 20 Aug 2011 00:33:27 +0000 (17:33 -0700)
committerYehuda Sadeh <yehuda@hq.newdream.net>
Sat, 20 Aug 2011 00:35:26 +0000 (17:35 -0700)
not necessary to recreate the same shadow, and also provides mutual
exclusion

src/rgw/rgw_access.h
src/rgw/rgw_op.cc
src/rgw/rgw_rados.cc
src/rgw/rgw_rados.h

index 7b78a91131d74d23a7754e159383432a43496192..b9e86618414646faf508b0c9c936eade17c7e544 100644 (file)
@@ -187,7 +187,7 @@ public:
     info.dst_ofs = dst_ofs;
     info.len = size;
     v.push_back(info);
-    return clone_objs(ctx, dst_obj, v, attrs, category, pmtime, true);
+    return clone_objs(ctx, dst_obj, v, attrs, category, pmtime, true, false);
   }
 
   virtual int clone_objs(void *ctx, rgw_obj& dst_obj,
@@ -195,7 +195,8 @@ public:
                         map<string, bufferlist> attrs,
                         string& category,
                         time_t *pmtime,
-                        bool truncate_dest) { return -ENOTSUP; }
+                        bool truncate_dest,
+                        bool exclusive) { return -ENOTSUP; }
  /**
    * a simple object read without keeping state
    */
index 04e5535d586f382fa3d3b1e38369944d2ccbb1c3..dae078317940f3c0df5993615e8f748818e26ef6 100644 (file)
@@ -1301,7 +1301,7 @@ void RGWCompleteMultipart::execute()
 
     ofs += obj_iter->second.size;
   }
-  ret = rgwstore->clone_objs(s->obj_ctx, target_obj, ranges, attrs, rgw_obj_category_main, NULL, true);
+  ret = rgwstore->clone_objs(s->obj_ctx, target_obj, ranges, attrs, rgw_obj_category_main, NULL, true, false);
   if (ret < 0)
     goto done;
 
index 4c5a182d6f16ccb356d9f4f7c1c89a07247e1c1b..2a456f16bcce3299ffedd017924de653a20ca631 100644 (file)
@@ -871,7 +871,10 @@ int RGWRados::prepare_atomic_for_write_impl(RGWRadosCtx *rctx, rgw_obj& obj, lib
       dest_obj.set_key(obj.object);
 
     pair<string, bufferlist> cond(RGW_ATTR_ID_TAG, state->obj_tag);
-    r = clone_obj_cond(NULL, dest_obj, 0, obj, 0, state->size, state->attrset, shadow_category, &state->mtime, &cond);
+    RGW_LOG(0) << "cloning: dest_obj=" << dest_obj << " size=" << state->size << " tag=" << state->obj_tag.c_str() << dendl;
+    r = clone_obj_cond(NULL, dest_obj, 0, obj, 0, state->size, state->attrset, shadow_category, &state->mtime, false, true, &cond);
+    if (r == -EEXIST)
+      r = 0;
     if (r == -ECANCELED) {
       /* we lost in a race here, original object was replaced, we assume it was cloned
          as required */
@@ -1138,6 +1141,7 @@ int RGWRados::clone_objs_impl(void *ctx, rgw_obj& dst_obj,
                         string& category,
                         time_t *pmtime,
                         bool truncate_dest,
+                        bool exclusive,
                         pair<string, bufferlist> *xattr_cond)
 {
   std::string& bucket = dst_obj.bucket;
@@ -1151,16 +1155,15 @@ int RGWRados::clone_objs_impl(void *ctx, rgw_obj& dst_obj,
 
   io_ctx.locator_set_key(dst_obj.key);
   ObjectWriteOperation op;
-
   if (truncate_dest) {
     op.remove();
     op.set_op_flags(OP_FAILOK); // don't fail if object didn't exist
   }
 
   if (category.size())
-    op.create(false, category);
+    op.create(exclusive, category);
   else
-    op.create(false);
+    op.create(exclusive);
 
 
   map<string, bufferlist>::iterator iter;
@@ -1215,11 +1218,12 @@ int RGWRados::clone_objs(void *ctx, rgw_obj& dst_obj,
                         string& category,
                         time_t *pmtime,
                         bool truncate_dest,
+                        bool exclusive,
                         pair<string, bufferlist> *xattr_cond)
 {
   int r;
   do {
-    r = clone_objs_impl(ctx, dst_obj, ranges, attrs, category, pmtime, truncate_dest, xattr_cond);
+    r = clone_objs_impl(ctx, dst_obj, ranges, attrs, category, pmtime, truncate_dest, exclusive, xattr_cond);
   } while (ctx && r == -ECANCELED);
   return r;
 }
index 4e3d94be7522d391227febe4a8549cb137d8e414..7960c12b50e94ca9c75e03202e2101b634b189df 100644 (file)
@@ -102,6 +102,7 @@ class RGWRados  : public RGWAccess
                  string& category,
                  time_t *pmtime,
                  bool truncate_dest,
+                 bool exclusive,
                  pair<string, bufferlist> *cmp_xattr);
   int delete_obj_impl(void *ctx, std::string& id, rgw_obj& src_obj, bool sync);
 public:
@@ -141,8 +142,8 @@ public:
                          vector<RGWCloneRangeInfo>& ranges,
                          map<string, bufferlist> attrs,
                          string& category,
-                         time_t *pmtime, bool truncate_dest) {
-    return clone_objs(ctx, dst_obj, ranges, attrs, category, pmtime, truncate_dest, NULL);
+                         time_t *pmtime, bool truncate_dest, bool exclusive) {
+    return clone_objs(ctx, dst_obj, ranges, attrs, category, pmtime, truncate_dest, exclusive, NULL);
   }
 
   int clone_objs(void *ctx, rgw_obj& dst_obj, 
@@ -151,6 +152,7 @@ public:
                  string& category,
                  time_t *pmtime,
                  bool truncate_dest,
+                 bool exclusive,
                  pair<string, bufferlist> *cmp_xattr);
 
   int clone_obj_cond(void *ctx, rgw_obj& dst_obj, off_t dst_ofs,
@@ -158,6 +160,8 @@ public:
                 uint64_t size, map<string, bufferlist> attrs,
                 string& category,
                 time_t *pmtime,
+                bool truncate_dest,
+                bool exclusive,
                 pair<string, bufferlist> *xattr_cond) {
     RGWCloneRangeInfo info;
     vector<RGWCloneRangeInfo> v;
@@ -166,7 +170,7 @@ public:
     info.dst_ofs = dst_ofs;
     info.len = size;
     v.push_back(info);
-    return clone_objs(ctx, dst_obj, v, attrs, category, pmtime, true, xattr_cond);
+    return clone_objs(ctx, dst_obj, v, attrs, category, pmtime, truncate_dest, exclusive, xattr_cond);
   }
 
   /** Copy an object, with many extra options */