aboutsummaryrefslogtreecommitdiffstats
path: root/fs/ocfs2
diff options
context:
space:
mode:
authorMark Fasheh <mark.fasheh@oracle.com>2006-03-09 20:55:56 -0500
committerMark Fasheh <mark.fasheh@oracle.com>2006-06-26 17:42:39 -0400
commita3d3329159ea76bae0b3b8680691a1c3ecf5801f (patch)
treea4521103c45190ff340f918d131649a20b414b27 /fs/ocfs2
parent65c491d833a06fd0d1383297590772c75d28155c (diff)
ocfs2: calculate lockid hash values outside of the spinlock
Fixes a performance bug - pointed out by Andrew. Signed-off-by: Mark Fasheh <mark.fasheh@oracle.com>
Diffstat (limited to 'fs/ocfs2')
-rw-r--r--fs/ocfs2/dlm/dlmcommon.h6
-rw-r--r--fs/ocfs2/dlm/dlmdomain.c12
-rw-r--r--fs/ocfs2/dlm/dlmmaster.c26
-rw-r--r--fs/ocfs2/dlm/dlmrecovery.c5
4 files changed, 30 insertions, 19 deletions
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h
index 1c05d485e019..3b675368762e 100644
--- a/fs/ocfs2/dlm/dlmcommon.h
+++ b/fs/ocfs2/dlm/dlmcommon.h
@@ -39,6 +39,9 @@
39 39
40#define DLM_HASH_BUCKETS (PAGE_SIZE / sizeof(struct hlist_head)) 40#define DLM_HASH_BUCKETS (PAGE_SIZE / sizeof(struct hlist_head))
41 41
42/* Intended to make it easier for us to switch out hash functions */
43#define dlm_lockid_hash(_n, _l) full_name_hash(_n, _l)
44
42enum dlm_ast_type { 45enum dlm_ast_type {
43 DLM_AST = 0, 46 DLM_AST = 0,
44 DLM_BAST, 47 DLM_BAST,
@@ -694,7 +697,8 @@ void __dlm_insert_lockres(struct dlm_ctxt *dlm,
694 struct dlm_lock_resource *res); 697 struct dlm_lock_resource *res);
695struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm, 698struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm,
696 const char *name, 699 const char *name,
697 unsigned int len); 700 unsigned int len,
701 unsigned int hash);
698struct dlm_lock_resource * dlm_lookup_lockres(struct dlm_ctxt *dlm, 702struct dlm_lock_resource * dlm_lookup_lockres(struct dlm_ctxt *dlm,
699 const char *name, 703 const char *name,
700 unsigned int len); 704 unsigned int len);
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index 8f3a9e3106fd..a818fde24476 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -90,7 +90,6 @@ void __dlm_insert_lockres(struct dlm_ctxt *dlm,
90 assert_spin_locked(&dlm->spinlock); 90 assert_spin_locked(&dlm->spinlock);
91 91
92 q = &res->lockname; 92 q = &res->lockname;
93 q->hash = full_name_hash(q->name, q->len);
94 bucket = &(dlm->lockres_hash[q->hash % DLM_HASH_BUCKETS]); 93 bucket = &(dlm->lockres_hash[q->hash % DLM_HASH_BUCKETS]);
95 94
96 /* get a reference for our hashtable */ 95 /* get a reference for our hashtable */
@@ -100,10 +99,10 @@ void __dlm_insert_lockres(struct dlm_ctxt *dlm,
100} 99}
101 100
102struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm, 101struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm,
103 const char *name, 102 const char *name,
104 unsigned int len) 103 unsigned int len,
104 unsigned int hash)
105{ 105{
106 unsigned int hash;
107 struct hlist_node *iter; 106 struct hlist_node *iter;
108 struct dlm_lock_resource *tmpres=NULL; 107 struct dlm_lock_resource *tmpres=NULL;
109 struct hlist_head *bucket; 108 struct hlist_head *bucket;
@@ -112,8 +111,6 @@ struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm,
112 111
113 assert_spin_locked(&dlm->spinlock); 112 assert_spin_locked(&dlm->spinlock);
114 113
115 hash = full_name_hash(name, len);
116
117 bucket = &(dlm->lockres_hash[hash % DLM_HASH_BUCKETS]); 114 bucket = &(dlm->lockres_hash[hash % DLM_HASH_BUCKETS]);
118 115
119 /* check for pre-existing lock */ 116 /* check for pre-existing lock */
@@ -135,9 +132,10 @@ struct dlm_lock_resource * dlm_lookup_lockres(struct dlm_ctxt *dlm,
135 unsigned int len) 132 unsigned int len)
136{ 133{
137 struct dlm_lock_resource *res; 134 struct dlm_lock_resource *res;
135 unsigned int hash = dlm_lockid_hash(name, len);
138 136
139 spin_lock(&dlm->spinlock); 137 spin_lock(&dlm->spinlock);
140 res = __dlm_lookup_lockres(dlm, name, len); 138 res = __dlm_lookup_lockres(dlm, name, len, hash);
141 spin_unlock(&dlm->spinlock); 139 spin_unlock(&dlm->spinlock);
142 return res; 140 return res;
143} 141}
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c
index 940be4c13b1f..953aa8421be4 100644
--- a/fs/ocfs2/dlm/dlmmaster.c
+++ b/fs/ocfs2/dlm/dlmmaster.c
@@ -603,7 +603,7 @@ static void dlm_init_lockres(struct dlm_ctxt *dlm,
603 memcpy(qname, name, namelen); 603 memcpy(qname, name, namelen);
604 604
605 res->lockname.len = namelen; 605 res->lockname.len = namelen;
606 res->lockname.hash = full_name_hash(name, namelen); 606 res->lockname.hash = dlm_lockid_hash(name, namelen);
607 607
608 init_waitqueue_head(&res->wq); 608 init_waitqueue_head(&res->wq);
609 spin_lock_init(&res->spinlock); 609 spin_lock_init(&res->spinlock);
@@ -677,19 +677,20 @@ struct dlm_lock_resource * dlm_get_lock_resource(struct dlm_ctxt *dlm,
677 int blocked = 0; 677 int blocked = 0;
678 int ret, nodenum; 678 int ret, nodenum;
679 struct dlm_node_iter iter; 679 struct dlm_node_iter iter;
680 unsigned int namelen; 680 unsigned int namelen, hash;
681 int tries = 0; 681 int tries = 0;
682 int bit, wait_on_recovery = 0; 682 int bit, wait_on_recovery = 0;
683 683
684 BUG_ON(!lockid); 684 BUG_ON(!lockid);
685 685
686 namelen = strlen(lockid); 686 namelen = strlen(lockid);
687 hash = dlm_lockid_hash(lockid, namelen);
687 688
688 mlog(0, "get lockres %s (len %d)\n", lockid, namelen); 689 mlog(0, "get lockres %s (len %d)\n", lockid, namelen);
689 690
690lookup: 691lookup:
691 spin_lock(&dlm->spinlock); 692 spin_lock(&dlm->spinlock);
692 tmpres = __dlm_lookup_lockres(dlm, lockid, namelen); 693 tmpres = __dlm_lookup_lockres(dlm, lockid, namelen, hash);
693 if (tmpres) { 694 if (tmpres) {
694 spin_unlock(&dlm->spinlock); 695 spin_unlock(&dlm->spinlock);
695 mlog(0, "found in hash!\n"); 696 mlog(0, "found in hash!\n");
@@ -1316,7 +1317,7 @@ int dlm_master_request_handler(struct o2net_msg *msg, u32 len, void *data)
1316 struct dlm_master_request *request = (struct dlm_master_request *) msg->buf; 1317 struct dlm_master_request *request = (struct dlm_master_request *) msg->buf;
1317 struct dlm_master_list_entry *mle = NULL, *tmpmle = NULL; 1318 struct dlm_master_list_entry *mle = NULL, *tmpmle = NULL;
1318 char *name; 1319 char *name;
1319 unsigned int namelen; 1320 unsigned int namelen, hash;
1320 int found, ret; 1321 int found, ret;
1321 int set_maybe; 1322 int set_maybe;
1322 int dispatch_assert = 0; 1323 int dispatch_assert = 0;
@@ -1331,6 +1332,7 @@ int dlm_master_request_handler(struct o2net_msg *msg, u32 len, void *data)
1331 1332
1332 name = request->name; 1333 name = request->name;
1333 namelen = request->namelen; 1334 namelen = request->namelen;
1335 hash = dlm_lockid_hash(name, namelen);
1334 1336
1335 if (namelen > DLM_LOCKID_NAME_MAX) { 1337 if (namelen > DLM_LOCKID_NAME_MAX) {
1336 response = DLM_IVBUFLEN; 1338 response = DLM_IVBUFLEN;
@@ -1339,7 +1341,7 @@ int dlm_master_request_handler(struct o2net_msg *msg, u32 len, void *data)
1339 1341
1340way_up_top: 1342way_up_top:
1341 spin_lock(&dlm->spinlock); 1343 spin_lock(&dlm->spinlock);
1342 res = __dlm_lookup_lockres(dlm, name, namelen); 1344 res = __dlm_lookup_lockres(dlm, name, namelen, hash);
1343 if (res) { 1345 if (res) {
1344 spin_unlock(&dlm->spinlock); 1346 spin_unlock(&dlm->spinlock);
1345 1347
@@ -1612,7 +1614,7 @@ int dlm_assert_master_handler(struct o2net_msg *msg, u32 len, void *data)
1612 struct dlm_assert_master *assert = (struct dlm_assert_master *)msg->buf; 1614 struct dlm_assert_master *assert = (struct dlm_assert_master *)msg->buf;
1613 struct dlm_lock_resource *res = NULL; 1615 struct dlm_lock_resource *res = NULL;
1614 char *name; 1616 char *name;
1615 unsigned int namelen; 1617 unsigned int namelen, hash;
1616 u32 flags; 1618 u32 flags;
1617 int master_request = 0; 1619 int master_request = 0;
1618 int ret = 0; 1620 int ret = 0;
@@ -1622,6 +1624,7 @@ int dlm_assert_master_handler(struct o2net_msg *msg, u32 len, void *data)
1622 1624
1623 name = assert->name; 1625 name = assert->name;
1624 namelen = assert->namelen; 1626 namelen = assert->namelen;
1627 hash = dlm_lockid_hash(name, namelen);
1625 flags = be32_to_cpu(assert->flags); 1628 flags = be32_to_cpu(assert->flags);
1626 1629
1627 if (namelen > DLM_LOCKID_NAME_MAX) { 1630 if (namelen > DLM_LOCKID_NAME_MAX) {
@@ -1670,7 +1673,7 @@ int dlm_assert_master_handler(struct o2net_msg *msg, u32 len, void *data)
1670 1673
1671 /* ok everything checks out with the MLE 1674 /* ok everything checks out with the MLE
1672 * now check to see if there is a lockres */ 1675 * now check to see if there is a lockres */
1673 res = __dlm_lookup_lockres(dlm, name, namelen); 1676 res = __dlm_lookup_lockres(dlm, name, namelen, hash);
1674 if (res) { 1677 if (res) {
1675 spin_lock(&res->spinlock); 1678 spin_lock(&res->spinlock);
1676 if (res->state & DLM_LOCK_RES_RECOVERING) { 1679 if (res->state & DLM_LOCK_RES_RECOVERING) {
@@ -2462,7 +2465,7 @@ int dlm_migrate_request_handler(struct o2net_msg *msg, u32 len, void *data)
2462 struct dlm_migrate_request *migrate = (struct dlm_migrate_request *) msg->buf; 2465 struct dlm_migrate_request *migrate = (struct dlm_migrate_request *) msg->buf;
2463 struct dlm_master_list_entry *mle = NULL, *oldmle = NULL; 2466 struct dlm_master_list_entry *mle = NULL, *oldmle = NULL;
2464 const char *name; 2467 const char *name;
2465 unsigned int namelen; 2468 unsigned int namelen, hash;
2466 int ret = 0; 2469 int ret = 0;
2467 2470
2468 if (!dlm_grab(dlm)) 2471 if (!dlm_grab(dlm))
@@ -2470,6 +2473,7 @@ int dlm_migrate_request_handler(struct o2net_msg *msg, u32 len, void *data)
2470 2473
2471 name = migrate->name; 2474 name = migrate->name;
2472 namelen = migrate->namelen; 2475 namelen = migrate->namelen;
2476 hash = dlm_lockid_hash(name, namelen);
2473 2477
2474 /* preallocate.. if this fails, abort */ 2478 /* preallocate.. if this fails, abort */
2475 mle = (struct dlm_master_list_entry *) kmem_cache_alloc(dlm_mle_cache, 2479 mle = (struct dlm_master_list_entry *) kmem_cache_alloc(dlm_mle_cache,
@@ -2482,7 +2486,7 @@ int dlm_migrate_request_handler(struct o2net_msg *msg, u32 len, void *data)
2482 2486
2483 /* check for pre-existing lock */ 2487 /* check for pre-existing lock */
2484 spin_lock(&dlm->spinlock); 2488 spin_lock(&dlm->spinlock);
2485 res = __dlm_lookup_lockres(dlm, name, namelen); 2489 res = __dlm_lookup_lockres(dlm, name, namelen, hash);
2486 spin_lock(&dlm->master_lock); 2490 spin_lock(&dlm->master_lock);
2487 2491
2488 if (res) { 2492 if (res) {
@@ -2601,6 +2605,7 @@ void dlm_clean_master_list(struct dlm_ctxt *dlm, u8 dead_node)
2601 struct list_head *iter, *iter2; 2605 struct list_head *iter, *iter2;
2602 struct dlm_master_list_entry *mle; 2606 struct dlm_master_list_entry *mle;
2603 struct dlm_lock_resource *res; 2607 struct dlm_lock_resource *res;
2608 unsigned int hash;
2604 2609
2605 mlog_entry("dlm=%s, dead node=%u\n", dlm->name, dead_node); 2610 mlog_entry("dlm=%s, dead node=%u\n", dlm->name, dead_node);
2606top: 2611top:
@@ -2684,8 +2689,9 @@ top:
2684 mle->master, mle->new_master); 2689 mle->master, mle->new_master);
2685 /* if there is a lockres associated with this 2690 /* if there is a lockres associated with this
2686 * mle, find it and set its owner to UNKNOWN */ 2691 * mle, find it and set its owner to UNKNOWN */
2692 hash = dlm_lockid_hash(mle->u.name.name, mle->u.name.len);
2687 res = __dlm_lookup_lockres(dlm, mle->u.name.name, 2693 res = __dlm_lookup_lockres(dlm, mle->u.name.name,
2688 mle->u.name.len); 2694 mle->u.name.len, hash);
2689 if (res) { 2695 if (res) {
2690 /* unfortunately if we hit this rare case, our 2696 /* unfortunately if we hit this rare case, our
2691 * lock ordering is messed. we need to drop 2697 * lock ordering is messed. we need to drop
diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c
index 9962190e7416..4f3d482a7299 100644
--- a/fs/ocfs2/dlm/dlmrecovery.c
+++ b/fs/ocfs2/dlm/dlmrecovery.c
@@ -1404,6 +1404,7 @@ int dlm_master_requery_handler(struct o2net_msg *msg, u32 len, void *data)
1404 struct dlm_ctxt *dlm = data; 1404 struct dlm_ctxt *dlm = data;
1405 struct dlm_master_requery *req = (struct dlm_master_requery *)msg->buf; 1405 struct dlm_master_requery *req = (struct dlm_master_requery *)msg->buf;
1406 struct dlm_lock_resource *res = NULL; 1406 struct dlm_lock_resource *res = NULL;
1407 unsigned int hash;
1407 int master = DLM_LOCK_RES_OWNER_UNKNOWN; 1408 int master = DLM_LOCK_RES_OWNER_UNKNOWN;
1408 u32 flags = DLM_ASSERT_MASTER_REQUERY; 1409 u32 flags = DLM_ASSERT_MASTER_REQUERY;
1409 1410
@@ -1413,8 +1414,10 @@ int dlm_master_requery_handler(struct o2net_msg *msg, u32 len, void *data)
1413 return master; 1414 return master;
1414 } 1415 }
1415 1416
1417 hash = dlm_lockid_hash(req->name, req->namelen);
1418
1416 spin_lock(&dlm->spinlock); 1419 spin_lock(&dlm->spinlock);
1417 res = __dlm_lookup_lockres(dlm, req->name, req->namelen); 1420 res = __dlm_lookup_lockres(dlm, req->name, req->namelen, hash);
1418 if (res) { 1421 if (res) {
1419 spin_lock(&res->spinlock); 1422 spin_lock(&res->spinlock);
1420 master = res->owner; 1423 master = res->owner;