From: Jeff Layton <jlayton@kernel.org>
Date: Thu, 6 Jun 2019 08:06:40 -0400
Subject: ceph: handle change_attr in cap messages
Git-commit: 176c77c9c9b1f843332496a28f4545eb96d5dab9
Patch-mainline: v5.3-rc1
References: bsc#1148133 bsc#1136682
Signed-off-by: Jeff Layton <jlayton@kernel.org>
Reviewed-by: "Yan, Zheng" <zyan@redhat.com>
Signed-off-by: Ilya Dryomov <idryomov@gmail.com>
Acked-by: Luis Henriques <lhenriques@suse.com>
[luis: s/timespec64/timespec]
---
fs/ceph/caps.c | 19 ++++++++++---------
fs/ceph/snap.c | 2 ++
fs/ceph/super.h | 1 +
3 files changed, 13 insertions(+), 9 deletions(-)
--- a/fs/ceph/caps.c
+++ b/fs/ceph/caps.c
@@ -7,6 +7,7 @@
#include <linux/vmalloc.h>
#include <linux/wait.h>
#include <linux/writeback.h>
+#include <linux/iversion.h>
#include "super.h"
#include "mds_client.h"
@@ -1114,6 +1115,7 @@ struct cap_msg_args {
u64 ino, cid, follows;
u64 flush_tid, oldest_flush_tid, size, max_size;
u64 xattr_version;
+ u64 change_attr;
struct ceph_buffer *xattr_buf;
struct timespec atime, mtime, ctime, btime;
int op, caps, wanted, dirty;
@@ -1220,15 +1222,10 @@ static int send_cap_msg(struct cap_msg_a
/* pool namespace (version 8) (mds always ignores this) */
ceph_encode_32(&p, 0);
- /*
- * btime and change_attr (version 9)
- *
- * We just zero these out for now, as the MDS ignores them unless
- * the requisite feature flags are set (which we don't do yet).
- */
+ /* btime and change_attr (version 9) */
ceph_encode_timespec(p, &arg->btime);
p += sizeof(struct ceph_timespec);
- ceph_encode_64(&p, 0);
+ ceph_encode_64(&p, arg->change_attr);
/* Advisory flags (version 10) */
ceph_encode_32(&p, arg->flags);
@@ -1356,6 +1353,7 @@ static int __send_cap(struct ceph_mds_cl
arg.atime = inode->i_atime;
arg.ctime = inode->i_ctime;
arg.btime = ci->i_btime;
+ arg.change_attr = inode_peek_iversion_raw(inode);
arg.op = op;
arg.caps = cap->implemented;
@@ -1416,6 +1414,7 @@ static inline int __send_flush_snap(stru
arg.mtime = capsnap->mtime;
arg.ctime = capsnap->ctime;
arg.btime = capsnap->btime;
+ arg.change_attr = capsnap->change_attr;
arg.op = CEPH_CAP_OP_FLUSHSNAP;
arg.caps = capsnap->issued;
@@ -3030,6 +3029,7 @@ struct cap_extra_info {
bool dirstat_valid;
u64 nfiles;
u64 nsubdirs;
+ u64 change_attr;
/* currently issued */
int issued;
struct timespec btime;
@@ -3114,6 +3114,8 @@ static void handle_cap_grant(struct inod
__check_cap_issue(ci, cap, newcaps);
+ inode_set_max_iversion_raw(inode, extra_info->change_attr);
+
if ((newcaps & CEPH_CAP_AUTH_SHARED) &&
(extra_info->issued & CEPH_CAP_AUTH_EXCL) == 0) {
inode->i_mode = le32_to_cpu(grant->mode);
@@ -3842,14 +3844,13 @@ void ceph_handle_caps(struct ceph_mds_se
if (msg_version >= 9) {
struct ceph_timespec *btime;
- u64 change_attr;
if (p + sizeof(*btime) > end)
goto bad;
btime = p;
ceph_decode_timespec(&extra_info.btime, btime);
p += sizeof(*btime);
- ceph_decode_64_safe(&p, end, change_attr, bad);
+ ceph_decode_64_safe(&p, end, extra_info.change_attr, bad);
}
if (msg_version >= 11) {
--- a/fs/ceph/snap.c
+++ b/fs/ceph/snap.c
@@ -2,6 +2,7 @@
#include <linux/sort.h>
#include <linux/slab.h>
+#include <linux/iversion.h>
#include "super.h"
#include "mds_client.h"
#include <linux/ceph/decode.h>
@@ -603,6 +604,7 @@ int __ceph_finish_cap_snap(struct ceph_i
capsnap->atime = inode->i_atime;
capsnap->ctime = inode->i_ctime;
capsnap->btime = ci->i_btime;
+ capsnap->change_attr = inode_peek_iversion_raw(inode);
capsnap->time_warp_seq = ci->i_time_warp_seq;
capsnap->truncate_size = ci->i_truncate_size;
capsnap->truncate_seq = ci->i_truncate_seq;
--- a/fs/ceph/super.h
+++ b/fs/ceph/super.h
@@ -193,6 +193,7 @@ struct ceph_cap_snap {
u64 xattr_version;
u64 size;
+ u64 change_attr;
struct timespec mtime, atime, ctime, btime;
u64 time_warp_seq;
u64 truncate_size;