/* NOTE: This function converts a lockname into a string. It uses knowledge * of the format of the lockname that should be outside the purview of the dlm. * We are adding only to make dlm debugging slightly easier. * * For more on lockname formats, please refer to dlmglue.c and ocfs2_lockid.h.
*/ staticint stringify_lockname(constchar *lockname, int locklen, char *buf, int len)
{ int out = 0;
__be64 inode_blkno_be;
#define OCFS2_DENTRY_LOCK_INO_START 18 if (*lockname == 'N') {
memcpy((__be64 *)&inode_blkno_be,
(char *)&lockname[OCFS2_DENTRY_LOCK_INO_START], sizeof(__be64));
out += scnprintf(buf + out, len - out, "%.*s%08x",
OCFS2_DENTRY_LOCK_INO_START - 1, lockname,
(unsignedint)be64_to_cpu(inode_blkno_be));
} else
out += scnprintf(buf + out, len - out, "%.*s",
locklen, lockname); return out;
}
staticint stringify_nodemap(unsignedlong *nodemap, int maxnodes, char *buf, int len)
{ int out = 0; int i = -1;
while ((i = find_next_bit(nodemap, maxnodes, i + 1)) < maxnodes)
out += scnprintf(buf + out, len - out, "%d ", i);
return out;
}
staticint dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
{ int out = 0; char *mle_type;
out += stringify_lockname(mle->mname, mle->mnamelen, buf + out, len - out);
out += scnprintf(buf + out, len - out, "\t%3s\tmas=%3u\tnew=%3u\tevt=%1d\tuse=%1d\tref=%3d\n",
mle_type, mle->master, mle->new_master,
!list_empty(&mle->hb_events),
!!mle->inuse,
kref_read(&mle->mle_refs));
out += scnprintf(buf + out, len - out, "Maybe=");
out += stringify_nodemap(mle->maybe_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
out += scnprintf(buf + out, len - out, "Vote=");
out += stringify_nodemap(mle->vote_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
out += scnprintf(buf + out, len - out, "Response=");
out += stringify_nodemap(mle->response_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
out += scnprintf(buf + out, len - out, "Node=");
out += stringify_nodemap(mle->node_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* begin - purge list funcs */ staticint debug_purgelist_print(struct dlm_ctxt *dlm, char *buf, int len)
{ struct dlm_lock_resource *res; int out = 0; unsignedlong total = 0;
out += scnprintf(buf + out, len - out, "Dumping Purgelist for Domain: %s\n", dlm->name);
spin_lock(&dlm->spinlock);
list_for_each_entry(res, &dlm->purge_list, purge) {
++total; if (len - out < 100) continue;
spin_lock(&res->spinlock);
out += stringify_lockname(res->lockname.name,
res->lockname.len,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\t%ld\n",
(jiffies - res->last_used)/HZ);
spin_unlock(&res->spinlock);
}
spin_unlock(&dlm->spinlock);
out += scnprintf(buf + out, len - out, "Total on list: %lu\n", total);
staticint dump_lockres(struct dlm_lock_resource *res, char *buf, int len)
{ struct dlm_lock *lock; int i; int out = 0;
out += scnprintf(buf + out, len - out, "NAME:");
out += stringify_lockname(res->lockname.name, res->lockname.len,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* refmap */
out += scnprintf(buf + out, len - out, "RMAP:");
out += stringify_nodemap(res->refmap, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* lvb */
out += scnprintf(buf + out, len - out, "LVBX:"); for (i = 0; i < DLM_LVB_LEN; i++)
out += scnprintf(buf + out, len - out, "%02x", (unsignedchar)res->lvb[i]);
out += scnprintf(buf + out, len - out, "\n");
/* granted */
list_for_each_entry(lock, &res->granted, list)
out += dump_lock(lock, 0, buf + out, len - out);
/* converting */
list_for_each_entry(lock, &res->converting, list)
out += dump_lock(lock, 1, buf + out, len - out);
/* blocked */
list_for_each_entry(lock, &res->blocked, list)
out += dump_lock(lock, 2, buf + out, len - out);
/* begin - debug state funcs */ staticint debug_state_print(struct dlm_ctxt *dlm, char *buf, int len)
{ int out = 0; struct dlm_reco_node_data *node; char *state; int cur_mles = 0, tot_mles = 0; int i;
spin_lock(&dlm->spinlock);
switch (dlm->dlm_state) { case DLM_CTXT_NEW:
state = "NEW"; break; case DLM_CTXT_JOINED:
state = "JOINED"; break; case DLM_CTXT_IN_SHUTDOWN:
state = "SHUTDOWN"; break; case DLM_CTXT_LEAVING:
state = "LEAVING"; break; default:
state = "UNKNOWN"; break;
}
/* Number of Joins: xxx Joining Node: xxx */
out += scnprintf(buf + out, len - out, "Number of Joins: %d Joining Node: %d\n",
dlm->num_joins, dlm->joining_node);
/* Domain Map: xx xx xx */
out += scnprintf(buf + out, len - out, "Domain Map: ");
out += stringify_nodemap(dlm->domain_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* Exit Domain Map: xx xx xx */
out += scnprintf(buf + out, len - out, "Exit Domain Map: ");
out += stringify_nodemap(dlm->exit_domain_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* Live Map: xx xx xx */
out += scnprintf(buf + out, len - out, "Live Map: ");
out += stringify_nodemap(dlm->live_nodes_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* Lock Resources: xxx (xxx) */
out += scnprintf(buf + out, len - out, "Lock Resources: %d (%d)\n",
atomic_read(&dlm->res_cur_count),
atomic_read(&dlm->res_tot_count));
for (i = 0; i < DLM_MLE_NUM_TYPES; ++i)
tot_mles += atomic_read(&dlm->mle_tot_count[i]);
for (i = 0; i < DLM_MLE_NUM_TYPES; ++i)
cur_mles += atomic_read(&dlm->mle_cur_count[i]);
/* MLEs: xxx (xxx) */
out += scnprintf(buf + out, len - out, "MLEs: %d (%d)\n", cur_mles, tot_mles);
/* Blocking: xxx (xxx) */
out += scnprintf(buf + out, len - out, " Blocking: %d (%d)\n",
atomic_read(&dlm->mle_cur_count[DLM_MLE_BLOCK]),
atomic_read(&dlm->mle_tot_count[DLM_MLE_BLOCK]));
/* Mastery: xxx (xxx) */
out += scnprintf(buf + out, len - out, " Mastery: %d (%d)\n",
atomic_read(&dlm->mle_cur_count[DLM_MLE_MASTER]),
atomic_read(&dlm->mle_tot_count[DLM_MLE_MASTER]));
/* Migration: xxx (xxx) */
out += scnprintf(buf + out, len - out, " Migration: %d (%d)\n",
atomic_read(&dlm->mle_cur_count[DLM_MLE_MIGRATION]),
atomic_read(&dlm->mle_tot_count[DLM_MLE_MIGRATION]));
/* Recovery Map: xx xx */
out += scnprintf(buf + out, len - out, "Recovery Map: ");
out += stringify_nodemap(dlm->recovery_map, O2NM_MAX_NODES,
buf + out, len - out);
out += scnprintf(buf + out, len - out, "\n");
/* Recovery Node State: */
out += scnprintf(buf + out, len - out, "Recovery Node State:\n");
list_for_each_entry(node, &dlm->reco.node_data, list) { switch (node->state) { case DLM_RECO_NODE_DATA_INIT:
state = "INIT"; break; case DLM_RECO_NODE_DATA_REQUESTING:
state = "REQUESTING"; break; case DLM_RECO_NODE_DATA_DEAD:
state = "DEAD"; break; case DLM_RECO_NODE_DATA_RECEIVING:
state = "RECEIVING"; break; case DLM_RECO_NODE_DATA_REQUESTED:
state = "REQUESTED"; break; case DLM_RECO_NODE_DATA_DONE:
state = "DONE"; break; case DLM_RECO_NODE_DATA_FINALIZE_SENT:
state = "FINALIZE-SENT"; break; default:
state = "BAD"; break;
}
out += scnprintf(buf + out, len - out, "\t%u - %s\n",
node->node_num, state);
}
/* files in subroot */ void dlm_debug_init(struct dlm_ctxt *dlm)
{ /* for dumping dlm_ctxt */
debugfs_create_file(DLM_DEBUGFS_DLM_STATE, S_IFREG|S_IRUSR,
dlm->dlm_debugfs_subroot, dlm, &debug_state_fops);
/* for dumping lockres */
debugfs_create_file(DLM_DEBUGFS_LOCKING_STATE, S_IFREG|S_IRUSR,
dlm->dlm_debugfs_subroot, dlm, &debug_lockres_fops);
/* for dumping mles */
debugfs_create_file(DLM_DEBUGFS_MLE_STATE, S_IFREG|S_IRUSR,
dlm->dlm_debugfs_subroot, dlm, &debug_mle_fops);
/* for dumping lockres on the purge list */
debugfs_create_file(DLM_DEBUGFS_PURGE_LIST, S_IFREG|S_IRUSR,
dlm->dlm_debugfs_subroot, dlm,
&debug_purgelist_fops);
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.