1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
6 #include "cls/rgw/cls_rgw_const.h"
7 #include "cls/rgw/cls_rgw_client.h"
9 #include "common/debug.h"
11 using namespace librados
;
13 const string
BucketIndexShardsManager::KEY_VALUE_SEPARATOR
= "#";
14 const string
BucketIndexShardsManager::SHARDS_SEPARATOR
= ",";
17 * This class represents the bucket index object operation callback context.
20 class ClsBucketIndexOpCtx
: public ObjectOperationCompletion
{
25 ClsBucketIndexOpCtx(T
* _data
, int *_ret_code
) : data(_data
), ret_code(_ret_code
) { ceph_assert(data
); }
26 ~ClsBucketIndexOpCtx() override
{}
27 void handle_completion(int r
, bufferlist
& outbl
) override
{
30 auto iter
= outbl
.cbegin();
31 decode((*data
), iter
);
32 } catch (buffer::error
& err
) {
42 void BucketIndexAioManager::do_completion(int id
) {
43 std::lock_guard l
{lock
};
45 map
<int, librados::AioCompletion
*>::iterator iter
= pendings
.find(id
);
46 ceph_assert(iter
!= pendings
.end());
47 completions
[id
] = iter
->second
;
50 // If the caller needs a list of finished objects, store them
51 // for further processing
52 map
<int, string
>::iterator miter
= pending_objs
.find(id
);
53 if (miter
!= pending_objs
.end()) {
54 completion_objs
[id
] = miter
->second
;
55 pending_objs
.erase(miter
);
61 bool BucketIndexAioManager::wait_for_completions(int valid_ret_code
,
62 int *num_completions
, int *ret_code
, map
<int, string
> *objs
) {
63 std::unique_lock locker
{lock
};
64 if (pendings
.empty() && completions
.empty()) {
68 if (completions
.empty()) {
69 // Wait for AIO completion
73 // Clear the completed AIOs
74 map
<int, librados::AioCompletion
*>::iterator iter
= completions
.begin();
75 for (; iter
!= completions
.end(); ++iter
) {
76 int r
= iter
->second
->get_return_value();
77 if (objs
&& r
== 0) { /* update list of successfully completed objs */
78 map
<int, string
>::iterator liter
= completion_objs
.find(iter
->first
);
79 if (liter
!= completion_objs
.end()) {
80 (*objs
)[liter
->first
] = liter
->second
;
83 if (ret_code
&& (r
< 0 && r
!= valid_ret_code
))
85 iter
->second
->release();
88 (*num_completions
) = completions
.size();
94 // note: currently only called by tesing code
95 void cls_rgw_bucket_init_index(ObjectWriteOperation
& o
)
98 o
.exec(RGW_CLASS
, RGW_BUCKET_INIT_INDEX
, in
);
101 static bool issue_bucket_index_init_op(librados::IoCtx
& io_ctx
,
103 BucketIndexAioManager
*manager
) {
105 librados::ObjectWriteOperation op
;
107 op
.exec(RGW_CLASS
, RGW_BUCKET_INIT_INDEX
, in
);
108 return manager
->aio_operate(io_ctx
, oid
, &op
);
111 static bool issue_bucket_index_clean_op(librados::IoCtx
& io_ctx
,
113 BucketIndexAioManager
*manager
) {
115 librados::ObjectWriteOperation op
;
117 return manager
->aio_operate(io_ctx
, oid
, &op
);
120 static bool issue_bucket_set_tag_timeout_op(librados::IoCtx
& io_ctx
,
121 const string
& oid
, uint64_t timeout
, BucketIndexAioManager
*manager
) {
123 rgw_cls_tag_timeout_op call
;
124 call
.tag_timeout
= timeout
;
126 ObjectWriteOperation op
;
127 op
.exec(RGW_CLASS
, RGW_BUCKET_SET_TAG_TIMEOUT
, in
);
128 return manager
->aio_operate(io_ctx
, oid
, &op
);
131 int CLSRGWIssueBucketIndexInit::issue_op(int shard_id
, const string
& oid
)
133 return issue_bucket_index_init_op(io_ctx
, oid
, &manager
);
136 void CLSRGWIssueBucketIndexInit::cleanup()
138 // Do best effort removal
139 for (auto citer
= objs_container
.begin(); citer
!= iter
; ++citer
) {
140 io_ctx
.remove(citer
->second
);
144 int CLSRGWIssueBucketIndexClean::issue_op(int shard_id
, const string
& oid
)
146 return issue_bucket_index_clean_op(io_ctx
, oid
, &manager
);
149 int CLSRGWIssueSetTagTimeout::issue_op(int shard_id
, const string
& oid
)
151 return issue_bucket_set_tag_timeout_op(io_ctx
, oid
, tag_timeout
, &manager
);
154 void cls_rgw_bucket_update_stats(librados::ObjectWriteOperation
& o
,
156 const map
<RGWObjCategory
, rgw_bucket_category_stats
>& stats
)
158 rgw_cls_bucket_update_stats_op call
;
159 call
.absolute
= absolute
;
163 o
.exec(RGW_CLASS
, RGW_BUCKET_UPDATE_STATS
, in
);
166 void cls_rgw_bucket_prepare_op(ObjectWriteOperation
& o
, RGWModifyOp op
, string
& tag
,
167 const cls_rgw_obj_key
& key
, const string
& locator
, bool log_op
,
168 uint16_t bilog_flags
, rgw_zone_set
& zones_trace
)
170 rgw_cls_obj_prepare_op call
;
174 call
.locator
= locator
;
175 call
.log_op
= log_op
;
176 call
.bilog_flags
= bilog_flags
;
177 call
.zones_trace
= zones_trace
;
180 o
.exec(RGW_CLASS
, RGW_BUCKET_PREPARE_OP
, in
);
183 void cls_rgw_bucket_complete_op(ObjectWriteOperation
& o
, RGWModifyOp op
, string
& tag
,
184 rgw_bucket_entry_ver
& ver
,
185 const cls_rgw_obj_key
& key
,
186 rgw_bucket_dir_entry_meta
& dir_meta
,
187 list
<cls_rgw_obj_key
> *remove_objs
, bool log_op
,
188 uint16_t bilog_flags
,
189 rgw_zone_set
*zones_trace
)
193 rgw_cls_obj_complete_op call
;
198 call
.meta
= dir_meta
;
199 call
.log_op
= log_op
;
200 call
.bilog_flags
= bilog_flags
;
202 call
.remove_objs
= *remove_objs
;
204 call
.zones_trace
= *zones_trace
;
207 o
.exec(RGW_CLASS
, RGW_BUCKET_COMPLETE_OP
, in
);
210 void cls_rgw_bucket_list_op(librados::ObjectReadOperation
& op
,
211 const cls_rgw_obj_key
& start_obj
,
212 const std::string
& filter_prefix
,
213 const std::string
& delimiter
,
214 uint32_t num_entries
,
216 rgw_cls_list_ret
* result
)
219 rgw_cls_list_op call
;
220 call
.start_obj
= start_obj
;
221 call
.filter_prefix
= filter_prefix
;
222 call
.delimiter
= delimiter
;
223 call
.num_entries
= num_entries
;
224 call
.list_versions
= list_versions
;
227 op
.exec(RGW_CLASS
, RGW_BUCKET_LIST
, in
,
228 new ClsBucketIndexOpCtx
<rgw_cls_list_ret
>(result
, NULL
));
231 static bool issue_bucket_list_op(librados::IoCtx
& io_ctx
,
233 const cls_rgw_obj_key
& start_obj
,
234 const string
& filter_prefix
,
235 const string
& delimiter
,
236 uint32_t num_entries
,
238 BucketIndexAioManager
*manager
,
239 rgw_cls_list_ret
*pdata
)
241 librados::ObjectReadOperation op
;
242 cls_rgw_bucket_list_op(op
,
243 start_obj
, filter_prefix
, delimiter
,
244 num_entries
, list_versions
, pdata
);
245 return manager
->aio_operate(io_ctx
, oid
, &op
);
248 int CLSRGWIssueBucketList::issue_op(int shard_id
, const string
& oid
)
250 return issue_bucket_list_op(io_ctx
, oid
,
251 start_obj
, filter_prefix
, delimiter
,
252 num_entries
, list_versions
, &manager
,
256 void cls_rgw_remove_obj(librados::ObjectWriteOperation
& o
, list
<string
>& keep_attr_prefixes
)
259 rgw_cls_obj_remove_op call
;
260 call
.keep_attr_prefixes
= keep_attr_prefixes
;
262 o
.exec(RGW_CLASS
, RGW_OBJ_REMOVE
, in
);
265 void cls_rgw_obj_store_pg_ver(librados::ObjectWriteOperation
& o
, const string
& attr
)
268 rgw_cls_obj_store_pg_ver_op call
;
271 o
.exec(RGW_CLASS
, RGW_OBJ_STORE_PG_VER
, in
);
274 void cls_rgw_obj_check_attrs_prefix(librados::ObjectOperation
& o
, const string
& prefix
, bool fail_if_exist
)
277 rgw_cls_obj_check_attrs_prefix call
;
278 call
.check_prefix
= prefix
;
279 call
.fail_if_exist
= fail_if_exist
;
281 o
.exec(RGW_CLASS
, RGW_OBJ_CHECK_ATTRS_PREFIX
, in
);
284 void cls_rgw_obj_check_mtime(librados::ObjectOperation
& o
, const real_time
& mtime
, bool high_precision_time
, RGWCheckMTimeType type
)
287 rgw_cls_obj_check_mtime call
;
289 call
.high_precision_time
= high_precision_time
;
292 o
.exec(RGW_CLASS
, RGW_OBJ_CHECK_MTIME
, in
);
295 int cls_rgw_bi_get(librados::IoCtx
& io_ctx
, const string oid
,
296 BIIndexType index_type
, cls_rgw_obj_key
& key
,
297 rgw_cls_bi_entry
*entry
)
300 rgw_cls_bi_get_op call
;
302 call
.type
= index_type
;
304 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_BI_GET
, in
, out
);
308 rgw_cls_bi_get_ret op_ret
;
309 auto iter
= out
.cbegin();
311 decode(op_ret
, iter
);
312 } catch (buffer::error
& err
) {
316 *entry
= op_ret
.entry
;
321 int cls_rgw_bi_put(librados::IoCtx
& io_ctx
, const string oid
, rgw_cls_bi_entry
& entry
)
324 rgw_cls_bi_put_op call
;
327 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_BI_PUT
, in
, out
);
334 void cls_rgw_bi_put(ObjectWriteOperation
& op
, const string oid
, rgw_cls_bi_entry
& entry
)
337 rgw_cls_bi_put_op call
;
340 op
.exec(RGW_CLASS
, RGW_BI_PUT
, in
);
343 int cls_rgw_bi_list(librados::IoCtx
& io_ctx
, const string oid
,
344 const string
& name
, const string
& marker
, uint32_t max
,
345 list
<rgw_cls_bi_entry
> *entries
, bool *is_truncated
)
348 rgw_cls_bi_list_op call
;
350 call
.marker
= marker
;
353 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_BI_LIST
, in
, out
);
357 rgw_cls_bi_list_ret op_ret
;
358 auto iter
= out
.cbegin();
360 decode(op_ret
, iter
);
361 } catch (buffer::error
& err
) {
365 entries
->swap(op_ret
.entries
);
366 *is_truncated
= op_ret
.is_truncated
;
371 int cls_rgw_bucket_link_olh(librados::IoCtx
& io_ctx
, const string
& oid
,
372 const cls_rgw_obj_key
& key
, bufferlist
& olh_tag
,
373 bool delete_marker
, const string
& op_tag
, rgw_bucket_dir_entry_meta
*meta
,
374 uint64_t olh_epoch
, ceph::real_time unmod_since
, bool high_precision_time
, bool log_op
, rgw_zone_set
& zones_trace
)
376 librados::ObjectWriteOperation op
;
377 cls_rgw_bucket_link_olh(op
, key
, olh_tag
, delete_marker
, op_tag
, meta
,
378 olh_epoch
, unmod_since
, high_precision_time
, log_op
,
381 return io_ctx
.operate(oid
, &op
);
385 void cls_rgw_bucket_link_olh(librados::ObjectWriteOperation
& op
, const cls_rgw_obj_key
& key
,
386 bufferlist
& olh_tag
, bool delete_marker
,
387 const string
& op_tag
, rgw_bucket_dir_entry_meta
*meta
,
388 uint64_t olh_epoch
, ceph::real_time unmod_since
, bool high_precision_time
, bool log_op
, rgw_zone_set
& zones_trace
)
391 rgw_cls_link_olh_op call
;
393 call
.olh_tag
= string(olh_tag
.c_str(), olh_tag
.length());
394 call
.op_tag
= op_tag
;
395 call
.delete_marker
= delete_marker
;
399 call
.olh_epoch
= olh_epoch
;
400 call
.log_op
= log_op
;
401 call
.unmod_since
= unmod_since
;
402 call
.high_precision_time
= high_precision_time
;
403 call
.zones_trace
= zones_trace
;
405 op
.exec(RGW_CLASS
, RGW_BUCKET_LINK_OLH
, in
);
408 int cls_rgw_bucket_unlink_instance(librados::IoCtx
& io_ctx
, const string
& oid
,
409 const cls_rgw_obj_key
& key
, const string
& op_tag
,
410 const string
& olh_tag
, uint64_t olh_epoch
, bool log_op
, rgw_zone_set
& zones_trace
)
412 librados::ObjectWriteOperation op
;
413 cls_rgw_bucket_unlink_instance(op
, key
, op_tag
, olh_tag
, olh_epoch
, log_op
, zones_trace
);
414 int r
= io_ctx
.operate(oid
, &op
);
421 void cls_rgw_bucket_unlink_instance(librados::ObjectWriteOperation
& op
,
422 const cls_rgw_obj_key
& key
, const string
& op_tag
,
423 const string
& olh_tag
, uint64_t olh_epoch
, bool log_op
, rgw_zone_set
& zones_trace
)
426 rgw_cls_unlink_instance_op call
;
428 call
.op_tag
= op_tag
;
429 call
.olh_epoch
= olh_epoch
;
430 call
.olh_tag
= olh_tag
;
431 call
.log_op
= log_op
;
432 call
.zones_trace
= zones_trace
;
434 op
.exec(RGW_CLASS
, RGW_BUCKET_UNLINK_INSTANCE
, in
);
437 void cls_rgw_get_olh_log(librados::ObjectReadOperation
& op
, const cls_rgw_obj_key
& olh
, uint64_t ver_marker
, const string
& olh_tag
, rgw_cls_read_olh_log_ret
& log_ret
, int& op_ret
)
440 rgw_cls_read_olh_log_op call
;
442 call
.ver_marker
= ver_marker
;
443 call
.olh_tag
= olh_tag
;
445 op
.exec(RGW_CLASS
, RGW_BUCKET_READ_OLH_LOG
, in
, new ClsBucketIndexOpCtx
<rgw_cls_read_olh_log_ret
>(&log_ret
, &op_ret
));
448 int cls_rgw_get_olh_log(IoCtx
& io_ctx
, string
& oid
, const cls_rgw_obj_key
& olh
, uint64_t ver_marker
,
449 const string
& olh_tag
,
450 rgw_cls_read_olh_log_ret
& log_ret
)
453 librados::ObjectReadOperation op
;
454 cls_rgw_get_olh_log(op
, olh
, ver_marker
, olh_tag
, log_ret
, op_ret
);
455 int r
= io_ctx
.operate(oid
, &op
, NULL
);
466 void cls_rgw_trim_olh_log(librados::ObjectWriteOperation
& op
, const cls_rgw_obj_key
& olh
, uint64_t ver
, const string
& olh_tag
)
469 rgw_cls_trim_olh_log_op call
;
472 call
.olh_tag
= olh_tag
;
474 op
.exec(RGW_CLASS
, RGW_BUCKET_TRIM_OLH_LOG
, in
);
477 int cls_rgw_clear_olh(IoCtx
& io_ctx
, string
& oid
, const cls_rgw_obj_key
& olh
, const string
& olh_tag
)
479 librados::ObjectWriteOperation op
;
480 cls_rgw_clear_olh(op
, olh
, olh_tag
);
482 return io_ctx
.operate(oid
, &op
);
485 void cls_rgw_clear_olh(librados::ObjectWriteOperation
& op
, const cls_rgw_obj_key
& olh
, const string
& olh_tag
)
488 rgw_cls_bucket_clear_olh_op call
;
490 call
.olh_tag
= olh_tag
;
492 op
.exec(RGW_CLASS
, RGW_BUCKET_CLEAR_OLH
, in
);
495 void cls_rgw_bilog_list(librados::ObjectReadOperation
& op
,
496 const std::string
& marker
, uint32_t max
,
497 cls_rgw_bi_log_list_ret
*pdata
, int *ret
)
499 cls_rgw_bi_log_list_op call
;
500 call
.marker
= marker
;
505 op
.exec(RGW_CLASS
, RGW_BI_LOG_LIST
, in
, new ClsBucketIndexOpCtx
<cls_rgw_bi_log_list_ret
>(pdata
, ret
));
508 static bool issue_bi_log_list_op(librados::IoCtx
& io_ctx
, const string
& oid
, int shard_id
,
509 BucketIndexShardsManager
& marker_mgr
, uint32_t max
,
510 BucketIndexAioManager
*manager
,
511 cls_rgw_bi_log_list_ret
*pdata
)
513 librados::ObjectReadOperation op
;
514 cls_rgw_bilog_list(op
, marker_mgr
.get(shard_id
, ""), max
, pdata
, nullptr);
515 return manager
->aio_operate(io_ctx
, oid
, &op
);
518 int CLSRGWIssueBILogList::issue_op(int shard_id
, const string
& oid
)
520 return issue_bi_log_list_op(io_ctx
, oid
, shard_id
, marker_mgr
, max
, &manager
, &result
[shard_id
]);
523 void cls_rgw_bilog_trim(librados::ObjectWriteOperation
& op
,
524 const std::string
& start_marker
,
525 const std::string
& end_marker
)
527 cls_rgw_bi_log_trim_op call
;
528 call
.start_marker
= start_marker
;
529 call
.end_marker
= end_marker
;
533 op
.exec(RGW_CLASS
, RGW_BI_LOG_TRIM
, in
);
536 static bool issue_bi_log_trim(librados::IoCtx
& io_ctx
, const string
& oid
, int shard_id
,
537 BucketIndexShardsManager
& start_marker_mgr
,
538 BucketIndexShardsManager
& end_marker_mgr
, BucketIndexAioManager
*manager
) {
539 cls_rgw_bi_log_trim_op call
;
540 librados::ObjectWriteOperation op
;
541 cls_rgw_bilog_trim(op
, start_marker_mgr
.get(shard_id
, ""),
542 end_marker_mgr
.get(shard_id
, ""));
543 return manager
->aio_operate(io_ctx
, oid
, &op
);
546 int CLSRGWIssueBILogTrim::issue_op(int shard_id
, const string
& oid
)
548 return issue_bi_log_trim(io_ctx
, oid
, shard_id
, start_marker_mgr
, end_marker_mgr
, &manager
);
551 static bool issue_bucket_check_index_op(IoCtx
& io_ctx
, const string
& oid
, BucketIndexAioManager
*manager
,
552 rgw_cls_check_index_ret
*pdata
) {
554 librados::ObjectReadOperation op
;
555 op
.exec(RGW_CLASS
, RGW_BUCKET_CHECK_INDEX
, in
, new ClsBucketIndexOpCtx
<rgw_cls_check_index_ret
>(
557 return manager
->aio_operate(io_ctx
, oid
, &op
);
560 int CLSRGWIssueBucketCheck::issue_op(int shard_id
, const string
& oid
)
562 return issue_bucket_check_index_op(io_ctx
, oid
, &manager
, &result
[shard_id
]);
565 static bool issue_bucket_rebuild_index_op(IoCtx
& io_ctx
, const string
& oid
,
566 BucketIndexAioManager
*manager
) {
568 librados::ObjectWriteOperation op
;
569 op
.exec(RGW_CLASS
, RGW_BUCKET_REBUILD_INDEX
, in
);
570 return manager
->aio_operate(io_ctx
, oid
, &op
);
573 int CLSRGWIssueBucketRebuild::issue_op(int shard_id
, const string
& oid
)
575 return issue_bucket_rebuild_index_op(io_ctx
, oid
, &manager
);
578 void cls_rgw_encode_suggestion(char op
, rgw_bucket_dir_entry
& dirent
, bufferlist
& updates
)
581 encode(dirent
, updates
);
584 void cls_rgw_suggest_changes(ObjectWriteOperation
& o
, bufferlist
& updates
)
586 o
.exec(RGW_CLASS
, RGW_DIR_SUGGEST_CHANGES
, updates
);
589 int CLSRGWIssueGetDirHeader::issue_op(int shard_id
, const string
& oid
)
591 cls_rgw_obj_key empty_key
;
593 string empty_delimiter
;
594 return issue_bucket_list_op(io_ctx
, oid
,
595 empty_key
, empty_prefix
, empty_delimiter
,
596 0, false, &manager
, &result
[shard_id
]);
599 static bool issue_resync_bi_log(librados::IoCtx
& io_ctx
, const string
& oid
, BucketIndexAioManager
*manager
)
602 librados::ObjectWriteOperation op
;
603 op
.exec(RGW_CLASS
, RGW_BI_LOG_RESYNC
, in
);
604 return manager
->aio_operate(io_ctx
, oid
, &op
);
607 int CLSRGWIssueResyncBucketBILog::issue_op(int shard_id
, const string
& oid
)
609 return issue_resync_bi_log(io_ctx
, oid
, &manager
);
612 static bool issue_bi_log_stop(librados::IoCtx
& io_ctx
, const string
& oid
, BucketIndexAioManager
*manager
)
615 librados::ObjectWriteOperation op
;
616 op
.exec(RGW_CLASS
, RGW_BI_LOG_STOP
, in
);
617 return manager
->aio_operate(io_ctx
, oid
, &op
);
620 int CLSRGWIssueBucketBILogStop::issue_op(int shard_id
, const string
& oid
)
622 return issue_bi_log_stop(io_ctx
, oid
, &manager
);
625 class GetDirHeaderCompletion
: public ObjectOperationCompletion
{
626 RGWGetDirHeader_CB
*ret_ctx
;
628 explicit GetDirHeaderCompletion(RGWGetDirHeader_CB
*_ctx
) : ret_ctx(_ctx
) {}
629 ~GetDirHeaderCompletion() override
{
632 void handle_completion(int r
, bufferlist
& outbl
) override
{
633 rgw_cls_list_ret ret
;
635 auto iter
= outbl
.cbegin();
637 } catch (buffer::error
& err
) {
641 ret_ctx
->handle_response(r
, ret
.dir
.header
);
645 int cls_rgw_get_dir_header_async(IoCtx
& io_ctx
, string
& oid
, RGWGetDirHeader_CB
*ctx
)
648 rgw_cls_list_op call
;
649 call
.num_entries
= 0;
651 ObjectReadOperation op
;
652 GetDirHeaderCompletion
*cb
= new GetDirHeaderCompletion(ctx
);
653 op
.exec(RGW_CLASS
, RGW_BUCKET_LIST
, in
, cb
);
654 AioCompletion
*c
= librados::Rados::aio_create_completion(nullptr, nullptr);
655 int r
= io_ctx
.aio_operate(oid
, c
, &op
, NULL
);
663 int cls_rgw_usage_log_read(IoCtx
& io_ctx
, const string
& oid
, const string
& user
, const string
& bucket
,
664 uint64_t start_epoch
, uint64_t end_epoch
, uint32_t max_entries
,
665 string
& read_iter
, map
<rgw_user_bucket
, rgw_usage_log_entry
>& usage
,
669 *is_truncated
= false;
672 rgw_cls_usage_log_read_op call
;
673 call
.start_epoch
= start_epoch
;
674 call
.end_epoch
= end_epoch
;
676 call
.max_entries
= max_entries
;
677 call
.bucket
= bucket
;
678 call
.iter
= read_iter
;
680 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_USER_USAGE_LOG_READ
, in
, out
);
685 rgw_cls_usage_log_read_ret result
;
686 auto iter
= out
.cbegin();
687 decode(result
, iter
);
688 read_iter
= result
.next_iter
;
690 *is_truncated
= result
.truncated
;
692 usage
= result
.usage
;
693 } catch (buffer::error
& e
) {
700 int cls_rgw_usage_log_trim(IoCtx
& io_ctx
, const string
& oid
, const string
& user
, const string
& bucket
,
701 uint64_t start_epoch
, uint64_t end_epoch
)
704 rgw_cls_usage_log_trim_op call
;
705 call
.start_epoch
= start_epoch
;
706 call
.end_epoch
= end_epoch
;
708 call
.bucket
= bucket
;
713 ObjectWriteOperation op
;
714 op
.exec(RGW_CLASS
, RGW_USER_USAGE_LOG_TRIM
, in
);
715 int r
= io_ctx
.operate(oid
, &op
);
725 void cls_rgw_usage_log_trim(librados::ObjectWriteOperation
& op
, const string
& user
, const string
& bucket
, uint64_t start_epoch
, uint64_t end_epoch
)
728 rgw_cls_usage_log_trim_op call
;
729 call
.start_epoch
= start_epoch
;
730 call
.end_epoch
= end_epoch
;
732 call
.bucket
= bucket
;
735 op
.exec(RGW_CLASS
, RGW_USER_USAGE_LOG_TRIM
, in
);
738 void cls_rgw_usage_log_clear(ObjectWriteOperation
& op
)
741 op
.exec(RGW_CLASS
, RGW_USAGE_LOG_CLEAR
, in
);
744 void cls_rgw_usage_log_add(ObjectWriteOperation
& op
, rgw_usage_log_info
& info
)
747 rgw_cls_usage_log_add_op call
;
750 op
.exec(RGW_CLASS
, RGW_USER_USAGE_LOG_ADD
, in
);
753 /* garbage collection */
755 void cls_rgw_gc_set_entry(ObjectWriteOperation
& op
, uint32_t expiration_secs
, cls_rgw_gc_obj_info
& info
)
758 cls_rgw_gc_set_entry_op call
;
759 call
.expiration_secs
= expiration_secs
;
762 op
.exec(RGW_CLASS
, RGW_GC_SET_ENTRY
, in
);
765 void cls_rgw_gc_defer_entry(ObjectWriteOperation
& op
, uint32_t expiration_secs
, const string
& tag
)
768 cls_rgw_gc_defer_entry_op call
;
769 call
.expiration_secs
= expiration_secs
;
772 op
.exec(RGW_CLASS
, RGW_GC_DEFER_ENTRY
, in
);
775 int cls_rgw_gc_list(IoCtx
& io_ctx
, string
& oid
, string
& marker
, uint32_t max
, bool expired_only
,
776 list
<cls_rgw_gc_obj_info
>& entries
, bool *truncated
, string
& next_marker
)
779 cls_rgw_gc_list_op call
;
780 call
.marker
= marker
;
782 call
.expired_only
= expired_only
;
784 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_GC_LIST
, in
, out
);
788 cls_rgw_gc_list_ret ret
;
790 auto iter
= out
.cbegin();
792 } catch (buffer::error
& err
) {
796 entries
.swap(ret
.entries
);
799 *truncated
= ret
.truncated
;
800 next_marker
= std::move(ret
.next_marker
);
804 void cls_rgw_gc_remove(librados::ObjectWriteOperation
& op
, const vector
<string
>& tags
)
807 cls_rgw_gc_remove_op call
;
810 op
.exec(RGW_CLASS
, RGW_GC_REMOVE
, in
);
813 int cls_rgw_lc_get_head(IoCtx
& io_ctx
, const string
& oid
, cls_rgw_lc_obj_head
& head
)
816 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_GET_HEAD
, in
, out
);
820 cls_rgw_lc_get_head_ret ret
;
822 auto iter
= out
.cbegin();
824 } catch (buffer::error
& err
) {
832 int cls_rgw_lc_put_head(IoCtx
& io_ctx
, const string
& oid
, cls_rgw_lc_obj_head
& head
)
835 cls_rgw_lc_put_head_op call
;
838 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_PUT_HEAD
, in
, out
);
842 int cls_rgw_lc_get_next_entry(IoCtx
& io_ctx
, const string
& oid
, string
& marker
,
843 cls_rgw_lc_entry
& entry
)
846 cls_rgw_lc_get_next_entry_op call
;
847 call
.marker
= marker
;
849 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_GET_NEXT_ENTRY
, in
, out
);
853 cls_rgw_lc_get_next_entry_ret ret
;
855 auto iter
= out
.cbegin();
857 } catch (buffer::error
& err
) {
865 int cls_rgw_lc_rm_entry(IoCtx
& io_ctx
, const string
& oid
,
866 const cls_rgw_lc_entry
& entry
)
869 cls_rgw_lc_rm_entry_op call
;
872 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_RM_ENTRY
, in
, out
);
876 int cls_rgw_lc_set_entry(IoCtx
& io_ctx
, const string
& oid
,
877 const cls_rgw_lc_entry
& entry
)
880 cls_rgw_lc_set_entry_op call
;
883 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_SET_ENTRY
, in
, out
);
887 int cls_rgw_lc_get_entry(IoCtx
& io_ctx
, const string
& oid
,
888 const std::string
& marker
, cls_rgw_lc_entry
& entry
)
891 cls_rgw_lc_get_entry_op call
{marker
};;
893 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_GET_ENTRY
, in
, out
);
899 cls_rgw_lc_get_entry_ret ret
;
901 auto iter
= out
.cbegin();
903 } catch (buffer::error
& err
) {
907 entry
= std::move(ret
.entry
);
911 int cls_rgw_lc_list(IoCtx
& io_ctx
, const string
& oid
,
912 const string
& marker
,
913 uint32_t max_entries
,
914 vector
<cls_rgw_lc_entry
>& entries
)
917 cls_rgw_lc_list_entries_op op
;
922 op
.max_entries
= max_entries
;
926 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_LC_LIST_ENTRIES
, in
, out
);
930 cls_rgw_lc_list_entries_ret ret
;
932 auto iter
= out
.cbegin();
934 } catch (buffer::error
& err
) {
938 std::sort(std::begin(ret
.entries
), std::end(ret
.entries
),
939 [](const cls_rgw_lc_entry
& a
, const cls_rgw_lc_entry
& b
)
940 { return a
.bucket
< b
.bucket
; });
941 entries
= std::move(ret
.entries
);
945 void cls_rgw_reshard_add(librados::ObjectWriteOperation
& op
, const cls_rgw_reshard_entry
& entry
)
948 cls_rgw_reshard_add_op call
;
951 op
.exec(RGW_CLASS
, RGW_RESHARD_ADD
, in
);
954 int cls_rgw_reshard_list(librados::IoCtx
& io_ctx
, const string
& oid
, string
& marker
, uint32_t max
,
955 list
<cls_rgw_reshard_entry
>& entries
, bool* is_truncated
)
958 cls_rgw_reshard_list_op call
;
959 call
.marker
= marker
;
962 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_RESHARD_LIST
, in
, out
);
966 cls_rgw_reshard_list_ret op_ret
;
967 auto iter
= out
.cbegin();
969 decode(op_ret
, iter
);
970 } catch (buffer::error
& err
) {
974 entries
.swap(op_ret
.entries
);
975 *is_truncated
= op_ret
.is_truncated
;
980 int cls_rgw_reshard_get(librados::IoCtx
& io_ctx
, const string
& oid
, cls_rgw_reshard_entry
& entry
)
983 cls_rgw_reshard_get_op call
;
986 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_RESHARD_GET
, in
, out
);
990 cls_rgw_reshard_get_ret op_ret
;
991 auto iter
= out
.cbegin();
993 decode(op_ret
, iter
);
994 } catch (buffer::error
& err
) {
998 entry
= op_ret
.entry
;
1003 void cls_rgw_reshard_remove(librados::ObjectWriteOperation
& op
, const cls_rgw_reshard_entry
& entry
)
1006 cls_rgw_reshard_remove_op call
;
1007 call
.tenant
= entry
.tenant
;
1008 call
.bucket_name
= entry
.bucket_name
;
1009 call
.bucket_id
= entry
.bucket_id
;
1011 op
.exec(RGW_CLASS
, RGW_RESHARD_REMOVE
, in
);
1014 int cls_rgw_set_bucket_resharding(librados::IoCtx
& io_ctx
, const string
& oid
,
1015 const cls_rgw_bucket_instance_entry
& entry
)
1018 cls_rgw_set_bucket_resharding_op call
;
1021 return io_ctx
.exec(oid
, RGW_CLASS
, RGW_SET_BUCKET_RESHARDING
, in
, out
);
1024 int cls_rgw_clear_bucket_resharding(librados::IoCtx
& io_ctx
, const string
& oid
)
1027 cls_rgw_clear_bucket_resharding_op call
;
1029 return io_ctx
.exec(oid
, RGW_CLASS
, RGW_CLEAR_BUCKET_RESHARDING
, in
, out
);
1032 int cls_rgw_get_bucket_resharding(librados::IoCtx
& io_ctx
, const string
& oid
,
1033 cls_rgw_bucket_instance_entry
*entry
)
1036 cls_rgw_get_bucket_resharding_op call
;
1038 int r
= io_ctx
.exec(oid
, RGW_CLASS
, RGW_GET_BUCKET_RESHARDING
, in
, out
);
1042 cls_rgw_get_bucket_resharding_ret op_ret
;
1043 auto iter
= out
.cbegin();
1045 decode(op_ret
, iter
);
1046 } catch (buffer::error
& err
) {
1050 *entry
= op_ret
.new_instance
;
1055 void cls_rgw_guard_bucket_resharding(librados::ObjectOperation
& op
, int ret_err
)
1058 cls_rgw_guard_bucket_resharding_op call
;
1059 call
.ret_err
= ret_err
;
1061 op
.exec(RGW_CLASS
, RGW_GUARD_BUCKET_RESHARDING
, in
);
1064 static bool issue_set_bucket_resharding(librados::IoCtx
& io_ctx
, const string
& oid
,
1065 const cls_rgw_bucket_instance_entry
& entry
,
1066 BucketIndexAioManager
*manager
) {
1068 cls_rgw_set_bucket_resharding_op call
;
1071 librados::ObjectWriteOperation op
;
1072 op
.exec(RGW_CLASS
, RGW_SET_BUCKET_RESHARDING
, in
);
1073 return manager
->aio_operate(io_ctx
, oid
, &op
);
1076 int CLSRGWIssueSetBucketResharding::issue_op(int shard_id
, const string
& oid
)
1078 return issue_set_bucket_resharding(io_ctx
, oid
, entry
, &manager
);