// -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
// vim: ts=8 sw=2 smarttab
+#include <limits>
+
#include "rgw_rados.h"
#include "rgw_bucket.h"
#include "rgw_reshard.h"
#define RESHARD_SHARD_WINDOW 64
#define RESHARD_MAX_AIO 128
+
class BucketReshardShard {
RGWRados *store;
const RGWBucketInfo& bucket_info;
reshard_oid << " with " << cpp_strerror(-ret) << dendl;
return ret;
}
+ reshard_lock.set_must_renew(false);
lock_start_time = now;
lock_renew_thresh = lock_start_time + lock_duration / 2;
ldout(store->ctx(), 20) << __func__ << "(): successfully renewed lock on " <<
return 0;
}
-int RGWBucketReshard::set_resharding_status(const string& new_instance_id, int32_t num_shards, cls_rgw_reshard_status status)
+int RGWBucketReshard::set_resharding_status(RGWRados* store,
+ RGWBucketInfo& bucket_info,
+ const string& new_instance_id,
+ int32_t num_shards,
+ cls_rgw_reshard_status status)
{
if (new_instance_id.empty()) {
ldout(store->ctx(), 0) << __func__ << " missing new bucket instance id" << dendl;
return 0;
}
+// reshard lock assumes lock is held
int RGWBucketReshard::clear_resharding()
{
- cls_rgw_bucket_instance_entry instance_entry;
+ int ret = clear_index_shard_reshard_status();
+ if (ret < 0) {
+ ldout(store->ctx(), 0) << "RGWBucketReshard::" << __func__ <<
+ " ERROR: error clearing reshard status from index shard " <<
+ cpp_strerror(-ret) << dendl;
+ return ret;
+ }
- int ret = store->bucket_set_reshard(bucket_info, instance_entry);
+ cls_rgw_bucket_instance_entry instance_entry;
+ ret = store->bucket_set_reshard(bucket_info, instance_entry);
if (ret < 0) {
- ldout(store->ctx(), 0) << "RGWReshard::" << __func__ << " ERROR: error setting bucket resharding flag on bucket index: "
- << cpp_strerror(-ret) << dendl;
+ ldout(store->ctx(), 0) << "RGWReshard::" << __func__ <<
+ " ERROR: error setting bucket resharding flag on bucket index: " <<
+ cpp_strerror(-ret) << dendl;
return ret;
}
+
+ return 0;
+}
+
+int RGWBucketReshard::clear_index_shard_reshard_status(RGWRados* store,
+ RGWBucketInfo& bucket_info)
+{
+ uint32_t num_shards = bucket_info.num_shards;
+
+ if (num_shards < std::numeric_limits<uint32_t>::max()) {
+ int ret = set_resharding_status(store, bucket_info,
+ bucket_info.bucket.bucket_id,
+ (num_shards < 1 ? 1 : num_shards),
+ CLS_RGW_RESHARD_NONE);
+ if (ret < 0) {
+ ldout(store->ctx(), 0) << "RGWBucketReshard::" << __func__ <<
+ " ERROR: error clearing reshard status from index shard " <<
+ cpp_strerror(-ret) << dendl;
+ return ret;
+ }
+ }
+
return 0;
}
ret = clear_resharding();
unlock_bucket();
- return 0;
+ return ret;
}
class BucketInfoReshardUpdate
~BucketInfoReshardUpdate() {
if (in_progress) {
+ int ret =
+ RGWBucketReshard::clear_index_shard_reshard_status(store, bucket_info);
+ if (ret < 0) {
+ lderr(store->ctx()) << "Error: " << __func__ <<
+ " clear_index_shard_status returned " << ret << dendl;
+ }
bucket_info.new_bucket_instance_id.clear();
- set_status(CLS_RGW_RESHARD_NONE);
+ set_status(CLS_RGW_RESHARD_NONE); // saves new_bucket_instance as well
}
}
return -EINVAL;
}
+ // NB: destructor cleans up sharding state if reshard does not
+ // complete successfully
BucketInfoReshardUpdate bucket_info_updater(store, bucket_info, bucket_attrs, new_bucket_info.bucket.bucket_id);
ret = bucket_info_updater.start();
int lock_bucket();
void unlock_bucket();
int renew_lock_bucket(const Clock::time_point&);
- int set_resharding_status(const string& new_instance_id, int32_t num_shards, cls_rgw_reshard_status status);
int clear_resharding();
int create_new_bucket_instance(int new_num_shards, RGWBucketInfo& new_bucket_info);
RGWReshard *reshard_log = nullptr);
int get_status(std::list<cls_rgw_bucket_instance_entry> *status);
int cancel();
+ static int clear_index_shard_reshard_status(RGWRados* store,
+ RGWBucketInfo& bucket_info);
+ int clear_index_shard_reshard_status() {
+ return clear_index_shard_reshard_status(store, bucket_info);
+ }
+ static int set_resharding_status(RGWRados* store, RGWBucketInfo& bucket_info,
+ const string& new_instance_id,
+ int32_t num_shards,
+ cls_rgw_reshard_status status);
+ int set_resharding_status(const string& new_instance_id,
+ int32_t num_shards,
+ cls_rgw_reshard_status status) {
+ return set_resharding_status(store, bucket_info,
+ new_instance_id, num_shards, status);
+ }
}; // RGWBucketReshard
class RGWReshard {