mirror of
https://github.com/ceph/ceph
synced 2025-03-11 02:39:05 +00:00
pass dir auth etc info to client separately from inode
git-svn-id: https://ceph.svn.sf.net/svnroot/ceph@1893 29311d96-e01e-0410-9327-a35deaab8ce9
This commit is contained in:
parent
ad05ba39e3
commit
7386f0e9c7
@ -1558,6 +1558,8 @@ void Server::handle_client_readdir(MDRequest *mdr)
|
||||
// build dir contents
|
||||
bufferlist dirbl;
|
||||
|
||||
DirStat::_encode(dirbl, dir, mds->get_nodeid());
|
||||
|
||||
int numfiles = 0;
|
||||
for (CDir::map_t::iterator it = dir->begin();
|
||||
it != dir->end();
|
||||
@ -1596,7 +1598,7 @@ void Server::handle_client_readdir(MDRequest *mdr)
|
||||
|
||||
// add this dentry + inodeinfo
|
||||
::_encode(it->first, dirbl);
|
||||
InodeStat::_encode(dirbl, in, mds->get_nodeid());
|
||||
InodeStat::_encode(dirbl, in);
|
||||
|
||||
// touch it
|
||||
mdcache->lru.lru_touch(dn);
|
||||
|
@ -50,18 +50,49 @@ class CInode;
|
||||
*
|
||||
*/
|
||||
|
||||
class InodeStat {
|
||||
public:
|
||||
struct DirStat {
|
||||
// mds distribution hints
|
||||
frag_t frag;
|
||||
int auth;
|
||||
set<int> dist;
|
||||
bool is_rep;
|
||||
|
||||
DirStat() {}
|
||||
DirStat(bufferlist::iterator& p) {
|
||||
_decode(p);
|
||||
}
|
||||
|
||||
void _decode(bufferlist::iterator& p) {
|
||||
::_decode_simple(frag, p);
|
||||
::_decode_simple(auth, p);
|
||||
::_decode_simple(dist, p);
|
||||
::_decode_simple(is_rep, p);
|
||||
}
|
||||
|
||||
static void _encode(bufferlist& bl, CDir *dir, int whoami) {
|
||||
frag_t frag = dir->get_frag();
|
||||
int auth;
|
||||
set<int> dist;
|
||||
bool is_rep;
|
||||
|
||||
auth = dir->get_dir_auth().first;
|
||||
if (dir->is_auth())
|
||||
dir->get_dist_spec(dist, whoami);
|
||||
is_rep = dir->is_rep();
|
||||
|
||||
::_encode_simple(frag, bl);
|
||||
::_encode_simple(auth, bl);
|
||||
::_encode_simple(dist, bl);
|
||||
::_encode_simple(is_rep, bl);
|
||||
}
|
||||
};
|
||||
|
||||
struct InodeStat {
|
||||
inode_t inode;
|
||||
string symlink; // symlink content (if symlink)
|
||||
fragtree_t dirfragtree;
|
||||
uint32_t mask;
|
||||
|
||||
// mds distribution hints
|
||||
map<frag_t,int> dirfrag_auth;
|
||||
map<frag_t,set<int> > dirfrag_dist;
|
||||
set<frag_t> dirfrag_rep;
|
||||
|
||||
public:
|
||||
InodeStat() {}
|
||||
InodeStat(bufferlist::iterator& p) {
|
||||
@ -71,14 +102,11 @@ class InodeStat {
|
||||
void _decode(bufferlist::iterator &p) {
|
||||
::_decode_simple(mask, p);
|
||||
::_decode_simple(inode, p);
|
||||
::_decode_simple(dirfrag_auth, p);
|
||||
::_decode_simple(dirfrag_dist, p);
|
||||
::_decode_simple(dirfrag_rep, p);
|
||||
::_decode_simple(symlink, p);
|
||||
dirfragtree._decode(p);
|
||||
}
|
||||
|
||||
static void _encode(bufferlist &bl, CInode *in, int whoami) {
|
||||
static void _encode(bufferlist &bl, CInode *in) {
|
||||
int mask = STAT_MASK_INO|STAT_MASK_TYPE|STAT_MASK_BASE;
|
||||
|
||||
// mask
|
||||
@ -88,29 +116,6 @@ class InodeStat {
|
||||
|
||||
::_encode_simple(mask, bl);
|
||||
::_encode_simple(in->inode, bl);
|
||||
|
||||
// dirfrag info
|
||||
map<frag_t,int> dirfrag_auth;
|
||||
map<frag_t,set<int> > dirfrag_dist;
|
||||
set<frag_t> dirfrag_rep;
|
||||
|
||||
list<CDir*> ls;
|
||||
in->get_dirfrags(ls);
|
||||
for (list<CDir*>::iterator p = ls.begin();
|
||||
p != ls.end();
|
||||
++p) {
|
||||
CDir *dir = *p;
|
||||
dirfrag_auth[dir->dirfrag().frag] = dir->get_dir_auth().first;
|
||||
if (dir->is_auth())
|
||||
dir->get_dist_spec(dirfrag_dist[dir->dirfrag().frag], whoami);
|
||||
if (dir->is_rep())
|
||||
dirfrag_rep.insert(dir->dirfrag().frag);
|
||||
}
|
||||
|
||||
::_encode_simple(dirfrag_auth, bl);
|
||||
::_encode_simple(dirfrag_dist, bl);
|
||||
::_encode_simple(dirfrag_rep, bl);
|
||||
|
||||
::_encode_simple(in->symlink, bl);
|
||||
in->dirfragtree._encode(bl);
|
||||
}
|
||||
@ -132,9 +137,11 @@ class MClientReply : public Message {
|
||||
string path;
|
||||
|
||||
list<InodeStat*> trace_in;
|
||||
list<DirStat*> trace_dir;
|
||||
list<string> trace_dn;
|
||||
bufferlist trace_bl;
|
||||
|
||||
DirStat *dir_dir;
|
||||
list<InodeStat*> dir_in;
|
||||
list<string> dir_dn;
|
||||
bufferlist dir_bl;
|
||||
@ -158,9 +165,9 @@ class MClientReply : public Message {
|
||||
void set_file_caps_seq(long s) { st.file_caps_seq = s; }
|
||||
void set_file_data_version(uint64_t v) { st.file_data_version = v; }
|
||||
|
||||
MClientReply() {};
|
||||
MClientReply() : dir_dir(0) {};
|
||||
MClientReply(MClientRequest *req, int result = 0) :
|
||||
Message(MSG_CLIENT_REPLY) {
|
||||
Message(MSG_CLIENT_REPLY), dir_dir(0) {
|
||||
memset(&st, 0, sizeof(st));
|
||||
this->st.tid = req->get_tid();
|
||||
this->st.op = req->get_op();
|
||||
@ -208,6 +215,7 @@ class MClientReply : public Message {
|
||||
}
|
||||
void _decode_dir() {
|
||||
bufferlist::iterator p = dir_bl.begin();
|
||||
dir_dir = new DirStat(p);
|
||||
while (!p.end()) {
|
||||
string dn;
|
||||
::_decode_simple(dn, p);
|
||||
@ -220,30 +228,40 @@ class MClientReply : public Message {
|
||||
if (dir_in.empty() && dir_bl.length()) _decode_dir();
|
||||
return dir_in;
|
||||
}
|
||||
const list<string>& get_dir_dn() {
|
||||
const list<string>& get_dir_dn() {
|
||||
if (dir_dn.empty() && dir_bl.length()) _decode_dir();
|
||||
return dir_dn;
|
||||
}
|
||||
const DirStat* get_dir_dir() {
|
||||
return dir_dir;
|
||||
}
|
||||
|
||||
|
||||
// trace
|
||||
void set_trace_dist(CInode *in, int whoami) {
|
||||
// inode, dentry, ..., inode
|
||||
// inode, dentry, dir, ..., inode
|
||||
while (in) {
|
||||
InodeStat::_encode(trace_bl, in, whoami);
|
||||
if (in->get_parent_dn())
|
||||
::_encode_simple(in->get_parent_dn()->get_name(), trace_bl);
|
||||
in = in->get_parent_inode();
|
||||
InodeStat::_encode(trace_bl, in);
|
||||
CDentry *dn = in->get_parent_dn();
|
||||
if (!dn) break;
|
||||
::_encode_simple(in->get_parent_dn()->get_name(), trace_bl);
|
||||
DirStat::_encode(trace_bl, dn->get_dir(), whoami);
|
||||
in = dn->get_dir()->get_inode();
|
||||
}
|
||||
}
|
||||
void _decode_trace() {
|
||||
bufferlist::iterator p = trace_bl.begin();
|
||||
while (!p.end()) {
|
||||
// inode
|
||||
trace_in.push_front(new InodeStat(p));
|
||||
if (!p.end()) {
|
||||
// dentry
|
||||
string ref_dn;
|
||||
::_decode_simple(ref_dn, p);
|
||||
trace_dn.push_front(ref_dn);
|
||||
|
||||
// dir
|
||||
trace_dir.push_front(new DirStat(p));
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -252,7 +270,11 @@ class MClientReply : public Message {
|
||||
if (trace_in.empty() && trace_bl.length()) _decode_trace();
|
||||
return trace_in;
|
||||
}
|
||||
const list<string>& get_trace_dn() {
|
||||
const list<DirStat*>& get_trace_dir() {
|
||||
if (trace_in.empty() && trace_bl.length()) _decode_trace();
|
||||
return trace_dir;
|
||||
}
|
||||
const list<string>& get_trace_dn() {
|
||||
if (trace_in.empty() && trace_bl.length()) _decode_trace();
|
||||
return trace_dn;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user