diff --git a/src/librbd/deep_copy/ObjectCopyRequest.cc b/src/librbd/deep_copy/ObjectCopyRequest.cc index 4424e09484e..35431391e41 100644 --- a/src/librbd/deep_copy/ObjectCopyRequest.cc +++ b/src/librbd/deep_copy/ObjectCopyRequest.cc @@ -340,6 +340,7 @@ void ObjectCopyRequest::send_write_object() { librados::ObjectWriteOperation op; if (!m_dst_image_ctx->migration_info.empty()) { + ldout(m_cct, 20) << "assert_snapc_seq=" << dst_snap_seq << dendl; cls_client::assert_snapc_seq(&op, dst_snap_seq, cls::rbd::ASSERT_SNAPC_SEQ_GT_SNAPSET_SEQ); } diff --git a/src/librbd/io/ImageDispatcher.cc b/src/librbd/io/ImageDispatcher.cc index a9c1c985522..fa0cc77703d 100644 --- a/src/librbd/io/ImageDispatcher.cc +++ b/src/librbd/io/ImageDispatcher.cc @@ -217,11 +217,11 @@ void ImageDispatcher::shut_down(Context* on_finish) { delete async_op; on_finish->complete(0); }); - on_finish = new LambdaContext([this, async_op, on_finish](int r) { - async_op->start_op(*this->m_image_ctx); - async_op->flush(on_finish); + on_finish = new LambdaContext([this, on_finish](int r) { + Dispatcher::shut_down(on_finish); }); - Dispatcher::shut_down(on_finish); + async_op->start_op(*this->m_image_ctx); + async_op->flush(on_finish); } template diff --git a/src/librbd/io/ObjectRequest.cc b/src/librbd/io/ObjectRequest.cc index 0914d08ef19..00fea70d609 100644 --- a/src/librbd/io/ObjectRequest.cc +++ b/src/librbd/io/ObjectRequest.cc @@ -232,7 +232,7 @@ void ObjectReadRequest::read_object() { } image_locker.unlock(); - ldout(image_ctx->cct, 20) << dendl; + ldout(image_ctx->cct, 20) << "snap_id=" << read_snap_id << dendl; neorados::ReadOp read_op; for (auto& extent: *this->m_extents) { @@ -485,14 +485,16 @@ void AbstractObjectWriteRequest::write_object() { neorados::WriteOp write_op; if (m_copyup_enabled) { - ldout(image_ctx->cct, 20) << "guarding write" << dendl; if (m_guarding_migration_write) { + auto snap_seq = (this->m_io_context->write_snap_context() ? + this->m_io_context->write_snap_context()->first : 0); + ldout(image_ctx->cct, 20) << "guarding write: snap_seq=" << snap_seq + << dendl; + cls_client::assert_snapc_seq( - &write_op, - (this->m_io_context->write_snap_context() ? - this->m_io_context->write_snap_context()->first : 0), - cls::rbd::ASSERT_SNAPC_SEQ_LE_SNAPSET_SEQ); + &write_op, snap_seq, cls::rbd::ASSERT_SNAPC_SEQ_LE_SNAPSET_SEQ); } else { + ldout(image_ctx->cct, 20) << "guarding write" << dendl; write_op.assert_exists(); } } @@ -844,7 +846,8 @@ void ObjectListSnapsRequest::handle_list_snaps(int r) { << "clone_end_snap_id=" << clone_end_snap_id << ", " << "diff=" << diff << ", " << "end_size=" << end_size << ", " - << "exists=" << exists << dendl; + << "exists=" << exists << ", " + << "whole_object=" << read_whole_object << dendl; if (end_snap_id <= first_snap_id) { // don't include deltas from the starting snapshots, but we iterate over // it to track its existence and size diff --git a/src/librbd/migration/OpenSourceImageRequest.cc b/src/librbd/migration/OpenSourceImageRequest.cc index e19739b5e11..8abdedf332d 100644 --- a/src/librbd/migration/OpenSourceImageRequest.cc +++ b/src/librbd/migration/OpenSourceImageRequest.cc @@ -41,7 +41,7 @@ void OpenSourceImageRequest::open_source() { ldout(m_cct, 10) << dendl; // note that all source image ctx properties are placeholders - *m_src_image_ctx = I::create("", "", m_src_snap_id, m_io_ctx, true); + *m_src_image_ctx = I::create("", "", CEPH_NOSNAP, m_io_ctx, true); auto src_image_ctx = *m_src_image_ctx; src_image_ctx->child = m_dst_image_ctx; @@ -63,6 +63,10 @@ void OpenSourceImageRequest::open_source() { import_only = false; } + ldout(m_cct, 15) << "source_spec=" << source_spec << ", " + << "source_snap_id=" << m_src_snap_id << ", " + << "import_only=" << import_only << dendl; + SourceSpecBuilder source_spec_builder{src_image_ctx}; json_spirit::mObject source_spec_object; int r = source_spec_builder.parse_source_spec(source_spec, @@ -169,6 +173,9 @@ void OpenSourceImageRequest::handle_get_snapshots(int r) { auto& [snap_id, snap_info] = *it; snapc.snaps.push_back(snap_id); + ldout(m_cct, 10) << "adding snap: ns=" << snap_info.snap_namespace << ", " + << "name=" << snap_info.name << ", " + << "id=" << snap_id << dendl; src_image_ctx->add_snap( snap_info.snap_namespace, snap_info.name, snap_id, snap_info.size, snap_info.parent, snap_info.protection_status, @@ -179,11 +186,22 @@ void OpenSourceImageRequest::handle_get_snapshots(int r) { } src_image_ctx->snapc = snapc; + ldout(m_cct, 15) << "read snap id: " << m_src_snap_id << ", " + << "write snapc={" + << "seq=" << snapc.seq << ", " + << "snaps=" << snapc.snaps << "}" << dendl; + // ensure data_ctx and data_io_context are pointing to correct snapshot - if (src_image_ctx->open_snap_id != CEPH_NOSNAP) { - int r = src_image_ctx->snap_set(src_image_ctx->open_snap_id); - ceph_assert(r == 0); - src_image_ctx->open_snap_id = CEPH_NOSNAP; + if (m_src_snap_id != CEPH_NOSNAP) { + int r = src_image_ctx->snap_set(m_src_snap_id); + if (r < 0) { + src_image_ctx->image_lock.unlock(); + + lderr(m_cct) << "error setting source image snap id: " + << cpp_strerror(r) << dendl; + finish(r); + return; + } } src_image_ctx->image_lock.unlock(); diff --git a/src/test/librados_test_stub/TestMemIoCtxImpl.cc b/src/test/librados_test_stub/TestMemIoCtxImpl.cc index 6c004af007b..6ad3ce3861a 100644 --- a/src/test/librados_test_stub/TestMemIoCtxImpl.cc +++ b/src/test/librados_test_stub/TestMemIoCtxImpl.cc @@ -11,6 +11,11 @@ #include #include +#define dout_subsys ceph_subsys_rados +#undef dout_prefix +#define dout_prefix *_dout << "TestMemIoCtxImpl: " << this << " " << __func__ \ + << ": " << oid << " " + static void to_vector(const interval_set &set, std::vector > *vec) { vec->clear(); @@ -73,6 +78,9 @@ int TestMemIoCtxImpl::append(const std::string& oid, const bufferlist &bl, return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "length=" << bl.length() << ", snapc=" << snapc << dendl; + TestMemCluster::SharedFile file; { std::unique_lock l{m_pool->file_lock}; @@ -127,6 +135,9 @@ int TestMemIoCtxImpl::create(const std::string& oid, bool exclusive, return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "snapc=" << snapc << dendl; + std::unique_lock l{m_pool->file_lock}; if (exclusive) { TestMemCluster::SharedFile file = get_file(oid, false, CEPH_NOSNAP, {}); @@ -140,6 +151,9 @@ int TestMemIoCtxImpl::create(const std::string& oid, bool exclusive, } int TestMemIoCtxImpl::list_snaps(const std::string& oid, snap_set_t *out_snaps) { + auto cct = m_client->cct(); + ldout(cct, 20) << dendl; + if (m_client->is_blocklisted()) { return -EBLOCKLISTED; } @@ -206,6 +220,23 @@ int TestMemIoCtxImpl::list_snaps(const std::string& oid, snap_set_t *out_snaps) out_snaps->clones.push_back(head_clone); } } + + ldout(cct, 20) << "seq=" << out_snaps->seq << ", " + << "clones=["; + bool first_clone = true; + for (auto& clone : out_snaps->clones) { + *_dout << "{" + << "cloneid=" << clone.cloneid << ", " + << "snaps=" << clone.snaps << ", " + << "overlap=" << clone.overlap << ", " + << "size=" << clone.size << "}"; + if (!first_clone) { + *_dout << ", "; + } else { + first_clone = false; + } + } + *_dout << "]" << dendl; return 0; } @@ -359,6 +390,9 @@ int TestMemIoCtxImpl::remove(const std::string& oid, const SnapContext &snapc) { return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "snapc=" << snapc << dendl; + std::unique_lock l{m_pool->file_lock}; TestMemCluster::SharedFile file = get_file(oid, false, CEPH_NOSNAP, snapc); if (file == NULL) { @@ -556,6 +590,9 @@ int TestMemIoCtxImpl::truncate(const std::string& oid, uint64_t size, return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "size=" << size << ", snapc=" << snapc << dendl; + TestMemCluster::SharedFile file; { std::unique_lock l{m_pool->file_lock}; @@ -594,6 +631,10 @@ int TestMemIoCtxImpl::write(const std::string& oid, bufferlist& bl, size_t len, return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "extent=" << off << "~" << len << ", snapc=" << snapc + << dendl; + TestMemCluster::SharedFile file; { std::unique_lock l{m_pool->file_lock}; @@ -621,6 +662,9 @@ int TestMemIoCtxImpl::write_full(const std::string& oid, bufferlist& bl, return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "length=" << bl.length() << ", snapc=" << snapc << dendl; + TestMemCluster::SharedFile file; { std::unique_lock l{m_pool->file_lock}; @@ -742,6 +786,10 @@ int TestMemIoCtxImpl::zero(const std::string& oid, uint64_t off, uint64_t len, return -EBLOCKLISTED; } + auto cct = m_client->cct(); + ldout(cct, 20) << "extent=" << off << "~" << len << ", snapc=" << snapc + << dendl; + bool truncate_redirect = false; TestMemCluster::SharedFile file; {