mirror of
https://github.com/ceph/ceph
synced 2025-02-24 11:37:37 +00:00
Merge pull request #38237 from myoungwon/wip-fix-clone-size-mismatch
osd: fix clone size mismatch when deduped object is evicted Reviewed-by: Samuel Just <sjust@redhat.com>
This commit is contained in:
commit
3ed7dccb84
@ -7183,14 +7183,13 @@ int PrimaryLogPG::do_osd_ops(OpContext *ctx, vector<OSDOp>& ops)
|
||||
chunk_length += p.second.length;
|
||||
}
|
||||
if (chunk_length == obs.oi.size) {
|
||||
// truncate
|
||||
for (auto p : obs.oi.manifest.chunk_map) {
|
||||
for (auto &p : obs.oi.manifest.chunk_map) {
|
||||
p.second.set_flag(chunk_info_t::FLAG_MISSING);
|
||||
}
|
||||
t->truncate(obs.oi.soid, 0);
|
||||
ctx->delta_stats.num_bytes -= obs.oi.size;
|
||||
// punch hole
|
||||
t->zero(soid, 0, oi.size);
|
||||
oi.clear_data_digest();
|
||||
ctx->delta_stats.num_wr++;
|
||||
oi.size = 0;
|
||||
ctx->cache_operation = true;
|
||||
}
|
||||
osd->logger->inc(l_osd_tier_evict);
|
||||
|
@ -4608,24 +4608,7 @@ TEST_F(LibRadosTwoPoolsPP, ManifestEvict) {
|
||||
|
||||
stat_op.stat(&size, NULL, NULL);
|
||||
ASSERT_EQ(0, ioctx.operate("foo", &stat_op, NULL));
|
||||
ASSERT_EQ(0, size);
|
||||
}
|
||||
|
||||
ioctx.snap_set_read(my_snaps[1]);
|
||||
{
|
||||
ObjectReadOperation op, stat_op;
|
||||
uint64_t size;
|
||||
op.tier_evict();
|
||||
librados::AioCompletion *completion = cluster.aio_create_completion();
|
||||
ASSERT_EQ(0, ioctx.aio_operate(
|
||||
"foo", completion, &op,
|
||||
librados::OPERATION_IGNORE_OVERLAY, NULL));
|
||||
completion->wait_for_complete();
|
||||
ASSERT_EQ(0, completion->get_return_value());
|
||||
|
||||
stat_op.stat(&size, NULL, NULL);
|
||||
ASSERT_EQ(0, ioctx.operate("foo", &stat_op, NULL));
|
||||
ASSERT_EQ(0, size);
|
||||
ASSERT_EQ(10, size);
|
||||
}
|
||||
|
||||
ioctx.snap_set_read(librados::SNAP_HEAD);
|
||||
@ -4647,6 +4630,117 @@ TEST_F(LibRadosTwoPoolsPP, ManifestEvict) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
TEST_F(LibRadosTwoPoolsPP, ManifestSnapSizeMismatch) {
|
||||
// skip test if not yet octopus
|
||||
if (_get_required_osd_release(cluster) < "octopus") {
|
||||
cout << "cluster is not yet octopus, skipping test" << std::endl;
|
||||
return;
|
||||
}
|
||||
|
||||
// create object
|
||||
{
|
||||
bufferlist bl;
|
||||
bl.append("there hiHI");
|
||||
ObjectWriteOperation op;
|
||||
op.write_full(bl);
|
||||
ASSERT_EQ(0, cache_ioctx.operate("foo", &op));
|
||||
}
|
||||
{
|
||||
bufferlist bl;
|
||||
bl.append("there hiHI");
|
||||
ObjectWriteOperation op;
|
||||
op.write_full(bl);
|
||||
ASSERT_EQ(0, ioctx.operate("chunk1", &op));
|
||||
}
|
||||
{
|
||||
bufferlist bl;
|
||||
bl.append("there HIHI");
|
||||
ObjectWriteOperation op;
|
||||
op.write_full(bl);
|
||||
ASSERT_EQ(0, ioctx.operate("chunk2", &op));
|
||||
}
|
||||
|
||||
// wait for maps to settle
|
||||
cluster.wait_for_latest_osdmap();
|
||||
|
||||
// create a snapshot, clone
|
||||
vector<uint64_t> my_snaps(1);
|
||||
ASSERT_EQ(0, cache_ioctx.selfmanaged_snap_create(&my_snaps[0]));
|
||||
ASSERT_EQ(0, cache_ioctx.selfmanaged_snap_set_write_ctx(my_snaps[0],
|
||||
my_snaps));
|
||||
|
||||
{
|
||||
bufferlist bl;
|
||||
bl.append("There hiHI");
|
||||
ASSERT_EQ(0, cache_ioctx.write("foo", bl, bl.length(), 0));
|
||||
}
|
||||
|
||||
my_snaps.resize(2);
|
||||
my_snaps[1] = my_snaps[0];
|
||||
ASSERT_EQ(0, cache_ioctx.selfmanaged_snap_create(&my_snaps[0]));
|
||||
ASSERT_EQ(0, cache_ioctx.selfmanaged_snap_set_write_ctx(my_snaps[0],
|
||||
my_snaps));
|
||||
|
||||
{
|
||||
bufferlist bl;
|
||||
bl.append("tHere hiHI");
|
||||
ASSERT_EQ(0, cache_ioctx.write("foo", bl, bl.length(), 0));
|
||||
}
|
||||
|
||||
// set-chunk
|
||||
manifest_set_chunk(cluster, ioctx, cache_ioctx, 0, 10, "chunk1", "foo");
|
||||
|
||||
cache_ioctx.snap_set_read(my_snaps[1]);
|
||||
|
||||
// set-chunk
|
||||
manifest_set_chunk(cluster, ioctx, cache_ioctx, 0, 10, "chunk2", "foo");
|
||||
|
||||
// evict
|
||||
{
|
||||
ObjectReadOperation op, stat_op;
|
||||
op.tier_evict();
|
||||
librados::AioCompletion *completion = cluster.aio_create_completion();
|
||||
ASSERT_EQ(0, cache_ioctx.aio_operate(
|
||||
"foo", completion, &op,
|
||||
librados::OPERATION_IGNORE_OVERLAY, NULL));
|
||||
completion->wait_for_complete();
|
||||
ASSERT_EQ(0, completion->get_return_value());
|
||||
}
|
||||
|
||||
uint32_t hash;
|
||||
ASSERT_EQ(0, cache_ioctx.get_object_pg_hash_position2("foo", &hash));
|
||||
|
||||
// scrub
|
||||
{
|
||||
for (int tries = 0; tries < 5; ++tries) {
|
||||
bufferlist inbl;
|
||||
ostringstream ss;
|
||||
ss << "{\"prefix\": \"pg deep-scrub\", \"pgid\": \""
|
||||
<< cache_ioctx.get_id() << "."
|
||||
<< std::hex << hash
|
||||
<< "\"}";
|
||||
int r = cluster.mon_command(ss.str(), inbl, NULL, NULL);
|
||||
if (r == -ENOENT ||
|
||||
r == -EAGAIN) {
|
||||
sleep(5);
|
||||
continue;
|
||||
}
|
||||
ASSERT_EQ(0, r);
|
||||
break;
|
||||
}
|
||||
cout << "waiting for scrubs..." << std::endl;
|
||||
sleep(20);
|
||||
cout << "done waiting" << std::endl;
|
||||
}
|
||||
|
||||
{
|
||||
bufferlist bl;
|
||||
ASSERT_EQ(1, cache_ioctx.read("foo", bl, 1, 0));
|
||||
ASSERT_EQ('t', bl[0]);
|
||||
}
|
||||
}
|
||||
|
||||
#include <common/CDC.h>
|
||||
TEST_F(LibRadosTwoPoolsPP, DedupFlushRead) {
|
||||
// skip test if not yet octopus
|
||||
|
Loading…
Reference in New Issue
Block a user