mds: add dirty_rstat CInode elist, state, pins

We need to track inodes with unpropagated rstat data on a per-dirfrag
basis so that we can propagate it when the nestlock becomes writeable.
This commit is contained in:
Sage Weil 2010-09-23 13:04:00 -07:00
parent 628e28e2b2
commit 29b1e84843
4 changed files with 38 additions and 0 deletions

View File

@ -139,6 +139,7 @@ ostream& CDir::print_db_line_prefix(ostream& out)
// CDir
CDir::CDir(CInode *in, frag_t fg, MDCache *mdcache, bool auth) :
dirty_rstat_inodes(member_offset(CInode, dirty_rstat_item)),
item_dirty(this), item_new(this)
{
g_num_dir++;

View File

@ -166,6 +166,9 @@ public:
snapid_t first;
map<snapid_t,old_rstat_t> dirty_old_rstat; // [value.first,key]
// my inodes with dirty rstat data
elist<CInode*> dirty_rstat_inodes;
protected:
version_t projected_version;
list<fnode_t*> projected_fnode;

View File

@ -221,6 +221,27 @@ void CInode::print(ostream& out)
}
void CInode::mark_dirty_rstat()
{
if (!state_test(STATE_DIRTYRSTAT)) {
dout(10) << "mark_dirty_rstat" << dendl;
state_set(STATE_DIRTYRSTAT);
get(PIN_DIRTYRSTAT);
CDentry *dn = get_projected_parent_dn();
dn->dir->dirty_rstat_inodes.push_back(&dirty_rstat_item);
}
}
void CInode::clear_dirty_rstat()
{
if (state_test(STATE_DIRTYRSTAT)) {
dout(10) << "clear_dirty_rstat" << dendl;
state_clear(STATE_DIRTYRSTAT);
put(PIN_DIRTYRSTAT);
dirty_rstat_item.remove_myself();
}
}
inode_t *CInode::project_inode(map<string,bufferptr> *px)
{
if (projected_nodes.empty()) {

View File

@ -100,6 +100,7 @@ public:
static const int PIN_TRUNCATING = 18;
static const int PIN_STRAY = 19; // we pin our stray inode while active
static const int PIN_NEEDSNAPFLUSH = 20;
static const int PIN_DIRTYRSTAT = 21;
const char *pin_name(int p) {
switch (p) {
@ -122,6 +123,7 @@ public:
case PIN_TRUNCATING: return "truncating";
case PIN_STRAY: return "stray";
case PIN_NEEDSNAPFLUSH: return "needsnapflush";
case PIN_DIRTYRSTAT: return "dirtyrstat";
default: return generic_pin_name(p);
}
}
@ -140,6 +142,7 @@ public:
static const int STATE_RECOVERING = (1<<12);
static const int STATE_PURGING = (1<<13);
static const int STATE_DIRTYPARENT = (1<<14);
static const int STATE_DIRTYRSTAT = (1<<15);
// -- waiters --
static const uint64_t WAIT_DIR = (1<<0);
@ -183,6 +186,16 @@ public:
//loff_t last_open_journaled; // log offset for the last journaled EOpen
utime_t last_dirstat_prop;
// list item node for when we have unpropagated rstat data
elist<CInode*>::item dirty_rstat_item;
bool is_dirty_rstat() {
return state_test(STATE_DIRTYRSTAT);
}
void mark_dirty_rstat();
void clear_dirty_rstat();
//bool hack_accessed;
//utime_t hack_load_stamp;