From ed91d23ccaaac4e72a4c28a58e77485395949f04 Mon Sep 17 00:00:00 2001 From: Matt Benjamin Date: Tue, 18 Apr 2017 09:19:13 -0400 Subject: [PATCH] rgw_file: pre-compute unix attrs in write_finish() New serialized Unix attrs need to reflect the change being made, and should be reverted if the change fails. Fixes: http://tracker.ceph.com/issues/19653 Signed-off-by: Matt Benjamin --- src/rgw/rgw_file.cc | 23 +++++++++++++++++------ src/rgw/rgw_file.h | 1 + 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/src/rgw/rgw_file.cc b/src/rgw/rgw_file.cc index 15f20ee1eab..be3d356ec41 100644 --- a/src/rgw/rgw_file.cc +++ b/src/rgw/rgw_file.cc @@ -1280,6 +1280,11 @@ namespace rgw { unsigned char m[CEPH_CRYPTO_MD5_DIGESTSIZE]; struct req_state* s = get_state(); + size_t osize = rgw_fh->get_size(); + struct timespec octime = rgw_fh->get_ctime(); + struct timespec omtime = rgw_fh->get_mtime(); + real_time appx_t = real_clock::now(); + s->obj_size = ofs; // XXX check ofs perfcounter->inc(l_rgw_put_b, s->obj_size); @@ -1300,7 +1305,12 @@ namespace rgw { policy.encode(aclbl); emplace_attr(RGW_ATTR_ACL, std::move(aclbl)); + /* unix attrs */ + rgw_fh->set_mtime(real_clock::to_timespec(appx_t)); + rgw_fh->set_ctime(real_clock::to_timespec(appx_t)); + rgw_fh->set_size(bytes_written); rgw_fh->encode_attrs(ux_key, ux_attrs); + emplace_attr(RGW_ATTR_UNIX_KEY1, std::move(ux_key)); emplace_attr(RGW_ATTR_UNIX1, std::move(ux_attrs)); @@ -1324,12 +1334,13 @@ namespace rgw { } op_ret = processor->complete(s->obj_size, etag, &mtime, real_time(), attrs, - (delete_at ? *delete_at : real_time()), if_match, if_nomatch); - if (! op_ret) { - /* update stats */ - rgw_fh->set_mtime(real_clock::to_timespec(mtime)); - rgw_fh->set_ctime(real_clock::to_timespec(mtime)); - rgw_fh->set_size(bytes_written); + (delete_at ? *delete_at : real_time()), + if_match, if_nomatch); + if (op_ret != 0) { + /* revert attr updates */ + rgw_fh->set_mtime(omtime); + rgw_fh->set_ctime(octime); + rgw_fh->set_size(osize); } done: diff --git a/src/rgw/rgw_file.h b/src/rgw/rgw_file.h index df53d4246aa..5d964f9c2aa 100644 --- a/src/rgw/rgw_file.h +++ b/src/rgw/rgw_file.h @@ -340,6 +340,7 @@ namespace rgw { uint32_t get_owner_uid() const { return state.owner_uid; } uint32_t get_owner_gid() const { return state.owner_gid; } + struct timespec get_ctime() const { return state.ctime; } struct timespec get_mtime() const { return state.mtime; } void create_stat(struct stat* st, uint32_t mask) {