aboutsummaryrefslogtreecommitdiffstats
path: root/fs/ocfs2/dlmglue.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/ocfs2/dlmglue.c')
-rw-r--r--fs/ocfs2/dlmglue.c136
1 files changed, 128 insertions, 8 deletions
diff --git a/fs/ocfs2/dlmglue.c b/fs/ocfs2/dlmglue.c
index 394d25a131a5..eae3d643a5e4 100644
--- a/fs/ocfs2/dlmglue.c
+++ b/fs/ocfs2/dlmglue.c
@@ -31,6 +31,7 @@
31#include <linux/pagemap.h> 31#include <linux/pagemap.h>
32#include <linux/debugfs.h> 32#include <linux/debugfs.h>
33#include <linux/seq_file.h> 33#include <linux/seq_file.h>
34#include <linux/time.h>
34 35
35#define MLOG_MASK_PREFIX ML_DLM_GLUE 36#define MLOG_MASK_PREFIX ML_DLM_GLUE
36#include <cluster/masklog.h> 37#include <cluster/masklog.h>
@@ -59,6 +60,9 @@ struct ocfs2_mask_waiter {
59 struct completion mw_complete; 60 struct completion mw_complete;
60 unsigned long mw_mask; 61 unsigned long mw_mask;
61 unsigned long mw_goal; 62 unsigned long mw_goal;
63#ifdef CONFIG_OCFS2_FS_STATS
64 unsigned long long mw_lock_start;
65#endif
62}; 66};
63 67
64static struct ocfs2_super *ocfs2_get_dentry_osb(struct ocfs2_lock_res *lockres); 68static struct ocfs2_super *ocfs2_get_dentry_osb(struct ocfs2_lock_res *lockres);
@@ -366,6 +370,75 @@ static void ocfs2_remove_lockres_tracking(struct ocfs2_lock_res *res)
366 spin_unlock(&ocfs2_dlm_tracking_lock); 370 spin_unlock(&ocfs2_dlm_tracking_lock);
367} 371}
368 372
373#ifdef CONFIG_OCFS2_FS_STATS
374static void ocfs2_init_lock_stats(struct ocfs2_lock_res *res)
375{
376 res->l_lock_num_prmode = 0;
377 res->l_lock_num_prmode_failed = 0;
378 res->l_lock_total_prmode = 0;
379 res->l_lock_max_prmode = 0;
380 res->l_lock_num_exmode = 0;
381 res->l_lock_num_exmode_failed = 0;
382 res->l_lock_total_exmode = 0;
383 res->l_lock_max_exmode = 0;
384 res->l_lock_refresh = 0;
385}
386
387static void ocfs2_update_lock_stats(struct ocfs2_lock_res *res, int level,
388 struct ocfs2_mask_waiter *mw, int ret)
389{
390 unsigned long long *num, *sum;
391 unsigned int *max, *failed;
392 struct timespec ts = current_kernel_time();
393 unsigned long long time = timespec_to_ns(&ts) - mw->mw_lock_start;
394
395 if (level == LKM_PRMODE) {
396 num = &res->l_lock_num_prmode;
397 sum = &res->l_lock_total_prmode;
398 max = &res->l_lock_max_prmode;
399 failed = &res->l_lock_num_prmode_failed;
400 } else if (level == LKM_EXMODE) {
401 num = &res->l_lock_num_exmode;
402 sum = &res->l_lock_total_exmode;
403 max = &res->l_lock_max_exmode;
404 failed = &res->l_lock_num_exmode_failed;
405 } else
406 return;
407
408 (*num)++;
409 (*sum) += time;
410 if (time > *max)
411 *max = time;
412 if (ret)
413 (*failed)++;
414}
415
416static inline void ocfs2_track_lock_refresh(struct ocfs2_lock_res *lockres)
417{
418 lockres->l_lock_refresh++;
419}
420
421static inline void ocfs2_init_start_time(struct ocfs2_mask_waiter *mw)
422{
423 struct timespec ts = current_kernel_time();
424 mw->mw_lock_start = timespec_to_ns(&ts);
425}
426#else
427static inline void ocfs2_init_lock_stats(struct ocfs2_lock_res *res)
428{
429}
430static inline void ocfs2_update_lock_stats(struct ocfs2_lock_res *res,
431 int level, struct ocfs2_mask_waiter *mw, int ret)
432{
433}
434static inline void ocfs2_track_lock_refresh(struct ocfs2_lock_res *lockres)
435{
436}
437static inline void ocfs2_init_start_time(struct ocfs2_mask_waiter *mw)
438{
439}
440#endif
441
369static void ocfs2_lock_res_init_common(struct ocfs2_super *osb, 442static void ocfs2_lock_res_init_common(struct ocfs2_super *osb,
370 struct ocfs2_lock_res *res, 443 struct ocfs2_lock_res *res,
371 enum ocfs2_lock_type type, 444 enum ocfs2_lock_type type,
@@ -385,6 +458,8 @@ static void ocfs2_lock_res_init_common(struct ocfs2_super *osb,
385 res->l_flags = OCFS2_LOCK_INITIALIZED; 458 res->l_flags = OCFS2_LOCK_INITIALIZED;
386 459
387 ocfs2_add_lockres_tracking(res, osb->osb_dlm_debug); 460 ocfs2_add_lockres_tracking(res, osb->osb_dlm_debug);
461
462 ocfs2_init_lock_stats(res);
388} 463}
389 464
390void ocfs2_lock_res_init_once(struct ocfs2_lock_res *res) 465void ocfs2_lock_res_init_once(struct ocfs2_lock_res *res)
@@ -1048,6 +1123,7 @@ static void ocfs2_init_mask_waiter(struct ocfs2_mask_waiter *mw)
1048{ 1123{
1049 INIT_LIST_HEAD(&mw->mw_item); 1124 INIT_LIST_HEAD(&mw->mw_item);
1050 init_completion(&mw->mw_complete); 1125 init_completion(&mw->mw_complete);
1126 ocfs2_init_start_time(mw);
1051} 1127}
1052 1128
1053static int ocfs2_wait_for_mask(struct ocfs2_mask_waiter *mw) 1129static int ocfs2_wait_for_mask(struct ocfs2_mask_waiter *mw)
@@ -1254,6 +1330,7 @@ out:
1254 goto again; 1330 goto again;
1255 mlog_errno(ret); 1331 mlog_errno(ret);
1256 } 1332 }
1333 ocfs2_update_lock_stats(lockres, level, &mw, ret);
1257 1334
1258 mlog_exit(ret); 1335 mlog_exit(ret);
1259 return ret; 1336 return ret;
@@ -1554,8 +1631,8 @@ out:
1554 */ 1631 */
1555int ocfs2_file_lock(struct file *file, int ex, int trylock) 1632int ocfs2_file_lock(struct file *file, int ex, int trylock)
1556{ 1633{
1557 int ret, level = ex ? LKM_EXMODE : LKM_PRMODE; 1634 int ret, level = ex ? DLM_LOCK_EX : DLM_LOCK_PR;
1558 unsigned int lkm_flags = trylock ? LKM_NOQUEUE : 0; 1635 unsigned int lkm_flags = trylock ? DLM_LKF_NOQUEUE : 0;
1559 unsigned long flags; 1636 unsigned long flags;
1560 struct ocfs2_file_private *fp = file->private_data; 1637 struct ocfs2_file_private *fp = file->private_data;
1561 struct ocfs2_lock_res *lockres = &fp->fp_flock; 1638 struct ocfs2_lock_res *lockres = &fp->fp_flock;
@@ -1582,7 +1659,7 @@ int ocfs2_file_lock(struct file *file, int ex, int trylock)
1582 * Get the lock at NLMODE to start - that way we 1659 * Get the lock at NLMODE to start - that way we
1583 * can cancel the upconvert request if need be. 1660 * can cancel the upconvert request if need be.
1584 */ 1661 */
1585 ret = ocfs2_lock_create(osb, lockres, LKM_NLMODE, 0); 1662 ret = ocfs2_lock_create(osb, lockres, DLM_LOCK_NL, 0);
1586 if (ret < 0) { 1663 if (ret < 0) {
1587 mlog_errno(ret); 1664 mlog_errno(ret);
1588 goto out; 1665 goto out;
@@ -1597,7 +1674,7 @@ int ocfs2_file_lock(struct file *file, int ex, int trylock)
1597 } 1674 }
1598 1675
1599 lockres->l_action = OCFS2_AST_CONVERT; 1676 lockres->l_action = OCFS2_AST_CONVERT;
1600 lkm_flags |= LKM_CONVERT; 1677 lkm_flags |= DLM_LKF_CONVERT;
1601 lockres->l_requested = level; 1678 lockres->l_requested = level;
1602 lockres_or_flags(lockres, OCFS2_LOCK_BUSY); 1679 lockres_or_flags(lockres, OCFS2_LOCK_BUSY);
1603 1680
@@ -1664,7 +1741,7 @@ void ocfs2_file_unlock(struct file *file)
1664 if (!(lockres->l_flags & OCFS2_LOCK_ATTACHED)) 1741 if (!(lockres->l_flags & OCFS2_LOCK_ATTACHED))
1665 return; 1742 return;
1666 1743
1667 if (lockres->l_level == LKM_NLMODE) 1744 if (lockres->l_level == DLM_LOCK_NL)
1668 return; 1745 return;
1669 1746
1670 mlog(0, "Unlock: \"%s\" flags: 0x%lx, level: %d, act: %d\n", 1747 mlog(0, "Unlock: \"%s\" flags: 0x%lx, level: %d, act: %d\n",
@@ -1678,11 +1755,11 @@ void ocfs2_file_unlock(struct file *file)
1678 lockres_or_flags(lockres, OCFS2_LOCK_BLOCKED); 1755 lockres_or_flags(lockres, OCFS2_LOCK_BLOCKED);
1679 lockres->l_blocking = DLM_LOCK_EX; 1756 lockres->l_blocking = DLM_LOCK_EX;
1680 1757
1681 gen = ocfs2_prepare_downconvert(lockres, LKM_NLMODE); 1758 gen = ocfs2_prepare_downconvert(lockres, DLM_LOCK_NL);
1682 lockres_add_mask_waiter(lockres, &mw, OCFS2_LOCK_BUSY, 0); 1759 lockres_add_mask_waiter(lockres, &mw, OCFS2_LOCK_BUSY, 0);
1683 spin_unlock_irqrestore(&lockres->l_lock, flags); 1760 spin_unlock_irqrestore(&lockres->l_lock, flags);
1684 1761
1685 ret = ocfs2_downconvert_lock(osb, lockres, LKM_NLMODE, 0, gen); 1762 ret = ocfs2_downconvert_lock(osb, lockres, DLM_LOCK_NL, 0, gen);
1686 if (ret) { 1763 if (ret) {
1687 mlog_errno(ret); 1764 mlog_errno(ret);
1688 return; 1765 return;
@@ -1983,6 +2060,7 @@ static int ocfs2_inode_lock_update(struct inode *inode,
1983 le32_to_cpu(fe->i_flags)); 2060 le32_to_cpu(fe->i_flags));
1984 2061
1985 ocfs2_refresh_inode(inode, fe); 2062 ocfs2_refresh_inode(inode, fe);
2063 ocfs2_track_lock_refresh(lockres);
1986 } 2064 }
1987 2065
1988 status = 0; 2066 status = 0;
@@ -2267,6 +2345,7 @@ int ocfs2_super_lock(struct ocfs2_super *osb,
2267 2345
2268 if (status < 0) 2346 if (status < 0)
2269 mlog_errno(status); 2347 mlog_errno(status);
2348 ocfs2_track_lock_refresh(lockres);
2270 } 2349 }
2271bail: 2350bail:
2272 mlog_exit(status); 2351 mlog_exit(status);
@@ -2461,7 +2540,7 @@ static void *ocfs2_dlm_seq_next(struct seq_file *m, void *v, loff_t *pos)
2461} 2540}
2462 2541
2463/* So that debugfs.ocfs2 can determine which format is being used */ 2542/* So that debugfs.ocfs2 can determine which format is being used */
2464#define OCFS2_DLM_DEBUG_STR_VERSION 1 2543#define OCFS2_DLM_DEBUG_STR_VERSION 2
2465static int ocfs2_dlm_seq_show(struct seq_file *m, void *v) 2544static int ocfs2_dlm_seq_show(struct seq_file *m, void *v)
2466{ 2545{
2467 int i; 2546 int i;
@@ -2502,6 +2581,47 @@ static int ocfs2_dlm_seq_show(struct seq_file *m, void *v)
2502 for(i = 0; i < DLM_LVB_LEN; i++) 2581 for(i = 0; i < DLM_LVB_LEN; i++)
2503 seq_printf(m, "0x%x\t", lvb[i]); 2582 seq_printf(m, "0x%x\t", lvb[i]);
2504 2583
2584#ifdef CONFIG_OCFS2_FS_STATS
2585# define lock_num_prmode(_l) (_l)->l_lock_num_prmode
2586# define lock_num_exmode(_l) (_l)->l_lock_num_exmode
2587# define lock_num_prmode_failed(_l) (_l)->l_lock_num_prmode_failed
2588# define lock_num_exmode_failed(_l) (_l)->l_lock_num_exmode_failed
2589# define lock_total_prmode(_l) (_l)->l_lock_total_prmode
2590# define lock_total_exmode(_l) (_l)->l_lock_total_exmode
2591# define lock_max_prmode(_l) (_l)->l_lock_max_prmode
2592# define lock_max_exmode(_l) (_l)->l_lock_max_exmode
2593# define lock_refresh(_l) (_l)->l_lock_refresh
2594#else
2595# define lock_num_prmode(_l) (0ULL)
2596# define lock_num_exmode(_l) (0ULL)
2597# define lock_num_prmode_failed(_l) (0)
2598# define lock_num_exmode_failed(_l) (0)
2599# define lock_total_prmode(_l) (0ULL)
2600# define lock_total_exmode(_l) (0ULL)
2601# define lock_max_prmode(_l) (0)
2602# define lock_max_exmode(_l) (0)
2603# define lock_refresh(_l) (0)
2604#endif
2605 /* The following seq_print was added in version 2 of this output */
2606 seq_printf(m, "%llu\t"
2607 "%llu\t"
2608 "%u\t"
2609 "%u\t"
2610 "%llu\t"
2611 "%llu\t"
2612 "%u\t"
2613 "%u\t"
2614 "%u\t",
2615 lock_num_prmode(lockres),
2616 lock_num_exmode(lockres),
2617 lock_num_prmode_failed(lockres),
2618 lock_num_exmode_failed(lockres),
2619 lock_total_prmode(lockres),
2620 lock_total_exmode(lockres),
2621 lock_max_prmode(lockres),
2622 lock_max_exmode(lockres),
2623 lock_refresh(lockres));
2624
2505 /* End the line */ 2625 /* End the line */
2506 seq_printf(m, "\n"); 2626 seq_printf(m, "\n");
2507 return 0; 2627 return 0;