mds: properly set COMPLETE flag when merging dirfrags

don't keep the COMPLETE flag when merging dirfrags during journal
replay, because it's inconvenience to check if the all dirfrags
under the 'basefrag' are in the cache and complete. One special case
is that newly created dirfrag get fragmented, then the fragment
operation get rolled back. The COMPLETE flag should be preserved in
this case because the dirfrag still doesn't exist on object store.

Signed-off-by: Yan, Zheng <zheng.z.yan@intel.com>
This commit is contained in:
Yan, Zheng 2014-01-15 11:12:43 +08:00
parent ee0ab2b733
commit 6e013cd675
4 changed files with 18 additions and 6 deletions

View File

@ -874,7 +874,7 @@ void CDir::split(int bits, list<CDir*>& subs, list<Context*>& waiters, bool repl
int n = 0;
for (list<frag_t>::iterator p = frags.begin(); p != frags.end(); ++p) {
CDir *f = new CDir(inode, *p, cache, is_auth());
f->state_set(state & MASK_STATE_FRAGMENT_KEPT);
f->state_set(state & (MASK_STATE_FRAGMENT_KEPT | STATE_COMPLETE));
f->replica_map = replica_map;
f->dir_auth = dir_auth;
f->init_fragment_pins();
@ -983,6 +983,9 @@ void CDir::merge(list<CDir*>& subs, list<Context*>& waiters, bool replay)
inode->close_dirfrag(dir->get_frag());
}
if (is_auth() && !replay)
mark_complete();
// FIXME: merge dirty old rstat
fnode.rstat.version = rstat_version;
fnode.accounted_rstat = fnode.rstat;

View File

@ -129,8 +129,7 @@ public:
|STATE_FROZENDIR
|STATE_STICKY);
static const unsigned MASK_STATE_FRAGMENT_KEPT =
(STATE_DIRTY |
STATE_COMPLETE |
(STATE_DIRTY|
STATE_EXPORTBOUND |
STATE_IMPORTBOUND);

View File

@ -11572,8 +11572,15 @@ void MDCache::add_uncommitted_fragment(dirfrag_t basedirfrag, int bits, list<fra
uf.bits = bits;
uf.ls = ls;
ls->uncommitted_fragments.insert(basedirfrag);
if (rollback)
if (rollback) {
uf.rollback.swap(*rollback);
// preserve COMPLETE flag for newly created dirfrag
if (bits > 0 && basedirfrag.frag == frag_t()) {
CDir *dir = get_dirfrag(basedirfrag);
if (dir && dir->is_complete())
uf.complete = true;
}
}
}
void MDCache::finish_uncommitted_fragment(dirfrag_t basedirfrag, int op)
@ -11658,6 +11665,8 @@ void MDCache::rollback_uncommitted_fragments()
dir->set_version(rollback.fnode.version);
dir->fnode = rollback.fnode;
if (uf.complete)
dir->mark_complete();
dir->_mark_dirty(ls);
if (!(dir->fnode.rstat == dir->fnode.accounted_rstat)) {
@ -11675,7 +11684,7 @@ void MDCache::rollback_uncommitted_fragments()
le->add_orig_frag(dir->get_frag());
le->metablob.add_dir_context(dir);
le->metablob.add_dir(dir, true);
le->metablob.add_dir(dir, true, uf.complete);
}
}

View File

@ -942,11 +942,12 @@ private:
struct ufragment {
int bits;
bool committed;
bool complete;
LogSegment *ls;
list<Context*> waiters;
list<frag_t> old_frags;
bufferlist rollback;
ufragment() : bits(0), committed(false), ls(NULL) {}
ufragment() : bits(0), committed(false), complete(false), ls(NULL) {}
};
map<dirfrag_t, ufragment> uncommitted_fragments;