mirror of
https://github.com/ceph/ceph
synced 2025-01-03 01:22:53 +00:00
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:
parent
ee0ab2b733
commit
6e013cd675
@ -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;
|
||||
|
@ -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);
|
||||
|
||||
|
@ -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);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -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;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user