From a39fb4ffa09c999a56ebb3beffdc17f20ba1e09f Mon Sep 17 00:00:00 2001 From: Jos Collin Date: Fri, 13 Jul 2018 19:08:37 +0530 Subject: [PATCH] cephfs: InodeStat versioning * Use the new feature bit CEPHFS_FEATURE_REPLY_ENCODING for encoding. * encode/decode in the new format. * The old format is maintained for backward compatibility. Fixes: http://tracker.ceph.com/issues/24444 Signed-off-by: Jos Collin --- src/client/Client.cc | 17 +++- src/client/MetaSession.h | 1 + src/mds/CInode.cc | 139 ++++++++++++++++++++------------ src/messages/MClientReply.h | 155 +++++++++++++++++++++++------------- 4 files changed, 205 insertions(+), 107 deletions(-) diff --git a/src/client/Client.cc b/src/client/Client.cc index 111d6c05b8b45..14880f8cc2130 100644 --- a/src/client/Client.cc +++ b/src/client/Client.cc @@ -1068,7 +1068,13 @@ void Client::insert_readdir_results(MetaRequest *request, MetaSession *session, MClientReply *reply = request->reply; ConnectionRef con = request->reply->get_connection(); - uint64_t features = con->get_features(); + uint64_t features; + if(session->mds_features.test(CEPHFS_FEATURE_REPLY_ENCODING)) { + features = (uint64_t)-1; + } + else { + features = con->get_features(); + } dir_result_t *dirp = request->dirp; assert(dirp); @@ -1266,7 +1272,13 @@ Inode* Client::insert_trace(MetaRequest *request, MetaSession *session) } ConnectionRef con = request->reply->get_connection(); - uint64_t features = con->get_features(); + uint64_t features; + if (session->mds_features.test(CEPHFS_FEATURE_REPLY_ENCODING)) { + features = (uint64_t)-1; + } + else { + features = con->get_features(); + } ldout(cct, 10) << " features 0x" << hex << features << dec << dendl; // snap trace @@ -2072,6 +2084,7 @@ void Client::handle_client_session(MClientSession *m) _closed_mds_session(session); break; } + session->mds_features = std::move(m->supported_features); renew_caps(session); session->state = MetaSession::STATE_OPEN; diff --git a/src/client/MetaSession.h b/src/client/MetaSession.h index 08159ac08b571..0879abdbe9f1a 100644 --- a/src/client/MetaSession.h +++ b/src/client/MetaSession.h @@ -24,6 +24,7 @@ struct MetaSession { utime_t cap_ttl, last_cap_renew_request; uint64_t cap_renew_seq; entity_addrvec_t addrs; + feature_bitset_t mds_features; enum { STATE_NEW, // Unused diff --git a/src/mds/CInode.cc b/src/mds/CInode.cc index e17241b23e2fd..ad87cec5a369a 100644 --- a/src/mds/CInode.cc +++ b/src/mds/CInode.cc @@ -47,6 +47,7 @@ #include "mds/MDSContinuation.h" #include "mds/InoTable.h" +#include "cephfs_features.h" #define dout_context g_ceph_context #define dout_subsys ceph_subsys_mds @@ -3317,7 +3318,6 @@ int CInode::encode_inodestat(bufferlist& bl, Session *session, { client_t client = session->get_client(); assert(snapid); - assert(session->connection); bool valid = true; @@ -3577,62 +3577,103 @@ int CInode::encode_inodestat(bufferlist& bl, Session *session, /* * note: encoding matches MClientReply::InodeStat */ - encode(oi->ino, bl); - encode(snapid, bl); - encode(oi->rdev, bl); - encode(version, bl); - - encode(xattr_version, bl); - - encode(ecap, bl); - { - ceph_file_layout legacy_layout; - layout.to_legacy(&legacy_layout); - encode(legacy_layout, bl); - } - encode(any_i->ctime, bl); - encode(file_i->mtime, bl); - encode(file_i->atime, bl); - encode(file_i->time_warp_seq, bl); - encode(file_i->size, bl); - encode(max_size, bl); - encode(file_i->truncate_size, bl); - encode(file_i->truncate_seq, bl); - - encode(auth_i->mode, bl); - encode((uint32_t)auth_i->uid, bl); - encode((uint32_t)auth_i->gid, bl); - - encode(link_i->nlink, bl); - - encode(file_i->dirstat.nfiles, bl); - encode(file_i->dirstat.nsubdirs, bl); - encode(file_i->rstat.rbytes, bl); - encode(file_i->rstat.rfiles, bl); - encode(file_i->rstat.rsubdirs, bl); - encode(file_i->rstat.rctime, bl); - - dirfragtree.encode(bl); - - encode(symlink, bl); - if (session->connection->has_feature(CEPH_FEATURE_DIRLAYOUTHASH)) { + if (session->info.has_feature(CEPHFS_FEATURE_REPLY_ENCODING)) { + ENCODE_START(1, 1, bl); + encode(oi->ino, bl); + encode(snapid, bl); + encode(oi->rdev, bl); + encode(version, bl); + encode(xattr_version, bl); + encode(ecap, bl); + { + ceph_file_layout legacy_layout; + layout.to_legacy(&legacy_layout); + encode(legacy_layout, bl); + } + encode(any_i->ctime, bl); + encode(file_i->mtime, bl); + encode(file_i->atime, bl); + encode(file_i->time_warp_seq, bl); + encode(file_i->size, bl); + encode(max_size, bl); + encode(file_i->truncate_size, bl); + encode(file_i->truncate_seq, bl); + encode(auth_i->mode, bl); + encode((uint32_t)auth_i->uid, bl); + encode((uint32_t)auth_i->gid, bl); + encode(link_i->nlink, bl); + encode(file_i->dirstat.nfiles, bl); + encode(file_i->dirstat.nsubdirs, bl); + encode(file_i->rstat.rbytes, bl); + encode(file_i->rstat.rfiles, bl); + encode(file_i->rstat.rsubdirs, bl); + encode(file_i->rstat.rctime, bl); + dirfragtree.encode(bl); + encode(symlink, bl); encode(file_i->dir_layout, bl); - } - encode(xbl, bl); - if (session->connection->has_feature(CEPH_FEATURE_MDS_INLINE_DATA)) { + encode(xbl, bl); encode(inline_version, bl); encode(inline_data, bl); - } - if (session->connection->has_feature(CEPH_FEATURE_MDS_QUOTA)) { mempool_inode *policy_i = ppolicy ? pi : oi; encode(policy_i->quota, bl); - } - if (session->connection->has_feature(CEPH_FEATURE_FS_FILE_LAYOUT_V2)) { encode(layout.pool_ns, bl); - } - if (session->connection->has_feature(CEPH_FEATURE_FS_BTIME)) { encode(any_i->btime, bl); encode(any_i->change_attr, bl); + ENCODE_FINISH(bl); + } + else { + assert(session->connection); + + encode(oi->ino, bl); + encode(snapid, bl); + encode(oi->rdev, bl); + encode(version, bl); + encode(xattr_version, bl); + encode(ecap, bl); + { + ceph_file_layout legacy_layout; + layout.to_legacy(&legacy_layout); + encode(legacy_layout, bl); + } + encode(any_i->ctime, bl); + encode(file_i->mtime, bl); + encode(file_i->atime, bl); + encode(file_i->time_warp_seq, bl); + encode(file_i->size, bl); + encode(max_size, bl); + encode(file_i->truncate_size, bl); + encode(file_i->truncate_seq, bl); + encode(auth_i->mode, bl); + encode((uint32_t)auth_i->uid, bl); + encode((uint32_t)auth_i->gid, bl); + encode(link_i->nlink, bl); + encode(file_i->dirstat.nfiles, bl); + encode(file_i->dirstat.nsubdirs, bl); + encode(file_i->rstat.rbytes, bl); + encode(file_i->rstat.rfiles, bl); + encode(file_i->rstat.rsubdirs, bl); + encode(file_i->rstat.rctime, bl); + dirfragtree.encode(bl); + encode(symlink, bl); + if (session->connection->has_feature(CEPH_FEATURE_DIRLAYOUTHASH)) { + encode(file_i->dir_layout, bl); + } + encode(xbl, bl); + if (session->connection->has_feature(CEPH_FEATURE_MDS_INLINE_DATA)) { + encode(inline_version, bl); + encode(inline_data, bl); + } + if (session->connection->has_feature(CEPH_FEATURE_MDS_QUOTA)) { + mempool_inode *policy_i = ppolicy ? pi : oi; + encode(policy_i->quota, bl); + } + if (session->connection->has_feature(CEPH_FEATURE_FS_FILE_LAYOUT_V2)) { + encode(layout.pool_ns, bl); + } + if (session->connection->has_feature(CEPH_FEATURE_FS_BTIME)) { + encode(any_i->btime, bl); + encode(any_i->change_attr, bl); + } } return valid; diff --git a/src/messages/MClientReply.h b/src/messages/MClientReply.h index 558e43e54482c..8706aec172039 100644 --- a/src/messages/MClientReply.h +++ b/src/messages/MClientReply.h @@ -130,73 +130,116 @@ struct InodeStat { public: InodeStat() {} - InodeStat(bufferlist::const_iterator& p, uint64_t features) { + InodeStat(bufferlist::const_iterator& p, const uint64_t features) { decode(p, features); } - void decode(bufferlist::const_iterator &p, uint64_t features) { + void decode(bufferlist::const_iterator &p, const uint64_t features) { using ceph::decode; - decode(vino.ino, p); - decode(vino.snapid, p); - decode(rdev, p); - decode(version, p); - decode(xattr_version, p); - decode(cap, p); - { - ceph_file_layout legacy_layout; - decode(legacy_layout, p); - layout.from_legacy(legacy_layout); - } - decode(ctime, p); - decode(mtime, p); - decode(atime, p); - decode(time_warp_seq, p); - decode(size, p); - decode(max_size, p); - decode(truncate_size, p); - decode(truncate_seq, p); - decode(mode, p); - decode(uid, p); - decode(gid, p); - decode(nlink, p); - decode(dirstat.nfiles, p); - decode(dirstat.nsubdirs, p); - decode(rstat.rbytes, p); - decode(rstat.rfiles, p); - decode(rstat.rsubdirs, p); - decode(rstat.rctime, p); - - decode(dirfragtree, p); - - decode(symlink, p); - - if (features & CEPH_FEATURE_DIRLAYOUTHASH) + if (features == (uint64_t)-1) { + DECODE_START(1, p); + decode(vino.ino, p); + decode(vino.snapid, p); + decode(rdev, p); + decode(version, p); + decode(xattr_version, p); + decode(cap, p); + { + ceph_file_layout legacy_layout; + decode(legacy_layout, p); + layout.from_legacy(legacy_layout); + } + decode(ctime, p); + decode(mtime, p); + decode(atime, p); + decode(time_warp_seq, p); + decode(size, p); + decode(max_size, p); + decode(truncate_size, p); + decode(truncate_seq, p); + decode(mode, p); + decode(uid, p); + decode(gid, p); + decode(nlink, p); + decode(dirstat.nfiles, p); + decode(dirstat.nsubdirs, p); + decode(rstat.rbytes, p); + decode(rstat.rfiles, p); + decode(rstat.rsubdirs, p); + decode(rstat.rctime, p); + decode(dirfragtree, p); + decode(symlink, p); decode(dir_layout, p); - else - memset(&dir_layout, 0, sizeof(dir_layout)); - - decode(xattrbl, p); - - if (features & CEPH_FEATURE_MDS_INLINE_DATA) { + decode(xattrbl, p); decode(inline_version, p); decode(inline_data, p); - } else { - inline_version = CEPH_INLINE_NONE; - } - - if (features & CEPH_FEATURE_MDS_QUOTA) decode(quota, p); - else - quota = quota_info_t{}; - - if ((features & CEPH_FEATURE_FS_FILE_LAYOUT_V2)) decode(layout.pool_ns, p); - if ((features & CEPH_FEATURE_FS_BTIME)) { decode(btime, p); decode(change_attr, p); - } else { - btime = utime_t(); - change_attr = 0; + DECODE_FINISH(p); + } + else { + decode(vino.ino, p); + decode(vino.snapid, p); + decode(rdev, p); + decode(version, p); + decode(xattr_version, p); + decode(cap, p); + { + ceph_file_layout legacy_layout; + decode(legacy_layout, p); + layout.from_legacy(legacy_layout); + } + decode(ctime, p); + decode(mtime, p); + decode(atime, p); + decode(time_warp_seq, p); + decode(size, p); + decode(max_size, p); + decode(truncate_size, p); + decode(truncate_seq, p); + decode(mode, p); + decode(uid, p); + decode(gid, p); + decode(nlink, p); + decode(dirstat.nfiles, p); + decode(dirstat.nsubdirs, p); + decode(rstat.rbytes, p); + decode(rstat.rfiles, p); + decode(rstat.rsubdirs, p); + decode(rstat.rctime, p); + decode(dirfragtree, p); + decode(symlink, p); + if (features & CEPH_FEATURE_DIRLAYOUTHASH) + decode(dir_layout, p); + else + memset(&dir_layout, 0, sizeof(dir_layout)); + + decode(xattrbl, p); + + if (features & CEPH_FEATURE_MDS_INLINE_DATA) { + decode(inline_version, p); + decode(inline_data, p); + } else { + inline_version = CEPH_INLINE_NONE; + } + + if (features & CEPH_FEATURE_MDS_QUOTA) + decode(quota, p); + else + quota = quota_info_t{}; + + if ((features & CEPH_FEATURE_FS_FILE_LAYOUT_V2)) + decode(layout.pool_ns, p); + + if ((features & CEPH_FEATURE_FS_BTIME)) { + decode(btime, p); + decode(change_attr, p); + } else { + btime = utime_t(); + change_attr = 0; + } } } -- 2.39.5