Skip to content

Commit e2fb2c6

Browse files
reshard: limiting the number of log to be recorded
When the bucket's index shards are already overloaded, avoid adding too many extra keys in the reshard log. Limiting the size of this reshard log to `rgw_reshardlog_threshold`, if an index write operation during the logrecord stage would exceed that limit, returning the ERR_BUSY_RESHARDING error early. Using the reshardlog_entries in `rgw_bucket_dir_header` to do this, when writting shards, adding the reshardlog_entries. But not need to add in deleting, because number of index entries reduce meanwhile. Signed-off-by: Mingyuan Liang <[email protected]>
1 parent cec5e83 commit e2fb2c6

File tree

8 files changed

+197
-47
lines changed

8 files changed

+197
-47
lines changed

src/cls/rgw/cls_rgw.cc

Lines changed: 117 additions & 40 deletions
Large diffs are not rendered by default.

src/cls/rgw/cls_rgw_types.cc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -697,6 +697,7 @@ void rgw_bucket_dir_header::dump(Formatter *f) const
697697
}
698698
f->close_section();
699699
::encode_json("new_instance", new_instance, f);
700+
f->dump_int("reshardlog_entries", reshardlog_entries);
700701
}
701702

702703
void rgw_bucket_dir::generate_test_instances(list<rgw_bucket_dir*>& o)

src/cls/rgw/cls_rgw_types.h

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -828,22 +828,25 @@ struct rgw_bucket_dir_header {
828828
std::string max_marker;
829829
cls_rgw_bucket_instance_entry new_instance;
830830
bool syncstopped;
831+
uint32_t reshardlog_entries;
831832

832-
rgw_bucket_dir_header() : tag_timeout(0), ver(0), master_ver(0), syncstopped(false) {}
833+
rgw_bucket_dir_header() : tag_timeout(0), ver(0), master_ver(0), syncstopped(false),
834+
reshardlog_entries(0) {}
833835

834836
void encode(ceph::buffer::list &bl) const {
835-
ENCODE_START(7, 2, bl);
837+
ENCODE_START(8, 2, bl);
836838
encode(stats, bl);
837839
encode(tag_timeout, bl);
838840
encode(ver, bl);
839841
encode(master_ver, bl);
840842
encode(max_marker, bl);
841843
encode(new_instance, bl);
842844
encode(syncstopped,bl);
845+
encode(reshardlog_entries, bl);
843846
ENCODE_FINISH(bl);
844847
}
845848
void decode(ceph::buffer::list::const_iterator &bl) {
846-
DECODE_START_LEGACY_COMPAT_LEN(6, 2, 2, bl);
849+
DECODE_START_LEGACY_COMPAT_LEN(8, 2, 2, bl);
847850
decode(stats, bl);
848851
if (struct_v > 2) {
849852
decode(tag_timeout, bl);
@@ -867,6 +870,11 @@ struct rgw_bucket_dir_header {
867870
if (struct_v >= 7) {
868871
decode(syncstopped,bl);
869872
}
873+
if (struct_v >= 8) {
874+
decode(reshardlog_entries, bl);
875+
} else {
876+
reshardlog_entries = 0;
877+
}
870878
DECODE_FINISH(bl);
871879
}
872880
void dump(ceph::Formatter *f) const;

src/common/options/rgw.yaml.in

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2730,6 +2730,17 @@ options:
27302730
- rgw
27312731
see_also:
27322732
- rgw_reshard_progress_judge_interval
2733+
- name: rgw_reshardlog_threshold
2734+
type: uint
2735+
level: dev
2736+
desc: threshold for a shard to record log before blocking writes
2737+
default: 30000
2738+
with_legacy: true
2739+
services:
2740+
- rgw
2741+
- osd
2742+
see_also:
2743+
- rgw_reshard_progress_judge_interval
27332744
- name: rgw_debug_inject_set_olh_err
27342745
type: uint
27352746
level: dev

src/rgw/driver/rados/rgw_rados.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7801,7 +7801,7 @@ int RGWRados::block_while_resharding(RGWRados::BucketShard *bs,
78017801
return ret;
78027802
}
78037803

7804-
if (!entry.resharding_in_progress()) {
7804+
if (!entry.resharding()) {
78057805
ret = fetch_new_bucket_info("get_bucket_resharding_succeeded");
78067806
if (ret < 0) {
78077807
ldpp_dout(dpp, 0) << "ERROR: " << __func__ <<

src/rgw/driver/rados/rgw_reshard.cc

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1357,14 +1357,15 @@ int RGWBucketReshard::execute(int num_shards,
13571357
return ret;
13581358
}
13591359

1360+
auto current_num_shards = rgw::num_shards(bucket_info.layout.current_index);
13601361
ret = commit_reshard(store, bucket_info, bucket_attrs, fault, dpp, y);
13611362
if (ret < 0) {
13621363
return ret;
13631364
}
13641365

13651366
ldpp_dout(dpp, 1) << __func__ << " INFO: reshard of bucket \"" <<
13661367
bucket_info.bucket.name << "\" from " <<
1367-
rgw::num_shards(bucket_info.layout.current_index) << " shards to " << num_shards <<
1368+
current_num_shards << " shards to " << num_shards <<
13681369
" shards completed successfully" << dendl;
13691370

13701371
return 0;

src/test/cli/radosgw-admin/help.t

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -182,8 +182,8 @@
182182
reshard cancel cancel resharding a bucket
183183
reshard stale-instances list list stale-instances from bucket resharding
184184
reshard stale-instances delete cleanup stale-instances from bucket resharding
185-
reshardlog list list bucket reshard newest generation log
186-
reshardlog purge trim all bucket resharding log
185+
reshardlog list list bucket resharding log
186+
reshardlog purge trim bucket resharding log
187187
sync error list list sync error
188188
sync error trim trim sync error
189189
mfa create create a new MFA TOTP token

src/test/cls_rgw/test_cls_rgw.cc

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1418,3 +1418,55 @@ TEST_F(cls_rgw, reshardlog_list)
14181418
ASSERT_FALSE(is_truncated);
14191419
ASSERT_EQ(2u, entries.size());
14201420
}
1421+
1422+
void reshardlog_entries(librados::IoCtx& ioctx, const std::string& oid, uint32_t num_entries)
1423+
{
1424+
map<int, struct rgw_cls_list_ret> results;
1425+
map<int, string> oids;
1426+
oids[0] = oid;
1427+
ASSERT_EQ(0, CLSRGWIssueGetDirHeader(ioctx, oids, results, 8)());
1428+
1429+
uint32_t entries = 0;
1430+
map<int, struct rgw_cls_list_ret>::iterator iter = results.begin();
1431+
for (; iter != results.end(); ++iter) {
1432+
entries += (iter->second).dir.header.reshardlog_entries;
1433+
}
1434+
ASSERT_EQ(entries, num_entries);
1435+
}
1436+
1437+
TEST_F(cls_rgw, reshardlog_num)
1438+
{
1439+
string bucket_oid = str_int("reshard2", 0);
1440+
1441+
ObjectWriteOperation op;
1442+
cls_rgw_bucket_init_index(op);
1443+
ASSERT_EQ(0, ioctx.operate(bucket_oid, &op));
1444+
1445+
cls_rgw_obj_key obj1 = str_int("obj1", 0);
1446+
string tag = str_int("tag-prepare", 0);
1447+
string loc = str_int("loc", 0);
1448+
index_prepare(ioctx, bucket_oid, CLS_RGW_OP_ADD, tag, obj1, loc);
1449+
rgw_bucket_dir_entry_meta meta;
1450+
index_complete(ioctx, bucket_oid, CLS_RGW_OP_ADD, tag, 1, obj1, meta);
1451+
1452+
// do not record logs
1453+
reshardlog_entries(ioctx, bucket_oid, 0u);
1454+
1455+
// set reshard status to IN_LOGRECORD
1456+
cls_rgw_bucket_instance_entry entry;
1457+
entry.reshard_status = cls_rgw_reshard_status::IN_LOGRECORD;
1458+
set_reshard_status(ioctx, bucket_oid, entry);
1459+
1460+
// record a log in prepare not add reshardlog_entry
1461+
cls_rgw_obj_key obj2 = str_int("obj2", 0);
1462+
index_prepare(ioctx, bucket_oid, CLS_RGW_OP_ADD, tag, obj2, loc);
1463+
reshardlog_entries(ioctx, bucket_oid, 0u);
1464+
// record a log in complete add reshardlog_entry
1465+
index_complete(ioctx, bucket_oid, CLS_RGW_OP_ADD, tag, 1, obj2, meta);
1466+
reshardlog_entries(ioctx, bucket_oid, 1u);
1467+
1468+
// record a log in deleting obj not add reshardlog_entry
1469+
index_prepare(ioctx, bucket_oid, CLS_RGW_OP_DEL, tag, obj1, loc);
1470+
index_complete(ioctx, bucket_oid, CLS_RGW_OP_DEL, tag, 1, obj1, meta);
1471+
reshardlog_entries(ioctx, bucket_oid, 1u);
1472+
}

0 commit comments

Comments
 (0)