From 27a3d3840697cfcf2d2af4f2895938997b87d711 Mon Sep 17 00:00:00 2001 From: Sage Weil Date: Mon, 28 Jul 2008 14:31:23 -0700 Subject: [PATCH] mds: dirty_old_fragstat to dirty_old_rstat --- src/mds/CDir.h | 2 +- src/mds/CInode.cc | 29 ++++++++------- src/mds/MDCache.cc | 89 ++++++++++++++++++++++++---------------------- src/mds/MDCache.h | 3 +- src/mds/mdstypes.h | 12 ++++--- 5 files changed, 71 insertions(+), 64 deletions(-) diff --git a/src/mds/CDir.h b/src/mds/CDir.h index 15bfe03fe14b2..07a251ea48121 100644 --- a/src/mds/CDir.h +++ b/src/mds/CDir.h @@ -157,7 +157,7 @@ class CDir : public MDSCacheObject { fnode_t fnode; snapid_t first; - map dirty_old_fnodes; // [value.first,key] + map dirty_old_rstat; // [value.first,key] protected: version_t projected_version; diff --git a/src/mds/CInode.cc b/src/mds/CInode.cc index 5f76aa9a622a0..aa128964200d7 100644 --- a/src/mds/CInode.cc +++ b/src/mds/CInode.cc @@ -590,6 +590,7 @@ void CInode::encode_lock_state(int type, bufferlist& bl) dout(20) << " accounted_fragstat " << p->second->fnode.accounted_fragstat << dendl; frag_t fg = p->second->dirfrag().frag; ::encode(fg, tmp); + ::encode(p->second->first, tmp); ::encode(p->second->fnode.fragstat, tmp); ::encode(p->second->fnode.accounted_fragstat, tmp); n++; @@ -617,7 +618,7 @@ void CInode::encode_lock_state(int type, bufferlist& bl) ::encode(p->second->first, tmp); ::encode(p->second->fnode.rstat, tmp); ::encode(p->second->fnode.accounted_rstat, tmp); - ::encode(p->second->dirty_old_fnodes, tmp); + ::encode(p->second->dirty_old_rstat, tmp); n++; } ::encode(n, bl); @@ -728,11 +729,9 @@ void CInode::decode_lock_state(int type, bufferlist& bl) frag_t fg; frag_info_t fragstat; frag_info_t accounted_fragstat; - map dirty_old_fnodes; ::decode(fg, p); ::decode(fragstat, p); ::decode(accounted_fragstat, p); - ::decode(dirty_old_fnodes, p); dout(10) << fg << " got changed fragstat " << fragstat << dendl; dout(20) << fg << " accounted_fragstat " << accounted_fragstat << dendl; @@ -743,22 +742,18 @@ void CInode::decode_lock_state(int type, bufferlist& bl) dout(20) << " " << fg << " accounted_fragstat " << accounted_fragstat << dendl; dir->fnode.fragstat = fragstat; dir->fnode.accounted_fragstat = accounted_fragstat; - dir->dirty_old_fnodes.swap(dirty_old_fnodes); - if (!(fragstat == accounted_fragstat) || - dirty_old_fnodes.size()) + if (!(fragstat == accounted_fragstat)) dirlock.set_updated(); } else { if (dir && dir->is_auth() && - (!(dir->fnode.accounted_fragstat == fragstat) || - dirty_old_fnodes.size())) { + !(dir->fnode.accounted_fragstat == fragstat)) { dout(10) << " setting accounted_fragstat " << fragstat << " and setting dirty bit on " << *dir << dendl; fnode_t *pf = dir->get_projected_fnode(); pf->accounted_fragstat = fragstat; if (dir->is_auth()) dir->_set_dirty_flag(); // bit of a hack - dir->dirty_old_fnodes.swap(dirty_old_fnodes); } } } @@ -781,10 +776,12 @@ void CInode::decode_lock_state(int type, bufferlist& bl) snapid_t fgfirst; nest_info_t rstat; nest_info_t accounted_rstat; + map dirty_old_rstat; ::decode(fg, p); ::decode(fgfirst, p); ::decode(rstat, p); ::decode(accounted_rstat, p); + ::decode(dirty_old_rstat, p); dout(10) << fg << " got changed rstat " << rstat << dendl; dout(20) << fg << " accounted_rstat " << accounted_rstat << dendl; @@ -795,7 +792,8 @@ void CInode::decode_lock_state(int type, bufferlist& bl) dout(20) << " " << fg << " accounted_rstat " << accounted_rstat << dendl; dir->fnode.rstat = rstat; dir->fnode.accounted_rstat = accounted_rstat; - if (!(rstat == accounted_rstat)) + dir->dirty_old_rstat.swap(dirty_old_rstat); + if (!(rstat == accounted_rstat) || dir->dirty_old_rstat.size()) dirlock.set_updated(); } else { if (dir && @@ -808,6 +806,7 @@ void CInode::decode_lock_state(int type, bufferlist& bl) pf->accounted_rstat = rstat; if (dir->is_auth()) dir->_set_dirty_flag(); // bit of a hack + dir->dirty_old_rstat.swap(dirty_old_rstat); } } } @@ -898,12 +897,12 @@ void CInode::finish_scatter_gather_update(int type) p++) { CDir *dir = p->second; fnode_t *pf = dir->get_projected_fnode(); - mdcache->project_rstat_frag_to_inode(*pf, dir->first, CEPH_NOSNAP, this, true); - for (map::iterator q = dir->dirty_old_fnodes.begin(); - q != dir->dirty_old_fnodes.end(); + mdcache->project_rstat_frag_to_inode(pf->rstat, pf->accounted_rstat, dir->first, CEPH_NOSNAP, this, true); + for (map::iterator q = dir->dirty_old_rstat.begin(); + q != dir->dirty_old_rstat.end(); q++) - mdcache->project_rstat_frag_to_inode(q->second.fnode, q->second.first, q->first, this, true); - dir->dirty_old_fnodes.clear(); + mdcache->project_rstat_frag_to_inode(q->second.rstat, q->second.accounted_rstat, q->second.first, q->first, this, true); + dir->dirty_old_rstat.clear(); } pi->rstat.version++; dout(20) << " final rstat " << pi->rstat << dendl; diff --git a/src/mds/MDCache.cc b/src/mds/MDCache.cc index f68146b962d7f..74a773ec016c1 100644 --- a/src/mds/MDCache.cc +++ b/src/mds/MDCache.cc @@ -1141,42 +1141,45 @@ void MDCache::project_rstat_inode_to_frag(inode_t& inode, snapid_t ofirst, snapi * update one segment at a time. then loop to cover the whole * [ofirst,last] interval. */ - fnode_t *pf; + nest_info_t *prstat; snapid_t first; + fnode_t *pf = parent->get_projected_fnode(); if (last == CEPH_NOSNAP) { first = MAX(ofirst, parent->first); - pf = parent->get_projected_fnode(); - dout(10) << " projecting to head [" << first << "," << last << "] " << pf->rstat << dendl; + prstat = &pf->rstat; + dout(10) << " projecting to head [" << first << "," << last << "] " << *prstat << dendl; if (first > parent->first && - !(pf->fragstat == pf->accounted_fragstat)) { - dout(10) << " target snapped and not fully accounted, cow to dirty_old_fnode [" + !(pf->rstat == pf->accounted_rstat)) { + dout(10) << " target snapped and not fully accounted, cow to dirty_old_rstat [" << parent->first << "," << (first-1) << "] " - << " " << pf->rstat << "/" << pf->accounted_rstat + << " " << *prstat << "/" << pf->accounted_rstat << dendl; - parent->dirty_old_fnodes[first-1].first = parent->first; - parent->dirty_old_fnodes[first-1].fnode = *pf; + parent->dirty_old_rstat[first-1].first = parent->first; + parent->dirty_old_rstat[first-1].rstat = pf->rstat; + parent->dirty_old_rstat[first-1].accounted_rstat = pf->accounted_rstat; parent->first = first; } } else if (last >= parent->first) { first = parent->first; - parent->dirty_old_fnodes[last].first = first; - parent->dirty_old_fnodes[last].fnode = *parent->get_projected_fnode(); - pf = &parent->dirty_old_fnodes[last].fnode; + parent->dirty_old_rstat[last].first = first; + parent->dirty_old_rstat[last].rstat = pf->rstat; + parent->dirty_old_rstat[last].accounted_rstat = pf->accounted_rstat; + prstat = &parent->dirty_old_rstat[last].rstat; dout(10) << " projecting to newly split dirty_old_fnode [" << first << "," << last << "] " - << " " << pf->rstat << "/" << pf->accounted_rstat << dendl; + << " " << *prstat << "/" << pf->accounted_rstat << dendl; } else { - // be careful, dirty_old_fnodes is a _sparse_ map. + // be careful, dirty_old_rstat is a _sparse_ map. // sorry, this is ugly. first = ofirst; // find any intersection with last - map::iterator p = parent->dirty_old_fnodes.lower_bound(last); - if (p == parent->dirty_old_fnodes.end()) { - dout(20) << " no dirty_old_fnode with last >= last " << last << dendl; - if (!parent->dirty_old_fnodes.empty() && parent->dirty_old_fnodes.rbegin()->first >= first) { - dout(20) << " last dirty_old_fnode ends at " << parent->dirty_old_fnodes.rbegin()->first << dendl; - first = parent->dirty_old_fnodes.rbegin()->first+1; + map::iterator p = parent->dirty_old_rstat.lower_bound(last); + if (p == parent->dirty_old_rstat.end()) { + dout(20) << " no dirty_old_rstat with last >= last " << last << dendl; + if (!parent->dirty_old_rstat.empty() && parent->dirty_old_rstat.rbegin()->first >= first) { + dout(20) << " last dirty_old_rstat ends at " << parent->dirty_old_rstat.rbegin()->first << dendl; + first = parent->dirty_old_rstat.rbegin()->first+1; } } else { // *p last is >= last @@ -1184,55 +1187,56 @@ void MDCache::project_rstat_inode_to_frag(inode_t& inode, snapid_t ofirst, snapi // *p intersects [first,last] if (p->second.first < first) { dout(10) << " splitting off left bit [" << p->second.first << "," << first-1 << "]" << dendl; - parent->dirty_old_fnodes[first-1] = p->second; + parent->dirty_old_rstat[first-1] = p->second; p->second.first = first; } if (p->second.first > first) first = p->second.first; if (last < p->first) { dout(10) << " splitting off right bit [" << last+1 << "," << p->first << "]" << dendl; - parent->dirty_old_fnodes[last] = p->second; + parent->dirty_old_rstat[last] = p->second; p->second.first = last+1; } } else { // *p is to the _right_ of [first,last] - p = parent->dirty_old_fnodes.lower_bound(first); + p = parent->dirty_old_rstat.lower_bound(first); // new *p last is >= first if (p->second.first <= last && // new *p isn't also to the right, and p->first >= first) { // it intersects our first bit, dout(10) << " staying to the right of [" << p->second.first << "," << p->first << "]..." << dendl; first = p->first+1; } - dout(10) << " projecting to new dirty_old_fnode [" << first << "," << last << "]" << dendl; + dout(10) << " projecting to new dirty_old_rstat [" << first << "," << last << "]" << dendl; } } - dout(10) << " projecting to dirty_old_fnode [" << first << "," << last << "]" << dendl; - parent->dirty_old_fnodes[last].first = first; - pf = &parent->dirty_old_fnodes[last].fnode; + dout(10) << " projecting to dirty_old_rstat [" << first << "," << last << "]" << dendl; + parent->dirty_old_rstat[last].first = first; + prstat = &parent->dirty_old_rstat[last].rstat; } // apply - dout(10) << " project to [" << first << "," << last << "] " << pf->rstat << dendl; + dout(10) << " project to [" << first << "," << last << "] " << *prstat << dendl; assert(last >= first); - pf->rstat.add(delta); + prstat->add(delta); inode.accounted_rstat = inode.rstat; - dout(10) << " result [" << first << "," << last << "] " << pf->rstat << " " << *parent << dendl; + dout(10) << " result [" << first << "," << last << "] " << *prstat << " " << *parent << dendl; last = first-1; } } -void MDCache::project_rstat_frag_to_inode(fnode_t& fnode, snapid_t ofirst, snapid_t last, +void MDCache::project_rstat_frag_to_inode(nest_info_t& rstat, nest_info_t& accounted_rstat, + snapid_t ofirst, snapid_t last, CInode *pin, bool cow_head) { dout(10) << "project_rstat_frag_to_inode [" << ofirst << "," << last << "]" << dendl; - dout(10) << " frag rstat " << fnode.rstat << dendl; - dout(10) << " frag accounted_rstat " << fnode.accounted_rstat << dendl; - nest_info_t delta = fnode.rstat; - delta.sub(fnode.accounted_rstat); + dout(10) << " frag rstat " << rstat << dendl; + dout(10) << " frag accounted_rstat " << accounted_rstat << dendl; + nest_info_t delta = rstat; + delta.sub(accounted_rstat); dout(10) << " delta " << delta << dendl; - fnode.accounted_rstat = fnode.rstat; + accounted_rstat = rstat; inode_t *pi_to_cow = cow_head ? pin->get_projected_inode() : pin->get_previous_projected_inode(); @@ -1484,12 +1488,12 @@ void MDCache::predirty_journal_parents(Mutation *mut, EMetaBlob *blob, // rstat if (primary_dn) { - for (map::iterator p = parent->dirty_old_fnodes.begin(); - p != parent->dirty_old_fnodes.end(); + for (map::iterator p = parent->dirty_old_rstat.begin(); + p != parent->dirty_old_rstat.end(); p++) - project_rstat_frag_to_inode(p->second.fnode, p->second.first, p->first, pin, true);//false); - parent->dirty_old_fnodes.clear(); - project_rstat_frag_to_inode(*pf, parent->first, CEPH_NOSNAP, pin, true);//false); + project_rstat_frag_to_inode(p->second.rstat, p->second.accounted_rstat, p->second.first, p->first, pin, true);//false); + parent->dirty_old_rstat.clear(); + project_rstat_frag_to_inode(pf->rstat, pf->accounted_rstat, parent->first, CEPH_NOSNAP, pin, true);//false); } // next parent! @@ -4871,9 +4875,10 @@ int MDCache::path_traverse(MDRequest *mdr, Message *req, // who dout(10) << "traverse: REP replicating to " << req->get_source() << " dn " << *dn << dendl; MDiscoverReply *reply = new MDiscoverReply(curdir->dirfrag()); reply->mark_unsolicited(); - reply->add_dentry( dn->replicate_to( from ) ); + reply->starts_with = MDiscoverReply::DENTRY; + replicate_dentry(dn, from, reply->trace); if (dn->is_primary()) - reply->add_inode( dn->inode->replicate_to( from ) ); + replicate_inode(dn->inode, from, reply->trace); mds->send_message_mds(reply, req->get_source().num()); } } diff --git a/src/mds/MDCache.h b/src/mds/MDCache.h index 3fde3afadeac3..fcd9847ce14ff 100644 --- a/src/mds/MDCache.h +++ b/src/mds/MDCache.h @@ -479,7 +479,8 @@ public: void project_rstat_inode_to_frag(inode_t& inode, snapid_t ofirst, snapid_t last, CDir *parent, int linkunlink=0); - void project_rstat_frag_to_inode(fnode_t& fnode, snapid_t ofirst, snapid_t last, + void project_rstat_frag_to_inode(nest_info_t& rstat, nest_info_t& accounted_rstat, + snapid_t ofirst, snapid_t last, CInode *pin, bool cow_head); void predirty_journal_parents(Mutation *mut, EMetaBlob *blob, CInode *in, CDir *parent, diff --git a/src/mds/mdstypes.h b/src/mds/mdstypes.h index d5f12a1ac7dd3..9dd51326d5230 100644 --- a/src/mds/mdstypes.h +++ b/src/mds/mdstypes.h @@ -376,20 +376,22 @@ struct fnode_t { WRITE_CLASS_ENCODER(fnode_t) -struct old_fnode_t { +struct old_rstat_t { snapid_t first; - fnode_t fnode; + nest_info_t rstat, accounted_rstat; void encode(bufferlist& bl) const { ::encode(first, bl); - ::encode(fnode, bl); + ::encode(rstat, bl); + ::encode(accounted_rstat, bl); } void decode(bufferlist::iterator& bl) { ::decode(first, bl); - ::decode(fnode, bl); + ::decode(rstat, bl); + ::decode(accounted_rstat, bl); } }; -WRITE_CLASS_ENCODER(old_fnode_t) +WRITE_CLASS_ENCODER(old_rstat_t) -- 2.39.5