From: Yan, Zheng Date: Thu, 27 Apr 2017 15:52:08 +0000 (+0800) Subject: mds: create auxiliary subtree inside auth subtree X-Git-Tag: v12.0.3~38^2~19 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=0d6d3205ef8440d1e38207eabdb57724991fcc33;p=ceph.git mds: create auxiliary subtree inside auth subtree Signed-off-by: "Yan, Zheng" --- diff --git a/src/mds/CDir.cc b/src/mds/CDir.cc index bad5c7a7b43b..979b8caae5c1 100644 --- a/src/mds/CDir.cc +++ b/src/mds/CDir.cc @@ -117,6 +117,7 @@ ostream& operator<<(ostream& out, const CDir& dir) if (dir.state_test(CDir::STATE_COMPLETE)) out << "|complete"; if (dir.state_test(CDir::STATE_FREEZINGTREE)) out << "|freezingtree"; if (dir.state_test(CDir::STATE_FROZENTREE)) out << "|frozentree"; + if (dir.state_test(CDir::STATE_AUXSUBTREE)) out << "|auxsubtree"; //if (dir.state_test(CDir::STATE_FROZENTREELEAF)) out << "|frozentreeleaf"; if (dir.state_test(CDir::STATE_FROZENDIR)) out << "|frozendir"; if (dir.state_test(CDir::STATE_FREEZINGDIR)) out << "|freezingdir"; diff --git a/src/mds/CDir.h b/src/mds/CDir.h index 03c53dee744a..447ca3cb8a6e 100644 --- a/src/mds/CDir.h +++ b/src/mds/CDir.h @@ -111,6 +111,7 @@ public: static const unsigned STATE_ASSIMRSTAT = (1<<17); // assimilating inode->frag rstats static const unsigned STATE_DIRTYDFT = (1<<18); // dirty dirfragtree static const unsigned STATE_BADFRAG = (1<<19); // bad dirfrag + static const unsigned STATE_AUXSUBTREE = (1<<20); // no subtree merge // common states static const unsigned STATE_CLEAN = 0; diff --git a/src/mds/MDCache.cc b/src/mds/MDCache.cc index dfe914772e97..ba34e4bf28ce 100644 --- a/src/mds/MDCache.cc +++ b/src/mds/MDCache.cc @@ -931,7 +931,8 @@ void MDCache::try_subtree_merge_at(CDir *dir, bool do_eval) if (parent != dir && // we have a parent, parent->dir_auth == dir->dir_auth && // auth matches, dir->dir_auth.second == CDIR_AUTH_UNKNOWN && // auth is unambiguous, - !dir->state_test(CDir::STATE_EXPORTBOUND)) { // not an exportbound, + !dir->state_test(CDir::STATE_EXPORTBOUND) && // not an exportbound, + !dir->state_test(CDir::STATE_AUXSUBTREE)) { // not aux subtree // merge with parent. dout(10) << " subtree merge at " << *dir << dendl; dir->set_dir_auth(CDIR_AUTH_DEFAULT); diff --git a/src/mds/Migrator.cc b/src/mds/Migrator.cc index 31aabc9c5754..76d9545c7bd8 100644 --- a/src/mds/Migrator.cc +++ b/src/mds/Migrator.cc @@ -819,6 +819,32 @@ void Migrator::export_dir(CDir *dir, mds_rank_t dest) return; } + if (g_conf->mds_thrash_exports) { + // create random subtree bound (which will not be exported) + list ls; + for (auto p = dir->begin(); p != dir->end(); ++p) { + auto dn = p->second; + CDentry::linkage_t *dnl= dn->get_linkage(); + if (dnl->is_primary()) { + CInode *in = dnl->get_inode(); + if (in->is_dir()) + in->get_nested_dirfrags(ls); + } + } + if (ls.size() > 0) { + int n = rand() % ls.size(); + auto p = ls.begin(); + while (n--) ++p; + CDir *bd = *p; + if (!(bd->is_frozen() || bd->is_freezing())) { + assert(bd->is_auth()); + dir->state_set(CDir::STATE_AUXSUBTREE); + mds->mdcache->adjust_subtree_auth(dir, mds->get_nodeid()); + dout(0) << "export_dir: create aux subtree " << *bd << " under " << *dir << dendl; + } + } + } + mds->hit_export_target(ceph_clock_now(), dest, -1); dir->auth_pin(this); @@ -1943,6 +1969,9 @@ void Migrator::export_finish(CDir *dir) bd->state_clear(CDir::STATE_EXPORTBOUND); } + if (dir->state_test(CDir::STATE_AUXSUBTREE)) + dir->state_clear(CDir::STATE_AUXSUBTREE); + // adjust auth, with possible subtree merge. // (we do this _after_ removing EXPORTBOUND pins, to allow merges) cache->adjust_subtree_auth(dir, it->second.peer); diff --git a/src/mds/journal.cc b/src/mds/journal.cc index db8efeba0c67..53dd3f466f13 100644 --- a/src/mds/journal.cc +++ b/src/mds/journal.cc @@ -335,13 +335,20 @@ void EMetaBlob::add_dir_context(CDir *dir, int mode) if (mode == TO_AUTH_SUBTREE_ROOT) { // subtree root? - if (dir->is_subtree_root() && !dir->state_test(CDir::STATE_EXPORTBOUND)) { - if (dir->is_auth() && !dir->is_ambiguous_auth()) { - // it's an auth subtree, we don't need maybe (if any), and we're done. - dout(20) << "EMetaBlob::add_dir_context(" << dir << ") reached unambig auth subtree, don't need " << maybe - << " at " << *dir << dendl; - maybe.clear(); - break; + if (dir->is_subtree_root() && + !dir->state_test(CDir::STATE_EXPORTBOUND)) { + if (dir->is_auth() && !dir->is_ambiguous_auth() ) { + if (dir->state_test(CDir::STATE_AUXSUBTREE) && + dir->get_dir_auth().first == diri->authority().first) { + // auxiliary subtree. treat it as normal dirfrag + dout(20) << "EMetaBlob::add_dir_context(" << dir << ") auxiliary subtree " << dendl; + } else { + // it's an auth subtree, we don't need maybe (if any), and we're done. + dout(20) << "EMetaBlob::add_dir_context(" << dir << ") reached unambig auth subtree, don't need " << maybe + << " at " << *dir << dendl; + maybe.clear(); + break; + } } else { dout(20) << "EMetaBlob::add_dir_context(" << dir << ") reached ambig or !auth subtree, need " << maybe << " at " << *dir << dendl;