diff options
author | Joel Becker <joel.becker@oracle.com> | 2008-02-01 17:39:35 -0500 |
---|---|---|
committer | Mark Fasheh <mfasheh@suse.com> | 2008-04-18 11:56:04 -0400 |
commit | 4670c46ded9a18268d1265417ff4ac72145a7917 (patch) | |
tree | 4f70822ddee389a9c8ed572b215a3355c20db3a1 /fs/ocfs2/dlmglue.c | |
parent | 8f2c9c1b16bf6ed0903b29c49d56fa0109a390e4 (diff) |
ocfs2: Introduce the new ocfs2_cluster_connect/disconnect() API.
This step introduces a cluster stack agnostic API for initializing and
exiting. fs/ocfs2/dlmglue.c no longer uses o2cb/o2dlm knowledge to
connect to the stack. It is all handled in stackglue.c.
heartbeat.c no longer needs to know how it gets called.
ocfs2_do_node_down() is now a clean recovery trigger.
The big gotcha is the ordering of initializations and de-initializations done
underneath ocfs2_cluster_connect(). ocfs2_dlm_init() used to do all
o2dlm initialization in one block. Thus, the o2dlm functionality of
ocfs2_cluster_connect() is very straightforward. ocfs2_dlm_shutdown(),
however, did a few things between de-registration of the eviction
callback and actually shutting down the domain. Now de-registration and
shutdown of the domain are wrapped within the single
ocfs2_cluster_disconnect() call. I've checked the code paths to make
sure we can safely tear down things in ocfs2_dlm_shutdown() before
calling ocfs2_cluster_disconnect(). The filesystem has already set
itself to ignore the callback.
Signed-off-by: Joel Becker <joel.becker@oracle.com>
Signed-off-by: Mark Fasheh <mfasheh@suse.com>
Diffstat (limited to 'fs/ocfs2/dlmglue.c')
-rw-r--r-- | fs/ocfs2/dlmglue.c | 97 |
1 files changed, 48 insertions, 49 deletions
diff --git a/fs/ocfs2/dlmglue.c b/fs/ocfs2/dlmglue.c index 459037653e5a..6652a48cbe0f 100644 --- a/fs/ocfs2/dlmglue.c +++ b/fs/ocfs2/dlmglue.c | |||
@@ -27,7 +27,6 @@ | |||
27 | #include <linux/slab.h> | 27 | #include <linux/slab.h> |
28 | #include <linux/highmem.h> | 28 | #include <linux/highmem.h> |
29 | #include <linux/mm.h> | 29 | #include <linux/mm.h> |
30 | #include <linux/crc32.h> | ||
31 | #include <linux/kthread.h> | 30 | #include <linux/kthread.h> |
32 | #include <linux/pagemap.h> | 31 | #include <linux/pagemap.h> |
33 | #include <linux/debugfs.h> | 32 | #include <linux/debugfs.h> |
@@ -259,31 +258,6 @@ static struct ocfs2_lock_res_ops ocfs2_flock_lops = { | |||
259 | .flags = 0, | 258 | .flags = 0, |
260 | }; | 259 | }; |
261 | 260 | ||
262 | /* | ||
263 | * This is the filesystem locking protocol version. | ||
264 | * | ||
265 | * Whenever the filesystem does new things with locks (adds or removes a | ||
266 | * lock, orders them differently, does different things underneath a lock), | ||
267 | * the version must be changed. The protocol is negotiated when joining | ||
268 | * the dlm domain. A node may join the domain if its major version is | ||
269 | * identical to all other nodes and its minor version is greater than | ||
270 | * or equal to all other nodes. When its minor version is greater than | ||
271 | * the other nodes, it will run at the minor version specified by the | ||
272 | * other nodes. | ||
273 | * | ||
274 | * If a locking change is made that will not be compatible with older | ||
275 | * versions, the major number must be increased and the minor version set | ||
276 | * to zero. If a change merely adds a behavior that can be disabled when | ||
277 | * speaking to older versions, the minor version must be increased. If a | ||
278 | * change adds a fully backwards compatible change (eg, LVB changes that | ||
279 | * are just ignored by older versions), the version does not need to be | ||
280 | * updated. | ||
281 | */ | ||
282 | const struct dlm_protocol_version ocfs2_locking_protocol = { | ||
283 | .pv_major = OCFS2_LOCKING_PROTOCOL_MAJOR, | ||
284 | .pv_minor = OCFS2_LOCKING_PROTOCOL_MINOR, | ||
285 | }; | ||
286 | |||
287 | static inline int ocfs2_is_inode_lock(struct ocfs2_lock_res *lockres) | 261 | static inline int ocfs2_is_inode_lock(struct ocfs2_lock_res *lockres) |
288 | { | 262 | { |
289 | return lockres->l_type == OCFS2_LOCK_TYPE_META || | 263 | return lockres->l_type == OCFS2_LOCK_TYPE_META || |
@@ -886,7 +860,7 @@ static int ocfs2_lock_create(struct ocfs2_super *osb, | |||
886 | lockres_or_flags(lockres, OCFS2_LOCK_BUSY); | 860 | lockres_or_flags(lockres, OCFS2_LOCK_BUSY); |
887 | spin_unlock_irqrestore(&lockres->l_lock, flags); | 861 | spin_unlock_irqrestore(&lockres->l_lock, flags); |
888 | 862 | ||
889 | ret = ocfs2_dlm_lock(osb->dlm, | 863 | ret = ocfs2_dlm_lock(osb->cconn, |
890 | level, | 864 | level, |
891 | &lockres->l_lksb, | 865 | &lockres->l_lksb, |
892 | dlm_flags, | 866 | dlm_flags, |
@@ -1085,7 +1059,7 @@ again: | |||
1085 | lockres->l_name, lockres->l_level, level); | 1059 | lockres->l_name, lockres->l_level, level); |
1086 | 1060 | ||
1087 | /* call dlm_lock to upgrade lock now */ | 1061 | /* call dlm_lock to upgrade lock now */ |
1088 | ret = ocfs2_dlm_lock(osb->dlm, | 1062 | ret = ocfs2_dlm_lock(osb->cconn, |
1089 | level, | 1063 | level, |
1090 | &lockres->l_lksb, | 1064 | &lockres->l_lksb, |
1091 | lkm_flags, | 1065 | lkm_flags, |
@@ -1492,7 +1466,7 @@ int ocfs2_file_lock(struct file *file, int ex, int trylock) | |||
1492 | lockres_add_mask_waiter(lockres, &mw, OCFS2_LOCK_BUSY, 0); | 1466 | lockres_add_mask_waiter(lockres, &mw, OCFS2_LOCK_BUSY, 0); |
1493 | spin_unlock_irqrestore(&lockres->l_lock, flags); | 1467 | spin_unlock_irqrestore(&lockres->l_lock, flags); |
1494 | 1468 | ||
1495 | ret = ocfs2_dlm_lock(osb->dlm, level, &lockres->l_lksb, lkm_flags, | 1469 | ret = ocfs2_dlm_lock(osb->cconn, level, &lockres->l_lksb, lkm_flags, |
1496 | lockres->l_name, OCFS2_LOCK_ID_MAX_LEN - 1, | 1470 | lockres->l_name, OCFS2_LOCK_ID_MAX_LEN - 1, |
1497 | lockres); | 1471 | lockres); |
1498 | if (ret) { | 1472 | if (ret) { |
@@ -2485,8 +2459,7 @@ static void ocfs2_dlm_shutdown_debug(struct ocfs2_super *osb) | |||
2485 | int ocfs2_dlm_init(struct ocfs2_super *osb) | 2459 | int ocfs2_dlm_init(struct ocfs2_super *osb) |
2486 | { | 2460 | { |
2487 | int status = 0; | 2461 | int status = 0; |
2488 | u32 dlm_key; | 2462 | struct ocfs2_cluster_connection *conn = NULL; |
2489 | struct dlm_ctxt *dlm = NULL; | ||
2490 | 2463 | ||
2491 | mlog_entry_void(); | 2464 | mlog_entry_void(); |
2492 | 2465 | ||
@@ -2508,26 +2481,21 @@ int ocfs2_dlm_init(struct ocfs2_super *osb) | |||
2508 | goto bail; | 2481 | goto bail; |
2509 | } | 2482 | } |
2510 | 2483 | ||
2511 | /* used by the dlm code to make message headers unique, each | ||
2512 | * node in this domain must agree on this. */ | ||
2513 | dlm_key = crc32_le(0, osb->uuid_str, strlen(osb->uuid_str)); | ||
2514 | |||
2515 | /* for now, uuid == domain */ | 2484 | /* for now, uuid == domain */ |
2516 | dlm = dlm_register_domain(osb->uuid_str, dlm_key, | 2485 | status = ocfs2_cluster_connect(osb->uuid_str, |
2517 | &osb->osb_locking_proto); | 2486 | strlen(osb->uuid_str), |
2518 | if (IS_ERR(dlm)) { | 2487 | ocfs2_do_node_down, osb, |
2519 | status = PTR_ERR(dlm); | 2488 | &conn); |
2489 | if (status) { | ||
2520 | mlog_errno(status); | 2490 | mlog_errno(status); |
2521 | goto bail; | 2491 | goto bail; |
2522 | } | 2492 | } |
2523 | 2493 | ||
2524 | dlm_register_eviction_cb(dlm, &osb->osb_eviction_cb); | ||
2525 | |||
2526 | local: | 2494 | local: |
2527 | ocfs2_super_lock_res_init(&osb->osb_super_lockres, osb); | 2495 | ocfs2_super_lock_res_init(&osb->osb_super_lockres, osb); |
2528 | ocfs2_rename_lock_res_init(&osb->osb_rename_lockres, osb); | 2496 | ocfs2_rename_lock_res_init(&osb->osb_rename_lockres, osb); |
2529 | 2497 | ||
2530 | osb->dlm = dlm; | 2498 | osb->cconn = conn; |
2531 | 2499 | ||
2532 | status = 0; | 2500 | status = 0; |
2533 | bail: | 2501 | bail: |
@@ -2545,10 +2513,14 @@ void ocfs2_dlm_shutdown(struct ocfs2_super *osb) | |||
2545 | { | 2513 | { |
2546 | mlog_entry_void(); | 2514 | mlog_entry_void(); |
2547 | 2515 | ||
2548 | dlm_unregister_eviction_cb(&osb->osb_eviction_cb); | ||
2549 | |||
2550 | ocfs2_drop_osb_locks(osb); | 2516 | ocfs2_drop_osb_locks(osb); |
2551 | 2517 | ||
2518 | /* | ||
2519 | * Now that we have dropped all locks and ocfs2_dismount_volume() | ||
2520 | * has disabled recovery, the DLM won't be talking to us. It's | ||
2521 | * safe to tear things down before disconnecting the cluster. | ||
2522 | */ | ||
2523 | |||
2552 | if (osb->dc_task) { | 2524 | if (osb->dc_task) { |
2553 | kthread_stop(osb->dc_task); | 2525 | kthread_stop(osb->dc_task); |
2554 | osb->dc_task = NULL; | 2526 | osb->dc_task = NULL; |
@@ -2557,8 +2529,8 @@ void ocfs2_dlm_shutdown(struct ocfs2_super *osb) | |||
2557 | ocfs2_lock_res_free(&osb->osb_super_lockres); | 2529 | ocfs2_lock_res_free(&osb->osb_super_lockres); |
2558 | ocfs2_lock_res_free(&osb->osb_rename_lockres); | 2530 | ocfs2_lock_res_free(&osb->osb_rename_lockres); |
2559 | 2531 | ||
2560 | dlm_unregister_domain(osb->dlm); | 2532 | ocfs2_cluster_disconnect(osb->cconn); |
2561 | osb->dlm = NULL; | 2533 | osb->cconn = NULL; |
2562 | 2534 | ||
2563 | ocfs2_dlm_shutdown_debug(osb); | 2535 | ocfs2_dlm_shutdown_debug(osb); |
2564 | 2536 | ||
@@ -2689,7 +2661,7 @@ static int ocfs2_drop_lock(struct ocfs2_super *osb, | |||
2689 | 2661 | ||
2690 | mlog(0, "lock %s\n", lockres->l_name); | 2662 | mlog(0, "lock %s\n", lockres->l_name); |
2691 | 2663 | ||
2692 | ret = ocfs2_dlm_unlock(osb->dlm, &lockres->l_lksb, lkm_flags, | 2664 | ret = ocfs2_dlm_unlock(osb->cconn, &lockres->l_lksb, lkm_flags, |
2693 | lockres); | 2665 | lockres); |
2694 | if (ret) { | 2666 | if (ret) { |
2695 | ocfs2_log_dlm_error("ocfs2_dlm_unlock", ret, lockres); | 2667 | ocfs2_log_dlm_error("ocfs2_dlm_unlock", ret, lockres); |
@@ -2823,7 +2795,7 @@ static int ocfs2_downconvert_lock(struct ocfs2_super *osb, | |||
2823 | if (lvb) | 2795 | if (lvb) |
2824 | dlm_flags |= DLM_LKF_VALBLK; | 2796 | dlm_flags |= DLM_LKF_VALBLK; |
2825 | 2797 | ||
2826 | ret = ocfs2_dlm_lock(osb->dlm, | 2798 | ret = ocfs2_dlm_lock(osb->cconn, |
2827 | new_level, | 2799 | new_level, |
2828 | &lockres->l_lksb, | 2800 | &lockres->l_lksb, |
2829 | dlm_flags, | 2801 | dlm_flags, |
@@ -2882,7 +2854,7 @@ static int ocfs2_cancel_convert(struct ocfs2_super *osb, | |||
2882 | mlog_entry_void(); | 2854 | mlog_entry_void(); |
2883 | mlog(0, "lock %s\n", lockres->l_name); | 2855 | mlog(0, "lock %s\n", lockres->l_name); |
2884 | 2856 | ||
2885 | ret = ocfs2_dlm_unlock(osb->dlm, &lockres->l_lksb, | 2857 | ret = ocfs2_dlm_unlock(osb->cconn, &lockres->l_lksb, |
2886 | DLM_LKF_CANCEL, lockres); | 2858 | DLM_LKF_CANCEL, lockres); |
2887 | if (ret) { | 2859 | if (ret) { |
2888 | ocfs2_log_dlm_error("ocfs2_dlm_unlock", ret, lockres); | 2860 | ocfs2_log_dlm_error("ocfs2_dlm_unlock", ret, lockres); |
@@ -3193,7 +3165,34 @@ static int ocfs2_dentry_convert_worker(struct ocfs2_lock_res *lockres, | |||
3193 | return UNBLOCK_CONTINUE_POST; | 3165 | return UNBLOCK_CONTINUE_POST; |
3194 | } | 3166 | } |
3195 | 3167 | ||
3168 | /* | ||
3169 | * This is the filesystem locking protocol. It provides the lock handling | ||
3170 | * hooks for the underlying DLM. It has a maximum version number. | ||
3171 | * The version number allows interoperability with systems running at | ||
3172 | * the same major number and an equal or smaller minor number. | ||
3173 | * | ||
3174 | * Whenever the filesystem does new things with locks (adds or removes a | ||
3175 | * lock, orders them differently, does different things underneath a lock), | ||
3176 | * the version must be changed. The protocol is negotiated when joining | ||
3177 | * the dlm domain. A node may join the domain if its major version is | ||
3178 | * identical to all other nodes and its minor version is greater than | ||
3179 | * or equal to all other nodes. When its minor version is greater than | ||
3180 | * the other nodes, it will run at the minor version specified by the | ||
3181 | * other nodes. | ||
3182 | * | ||
3183 | * If a locking change is made that will not be compatible with older | ||
3184 | * versions, the major number must be increased and the minor version set | ||
3185 | * to zero. If a change merely adds a behavior that can be disabled when | ||
3186 | * speaking to older versions, the minor version must be increased. If a | ||
3187 | * change adds a fully backwards compatible change (eg, LVB changes that | ||
3188 | * are just ignored by older versions), the version does not need to be | ||
3189 | * updated. | ||
3190 | */ | ||
3196 | static struct ocfs2_locking_protocol lproto = { | 3191 | static struct ocfs2_locking_protocol lproto = { |
3192 | .lp_max_version = { | ||
3193 | .pv_major = OCFS2_LOCKING_PROTOCOL_MAJOR, | ||
3194 | .pv_minor = OCFS2_LOCKING_PROTOCOL_MINOR, | ||
3195 | }, | ||
3197 | .lp_lock_ast = ocfs2_locking_ast, | 3196 | .lp_lock_ast = ocfs2_locking_ast, |
3198 | .lp_blocking_ast = ocfs2_blocking_ast, | 3197 | .lp_blocking_ast = ocfs2_blocking_ast, |
3199 | .lp_unlock_ast = ocfs2_unlock_ast, | 3198 | .lp_unlock_ast = ocfs2_unlock_ast, |