// pin/unpin item in cache
void lru_pin();
void lru_unpin();
+ bool lru_is_expireable() { return lru_expireable; }
friend class LRU;
+ //friend class MDCache;
};
__uint32_t lru_max; // max items
friend class LRUObject;
-
+ //friend class MDCache; // hack
public:
LRU() {
lru_ntop = lru_nbot = lru_num = 0;
#undef dout
#define dout(x) if (x <= g_conf.debug) cout << "mds" << mds->get_nodeid() << " cdir: "
+map<int,int> cdir_pins;
+
ostream& operator<<(ostream& out, CDir& dir)
{
// ref counts
void CDir::put(int by) {
+ cdir_pins[by]--;
+
// bad?
if (ref == 0 || ref_set.count(by) != 1) {
dout(7) << *this << " bad put by " << by << " " << cdir_pin_names[by] << " was " << ref << " (" << ref_set << ")" << endl;
}
void CDir::get(int by) {
+ cdir_pins[by]++;
+
// inode
if (ref == 0)
inode->get(CINODE_PIN_DIR);
"freeze",
"proxy",
"authpin",
- "importing",
- "importingexport",
- "requestpins",
+ "imping",
+ "impgex",
+ "reqpins",
"dirty"
};
// CDir
typedef map<string, CDentry*> CDir_map_t;
+
+extern map<int, int> cdir_pins; // counts
+
+
class CDir {
public:
CInode *inode;
#define dout(x) if (x <= g_conf.debug) cout << "cinode: "
+map<int, int> cinode_pins; // counts
+
ostream& operator<<(ostream& out, CInode& in)
{
"opentok",
"dndirty",
"authpin",
- "importing",
+ "imping",
"request",
- "renamesrc",
- "archoring",
+ "rensrc",
+ "anching",
"--",
- "dentrylock"
+ "dnlock"
};
ostream& operator<<(ostream& out, CInode& in);
+extern map<int, int> cinode_pins; // counts
+
+
// cached inode wrapper
class CInode : LRUObject {
public:
void make_anchor_trace(vector<class Anchor*>& trace);
+
// -- state --
unsigned get_state() { return state; }
void state_clear(unsigned mask) { state &= ~mask; }
bool is_pinned() { return ref > 0; }
set<int>& get_ref_set() { return ref_set; }
void put(int by) {
+ cinode_pins[by]--;
if (ref == 0 || ref_set.count(by) != 1) {
dout(7) << " bad put " << *this << " by " << by << " " << cinode_pin_names[by] << " was " << ref << " (" << ref_set << ")" << endl;
assert(ref_set.count(by) == 1);
dout(7) << " put " << *this << " by " << by << " " << cinode_pin_names[by] << " now " << ref << " (" << ref_set << ")" << endl;
}
void get(int by) {
+ cinode_pins[by]++;
if (ref == 0)
lru_pin();
if (ref_set.count(by)) {
in->popularity[MDS_POP_CURDOM].take( st.popularity_curdom );
in->popularity[MDS_POP_ANYDOM].adjust(now, newcurdom);
- if (st.is_dirty)
+ if (st.is_dirty) {
in->mark_dirty();
+ }
in->cached_by.clear();
in->cached_by = cached_by;
}
}
+ /* hack
+ if (lru.lru_get_size() == max) {
+ int i;
+ dout(1) << "lru_top " << lru.lru_ntop << "/" << lru.lru_num << endl;
+ CInode *cur = (CInode*)lru.lru_tophead;
+ i = 1;
+ while (cur) {
+ dout(1) << " top " << i++ << "/" << lru.lru_ntop << " " << cur->lru_is_expireable() << " " << *cur << endl;
+ cur = (CInode*)cur->lru_next;
+ }
+
+ dout(1) << "lru_bot " << lru.lru_nbot << "/" << lru.lru_num << endl;
+ cur = (CInode*)lru.lru_bothead;
+ i = 1;
+ while (cur) {
+ dout(1) << " bot " << i++ << "/" << lru.lru_nbot << " " << cur->lru_is_expireable() << " " << *cur << endl;
+ cur = (CInode*)cur->lru_next;
+ }
+
+ }
+ */
+
// send expires
for (map<int, MCacheExpire*>::iterator it = expiremap.begin();
it != expiremap.end();
// keep going.
trace.push_back(dn);
cur = dn->inode;
+ touch_inode(cur);
depth++;
continue;
}
// directory isn't complete; reload
dout(7) << "traverse: incomplete dir contents for " << *cur << ", fetching" << endl;
- lru.lru_touch(cur); // touch readdiree
+ touch_inode(cur);
mds->mdstore->fetch_dir(cur->dir, ondelay);
mds->logger->inc("cmiss");
} else {
dout(7) << "traverse: discover on " << *cur << " for " << want.get_path() << " to mds" << dauth << endl;
- lru.lru_touch(cur); // touch discoveree
+ touch_inode(cur);
mds->messenger->send_message(new MDiscover(mds->get_nodeid(),
cur->ino(),
mds->logger->set("cpin", lru.lru_get_num_pinned());
mds->logger->set("cmax", lru.lru_get_max());
+ // pin
+ for (map<int,int>::iterator it = cinode_pins.begin();
+ it != cinode_pins.end();
+ it++) {
+ //string s = "I";
+ //s += cinode_pin_names[it->first];
+ mds->logger2->set(//s,
+ cinode_pin_names[it->first],
+ it->second);
+ }
+ /*
+ for (map<int,int>::iterator it = cdir_pins.begin();
+ it != cdir_pins.end();
+ it++) {
+ //string s = "D";
+ //s += cdir_pin_names[it->first];
+ mds->logger2->set(//s,
+ cdir_pin_names[it->first],
+ it->second);
+ }
+ */
+
}
} else {
in->set_auth(true);
}
-
- // state
+
+ // link before state
+ if (dn->inode != in) {
+ assert(!dn->inode);
+ dn->dir->link_inode(dn, in);
+ }
+
+ // state after link
istate.update_inode(in, now);
-
+
+
// add inode?
if (added) {
add_inode(in);
dout(10) << " had " << *in << endl;
}
- // link to dentry
- if (dn->inode != in) {
- assert(!dn->inode);
- dn->dir->link_inode(dn, in);
- }
// cached_by
assert(!in->is_cached_by(oldauth));
typedef hash_map<inodeno_t, CInode*> inode_map_t;
+
typedef const char* pchar;
/** active_request_t
void remove_inode(CInode *in);
void destroy_inode(CInode *in);
+ void touch_inode(CInode *in) {
+ if (in->is_auth())
+ lru.lru_touch(in);
+ else
+ lru.lru_midtouch(in);
+ }
+
public:
void export_empty_import(CDir *dir);
using namespace std;
-LogType mds_logtype;
+LogType mds_logtype, mds_cache_logtype;
#include "include/config.h"
#undef dout
mds_logtype.add_set("nex");
mds_logtype.add_set("nim");
+ char n[80];
+ sprintf(n, "mds%d.cache", whoami);
+ logger2 = new Logger(n, (LogType*)&mds_cache_logtype);
+
// alloc
idalloc = new IdAllocator(this);
MDLog *mdlog;
MDBalancer *balancer;
- Logger *logger;
+ Logger *logger, *logger2;
protected:
__uint64_t stat_ops;