diff options
author | Mark Fasheh <mark.fasheh@oracle.com> | 2006-02-28 20:31:22 -0500 |
---|---|---|
committer | Mark Fasheh <mark.fasheh@oracle.com> | 2006-03-01 15:18:16 -0500 |
commit | 81f2094a631df1ba275f4d4bd7ea5bacfd8dbcfc (patch) | |
tree | 20efc0b486ec9cb260d22dd09f02de13c0e71eb1 /fs/ocfs2/dlm | |
parent | b7668c72d2ae004363fb0588600bfa942e1b245c (diff) |
[PATCH] ocfs2: use hlists for lockres hash
Switch from list_head to hlist_head. Make the size of the hash dependent
upon the allocated area, rather than a constant.
Signed-off-by: Mark Fasheh <mark.fasheh@oracle.com>
Diffstat (limited to 'fs/ocfs2/dlm')
-rw-r--r-- | fs/ocfs2/dlm/dlmcommon.h | 8 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmdebug.c | 12 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmdomain.c | 39 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmmaster.c | 4 | ||||
-rw-r--r-- | fs/ocfs2/dlm/dlmrecovery.c | 23 |
5 files changed, 41 insertions, 45 deletions
diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h index 23ceaa7127b4..9c772583744a 100644 --- a/fs/ocfs2/dlm/dlmcommon.h +++ b/fs/ocfs2/dlm/dlmcommon.h | |||
@@ -37,9 +37,7 @@ | |||
37 | #define DLM_THREAD_SHUFFLE_INTERVAL 5 // flush everything every 5 passes | 37 | #define DLM_THREAD_SHUFFLE_INTERVAL 5 // flush everything every 5 passes |
38 | #define DLM_THREAD_MS 200 // flush at least every 200 ms | 38 | #define DLM_THREAD_MS 200 // flush at least every 200 ms |
39 | 39 | ||
40 | #define DLM_HASH_BITS 7 | 40 | #define DLM_HASH_BUCKETS (PAGE_SIZE / sizeof(struct hlist_head)) |
41 | #define DLM_HASH_SIZE (1 << DLM_HASH_BITS) | ||
42 | #define DLM_HASH_MASK (DLM_HASH_SIZE - 1) | ||
43 | 41 | ||
44 | enum dlm_ast_type { | 42 | enum dlm_ast_type { |
45 | DLM_AST = 0, | 43 | DLM_AST = 0, |
@@ -87,7 +85,7 @@ enum dlm_ctxt_state { | |||
87 | struct dlm_ctxt | 85 | struct dlm_ctxt |
88 | { | 86 | { |
89 | struct list_head list; | 87 | struct list_head list; |
90 | struct list_head *resources; | 88 | struct hlist_head *lockres_hash; |
91 | struct list_head dirty_list; | 89 | struct list_head dirty_list; |
92 | struct list_head purge_list; | 90 | struct list_head purge_list; |
93 | struct list_head pending_asts; | 91 | struct list_head pending_asts; |
@@ -217,7 +215,7 @@ struct dlm_lock_resource | |||
217 | { | 215 | { |
218 | /* WARNING: Please see the comment in dlm_init_lockres before | 216 | /* WARNING: Please see the comment in dlm_init_lockres before |
219 | * adding fields here. */ | 217 | * adding fields here. */ |
220 | struct list_head list; | 218 | struct hlist_node hash_node; |
221 | struct kref refs; | 219 | struct kref refs; |
222 | 220 | ||
223 | /* please keep these next 3 in this order | 221 | /* please keep these next 3 in this order |
diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c index f339fe27975a..54f61b76ab51 100644 --- a/fs/ocfs2/dlm/dlmdebug.c +++ b/fs/ocfs2/dlm/dlmdebug.c | |||
@@ -117,8 +117,8 @@ EXPORT_SYMBOL_GPL(dlm_print_one_lock); | |||
117 | void dlm_dump_lock_resources(struct dlm_ctxt *dlm) | 117 | void dlm_dump_lock_resources(struct dlm_ctxt *dlm) |
118 | { | 118 | { |
119 | struct dlm_lock_resource *res; | 119 | struct dlm_lock_resource *res; |
120 | struct list_head *iter; | 120 | struct hlist_node *iter; |
121 | struct list_head *bucket; | 121 | struct hlist_head *bucket; |
122 | int i; | 122 | int i; |
123 | 123 | ||
124 | mlog(ML_NOTICE, "struct dlm_ctxt: %s, node=%u, key=%u\n", | 124 | mlog(ML_NOTICE, "struct dlm_ctxt: %s, node=%u, key=%u\n", |
@@ -129,12 +129,10 @@ void dlm_dump_lock_resources(struct dlm_ctxt *dlm) | |||
129 | } | 129 | } |
130 | 130 | ||
131 | spin_lock(&dlm->spinlock); | 131 | spin_lock(&dlm->spinlock); |
132 | for (i=0; i<DLM_HASH_SIZE; i++) { | 132 | for (i=0; i<DLM_HASH_BUCKETS; i++) { |
133 | bucket = &(dlm->resources[i]); | 133 | bucket = &(dlm->lockres_hash[i]); |
134 | list_for_each(iter, bucket) { | 134 | hlist_for_each_entry(res, iter, bucket, hash_node) |
135 | res = list_entry(iter, struct dlm_lock_resource, list); | ||
136 | dlm_print_one_lock_resource(res); | 135 | dlm_print_one_lock_resource(res); |
137 | } | ||
138 | } | 136 | } |
139 | spin_unlock(&dlm->spinlock); | 137 | spin_unlock(&dlm->spinlock); |
140 | } | 138 | } |
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c index 6ee30837389c..8f3a9e3106fd 100644 --- a/fs/ocfs2/dlm/dlmdomain.c +++ b/fs/ocfs2/dlm/dlmdomain.c | |||
@@ -77,26 +77,26 @@ static void dlm_unregister_domain_handlers(struct dlm_ctxt *dlm); | |||
77 | 77 | ||
78 | void __dlm_unhash_lockres(struct dlm_lock_resource *lockres) | 78 | void __dlm_unhash_lockres(struct dlm_lock_resource *lockres) |
79 | { | 79 | { |
80 | list_del_init(&lockres->list); | 80 | hlist_del_init(&lockres->hash_node); |
81 | dlm_lockres_put(lockres); | 81 | dlm_lockres_put(lockres); |
82 | } | 82 | } |
83 | 83 | ||
84 | void __dlm_insert_lockres(struct dlm_ctxt *dlm, | 84 | void __dlm_insert_lockres(struct dlm_ctxt *dlm, |
85 | struct dlm_lock_resource *res) | 85 | struct dlm_lock_resource *res) |
86 | { | 86 | { |
87 | struct list_head *bucket; | 87 | struct hlist_head *bucket; |
88 | struct qstr *q; | 88 | struct qstr *q; |
89 | 89 | ||
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); | 93 | q->hash = full_name_hash(q->name, q->len); |
94 | bucket = &(dlm->resources[q->hash & DLM_HASH_MASK]); | 94 | bucket = &(dlm->lockres_hash[q->hash % DLM_HASH_BUCKETS]); |
95 | 95 | ||
96 | /* get a reference for our hashtable */ | 96 | /* get a reference for our hashtable */ |
97 | dlm_lockres_get(res); | 97 | dlm_lockres_get(res); |
98 | 98 | ||
99 | list_add_tail(&res->list, bucket); | 99 | hlist_add_head(&res->hash_node, bucket); |
100 | } | 100 | } |
101 | 101 | ||
102 | struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm, | 102 | struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm, |
@@ -104,9 +104,9 @@ struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm, | |||
104 | unsigned int len) | 104 | unsigned int len) |
105 | { | 105 | { |
106 | unsigned int hash; | 106 | unsigned int hash; |
107 | struct list_head *iter; | 107 | struct hlist_node *iter; |
108 | struct dlm_lock_resource *tmpres=NULL; | 108 | struct dlm_lock_resource *tmpres=NULL; |
109 | struct list_head *bucket; | 109 | struct hlist_head *bucket; |
110 | 110 | ||
111 | mlog_entry("%.*s\n", len, name); | 111 | mlog_entry("%.*s\n", len, name); |
112 | 112 | ||
@@ -114,11 +114,11 @@ struct dlm_lock_resource * __dlm_lookup_lockres(struct dlm_ctxt *dlm, | |||
114 | 114 | ||
115 | hash = full_name_hash(name, len); | 115 | hash = full_name_hash(name, len); |
116 | 116 | ||
117 | bucket = &(dlm->resources[hash & DLM_HASH_MASK]); | 117 | bucket = &(dlm->lockres_hash[hash % DLM_HASH_BUCKETS]); |
118 | 118 | ||
119 | /* check for pre-existing lock */ | 119 | /* check for pre-existing lock */ |
120 | list_for_each(iter, bucket) { | 120 | hlist_for_each(iter, bucket) { |
121 | tmpres = list_entry(iter, struct dlm_lock_resource, list); | 121 | tmpres = hlist_entry(iter, struct dlm_lock_resource, hash_node); |
122 | if (tmpres->lockname.len == len && | 122 | if (tmpres->lockname.len == len && |
123 | memcmp(tmpres->lockname.name, name, len) == 0) { | 123 | memcmp(tmpres->lockname.name, name, len) == 0) { |
124 | dlm_lockres_get(tmpres); | 124 | dlm_lockres_get(tmpres); |
@@ -193,8 +193,8 @@ static int dlm_wait_on_domain_helper(const char *domain) | |||
193 | 193 | ||
194 | static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm) | 194 | static void dlm_free_ctxt_mem(struct dlm_ctxt *dlm) |
195 | { | 195 | { |
196 | if (dlm->resources) | 196 | if (dlm->lockres_hash) |
197 | free_page((unsigned long) dlm->resources); | 197 | free_page((unsigned long) dlm->lockres_hash); |
198 | 198 | ||
199 | if (dlm->name) | 199 | if (dlm->name) |
200 | kfree(dlm->name); | 200 | kfree(dlm->name); |
@@ -303,10 +303,10 @@ static void dlm_migrate_all_locks(struct dlm_ctxt *dlm) | |||
303 | mlog(0, "Migrating locks from domain %s\n", dlm->name); | 303 | mlog(0, "Migrating locks from domain %s\n", dlm->name); |
304 | restart: | 304 | restart: |
305 | spin_lock(&dlm->spinlock); | 305 | spin_lock(&dlm->spinlock); |
306 | for (i=0; i<DLM_HASH_SIZE; i++) { | 306 | for (i = 0; i < DLM_HASH_BUCKETS; i++) { |
307 | while (!list_empty(&dlm->resources[i])) { | 307 | while (!hlist_empty(&dlm->lockres_hash[i])) { |
308 | res = list_entry(dlm->resources[i].next, | 308 | res = hlist_entry(dlm->lockres_hash[i].first, |
309 | struct dlm_lock_resource, list); | 309 | struct dlm_lock_resource, hash_node); |
310 | /* need reference when manually grabbing lockres */ | 310 | /* need reference when manually grabbing lockres */ |
311 | dlm_lockres_get(res); | 311 | dlm_lockres_get(res); |
312 | /* this should unhash the lockres | 312 | /* this should unhash the lockres |
@@ -1191,18 +1191,17 @@ static struct dlm_ctxt *dlm_alloc_ctxt(const char *domain, | |||
1191 | goto leave; | 1191 | goto leave; |
1192 | } | 1192 | } |
1193 | 1193 | ||
1194 | dlm->resources = (struct list_head *) __get_free_page(GFP_KERNEL); | 1194 | dlm->lockres_hash = (struct hlist_head *) __get_free_page(GFP_KERNEL); |
1195 | if (!dlm->resources) { | 1195 | if (!dlm->lockres_hash) { |
1196 | mlog_errno(-ENOMEM); | 1196 | mlog_errno(-ENOMEM); |
1197 | kfree(dlm->name); | 1197 | kfree(dlm->name); |
1198 | kfree(dlm); | 1198 | kfree(dlm); |
1199 | dlm = NULL; | 1199 | dlm = NULL; |
1200 | goto leave; | 1200 | goto leave; |
1201 | } | 1201 | } |
1202 | memset(dlm->resources, 0, PAGE_SIZE); | ||
1203 | 1202 | ||
1204 | for (i=0; i<DLM_HASH_SIZE; i++) | 1203 | for (i=0; i<DLM_HASH_BUCKETS; i++) |
1205 | INIT_LIST_HEAD(&dlm->resources[i]); | 1204 | INIT_HLIST_HEAD(&dlm->lockres_hash[i]); |
1206 | 1205 | ||
1207 | strcpy(dlm->name, domain); | 1206 | strcpy(dlm->name, domain); |
1208 | dlm->key = key; | 1207 | dlm->key = key; |
diff --git a/fs/ocfs2/dlm/dlmmaster.c b/fs/ocfs2/dlm/dlmmaster.c index 2e2e95e69499..847dd3cc4cf5 100644 --- a/fs/ocfs2/dlm/dlmmaster.c +++ b/fs/ocfs2/dlm/dlmmaster.c | |||
@@ -564,7 +564,7 @@ static void dlm_lockres_release(struct kref *kref) | |||
564 | 564 | ||
565 | /* By the time we're ready to blow this guy away, we shouldn't | 565 | /* By the time we're ready to blow this guy away, we shouldn't |
566 | * be on any lists. */ | 566 | * be on any lists. */ |
567 | BUG_ON(!list_empty(&res->list)); | 567 | BUG_ON(!hlist_unhashed(&res->hash_node)); |
568 | BUG_ON(!list_empty(&res->granted)); | 568 | BUG_ON(!list_empty(&res->granted)); |
569 | BUG_ON(!list_empty(&res->converting)); | 569 | BUG_ON(!list_empty(&res->converting)); |
570 | BUG_ON(!list_empty(&res->blocked)); | 570 | BUG_ON(!list_empty(&res->blocked)); |
@@ -605,7 +605,7 @@ static void dlm_init_lockres(struct dlm_ctxt *dlm, | |||
605 | 605 | ||
606 | init_waitqueue_head(&res->wq); | 606 | init_waitqueue_head(&res->wq); |
607 | spin_lock_init(&res->spinlock); | 607 | spin_lock_init(&res->spinlock); |
608 | INIT_LIST_HEAD(&res->list); | 608 | INIT_HLIST_NODE(&res->hash_node); |
609 | INIT_LIST_HEAD(&res->granted); | 609 | INIT_LIST_HEAD(&res->granted); |
610 | INIT_LIST_HEAD(&res->converting); | 610 | INIT_LIST_HEAD(&res->converting); |
611 | INIT_LIST_HEAD(&res->blocked); | 611 | INIT_LIST_HEAD(&res->blocked); |
diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c index ed76bda1a534..1e232000f3f7 100644 --- a/fs/ocfs2/dlm/dlmrecovery.c +++ b/fs/ocfs2/dlm/dlmrecovery.c | |||
@@ -1693,7 +1693,10 @@ static void dlm_finish_local_lockres_recovery(struct dlm_ctxt *dlm, | |||
1693 | u8 dead_node, u8 new_master) | 1693 | u8 dead_node, u8 new_master) |
1694 | { | 1694 | { |
1695 | int i; | 1695 | int i; |
1696 | struct list_head *iter, *iter2, *bucket; | 1696 | struct list_head *iter, *iter2; |
1697 | struct hlist_node *hash_iter; | ||
1698 | struct hlist_head *bucket; | ||
1699 | |||
1697 | struct dlm_lock_resource *res; | 1700 | struct dlm_lock_resource *res; |
1698 | 1701 | ||
1699 | mlog_entry_void(); | 1702 | mlog_entry_void(); |
@@ -1717,10 +1720,9 @@ static void dlm_finish_local_lockres_recovery(struct dlm_ctxt *dlm, | |||
1717 | * for now we need to run the whole hash, clear | 1720 | * for now we need to run the whole hash, clear |
1718 | * the RECOVERING state and set the owner | 1721 | * the RECOVERING state and set the owner |
1719 | * if necessary */ | 1722 | * if necessary */ |
1720 | for (i=0; i<DLM_HASH_SIZE; i++) { | 1723 | for (i = 0; i < DLM_HASH_BUCKETS; i++) { |
1721 | bucket = &(dlm->resources[i]); | 1724 | bucket = &(dlm->lockres_hash[i]); |
1722 | list_for_each(iter, bucket) { | 1725 | hlist_for_each_entry(res, hash_iter, bucket, hash_node) { |
1723 | res = list_entry (iter, struct dlm_lock_resource, list); | ||
1724 | if (res->state & DLM_LOCK_RES_RECOVERING) { | 1726 | if (res->state & DLM_LOCK_RES_RECOVERING) { |
1725 | if (res->owner == dead_node) { | 1727 | if (res->owner == dead_node) { |
1726 | mlog(0, "(this=%u) res %.*s owner=%u " | 1728 | mlog(0, "(this=%u) res %.*s owner=%u " |
@@ -1852,10 +1854,10 @@ static void dlm_free_dead_locks(struct dlm_ctxt *dlm, | |||
1852 | 1854 | ||
1853 | static void dlm_do_local_recovery_cleanup(struct dlm_ctxt *dlm, u8 dead_node) | 1855 | static void dlm_do_local_recovery_cleanup(struct dlm_ctxt *dlm, u8 dead_node) |
1854 | { | 1856 | { |
1855 | struct list_head *iter; | 1857 | struct hlist_node *iter; |
1856 | struct dlm_lock_resource *res; | 1858 | struct dlm_lock_resource *res; |
1857 | int i; | 1859 | int i; |
1858 | struct list_head *bucket; | 1860 | struct hlist_head *bucket; |
1859 | struct dlm_lock *lock; | 1861 | struct dlm_lock *lock; |
1860 | 1862 | ||
1861 | 1863 | ||
@@ -1876,10 +1878,9 @@ static void dlm_do_local_recovery_cleanup(struct dlm_ctxt *dlm, u8 dead_node) | |||
1876 | * can be kicked again to see if any ASTs or BASTs | 1878 | * can be kicked again to see if any ASTs or BASTs |
1877 | * need to be fired as a result. | 1879 | * need to be fired as a result. |
1878 | */ | 1880 | */ |
1879 | for (i=0; i<DLM_HASH_SIZE; i++) { | 1881 | for (i = 0; i < DLM_HASH_BUCKETS; i++) { |
1880 | bucket = &(dlm->resources[i]); | 1882 | bucket = &(dlm->lockres_hash[i]); |
1881 | list_for_each(iter, bucket) { | 1883 | hlist_for_each_entry(res, iter, bucket, hash_node) { |
1882 | res = list_entry (iter, struct dlm_lock_resource, list); | ||
1883 | /* always prune any $RECOVERY entries for dead nodes, | 1884 | /* always prune any $RECOVERY entries for dead nodes, |
1884 | * otherwise hangs can occur during later recovery */ | 1885 | * otherwise hangs can occur during later recovery */ |
1885 | if (dlm_is_recovery_lock(res->lockname.name, | 1886 | if (dlm_is_recovery_lock(res->lockname.name, |