* [Ocfs2-devel] [PATCH 06/18] ocfs2_dlm: Link all lockres' to a tracking list
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:32 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 12/18] ocfs2_dlm: Dumps the purgelist into a debugfs file Sunil Mushran
` (16 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch links all the lockres' to a tracking list in dlm_ctxt.
We will use this in the upcoming patch that will walk the entire
list and to dump the lockres states to a debugfs file.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 4 ++++
fs/ocfs2/dlm/dlmdomain.c | 11 +++++++++++
fs/ocfs2/dlm/dlmmaster.c | 11 +++++++++++
3 files changed, 26 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index eac1b3b..a3b22bf 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -101,6 +101,7 @@ struct dlm_ctxt
struct list_head purge_list;
struct list_head pending_asts;
struct list_head pending_basts;
+ struct list_head tracking_list;
unsigned int purge_count;
spinlock_t spinlock;
spinlock_t ast_lock;
@@ -266,6 +267,9 @@ struct dlm_lock_resource
struct list_head dirty;
struct list_head recovering; // dlm_recovery_ctxt.resources list
+ /* Added during init and removed during release */
+ struct list_head tracking; /* dlm->tracking_list */
+
/* unused lock resources have their last_used stamped and are
* put on a list for the dlm thread to run. */
unsigned long last_used;
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index 6d02ef5..1d382f1 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -634,6 +634,7 @@ int dlm_shutting_down(struct dlm_ctxt *dlm)
void dlm_unregister_domain(struct dlm_ctxt *dlm)
{
int leave = 0;
+ struct dlm_lock_resource *res;
spin_lock(&dlm_domain_lock);
BUG_ON(dlm->dlm_state != DLM_CTXT_JOINED);
@@ -663,6 +664,15 @@ void dlm_unregister_domain(struct dlm_ctxt *dlm)
msleep(500);
mlog(0, "%s: more migration to do\n", dlm->name);
}
+
+ /* This list should be empty. If not, print remaining lockres */
+ if (!list_empty(&dlm->tracking_list)) {
+ mlog(ML_ERROR, "Following lockres' are still on the "
+ "tracking list:\n");
+ list_for_each_entry(res, &dlm->tracking_list, tracking)
+ dlm_print_one_lock_resource(res);
+ }
+
dlm_mark_domain_leaving(dlm);
dlm_leave_domain(dlm);
dlm_complete_dlm_shutdown(dlm);
@@ -1404,6 +1414,7 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
INIT_LIST_HEAD(&dlm->reco.node_data);
INIT_LIST_HEAD(&dlm->purge_list);
INIT_LIST_HEAD(&dlm->dlm_domain_handlers);
+ INIT_LIST_HEAD(&dlm->tracking_list);
dlm->reco.state = 0;
INIT_LIST_HEAD(&dlm->pending_asts);
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index d07a30a..d10fe48 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -642,6 +642,14 @@ static void dlm_lockres_release(struct kref *kref)
mlog(0, "destroying lockres %.*s\n", res->lockname.len,
res->lockname.name);
+ if (!list_empty(&res->tracking))
+ list_del_init(&res->tracking);
+ else {
+ mlog(ML_ERROR, "Resource %.*s not on the Tracking list\n",
+ res->lockname.len, res->lockname.name);
+ dlm_print_one_lock_resource(res);
+ }
+
if (!hlist_unhashed(&res->hash_node) ||
!list_empty(&res->granted) ||
!list_empty(&res->converting) ||
@@ -709,6 +717,7 @@ static void dlm_init_lockres(struct dlm_ctxt *dlm,
INIT_LIST_HEAD(&res->dirty);
INIT_LIST_HEAD(&res->recovering);
INIT_LIST_HEAD(&res->purge);
+ INIT_LIST_HEAD(&res->tracking);
atomic_set(&res->asts_reserved, 0);
res->migration_pending = 0;
res->inflight_locks = 0;
@@ -724,6 +733,8 @@ static void dlm_init_lockres(struct dlm_ctxt *dlm,
res->last_used = 0;
+ list_add_tail(&res->tracking, &dlm->tracking_list);
+
memset(res->lvb, 0, DLM_LVB_LEN);
memset(res->refmap, 0, sizeof(res->refmap));
}
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 06/18] ocfs2_dlm: Link all lockres' to a tracking list
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 06/18] ocfs2_dlm: Link all lockres' to a tracking list Sunil Mushran
@ 2008-02-28 16:32 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:32 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:50PM -0800, Sunil Mushran wrote:
> This patch links all the lockres' to a tracking list in dlm_ctxt.
> We will use this in the upcoming patch that will walk the entire
> list and to dump the lockres states to a debugfs file.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmcommon.h | 4 ++++
> fs/ocfs2/dlm/dlmdomain.c | 11 +++++++++++
> fs/ocfs2/dlm/dlmmaster.c | 11 +++++++++++
> 3 files changed, 26 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index eac1b3b..a3b22bf 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -101,6 +101,7 @@ struct dlm_ctxt
> struct list_head purge_list;
> struct list_head pending_asts;
> struct list_head pending_basts;
> + struct list_head tracking_list;
> unsigned int purge_count;
> spinlock_t spinlock;
> spinlock_t ast_lock;
> @@ -266,6 +267,9 @@ struct dlm_lock_resource
> struct list_head dirty;
> struct list_head recovering; // dlm_recovery_ctxt.resources list
>
> + /* Added during init and removed during release */
> + struct list_head tracking; /* dlm->tracking_list */
> +
> /* unused lock resources have their last_used stamped and are
> * put on a list for the dlm thread to run. */
> unsigned long last_used;
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index 6d02ef5..1d382f1 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -634,6 +634,7 @@ int dlm_shutting_down(struct dlm_ctxt *dlm)
> void dlm_unregister_domain(struct dlm_ctxt *dlm)
> {
> int leave = 0;
> + struct dlm_lock_resource *res;
>
> spin_lock(&dlm_domain_lock);
> BUG_ON(dlm->dlm_state != DLM_CTXT_JOINED);
> @@ -663,6 +664,15 @@ void dlm_unregister_domain(struct dlm_ctxt *dlm)
> msleep(500);
> mlog(0, "%s: more migration to do\n", dlm->name);
> }
> +
> + /* This list should be empty. If not, print remaining lockres */
> + if (!list_empty(&dlm->tracking_list)) {
> + mlog(ML_ERROR, "Following lockres' are still on the "
> + "tracking list:\n");
> + list_for_each_entry(res, &dlm->tracking_list, tracking)
> + dlm_print_one_lock_resource(res);
> + }
> +
> dlm_mark_domain_leaving(dlm);
> dlm_leave_domain(dlm);
> dlm_complete_dlm_shutdown(dlm);
> @@ -1404,6 +1414,7 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
> INIT_LIST_HEAD(&dlm->reco.node_data);
> INIT_LIST_HEAD(&dlm->purge_list);
> INIT_LIST_HEAD(&dlm->dlm_domain_handlers);
> + INIT_LIST_HEAD(&dlm->tracking_list);
> dlm->reco.state = 0;
>
> INIT_LIST_HEAD(&dlm->pending_asts);
> diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
> index d07a30a..d10fe48 100644
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -642,6 +642,14 @@ static void dlm_lockres_release(struct kref *kref)
> mlog(0, "destroying lockres %.*s\n", res->lockname.len,
> res->lockname.name);
>
> + if (!list_empty(&res->tracking))
> + list_del_init(&res->tracking);
> + else {
> + mlog(ML_ERROR, "Resource %.*s not on the Tracking list\n",
> + res->lockname.len, res->lockname.name);
> + dlm_print_one_lock_resource(res);
> + }
> +
> if (!hlist_unhashed(&res->hash_node) ||
> !list_empty(&res->granted) ||
> !list_empty(&res->converting) ||
> @@ -709,6 +717,7 @@ static void dlm_init_lockres(struct dlm_ctxt *dlm,
> INIT_LIST_HEAD(&res->dirty);
> INIT_LIST_HEAD(&res->recovering);
> INIT_LIST_HEAD(&res->purge);
> + INIT_LIST_HEAD(&res->tracking);
> atomic_set(&res->asts_reserved, 0);
> res->migration_pending = 0;
> res->inflight_locks = 0;
> @@ -724,6 +733,8 @@ static void dlm_init_lockres(struct dlm_ctxt *dlm,
>
> res->last_used = 0;
>
> + list_add_tail(&res->tracking, &dlm->tracking_list);
> +
> memset(res->lvb, 0, DLM_LVB_LEN);
> memset(res->refmap, 0, sizeof(res->refmap));
> }
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
Life's Little Instruction Book #222
"Think twice before burdening a friend with a secret."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 12/18] ocfs2_dlm: Dumps the purgelist into a debugfs file
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 06/18] ocfs2_dlm: Link all lockres' to a tracking list Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:53 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 10/18] ocfs2_dlm: Moves struct dlm_master_list_entry to dlmcommon.h Sunil Mushran
` (15 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch dumps all the lockres' on the purgelist it can fit in one page
into a debugfs file. Useful for debugging.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmdebug.c | 71 +++++++++++++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmdebug.h | 1 +
2 files changed, 72 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index 158b2e5..ffdc976 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -707,6 +707,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
#define DLM_DEBUGFS_DLM_STATE "dlm_state"
#define DLM_DEBUGFS_LOCKING_STATE "locking_state"
#define DLM_DEBUGFS_MLE_STATE "mle_state"
+#define DLM_DEBUGFS_PURGE_LIST "purge_list"
/* 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.
@@ -828,6 +829,63 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
}
/* end - util funcs */
+/* begin - purge list funcs */
+static int debug_purgelist_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
+{
+ struct dlm_lock_resource *res;
+ int out = 0;
+ unsigned long total = 0;
+
+ out += snprintf(db->buf + out, db->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 (db->len - out < 100)
+ continue;
+ spin_lock(&res->spinlock);
+ out += stringify_lockname(res->lockname.name,
+ res->lockname.len,
+ db->buf + out, db->len - out);
+ out += snprintf(db->buf + out, db->len - out, "\t%ld\n",
+ (jiffies - res->last_used)/HZ);
+ spin_unlock(&res->spinlock);
+ }
+ spin_unlock(&dlm->spinlock);
+
+ out += snprintf(db->buf + out, db->len - out,
+ "Total on list: %ld\n", total);
+
+ return out;
+}
+
+static int debug_purgelist_open(struct inode *inode, struct file *file)
+{
+ struct dlm_ctxt *dlm = inode->i_private;
+ struct debug_buffer *db;
+
+ db = debug_buffer_allocate();
+ if (!db)
+ goto bail;
+
+ db->len = debug_purgelist_print(dlm, db);
+
+ file->private_data = db;
+
+ return 0;
+bail:
+ return -ENOMEM;
+}
+
+static struct file_operations debug_purgelist_fops = {
+ .open = debug_purgelist_open,
+ .release = debug_buffer_release,
+ .read = debug_buffer_read,
+ .llseek = debug_buffer_llseek,
+};
+/* end - purge list funcs */
+
/* begin - debug mle funcs */
static int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
{
@@ -1339,6 +1397,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
goto bail;
}
+ /* for dumping lockres on the purge list */
+ dc->debug_purgelist_dentry =
+ debugfs_create_file(DLM_DEBUGFS_PURGE_LIST,
+ S_IFREG|S_IRUSR,
+ dlm->dlm_debugfs_subroot,
+ dlm, &debug_purgelist_fops);
+ if (!dc->debug_purgelist_dentry) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+
dlm_debug_get(dc);
return 0;
@@ -1352,6 +1421,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
if (dc) {
+ if (dc->debug_purgelist_dentry)
+ debugfs_remove(dc->debug_purgelist_dentry);
if (dc->debug_mle_dentry)
debugfs_remove(dc->debug_mle_dentry);
if (dc->debug_lockres_dentry)
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index c6b240f..ca7bc32 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -30,6 +30,7 @@ struct dlm_debug_ctxt {
struct dentry *debug_state_dentry;
struct dentry *debug_lockres_dentry;
struct dentry *debug_mle_dentry;
+ struct dentry *debug_purgelist_dentry;
};
struct debug_buffer
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 12/18] ocfs2_dlm: Dumps the purgelist into a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 12/18] ocfs2_dlm: Dumps the purgelist into a debugfs file Sunil Mushran
@ 2008-02-28 16:53 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:53 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:56PM -0800, Sunil Mushran wrote:
> This patch dumps all the lockres' on the purgelist it can fit in one page
> into a debugfs file. Useful for debugging.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Looks good modulo DEBUG_FS.
Joel
> ---
> fs/ocfs2/dlm/dlmdebug.c | 71 +++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 1 +
> 2 files changed, 72 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 158b2e5..ffdc976 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -707,6 +707,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
> #define DLM_DEBUGFS_DLM_STATE "dlm_state"
> #define DLM_DEBUGFS_LOCKING_STATE "locking_state"
> #define DLM_DEBUGFS_MLE_STATE "mle_state"
> +#define DLM_DEBUGFS_PURGE_LIST "purge_list"
>
> /* 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.
> @@ -828,6 +829,63 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
> }
> /* end - util funcs */
>
> +/* begin - purge list funcs */
> +static int debug_purgelist_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> +{
> + struct dlm_lock_resource *res;
> + int out = 0;
> + unsigned long total = 0;
> +
> + out += snprintf(db->buf + out, db->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 (db->len - out < 100)
> + continue;
> + spin_lock(&res->spinlock);
> + out += stringify_lockname(res->lockname.name,
> + res->lockname.len,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\t%ld\n",
> + (jiffies - res->last_used)/HZ);
> + spin_unlock(&res->spinlock);
> + }
> + spin_unlock(&dlm->spinlock);
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Total on list: %ld\n", total);
> +
> + return out;
> +}
> +
> +static int debug_purgelist_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + struct debug_buffer *db;
> +
> + db = debug_buffer_allocate();
> + if (!db)
> + goto bail;
> +
> + db->len = debug_purgelist_print(dlm, db);
> +
> + file->private_data = db;
> +
> + return 0;
> +bail:
> + return -ENOMEM;
> +}
> +
> +static struct file_operations debug_purgelist_fops = {
> + .open = debug_purgelist_open,
> + .release = debug_buffer_release,
> + .read = debug_buffer_read,
> + .llseek = debug_buffer_llseek,
> +};
> +/* end - purge list funcs */
> +
> /* begin - debug mle funcs */
> static int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
> {
> @@ -1339,6 +1397,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + /* for dumping lockres on the purge list */
> + dc->debug_purgelist_dentry =
> + debugfs_create_file(DLM_DEBUGFS_PURGE_LIST,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_purgelist_fops);
> + if (!dc->debug_purgelist_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> dlm_debug_get(dc);
> return 0;
>
> @@ -1352,6 +1421,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
>
> if (dc) {
> + if (dc->debug_purgelist_dentry)
> + debugfs_remove(dc->debug_purgelist_dentry);
> if (dc->debug_mle_dentry)
> debugfs_remove(dc->debug_mle_dentry);
> if (dc->debug_lockres_dentry)
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index c6b240f..ca7bc32 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -30,6 +30,7 @@ struct dlm_debug_ctxt {
> struct dentry *debug_state_dentry;
> struct dentry *debug_lockres_dentry;
> struct dentry *debug_mle_dentry;
> + struct dentry *debug_purgelist_dentry;
> };
>
> struct debug_buffer
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"The trouble with being punctual is that nobody's there to
appreciate it."
- Franklin P. Jones
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 10/18] ocfs2_dlm: Moves struct dlm_master_list_entry to dlmcommon.h
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 06/18] ocfs2_dlm: Link all lockres' to a tracking list Sunil Mushran
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 12/18] ocfs2_dlm: Dumps the purgelist into a debugfs file Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 05/18] ocfs2_dlm: Add missing dlm_lockres_put()s Sunil Mushran
` (14 subsequent siblings)
17 siblings, 0 replies; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch moves some mle related definitions from dlmmaster.c
to dlmcommon.h.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 37 +++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmmaster.c | 37 -------------------------------------
2 files changed, 37 insertions(+), 37 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index a2cfd61..41c8d90 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -49,6 +49,43 @@
/* Intended to make it easier for us to switch out hash functions */
#define dlm_lockid_hash(_n, _l) full_name_hash(_n, _l)
+enum dlm_mle_type {
+ DLM_MLE_BLOCK,
+ DLM_MLE_MASTER,
+ DLM_MLE_MIGRATION
+};
+
+struct dlm_lock_name
+{
+ u8 len;
+ u8 name[DLM_LOCKID_NAME_MAX];
+};
+
+struct dlm_master_list_entry
+{
+ struct list_head list;
+ struct list_head hb_events;
+ struct dlm_ctxt *dlm;
+ spinlock_t spinlock;
+ wait_queue_head_t wq;
+ atomic_t woken;
+ struct kref mle_refs;
+ int inuse;
+ unsigned long maybe_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
+ unsigned long vote_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
+ unsigned long response_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
+ unsigned long node_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
+ u8 master;
+ u8 new_master;
+ enum dlm_mle_type type;
+ struct o2hb_callback_func mle_hb_up;
+ struct o2hb_callback_func mle_hb_down;
+ union {
+ struct dlm_lock_resource *res;
+ struct dlm_lock_name name;
+ } u;
+};
+
enum dlm_ast_type {
DLM_AST = 0,
DLM_BAST,
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index d10fe48..c491b9e 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -52,43 +52,6 @@
#define MLOG_MASK_PREFIX (ML_DLM|ML_DLM_MASTER)
#include "cluster/masklog.h"
-enum dlm_mle_type {
- DLM_MLE_BLOCK,
- DLM_MLE_MASTER,
- DLM_MLE_MIGRATION
-};
-
-struct dlm_lock_name
-{
- u8 len;
- u8 name[DLM_LOCKID_NAME_MAX];
-};
-
-struct dlm_master_list_entry
-{
- struct list_head list;
- struct list_head hb_events;
- struct dlm_ctxt *dlm;
- spinlock_t spinlock;
- wait_queue_head_t wq;
- atomic_t woken;
- struct kref mle_refs;
- int inuse;
- unsigned long maybe_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
- unsigned long vote_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
- unsigned long response_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
- unsigned long node_map[BITS_TO_LONGS(O2NM_MAX_NODES)];
- u8 master;
- u8 new_master;
- enum dlm_mle_type type;
- struct o2hb_callback_func mle_hb_up;
- struct o2hb_callback_func mle_hb_down;
- union {
- struct dlm_lock_resource *res;
- struct dlm_lock_name name;
- } u;
-};
-
static void dlm_mle_node_down(struct dlm_ctxt *dlm,
struct dlm_master_list_entry *mle,
struct o2nm_node *node,
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 05/18] ocfs2_dlm: Add missing dlm_lockres_put()s
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (2 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 10/18] ocfs2_dlm: Moves struct dlm_master_list_entry to dlmcommon.h Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 14:50 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 15/18] ocfs2_dlm: Move dlm_print_one_mle() from dlmmaster.c to dlmdebug.c Sunil Mushran
` (13 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch adds few missing puts in dlm_master_request_handler().
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmmaster.c | 6 ++++++
1 files changed, 6 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index 8e3c40e..d07a30a 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -1718,7 +1718,13 @@ send_response:
if (ret < 0) {
mlog(ML_ERROR, "failed to dispatch assert master work\n");
response = DLM_MASTER_RESP_ERROR;
+ /* incase dlm_assert_master_worker() was not called */
+ dlm_lockres_put(res);
}
+ } else {
+ /* match the put in dlm_assert_master_worker() */
+ if (res)
+ dlm_lockres_put(res);
}
dlm_put(dlm);
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 05/18] ocfs2_dlm: Add missing dlm_lockres_put()s
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 05/18] ocfs2_dlm: Add missing dlm_lockres_put()s Sunil Mushran
@ 2008-02-28 14:50 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 14:50 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:49PM -0800, Sunil Mushran wrote:
> This patch adds few missing puts in dlm_master_request_handler().
dlm_master_request_handler() forgot to put a lockres when
dlm_assert_master_worker() failed or was skipped.
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -1718,7 +1718,13 @@ send_response:
> if (ret < 0) {
> mlog(ML_ERROR, "failed to dispatch assert master work\n");
> response = DLM_MASTER_RESP_ERROR;
> + /* incase dlm_assert_master_worker() was not called */
> + dlm_lockres_put(res);
> }
> + } else {
> + /* match the put in dlm_assert_master_worker() */
> + if (res)
> + dlm_lockres_put(res);
The put()s are correct, but I'd remove those comments and place
a comment above the whole if() block. The comments you have assume more
knowledge of the flow than is obvious.
+ /*
+ * __dlm_lookup_lockres() grabbed a reference to this lockres.
+ * The reference is released by dlm_assert_master_worker() under
+ * the call to dlm_dispatch_assert_master(). If
+ * dlm_assert_master_worker() isn't called, we drop it here.
+ */
if (dispatch_assert) {
Joel
--
Life's Little Instruction Book #252
"Take good care of those you love."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 15/18] ocfs2_dlm: Move dlm_print_one_mle() from dlmmaster.c to dlmdebug.c
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (3 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 05/18] ocfs2_dlm: Add missing dlm_lockres_put()s Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:55 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 18/18] ocfs2_dlm: Print message showing the recomaster Sunil Mushran
` (12 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch helps in consolidating debugging related functions in dlmdebug.c.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 1 -
fs/ocfs2/dlm/dlmdebug.c | 15 +++++++-
fs/ocfs2/dlm/dlmdebug.h | 2 +
fs/ocfs2/dlm/dlmmaster.c | 87 +---------------------------------------------
4 files changed, 17 insertions(+), 88 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index 1d05ebf..ba192c0 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -1006,7 +1006,6 @@ int dlm_drop_lockres_ref(struct dlm_ctxt *dlm,
void dlm_clean_master_list(struct dlm_ctxt *dlm,
u8 dead_node);
int dlm_lock_basts_flushed(struct dlm_ctxt *dlm, struct dlm_lock *lock);
-int dlm_dump_all_mles(const char __user *data, unsigned int len);
int __dlm_lockres_has_locks(struct dlm_lock_resource *res);
int __dlm_lockres_unused(struct dlm_lock_resource *res);
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index e8fa5a9..24d2f5c 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -46,6 +46,8 @@
static struct dentry *dlm_debugfs_root = NULL;
+int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len);
+
static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
{
int bit;
@@ -139,6 +141,17 @@ void dlm_print_one_lock(struct dlm_lock *lockid)
}
EXPORT_SYMBOL_GPL(dlm_print_one_lock);
+void dlm_print_one_mle(struct dlm_master_list_entry *mle)
+{
+ char *buf;
+
+ buf = (char *) get_zeroed_page(GFP_NOFS);
+ if (buf) {
+ dump_mle(mle, buf, PAGE_SIZE - 1);
+ free_page((unsigned long)buf);
+ }
+}
+
static const char *dlm_errnames[] = {
[DLM_NORMAL] = "DLM_NORMAL",
[DLM_GRANTED] = "DLM_GRANTED",
@@ -509,7 +522,7 @@ static struct file_operations debug_purgelist_fops = {
/* end - purge list funcs */
/* begin - debug mle funcs */
-static int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
+int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
{
int out = 0;
unsigned int namelen;
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index f6537ac..cf5ada9 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -57,4 +57,6 @@ void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
int dlm_create_debugfs_root(void);
void dlm_destroy_debugfs_root(void);
+void dlm_print_one_mle(struct dlm_master_list_entry *mle);
+
#endif
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index c491b9e..3d681fe 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -48,6 +48,7 @@
#include "dlmapi.h"
#include "dlmcommon.h"
#include "dlmdomain.h"
+#include "dlmdebug.h"
#define MLOG_MASK_PREFIX (ML_DLM|ML_DLM_MASTER)
#include "cluster/masklog.h"
@@ -90,92 +91,6 @@ static inline int dlm_mle_equal(struct dlm_ctxt *dlm,
return 1;
}
-#define dlm_print_nodemap(m) _dlm_print_nodemap(m,#m)
-static void _dlm_print_nodemap(unsigned long *map, const char *mapname)
-{
- int i;
- printk("%s=[ ", mapname);
- for (i=0; i<O2NM_MAX_NODES; i++)
- if (test_bit(i, map))
- printk("%d ", i);
- printk("]");
-}
-
-static void dlm_print_one_mle(struct dlm_master_list_entry *mle)
-{
- int refs;
- char *type;
- char attached;
- u8 master;
- unsigned int namelen;
- const char *name;
- struct kref *k;
- unsigned long *maybe = mle->maybe_map,
- *vote = mle->vote_map,
- *resp = mle->response_map,
- *node = mle->node_map;
-
- k = &mle->mle_refs;
- if (mle->type == DLM_MLE_BLOCK)
- type = "BLK";
- else if (mle->type == DLM_MLE_MASTER)
- type = "MAS";
- else
- type = "MIG";
- refs = atomic_read(&k->refcount);
- master = mle->master;
- attached = (list_empty(&mle->hb_events) ? 'N' : 'Y');
-
- if (mle->type != DLM_MLE_MASTER) {
- namelen = mle->u.name.len;
- name = mle->u.name.name;
- } else {
- namelen = mle->u.res->lockname.len;
- name = mle->u.res->lockname.name;
- }
-
- mlog(ML_NOTICE, "%.*s: %3s refs=%3d mas=%3u new=%3u evt=%c inuse=%d ",
- namelen, name, type, refs, master, mle->new_master, attached,
- mle->inuse);
- dlm_print_nodemap(maybe);
- printk(", ");
- dlm_print_nodemap(vote);
- printk(", ");
- dlm_print_nodemap(resp);
- printk(", ");
- dlm_print_nodemap(node);
- printk(", ");
- printk("\n");
-}
-
-
-/* Code here is included but defined out as it aids debugging */
-
-static void dlm_dump_mles(struct dlm_ctxt *dlm)
-{
- struct dlm_master_list_entry *mle;
-
- mlog(ML_NOTICE, "dumping all mles for domain %s:\n", dlm->name);
- spin_lock(&dlm->master_lock);
- list_for_each_entry(mle, &dlm->master_list, list)
- dlm_print_one_mle(mle);
- spin_unlock(&dlm->master_lock);
-}
-
-int dlm_dump_all_mles(const char __user *data, unsigned int len)
-{
- struct dlm_ctxt *dlm;
-
- spin_lock(&dlm_domain_lock);
- list_for_each_entry(dlm, &dlm_domains, list) {
- mlog(ML_NOTICE, "found dlm: %p, name=%s\n", dlm, dlm->name);
- dlm_dump_mles(dlm);
- }
- spin_unlock(&dlm_domain_lock);
- return len;
-}
-EXPORT_SYMBOL_GPL(dlm_dump_all_mles);
-
/* dlm slab caches */
static struct kmem_cache *dlm_lockres_cache = NULL;
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 15/18] ocfs2_dlm: Move dlm_print_one_mle() from dlmmaster.c to dlmdebug.c
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 15/18] ocfs2_dlm: Move dlm_print_one_mle() from dlmmaster.c to dlmdebug.c Sunil Mushran
@ 2008-02-28 16:55 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:55 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:59PM -0800, Sunil Mushran wrote:
> This patch helps in consolidating debugging related functions in dlmdebug.c.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmcommon.h | 1 -
> fs/ocfs2/dlm/dlmdebug.c | 15 +++++++-
> fs/ocfs2/dlm/dlmdebug.h | 2 +
> fs/ocfs2/dlm/dlmmaster.c | 87 +---------------------------------------------
> 4 files changed, 17 insertions(+), 88 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index 1d05ebf..ba192c0 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -1006,7 +1006,6 @@ int dlm_drop_lockres_ref(struct dlm_ctxt *dlm,
> void dlm_clean_master_list(struct dlm_ctxt *dlm,
> u8 dead_node);
> int dlm_lock_basts_flushed(struct dlm_ctxt *dlm, struct dlm_lock *lock);
> -int dlm_dump_all_mles(const char __user *data, unsigned int len);
> int __dlm_lockres_has_locks(struct dlm_lock_resource *res);
> int __dlm_lockres_unused(struct dlm_lock_resource *res);
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index e8fa5a9..24d2f5c 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -46,6 +46,8 @@
>
> static struct dentry *dlm_debugfs_root = NULL;
>
> +int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len);
> +
> static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
> {
> int bit;
> @@ -139,6 +141,17 @@ void dlm_print_one_lock(struct dlm_lock *lockid)
> }
> EXPORT_SYMBOL_GPL(dlm_print_one_lock);
>
> +void dlm_print_one_mle(struct dlm_master_list_entry *mle)
> +{
> + char *buf;
> +
> + buf = (char *) get_zeroed_page(GFP_NOFS);
> + if (buf) {
> + dump_mle(mle, buf, PAGE_SIZE - 1);
> + free_page((unsigned long)buf);
> + }
> +}
> +
> static const char *dlm_errnames[] = {
> [DLM_NORMAL] = "DLM_NORMAL",
> [DLM_GRANTED] = "DLM_GRANTED",
> @@ -509,7 +522,7 @@ static struct file_operations debug_purgelist_fops = {
> /* end - purge list funcs */
>
> /* begin - debug mle funcs */
> -static int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
> +int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
> {
> int out = 0;
> unsigned int namelen;
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index f6537ac..cf5ada9 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -57,4 +57,6 @@ void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
> int dlm_create_debugfs_root(void);
> void dlm_destroy_debugfs_root(void);
>
> +void dlm_print_one_mle(struct dlm_master_list_entry *mle);
> +
> #endif
> diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
> index c491b9e..3d681fe 100644
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -48,6 +48,7 @@
> #include "dlmapi.h"
> #include "dlmcommon.h"
> #include "dlmdomain.h"
> +#include "dlmdebug.h"
>
> #define MLOG_MASK_PREFIX (ML_DLM|ML_DLM_MASTER)
> #include "cluster/masklog.h"
> @@ -90,92 +91,6 @@ static inline int dlm_mle_equal(struct dlm_ctxt *dlm,
> return 1;
> }
>
> -#define dlm_print_nodemap(m) _dlm_print_nodemap(m,#m)
> -static void _dlm_print_nodemap(unsigned long *map, const char *mapname)
> -{
> - int i;
> - printk("%s=[ ", mapname);
> - for (i=0; i<O2NM_MAX_NODES; i++)
> - if (test_bit(i, map))
> - printk("%d ", i);
> - printk("]");
> -}
> -
> -static void dlm_print_one_mle(struct dlm_master_list_entry *mle)
> -{
> - int refs;
> - char *type;
> - char attached;
> - u8 master;
> - unsigned int namelen;
> - const char *name;
> - struct kref *k;
> - unsigned long *maybe = mle->maybe_map,
> - *vote = mle->vote_map,
> - *resp = mle->response_map,
> - *node = mle->node_map;
> -
> - k = &mle->mle_refs;
> - if (mle->type == DLM_MLE_BLOCK)
> - type = "BLK";
> - else if (mle->type == DLM_MLE_MASTER)
> - type = "MAS";
> - else
> - type = "MIG";
> - refs = atomic_read(&k->refcount);
> - master = mle->master;
> - attached = (list_empty(&mle->hb_events) ? 'N' : 'Y');
> -
> - if (mle->type != DLM_MLE_MASTER) {
> - namelen = mle->u.name.len;
> - name = mle->u.name.name;
> - } else {
> - namelen = mle->u.res->lockname.len;
> - name = mle->u.res->lockname.name;
> - }
> -
> - mlog(ML_NOTICE, "%.*s: %3s refs=%3d mas=%3u new=%3u evt=%c inuse=%d ",
> - namelen, name, type, refs, master, mle->new_master, attached,
> - mle->inuse);
> - dlm_print_nodemap(maybe);
> - printk(", ");
> - dlm_print_nodemap(vote);
> - printk(", ");
> - dlm_print_nodemap(resp);
> - printk(", ");
> - dlm_print_nodemap(node);
> - printk(", ");
> - printk("\n");
> -}
> -
> -
> -/* Code here is included but defined out as it aids debugging */
> -
> -static void dlm_dump_mles(struct dlm_ctxt *dlm)
> -{
> - struct dlm_master_list_entry *mle;
> -
> - mlog(ML_NOTICE, "dumping all mles for domain %s:\n", dlm->name);
> - spin_lock(&dlm->master_lock);
> - list_for_each_entry(mle, &dlm->master_list, list)
> - dlm_print_one_mle(mle);
> - spin_unlock(&dlm->master_lock);
> -}
> -
> -int dlm_dump_all_mles(const char __user *data, unsigned int len)
> -{
> - struct dlm_ctxt *dlm;
> -
> - spin_lock(&dlm_domain_lock);
> - list_for_each_entry(dlm, &dlm_domains, list) {
> - mlog(ML_NOTICE, "found dlm: %p, name=%s\n", dlm, dlm->name);
> - dlm_dump_mles(dlm);
> - }
> - spin_unlock(&dlm_domain_lock);
> - return len;
> -}
> -EXPORT_SYMBOL_GPL(dlm_dump_all_mles);
> -
>
> /* dlm slab caches */
> static struct kmem_cache *dlm_lockres_cache = NULL;
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"War doesn't determine who's right; war determines who's left."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 18/18] ocfs2_dlm: Print message showing the recomaster
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (4 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 15/18] ocfs2_dlm: Move dlm_print_one_mle() from dlmmaster.c to dlmdebug.c Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:57 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 01/18] ocfs2_dlm: Rename slabcache dlm_mle_cache to o2dlm_mle Sunil Mushran
` (11 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
Knowing the dlm recovery master helps in debugging recovery
issues. This patch printks the message on the recomaster node.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmrecovery.c | 6 +++---
1 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c
index 487c50e..fae0543 100644
--- a/fs/ocfs2/dlm/dlmrecovery.c
+++ b/fs/ocfs2/dlm/dlmrecovery.c
@@ -517,9 +517,9 @@ static int dlm_do_recovery(struct dlm_ctxt *dlm)
return 0;
master_here:
- mlog(0, "(%d) mastering recovery of %s:%u here(this=%u)!\n",
- dlm->dlm_reco_thread_task->pid,
- dlm->name, dlm->reco.dead_node, dlm->node_num);
+ mlog(ML_NOTICE, "(%d) Node %u is the Recovery Master for the Dead Node "
+ "%u for Domain %s\n", dlm->dlm_reco_thread_task->pid,
+ dlm->node_num, dlm->reco.dead_node, dlm->name);
status = dlm_remaster_locks(dlm, dlm->reco.dead_node);
if (status < 0) {
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 18/18] ocfs2_dlm: Print message showing the recomaster
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 18/18] ocfs2_dlm: Print message showing the recomaster Sunil Mushran
@ 2008-02-28 16:57 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:57 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:21:02PM -0800, Sunil Mushran wrote:
> Knowing the dlm recovery master helps in debugging recovery
> issues. This patch printks the message on the recomaster node.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmrecovery.c | 6 +++---
> 1 files changed, 3 insertions(+), 3 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c
> index 487c50e..fae0543 100644
> --- a/fs/ocfs2/dlm/dlmrecovery.c
> +++ b/fs/ocfs2/dlm/dlmrecovery.c
> @@ -517,9 +517,9 @@ static int dlm_do_recovery(struct dlm_ctxt *dlm)
> return 0;
>
> master_here:
> - mlog(0, "(%d) mastering recovery of %s:%u here(this=%u)!\n",
> - dlm->dlm_reco_thread_task->pid,
> - dlm->name, dlm->reco.dead_node, dlm->node_num);
> + mlog(ML_NOTICE, "(%d) Node %u is the Recovery Master for the Dead Node "
> + "%u for Domain %s\n", dlm->dlm_reco_thread_task->pid,
> + dlm->node_num, dlm->reco.dead_node, dlm->name);
>
> status = dlm_remaster_locks(dlm, dlm->reco.dead_node);
> if (status < 0) {
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"What do you take me for, an idiot?"
- General Charles de Gaulle, when a journalist asked him
if he was happy.
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 01/18] ocfs2_dlm: Rename slabcache dlm_mle_cache to o2dlm_mle
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (5 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 18/18] ocfs2_dlm: Print message showing the recomaster Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 14:12 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks Sunil Mushran
` (10 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch renames dlm_mle_slabcache to prevent namespace
clashes with fs/dlm.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmdomain.c | 4 +++-
fs/ocfs2/dlm/dlmmaster.c | 2 +-
2 files changed, 4 insertions(+), 2 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index 1d854d5..502712b 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -1648,8 +1648,10 @@ static int __init dlm_init(void)
dlm_print_version();
status = dlm_init_mle_cache();
- if (status)
+ if (status) {
+ mlog(ML_ERROR, "Could not create o2dlm_mle slabcache\n");
return -1;
+ }
status = dlm_register_net_handlers();
if (status) {
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index 42ea5af..cc4e624 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -506,7 +506,7 @@ static void dlm_mle_node_up(struct dlm_ctxt *dlm,
int dlm_init_mle_cache(void)
{
- dlm_mle_cache = kapi_kmem_cache_create("dlm_mle_cache",
+ dlm_mle_cache = kapi_kmem_cache_create("o2dlm_mle",
sizeof(struct dlm_master_list_entry),
0, SLAB_HWCACHE_ALIGN,
NULL);
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 01/18] ocfs2_dlm: Rename slabcache dlm_mle_cache to o2dlm_mle
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 01/18] ocfs2_dlm: Rename slabcache dlm_mle_cache to o2dlm_mle Sunil Mushran
@ 2008-02-28 14:12 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 14:12 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:45PM -0800, Sunil Mushran wrote:
> This patch renames dlm_mle_slabcache to prevent namespace
> clashes with fs/dlm.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmdomain.c | 4 +++-
> fs/ocfs2/dlm/dlmmaster.c | 2 +-
> 2 files changed, 4 insertions(+), 2 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index 1d854d5..502712b 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -1648,8 +1648,10 @@ static int __init dlm_init(void)
> dlm_print_version();
>
> status = dlm_init_mle_cache();
> - if (status)
> + if (status) {
> + mlog(ML_ERROR, "Could not create o2dlm_mle slabcache\n");
> return -1;
> + }
>
> status = dlm_register_net_handlers();
> if (status) {
> diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
> index 42ea5af..cc4e624 100644
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -506,7 +506,7 @@ static void dlm_mle_node_up(struct dlm_ctxt *dlm,
>
> int dlm_init_mle_cache(void)
> {
> - dlm_mle_cache = kapi_kmem_cache_create("dlm_mle_cache",
> + dlm_mle_cache = kapi_kmem_cache_create("o2dlm_mle",
> sizeof(struct dlm_master_list_entry),
> 0, SLAB_HWCACHE_ALIGN,
> NULL);
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"And yet I find,
And yet I find repeating in my head.
If I can't be my own,
I'd feel better dead."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (6 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 01/18] ocfs2_dlm: Rename slabcache dlm_mle_cache to o2dlm_mle Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 14:37 ` Joel Becker
2008-02-28 17:09 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 04/18] ocfs2_dlm: Add missing dlm_lockres_put()s in migration path Sunil Mushran
` (9 subsequent siblings)
17 siblings, 2 replies; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch makes the o2dlm allocate memory for lockres, lockname and lock
structures from slabcaches rather than kmalloc. This allows us to not only
make these allocs more efficient but also allows us to track the memory being
consumed by these structures.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 10 +++++++
fs/ocfs2/dlm/dlmdomain.c | 33 ++++++++++++++++++++---
fs/ocfs2/dlm/dlmlock.c | 23 +++++++++++++++-
fs/ocfs2/dlm/dlmmaster.c | 65 +++++++++++++++++++++++++++++++++++++--------
4 files changed, 113 insertions(+), 18 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index f3afb15..041ec68 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -944,9 +944,19 @@ static inline void __dlm_wait_on_lockres(struct dlm_lock_resource *res)
DLM_LOCK_RES_MIGRATING));
}
+/* create/destroy slab caches */
+int dlm_init_lockres_cache(void);
+void dlm_destroy_lockres_cache(void);
+
+int dlm_init_lockname_cache(void);
+void dlm_destroy_lockname_cache(void);
+
+int dlm_init_lock_cache(void);
+void dlm_destroy_lock_cache(void);
int dlm_init_mle_cache(void);
void dlm_destroy_mle_cache(void);
+
void dlm_hb_event_notify_attached(struct dlm_ctxt *dlm, int idx, int node_up);
int dlm_drop_lockres_ref(struct dlm_ctxt *dlm,
struct dlm_lock_resource *res);
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index 502712b..6d02ef5 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -1650,24 +1650,49 @@ static int __init dlm_init(void)
status = dlm_init_mle_cache();
if (status) {
mlog(ML_ERROR, "Could not create o2dlm_mle slabcache\n");
- return -1;
+ goto error;
}
- status = dlm_register_net_handlers();
+ status = dlm_init_lockres_cache();
+ if (status) {
+ mlog(ML_ERROR, "Could not create o2dlm_lockres slabcache\n");
+ goto error;
+ }
+
+ status = dlm_init_lockname_cache();
if (status) {
- dlm_destroy_mle_cache();
- return -1;
+ mlog(ML_ERROR, "Could not create o2dlm_lockname slabcache\n");
+ goto error;
}
+ status = dlm_init_lock_cache();
+ if (status) {
+ mlog(ML_ERROR, "Could not create o2dlm_lock slabcache\n");
+ goto error;
+ }
+
+ status = dlm_register_net_handlers();
+ if (status)
+ goto error;
+
dlm_init_proc();
return 0;
+error:
+ dlm_destroy_lock_cache();
+ dlm_destroy_lockname_cache();
+ dlm_destroy_lockres_cache();
+ dlm_destroy_mle_cache();
+ return -1;
}
static void __exit dlm_exit (void)
{
dlm_remove_proc();
dlm_unregister_net_handlers();
+ dlm_destroy_lock_cache();
+ dlm_destroy_lockname_cache();
+ dlm_destroy_lockres_cache();
dlm_destroy_mle_cache();
}
diff --git a/fs/ocfs2/dlm/dlmlock.c b/fs/ocfs2/dlm/dlmlock.c
index 52578d9..ea393b6 100644
--- a/fs/ocfs2/dlm/dlmlock.c
+++ b/fs/ocfs2/dlm/dlmlock.c
@@ -53,6 +53,8 @@
#define MLOG_MASK_PREFIX ML_DLM
#include "cluster/masklog.h"
+static struct kmem_cache *dlm_lock_cache = NULL;
+
static DEFINE_SPINLOCK(dlm_cookie_lock);
static u64 dlm_next_cookie = 1;
@@ -64,6 +66,22 @@ static void dlm_init_lock(struct dlm_lock *newlock, int type,
static void dlm_lock_release(struct kref *kref);
static void dlm_lock_detach_lockres(struct dlm_lock *lock);
+int dlm_init_lock_cache(void)
+{
+ dlm_lock_cache = kapi_kmem_cache_create("o2dlm_lock",
+ sizeof(struct dlm_lock),
+ 0, SLAB_HWCACHE_ALIGN, NULL);
+ if (dlm_lock_cache == NULL)
+ return -ENOMEM;
+ return 0;
+}
+
+void dlm_destroy_lock_cache(void)
+{
+ if (dlm_lock_cache)
+ kmem_cache_destroy(dlm_lock_cache);
+}
+
/* Tell us whether we can grant a new lock request.
* locking:
* caller needs: res->spinlock
@@ -353,7 +371,7 @@ static void dlm_lock_release(struct kref *kref)
mlog(0, "freeing kernel-allocated lksb\n");
kfree(lock->lksb);
}
- kfree(lock);
+ kmem_cache_free(dlm_lock_cache, lock);
}
/* associate a lock with it's lockres, getting a ref on the lockres */
@@ -412,9 +430,10 @@ struct dlm_lock * dlm_new_lock(int type, u8 node, u64 cookie,
struct dlm_lock *lock;
int kernel_allocated = 0;
- lock = kzalloc(sizeof(*lock), GFP_NOFS);
+ lock = (struct dlm_lock *) kmem_cache_alloc(dlm_lock_cache, GFP_NOFS);
if (!lock)
return NULL;
+ memset(lock, 0, sizeof(struct dlm_lock));
if (!lksb) {
/* zero memory only if kernel-allocated */
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index cc4e624..939b863 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -214,8 +214,9 @@ int dlm_dump_all_mles(const char __user *data, unsigned int len)
EXPORT_SYMBOL_GPL(dlm_dump_all_mles);
-
-
+/* dlm slab caches */
+static struct kmem_cache *dlm_lockres_cache = NULL;
+static struct kmem_cache *dlm_lockname_cache = NULL;
static struct kmem_cache *dlm_mle_cache = NULL;
@@ -559,6 +560,38 @@ static void dlm_mle_release(struct kref *kref)
* LOCK RESOURCE FUNCTIONS
*/
+int dlm_init_lockres_cache(void)
+{
+ dlm_lockres_cache = kapi_kmem_cache_create("o2dlm_lockres",
+ sizeof(struct dlm_lock_resource), 0,
+ SLAB_HWCACHE_ALIGN, NULL);
+ if (dlm_lockres_cache == NULL)
+ return -ENOMEM;
+ return 0;
+}
+
+void dlm_destroy_lockres_cache(void)
+{
+ if (dlm_lockres_cache)
+ kmem_cache_destroy(dlm_lockres_cache);
+}
+
+int dlm_init_lockname_cache(void)
+{
+ dlm_lockname_cache = kapi_kmem_cache_create("o2dlm_lockname",
+ DLM_LOCKID_NAME_MAX, 0,
+ SLAB_HWCACHE_ALIGN, NULL);
+ if (dlm_lockname_cache == NULL)
+ return -ENOMEM;
+ return 0;
+}
+
+void dlm_destroy_lockname_cache(void)
+{
+ if (dlm_lockname_cache)
+ kmem_cache_destroy(dlm_lockname_cache);
+}
+
static void dlm_set_lockres_owner(struct dlm_ctxt *dlm,
struct dlm_lock_resource *res,
u8 owner)
@@ -641,9 +674,9 @@ static void dlm_lockres_release(struct kref *kref)
BUG_ON(!list_empty(&res->recovering));
BUG_ON(!list_empty(&res->purge));
- kfree(res->lockname.name);
+ kmem_cache_free(dlm_lockname_cache, (void *)res->lockname.name);
- kfree(res);
+ kmem_cache_free(dlm_lockres_cache, res);
}
void dlm_lockres_put(struct dlm_lock_resource *res)
@@ -699,20 +732,28 @@ struct dlm_lock_resource *dlm_new_lockres(struct dlm_ctxt *dlm,
const char *name,
unsigned int namelen)
{
- struct dlm_lock_resource *res;
+ struct dlm_lock_resource *res = NULL;
- res = kmalloc(sizeof(struct dlm_lock_resource), GFP_NOFS);
+ res = (struct dlm_lock_resource *)
+ kmem_cache_alloc(dlm_lockres_cache, GFP_NOFS);
if (!res)
- return NULL;
+ goto error;
- res->lockname.name = kmalloc(namelen, GFP_NOFS);
- if (!res->lockname.name) {
- kfree(res);
- return NULL;
- }
+ res->lockname.name = (char *)
+ kmem_cache_alloc(dlm_lockname_cache, GFP_NOFS);
+ if (!res->lockname.name)
+ goto error;
dlm_init_lockres(dlm, res, name, namelen);
return res;
+
+error:
+ if (res && res->lockname.name)
+ kmem_cache_free(dlm_lockname_cache, (void *)res->lockname.name);
+
+ if (res)
+ kmem_cache_free(dlm_lockres_cache, res);
+ return NULL;
}
void __dlm_lockres_grab_inflight_ref(struct dlm_ctxt *dlm,
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks Sunil Mushran
@ 2008-02-28 14:37 ` Joel Becker
2008-02-28 17:09 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 14:37 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:46PM -0800, Sunil Mushran wrote:
> This patch makes the o2dlm allocate memory for lockres, lockname and lock
> structures from slabcaches rather than kmalloc. This allows us to not only
> make these allocs more efficient but also allows us to track the memory being
> consumed by these structures.
>
...
> +/* create/destroy slab caches */
> +int dlm_init_lockres_cache(void);
> +void dlm_destroy_lockres_cache(void);
> +
> +int dlm_init_lockname_cache(void);
> +void dlm_destroy_lockname_cache(void);
Why not have one dlm_init_master_caches()? These two are in the
same file.
> - lock = kzalloc(sizeof(*lock), GFP_NOFS);
> + lock = (struct dlm_lock *) kmem_cache_alloc(dlm_lock_cache, GFP_NOFS);
> if (!lock)
> return NULL;
> + memset(lock, 0, sizeof(struct dlm_lock));
Probably want to use kmem_cache_zalloc().
Joel
--
Life's Little Instruction Book #444
"Never underestimate the power of a kind word or deed."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks Sunil Mushran
2008-02-28 14:37 ` Joel Becker
@ 2008-02-28 17:09 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 17:09 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:46PM -0800, Sunil Mushran wrote:
> This patch makes the o2dlm allocate memory for lockres, lockname and lock
> structures from slabcaches rather than kmalloc. This allows us to not only
> make these allocs more efficient but also allows us to track the memory being
> consumed by these structures.
Please run through checkpatch.pl.
Joel
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
> ---
> fs/ocfs2/dlm/dlmcommon.h | 10 +++++++
> fs/ocfs2/dlm/dlmdomain.c | 33 ++++++++++++++++++++---
> fs/ocfs2/dlm/dlmlock.c | 23 +++++++++++++++-
> fs/ocfs2/dlm/dlmmaster.c | 65 +++++++++++++++++++++++++++++++++++++--------
> 4 files changed, 113 insertions(+), 18 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index f3afb15..041ec68 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -944,9 +944,19 @@ static inline void __dlm_wait_on_lockres(struct dlm_lock_resource *res)
> DLM_LOCK_RES_MIGRATING));
> }
>
> +/* create/destroy slab caches */
> +int dlm_init_lockres_cache(void);
> +void dlm_destroy_lockres_cache(void);
> +
> +int dlm_init_lockname_cache(void);
> +void dlm_destroy_lockname_cache(void);
> +
> +int dlm_init_lock_cache(void);
> +void dlm_destroy_lock_cache(void);
>
> int dlm_init_mle_cache(void);
> void dlm_destroy_mle_cache(void);
> +
> void dlm_hb_event_notify_attached(struct dlm_ctxt *dlm, int idx, int node_up);
> int dlm_drop_lockres_ref(struct dlm_ctxt *dlm,
> struct dlm_lock_resource *res);
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index 502712b..6d02ef5 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -1650,24 +1650,49 @@ static int __init dlm_init(void)
> status = dlm_init_mle_cache();
> if (status) {
> mlog(ML_ERROR, "Could not create o2dlm_mle slabcache\n");
> - return -1;
> + goto error;
> }
>
> - status = dlm_register_net_handlers();
> + status = dlm_init_lockres_cache();
> + if (status) {
> + mlog(ML_ERROR, "Could not create o2dlm_lockres slabcache\n");
> + goto error;
> + }
> +
> + status = dlm_init_lockname_cache();
> if (status) {
> - dlm_destroy_mle_cache();
> - return -1;
> + mlog(ML_ERROR, "Could not create o2dlm_lockname slabcache\n");
> + goto error;
> }
>
> + status = dlm_init_lock_cache();
> + if (status) {
> + mlog(ML_ERROR, "Could not create o2dlm_lock slabcache\n");
> + goto error;
> + }
> +
> + status = dlm_register_net_handlers();
> + if (status)
> + goto error;
> +
> dlm_init_proc();
>
> return 0;
> +error:
> + dlm_destroy_lock_cache();
> + dlm_destroy_lockname_cache();
> + dlm_destroy_lockres_cache();
> + dlm_destroy_mle_cache();
> + return -1;
> }
>
> static void __exit dlm_exit (void)
> {
> dlm_remove_proc();
> dlm_unregister_net_handlers();
> + dlm_destroy_lock_cache();
> + dlm_destroy_lockname_cache();
> + dlm_destroy_lockres_cache();
> dlm_destroy_mle_cache();
> }
>
> diff --git a/fs/ocfs2/dlm/dlmlock.c b/fs/ocfs2/dlm/dlmlock.c
> index 52578d9..ea393b6 100644
> --- a/fs/ocfs2/dlm/dlmlock.c
> +++ b/fs/ocfs2/dlm/dlmlock.c
> @@ -53,6 +53,8 @@
> #define MLOG_MASK_PREFIX ML_DLM
> #include "cluster/masklog.h"
>
> +static struct kmem_cache *dlm_lock_cache = NULL;
> +
> static DEFINE_SPINLOCK(dlm_cookie_lock);
> static u64 dlm_next_cookie = 1;
>
> @@ -64,6 +66,22 @@ static void dlm_init_lock(struct dlm_lock *newlock, int type,
> static void dlm_lock_release(struct kref *kref);
> static void dlm_lock_detach_lockres(struct dlm_lock *lock);
>
> +int dlm_init_lock_cache(void)
> +{
> + dlm_lock_cache = kapi_kmem_cache_create("o2dlm_lock",
> + sizeof(struct dlm_lock),
> + 0, SLAB_HWCACHE_ALIGN, NULL);
> + if (dlm_lock_cache == NULL)
> + return -ENOMEM;
> + return 0;
> +}
> +
> +void dlm_destroy_lock_cache(void)
> +{
> + if (dlm_lock_cache)
> + kmem_cache_destroy(dlm_lock_cache);
> +}
> +
> /* Tell us whether we can grant a new lock request.
> * locking:
> * caller needs: res->spinlock
> @@ -353,7 +371,7 @@ static void dlm_lock_release(struct kref *kref)
> mlog(0, "freeing kernel-allocated lksb\n");
> kfree(lock->lksb);
> }
> - kfree(lock);
> + kmem_cache_free(dlm_lock_cache, lock);
> }
>
> /* associate a lock with it's lockres, getting a ref on the lockres */
> @@ -412,9 +430,10 @@ struct dlm_lock * dlm_new_lock(int type, u8 node, u64 cookie,
> struct dlm_lock *lock;
> int kernel_allocated = 0;
>
> - lock = kzalloc(sizeof(*lock), GFP_NOFS);
> + lock = (struct dlm_lock *) kmem_cache_alloc(dlm_lock_cache, GFP_NOFS);
> if (!lock)
> return NULL;
> + memset(lock, 0, sizeof(struct dlm_lock));
>
> if (!lksb) {
> /* zero memory only if kernel-allocated */
> diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
> index cc4e624..939b863 100644
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -214,8 +214,9 @@ int dlm_dump_all_mles(const char __user *data, unsigned int len)
> EXPORT_SYMBOL_GPL(dlm_dump_all_mles);
>
>
> -
> -
> +/* dlm slab caches */
> +static struct kmem_cache *dlm_lockres_cache = NULL;
> +static struct kmem_cache *dlm_lockname_cache = NULL;
> static struct kmem_cache *dlm_mle_cache = NULL;
>
>
> @@ -559,6 +560,38 @@ static void dlm_mle_release(struct kref *kref)
> * LOCK RESOURCE FUNCTIONS
> */
>
> +int dlm_init_lockres_cache(void)
> +{
> + dlm_lockres_cache = kapi_kmem_cache_create("o2dlm_lockres",
> + sizeof(struct dlm_lock_resource), 0,
> + SLAB_HWCACHE_ALIGN, NULL);
> + if (dlm_lockres_cache == NULL)
> + return -ENOMEM;
> + return 0;
> +}
> +
> +void dlm_destroy_lockres_cache(void)
> +{
> + if (dlm_lockres_cache)
> + kmem_cache_destroy(dlm_lockres_cache);
> +}
> +
> +int dlm_init_lockname_cache(void)
> +{
> + dlm_lockname_cache = kapi_kmem_cache_create("o2dlm_lockname",
> + DLM_LOCKID_NAME_MAX, 0,
> + SLAB_HWCACHE_ALIGN, NULL);
> + if (dlm_lockname_cache == NULL)
> + return -ENOMEM;
> + return 0;
> +}
> +
> +void dlm_destroy_lockname_cache(void)
> +{
> + if (dlm_lockname_cache)
> + kmem_cache_destroy(dlm_lockname_cache);
> +}
> +
> static void dlm_set_lockres_owner(struct dlm_ctxt *dlm,
> struct dlm_lock_resource *res,
> u8 owner)
> @@ -641,9 +674,9 @@ static void dlm_lockres_release(struct kref *kref)
> BUG_ON(!list_empty(&res->recovering));
> BUG_ON(!list_empty(&res->purge));
>
> - kfree(res->lockname.name);
> + kmem_cache_free(dlm_lockname_cache, (void *)res->lockname.name);
>
> - kfree(res);
> + kmem_cache_free(dlm_lockres_cache, res);
> }
>
> void dlm_lockres_put(struct dlm_lock_resource *res)
> @@ -699,20 +732,28 @@ struct dlm_lock_resource *dlm_new_lockres(struct dlm_ctxt *dlm,
> const char *name,
> unsigned int namelen)
> {
> - struct dlm_lock_resource *res;
> + struct dlm_lock_resource *res = NULL;
>
> - res = kmalloc(sizeof(struct dlm_lock_resource), GFP_NOFS);
> + res = (struct dlm_lock_resource *)
> + kmem_cache_alloc(dlm_lockres_cache, GFP_NOFS);
> if (!res)
> - return NULL;
> + goto error;
>
> - res->lockname.name = kmalloc(namelen, GFP_NOFS);
> - if (!res->lockname.name) {
> - kfree(res);
> - return NULL;
> - }
> + res->lockname.name = (char *)
> + kmem_cache_alloc(dlm_lockname_cache, GFP_NOFS);
> + if (!res->lockname.name)
> + goto error;
>
> dlm_init_lockres(dlm, res, name, namelen);
> return res;
> +
> +error:
> + if (res && res->lockname.name)
> + kmem_cache_free(dlm_lockname_cache, (void *)res->lockname.name);
> +
> + if (res)
> + kmem_cache_free(dlm_lockres_cache, res);
> + return NULL;
> }
>
> void __dlm_lockres_grab_inflight_ref(struct dlm_ctxt *dlm,
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Sometimes one pays most for the things one gets for nothing."
- Albert Einstein
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 04/18] ocfs2_dlm: Add missing dlm_lockres_put()s in migration path
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (7 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 02/18] ocfs2_dlm: Creates slabcaches for the lockres' and the locks Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 14:41 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs Sunil Mushran
` (8 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
The inline comments explain the missing puts in the lockres
migration paths.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 1 +
fs/ocfs2/dlm/dlmrecovery.c | 41 +++++++++++++++++++++++++++++++++++------
2 files changed, 36 insertions(+), 6 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index 041ec68..eac1b3b 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -172,6 +172,7 @@ struct dlm_mig_lockres_priv
{
struct dlm_lock_resource *lockres;
u8 real_master;
+ u8 extra_ref;
};
struct dlm_assert_master_priv
diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c
index 455dc72..487c50e 100644
--- a/fs/ocfs2/dlm/dlmrecovery.c
+++ b/fs/ocfs2/dlm/dlmrecovery.c
@@ -1325,6 +1325,7 @@ int dlm_mig_lockres_handler(struct o2net_msg *msg, u32 len, void *data,
(struct dlm_migratable_lockres *)msg->buf;
int ret = 0;
u8 real_master;
+ u8 extra_refs = 0;
char *buf = NULL;
struct dlm_work_item *item = NULL;
struct dlm_lock_resource *res = NULL;
@@ -1402,16 +1403,28 @@ int dlm_mig_lockres_handler(struct o2net_msg *msg, u32 len, void *data,
__dlm_insert_lockres(dlm, res);
spin_unlock(&dlm->spinlock);
+ /* Add an extra ref for this lock-less lockres lest the
+ * dlm_thread purges it before we get the chance to add
+ * locks to it */
+ dlm_lockres_get(res);
+
+ /* There are three refs that need to be put.
+ * 1. Taken above.
+ * 2. kref_init in dlm_new_lockres()->dlm_init_lockres().
+ * 3. dlm_lookup_lockres()
+ * The first one is handled at the end of this function. The
+ * other two are handled in the worker thread after locks have
+ * been attached. Yes, we don't wait for purge time to match
+ * kref_init. The lockres will still have atleast one ref
+ * added because it is in the hash __dlm_insert_lockres() */
+ extra_refs++;
+
/* now that the new lockres is inserted,
* make it usable by other processes */
spin_lock(&res->spinlock);
res->state &= ~DLM_LOCK_RES_IN_PROGRESS;
spin_unlock(&res->spinlock);
wake_up(&res->wq);
-
- /* add an extra ref for just-allocated lockres
- * otherwise the lockres will be purged immediately */
- dlm_lockres_get(res);
}
/* at this point we have allocated everything we need,
@@ -1441,12 +1454,17 @@ int dlm_mig_lockres_handler(struct o2net_msg *msg, u32 len, void *data,
dlm_init_work_item(dlm, item, dlm_mig_lockres_worker, buf);
item->u.ml.lockres = res; /* already have a ref */
item->u.ml.real_master = real_master;
+ item->u.ml.extra_ref = extra_refs;
spin_lock(&dlm->work_lock);
list_add_tail(&item->list, &dlm->work_list);
spin_unlock(&dlm->work_lock);
queue_work(dlm->dlm_worker, &dlm->dispatched_work);
leave:
+ /* One extra ref taken needs to be put here */
+ if (extra_refs)
+ dlm_lockres_put(res);
+
dlm_put(dlm);
if (ret < 0) {
if (buf)
@@ -1462,17 +1480,19 @@ leave:
void dlm_mig_lockres_worker(struct dlm_work_item *item, void *data)
{
- struct dlm_ctxt *dlm = data;
+ struct dlm_ctxt *dlm;
struct dlm_migratable_lockres *mres;
int ret = 0;
struct dlm_lock_resource *res;
u8 real_master;
+ u8 extra_ref;
dlm = item->dlm;
mres = (struct dlm_migratable_lockres *)data;
res = item->u.ml.lockres;
real_master = item->u.ml.real_master;
+ extra_ref = item->u.ml.extra_ref;
if (real_master == DLM_LOCK_RES_OWNER_UNKNOWN) {
/* this case is super-rare. only occurs if
@@ -1515,6 +1535,12 @@ again:
}
leave:
+ /* See comment in dlm_mig_lockres_handler() */
+ if (res) {
+ if (extra_ref)
+ dlm_lockres_put(res);
+ dlm_lockres_put(res);
+ }
kfree(data);
mlog_exit(ret);
}
@@ -1642,7 +1668,8 @@ int dlm_master_requery_handler(struct o2net_msg *msg, u32 len, void *data,
/* retry!? */
BUG();
}
- }
+ } else /* put.. incase we are not the master */
+ dlm_lockres_put(res);
spin_unlock(&res->spinlock);
}
spin_unlock(&dlm->spinlock);
@@ -1919,6 +1946,8 @@ void dlm_move_lockres_to_recovery_list(struct dlm_ctxt *dlm,
"Recovering res %s:%.*s, is already on recovery list!\n",
dlm->name, res->lockname.len, res->lockname.name);
list_del_init(&res->recovering);
+ /* Duh... */
+ dlm_lockres_put(res);
}
/* We need to hold a reference while on the recovery list */
dlm_lockres_get(res);
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 04/18] ocfs2_dlm: Add missing dlm_lockres_put()s in migration path
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 04/18] ocfs2_dlm: Add missing dlm_lockres_put()s in migration path Sunil Mushran
@ 2008-02-28 14:41 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 14:41 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:48PM -0800, Sunil Mushran wrote:
> The inline comments explain the missing puts in the lockres
> migration paths.
The comments are readable in a patch email, but not in a 'git
log'. Can you expound on the problem in the patch header too, please?
> @@ -1919,6 +1946,8 @@ void dlm_move_lockres_to_recovery_list(struct dlm_ctxt *dlm,
> "Recovering res %s:%.*s, is already on recovery list!\n",
> dlm->name, res->lockname.len, res->lockname.name);
> list_del_init(&res->recovering);
> + /* Duh... */
> + dlm_lockres_put(res);
Why is this "Duh..."? People looking later won't have the
benefit of your memory :-)
Joel
--
"Practice random acts of kindness and senseless acts of beauty."
Oh, and don't forget where your towel is.
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (8 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 04/18] ocfs2_dlm: Add missing dlm_lockres_put()s in migration path Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:34 ` Joel Becker
2008-02-28 17:09 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 16/18] ocfs2_dlm: Small fix regarding dlm_print_one_lock_resource() Sunil Mushran
` (7 subsequent siblings)
17 siblings, 2 replies; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch creates the debugfs directories that will hold the
files to be used to dump the dlm state.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 2 ++
fs/ocfs2/dlm/dlmdebug.c | 44 ++++++++++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmdebug.h | 7 +++++++
fs/ocfs2/dlm/dlmdomain.c | 20 ++++++++++++++++++++
4 files changed, 73 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index a3b22bf..810e9b4 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -125,6 +125,8 @@ struct dlm_ctxt
atomic_t remote_resources;
atomic_t unknown_resources;
+ struct dentry *dlm_debugfs_subroot;
+
/* NOTE: Next three are protected by dlm_domain_lock */
struct kref dlm_refs;
enum dlm_ctxt_state dlm_state;
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index e4f1fe9..baa8e24 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -31,6 +31,7 @@
#include <linux/sysctl.h>
#include <linux/spinlock.h>
#include <linux/proc_fs.h>
+#include <linux/debugfs.h>
#include "cluster/heartbeat.h"
#include "cluster/nodemanager.h"
@@ -46,6 +47,8 @@
#define MLOG_MASK_PREFIX ML_DLM
#include "cluster/masklog.h"
+static struct dentry *dlm_debugfs_root = NULL;
+
static int dlm_dump_all_lock_resources(const char __user *data,
unsigned int len);
static void dlm_dump_purge_list(struct dlm_ctxt *dlm);
@@ -699,3 +702,44 @@ const char *dlm_errname(enum dlm_status err)
return dlm_errnames[err];
}
EXPORT_SYMBOL_GPL(dlm_errname);
+
+#define DLM_DEBUGFS_DIR "o2dlm"
+
+/* subroot - domain dir */
+int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
+{
+ dlm->dlm_debugfs_subroot = debugfs_create_dir(dlm->name, dlm_debugfs_root);
+ if (!dlm->dlm_debugfs_subroot) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+
+ return 0;
+bail:
+ dlm_destroy_debugfs_subroot(dlm);
+ return -ENOMEM;
+}
+
+void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm)
+{
+ if (dlm->dlm_debugfs_subroot)
+ debugfs_remove(dlm->dlm_debugfs_subroot);
+}
+
+/* debugfs root */
+int dlm_create_debugfs_root(void)
+{
+ dlm_debugfs_root = debugfs_create_dir(DLM_DEBUGFS_DIR, NULL);
+ if (!dlm_debugfs_root) {
+ mlog_errno(-ENOMEM);
+ return -ENOMEM;
+ }
+
+ return 0;
+}
+
+void dlm_destroy_debugfs_root(void)
+{
+ if (dlm_debugfs_root)
+ debugfs_remove(dlm_debugfs_root);
+}
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index dbe3a3d..e701499 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -31,4 +31,11 @@ void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
void dlm_proc_add_domain(struct dlm_ctxt *dlm);
void dlm_proc_del_domain(struct dlm_ctxt *dlm);
void dlm_dump_work_queue(struct dlm_ctxt *dlm);
+
+int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm);
+void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
+
+int dlm_create_debugfs_root(void);
+void dlm_destroy_debugfs_root(void);
+
#endif
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index 1d382f1..da2a155 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -33,6 +33,7 @@
#include <linux/spinlock.h>
#include <linux/delay.h>
#include <linux/err.h>
+#include <linux/debugfs.h>
#include "cluster/heartbeat.h"
#include "cluster/nodemanager.h"
@@ -43,6 +44,7 @@
#include "dlmdebug.h"
#include "dlmdomain.h"
+#include "dlmdebug.h"
#include "dlmver.h"
@@ -288,6 +290,8 @@ static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm)
{
dlm_proc_del_domain(dlm);
+ dlm_destroy_debugfs_subroot(dlm);
+
if (dlm->lockres_hash)
dlm_free_pagevec((void **)dlm->lockres_hash, DLM_HASH_PAGES);
@@ -1372,6 +1376,7 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
u32 key)
{
int i;
+ int ret;
struct dlm_ctxt *dlm = NULL;
dlm = kzalloc(sizeof(*dlm), GFP_KERNEL);
@@ -1404,6 +1409,15 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
dlm->key = key;
dlm->node_num = o2nm_this_node();
+ ret = dlm_create_debugfs_subroot(dlm);
+ if (ret < 0) {
+ dlm_free_pagevec((void **)dlm->lockres_hash, DLM_HASH_PAGES);
+ kfree(dlm->name);
+ kfree(dlm);
+ dlm = NULL;
+ goto leave;
+ }
+
spin_lock_init(&dlm->spinlock);
spin_lock_init(&dlm->master_lock);
spin_lock_init(&dlm->ast_lock);
@@ -1688,8 +1702,13 @@ static int __init dlm_init(void)
dlm_init_proc();
+ status = dlm_create_debugfs_root();
+ if (status)
+ goto error;
+
return 0;
error:
+ dlm_unregister_net_handlers();
dlm_destroy_lock_cache();
dlm_destroy_lockname_cache();
dlm_destroy_lockres_cache();
@@ -1699,6 +1718,7 @@ error:
static void __exit dlm_exit (void)
{
+ dlm_destroy_debugfs_root();
dlm_remove_proc();
dlm_unregister_net_handlers();
dlm_destroy_lock_cache();
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs Sunil Mushran
@ 2008-02-28 16:34 ` Joel Becker
2008-02-28 17:09 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:34 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:51PM -0800, Sunil Mushran wrote:
> This patch creates the debugfs directories that will hold the
> files to be used to dump the dlm state.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Looks good, but once again it needs to either be conditional on
CONFIG_DEBUG_FS or have OCFS2 depend on it.
Joel
> ---
> fs/ocfs2/dlm/dlmcommon.h | 2 ++
> fs/ocfs2/dlm/dlmdebug.c | 44 ++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 7 +++++++
> fs/ocfs2/dlm/dlmdomain.c | 20 ++++++++++++++++++++
> 4 files changed, 73 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index a3b22bf..810e9b4 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -125,6 +125,8 @@ struct dlm_ctxt
> atomic_t remote_resources;
> atomic_t unknown_resources;
>
> + struct dentry *dlm_debugfs_subroot;
> +
> /* NOTE: Next three are protected by dlm_domain_lock */
> struct kref dlm_refs;
> enum dlm_ctxt_state dlm_state;
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index e4f1fe9..baa8e24 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -31,6 +31,7 @@
> #include <linux/sysctl.h>
> #include <linux/spinlock.h>
> #include <linux/proc_fs.h>
> +#include <linux/debugfs.h>
>
> #include "cluster/heartbeat.h"
> #include "cluster/nodemanager.h"
> @@ -46,6 +47,8 @@
> #define MLOG_MASK_PREFIX ML_DLM
> #include "cluster/masklog.h"
>
> +static struct dentry *dlm_debugfs_root = NULL;
> +
> static int dlm_dump_all_lock_resources(const char __user *data,
> unsigned int len);
> static void dlm_dump_purge_list(struct dlm_ctxt *dlm);
> @@ -699,3 +702,44 @@ const char *dlm_errname(enum dlm_status err)
> return dlm_errnames[err];
> }
> EXPORT_SYMBOL_GPL(dlm_errname);
> +
> +#define DLM_DEBUGFS_DIR "o2dlm"
> +
> +/* subroot - domain dir */
> +int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
> +{
> + dlm->dlm_debugfs_subroot = debugfs_create_dir(dlm->name, dlm_debugfs_root);
> + if (!dlm->dlm_debugfs_subroot) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> + return 0;
> +bail:
> + dlm_destroy_debugfs_subroot(dlm);
> + return -ENOMEM;
> +}
> +
> +void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm)
> +{
> + if (dlm->dlm_debugfs_subroot)
> + debugfs_remove(dlm->dlm_debugfs_subroot);
> +}
> +
> +/* debugfs root */
> +int dlm_create_debugfs_root(void)
> +{
> + dlm_debugfs_root = debugfs_create_dir(DLM_DEBUGFS_DIR, NULL);
> + if (!dlm_debugfs_root) {
> + mlog_errno(-ENOMEM);
> + return -ENOMEM;
> + }
> +
> + return 0;
> +}
> +
> +void dlm_destroy_debugfs_root(void)
> +{
> + if (dlm_debugfs_root)
> + debugfs_remove(dlm_debugfs_root);
> +}
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index dbe3a3d..e701499 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -31,4 +31,11 @@ void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> void dlm_proc_add_domain(struct dlm_ctxt *dlm);
> void dlm_proc_del_domain(struct dlm_ctxt *dlm);
> void dlm_dump_work_queue(struct dlm_ctxt *dlm);
> +
> +int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm);
> +void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
> +
> +int dlm_create_debugfs_root(void);
> +void dlm_destroy_debugfs_root(void);
> +
> #endif
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index 1d382f1..da2a155 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -33,6 +33,7 @@
> #include <linux/spinlock.h>
> #include <linux/delay.h>
> #include <linux/err.h>
> +#include <linux/debugfs.h>
>
> #include "cluster/heartbeat.h"
> #include "cluster/nodemanager.h"
> @@ -43,6 +44,7 @@
>
> #include "dlmdebug.h"
> #include "dlmdomain.h"
> +#include "dlmdebug.h"
>
> #include "dlmver.h"
>
> @@ -288,6 +290,8 @@ static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm)
> {
> dlm_proc_del_domain(dlm);
>
> + dlm_destroy_debugfs_subroot(dlm);
> +
> if (dlm->lockres_hash)
> dlm_free_pagevec((void **)dlm->lockres_hash, DLM_HASH_PAGES);
>
> @@ -1372,6 +1376,7 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
> u32 key)
> {
> int i;
> + int ret;
> struct dlm_ctxt *dlm = NULL;
>
> dlm = kzalloc(sizeof(*dlm), GFP_KERNEL);
> @@ -1404,6 +1409,15 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
> dlm->key = key;
> dlm->node_num = o2nm_this_node();
>
> + ret = dlm_create_debugfs_subroot(dlm);
> + if (ret < 0) {
> + dlm_free_pagevec((void **)dlm->lockres_hash, DLM_HASH_PAGES);
> + kfree(dlm->name);
> + kfree(dlm);
> + dlm = NULL;
> + goto leave;
> + }
> +
> spin_lock_init(&dlm->spinlock);
> spin_lock_init(&dlm->master_lock);
> spin_lock_init(&dlm->ast_lock);
> @@ -1688,8 +1702,13 @@ static int __init dlm_init(void)
>
> dlm_init_proc();
>
> + status = dlm_create_debugfs_root();
> + if (status)
> + goto error;
> +
> return 0;
> error:
> + dlm_unregister_net_handlers();
> dlm_destroy_lock_cache();
> dlm_destroy_lockname_cache();
> dlm_destroy_lockres_cache();
> @@ -1699,6 +1718,7 @@ error:
>
> static void __exit dlm_exit (void)
> {
> + dlm_destroy_debugfs_root();
> dlm_remove_proc();
> dlm_unregister_net_handlers();
> dlm_destroy_lock_cache();
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"The question of whether computers can think is just like the question
of whether submarines can swim."
- Edsger W. Dijkstra
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs Sunil Mushran
2008-02-28 16:34 ` Joel Becker
@ 2008-02-28 17:09 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 17:09 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:51PM -0800, Sunil Mushran wrote:
> This patch creates the debugfs directories that will hold the
> files to be used to dump the dlm state.
Please run through checkpatch.pl.
Joel
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
> ---
> fs/ocfs2/dlm/dlmcommon.h | 2 ++
> fs/ocfs2/dlm/dlmdebug.c | 44 ++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 7 +++++++
> fs/ocfs2/dlm/dlmdomain.c | 20 ++++++++++++++++++++
> 4 files changed, 73 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index a3b22bf..810e9b4 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -125,6 +125,8 @@ struct dlm_ctxt
> atomic_t remote_resources;
> atomic_t unknown_resources;
>
> + struct dentry *dlm_debugfs_subroot;
> +
> /* NOTE: Next three are protected by dlm_domain_lock */
> struct kref dlm_refs;
> enum dlm_ctxt_state dlm_state;
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index e4f1fe9..baa8e24 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -31,6 +31,7 @@
> #include <linux/sysctl.h>
> #include <linux/spinlock.h>
> #include <linux/proc_fs.h>
> +#include <linux/debugfs.h>
>
> #include "cluster/heartbeat.h"
> #include "cluster/nodemanager.h"
> @@ -46,6 +47,8 @@
> #define MLOG_MASK_PREFIX ML_DLM
> #include "cluster/masklog.h"
>
> +static struct dentry *dlm_debugfs_root = NULL;
> +
> static int dlm_dump_all_lock_resources(const char __user *data,
> unsigned int len);
> static void dlm_dump_purge_list(struct dlm_ctxt *dlm);
> @@ -699,3 +702,44 @@ const char *dlm_errname(enum dlm_status err)
> return dlm_errnames[err];
> }
> EXPORT_SYMBOL_GPL(dlm_errname);
> +
> +#define DLM_DEBUGFS_DIR "o2dlm"
> +
> +/* subroot - domain dir */
> +int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
> +{
> + dlm->dlm_debugfs_subroot = debugfs_create_dir(dlm->name, dlm_debugfs_root);
> + if (!dlm->dlm_debugfs_subroot) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> + return 0;
> +bail:
> + dlm_destroy_debugfs_subroot(dlm);
> + return -ENOMEM;
> +}
> +
> +void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm)
> +{
> + if (dlm->dlm_debugfs_subroot)
> + debugfs_remove(dlm->dlm_debugfs_subroot);
> +}
> +
> +/* debugfs root */
> +int dlm_create_debugfs_root(void)
> +{
> + dlm_debugfs_root = debugfs_create_dir(DLM_DEBUGFS_DIR, NULL);
> + if (!dlm_debugfs_root) {
> + mlog_errno(-ENOMEM);
> + return -ENOMEM;
> + }
> +
> + return 0;
> +}
> +
> +void dlm_destroy_debugfs_root(void)
> +{
> + if (dlm_debugfs_root)
> + debugfs_remove(dlm_debugfs_root);
> +}
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index dbe3a3d..e701499 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -31,4 +31,11 @@ void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> void dlm_proc_add_domain(struct dlm_ctxt *dlm);
> void dlm_proc_del_domain(struct dlm_ctxt *dlm);
> void dlm_dump_work_queue(struct dlm_ctxt *dlm);
> +
> +int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm);
> +void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
> +
> +int dlm_create_debugfs_root(void);
> +void dlm_destroy_debugfs_root(void);
> +
> #endif
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index 1d382f1..da2a155 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -33,6 +33,7 @@
> #include <linux/spinlock.h>
> #include <linux/delay.h>
> #include <linux/err.h>
> +#include <linux/debugfs.h>
>
> #include "cluster/heartbeat.h"
> #include "cluster/nodemanager.h"
> @@ -43,6 +44,7 @@
>
> #include "dlmdebug.h"
> #include "dlmdomain.h"
> +#include "dlmdebug.h"
>
> #include "dlmver.h"
>
> @@ -288,6 +290,8 @@ static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm)
> {
> dlm_proc_del_domain(dlm);
>
> + dlm_destroy_debugfs_subroot(dlm);
> +
> if (dlm->lockres_hash)
> dlm_free_pagevec((void **)dlm->lockres_hash, DLM_HASH_PAGES);
>
> @@ -1372,6 +1376,7 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
> u32 key)
> {
> int i;
> + int ret;
> struct dlm_ctxt *dlm = NULL;
>
> dlm = kzalloc(sizeof(*dlm), GFP_KERNEL);
> @@ -1404,6 +1409,15 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
> dlm->key = key;
> dlm->node_num = o2nm_this_node();
>
> + ret = dlm_create_debugfs_subroot(dlm);
> + if (ret < 0) {
> + dlm_free_pagevec((void **)dlm->lockres_hash, DLM_HASH_PAGES);
> + kfree(dlm->name);
> + kfree(dlm);
> + dlm = NULL;
> + goto leave;
> + }
> +
> spin_lock_init(&dlm->spinlock);
> spin_lock_init(&dlm->master_lock);
> spin_lock_init(&dlm->ast_lock);
> @@ -1688,8 +1702,13 @@ static int __init dlm_init(void)
>
> dlm_init_proc();
>
> + status = dlm_create_debugfs_root();
> + if (status)
> + goto error;
> +
> return 0;
> error:
> + dlm_unregister_net_handlers();
> dlm_destroy_lock_cache();
> dlm_destroy_lockname_cache();
> dlm_destroy_lockres_cache();
> @@ -1699,6 +1718,7 @@ error:
>
> static void __exit dlm_exit (void)
> {
> + dlm_destroy_debugfs_root();
> dlm_remove_proc();
> dlm_unregister_net_handlers();
> dlm_destroy_lock_cache();
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Gone to plant a weeping willow
On the bank's green edge it will roll, roll, roll.
Sing a lulaby beside the waters.
Lovers come and go, the river roll, roll, rolls."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 16/18] ocfs2_dlm: Small fix regarding dlm_print_one_lock_resource()
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (9 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 07/18] ocfs2_dlm: Create debugfs dirs Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:55 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 17/18] ocfs2_dlm: Fix lockname in lockres print function Sunil Mushran
` (6 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
Some fucntions were calling __dlm_print_one_lock_resource() instead
of dlm_print_one_lock_resource()
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmconvert.c | 2 +-
fs/ocfs2/dlm/dlmdebug.c | 3 ---
fs/ocfs2/dlm/dlmmaster.c | 4 ++--
3 files changed, 3 insertions(+), 6 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmconvert.c b/fs/ocfs2/dlm/dlmconvert.c
index ecb4d99..75997b4 100644
--- a/fs/ocfs2/dlm/dlmconvert.c
+++ b/fs/ocfs2/dlm/dlmconvert.c
@@ -487,7 +487,7 @@ int dlm_convert_lock_handler(struct o2net_msg *msg, u32 len, void *data,
"cookie=%u:%llu\n",
dlm_get_lock_cookie_node(be64_to_cpu(cnv->cookie)),
dlm_get_lock_cookie_seq(be64_to_cpu(cnv->cookie)));
- __dlm_print_one_lock_resource(res);
+ dlm_print_one_lock_resource(res);
goto leave;
}
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index 24d2f5c..2a1c27c 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -67,9 +67,6 @@ static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
void dlm_print_one_lock_resource(struct dlm_lock_resource *res)
{
- mlog(ML_NOTICE, "lockres: %.*s, owner=%u, state=%u\n",
- res->lockname.len, res->lockname.name,
- res->owner, res->state);
spin_lock(&res->spinlock);
__dlm_print_one_lock_resource(res);
spin_unlock(&res->spinlock);
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index 3d681fe..0af2532 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -2283,7 +2283,7 @@ int dlm_deref_lockres_handler(struct o2net_msg *msg, u32 len, void *data,
mlog(ML_ERROR, "%s:%.*s: node %u trying to drop ref "
"but it is already dropped!\n", dlm->name,
res->lockname.len, res->lockname.name, node);
- __dlm_print_one_lock_resource(res);
+ dlm_print_one_lock_resource(res);
}
ret = 0;
goto done;
@@ -2343,7 +2343,7 @@ static void dlm_deref_lockres_worker(struct dlm_work_item *item, void *data)
mlog(ML_ERROR, "%s:%.*s: node %u trying to drop ref "
"but it is already dropped!\n", dlm->name,
res->lockname.len, res->lockname.name, node);
- __dlm_print_one_lock_resource(res);
+ dlm_print_one_lock_resource(res);
}
dlm_lockres_put(res);
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 16/18] ocfs2_dlm: Small fix regarding dlm_print_one_lock_resource()
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 16/18] ocfs2_dlm: Small fix regarding dlm_print_one_lock_resource() Sunil Mushran
@ 2008-02-28 16:55 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:55 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:21:00PM -0800, Sunil Mushran wrote:
> Some fucntions were calling __dlm_print_one_lock_resource() instead
> of dlm_print_one_lock_resource()
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmconvert.c | 2 +-
> fs/ocfs2/dlm/dlmdebug.c | 3 ---
> fs/ocfs2/dlm/dlmmaster.c | 4 ++--
> 3 files changed, 3 insertions(+), 6 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmconvert.c b/fs/ocfs2/dlm/dlmconvert.c
> index ecb4d99..75997b4 100644
> --- a/fs/ocfs2/dlm/dlmconvert.c
> +++ b/fs/ocfs2/dlm/dlmconvert.c
> @@ -487,7 +487,7 @@ int dlm_convert_lock_handler(struct o2net_msg *msg, u32 len, void *data,
> "cookie=%u:%llu\n",
> dlm_get_lock_cookie_node(be64_to_cpu(cnv->cookie)),
> dlm_get_lock_cookie_seq(be64_to_cpu(cnv->cookie)));
> - __dlm_print_one_lock_resource(res);
> + dlm_print_one_lock_resource(res);
> goto leave;
> }
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 24d2f5c..2a1c27c 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -67,9 +67,6 @@ static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
>
> void dlm_print_one_lock_resource(struct dlm_lock_resource *res)
> {
> - mlog(ML_NOTICE, "lockres: %.*s, owner=%u, state=%u\n",
> - res->lockname.len, res->lockname.name,
> - res->owner, res->state);
> spin_lock(&res->spinlock);
> __dlm_print_one_lock_resource(res);
> spin_unlock(&res->spinlock);
> diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
> index 3d681fe..0af2532 100644
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -2283,7 +2283,7 @@ int dlm_deref_lockres_handler(struct o2net_msg *msg, u32 len, void *data,
> mlog(ML_ERROR, "%s:%.*s: node %u trying to drop ref "
> "but it is already dropped!\n", dlm->name,
> res->lockname.len, res->lockname.name, node);
> - __dlm_print_one_lock_resource(res);
> + dlm_print_one_lock_resource(res);
> }
> ret = 0;
> goto done;
> @@ -2343,7 +2343,7 @@ static void dlm_deref_lockres_worker(struct dlm_work_item *item, void *data)
> mlog(ML_ERROR, "%s:%.*s: node %u trying to drop ref "
> "but it is already dropped!\n", dlm->name,
> res->lockname.len, res->lockname.name, node);
> - __dlm_print_one_lock_resource(res);
> + dlm_print_one_lock_resource(res);
> }
>
> dlm_lockres_put(res);
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"You can get more with a kind word and a gun than you can with
a kind word alone."
- Al Capone
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 17/18] ocfs2_dlm: Fix lockname in lockres print function
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (10 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 16/18] ocfs2_dlm: Small fix regarding dlm_print_one_lock_resource() Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:57 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file Sunil Mushran
` (5 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
__dlm_print_one_lock_resource was printing lockname incorrectly.
This patch fixes that among other small printk cleanups.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmdebug.c | 26 ++++++++++++++++++--------
1 files changed, 18 insertions(+), 8 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index 2a1c27c..3e16e91 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -47,6 +47,7 @@
static struct dentry *dlm_debugfs_root = NULL;
int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len);
+int stringify_lockname(const char *lockname, int locklen, char *buf, int len);
static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
{
@@ -76,14 +77,23 @@ void __dlm_print_one_lock_resource(struct dlm_lock_resource *res)
{
struct list_head *iter2;
struct dlm_lock *lock;
+ char buf[DLM_LOCKID_NAME_MAX];
assert_spin_locked(&res->spinlock);
- mlog(ML_NOTICE, "lockres: %.*s, owner=%u, state=%u\n",
- res->lockname.len, res->lockname.name,
- res->owner, res->state);
- mlog(ML_NOTICE, " last used: %lu, on purge list: %s\n",
- res->last_used, list_empty(&res->purge) ? "no" : "yes");
+ stringify_lockname(res->lockname.name, res->lockname.len,
+ buf, sizeof(buf) - 1);
+ mlog(ML_NOTICE, "lockres: %s, owner=%u, state=%u\n", buf, res->owner,
+ res->state);
+ mlog(ML_NOTICE, " last used: %lu, refcnt: %u, on purge list: %s\n",
+ res->last_used, atomic_read(&res->refs.refcount),
+ list_empty(&res->purge) ? "no" : "yes");
+ mlog(ML_NOTICE, " on dirty list: %s, on reco list: %s, migrating pending: %s\n",
+ list_empty(&res->dirty) ? "no" : "yes",
+ list_empty(&res->recovering) ? "no" : "yes",
+ res->migration_pending ? "yes" : "no");
+ mlog(ML_NOTICE, " inflight locks: %d, asts reserved: %d\n",
+ res->inflight_locks, atomic_read(&res->asts_reserved));
dlm_print_lockres_refmap(res);
mlog(ML_NOTICE, " granted queue: \n");
list_for_each(iter2, &res->granted) {
@@ -105,10 +115,11 @@ void __dlm_print_one_lock_resource(struct dlm_lock_resource *res)
lock = list_entry(iter2, struct dlm_lock, list);
spin_lock(&lock->spinlock);
mlog(ML_NOTICE, " type=%d, conv=%d, node=%u, "
- "cookie=%u:%llu, ast=(empty=%c,pend=%c), bast=(empty=%c,pend=%c)\n",
+ "cookie=%u:%llu, ref=%u, ast=(empty=%c,pend=%c), bast=(empty=%c,pend=%c)\n",
lock->ml.type, lock->ml.convert_type, lock->ml.node,
dlm_get_lock_cookie_node(be64_to_cpu(lock->ml.cookie)),
dlm_get_lock_cookie_seq(be64_to_cpu(lock->ml.cookie)),
+ atomic_read(&lock->lock_refs.refcount),
list_empty(&lock->ast_list) ? 'y' : 'n',
lock->ast_pending ? 'y' : 'n',
list_empty(&lock->bast_list) ? 'y' : 'n',
@@ -268,8 +279,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
*
* For more on lockname formats, please refer to dlmglue.c and ocfs2_lockid.h.
*/
-static int stringify_lockname(const char *lockname, int locklen,
- char *buf, int len)
+int stringify_lockname(const char *lockname, int locklen, char *buf, int len)
{
int out = 0;
__be64 inode_blkno_be;
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 17/18] ocfs2_dlm: Fix lockname in lockres print function
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 17/18] ocfs2_dlm: Fix lockname in lockres print function Sunil Mushran
@ 2008-02-28 16:57 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:57 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:21:01PM -0800, Sunil Mushran wrote:
> __dlm_print_one_lock_resource was printing lockname incorrectly.
> This patch fixes that among other small printk cleanups.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmdebug.c | 26 ++++++++++++++++++--------
> 1 files changed, 18 insertions(+), 8 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 2a1c27c..3e16e91 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -47,6 +47,7 @@
> static struct dentry *dlm_debugfs_root = NULL;
>
> int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len);
> +int stringify_lockname(const char *lockname, int locklen, char *buf, int len);
>
> static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
> {
> @@ -76,14 +77,23 @@ void __dlm_print_one_lock_resource(struct dlm_lock_resource *res)
> {
> struct list_head *iter2;
> struct dlm_lock *lock;
> + char buf[DLM_LOCKID_NAME_MAX];
>
> assert_spin_locked(&res->spinlock);
>
> - mlog(ML_NOTICE, "lockres: %.*s, owner=%u, state=%u\n",
> - res->lockname.len, res->lockname.name,
> - res->owner, res->state);
> - mlog(ML_NOTICE, " last used: %lu, on purge list: %s\n",
> - res->last_used, list_empty(&res->purge) ? "no" : "yes");
> + stringify_lockname(res->lockname.name, res->lockname.len,
> + buf, sizeof(buf) - 1);
> + mlog(ML_NOTICE, "lockres: %s, owner=%u, state=%u\n", buf, res->owner,
> + res->state);
> + mlog(ML_NOTICE, " last used: %lu, refcnt: %u, on purge list: %s\n",
> + res->last_used, atomic_read(&res->refs.refcount),
> + list_empty(&res->purge) ? "no" : "yes");
> + mlog(ML_NOTICE, " on dirty list: %s, on reco list: %s, migrating pending: %s\n",
> + list_empty(&res->dirty) ? "no" : "yes",
> + list_empty(&res->recovering) ? "no" : "yes",
> + res->migration_pending ? "yes" : "no");
> + mlog(ML_NOTICE, " inflight locks: %d, asts reserved: %d\n",
> + res->inflight_locks, atomic_read(&res->asts_reserved));
> dlm_print_lockres_refmap(res);
> mlog(ML_NOTICE, " granted queue: \n");
> list_for_each(iter2, &res->granted) {
> @@ -105,10 +115,11 @@ void __dlm_print_one_lock_resource(struct dlm_lock_resource *res)
> lock = list_entry(iter2, struct dlm_lock, list);
> spin_lock(&lock->spinlock);
> mlog(ML_NOTICE, " type=%d, conv=%d, node=%u, "
> - "cookie=%u:%llu, ast=(empty=%c,pend=%c), bast=(empty=%c,pend=%c)\n",
> + "cookie=%u:%llu, ref=%u, ast=(empty=%c,pend=%c), bast=(empty=%c,pend=%c)\n",
> lock->ml.type, lock->ml.convert_type, lock->ml.node,
> dlm_get_lock_cookie_node(be64_to_cpu(lock->ml.cookie)),
> dlm_get_lock_cookie_seq(be64_to_cpu(lock->ml.cookie)),
> + atomic_read(&lock->lock_refs.refcount),
> list_empty(&lock->ast_list) ? 'y' : 'n',
> lock->ast_pending ? 'y' : 'n',
> list_empty(&lock->bast_list) ? 'y' : 'n',
> @@ -268,8 +279,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
> *
> * For more on lockname formats, please refer to dlmglue.c and ocfs2_lockid.h.
> */
> -static int stringify_lockname(const char *lockname, int locklen,
> - char *buf, int len)
> +int stringify_lockname(const char *lockname, int locklen, char *buf, int len)
> {
> int out = 0;
> __be64 inode_blkno_be;
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Nearly all men can stand adversity, but if you really want to
test a man's character, give him power."
- Abraham Lincoln
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (11 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 17/18] ocfs2_dlm: Fix lockname in lockres print function Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:51 ` Joel Becker
2008-02-28 17:11 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 03/18] ocfs2_dlm: Add missing dlm_lock_put()s Sunil Mushran
` (4 subsequent siblings)
17 siblings, 2 replies; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch dumps all the lockres' alongwith all the locks into
a debugfs file. Useful for debugging.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmdebug.c | 248 +++++++++++++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmdebug.h | 9 ++
2 files changed, 257 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index 83f3ac6..905145a 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -705,7 +705,34 @@ EXPORT_SYMBOL_GPL(dlm_errname);
#define DLM_DEBUGFS_DIR "o2dlm"
#define DLM_DEBUGFS_DLM_STATE "dlm_state"
+#define DLM_DEBUGFS_LOCKING_STATE "locking_state"
+/* 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.
+ */
+static int stringify_lockname(const char *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 += snprintf(buf + out, len - out, "%.*s%08x",
+ OCFS2_DENTRY_LOCK_INO_START - 1, lockname,
+ (unsigned int)be64_to_cpu(inode_blkno_be));
+ } else
+ out += snprintf(buf + out, len - out, "%.*s",
+ locklen, lockname);
+ return out;
+}
+
/* begin - utils funcs */
static void dlm_debug_free(struct kref *kref)
{
@@ -800,6 +827,214 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
}
/* end - util funcs */
+/* begin - debug lockres funcs */
+static int dump_lock(struct dlm_lock *lock, int list_type, char *buf, int len)
+{
+ int out;
+
+#define DEBUG_LOCK_VERSION 1
+ spin_lock(&lock->spinlock);
+ out = snprintf(buf, len, "LOCK:%d,%d,%d,%d,%d,%d:%lld,%d,%d,%d,%d,%d,"
+ "%d,%d,%d,%d\n",
+ DEBUG_LOCK_VERSION,
+ list_type, lock->ml.type, lock->ml.convert_type,
+ lock->ml.node,
+ dlm_get_lock_cookie_node(be64_to_cpu(lock->ml.cookie)),
+ dlm_get_lock_cookie_seq(be64_to_cpu(lock->ml.cookie)),
+ !list_empty(&lock->ast_list),
+ !list_empty(&lock->bast_list),
+ lock->ast_pending, lock->bast_pending,
+ lock->convert_pending, lock->lock_pending,
+ lock->cancel_pending, lock->unlock_pending,
+ atomic_read(&lock->lock_refs.refcount));
+ spin_unlock(&lock->spinlock);
+
+ return out;
+}
+
+static int dump_lockres(struct dlm_lock_resource *res, char *buf, int len)
+{
+ struct dlm_lock *lock;
+ int i;
+ int out = 0;
+
+ out += snprintf(buf + out, len - out, "NAME:");
+ out += stringify_lockname(res->lockname.name, res->lockname.len,
+ buf + out, len - out);
+ out += snprintf(buf + out, len - out, "\n");
+
+#define DEBUG_LRES_VERSION 1
+ out += snprintf(buf + out, len - out,
+ "LRES:%d,%d,%d,%ld,%d,%d,%d,%d,%d,%d,%d\n",
+ DEBUG_LRES_VERSION,
+ res->owner, res->state, res->last_used,
+ !list_empty(&res->purge),
+ !list_empty(&res->dirty),
+ !list_empty(&res->recovering),
+ res->inflight_locks, res->migration_pending,
+ atomic_read(&res->asts_reserved),
+ atomic_read(&res->refs.refcount));
+
+ /* refmap */
+ out += snprintf(buf + out, len - out, "RMAP:");
+ out += stringify_nodemap(res->refmap, O2NM_MAX_NODES,
+ buf + out, len - out);
+ out += snprintf(buf + out, len - out, "\n");
+
+ /* lvb */
+ out += snprintf(buf + out, len - out, "LVBX:");
+ for (i = 0; i < DLM_LVB_LEN; i++)
+ out += snprintf(buf + out, len - out,
+ "%02x", (unsigned char)res->lvb[i]);
+ out += snprintf(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);
+
+ out += snprintf(buf + out, len - out, "\n");
+
+ return out;
+}
+
+static void *lockres_seq_start(struct seq_file *m, loff_t *pos)
+{
+ struct debug_lockres *dl = m->private;
+ struct dlm_ctxt *dlm = dl->dl_ctxt;
+ struct dlm_lock_resource *res = NULL;
+
+ spin_lock(&dlm->spinlock);
+
+ if (dl->dl_res) {
+ list_for_each_entry(res, &dl->dl_res->tracking, tracking) {
+ if (dl->dl_res) {
+ dlm_lockres_put(dl->dl_res);
+ dl->dl_res = NULL;
+ }
+ if (&res->tracking == &dlm->tracking_list) {
+ mlog(0, "End of list found, %p\n", res);
+ dl = NULL;
+ break;
+ }
+ dlm_lockres_get(res);
+ dl->dl_res = res;
+ break;
+ }
+ } else {
+ if (!list_empty(&dlm->tracking_list)) {
+ list_for_each_entry(res, &dlm->tracking_list, tracking)
+ break;
+ dlm_lockres_get(res);
+ dl->dl_res = res;
+ } else
+ dl = NULL;
+ }
+
+ if (dl) {
+ spin_lock(&dl->dl_res->spinlock);
+ dump_lockres(dl->dl_res, dl->dl_buf, dl->dl_len - 1);
+ spin_unlock(&dl->dl_res->spinlock);
+ }
+
+ spin_unlock(&dlm->spinlock);
+
+ return dl;
+}
+
+static void lockres_seq_stop(struct seq_file *m, void *v)
+{
+}
+
+static void *lockres_seq_next(struct seq_file *m, void *v, loff_t *pos)
+{
+ return NULL;
+}
+
+static int lockres_seq_show(struct seq_file *s, void *v)
+{
+ struct debug_lockres *dl = (struct debug_lockres *)v;
+
+ seq_printf(s, "%s", dl->dl_buf);
+
+ return 0;
+}
+
+static struct seq_operations debug_lockres_ops = {
+ .start = lockres_seq_start,
+ .stop = lockres_seq_stop,
+ .next = lockres_seq_next,
+ .show = lockres_seq_show,
+};
+
+static int debug_lockres_open(struct inode *inode, struct file *file)
+{
+ struct dlm_ctxt *dlm = inode->i_private;
+ int ret = -ENOMEM;
+ struct seq_file *seq;
+ struct debug_lockres *dl = NULL;
+
+ dl = kzalloc(sizeof(struct debug_lockres), GFP_KERNEL);
+ if (!dl) {
+ mlog_errno(ret);
+ goto bail;
+ }
+
+ dl->dl_len = PAGE_SIZE;
+ dl->dl_buf = kmalloc(dl->dl_len, GFP_KERNEL);
+ if (!dl->dl_buf) {
+ mlog_errno(ret);
+ goto bail;
+ }
+
+ ret = seq_open(file, &debug_lockres_ops);
+ if (ret) {
+ mlog_errno(ret);
+ goto bail;
+ }
+
+ seq = (struct seq_file *) file->private_data;
+ seq->private = dl;
+
+ dlm_grab(dlm);
+ dl->dl_ctxt = dlm;
+
+ return 0;
+bail:
+ if (dl && dl->dl_buf)
+ kfree(dl->dl_buf);
+ if (dl)
+ kfree(dl);
+ return ret;
+}
+
+static int debug_lockres_release(struct inode *inode, struct file *file)
+{
+ struct seq_file *seq = (struct seq_file *)file->private_data;
+ struct debug_lockres *dl = (struct debug_lockres *)seq->private;
+
+ if (dl->dl_res)
+ dlm_lockres_put(dl->dl_res);
+ dlm_put(dl->dl_ctxt);
+ kfree(dl->dl_buf);
+ return seq_release_private(inode, file);
+}
+
+static struct file_operations debug_lockres_fops = {
+ .open = debug_lockres_open,
+ .release = debug_lockres_release,
+ .read = seq_read,
+ .llseek = seq_lseek,
+};
+/* end - debug lockres funcs */
+
/* begin - debug state funcs */
static int debug_state_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
{
@@ -976,6 +1211,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
goto bail;
}
+ /* for dumping lockres */
+ dc->debug_lockres_dentry =
+ debugfs_create_file(DLM_DEBUGFS_LOCKING_STATE,
+ S_IFREG|S_IRUSR,
+ dlm->dlm_debugfs_subroot,
+ dlm, &debug_lockres_fops);
+ if (!dc->debug_lockres_dentry) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+
dlm_debug_get(dc);
return 0;
@@ -989,6 +1235,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
if (dc) {
+ if (dc->debug_lockres_dentry)
+ debugfs_remove(dc->debug_lockres_dentry);
if (dc->debug_state_dentry)
debugfs_remove(dc->debug_state_dentry);
dlm_debug_put(dc);
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index 50cb10f..86d02f4 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -28,6 +28,7 @@
struct dlm_debug_ctxt {
struct kref debug_refcnt;
struct dentry *debug_state_dentry;
+ struct dentry *debug_lockres_dentry;
};
struct debug_buffer
@@ -36,6 +37,14 @@ struct debug_buffer
char *buf;
};
+struct debug_lockres
+{
+ int dl_len;
+ char *dl_buf;
+ struct dlm_ctxt *dl_ctxt;
+ struct dlm_lock_resource *dl_res;
+};
+
void dlm_remove_proc(void);
void dlm_init_proc(void);
void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file Sunil Mushran
@ 2008-02-28 16:51 ` Joel Becker
2008-02-28 17:11 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:51 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:53PM -0800, Sunil Mushran wrote:
> This patch dumps all the lockres' alongwith all the locks into
> a debugfs file. Useful for debugging.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Looks good modulo DEBUG_FS.
Joel
> ---
> fs/ocfs2/dlm/dlmdebug.c | 248 +++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 9 ++
> 2 files changed, 257 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 83f3ac6..905145a 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -705,7 +705,34 @@ EXPORT_SYMBOL_GPL(dlm_errname);
>
> #define DLM_DEBUGFS_DIR "o2dlm"
> #define DLM_DEBUGFS_DLM_STATE "dlm_state"
> +#define DLM_DEBUGFS_LOCKING_STATE "locking_state"
>
> +/* 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.
> + */
> +static int stringify_lockname(const char *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 += snprintf(buf + out, len - out, "%.*s%08x",
> + OCFS2_DENTRY_LOCK_INO_START - 1, lockname,
> + (unsigned int)be64_to_cpu(inode_blkno_be));
> + } else
> + out += snprintf(buf + out, len - out, "%.*s",
> + locklen, lockname);
> + return out;
> +}
> +
> /* begin - utils funcs */
> static void dlm_debug_free(struct kref *kref)
> {
> @@ -800,6 +827,214 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
> }
> /* end - util funcs */
>
> +/* begin - debug lockres funcs */
> +static int dump_lock(struct dlm_lock *lock, int list_type, char *buf, int len)
> +{
> + int out;
> +
> +#define DEBUG_LOCK_VERSION 1
> + spin_lock(&lock->spinlock);
> + out = snprintf(buf, len, "LOCK:%d,%d,%d,%d,%d,%d:%lld,%d,%d,%d,%d,%d,"
> + "%d,%d,%d,%d\n",
> + DEBUG_LOCK_VERSION,
> + list_type, lock->ml.type, lock->ml.convert_type,
> + lock->ml.node,
> + dlm_get_lock_cookie_node(be64_to_cpu(lock->ml.cookie)),
> + dlm_get_lock_cookie_seq(be64_to_cpu(lock->ml.cookie)),
> + !list_empty(&lock->ast_list),
> + !list_empty(&lock->bast_list),
> + lock->ast_pending, lock->bast_pending,
> + lock->convert_pending, lock->lock_pending,
> + lock->cancel_pending, lock->unlock_pending,
> + atomic_read(&lock->lock_refs.refcount));
> + spin_unlock(&lock->spinlock);
> +
> + return out;
> +}
> +
> +static int dump_lockres(struct dlm_lock_resource *res, char *buf, int len)
> +{
> + struct dlm_lock *lock;
> + int i;
> + int out = 0;
> +
> + out += snprintf(buf + out, len - out, "NAME:");
> + out += stringify_lockname(res->lockname.name, res->lockname.len,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> +#define DEBUG_LRES_VERSION 1
> + out += snprintf(buf + out, len - out,
> + "LRES:%d,%d,%d,%ld,%d,%d,%d,%d,%d,%d,%d\n",
> + DEBUG_LRES_VERSION,
> + res->owner, res->state, res->last_used,
> + !list_empty(&res->purge),
> + !list_empty(&res->dirty),
> + !list_empty(&res->recovering),
> + res->inflight_locks, res->migration_pending,
> + atomic_read(&res->asts_reserved),
> + atomic_read(&res->refs.refcount));
> +
> + /* refmap */
> + out += snprintf(buf + out, len - out, "RMAP:");
> + out += stringify_nodemap(res->refmap, O2NM_MAX_NODES,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> + /* lvb */
> + out += snprintf(buf + out, len - out, "LVBX:");
> + for (i = 0; i < DLM_LVB_LEN; i++)
> + out += snprintf(buf + out, len - out,
> + "%02x", (unsigned char)res->lvb[i]);
> + out += snprintf(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);
> +
> + out += snprintf(buf + out, len - out, "\n");
> +
> + return out;
> +}
> +
> +static void *lockres_seq_start(struct seq_file *m, loff_t *pos)
> +{
> + struct debug_lockres *dl = m->private;
> + struct dlm_ctxt *dlm = dl->dl_ctxt;
> + struct dlm_lock_resource *res = NULL;
> +
> + spin_lock(&dlm->spinlock);
> +
> + if (dl->dl_res) {
> + list_for_each_entry(res, &dl->dl_res->tracking, tracking) {
> + if (dl->dl_res) {
> + dlm_lockres_put(dl->dl_res);
> + dl->dl_res = NULL;
> + }
> + if (&res->tracking == &dlm->tracking_list) {
> + mlog(0, "End of list found, %p\n", res);
> + dl = NULL;
> + break;
> + }
> + dlm_lockres_get(res);
> + dl->dl_res = res;
> + break;
> + }
> + } else {
> + if (!list_empty(&dlm->tracking_list)) {
> + list_for_each_entry(res, &dlm->tracking_list, tracking)
> + break;
> + dlm_lockres_get(res);
> + dl->dl_res = res;
> + } else
> + dl = NULL;
> + }
> +
> + if (dl) {
> + spin_lock(&dl->dl_res->spinlock);
> + dump_lockres(dl->dl_res, dl->dl_buf, dl->dl_len - 1);
> + spin_unlock(&dl->dl_res->spinlock);
> + }
> +
> + spin_unlock(&dlm->spinlock);
> +
> + return dl;
> +}
> +
> +static void lockres_seq_stop(struct seq_file *m, void *v)
> +{
> +}
> +
> +static void *lockres_seq_next(struct seq_file *m, void *v, loff_t *pos)
> +{
> + return NULL;
> +}
> +
> +static int lockres_seq_show(struct seq_file *s, void *v)
> +{
> + struct debug_lockres *dl = (struct debug_lockres *)v;
> +
> + seq_printf(s, "%s", dl->dl_buf);
> +
> + return 0;
> +}
> +
> +static struct seq_operations debug_lockres_ops = {
> + .start = lockres_seq_start,
> + .stop = lockres_seq_stop,
> + .next = lockres_seq_next,
> + .show = lockres_seq_show,
> +};
> +
> +static int debug_lockres_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + int ret = -ENOMEM;
> + struct seq_file *seq;
> + struct debug_lockres *dl = NULL;
> +
> + dl = kzalloc(sizeof(struct debug_lockres), GFP_KERNEL);
> + if (!dl) {
> + mlog_errno(ret);
> + goto bail;
> + }
> +
> + dl->dl_len = PAGE_SIZE;
> + dl->dl_buf = kmalloc(dl->dl_len, GFP_KERNEL);
> + if (!dl->dl_buf) {
> + mlog_errno(ret);
> + goto bail;
> + }
> +
> + ret = seq_open(file, &debug_lockres_ops);
> + if (ret) {
> + mlog_errno(ret);
> + goto bail;
> + }
> +
> + seq = (struct seq_file *) file->private_data;
> + seq->private = dl;
> +
> + dlm_grab(dlm);
> + dl->dl_ctxt = dlm;
> +
> + return 0;
> +bail:
> + if (dl && dl->dl_buf)
> + kfree(dl->dl_buf);
> + if (dl)
> + kfree(dl);
> + return ret;
> +}
> +
> +static int debug_lockres_release(struct inode *inode, struct file *file)
> +{
> + struct seq_file *seq = (struct seq_file *)file->private_data;
> + struct debug_lockres *dl = (struct debug_lockres *)seq->private;
> +
> + if (dl->dl_res)
> + dlm_lockres_put(dl->dl_res);
> + dlm_put(dl->dl_ctxt);
> + kfree(dl->dl_buf);
> + return seq_release_private(inode, file);
> +}
> +
> +static struct file_operations debug_lockres_fops = {
> + .open = debug_lockres_open,
> + .release = debug_lockres_release,
> + .read = seq_read,
> + .llseek = seq_lseek,
> +};
> +/* end - debug lockres funcs */
> +
> /* begin - debug state funcs */
> static int debug_state_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> {
> @@ -976,6 +1211,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + /* for dumping lockres */
> + dc->debug_lockres_dentry =
> + debugfs_create_file(DLM_DEBUGFS_LOCKING_STATE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_lockres_fops);
> + if (!dc->debug_lockres_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> dlm_debug_get(dc);
> return 0;
>
> @@ -989,6 +1235,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
>
> if (dc) {
> + if (dc->debug_lockres_dentry)
> + debugfs_remove(dc->debug_lockres_dentry);
> if (dc->debug_state_dentry)
> debugfs_remove(dc->debug_state_dentry);
> dlm_debug_put(dc);
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index 50cb10f..86d02f4 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -28,6 +28,7 @@
> struct dlm_debug_ctxt {
> struct kref debug_refcnt;
> struct dentry *debug_state_dentry;
> + struct dentry *debug_lockres_dentry;
> };
>
> struct debug_buffer
> @@ -36,6 +37,14 @@ struct debug_buffer
> char *buf;
> };
>
> +struct debug_lockres
> +{
> + int dl_len;
> + char *dl_buf;
> + struct dlm_ctxt *dl_ctxt;
> + struct dlm_lock_resource *dl_res;
> +};
> +
> void dlm_remove_proc(void);
> void dlm_init_proc(void);
> void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Sometimes when reading Goethe I have the paralyzing suspicion
that he is trying to be funny."
- Guy Davenport
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file Sunil Mushran
2008-02-28 16:51 ` Joel Becker
@ 2008-02-28 17:11 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 17:11 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:53PM -0800, Sunil Mushran wrote:
> This patch dumps all the lockres' alongwith all the locks into
> a debugfs file. Useful for debugging.
This one also needs checkpatch.pl.
Joel
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
> ---
> fs/ocfs2/dlm/dlmdebug.c | 248 +++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 9 ++
> 2 files changed, 257 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 83f3ac6..905145a 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -705,7 +705,34 @@ EXPORT_SYMBOL_GPL(dlm_errname);
>
> #define DLM_DEBUGFS_DIR "o2dlm"
> #define DLM_DEBUGFS_DLM_STATE "dlm_state"
> +#define DLM_DEBUGFS_LOCKING_STATE "locking_state"
>
> +/* 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.
> + */
> +static int stringify_lockname(const char *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 += snprintf(buf + out, len - out, "%.*s%08x",
> + OCFS2_DENTRY_LOCK_INO_START - 1, lockname,
> + (unsigned int)be64_to_cpu(inode_blkno_be));
> + } else
> + out += snprintf(buf + out, len - out, "%.*s",
> + locklen, lockname);
> + return out;
> +}
> +
> /* begin - utils funcs */
> static void dlm_debug_free(struct kref *kref)
> {
> @@ -800,6 +827,214 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
> }
> /* end - util funcs */
>
> +/* begin - debug lockres funcs */
> +static int dump_lock(struct dlm_lock *lock, int list_type, char *buf, int len)
> +{
> + int out;
> +
> +#define DEBUG_LOCK_VERSION 1
> + spin_lock(&lock->spinlock);
> + out = snprintf(buf, len, "LOCK:%d,%d,%d,%d,%d,%d:%lld,%d,%d,%d,%d,%d,"
> + "%d,%d,%d,%d\n",
> + DEBUG_LOCK_VERSION,
> + list_type, lock->ml.type, lock->ml.convert_type,
> + lock->ml.node,
> + dlm_get_lock_cookie_node(be64_to_cpu(lock->ml.cookie)),
> + dlm_get_lock_cookie_seq(be64_to_cpu(lock->ml.cookie)),
> + !list_empty(&lock->ast_list),
> + !list_empty(&lock->bast_list),
> + lock->ast_pending, lock->bast_pending,
> + lock->convert_pending, lock->lock_pending,
> + lock->cancel_pending, lock->unlock_pending,
> + atomic_read(&lock->lock_refs.refcount));
> + spin_unlock(&lock->spinlock);
> +
> + return out;
> +}
> +
> +static int dump_lockres(struct dlm_lock_resource *res, char *buf, int len)
> +{
> + struct dlm_lock *lock;
> + int i;
> + int out = 0;
> +
> + out += snprintf(buf + out, len - out, "NAME:");
> + out += stringify_lockname(res->lockname.name, res->lockname.len,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> +#define DEBUG_LRES_VERSION 1
> + out += snprintf(buf + out, len - out,
> + "LRES:%d,%d,%d,%ld,%d,%d,%d,%d,%d,%d,%d\n",
> + DEBUG_LRES_VERSION,
> + res->owner, res->state, res->last_used,
> + !list_empty(&res->purge),
> + !list_empty(&res->dirty),
> + !list_empty(&res->recovering),
> + res->inflight_locks, res->migration_pending,
> + atomic_read(&res->asts_reserved),
> + atomic_read(&res->refs.refcount));
> +
> + /* refmap */
> + out += snprintf(buf + out, len - out, "RMAP:");
> + out += stringify_nodemap(res->refmap, O2NM_MAX_NODES,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> + /* lvb */
> + out += snprintf(buf + out, len - out, "LVBX:");
> + for (i = 0; i < DLM_LVB_LEN; i++)
> + out += snprintf(buf + out, len - out,
> + "%02x", (unsigned char)res->lvb[i]);
> + out += snprintf(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);
> +
> + out += snprintf(buf + out, len - out, "\n");
> +
> + return out;
> +}
> +
> +static void *lockres_seq_start(struct seq_file *m, loff_t *pos)
> +{
> + struct debug_lockres *dl = m->private;
> + struct dlm_ctxt *dlm = dl->dl_ctxt;
> + struct dlm_lock_resource *res = NULL;
> +
> + spin_lock(&dlm->spinlock);
> +
> + if (dl->dl_res) {
> + list_for_each_entry(res, &dl->dl_res->tracking, tracking) {
> + if (dl->dl_res) {
> + dlm_lockres_put(dl->dl_res);
> + dl->dl_res = NULL;
> + }
> + if (&res->tracking == &dlm->tracking_list) {
> + mlog(0, "End of list found, %p\n", res);
> + dl = NULL;
> + break;
> + }
> + dlm_lockres_get(res);
> + dl->dl_res = res;
> + break;
> + }
> + } else {
> + if (!list_empty(&dlm->tracking_list)) {
> + list_for_each_entry(res, &dlm->tracking_list, tracking)
> + break;
> + dlm_lockres_get(res);
> + dl->dl_res = res;
> + } else
> + dl = NULL;
> + }
> +
> + if (dl) {
> + spin_lock(&dl->dl_res->spinlock);
> + dump_lockres(dl->dl_res, dl->dl_buf, dl->dl_len - 1);
> + spin_unlock(&dl->dl_res->spinlock);
> + }
> +
> + spin_unlock(&dlm->spinlock);
> +
> + return dl;
> +}
> +
> +static void lockres_seq_stop(struct seq_file *m, void *v)
> +{
> +}
> +
> +static void *lockres_seq_next(struct seq_file *m, void *v, loff_t *pos)
> +{
> + return NULL;
> +}
> +
> +static int lockres_seq_show(struct seq_file *s, void *v)
> +{
> + struct debug_lockres *dl = (struct debug_lockres *)v;
> +
> + seq_printf(s, "%s", dl->dl_buf);
> +
> + return 0;
> +}
> +
> +static struct seq_operations debug_lockres_ops = {
> + .start = lockres_seq_start,
> + .stop = lockres_seq_stop,
> + .next = lockres_seq_next,
> + .show = lockres_seq_show,
> +};
> +
> +static int debug_lockres_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + int ret = -ENOMEM;
> + struct seq_file *seq;
> + struct debug_lockres *dl = NULL;
> +
> + dl = kzalloc(sizeof(struct debug_lockres), GFP_KERNEL);
> + if (!dl) {
> + mlog_errno(ret);
> + goto bail;
> + }
> +
> + dl->dl_len = PAGE_SIZE;
> + dl->dl_buf = kmalloc(dl->dl_len, GFP_KERNEL);
> + if (!dl->dl_buf) {
> + mlog_errno(ret);
> + goto bail;
> + }
> +
> + ret = seq_open(file, &debug_lockres_ops);
> + if (ret) {
> + mlog_errno(ret);
> + goto bail;
> + }
> +
> + seq = (struct seq_file *) file->private_data;
> + seq->private = dl;
> +
> + dlm_grab(dlm);
> + dl->dl_ctxt = dlm;
> +
> + return 0;
> +bail:
> + if (dl && dl->dl_buf)
> + kfree(dl->dl_buf);
> + if (dl)
> + kfree(dl);
> + return ret;
> +}
> +
> +static int debug_lockres_release(struct inode *inode, struct file *file)
> +{
> + struct seq_file *seq = (struct seq_file *)file->private_data;
> + struct debug_lockres *dl = (struct debug_lockres *)seq->private;
> +
> + if (dl->dl_res)
> + dlm_lockres_put(dl->dl_res);
> + dlm_put(dl->dl_ctxt);
> + kfree(dl->dl_buf);
> + return seq_release_private(inode, file);
> +}
> +
> +static struct file_operations debug_lockres_fops = {
> + .open = debug_lockres_open,
> + .release = debug_lockres_release,
> + .read = seq_read,
> + .llseek = seq_lseek,
> +};
> +/* end - debug lockres funcs */
> +
> /* begin - debug state funcs */
> static int debug_state_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> {
> @@ -976,6 +1211,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + /* for dumping lockres */
> + dc->debug_lockres_dentry =
> + debugfs_create_file(DLM_DEBUGFS_LOCKING_STATE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_lockres_fops);
> + if (!dc->debug_lockres_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> dlm_debug_get(dc);
> return 0;
>
> @@ -989,6 +1235,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
>
> if (dc) {
> + if (dc->debug_lockres_dentry)
> + debugfs_remove(dc->debug_lockres_dentry);
> if (dc->debug_state_dentry)
> debugfs_remove(dc->debug_state_dentry);
> dlm_debug_put(dc);
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index 50cb10f..86d02f4 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -28,6 +28,7 @@
> struct dlm_debug_ctxt {
> struct kref debug_refcnt;
> struct dentry *debug_state_dentry;
> + struct dentry *debug_lockres_dentry;
> };
>
> struct debug_buffer
> @@ -36,6 +37,14 @@ struct debug_buffer
> char *buf;
> };
>
> +struct debug_lockres
> +{
> + int dl_len;
> + char *dl_buf;
> + struct dlm_ctxt *dl_ctxt;
> + struct dlm_lock_resource *dl_res;
> +};
> +
> void dlm_remove_proc(void);
> void dlm_init_proc(void);
> void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
Joel's First Law:
Nature abhors a GUI.
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 03/18] ocfs2_dlm: Add missing dlm_lock_put()s
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (12 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 09/18] ocfs2_dlm: Dumps the lockres' into a debugfs file Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 14:39 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file Sunil Mushran
` (3 subsequent siblings)
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
Normally locks for remote nodes are freed when that node sends an UNLOCK
message to the master. The master node tags an DLM_UNLOCK_FREE_LOCK action
to do an extra put on the lock at the end.
However, there are times when the master node has to free the locks for the
remote nodes forcibly.
Two cases when this happens are:
1. When the master has migrated the lockres plus all locks to another node.
2. When the master is clearing all the locks of a dead node.
It was in the above two conditions that the dlm was missing the extra put.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmmaster.c | 2 ++
fs/ocfs2/dlm/dlmrecovery.c | 6 ++++++
2 files changed, 8 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index 939b863..8e3c40e 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -2973,6 +2973,8 @@ static void dlm_remove_nonlocal_locks(struct dlm_ctxt *dlm,
dlm_lockres_clear_refmap_bit(lock->ml.node, res);
list_del_init(&lock->list);
dlm_lock_put(lock);
+ /* DLM_UNLOCK_FREE_LOCK put */
+ dlm_lock_put(lock);
}
}
queue++;
diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c
index 4294d76..455dc72 100644
--- a/fs/ocfs2/dlm/dlmrecovery.c
+++ b/fs/ocfs2/dlm/dlmrecovery.c
@@ -2133,6 +2133,8 @@ static void dlm_free_dead_locks(struct dlm_ctxt *dlm,
if (lock->ml.node == dead_node) {
list_del_init(&lock->list);
dlm_lock_put(lock);
+ /* DLM_UNLOCK_FREE_LOCK put */
+ dlm_lock_put(lock);
freed++;
}
}
@@ -2140,6 +2142,8 @@ static void dlm_free_dead_locks(struct dlm_ctxt *dlm,
if (lock->ml.node == dead_node) {
list_del_init(&lock->list);
dlm_lock_put(lock);
+ /* DLM_UNLOCK_FREE_LOCK put */
+ dlm_lock_put(lock);
freed++;
}
}
@@ -2147,6 +2151,8 @@ static void dlm_free_dead_locks(struct dlm_ctxt *dlm,
if (lock->ml.node == dead_node) {
list_del_init(&lock->list);
dlm_lock_put(lock);
+ /* DLM_UNLOCK_FREE_LOCK put */
+ dlm_lock_put(lock);
freed++;
}
}
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 03/18] ocfs2_dlm: Add missing dlm_lock_put()s
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 03/18] ocfs2_dlm: Add missing dlm_lock_put()s Sunil Mushran
@ 2008-02-28 14:39 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 14:39 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:47PM -0800, Sunil Mushran wrote:
> Normally locks for remote nodes are freed when that node sends an UNLOCK
> message to the master. The master node tags an DLM_UNLOCK_FREE_LOCK action
> to do an extra put on the lock at the end.
>
> However, there are times when the master node has to free the locks for the
> remote nodes forcibly.
>
> Two cases when this happens are:
> 1. When the master has migrated the lockres plus all locks to another node.
> 2. When the master is clearing all the locks of a dead node.
>
> It was in the above two conditions that the dlm was missing the extra put.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
> ---
> fs/ocfs2/dlm/dlmmaster.c | 2 ++
> fs/ocfs2/dlm/dlmrecovery.c | 6 ++++++
> 2 files changed, 8 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
> index 939b863..8e3c40e 100644
> --- a/fs/ocfs2/dlm/dlmmaster.c
> +++ b/fs/ocfs2/dlm/dlmmaster.c
> @@ -2973,6 +2973,8 @@ static void dlm_remove_nonlocal_locks(struct dlm_ctxt *dlm,
> dlm_lockres_clear_refmap_bit(lock->ml.node, res);
> list_del_init(&lock->list);
> dlm_lock_put(lock);
> + /* DLM_UNLOCK_FREE_LOCK put */
> + dlm_lock_put(lock);
Good description in the patch, but it's opaque here. Can we
have a comment like:
/* Can't schedule DLM_UNLOCK_FREE_LOCK,
* do it here. */
Joel
--
"Depend on the rabbit's foot if you will, but remember, it didn't
help the rabbit."
- R. E. Shay
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (13 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 03/18] ocfs2_dlm: Add missing dlm_lock_put()s Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:53 ` Joel Becker
2008-02-28 17:11 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 14/18] ocfs2_dlm: Remove the proc interface Sunil Mushran
` (2 subsequent siblings)
17 siblings, 2 replies; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch dumps all the tasks on the workqueue it can fit in one page
into a debugfs file. Useful for debugging.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmdebug.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmdebug.h | 1 +
2 files changed, 94 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index ffdc976..1864731 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -708,6 +708,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
#define DLM_DEBUGFS_LOCKING_STATE "locking_state"
#define DLM_DEBUGFS_MLE_STATE "mle_state"
#define DLM_DEBUGFS_PURGE_LIST "purge_list"
+#define DLM_DEBUGFS_WORK_QUEUE "work_queue"
/* 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.
@@ -829,6 +830,85 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
}
/* end - util funcs */
+/* begin - work queue funcs */
+static int debug_workqueue_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
+{
+ struct dlm_work_item *wi;
+ int out = 0;
+ unsigned long total = 0;
+
+ out += snprintf(db->buf + out, db->len - out,
+ "Dumping Workqueue for Domain: %s\n", dlm->name);
+
+ spin_lock(&dlm->work_lock);
+ list_for_each_entry(wi, &dlm->work_list, list) {
+ ++total;
+ if (db->len - out < 100)
+ continue;
+ if (wi->func == dlm_request_all_locks_worker) {
+ out += snprintf(db->buf + out, db->len - out,
+ "RequestAllLocks, "
+ "recomaster=%d, deadnode=%d\n",
+ wi->u.ral.reco_master,
+ wi->u.ral.dead_node);
+ } else if (wi->func == dlm_mig_lockres_worker) {
+ out += snprintf(db->buf + out, db->len - out,
+ "MigrateLockres, ");
+ out += stringify_lockname(wi->u.ml.lockres->lockname.name,
+ wi->u.ml.lockres->lockname.len,
+ db->buf + out, db->len - out);
+ out += snprintf(db->buf + out, db->len - out,
+ " master=%d\n", wi->u.ml.real_master);
+ } else if (wi->func == dlm_assert_master_worker) {
+ out += snprintf(db->buf + out, db->len - out,
+ "AssertMaster, ");
+ out += stringify_lockname(wi->u.am.lockres->lockname.name,
+ wi->u.am.lockres->lockname.len,
+ db->buf + out, db->len - out);
+ out += snprintf(db->buf + out, db->len - out,
+ " from=%d, flags=0x%X, ignore=%d\n",
+ wi->u.am.request_from,
+ wi->u.am.flags,
+ wi->u.am.ignore_higher);
+ } else {
+ out += snprintf(db->buf + out, db->len - out,
+ "Unknown, 0x%p\n", wi->func);
+ }
+ }
+ spin_unlock(&dlm->work_lock);
+
+ out += snprintf(db->buf + out, db->len - out,
+ "Total on list: %ld\n", total);
+
+ return out;
+}
+
+static int debug_workqueue_open(struct inode *inode, struct file *file)
+{
+ struct dlm_ctxt *dlm = inode->i_private;
+ struct debug_buffer *db;
+
+ db = debug_buffer_allocate();
+ if (!db)
+ goto bail;
+
+ db->len = debug_workqueue_print(dlm, db);
+
+ file->private_data = db;
+
+ return 0;
+bail:
+ return -ENOMEM;
+}
+
+static struct file_operations debug_workqueue_fops = {
+ .open = debug_workqueue_open,
+ .release = debug_buffer_release,
+ .read = debug_buffer_read,
+ .llseek = debug_buffer_llseek,
+};
+/* end - work queue funcs */
+
/* begin - purge list funcs */
static int debug_purgelist_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
{
@@ -1408,6 +1488,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
goto bail;
}
+ /* for dumping the dlm work queue */
+ dc->debug_workqueue_dentry =
+ debugfs_create_file(DLM_DEBUGFS_WORK_QUEUE,
+ S_IFREG|S_IRUSR,
+ dlm->dlm_debugfs_subroot,
+ dlm, &debug_workqueue_fops);
+ if (!dc->debug_workqueue_dentry) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+
dlm_debug_get(dc);
return 0;
@@ -1421,6 +1512,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
if (dc) {
+ if (dc->debug_workqueue_dentry)
+ debugfs_remove(dc->debug_workqueue_dentry);
if (dc->debug_purgelist_dentry)
debugfs_remove(dc->debug_purgelist_dentry);
if (dc->debug_mle_dentry)
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index ca7bc32..fcc19c8 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -31,6 +31,7 @@ struct dlm_debug_ctxt {
struct dentry *debug_lockres_dentry;
struct dentry *debug_mle_dentry;
struct dentry *debug_purgelist_dentry;
+ struct dentry *debug_workqueue_dentry;
};
struct debug_buffer
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file Sunil Mushran
@ 2008-02-28 16:53 ` Joel Becker
2008-02-28 17:11 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:53 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:57PM -0800, Sunil Mushran wrote:
> This patch dumps all the tasks on the workqueue it can fit in one page
> into a debugfs file. Useful for debugging.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Looks good modulo DEBUG_FS.
Joel
> ---
> fs/ocfs2/dlm/dlmdebug.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 1 +
> 2 files changed, 94 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index ffdc976..1864731 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -708,6 +708,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
> #define DLM_DEBUGFS_LOCKING_STATE "locking_state"
> #define DLM_DEBUGFS_MLE_STATE "mle_state"
> #define DLM_DEBUGFS_PURGE_LIST "purge_list"
> +#define DLM_DEBUGFS_WORK_QUEUE "work_queue"
>
> /* 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.
> @@ -829,6 +830,85 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
> }
> /* end - util funcs */
>
> +/* begin - work queue funcs */
> +static int debug_workqueue_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> +{
> + struct dlm_work_item *wi;
> + int out = 0;
> + unsigned long total = 0;
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Dumping Workqueue for Domain: %s\n", dlm->name);
> +
> + spin_lock(&dlm->work_lock);
> + list_for_each_entry(wi, &dlm->work_list, list) {
> + ++total;
> + if (db->len - out < 100)
> + continue;
> + if (wi->func == dlm_request_all_locks_worker) {
> + out += snprintf(db->buf + out, db->len - out,
> + "RequestAllLocks, "
> + "recomaster=%d, deadnode=%d\n",
> + wi->u.ral.reco_master,
> + wi->u.ral.dead_node);
> + } else if (wi->func == dlm_mig_lockres_worker) {
> + out += snprintf(db->buf + out, db->len - out,
> + "MigrateLockres, ");
> + out += stringify_lockname(wi->u.ml.lockres->lockname.name,
> + wi->u.ml.lockres->lockname.len,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out,
> + " master=%d\n", wi->u.ml.real_master);
> + } else if (wi->func == dlm_assert_master_worker) {
> + out += snprintf(db->buf + out, db->len - out,
> + "AssertMaster, ");
> + out += stringify_lockname(wi->u.am.lockres->lockname.name,
> + wi->u.am.lockres->lockname.len,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out,
> + " from=%d, flags=0x%X, ignore=%d\n",
> + wi->u.am.request_from,
> + wi->u.am.flags,
> + wi->u.am.ignore_higher);
> + } else {
> + out += snprintf(db->buf + out, db->len - out,
> + "Unknown, 0x%p\n", wi->func);
> + }
> + }
> + spin_unlock(&dlm->work_lock);
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Total on list: %ld\n", total);
> +
> + return out;
> +}
> +
> +static int debug_workqueue_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + struct debug_buffer *db;
> +
> + db = debug_buffer_allocate();
> + if (!db)
> + goto bail;
> +
> + db->len = debug_workqueue_print(dlm, db);
> +
> + file->private_data = db;
> +
> + return 0;
> +bail:
> + return -ENOMEM;
> +}
> +
> +static struct file_operations debug_workqueue_fops = {
> + .open = debug_workqueue_open,
> + .release = debug_buffer_release,
> + .read = debug_buffer_read,
> + .llseek = debug_buffer_llseek,
> +};
> +/* end - work queue funcs */
> +
> /* begin - purge list funcs */
> static int debug_purgelist_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> {
> @@ -1408,6 +1488,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + /* for dumping the dlm work queue */
> + dc->debug_workqueue_dentry =
> + debugfs_create_file(DLM_DEBUGFS_WORK_QUEUE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_workqueue_fops);
> + if (!dc->debug_workqueue_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> dlm_debug_get(dc);
> return 0;
>
> @@ -1421,6 +1512,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
>
> if (dc) {
> + if (dc->debug_workqueue_dentry)
> + debugfs_remove(dc->debug_workqueue_dentry);
> if (dc->debug_purgelist_dentry)
> debugfs_remove(dc->debug_purgelist_dentry);
> if (dc->debug_mle_dentry)
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index ca7bc32..fcc19c8 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -31,6 +31,7 @@ struct dlm_debug_ctxt {
> struct dentry *debug_lockres_dentry;
> struct dentry *debug_mle_dentry;
> struct dentry *debug_purgelist_dentry;
> + struct dentry *debug_workqueue_dentry;
> };
>
> struct debug_buffer
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Sometimes when reading Goethe I have the paralyzing suspicion
that he is trying to be funny."
- Guy Davenport
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file Sunil Mushran
2008-02-28 16:53 ` Joel Becker
@ 2008-02-28 17:11 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 17:11 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:57PM -0800, Sunil Mushran wrote:
> This patch dumps all the tasks on the workqueue it can fit in one page
> into a debugfs file. Useful for debugging.
Check the warnings from checkpatch.pl. I'm not sure if they're
worth fixing, but have a look.
Joel
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
> ---
> fs/ocfs2/dlm/dlmdebug.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 1 +
> 2 files changed, 94 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index ffdc976..1864731 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -708,6 +708,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
> #define DLM_DEBUGFS_LOCKING_STATE "locking_state"
> #define DLM_DEBUGFS_MLE_STATE "mle_state"
> #define DLM_DEBUGFS_PURGE_LIST "purge_list"
> +#define DLM_DEBUGFS_WORK_QUEUE "work_queue"
>
> /* 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.
> @@ -829,6 +830,85 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
> }
> /* end - util funcs */
>
> +/* begin - work queue funcs */
> +static int debug_workqueue_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> +{
> + struct dlm_work_item *wi;
> + int out = 0;
> + unsigned long total = 0;
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Dumping Workqueue for Domain: %s\n", dlm->name);
> +
> + spin_lock(&dlm->work_lock);
> + list_for_each_entry(wi, &dlm->work_list, list) {
> + ++total;
> + if (db->len - out < 100)
> + continue;
> + if (wi->func == dlm_request_all_locks_worker) {
> + out += snprintf(db->buf + out, db->len - out,
> + "RequestAllLocks, "
> + "recomaster=%d, deadnode=%d\n",
> + wi->u.ral.reco_master,
> + wi->u.ral.dead_node);
> + } else if (wi->func == dlm_mig_lockres_worker) {
> + out += snprintf(db->buf + out, db->len - out,
> + "MigrateLockres, ");
> + out += stringify_lockname(wi->u.ml.lockres->lockname.name,
> + wi->u.ml.lockres->lockname.len,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out,
> + " master=%d\n", wi->u.ml.real_master);
> + } else if (wi->func == dlm_assert_master_worker) {
> + out += snprintf(db->buf + out, db->len - out,
> + "AssertMaster, ");
> + out += stringify_lockname(wi->u.am.lockres->lockname.name,
> + wi->u.am.lockres->lockname.len,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out,
> + " from=%d, flags=0x%X, ignore=%d\n",
> + wi->u.am.request_from,
> + wi->u.am.flags,
> + wi->u.am.ignore_higher);
> + } else {
> + out += snprintf(db->buf + out, db->len - out,
> + "Unknown, 0x%p\n", wi->func);
> + }
> + }
> + spin_unlock(&dlm->work_lock);
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Total on list: %ld\n", total);
> +
> + return out;
> +}
> +
> +static int debug_workqueue_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + struct debug_buffer *db;
> +
> + db = debug_buffer_allocate();
> + if (!db)
> + goto bail;
> +
> + db->len = debug_workqueue_print(dlm, db);
> +
> + file->private_data = db;
> +
> + return 0;
> +bail:
> + return -ENOMEM;
> +}
> +
> +static struct file_operations debug_workqueue_fops = {
> + .open = debug_workqueue_open,
> + .release = debug_buffer_release,
> + .read = debug_buffer_read,
> + .llseek = debug_buffer_llseek,
> +};
> +/* end - work queue funcs */
> +
> /* begin - purge list funcs */
> static int debug_purgelist_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> {
> @@ -1408,6 +1488,17 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + /* for dumping the dlm work queue */
> + dc->debug_workqueue_dentry =
> + debugfs_create_file(DLM_DEBUGFS_WORK_QUEUE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_workqueue_fops);
> + if (!dc->debug_workqueue_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> dlm_debug_get(dc);
> return 0;
>
> @@ -1421,6 +1512,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
>
> if (dc) {
> + if (dc->debug_workqueue_dentry)
> + debugfs_remove(dc->debug_workqueue_dentry);
> if (dc->debug_purgelist_dentry)
> debugfs_remove(dc->debug_purgelist_dentry);
> if (dc->debug_mle_dentry)
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index ca7bc32..fcc19c8 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -31,6 +31,7 @@ struct dlm_debug_ctxt {
> struct dentry *debug_lockres_dentry;
> struct dentry *debug_mle_dentry;
> struct dentry *debug_purgelist_dentry;
> + struct dentry *debug_workqueue_dentry;
> };
>
> struct debug_buffer
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
There are morethings in heaven and earth, Horatio,
Than are dreamt of in your philosophy.
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 14/18] ocfs2_dlm: Remove the proc interface
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (14 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 13/18] ocfs2_dlm: Dumps the workqueue into a debugfs file Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:55 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file Sunil Mushran
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 11/18] ocfs2_dlm: Dumps the mles into " Sunil Mushran
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
The proc debug interface is no longer needed as all the functionality
it provided has been moved to the debugfs interface.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 2 -
fs/ocfs2/dlm/dlmdebug.c | 458 ----------------------------------------------
fs/ocfs2/dlm/dlmdebug.h | 7 -
fs/ocfs2/dlm/dlmdomain.c | 8 -
4 files changed, 0 insertions(+), 475 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index 41c8d90..1d05ebf 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -155,8 +155,6 @@ struct dlm_ctxt
struct list_head master_list;
struct list_head mle_hb_events;
- struct proc_dir_entry *dlm_proc;
-
/* these give a really vague idea of the system load */
atomic_t local_resources;
atomic_t remote_resources;
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index 1864731..e8fa5a9 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -30,7 +30,6 @@
#include <linux/utsname.h>
#include <linux/sysctl.h>
#include <linux/spinlock.h>
-#include <linux/proc_fs.h>
#include <linux/debugfs.h>
#include "cluster/heartbeat.h"
@@ -39,8 +38,6 @@
#include "dlmapi.h"
#include "dlmcommon.h"
-#include "dlmdebug.h"
-
#include "dlmdomain.h"
#include "dlmdebug.h"
@@ -49,233 +46,6 @@
static struct dentry *dlm_debugfs_root = NULL;
-static int dlm_dump_all_lock_resources(const char __user *data,
- unsigned int len);
-static void dlm_dump_purge_list(struct dlm_ctxt *dlm);
-static int dlm_dump_all_purge_lists(const char __user *data, unsigned int len);
-static int dlm_trigger_migration(const char __user *data, unsigned int len);
-static int dlm_dump_one_lock_resource(const char __user *data,
- unsigned int len);
-static int dlm_dump_work_queues(const char __user *data, unsigned int len);
-
-static int dlm_parse_domain_and_lockres(char *buf, unsigned int len,
- struct dlm_ctxt **dlm,
- struct dlm_lock_resource **res);
-
-static int dlm_proc_stats(char *page, char **start, off_t off,
- int count, int *eof, void *data);
-
-typedef int (dlm_debug_func_t)(const char __user *data, unsigned int len);
-
-struct dlm_debug_funcs
-{
- char key;
- dlm_debug_func_t *func;
-};
-
-static struct dlm_debug_funcs dlm_debug_map[] = {
- { 'r', dlm_dump_all_lock_resources },
- { 'R', dlm_dump_one_lock_resource },
- { 'm', dlm_dump_all_mles },
- { 'p', dlm_dump_all_purge_lists },
- { 'M', dlm_trigger_migration },
- { 'w', dlm_dump_work_queues }
-};
-static int dlm_debug_map_sz = (sizeof(dlm_debug_map) /
- sizeof(struct dlm_debug_funcs));
-
-static ssize_t write_dlm_debug(struct file *file, const char __user *buf,
- size_t count, loff_t *ppos)
-{
- int i;
- char c;
- dlm_debug_func_t *fn;
- int ret;
-
- mlog(0, "(%p, %p, %u, %lld)\n",
- file, buf, (unsigned int)count, (long long)*ppos);
- ret = 0;
- if (count<=0)
- goto done;
-
- ret = -EFAULT;
- if (get_user(c, buf))
- goto done;
-
- ret = count;
- for (i=0; i < dlm_debug_map_sz; i++) {
- struct dlm_debug_funcs *d = &dlm_debug_map[i];
- if (c == d->key) {
- fn = d->func;
- if (fn)
- ret = (fn)(buf, count);
- goto done;
- }
- }
-done:
- return ret;
-}
-
-static struct file_operations dlm_debug_operations = {
- .write = write_dlm_debug,
-};
-
-#define OCFS2_DLM_PROC_PATH "fs/ocfs2_dlm"
-#define DLM_DEBUG_PROC_NAME "debug"
-#define DLM_STAT_PROC_NAME "stat"
-
-static struct proc_dir_entry *ocfs2_dlm_proc;
-
-void dlm_remove_proc(void)
-{
- if (ocfs2_dlm_proc) {
- remove_proc_entry(DLM_DEBUG_PROC_NAME, ocfs2_dlm_proc);
- remove_proc_entry(OCFS2_DLM_PROC_PATH, NULL);
- }
-}
-
-void dlm_init_proc(void)
-{
- struct proc_dir_entry *entry;
-
- ocfs2_dlm_proc = proc_mkdir(OCFS2_DLM_PROC_PATH, NULL);
- if (!ocfs2_dlm_proc) {
- mlog_errno(-ENOMEM);
- return;
- }
-
- entry = create_proc_entry(DLM_DEBUG_PROC_NAME, S_IWUSR,
- ocfs2_dlm_proc);
- if (entry)
- entry->proc_fops = &dlm_debug_operations;
-}
-
-static int dlm_proc_stats(char *page, char **start, off_t off,
- int count, int *eof, void *data)
-{
- int len;
- struct dlm_ctxt *dlm = data;
-
- len = sprintf(page, "local=%d, remote=%d, unknown=%d, key=0x%08x\n",
- atomic_read(&dlm->local_resources),
- atomic_read(&dlm->remote_resources),
- atomic_read(&dlm->unknown_resources),
- dlm->key);
-
- if (len <= off + count)
- *eof = 1;
-
- *start = page + off;
- len -= off;
- if (len > count)
- len = count;
- if (len < 0)
- len = 0;
-
- return len;
-}
-
-void dlm_proc_add_domain(struct dlm_ctxt *dlm)
-{
- struct proc_dir_entry *entry;
-
- dlm->dlm_proc = proc_mkdir(dlm->name, ocfs2_dlm_proc);
- if (dlm->dlm_proc) {
- entry = create_proc_read_entry(DLM_STAT_PROC_NAME,
- S_IFREG | S_IRUGO, dlm->dlm_proc,
- dlm_proc_stats, (char *)dlm);
- if (entry)
- entry->owner = THIS_MODULE;
- }
-}
-
-void dlm_proc_del_domain(struct dlm_ctxt *dlm)
-{
- if (dlm->dlm_proc) {
- remove_proc_entry(DLM_STAT_PROC_NAME, dlm->dlm_proc);
- remove_proc_entry(dlm->name, ocfs2_dlm_proc);
- }
-}
-
-/* lock resource printing is usually very important (printed
- * right before a BUG in some cases), but we'd like to be
- * able to shut it off if needed, hence the KERN_NOTICE level */
-static int dlm_dump_all_lock_resources(const char __user *data,
- unsigned int len)
-{
- struct dlm_ctxt *dlm;
- struct list_head *iter;
-
- mlog(ML_NOTICE, "dumping ALL dlm state for node %s\n",
-#ifndef NO_SYSTEM_UTSNAME
- system_utsname.nodename);
-#else
- init_uts_ns.name.nodename);
-#endif
- spin_lock(&dlm_domain_lock);
- list_for_each(iter, &dlm_domains) {
- dlm = list_entry (iter, struct dlm_ctxt, list);
- dlm_dump_lock_resources(dlm);
- }
- spin_unlock(&dlm_domain_lock);
- return len;
-}
-
-static int dlm_dump_one_lock_resource(const char __user *data,
- unsigned int len)
-{
- struct dlm_ctxt *dlm;
- struct dlm_lock_resource *res;
- char *buf = NULL;
- int ret = -EINVAL;
- int tmpret;
-
- if (len >= PAGE_SIZE-1) {
- mlog(ML_ERROR, "user passed too much data: %d bytes\n", len);
- goto leave;
- }
- if (len < 5) {
- mlog(ML_ERROR, "user passed too little data: %d bytes\n", len);
- goto leave;
- }
- buf = kmalloc(len+1, GFP_NOFS);
- if (!buf) {
- mlog(ML_ERROR, "could not alloc %d bytes\n", len+1);
- ret = -ENOMEM;
- goto leave;
- }
- if (strncpy_from_user(buf, data, len) < len) {
- mlog(ML_ERROR, "failed to get all user data. done.\n");
- goto leave;
- }
- buf[len]='\0';
- mlog(0, "got this data from user: %s\n", buf);
-
- if (*buf != 'R') {
- mlog(0, "bad data\n");
- goto leave;
- }
-
- tmpret = dlm_parse_domain_and_lockres(buf, len, &dlm, &res);
- if (tmpret < 0) {
- mlog(0, "bad data\n");
- goto leave;
- }
-
- mlog(ML_NOTICE, "struct dlm_ctxt: %s, node=%u, key=%u\n",
- dlm->name, dlm->node_num, dlm->key);
-
- dlm_print_one_lock_resource(res);
- dlm_lockres_put(res);
- dlm_put(dlm);
- ret = len;
-
-leave:
- if (buf)
- kfree(buf);
- return ret;
-}
-
static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
{
int bit;
@@ -369,234 +139,6 @@ void dlm_print_one_lock(struct dlm_lock *lockid)
}
EXPORT_SYMBOL_GPL(dlm_print_one_lock);
-void dlm_dump_lock_resources(struct dlm_ctxt *dlm)
-{
- struct dlm_lock_resource *res;
- struct hlist_node *iter;
- struct hlist_head *bucket;
- int i;
-
- mlog(ML_NOTICE, "struct dlm_ctxt: %s, node=%u, key=%u\n",
- dlm->name, dlm->node_num, dlm->key);
- if (!dlm || !dlm->name) {
- mlog(ML_ERROR, "dlm=%p\n", dlm);
- return;
- }
-
- spin_lock(&dlm->spinlock);
- for (i=0; i<DLM_HASH_BUCKETS; i++) {
- bucket = dlm_lockres_hash(dlm, i);
- hlist_for_each_entry(res, iter, bucket, hash_node)
- dlm_print_one_lock_resource(res);
- }
- spin_unlock(&dlm->spinlock);
-}
-static void dlm_dump_purge_list(struct dlm_ctxt *dlm)
-{
- struct list_head *iter;
- struct dlm_lock_resource *lockres;
-
- mlog(ML_NOTICE, "Purge list for DLM Domain \"%s\"\n", dlm->name);
- mlog(ML_NOTICE, "Last_used\tName\n");
-
- spin_lock(&dlm->spinlock);
- list_for_each(iter, &dlm->purge_list) {
- lockres = list_entry(iter, struct dlm_lock_resource, purge);
-
- spin_lock(&lockres->spinlock);
- mlog(ML_NOTICE, "%lu\t%.*s\n", lockres->last_used,
- lockres->lockname.len, lockres->lockname.name);
- spin_unlock(&lockres->spinlock);
- }
- spin_unlock(&dlm->spinlock);
-}
-
-void dlm_dump_work_queue(struct dlm_ctxt *dlm)
-{
- struct list_head *iter;
- struct dlm_work_item *item;
-
- spin_lock(&dlm->work_lock);
- list_for_each(iter, &dlm->work_list) {
- item = list_entry(iter, struct dlm_work_item, list);
- if (item->func == dlm_request_all_locks_worker) {
- printk("%s: found requestalllocks, mas=%u, dead=%u\n",
- dlm->name, item->u.ral.reco_master,
- item->u.ral.dead_node);
- } else if (item->func == dlm_mig_lockres_worker) {
- printk("%s:%.*s: found assert_master, realmaster=%u\n",
- dlm->name, item->u.ml.lockres->lockname.len,
- item->u.ml.lockres->lockname.name,
- item->u.ml.real_master);
- } else if (item->func == dlm_assert_master_worker) {
- printk("%s:%.*s: found assert_master, from=%u, "
- "flags=%u, ignore=%d\n",
- dlm->name, item->u.am.lockres->lockname.len,
- item->u.am.lockres->lockname.name,
- item->u.am.request_from, item->u.am.flags,
- item->u.am.ignore_higher);
- } else {
- printk("%s: found INVALID work item, func=%p\n",
- dlm->name, item->func);
- }
- }
- spin_unlock(&dlm->work_lock);
-}
-
-static int dlm_dump_work_queues(const char __user *data, unsigned int len)
-{
- struct dlm_ctxt *dlm;
- struct list_head *iter;
-
- spin_lock(&dlm_domain_lock);
- list_for_each(iter, &dlm_domains) {
- dlm = list_entry (iter, struct dlm_ctxt, list);
- dlm_dump_work_queue(dlm);
- }
- spin_unlock(&dlm_domain_lock);
- return len;
-
-}
-
-static int dlm_dump_all_purge_lists(const char __user *data, unsigned int len)
-{
- struct dlm_ctxt *dlm;
- struct list_head *iter;
-
- spin_lock(&dlm_domain_lock);
- list_for_each(iter, &dlm_domains) {
- dlm = list_entry (iter, struct dlm_ctxt, list);
- dlm_dump_purge_list(dlm);
- }
- spin_unlock(&dlm_domain_lock);
- return len;
-}
-
-static int dlm_parse_domain_and_lockres(char *buf, unsigned int len,
- struct dlm_ctxt **dlm,
- struct dlm_lock_resource **res)
-{
- char *resname;
- char *domainname;
- char *tmp;
- int ret = -EINVAL;
-
- *dlm = NULL;
- *res = NULL;
-
- tmp = buf;
- tmp++;
- if (*tmp != ' ') {
- mlog(0, "bad data\n");
- goto leave;
- }
- tmp++;
- domainname = tmp;
-
- while (*tmp) {
- if (*tmp == ' ')
- break;
- tmp++;
- }
- if (!*tmp || !*(tmp+1)) {
- mlog(0, "bad data\n");
- goto leave;
- }
-
- *tmp = '\0'; // null term the domainname
- tmp++;
- resname = tmp;
- while (*tmp) {
- if (*tmp == '\n' ||
- *tmp == ' ' ||
- *tmp == '\r') {
- *tmp = '\0';
- break;
- }
- tmp++;
- }
-
- mlog(0, "now looking up domain %s, lockres %s\n",
- domainname, resname);
- spin_lock(&dlm_domain_lock);
- *dlm = __dlm_lookup_domain(domainname);
- spin_unlock(&dlm_domain_lock);
-
- if (!dlm_grab(*dlm)) {
- mlog(ML_ERROR, "bad dlm!\n");
- *dlm = NULL;
- goto leave;
- }
-
- *res = dlm_lookup_lockres(*dlm, resname, strlen(resname));
- if (!*res) {
- mlog(ML_ERROR, "bad lockres!\n");
- dlm_put(*dlm);
- *dlm = NULL;
- goto leave;
- }
-
- mlog(0, "found dlm=%p, lockres=%p\n", *dlm, *res);
- ret = 0;
-
-leave:
- return ret;
-}
-
-static int dlm_trigger_migration(const char __user *data, unsigned int len)
-{
- struct dlm_lock_resource *res;
- struct dlm_ctxt *dlm;
- char *buf = NULL;
- int ret = -EINVAL;
- int tmpret;
-
- if (len >= PAGE_SIZE-1) {
- mlog(ML_ERROR, "user passed too much data: %d bytes\n", len);
- goto leave;
- }
- if (len < 5) {
- mlog(ML_ERROR, "user passed too little data: %d bytes\n", len);
- goto leave;
- }
- buf = kmalloc(len+1, GFP_NOFS);
- if (!buf) {
- mlog(ML_ERROR, "could not alloc %d bytes\n", len+1);
- ret = -ENOMEM;
- goto leave;
- }
- if (strncpy_from_user(buf, data, len) < len) {
- mlog(ML_ERROR, "failed to get all user data. done.\n");
- goto leave;
- }
- buf[len]='\0';
- mlog(0, "got this data from user: %s\n", buf);
-
- if (*buf != 'M') {
- mlog(0, "bad data\n");
- goto leave;
- }
-
- tmpret = dlm_parse_domain_and_lockres(buf, len, &dlm, &res);
- if (tmpret < 0) {
- mlog(0, "bad data\n");
- goto leave;
- }
- tmpret = dlm_migrate_lockres(dlm, res, O2NM_MAX_NODES);
- mlog(0, "dlm_migrate_lockres returned %d\n", tmpret);
- if (tmpret < 0)
- mlog(ML_ERROR, "failed to migrate %.*s: %d\n",
- res->lockname.len, res->lockname.name, tmpret);
- dlm_lockres_put(res);
- dlm_put(dlm);
- ret = len;
-
-leave:
- if (buf)
- kfree(buf);
- return ret;
-}
-
static const char *dlm_errnames[] = {
[DLM_NORMAL] = "DLM_NORMAL",
[DLM_GRANTED] = "DLM_GRANTED",
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index fcc19c8..f6537ac 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -48,13 +48,6 @@ struct debug_lockres
struct dlm_lock_resource *dl_res;
};
-void dlm_remove_proc(void);
-void dlm_init_proc(void);
-void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
-void dlm_proc_add_domain(struct dlm_ctxt *dlm);
-void dlm_proc_del_domain(struct dlm_ctxt *dlm);
-void dlm_dump_work_queue(struct dlm_ctxt *dlm);
-
int dlm_debug_init(struct dlm_ctxt *dlm);
void dlm_debug_shutdown(struct dlm_ctxt *dlm);
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index c22ebed..307d147 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -41,8 +41,6 @@
#include "dlmapi.h"
#include "dlmcommon.h"
-
-#include "dlmdebug.h"
#include "dlmdomain.h"
#include "dlmdebug.h"
@@ -288,8 +286,6 @@ static int dlm_wait_on_domain_helper(const char *domain)
static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm)
{
- dlm_proc_del_domain(dlm);
-
dlm_destroy_debugfs_subroot(dlm);
if (dlm->lockres_hash)
@@ -1477,7 +1473,6 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
dlm->dlm_state = DLM_CTXT_NEW;
INIT_LIST_HEAD(&dlm->dlm_eviction_callbacks);
- dlm_proc_add_domain(dlm);
mlog(0, "context init: refcount %u\n",
atomic_read(&dlm->dlm_refs.refcount));
@@ -1708,8 +1703,6 @@ static int __init dlm_init(void)
if (status)
goto error;
- dlm_init_proc();
-
status = dlm_create_debugfs_root();
if (status)
goto error;
@@ -1727,7 +1720,6 @@ error:
static void __exit dlm_exit (void)
{
dlm_destroy_debugfs_root();
- dlm_remove_proc();
dlm_unregister_net_handlers();
dlm_destroy_lock_cache();
dlm_destroy_lockname_cache();
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 14/18] ocfs2_dlm: Remove the proc interface
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 14/18] ocfs2_dlm: Remove the proc interface Sunil Mushran
@ 2008-02-28 16:55 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:55 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:58PM -0800, Sunil Mushran wrote:
> The proc debug interface is no longer needed as all the functionality
> it provided has been moved to the debugfs interface.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Signed-off-by: Joel Becker <joel.becker@oracle.com>
> ---
> fs/ocfs2/dlm/dlmcommon.h | 2 -
> fs/ocfs2/dlm/dlmdebug.c | 458 ----------------------------------------------
> fs/ocfs2/dlm/dlmdebug.h | 7 -
> fs/ocfs2/dlm/dlmdomain.c | 8 -
> 4 files changed, 0 insertions(+), 475 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index 41c8d90..1d05ebf 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -155,8 +155,6 @@ struct dlm_ctxt
> struct list_head master_list;
> struct list_head mle_hb_events;
>
> - struct proc_dir_entry *dlm_proc;
> -
> /* these give a really vague idea of the system load */
> atomic_t local_resources;
> atomic_t remote_resources;
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 1864731..e8fa5a9 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -30,7 +30,6 @@
> #include <linux/utsname.h>
> #include <linux/sysctl.h>
> #include <linux/spinlock.h>
> -#include <linux/proc_fs.h>
> #include <linux/debugfs.h>
>
> #include "cluster/heartbeat.h"
> @@ -39,8 +38,6 @@
>
> #include "dlmapi.h"
> #include "dlmcommon.h"
> -#include "dlmdebug.h"
> -
> #include "dlmdomain.h"
> #include "dlmdebug.h"
>
> @@ -49,233 +46,6 @@
>
> static struct dentry *dlm_debugfs_root = NULL;
>
> -static int dlm_dump_all_lock_resources(const char __user *data,
> - unsigned int len);
> -static void dlm_dump_purge_list(struct dlm_ctxt *dlm);
> -static int dlm_dump_all_purge_lists(const char __user *data, unsigned int len);
> -static int dlm_trigger_migration(const char __user *data, unsigned int len);
> -static int dlm_dump_one_lock_resource(const char __user *data,
> - unsigned int len);
> -static int dlm_dump_work_queues(const char __user *data, unsigned int len);
> -
> -static int dlm_parse_domain_and_lockres(char *buf, unsigned int len,
> - struct dlm_ctxt **dlm,
> - struct dlm_lock_resource **res);
> -
> -static int dlm_proc_stats(char *page, char **start, off_t off,
> - int count, int *eof, void *data);
> -
> -typedef int (dlm_debug_func_t)(const char __user *data, unsigned int len);
> -
> -struct dlm_debug_funcs
> -{
> - char key;
> - dlm_debug_func_t *func;
> -};
> -
> -static struct dlm_debug_funcs dlm_debug_map[] = {
> - { 'r', dlm_dump_all_lock_resources },
> - { 'R', dlm_dump_one_lock_resource },
> - { 'm', dlm_dump_all_mles },
> - { 'p', dlm_dump_all_purge_lists },
> - { 'M', dlm_trigger_migration },
> - { 'w', dlm_dump_work_queues }
> -};
> -static int dlm_debug_map_sz = (sizeof(dlm_debug_map) /
> - sizeof(struct dlm_debug_funcs));
> -
> -static ssize_t write_dlm_debug(struct file *file, const char __user *buf,
> - size_t count, loff_t *ppos)
> -{
> - int i;
> - char c;
> - dlm_debug_func_t *fn;
> - int ret;
> -
> - mlog(0, "(%p, %p, %u, %lld)\n",
> - file, buf, (unsigned int)count, (long long)*ppos);
> - ret = 0;
> - if (count<=0)
> - goto done;
> -
> - ret = -EFAULT;
> - if (get_user(c, buf))
> - goto done;
> -
> - ret = count;
> - for (i=0; i < dlm_debug_map_sz; i++) {
> - struct dlm_debug_funcs *d = &dlm_debug_map[i];
> - if (c == d->key) {
> - fn = d->func;
> - if (fn)
> - ret = (fn)(buf, count);
> - goto done;
> - }
> - }
> -done:
> - return ret;
> -}
> -
> -static struct file_operations dlm_debug_operations = {
> - .write = write_dlm_debug,
> -};
> -
> -#define OCFS2_DLM_PROC_PATH "fs/ocfs2_dlm"
> -#define DLM_DEBUG_PROC_NAME "debug"
> -#define DLM_STAT_PROC_NAME "stat"
> -
> -static struct proc_dir_entry *ocfs2_dlm_proc;
> -
> -void dlm_remove_proc(void)
> -{
> - if (ocfs2_dlm_proc) {
> - remove_proc_entry(DLM_DEBUG_PROC_NAME, ocfs2_dlm_proc);
> - remove_proc_entry(OCFS2_DLM_PROC_PATH, NULL);
> - }
> -}
> -
> -void dlm_init_proc(void)
> -{
> - struct proc_dir_entry *entry;
> -
> - ocfs2_dlm_proc = proc_mkdir(OCFS2_DLM_PROC_PATH, NULL);
> - if (!ocfs2_dlm_proc) {
> - mlog_errno(-ENOMEM);
> - return;
> - }
> -
> - entry = create_proc_entry(DLM_DEBUG_PROC_NAME, S_IWUSR,
> - ocfs2_dlm_proc);
> - if (entry)
> - entry->proc_fops = &dlm_debug_operations;
> -}
> -
> -static int dlm_proc_stats(char *page, char **start, off_t off,
> - int count, int *eof, void *data)
> -{
> - int len;
> - struct dlm_ctxt *dlm = data;
> -
> - len = sprintf(page, "local=%d, remote=%d, unknown=%d, key=0x%08x\n",
> - atomic_read(&dlm->local_resources),
> - atomic_read(&dlm->remote_resources),
> - atomic_read(&dlm->unknown_resources),
> - dlm->key);
> -
> - if (len <= off + count)
> - *eof = 1;
> -
> - *start = page + off;
> - len -= off;
> - if (len > count)
> - len = count;
> - if (len < 0)
> - len = 0;
> -
> - return len;
> -}
> -
> -void dlm_proc_add_domain(struct dlm_ctxt *dlm)
> -{
> - struct proc_dir_entry *entry;
> -
> - dlm->dlm_proc = proc_mkdir(dlm->name, ocfs2_dlm_proc);
> - if (dlm->dlm_proc) {
> - entry = create_proc_read_entry(DLM_STAT_PROC_NAME,
> - S_IFREG | S_IRUGO, dlm->dlm_proc,
> - dlm_proc_stats, (char *)dlm);
> - if (entry)
> - entry->owner = THIS_MODULE;
> - }
> -}
> -
> -void dlm_proc_del_domain(struct dlm_ctxt *dlm)
> -{
> - if (dlm->dlm_proc) {
> - remove_proc_entry(DLM_STAT_PROC_NAME, dlm->dlm_proc);
> - remove_proc_entry(dlm->name, ocfs2_dlm_proc);
> - }
> -}
> -
> -/* lock resource printing is usually very important (printed
> - * right before a BUG in some cases), but we'd like to be
> - * able to shut it off if needed, hence the KERN_NOTICE level */
> -static int dlm_dump_all_lock_resources(const char __user *data,
> - unsigned int len)
> -{
> - struct dlm_ctxt *dlm;
> - struct list_head *iter;
> -
> - mlog(ML_NOTICE, "dumping ALL dlm state for node %s\n",
> -#ifndef NO_SYSTEM_UTSNAME
> - system_utsname.nodename);
> -#else
> - init_uts_ns.name.nodename);
> -#endif
> - spin_lock(&dlm_domain_lock);
> - list_for_each(iter, &dlm_domains) {
> - dlm = list_entry (iter, struct dlm_ctxt, list);
> - dlm_dump_lock_resources(dlm);
> - }
> - spin_unlock(&dlm_domain_lock);
> - return len;
> -}
> -
> -static int dlm_dump_one_lock_resource(const char __user *data,
> - unsigned int len)
> -{
> - struct dlm_ctxt *dlm;
> - struct dlm_lock_resource *res;
> - char *buf = NULL;
> - int ret = -EINVAL;
> - int tmpret;
> -
> - if (len >= PAGE_SIZE-1) {
> - mlog(ML_ERROR, "user passed too much data: %d bytes\n", len);
> - goto leave;
> - }
> - if (len < 5) {
> - mlog(ML_ERROR, "user passed too little data: %d bytes\n", len);
> - goto leave;
> - }
> - buf = kmalloc(len+1, GFP_NOFS);
> - if (!buf) {
> - mlog(ML_ERROR, "could not alloc %d bytes\n", len+1);
> - ret = -ENOMEM;
> - goto leave;
> - }
> - if (strncpy_from_user(buf, data, len) < len) {
> - mlog(ML_ERROR, "failed to get all user data. done.\n");
> - goto leave;
> - }
> - buf[len]='\0';
> - mlog(0, "got this data from user: %s\n", buf);
> -
> - if (*buf != 'R') {
> - mlog(0, "bad data\n");
> - goto leave;
> - }
> -
> - tmpret = dlm_parse_domain_and_lockres(buf, len, &dlm, &res);
> - if (tmpret < 0) {
> - mlog(0, "bad data\n");
> - goto leave;
> - }
> -
> - mlog(ML_NOTICE, "struct dlm_ctxt: %s, node=%u, key=%u\n",
> - dlm->name, dlm->node_num, dlm->key);
> -
> - dlm_print_one_lock_resource(res);
> - dlm_lockres_put(res);
> - dlm_put(dlm);
> - ret = len;
> -
> -leave:
> - if (buf)
> - kfree(buf);
> - return ret;
> -}
> -
> static void dlm_print_lockres_refmap(struct dlm_lock_resource *res)
> {
> int bit;
> @@ -369,234 +139,6 @@ void dlm_print_one_lock(struct dlm_lock *lockid)
> }
> EXPORT_SYMBOL_GPL(dlm_print_one_lock);
>
> -void dlm_dump_lock_resources(struct dlm_ctxt *dlm)
> -{
> - struct dlm_lock_resource *res;
> - struct hlist_node *iter;
> - struct hlist_head *bucket;
> - int i;
> -
> - mlog(ML_NOTICE, "struct dlm_ctxt: %s, node=%u, key=%u\n",
> - dlm->name, dlm->node_num, dlm->key);
> - if (!dlm || !dlm->name) {
> - mlog(ML_ERROR, "dlm=%p\n", dlm);
> - return;
> - }
> -
> - spin_lock(&dlm->spinlock);
> - for (i=0; i<DLM_HASH_BUCKETS; i++) {
> - bucket = dlm_lockres_hash(dlm, i);
> - hlist_for_each_entry(res, iter, bucket, hash_node)
> - dlm_print_one_lock_resource(res);
> - }
> - spin_unlock(&dlm->spinlock);
> -}
> -static void dlm_dump_purge_list(struct dlm_ctxt *dlm)
> -{
> - struct list_head *iter;
> - struct dlm_lock_resource *lockres;
> -
> - mlog(ML_NOTICE, "Purge list for DLM Domain \"%s\"\n", dlm->name);
> - mlog(ML_NOTICE, "Last_used\tName\n");
> -
> - spin_lock(&dlm->spinlock);
> - list_for_each(iter, &dlm->purge_list) {
> - lockres = list_entry(iter, struct dlm_lock_resource, purge);
> -
> - spin_lock(&lockres->spinlock);
> - mlog(ML_NOTICE, "%lu\t%.*s\n", lockres->last_used,
> - lockres->lockname.len, lockres->lockname.name);
> - spin_unlock(&lockres->spinlock);
> - }
> - spin_unlock(&dlm->spinlock);
> -}
> -
> -void dlm_dump_work_queue(struct dlm_ctxt *dlm)
> -{
> - struct list_head *iter;
> - struct dlm_work_item *item;
> -
> - spin_lock(&dlm->work_lock);
> - list_for_each(iter, &dlm->work_list) {
> - item = list_entry(iter, struct dlm_work_item, list);
> - if (item->func == dlm_request_all_locks_worker) {
> - printk("%s: found requestalllocks, mas=%u, dead=%u\n",
> - dlm->name, item->u.ral.reco_master,
> - item->u.ral.dead_node);
> - } else if (item->func == dlm_mig_lockres_worker) {
> - printk("%s:%.*s: found assert_master, realmaster=%u\n",
> - dlm->name, item->u.ml.lockres->lockname.len,
> - item->u.ml.lockres->lockname.name,
> - item->u.ml.real_master);
> - } else if (item->func == dlm_assert_master_worker) {
> - printk("%s:%.*s: found assert_master, from=%u, "
> - "flags=%u, ignore=%d\n",
> - dlm->name, item->u.am.lockres->lockname.len,
> - item->u.am.lockres->lockname.name,
> - item->u.am.request_from, item->u.am.flags,
> - item->u.am.ignore_higher);
> - } else {
> - printk("%s: found INVALID work item, func=%p\n",
> - dlm->name, item->func);
> - }
> - }
> - spin_unlock(&dlm->work_lock);
> -}
> -
> -static int dlm_dump_work_queues(const char __user *data, unsigned int len)
> -{
> - struct dlm_ctxt *dlm;
> - struct list_head *iter;
> -
> - spin_lock(&dlm_domain_lock);
> - list_for_each(iter, &dlm_domains) {
> - dlm = list_entry (iter, struct dlm_ctxt, list);
> - dlm_dump_work_queue(dlm);
> - }
> - spin_unlock(&dlm_domain_lock);
> - return len;
> -
> -}
> -
> -static int dlm_dump_all_purge_lists(const char __user *data, unsigned int len)
> -{
> - struct dlm_ctxt *dlm;
> - struct list_head *iter;
> -
> - spin_lock(&dlm_domain_lock);
> - list_for_each(iter, &dlm_domains) {
> - dlm = list_entry (iter, struct dlm_ctxt, list);
> - dlm_dump_purge_list(dlm);
> - }
> - spin_unlock(&dlm_domain_lock);
> - return len;
> -}
> -
> -static int dlm_parse_domain_and_lockres(char *buf, unsigned int len,
> - struct dlm_ctxt **dlm,
> - struct dlm_lock_resource **res)
> -{
> - char *resname;
> - char *domainname;
> - char *tmp;
> - int ret = -EINVAL;
> -
> - *dlm = NULL;
> - *res = NULL;
> -
> - tmp = buf;
> - tmp++;
> - if (*tmp != ' ') {
> - mlog(0, "bad data\n");
> - goto leave;
> - }
> - tmp++;
> - domainname = tmp;
> -
> - while (*tmp) {
> - if (*tmp == ' ')
> - break;
> - tmp++;
> - }
> - if (!*tmp || !*(tmp+1)) {
> - mlog(0, "bad data\n");
> - goto leave;
> - }
> -
> - *tmp = '\0'; // null term the domainname
> - tmp++;
> - resname = tmp;
> - while (*tmp) {
> - if (*tmp == '\n' ||
> - *tmp == ' ' ||
> - *tmp == '\r') {
> - *tmp = '\0';
> - break;
> - }
> - tmp++;
> - }
> -
> - mlog(0, "now looking up domain %s, lockres %s\n",
> - domainname, resname);
> - spin_lock(&dlm_domain_lock);
> - *dlm = __dlm_lookup_domain(domainname);
> - spin_unlock(&dlm_domain_lock);
> -
> - if (!dlm_grab(*dlm)) {
> - mlog(ML_ERROR, "bad dlm!\n");
> - *dlm = NULL;
> - goto leave;
> - }
> -
> - *res = dlm_lookup_lockres(*dlm, resname, strlen(resname));
> - if (!*res) {
> - mlog(ML_ERROR, "bad lockres!\n");
> - dlm_put(*dlm);
> - *dlm = NULL;
> - goto leave;
> - }
> -
> - mlog(0, "found dlm=%p, lockres=%p\n", *dlm, *res);
> - ret = 0;
> -
> -leave:
> - return ret;
> -}
> -
> -static int dlm_trigger_migration(const char __user *data, unsigned int len)
> -{
> - struct dlm_lock_resource *res;
> - struct dlm_ctxt *dlm;
> - char *buf = NULL;
> - int ret = -EINVAL;
> - int tmpret;
> -
> - if (len >= PAGE_SIZE-1) {
> - mlog(ML_ERROR, "user passed too much data: %d bytes\n", len);
> - goto leave;
> - }
> - if (len < 5) {
> - mlog(ML_ERROR, "user passed too little data: %d bytes\n", len);
> - goto leave;
> - }
> - buf = kmalloc(len+1, GFP_NOFS);
> - if (!buf) {
> - mlog(ML_ERROR, "could not alloc %d bytes\n", len+1);
> - ret = -ENOMEM;
> - goto leave;
> - }
> - if (strncpy_from_user(buf, data, len) < len) {
> - mlog(ML_ERROR, "failed to get all user data. done.\n");
> - goto leave;
> - }
> - buf[len]='\0';
> - mlog(0, "got this data from user: %s\n", buf);
> -
> - if (*buf != 'M') {
> - mlog(0, "bad data\n");
> - goto leave;
> - }
> -
> - tmpret = dlm_parse_domain_and_lockres(buf, len, &dlm, &res);
> - if (tmpret < 0) {
> - mlog(0, "bad data\n");
> - goto leave;
> - }
> - tmpret = dlm_migrate_lockres(dlm, res, O2NM_MAX_NODES);
> - mlog(0, "dlm_migrate_lockres returned %d\n", tmpret);
> - if (tmpret < 0)
> - mlog(ML_ERROR, "failed to migrate %.*s: %d\n",
> - res->lockname.len, res->lockname.name, tmpret);
> - dlm_lockres_put(res);
> - dlm_put(dlm);
> - ret = len;
> -
> -leave:
> - if (buf)
> - kfree(buf);
> - return ret;
> -}
> -
> static const char *dlm_errnames[] = {
> [DLM_NORMAL] = "DLM_NORMAL",
> [DLM_GRANTED] = "DLM_GRANTED",
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index fcc19c8..f6537ac 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -48,13 +48,6 @@ struct debug_lockres
> struct dlm_lock_resource *dl_res;
> };
>
> -void dlm_remove_proc(void);
> -void dlm_init_proc(void);
> -void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> -void dlm_proc_add_domain(struct dlm_ctxt *dlm);
> -void dlm_proc_del_domain(struct dlm_ctxt *dlm);
> -void dlm_dump_work_queue(struct dlm_ctxt *dlm);
> -
> int dlm_debug_init(struct dlm_ctxt *dlm);
> void dlm_debug_shutdown(struct dlm_ctxt *dlm);
>
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index c22ebed..307d147 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -41,8 +41,6 @@
>
> #include "dlmapi.h"
> #include "dlmcommon.h"
> -
> -#include "dlmdebug.h"
> #include "dlmdomain.h"
> #include "dlmdebug.h"
>
> @@ -288,8 +286,6 @@ static int dlm_wait_on_domain_helper(const char *domain)
>
> static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm)
> {
> - dlm_proc_del_domain(dlm);
> -
> dlm_destroy_debugfs_subroot(dlm);
>
> if (dlm->lockres_hash)
> @@ -1477,7 +1473,6 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain,
> dlm->dlm_state = DLM_CTXT_NEW;
>
> INIT_LIST_HEAD(&dlm->dlm_eviction_callbacks);
> - dlm_proc_add_domain(dlm);
>
> mlog(0, "context init: refcount %u\n",
> atomic_read(&dlm->dlm_refs.refcount));
> @@ -1708,8 +1703,6 @@ static int __init dlm_init(void)
> if (status)
> goto error;
>
> - dlm_init_proc();
> -
> status = dlm_create_debugfs_root();
> if (status)
> goto error;
> @@ -1727,7 +1720,6 @@ error:
> static void __exit dlm_exit (void)
> {
> dlm_destroy_debugfs_root();
> - dlm_remove_proc();
> dlm_unregister_net_handlers();
> dlm_destroy_lock_cache();
> dlm_destroy_lockname_cache();
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
#!/bin/perl -sp0777i<X+d*lMLa^*lN%0]dsXx++lMlN/dsM0<j]dsj
$/=unpack('H*',$_);$_=`echo 16dio\U$k"SK$/SM$n\EsN0p[lN*1
lK[d2%Sa2/d0$^Ixp"|dc`;s/\W//g;$_=pack('H*',/((..)*)$/)
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (15 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 14/18] ocfs2_dlm: Remove the proc interface Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:38 ` Joel Becker
2008-02-28 17:11 ` Joel Becker
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 11/18] ocfs2_dlm: Dumps the mles into " Sunil Mushran
17 siblings, 2 replies; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch dumps the dlm state (dlm_ctxt) into a debugfs file.
Useful for debugging.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmcommon.h | 1 +
fs/ocfs2/dlm/dlmdebug.c | 297 ++++++++++++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmdebug.h | 14 ++
fs/ocfs2/dlm/dlmdomain.c | 8 ++
4 files changed, 320 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index 810e9b4..a2cfd61 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -125,6 +125,7 @@ struct dlm_ctxt
atomic_t remote_resources;
atomic_t unknown_resources;
+ struct dlm_debug_ctxt *dlm_debug_ctxt;
struct dentry *dlm_debugfs_subroot;
/* NOTE: Next three are protected by dlm_domain_lock */
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index baa8e24..83f3ac6 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -704,6 +704,296 @@ const char *dlm_errname(enum dlm_status err)
EXPORT_SYMBOL_GPL(dlm_errname);
#define DLM_DEBUGFS_DIR "o2dlm"
+#define DLM_DEBUGFS_DLM_STATE "dlm_state"
+
+/* begin - utils funcs */
+static void dlm_debug_free(struct kref *kref)
+{
+ struct dlm_debug_ctxt *dc;
+
+ dc = container_of(kref, struct dlm_debug_ctxt, debug_refcnt);
+
+ kfree(dc);
+}
+
+void dlm_debug_put(struct dlm_debug_ctxt *dc)
+{
+ if (dc)
+ kref_put(&dc->debug_refcnt, dlm_debug_free);
+}
+
+static void dlm_debug_get(struct dlm_debug_ctxt *dc)
+{
+ kref_get(&dc->debug_refcnt);
+}
+
+static int stringify_nodemap(unsigned long *nodemap, int maxnodes,
+ char *buf, int len)
+{
+ int out = 0;
+ int i = -1;
+
+ while ((i = find_next_bit(nodemap, maxnodes, i + 1)) < maxnodes)
+ out += snprintf(buf + out, len - out, "%d ", i);
+
+ return out;
+}
+
+static struct debug_buffer *debug_buffer_allocate(void)
+{
+ struct debug_buffer *db = NULL;
+
+ db = kzalloc(sizeof(struct debug_buffer), GFP_KERNEL);
+ if (!db)
+ goto bail;
+
+ db->len = PAGE_SIZE;
+ db->buf = kmalloc(db->len, GFP_KERNEL);
+ if (!db->buf)
+ goto bail;
+
+ return db;
+bail:
+ if (db)
+ kfree(db);
+ return NULL;
+}
+
+static ssize_t debug_buffer_read(struct file *file, char __user *buf,
+ size_t nbytes, loff_t *ppos)
+{
+ struct debug_buffer *db = file->private_data;
+
+ return simple_read_from_buffer(buf, nbytes, ppos, db->buf, db->len);
+}
+
+static loff_t debug_buffer_llseek(struct file *file, loff_t off, int whence)
+{
+ struct debug_buffer *db = file->private_data;
+ loff_t new = -1;
+
+ switch (whence) {
+ case 0:
+ new = off;
+ break;
+ case 1:
+ new = file->f_pos + off;
+ break;
+ }
+
+ if (new < 0 || new > db->len)
+ return -EINVAL;
+
+ return (file->f_pos = new);
+}
+
+static int debug_buffer_release(struct inode *inode, struct file *file)
+{
+ struct debug_buffer *db = (struct debug_buffer *)file->private_data;
+
+ if (db && db->buf)
+ kfree(db->buf);
+ if (db)
+ kfree(db);
+
+ return 0;
+}
+/* end - util funcs */
+
+/* begin - debug state funcs */
+static int debug_state_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
+{
+ int out = 0;
+ struct dlm_reco_node_data *node;
+ char *state;
+ int lres, rres, ures, tres;
+
+ lres = atomic_read(&dlm->local_resources);
+ rres = atomic_read(&dlm->remote_resources);
+ ures = atomic_read(&dlm->unknown_resources);
+ tres = lres + rres + ures;
+
+ 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;
+ }
+
+ /* Domain: xxxxxxxxxx Key: 0xdfbac769 */
+ out += snprintf(db->buf + out, db->len - out,
+ "Domain: %s Key: 0x%08x\n", dlm->name, dlm->key);
+
+ /* Thread Pid: xxx Node: xxx State: xxxxx */
+ out += snprintf(db->buf + out, db->len - out,
+ "Thread Pid: %d Node: %d State: %s\n",
+ dlm->dlm_thread_task->pid, dlm->node_num, state);
+
+ /* Number of Joins: xxx Joining Node: xxx */
+ out += snprintf(db->buf + out, db->len - out,
+ "Number of Joins: %d Joining Node: %d\n",
+ dlm->num_joins, dlm->joining_node);
+
+ /* Domain Map: xx, xx, xx, */
+ out += snprintf(db->buf + out, db->len - out, "Domain Map: ");
+ out += stringify_nodemap(dlm->domain_map, O2NM_MAX_NODES,
+ db->buf + out, db->len - out);
+ out += snprintf(db->buf + out, db->len - out, "\n");
+
+ /* Live Map: xx, xx, xx, */
+ out += snprintf(db->buf + out, db->len - out, "Live Map: ");
+ out += stringify_nodemap(dlm->live_nodes_map, O2NM_MAX_NODES,
+ db->buf + out, db->len - out);
+ out += snprintf(db->buf + out, db->len - out, "\n");
+
+ /* Mastered Resources Total: xxx Locally: xxx Remotely: xxx Unknown: xxx */
+ out += snprintf(db->buf + out, db->len - out,
+ "Mastered Resources Total: %d Locally: %d "
+ "Remotely: %d Unknown: %d\n",
+ tres, lres, rres, ures);
+
+ /* Empty Lists: Dirty=No Purge=Yes PendingASTs=No PendingBASTs=Yes Master=No */
+ out += snprintf(db->buf + out, db->len - out,
+ "Empty Lists: Dirty=%s Purge=%s PendingASTs=%s "
+ "PendingBASTs=%s Master=%s\n",
+ (list_empty(&dlm->dirty_list) ? "Yes" : "No"),
+ (list_empty(&dlm->purge_list) ? "Yes" : "No"),
+ (list_empty(&dlm->pending_asts) ? "Yes" : "No"),
+ (list_empty(&dlm->pending_basts) ? "Yes" : "No"),
+ (list_empty(&dlm->master_list) ? "Yes" : "No"));
+
+ /* Purge Count: xxx Refs: xxx */
+ out += snprintf(db->buf + out, db->len - out,
+ "Purge Count: %d Refs: %d\n", dlm->purge_count,
+ atomic_read(&dlm->dlm_refs.refcount));
+
+ /* Dead Node: xxx */
+ out += snprintf(db->buf + out, db->len - out,
+ "Dead Node: %d\n", dlm->reco.dead_node);
+
+ /* What about DLM_RECO_STATE_FINALIZE? */
+ if (dlm->reco.state == DLM_RECO_STATE_ACTIVE)
+ state = "Active";
+ else
+ state = "Inactive";
+
+ /* Recovery Pid: xxxx Master: xxx State: xxxx */
+ out += snprintf(db->buf + out, db->len - out,
+ "Recovery Pid: %d Master: %d State: %s\n",
+ dlm->dlm_reco_thread_task->pid,
+ dlm->reco.new_master, state);
+
+ /* Recovery Map: xx, xx, */
+ out += snprintf(db->buf + out, db->len - out, "Recovery Map: ");
+ out += stringify_nodemap(dlm->recovery_map, O2NM_MAX_NODES,
+ db->buf + out, db->len - out);
+ out += snprintf(db->buf + out, db->len - out, "\n");
+
+ /* Recovery Node State: */
+ out += snprintf(db->buf + out, db->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 += snprintf(db->buf + out, db->len - out, "\t%u - %s\n",
+ node->node_num, state);
+ }
+
+ spin_unlock(&dlm->spinlock);
+
+ return out;
+}
+
+static int debug_state_open(struct inode *inode, struct file *file)
+{
+ struct dlm_ctxt *dlm = inode->i_private;
+ struct debug_buffer *db = NULL;
+
+ db = debug_buffer_allocate();
+ if (!db)
+ goto bail;
+
+ db->len = debug_state_print(dlm, db);
+
+ file->private_data = db;
+
+ return 0;
+bail:
+ return -ENOMEM;
+}
+
+static struct file_operations debug_state_fops = {
+ .open = debug_state_open,
+ .release = debug_buffer_release,
+ .read = debug_buffer_read,
+ .llseek = debug_buffer_llseek,
+};
+/* end - debug state funcs */
+
+/* files in subroot */
+int dlm_debug_init(struct dlm_ctxt *dlm)
+{
+ struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
+
+ /* for dumping dlm_ctxt */
+ dc->debug_state_dentry = debugfs_create_file(DLM_DEBUGFS_DLM_STATE,
+ S_IFREG|S_IRUSR,
+ dlm->dlm_debugfs_subroot,
+ dlm, &debug_state_fops);
+ if (!dc->debug_state_dentry) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+
+ dlm_debug_get(dc);
+ return 0;
+
+bail:
+ dlm_debug_shutdown(dlm);
+ return -ENOMEM;
+}
+
+void dlm_debug_shutdown(struct dlm_ctxt *dlm)
+{
+ struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
+
+ if (dc) {
+ if (dc->debug_state_dentry)
+ debugfs_remove(dc->debug_state_dentry);
+ dlm_debug_put(dc);
+ }
+}
/* subroot - domain dir */
int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
@@ -714,6 +1004,13 @@ int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
goto bail;
}
+ dlm->dlm_debug_ctxt = kzalloc(sizeof(struct dlm_debug_ctxt), GFP_KERNEL);
+ if (!dlm->dlm_debug_ctxt) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+ kref_init(&dlm->dlm_debug_ctxt->debug_refcnt);
+
return 0;
bail:
dlm_destroy_debugfs_subroot(dlm);
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index e701499..50cb10f 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -25,6 +25,17 @@
#ifndef DLMDEBUG_H
#define DLMDEBUG_H
+struct dlm_debug_ctxt {
+ struct kref debug_refcnt;
+ struct dentry *debug_state_dentry;
+};
+
+struct debug_buffer
+{
+ int len;
+ char *buf;
+};
+
void dlm_remove_proc(void);
void dlm_init_proc(void);
void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
@@ -32,6 +43,9 @@ void dlm_proc_add_domain(struct dlm_ctxt *dlm);
void dlm_proc_del_domain(struct dlm_ctxt *dlm);
void dlm_dump_work_queue(struct dlm_ctxt *dlm);
+int dlm_debug_init(struct dlm_ctxt *dlm);
+void dlm_debug_shutdown(struct dlm_ctxt *dlm);
+
int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm);
void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index da2a155..c22ebed 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -389,6 +389,7 @@ static void dlm_destroy_dlm_worker(struct dlm_ctxt *dlm)
static void dlm_complete_dlm_shutdown(struct dlm_ctxt *dlm)
{
dlm_unregister_domain_handlers(dlm);
+ dlm_debug_shutdown(dlm);
dlm_complete_thread(dlm);
dlm_complete_recovery_thread(dlm);
dlm_destroy_dlm_worker(dlm);
@@ -1297,6 +1298,12 @@ static int dlm_join_domain(struct dlm_ctxt *dlm)
goto bail;
}
+ status = dlm_debug_init(dlm);
+ if (status < 0) {
+ mlog_errno(status);
+ goto bail;
+ }
+
status = dlm_launch_thread(dlm);
if (status < 0) {
mlog_errno(status);
@@ -1364,6 +1371,7 @@ bail:
if (status) {
dlm_unregister_domain_handlers(dlm);
+ dlm_debug_shutdown(dlm);
dlm_complete_thread(dlm);
dlm_complete_recovery_thread(dlm);
dlm_destroy_dlm_worker(dlm);
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file Sunil Mushran
@ 2008-02-28 16:38 ` Joel Becker
2008-02-28 17:11 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:38 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:52PM -0800, Sunil Mushran wrote:
> This patch dumps the dlm state (dlm_ctxt) into a debugfs file.
> Useful for debugging.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Also needs CONFIG_DEBUG_FS handling.
Joel
> ---
> fs/ocfs2/dlm/dlmcommon.h | 1 +
> fs/ocfs2/dlm/dlmdebug.c | 297 ++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 14 ++
> fs/ocfs2/dlm/dlmdomain.c | 8 ++
> 4 files changed, 320 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index 810e9b4..a2cfd61 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -125,6 +125,7 @@ struct dlm_ctxt
> atomic_t remote_resources;
> atomic_t unknown_resources;
>
> + struct dlm_debug_ctxt *dlm_debug_ctxt;
> struct dentry *dlm_debugfs_subroot;
>
> /* NOTE: Next three are protected by dlm_domain_lock */
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index baa8e24..83f3ac6 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -704,6 +704,296 @@ const char *dlm_errname(enum dlm_status err)
> EXPORT_SYMBOL_GPL(dlm_errname);
>
> #define DLM_DEBUGFS_DIR "o2dlm"
> +#define DLM_DEBUGFS_DLM_STATE "dlm_state"
> +
> +/* begin - utils funcs */
> +static void dlm_debug_free(struct kref *kref)
> +{
> + struct dlm_debug_ctxt *dc;
> +
> + dc = container_of(kref, struct dlm_debug_ctxt, debug_refcnt);
> +
> + kfree(dc);
> +}
> +
> +void dlm_debug_put(struct dlm_debug_ctxt *dc)
> +{
> + if (dc)
> + kref_put(&dc->debug_refcnt, dlm_debug_free);
> +}
> +
> +static void dlm_debug_get(struct dlm_debug_ctxt *dc)
> +{
> + kref_get(&dc->debug_refcnt);
> +}
> +
> +static int stringify_nodemap(unsigned long *nodemap, int maxnodes,
> + char *buf, int len)
> +{
> + int out = 0;
> + int i = -1;
> +
> + while ((i = find_next_bit(nodemap, maxnodes, i + 1)) < maxnodes)
> + out += snprintf(buf + out, len - out, "%d ", i);
> +
> + return out;
> +}
> +
> +static struct debug_buffer *debug_buffer_allocate(void)
> +{
> + struct debug_buffer *db = NULL;
> +
> + db = kzalloc(sizeof(struct debug_buffer), GFP_KERNEL);
> + if (!db)
> + goto bail;
> +
> + db->len = PAGE_SIZE;
> + db->buf = kmalloc(db->len, GFP_KERNEL);
> + if (!db->buf)
> + goto bail;
> +
> + return db;
> +bail:
> + if (db)
> + kfree(db);
> + return NULL;
> +}
> +
> +static ssize_t debug_buffer_read(struct file *file, char __user *buf,
> + size_t nbytes, loff_t *ppos)
> +{
> + struct debug_buffer *db = file->private_data;
> +
> + return simple_read_from_buffer(buf, nbytes, ppos, db->buf, db->len);
> +}
> +
> +static loff_t debug_buffer_llseek(struct file *file, loff_t off, int whence)
> +{
> + struct debug_buffer *db = file->private_data;
> + loff_t new = -1;
> +
> + switch (whence) {
> + case 0:
> + new = off;
> + break;
> + case 1:
> + new = file->f_pos + off;
> + break;
> + }
> +
> + if (new < 0 || new > db->len)
> + return -EINVAL;
> +
> + return (file->f_pos = new);
> +}
> +
> +static int debug_buffer_release(struct inode *inode, struct file *file)
> +{
> + struct debug_buffer *db = (struct debug_buffer *)file->private_data;
> +
> + if (db && db->buf)
> + kfree(db->buf);
> + if (db)
> + kfree(db);
> +
> + return 0;
> +}
> +/* end - util funcs */
> +
> +/* begin - debug state funcs */
> +static int debug_state_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> +{
> + int out = 0;
> + struct dlm_reco_node_data *node;
> + char *state;
> + int lres, rres, ures, tres;
> +
> + lres = atomic_read(&dlm->local_resources);
> + rres = atomic_read(&dlm->remote_resources);
> + ures = atomic_read(&dlm->unknown_resources);
> + tres = lres + rres + ures;
> +
> + 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;
> + }
> +
> + /* Domain: xxxxxxxxxx Key: 0xdfbac769 */
> + out += snprintf(db->buf + out, db->len - out,
> + "Domain: %s Key: 0x%08x\n", dlm->name, dlm->key);
> +
> + /* Thread Pid: xxx Node: xxx State: xxxxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Thread Pid: %d Node: %d State: %s\n",
> + dlm->dlm_thread_task->pid, dlm->node_num, state);
> +
> + /* Number of Joins: xxx Joining Node: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Number of Joins: %d Joining Node: %d\n",
> + dlm->num_joins, dlm->joining_node);
> +
> + /* Domain Map: xx, xx, xx, */
> + out += snprintf(db->buf + out, db->len - out, "Domain Map: ");
> + out += stringify_nodemap(dlm->domain_map, O2NM_MAX_NODES,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\n");
> +
> + /* Live Map: xx, xx, xx, */
> + out += snprintf(db->buf + out, db->len - out, "Live Map: ");
> + out += stringify_nodemap(dlm->live_nodes_map, O2NM_MAX_NODES,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\n");
> +
> + /* Mastered Resources Total: xxx Locally: xxx Remotely: xxx Unknown: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Mastered Resources Total: %d Locally: %d "
> + "Remotely: %d Unknown: %d\n",
> + tres, lres, rres, ures);
> +
> + /* Empty Lists: Dirty=No Purge=Yes PendingASTs=No PendingBASTs=Yes Master=No */
> + out += snprintf(db->buf + out, db->len - out,
> + "Empty Lists: Dirty=%s Purge=%s PendingASTs=%s "
> + "PendingBASTs=%s Master=%s\n",
> + (list_empty(&dlm->dirty_list) ? "Yes" : "No"),
> + (list_empty(&dlm->purge_list) ? "Yes" : "No"),
> + (list_empty(&dlm->pending_asts) ? "Yes" : "No"),
> + (list_empty(&dlm->pending_basts) ? "Yes" : "No"),
> + (list_empty(&dlm->master_list) ? "Yes" : "No"));
> +
> + /* Purge Count: xxx Refs: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Purge Count: %d Refs: %d\n", dlm->purge_count,
> + atomic_read(&dlm->dlm_refs.refcount));
> +
> + /* Dead Node: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Dead Node: %d\n", dlm->reco.dead_node);
> +
> + /* What about DLM_RECO_STATE_FINALIZE? */
> + if (dlm->reco.state == DLM_RECO_STATE_ACTIVE)
> + state = "Active";
> + else
> + state = "Inactive";
> +
> + /* Recovery Pid: xxxx Master: xxx State: xxxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Recovery Pid: %d Master: %d State: %s\n",
> + dlm->dlm_reco_thread_task->pid,
> + dlm->reco.new_master, state);
> +
> + /* Recovery Map: xx, xx, */
> + out += snprintf(db->buf + out, db->len - out, "Recovery Map: ");
> + out += stringify_nodemap(dlm->recovery_map, O2NM_MAX_NODES,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\n");
> +
> + /* Recovery Node State: */
> + out += snprintf(db->buf + out, db->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 += snprintf(db->buf + out, db->len - out, "\t%u - %s\n",
> + node->node_num, state);
> + }
> +
> + spin_unlock(&dlm->spinlock);
> +
> + return out;
> +}
> +
> +static int debug_state_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + struct debug_buffer *db = NULL;
> +
> + db = debug_buffer_allocate();
> + if (!db)
> + goto bail;
> +
> + db->len = debug_state_print(dlm, db);
> +
> + file->private_data = db;
> +
> + return 0;
> +bail:
> + return -ENOMEM;
> +}
> +
> +static struct file_operations debug_state_fops = {
> + .open = debug_state_open,
> + .release = debug_buffer_release,
> + .read = debug_buffer_read,
> + .llseek = debug_buffer_llseek,
> +};
> +/* end - debug state funcs */
> +
> +/* files in subroot */
> +int dlm_debug_init(struct dlm_ctxt *dlm)
> +{
> + struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
> +
> + /* for dumping dlm_ctxt */
> + dc->debug_state_dentry = debugfs_create_file(DLM_DEBUGFS_DLM_STATE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_state_fops);
> + if (!dc->debug_state_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> + dlm_debug_get(dc);
> + return 0;
> +
> +bail:
> + dlm_debug_shutdown(dlm);
> + return -ENOMEM;
> +}
> +
> +void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> +{
> + struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
> +
> + if (dc) {
> + if (dc->debug_state_dentry)
> + debugfs_remove(dc->debug_state_dentry);
> + dlm_debug_put(dc);
> + }
> +}
>
> /* subroot - domain dir */
> int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
> @@ -714,6 +1004,13 @@ int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + dlm->dlm_debug_ctxt = kzalloc(sizeof(struct dlm_debug_ctxt), GFP_KERNEL);
> + if (!dlm->dlm_debug_ctxt) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> + kref_init(&dlm->dlm_debug_ctxt->debug_refcnt);
> +
> return 0;
> bail:
> dlm_destroy_debugfs_subroot(dlm);
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index e701499..50cb10f 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -25,6 +25,17 @@
> #ifndef DLMDEBUG_H
> #define DLMDEBUG_H
>
> +struct dlm_debug_ctxt {
> + struct kref debug_refcnt;
> + struct dentry *debug_state_dentry;
> +};
> +
> +struct debug_buffer
> +{
> + int len;
> + char *buf;
> +};
> +
> void dlm_remove_proc(void);
> void dlm_init_proc(void);
> void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> @@ -32,6 +43,9 @@ void dlm_proc_add_domain(struct dlm_ctxt *dlm);
> void dlm_proc_del_domain(struct dlm_ctxt *dlm);
> void dlm_dump_work_queue(struct dlm_ctxt *dlm);
>
> +int dlm_debug_init(struct dlm_ctxt *dlm);
> +void dlm_debug_shutdown(struct dlm_ctxt *dlm);
> +
> int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm);
> void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
>
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index da2a155..c22ebed 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -389,6 +389,7 @@ static void dlm_destroy_dlm_worker(struct dlm_ctxt *dlm)
> static void dlm_complete_dlm_shutdown(struct dlm_ctxt *dlm)
> {
> dlm_unregister_domain_handlers(dlm);
> + dlm_debug_shutdown(dlm);
> dlm_complete_thread(dlm);
> dlm_complete_recovery_thread(dlm);
> dlm_destroy_dlm_worker(dlm);
> @@ -1297,6 +1298,12 @@ static int dlm_join_domain(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + status = dlm_debug_init(dlm);
> + if (status < 0) {
> + mlog_errno(status);
> + goto bail;
> + }
> +
> status = dlm_launch_thread(dlm);
> if (status < 0) {
> mlog_errno(status);
> @@ -1364,6 +1371,7 @@ bail:
>
> if (status) {
> dlm_unregister_domain_handlers(dlm);
> + dlm_debug_shutdown(dlm);
> dlm_complete_thread(dlm);
> dlm_complete_recovery_thread(dlm);
> dlm_destroy_dlm_worker(dlm);
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Baby, even the losers
Get luck sometimes.
Even the losers
Keep a little bit of pride."
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file Sunil Mushran
2008-02-28 16:38 ` Joel Becker
@ 2008-02-28 17:11 ` Joel Becker
1 sibling, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 17:11 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:52PM -0800, Sunil Mushran wrote:
> This patch dumps the dlm state (dlm_ctxt) into a debugfs file.
> Useful for debugging.
Please run checkpatch.pl.
Joel
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
> ---
> fs/ocfs2/dlm/dlmcommon.h | 1 +
> fs/ocfs2/dlm/dlmdebug.c | 297 ++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 14 ++
> fs/ocfs2/dlm/dlmdomain.c | 8 ++
> 4 files changed, 320 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
> index 810e9b4..a2cfd61 100644
> --- a/fs/ocfs2/dlm/dlmcommon.h
> +++ b/fs/ocfs2/dlm/dlmcommon.h
> @@ -125,6 +125,7 @@ struct dlm_ctxt
> atomic_t remote_resources;
> atomic_t unknown_resources;
>
> + struct dlm_debug_ctxt *dlm_debug_ctxt;
> struct dentry *dlm_debugfs_subroot;
>
> /* NOTE: Next three are protected by dlm_domain_lock */
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index baa8e24..83f3ac6 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -704,6 +704,296 @@ const char *dlm_errname(enum dlm_status err)
> EXPORT_SYMBOL_GPL(dlm_errname);
>
> #define DLM_DEBUGFS_DIR "o2dlm"
> +#define DLM_DEBUGFS_DLM_STATE "dlm_state"
> +
> +/* begin - utils funcs */
> +static void dlm_debug_free(struct kref *kref)
> +{
> + struct dlm_debug_ctxt *dc;
> +
> + dc = container_of(kref, struct dlm_debug_ctxt, debug_refcnt);
> +
> + kfree(dc);
> +}
> +
> +void dlm_debug_put(struct dlm_debug_ctxt *dc)
> +{
> + if (dc)
> + kref_put(&dc->debug_refcnt, dlm_debug_free);
> +}
> +
> +static void dlm_debug_get(struct dlm_debug_ctxt *dc)
> +{
> + kref_get(&dc->debug_refcnt);
> +}
> +
> +static int stringify_nodemap(unsigned long *nodemap, int maxnodes,
> + char *buf, int len)
> +{
> + int out = 0;
> + int i = -1;
> +
> + while ((i = find_next_bit(nodemap, maxnodes, i + 1)) < maxnodes)
> + out += snprintf(buf + out, len - out, "%d ", i);
> +
> + return out;
> +}
> +
> +static struct debug_buffer *debug_buffer_allocate(void)
> +{
> + struct debug_buffer *db = NULL;
> +
> + db = kzalloc(sizeof(struct debug_buffer), GFP_KERNEL);
> + if (!db)
> + goto bail;
> +
> + db->len = PAGE_SIZE;
> + db->buf = kmalloc(db->len, GFP_KERNEL);
> + if (!db->buf)
> + goto bail;
> +
> + return db;
> +bail:
> + if (db)
> + kfree(db);
> + return NULL;
> +}
> +
> +static ssize_t debug_buffer_read(struct file *file, char __user *buf,
> + size_t nbytes, loff_t *ppos)
> +{
> + struct debug_buffer *db = file->private_data;
> +
> + return simple_read_from_buffer(buf, nbytes, ppos, db->buf, db->len);
> +}
> +
> +static loff_t debug_buffer_llseek(struct file *file, loff_t off, int whence)
> +{
> + struct debug_buffer *db = file->private_data;
> + loff_t new = -1;
> +
> + switch (whence) {
> + case 0:
> + new = off;
> + break;
> + case 1:
> + new = file->f_pos + off;
> + break;
> + }
> +
> + if (new < 0 || new > db->len)
> + return -EINVAL;
> +
> + return (file->f_pos = new);
> +}
> +
> +static int debug_buffer_release(struct inode *inode, struct file *file)
> +{
> + struct debug_buffer *db = (struct debug_buffer *)file->private_data;
> +
> + if (db && db->buf)
> + kfree(db->buf);
> + if (db)
> + kfree(db);
> +
> + return 0;
> +}
> +/* end - util funcs */
> +
> +/* begin - debug state funcs */
> +static int debug_state_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> +{
> + int out = 0;
> + struct dlm_reco_node_data *node;
> + char *state;
> + int lres, rres, ures, tres;
> +
> + lres = atomic_read(&dlm->local_resources);
> + rres = atomic_read(&dlm->remote_resources);
> + ures = atomic_read(&dlm->unknown_resources);
> + tres = lres + rres + ures;
> +
> + 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;
> + }
> +
> + /* Domain: xxxxxxxxxx Key: 0xdfbac769 */
> + out += snprintf(db->buf + out, db->len - out,
> + "Domain: %s Key: 0x%08x\n", dlm->name, dlm->key);
> +
> + /* Thread Pid: xxx Node: xxx State: xxxxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Thread Pid: %d Node: %d State: %s\n",
> + dlm->dlm_thread_task->pid, dlm->node_num, state);
> +
> + /* Number of Joins: xxx Joining Node: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Number of Joins: %d Joining Node: %d\n",
> + dlm->num_joins, dlm->joining_node);
> +
> + /* Domain Map: xx, xx, xx, */
> + out += snprintf(db->buf + out, db->len - out, "Domain Map: ");
> + out += stringify_nodemap(dlm->domain_map, O2NM_MAX_NODES,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\n");
> +
> + /* Live Map: xx, xx, xx, */
> + out += snprintf(db->buf + out, db->len - out, "Live Map: ");
> + out += stringify_nodemap(dlm->live_nodes_map, O2NM_MAX_NODES,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\n");
> +
> + /* Mastered Resources Total: xxx Locally: xxx Remotely: xxx Unknown: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Mastered Resources Total: %d Locally: %d "
> + "Remotely: %d Unknown: %d\n",
> + tres, lres, rres, ures);
> +
> + /* Empty Lists: Dirty=No Purge=Yes PendingASTs=No PendingBASTs=Yes Master=No */
> + out += snprintf(db->buf + out, db->len - out,
> + "Empty Lists: Dirty=%s Purge=%s PendingASTs=%s "
> + "PendingBASTs=%s Master=%s\n",
> + (list_empty(&dlm->dirty_list) ? "Yes" : "No"),
> + (list_empty(&dlm->purge_list) ? "Yes" : "No"),
> + (list_empty(&dlm->pending_asts) ? "Yes" : "No"),
> + (list_empty(&dlm->pending_basts) ? "Yes" : "No"),
> + (list_empty(&dlm->master_list) ? "Yes" : "No"));
> +
> + /* Purge Count: xxx Refs: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Purge Count: %d Refs: %d\n", dlm->purge_count,
> + atomic_read(&dlm->dlm_refs.refcount));
> +
> + /* Dead Node: xxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Dead Node: %d\n", dlm->reco.dead_node);
> +
> + /* What about DLM_RECO_STATE_FINALIZE? */
> + if (dlm->reco.state == DLM_RECO_STATE_ACTIVE)
> + state = "Active";
> + else
> + state = "Inactive";
> +
> + /* Recovery Pid: xxxx Master: xxx State: xxxx */
> + out += snprintf(db->buf + out, db->len - out,
> + "Recovery Pid: %d Master: %d State: %s\n",
> + dlm->dlm_reco_thread_task->pid,
> + dlm->reco.new_master, state);
> +
> + /* Recovery Map: xx, xx, */
> + out += snprintf(db->buf + out, db->len - out, "Recovery Map: ");
> + out += stringify_nodemap(dlm->recovery_map, O2NM_MAX_NODES,
> + db->buf + out, db->len - out);
> + out += snprintf(db->buf + out, db->len - out, "\n");
> +
> + /* Recovery Node State: */
> + out += snprintf(db->buf + out, db->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 += snprintf(db->buf + out, db->len - out, "\t%u - %s\n",
> + node->node_num, state);
> + }
> +
> + spin_unlock(&dlm->spinlock);
> +
> + return out;
> +}
> +
> +static int debug_state_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + struct debug_buffer *db = NULL;
> +
> + db = debug_buffer_allocate();
> + if (!db)
> + goto bail;
> +
> + db->len = debug_state_print(dlm, db);
> +
> + file->private_data = db;
> +
> + return 0;
> +bail:
> + return -ENOMEM;
> +}
> +
> +static struct file_operations debug_state_fops = {
> + .open = debug_state_open,
> + .release = debug_buffer_release,
> + .read = debug_buffer_read,
> + .llseek = debug_buffer_llseek,
> +};
> +/* end - debug state funcs */
> +
> +/* files in subroot */
> +int dlm_debug_init(struct dlm_ctxt *dlm)
> +{
> + struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
> +
> + /* for dumping dlm_ctxt */
> + dc->debug_state_dentry = debugfs_create_file(DLM_DEBUGFS_DLM_STATE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_state_fops);
> + if (!dc->debug_state_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> + dlm_debug_get(dc);
> + return 0;
> +
> +bail:
> + dlm_debug_shutdown(dlm);
> + return -ENOMEM;
> +}
> +
> +void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> +{
> + struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
> +
> + if (dc) {
> + if (dc->debug_state_dentry)
> + debugfs_remove(dc->debug_state_dentry);
> + dlm_debug_put(dc);
> + }
> +}
>
> /* subroot - domain dir */
> int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
> @@ -714,6 +1004,13 @@ int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + dlm->dlm_debug_ctxt = kzalloc(sizeof(struct dlm_debug_ctxt), GFP_KERNEL);
> + if (!dlm->dlm_debug_ctxt) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> + kref_init(&dlm->dlm_debug_ctxt->debug_refcnt);
> +
> return 0;
> bail:
> dlm_destroy_debugfs_subroot(dlm);
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index e701499..50cb10f 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -25,6 +25,17 @@
> #ifndef DLMDEBUG_H
> #define DLMDEBUG_H
>
> +struct dlm_debug_ctxt {
> + struct kref debug_refcnt;
> + struct dentry *debug_state_dentry;
> +};
> +
> +struct debug_buffer
> +{
> + int len;
> + char *buf;
> +};
> +
> void dlm_remove_proc(void);
> void dlm_init_proc(void);
> void dlm_dump_lock_resources(struct dlm_ctxt *dlm);
> @@ -32,6 +43,9 @@ void dlm_proc_add_domain(struct dlm_ctxt *dlm);
> void dlm_proc_del_domain(struct dlm_ctxt *dlm);
> void dlm_dump_work_queue(struct dlm_ctxt *dlm);
>
> +int dlm_debug_init(struct dlm_ctxt *dlm);
> +void dlm_debug_shutdown(struct dlm_ctxt *dlm);
> +
> int dlm_create_debugfs_subroot(struct dlm_ctxt *dlm);
> void dlm_destroy_debugfs_subroot(struct dlm_ctxt *dlm);
>
> diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
> index da2a155..c22ebed 100644
> --- a/fs/ocfs2/dlm/dlmdomain.c
> +++ b/fs/ocfs2/dlm/dlmdomain.c
> @@ -389,6 +389,7 @@ static void dlm_destroy_dlm_worker(struct dlm_ctxt *dlm)
> static void dlm_complete_dlm_shutdown(struct dlm_ctxt *dlm)
> {
> dlm_unregister_domain_handlers(dlm);
> + dlm_debug_shutdown(dlm);
> dlm_complete_thread(dlm);
> dlm_complete_recovery_thread(dlm);
> dlm_destroy_dlm_worker(dlm);
> @@ -1297,6 +1298,12 @@ static int dlm_join_domain(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + status = dlm_debug_init(dlm);
> + if (status < 0) {
> + mlog_errno(status);
> + goto bail;
> + }
> +
> status = dlm_launch_thread(dlm);
> if (status < 0) {
> mlog_errno(status);
> @@ -1364,6 +1371,7 @@ bail:
>
> if (status) {
> dlm_unregister_domain_handlers(dlm);
> + dlm_debug_shutdown(dlm);
> dlm_complete_thread(dlm);
> dlm_complete_recovery_thread(dlm);
> dlm_destroy_dlm_worker(dlm);
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
"Win95 file and print sharing are for relatively friendly nets."
- Paul Leach, Microsoft
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread
* [Ocfs2-devel] [PATCH 11/18] ocfs2_dlm: Dumps the mles into a debugfs file
2008-02-25 12:21 [Ocfs2-devel] New dlm debug infrastructure Sunil Mushran
` (16 preceding siblings ...)
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 08/18] ocfs2_dlm: Dump the dlm state in a debugfs file Sunil Mushran
@ 2008-02-25 12:21 ` Sunil Mushran
2008-02-28 16:53 ` Joel Becker
17 siblings, 1 reply; 41+ messages in thread
From: Sunil Mushran @ 2008-02-25 12:21 UTC (permalink / raw)
To: ocfs2-devel
This patch dumps all mles it can fit in one page into a debugfs file.
Useful for debugging.
Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
---
fs/ocfs2/dlm/dlmdebug.c | 119 +++++++++++++++++++++++++++++++++++++++++++++++
fs/ocfs2/dlm/dlmdebug.h | 1 +
2 files changed, 120 insertions(+), 0 deletions(-)
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
index 905145a..158b2e5 100644
--- a/fs/ocfs2/dlm/dlmdebug.c
+++ b/fs/ocfs2/dlm/dlmdebug.c
@@ -706,6 +706,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
#define DLM_DEBUGFS_DIR "o2dlm"
#define DLM_DEBUGFS_DLM_STATE "dlm_state"
#define DLM_DEBUGFS_LOCKING_STATE "locking_state"
+#define DLM_DEBUGFS_MLE_STATE "mle_state"
/* 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.
@@ -827,6 +828,112 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
}
/* end - util funcs */
+/* begin - debug mle funcs */
+static int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
+{
+ int out = 0;
+ unsigned int namelen;
+ const char *name;
+ char *mle_type;
+
+ if (mle->type != DLM_MLE_MASTER) {
+ namelen = mle->u.name.len;
+ name = mle->u.name.name;
+ } else {
+ namelen = mle->u.res->lockname.len;
+ name = mle->u.res->lockname.name;
+ }
+
+ if (mle->type == DLM_MLE_BLOCK)
+ mle_type = "BLK";
+ else if (mle->type == DLM_MLE_MASTER)
+ mle_type = "MAS";
+ else
+ mle_type = "MIG";
+
+ out += stringify_lockname(name, namelen, buf + out, len - out);
+ out += snprintf(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,
+ atomic_read(&mle->mle_refs.refcount));
+
+ out += snprintf(buf + out, len - out, "Maybe=");
+ out += stringify_nodemap(mle->maybe_map, O2NM_MAX_NODES,
+ buf + out, len - out);
+ out += snprintf(buf + out, len - out, "\n");
+
+ out += snprintf(buf + out, len - out, "Vote=");
+ out += stringify_nodemap(mle->vote_map, O2NM_MAX_NODES,
+ buf + out, len - out);
+ out += snprintf(buf + out, len - out, "\n");
+
+ out += snprintf(buf + out, len - out, "Response=");
+ out += stringify_nodemap(mle->response_map, O2NM_MAX_NODES,
+ buf + out, len - out);
+ out += snprintf(buf + out, len - out, "\n");
+
+ out += snprintf(buf + out, len - out, "Node=");
+ out += stringify_nodemap(mle->node_map, O2NM_MAX_NODES,
+ buf + out, len - out);
+ out += snprintf(buf + out, len - out, "\n");
+
+ out += snprintf(buf + out, len - out, "\n");
+
+ return out;
+}
+
+static int debug_mle_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
+{
+ struct dlm_master_list_entry *mle;
+ int out = 0;
+ unsigned long total = 0;
+
+ out += snprintf(db->buf + out, db->len - out,
+ "Dumping MLEs for Domain: %s\n", dlm->name);
+
+ spin_lock(&dlm->master_lock);
+ list_for_each_entry(mle, &dlm->master_list, list) {
+ ++total;
+ if (db->len - out < 200)
+ continue;
+ out += dump_mle(mle, db->buf + out, db->len - out);
+ }
+ spin_unlock(&dlm->master_lock);
+
+ out += snprintf(db->buf + out, db->len - out,
+ "Total on list: %ld\n", total);
+ return out;
+}
+
+static int debug_mle_open(struct inode *inode, struct file *file)
+{
+ struct dlm_ctxt *dlm = inode->i_private;
+ struct debug_buffer *db;
+
+ db = debug_buffer_allocate();
+ if (!db)
+ goto bail;
+
+ db->len = debug_mle_print(dlm, db);
+
+ file->private_data = db;
+
+ return 0;
+bail:
+ return -ENOMEM;
+}
+
+static struct file_operations debug_mle_fops = {
+ .open = debug_mle_open,
+ .release = debug_buffer_release,
+ .read = debug_buffer_read,
+ .llseek = debug_buffer_llseek,
+};
+
+/* end - debug mle funcs */
+
/* begin - debug lockres funcs */
static int dump_lock(struct dlm_lock *lock, int list_type, char *buf, int len)
{
@@ -1222,6 +1329,16 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
goto bail;
}
+ /* for dumping mles */
+ dc->debug_mle_dentry = debugfs_create_file(DLM_DEBUGFS_MLE_STATE,
+ S_IFREG|S_IRUSR,
+ dlm->dlm_debugfs_subroot,
+ dlm, &debug_mle_fops);
+ if (!dc->debug_mle_dentry) {
+ mlog_errno(-ENOMEM);
+ goto bail;
+ }
+
dlm_debug_get(dc);
return 0;
@@ -1235,6 +1352,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
if (dc) {
+ if (dc->debug_mle_dentry)
+ debugfs_remove(dc->debug_mle_dentry);
if (dc->debug_lockres_dentry)
debugfs_remove(dc->debug_lockres_dentry);
if (dc->debug_state_dentry)
diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
index 86d02f4..c6b240f 100644
--- a/fs/ocfs2/dlm/dlmdebug.h
+++ b/fs/ocfs2/dlm/dlmdebug.h
@@ -29,6 +29,7 @@ struct dlm_debug_ctxt {
struct kref debug_refcnt;
struct dentry *debug_state_dentry;
struct dentry *debug_lockres_dentry;
+ struct dentry *debug_mle_dentry;
};
struct debug_buffer
--
1.5.2.5
^ permalink raw reply related [flat|nested] 41+ messages in thread* [Ocfs2-devel] [PATCH 11/18] ocfs2_dlm: Dumps the mles into a debugfs file
2008-02-25 12:21 ` [Ocfs2-devel] [PATCH 11/18] ocfs2_dlm: Dumps the mles into " Sunil Mushran
@ 2008-02-28 16:53 ` Joel Becker
0 siblings, 0 replies; 41+ messages in thread
From: Joel Becker @ 2008-02-28 16:53 UTC (permalink / raw)
To: ocfs2-devel
On Mon, Feb 25, 2008 at 12:20:55PM -0800, Sunil Mushran wrote:
> This patch dumps all mles it can fit in one page into a debugfs file.
> Useful for debugging.
>
> Signed-off-by: Sunil Mushran <sunil.mushran@oracle.com>
Looks good modulo DEBUG_FS.
Joel
> ---
> fs/ocfs2/dlm/dlmdebug.c | 119 +++++++++++++++++++++++++++++++++++++++++++++++
> fs/ocfs2/dlm/dlmdebug.h | 1 +
> 2 files changed, 120 insertions(+), 0 deletions(-)
>
> diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c
> index 905145a..158b2e5 100644
> --- a/fs/ocfs2/dlm/dlmdebug.c
> +++ b/fs/ocfs2/dlm/dlmdebug.c
> @@ -706,6 +706,7 @@ EXPORT_SYMBOL_GPL(dlm_errname);
> #define DLM_DEBUGFS_DIR "o2dlm"
> #define DLM_DEBUGFS_DLM_STATE "dlm_state"
> #define DLM_DEBUGFS_LOCKING_STATE "locking_state"
> +#define DLM_DEBUGFS_MLE_STATE "mle_state"
>
> /* 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.
> @@ -827,6 +828,112 @@ static int debug_buffer_release(struct inode *inode, struct file *file)
> }
> /* end - util funcs */
>
> +/* begin - debug mle funcs */
> +static int dump_mle(struct dlm_master_list_entry *mle, char *buf, int len)
> +{
> + int out = 0;
> + unsigned int namelen;
> + const char *name;
> + char *mle_type;
> +
> + if (mle->type != DLM_MLE_MASTER) {
> + namelen = mle->u.name.len;
> + name = mle->u.name.name;
> + } else {
> + namelen = mle->u.res->lockname.len;
> + name = mle->u.res->lockname.name;
> + }
> +
> + if (mle->type == DLM_MLE_BLOCK)
> + mle_type = "BLK";
> + else if (mle->type == DLM_MLE_MASTER)
> + mle_type = "MAS";
> + else
> + mle_type = "MIG";
> +
> + out += stringify_lockname(name, namelen, buf + out, len - out);
> + out += snprintf(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,
> + atomic_read(&mle->mle_refs.refcount));
> +
> + out += snprintf(buf + out, len - out, "Maybe=");
> + out += stringify_nodemap(mle->maybe_map, O2NM_MAX_NODES,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> + out += snprintf(buf + out, len - out, "Vote=");
> + out += stringify_nodemap(mle->vote_map, O2NM_MAX_NODES,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> + out += snprintf(buf + out, len - out, "Response=");
> + out += stringify_nodemap(mle->response_map, O2NM_MAX_NODES,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> + out += snprintf(buf + out, len - out, "Node=");
> + out += stringify_nodemap(mle->node_map, O2NM_MAX_NODES,
> + buf + out, len - out);
> + out += snprintf(buf + out, len - out, "\n");
> +
> + out += snprintf(buf + out, len - out, "\n");
> +
> + return out;
> +}
> +
> +static int debug_mle_print(struct dlm_ctxt *dlm, struct debug_buffer *db)
> +{
> + struct dlm_master_list_entry *mle;
> + int out = 0;
> + unsigned long total = 0;
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Dumping MLEs for Domain: %s\n", dlm->name);
> +
> + spin_lock(&dlm->master_lock);
> + list_for_each_entry(mle, &dlm->master_list, list) {
> + ++total;
> + if (db->len - out < 200)
> + continue;
> + out += dump_mle(mle, db->buf + out, db->len - out);
> + }
> + spin_unlock(&dlm->master_lock);
> +
> + out += snprintf(db->buf + out, db->len - out,
> + "Total on list: %ld\n", total);
> + return out;
> +}
> +
> +static int debug_mle_open(struct inode *inode, struct file *file)
> +{
> + struct dlm_ctxt *dlm = inode->i_private;
> + struct debug_buffer *db;
> +
> + db = debug_buffer_allocate();
> + if (!db)
> + goto bail;
> +
> + db->len = debug_mle_print(dlm, db);
> +
> + file->private_data = db;
> +
> + return 0;
> +bail:
> + return -ENOMEM;
> +}
> +
> +static struct file_operations debug_mle_fops = {
> + .open = debug_mle_open,
> + .release = debug_buffer_release,
> + .read = debug_buffer_read,
> + .llseek = debug_buffer_llseek,
> +};
> +
> +/* end - debug mle funcs */
> +
> /* begin - debug lockres funcs */
> static int dump_lock(struct dlm_lock *lock, int list_type, char *buf, int len)
> {
> @@ -1222,6 +1329,16 @@ int dlm_debug_init(struct dlm_ctxt *dlm)
> goto bail;
> }
>
> + /* for dumping mles */
> + dc->debug_mle_dentry = debugfs_create_file(DLM_DEBUGFS_MLE_STATE,
> + S_IFREG|S_IRUSR,
> + dlm->dlm_debugfs_subroot,
> + dlm, &debug_mle_fops);
> + if (!dc->debug_mle_dentry) {
> + mlog_errno(-ENOMEM);
> + goto bail;
> + }
> +
> dlm_debug_get(dc);
> return 0;
>
> @@ -1235,6 +1352,8 @@ void dlm_debug_shutdown(struct dlm_ctxt *dlm)
> struct dlm_debug_ctxt *dc = dlm->dlm_debug_ctxt;
>
> if (dc) {
> + if (dc->debug_mle_dentry)
> + debugfs_remove(dc->debug_mle_dentry);
> if (dc->debug_lockres_dentry)
> debugfs_remove(dc->debug_lockres_dentry);
> if (dc->debug_state_dentry)
> diff --git a/fs/ocfs2/dlm/dlmdebug.h b/fs/ocfs2/dlm/dlmdebug.h
> index 86d02f4..c6b240f 100644
> --- a/fs/ocfs2/dlm/dlmdebug.h
> +++ b/fs/ocfs2/dlm/dlmdebug.h
> @@ -29,6 +29,7 @@ struct dlm_debug_ctxt {
> struct kref debug_refcnt;
> struct dentry *debug_state_dentry;
> struct dentry *debug_lockres_dentry;
> + struct dentry *debug_mle_dentry;
> };
>
> struct debug_buffer
> --
> 1.5.2.5
>
>
> _______________________________________________
> Ocfs2-devel mailing list
> Ocfs2-devel@oss.oracle.com
> http://oss.oracle.com/mailman/listinfo/ocfs2-devel
--
Bram's Law:
The easier a piece of software is to write, the worse it's
implemented in practice.
Joel Becker
Principal Software Developer
Oracle
E-mail: joel.becker@oracle.com
Phone: (650) 506-8127
^ permalink raw reply [flat|nested] 41+ messages in thread