f(SET_REDIRECT, __CEPH_OSD_OP(WR, DATA, 39), "set-redirect") \
f(SET_CHUNK, __CEPH_OSD_OP(WR, DATA, 40), "set-chunk") \
f(TIER_PROMOTE, __CEPH_OSD_OP(WR, DATA, 41), "tier-promote") \
+ f(UNSET_MANIFEST, __CEPH_OSD_OP(WR, DATA, 42), "unset-manifest") \
\
/** attrs **/ \
/* read */ \
void set_chunk(uint64_t src_offset, uint64_t src_length, const IoCtx& tgt_ioctx,
std::string tgt_oid, uint64_t tgt_offset, int flag = 0);
void tier_promote();
+ void unset_manifest();
friend class IoCtx;
o->tier_promote();
}
+void librados::ObjectWriteOperation::unset_manifest()
+{
+ ::ObjectOperation *o = &impl->o;
+ o->unset_manifest();
+}
+
void librados::ObjectWriteOperation::tmap_put(const bufferlist &bl)
{
::ObjectOperation *o = &impl->o;
ceph_osd_op& op = osd_op.op;
if (op.op == CEPH_OSD_OP_SET_REDIRECT ||
op.op == CEPH_OSD_OP_SET_CHUNK ||
- op.op == CEPH_OSD_OP_TIER_PROMOTE) {
+ op.op == CEPH_OSD_OP_TIER_PROMOTE ||
+ op.op == CEPH_OSD_OP_UNSET_MANIFEST) {
return cache_result_t::NOOP;
}
}
break;
+ case CEPH_OSD_OP_UNSET_MANIFEST:
+ ++ctx->num_write;
+ {
+ if (pool.info.is_tier()) {
+ result = -EINVAL;
+ break;
+ }
+ if (!obs.exists) {
+ result = -ENOENT;
+ break;
+ }
+ if (!oi.has_manifest()) {
+ result = -EOPNOTSUPP;
+ break;
+ }
+ if (get_osdmap()->require_osd_release < CEPH_RELEASE_LUMINOUS) {
+ result = -EOPNOTSUPP;
+ break;
+ }
+
+ if (oi.manifest.is_redirect()) {
+ if ((oi.flags & object_info_t::FLAG_REDIRECT_HAS_REFERENCE)) {
+ ctx->register_on_commit(
+ [oi, ctx, this](){
+ object_locator_t target_oloc(oi.manifest.redirect_target);
+ refcount_manifest(ctx->obc, target_oloc, oi.manifest.redirect_target,
+ SnapContext(), false, NULL, 0);
+ });
+ }
+ } else if (oi.manifest.is_chunked()) {
+ ctx->register_on_commit(
+ [oi, ctx, this](){
+ for (auto p : oi.manifest.chunk_map) {
+ if (p.second.flags & chunk_info_t::FLAG_HAS_REFERENCE) {
+ object_locator_t target_oloc(p.second.oid);
+ refcount_manifest(ctx->obc, target_oloc, p.second.oid,
+ SnapContext(), false, NULL, p.first);
+ }
+ }
+ });
+ } else {
+ assert(0 == "unrecognized manifest type");
+ }
+
+ oi.clear_flag(object_info_t::FLAG_MANIFEST);
+ oi.manifest = object_manifest_t();
+ ctx->delta_stats.num_objects_manifest--;
+ ctx->delta_stats.num_wr++;
+ ctx->modify = true;
+ }
+
+ break;
+
// -- object attrs --
case CEPH_OSD_OP_SETXATTR:
add_op(CEPH_OSD_OP_TIER_PROMOTE);
}
+ void unset_manifest() {
+ add_op(CEPH_OSD_OP_UNSET_MANIFEST);
+ }
+
void set_alloc_hint(uint64_t expected_object_size,
uint64_t expected_write_size,
uint32_t flags) {
" set-chunk <object A> <offset> <length> --target-pool <caspool> <target object A> <taget-offset> [--with-reference]\n"
" convert an object to chunked object\n"
" tier-promote <obj-name> promote the object to the base tier\n"
+" unset-manifest <obj-name> unset redirect or chunked object\n"
"\n"
"IMPORT AND EXPORT\n"
" export [filename]\n"
<< cpp_strerror(ret) << std::endl;
goto out;
}
+ } else if (strcmp(nargs[0], "unset-manifest") == 0) {
+ if (!pool_name || nargs.size() < 2)
+ usage_exit();
+ string oid(nargs[1]);
+
+ ObjectWriteOperation op;
+ op.unset_manifest();
+ ret = io_ctx.operate(oid, &op);
+ if (ret < 0) {
+ cerr << "error unset-manifest " << pool_name << "/" << oid << " : "
+ << cpp_strerror(ret) << std::endl;
+ goto out;
+ }
} else if (strcmp(nargs[0], "export") == 0) {
// export [filename]
if (!pool_name || nargs.size() > 2) {