diff options
author | Sage Weil <sage@inktank.com> | 2013-07-10 16:51:19 -0700 |
---|---|---|
committer | Sage Weil <sage@inktank.com> | 2013-09-04 17:53:30 -0700 |
commit | 82cdb75f541eace3d3719da7ada723c4e47ed10b (patch) | |
tree | 6664cfea29269559966f61d8ee4399fd96fc9e40 | |
parent | a2c8067898010a2ec5767c882b53323670ff2293 (diff) | |
download | ceph-82cdb75f541eace3d3719da7ada723c4e47ed10b.tar.gz |
mds: include requested caps (namely, xattrs) on getattr reply
For xattrs, we only include them in the reply if we are issuing caps on
them. However, in the getattr case, we need to include the snapshot of the
current state.
The original problem is reproduced by LibCephFS.Xattrs_ll (a simple set
then get).
Signed-off-by: Sage Weil <sage@inktank.com>
-rw-r--r-- | src/mds/CInode.cc | 8 | ||||
-rw-r--r-- | src/mds/CInode.h | 3 | ||||
-rw-r--r-- | src/mds/Mutation.h | 4 | ||||
-rw-r--r-- | src/mds/Server.cc | 6 |
4 files changed, 16 insertions, 5 deletions
diff --git a/src/mds/CInode.cc b/src/mds/CInode.cc index dd483263b6d..92b09678e4b 100644 --- a/src/mds/CInode.cc +++ b/src/mds/CInode.cc @@ -2722,8 +2722,10 @@ void CInode::replicate_relax_locks() // ============================================= int CInode::encode_inodestat(bufferlist& bl, Session *session, - SnapRealm *dir_realm, - snapid_t snapid, unsigned max_bytes) + SnapRealm *dir_realm, + snapid_t snapid, + unsigned max_bytes, + int getattr_caps) { int client = session->info.inst.name.num(); assert(snapid); @@ -2933,7 +2935,7 @@ int CInode::encode_inodestat(bufferlist& bl, Session *session, // include those xattrs? if (xbl.length() && cap) { - if (cap->pending() & CEPH_CAP_XATTR_SHARED) { + if ((cap->pending() | getattr_caps) & CEPH_CAP_XATTR_SHARED) { dout(10) << "including xattrs version " << i->xattr_version << dendl; cap->client_xattr_version = i->xattr_version; } else { diff --git a/src/mds/CInode.h b/src/mds/CInode.h index 8e760220c14..aa4b2056682 100644 --- a/src/mds/CInode.h +++ b/src/mds/CInode.h @@ -597,7 +597,8 @@ private: // for giving to clients int encode_inodestat(bufferlist& bl, Session *session, SnapRealm *realm, - snapid_t snapid=CEPH_NOSNAP, unsigned max_bytes=0); + snapid_t snapid=CEPH_NOSNAP, unsigned max_bytes=0, + int getattr_wants=0); void encode_cap_message(MClientCaps *m, Capability *cap); diff --git a/src/mds/Mutation.h b/src/mds/Mutation.h index b50a03cefa4..94e29fce434 100644 --- a/src/mds/Mutation.h +++ b/src/mds/Mutation.h @@ -178,6 +178,7 @@ struct MDRequest : public Mutation { int snap_caps; bool did_early_reply; bool o_trunc; ///< request is an O_TRUNC mutation + int getattr_caps; ///< caps requested by getattr bufferlist reply_extra_bl; @@ -250,6 +251,7 @@ struct MDRequest : public Mutation { client_request(0), straydn(NULL), snapid(CEPH_NOSNAP), tracei(0), tracedn(0), alloc_ino(0), used_prealloc_ino(0), snap_caps(0), did_early_reply(false), o_trunc(false), + getattr_caps(0), slave_request(0), internal_op(-1), retry(0), @@ -264,6 +266,7 @@ struct MDRequest : public Mutation { client_request(req), straydn(NULL), snapid(CEPH_NOSNAP), tracei(0), tracedn(0), alloc_ino(0), used_prealloc_ino(0), snap_caps(0), did_early_reply(false), o_trunc(false), + getattr_caps(0), slave_request(0), internal_op(-1), retry(0), @@ -278,6 +281,7 @@ struct MDRequest : public Mutation { client_request(0), straydn(NULL), snapid(CEPH_NOSNAP), tracei(0), tracedn(0), alloc_ino(0), used_prealloc_ino(0), snap_caps(0), did_early_reply(false), o_trunc(false), + getattr_caps(0), slave_request(0), internal_op(-1), retry(0), diff --git a/src/mds/Server.cc b/src/mds/Server.cc index 84d786116f4..7cd2be73a7c 100644 --- a/src/mds/Server.cc +++ b/src/mds/Server.cc @@ -1034,7 +1034,7 @@ void Server::set_trace_dist(Session *session, MClientReply *reply, // inode if (in) { - in->encode_inodestat(bl, session, NULL, snapid); + in->encode_inodestat(bl, session, NULL, snapid, 0, mdr->getattr_caps); dout(20) << "set_trace_dist added in " << *in << dendl; reply->head.is_target = 1; } else @@ -2281,6 +2281,10 @@ void Server::handle_client_getattr(MDRequest *mdr, bool is_lookup) if (!mds->locker->acquire_locks(mdr, rdlocks, wrlocks, xlocks)) return; + // note which caps are requested, so we return at least a snapshot + // value for them. (currently this only matters for xattrs) + mdr->getattr_caps = mask; + mds->balancer->hit_inode(ceph_clock_now(g_ceph_context), ref, META_POP_IRD, mdr->client_request->get_source().num()); |