From cdc9c70c765b1b45ae733283a595014fe3cc4a4c Mon Sep 17 00:00:00 2001 From: Kautilya Tripathi Date: Tue, 17 Feb 2026 16:28:31 +0530 Subject: [PATCH] crimson/osd: fix cmp_xattr handling for RGW delete Match classic ENODATA behavior by only treating missing xattr as empty for EQ+STRING with an empty expected value, so RGW null-version deletes succeed. Signed-off-by: Kautilya Tripathi --- src/crimson/osd/pg_backend.cc | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/src/crimson/osd/pg_backend.cc b/src/crimson/osd/pg_backend.cc index f3c9c1cc9f3..6f7a670fced 100644 --- a/src/crimson/osd/pg_backend.cc +++ b/src/crimson/osd/pg_backend.cc @@ -1314,6 +1314,22 @@ PGBackend::cmp_xattr_ierrorator::future<> PGBackend::cmp_xattr( ->cmp_xattr_errorator::future<> { delta_stats.num_rd++; delta_stats.num_rd_kb += shift_round_up(osd_op.op.xattr.value_len, 10); + + // RGW delete uses cmpxattr with an empty expected value and expects a + // missing xattr to compare equal (classic OSD behavior). + if (osd_op.op.xattr.cmp_op == CEPH_OSD_CMPXATTR_OP_EQ) { + auto bp = osd_op.indata.cbegin(); + bp += osd_op.op.xattr.name_len; + if (osd_op.op.xattr.cmp_mode == CEPH_OSD_CMPXATTR_MODE_STRING) { + string lhs; + bp.copy(osd_op.op.xattr.value_len, lhs); + if (lhs.empty()) { + osd_op.rval = 1; + return cmp_xattr_errorator::now(); + } + } + } + logger().debug("cmpxattr: xattr does not exist, comparison failed"); return crimson::ct_error::ecanceled::make(); }), cmp_xattr_errorator::pass_further{} -- 2.47.3