summaryrefslogtreecommitdiffstats
path: root/fs/ocfs2/dlm
diff options
context:
space:
mode:
authorJun Piao <piaojun@huawei.com>2018-04-05 19:18:48 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2018-04-06 00:36:22 -0400
commitbb34f24c7d2c98d0c81838a7700e6068325b17a0 (patch)
tree52dcf71dc487a0148329513907bb281c93daad55 /fs/ocfs2/dlm
parent1202d4ba2899e083417b7b4fb9b544942fd2b9b7 (diff)
ocfs2/dlm: don't handle migrate lockres if already in shutdown
We should not handle migrate lockres if we are already in 'DLM_CTXT_IN_SHUTDOWN', as that will cause lockres remains after leaving dlm domain. At last other nodes will get stuck into infinite loop when requsting lock from us. The problem is caused by concurrency umount between nodes. Before receiveing N1's DLM_BEGIN_EXIT_DOMAIN_MSG, N2 has picked up N1 as the migrate target. So N2 will continue sending lockres to N1 even though N1 has left domain. N1 N2 (owner) touch file access the file, and get pr lock begin leave domain and pick up N1 as new owner begin leave domain and migrate all lockres done begin migrate lockres to N1 end leave domain, but the lockres left unexpectedly, because migrate task has passed [piaojun@huawei.com: v3] Link: http://lkml.kernel.org/r/5A9CBD19.5020107@huawei.com Link: http://lkml.kernel.org/r/5A99F028.2090902@huawei.com Signed-off-by: Jun Piao <piaojun@huawei.com> Reviewed-by: Yiwen Jiang <jiangyiwen@huawei.com> Reviewed-by: Joseph Qi <jiangqi903@gmail.com> Reviewed-by: Changwei Ge <ge.changwei@h3c.com> Cc: Mark Fasheh <mark@fasheh.com> Cc: Joel Becker <jlbec@evilplan.org> Cc: Junxiao Bi <junxiao.bi@oracle.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'fs/ocfs2/dlm')
-rw-r--r--fs/ocfs2/dlm/dlmdomain.c14
-rw-r--r--fs/ocfs2/dlm/dlmdomain.h25
-rw-r--r--fs/ocfs2/dlm/dlmrecovery.c9
3 files changed, 33 insertions, 15 deletions
diff --git a/fs/ocfs2/dlm/dlmdomain.c b/fs/ocfs2/dlm/dlmdomain.c
index e1fea149f50b..25b76f0d082b 100644
--- a/fs/ocfs2/dlm/dlmdomain.c
+++ b/fs/ocfs2/dlm/dlmdomain.c
@@ -675,20 +675,6 @@ static void dlm_leave_domain(struct dlm_ctxt *dlm)
675 spin_unlock(&dlm->spinlock); 675 spin_unlock(&dlm->spinlock);
676} 676}
677 677
678int dlm_shutting_down(struct dlm_ctxt *dlm)
679{
680 int ret = 0;
681
682 spin_lock(&dlm_domain_lock);
683
684 if (dlm->dlm_state == DLM_CTXT_IN_SHUTDOWN)
685 ret = 1;
686
687 spin_unlock(&dlm_domain_lock);
688
689 return ret;
690}
691
692void dlm_unregister_domain(struct dlm_ctxt *dlm) 678void dlm_unregister_domain(struct dlm_ctxt *dlm)
693{ 679{
694 int leave = 0; 680 int leave = 0;
diff --git a/fs/ocfs2/dlm/dlmdomain.h b/fs/ocfs2/dlm/dlmdomain.h
index fd6122a38dbd..8a9281411c18 100644
--- a/fs/ocfs2/dlm/dlmdomain.h
+++ b/fs/ocfs2/dlm/dlmdomain.h
@@ -28,7 +28,30 @@
28extern spinlock_t dlm_domain_lock; 28extern spinlock_t dlm_domain_lock;
29extern struct list_head dlm_domains; 29extern struct list_head dlm_domains;
30 30
31int dlm_shutting_down(struct dlm_ctxt *dlm); 31static inline int dlm_joined(struct dlm_ctxt *dlm)
32{
33 int ret = 0;
34
35 spin_lock(&dlm_domain_lock);
36 if (dlm->dlm_state == DLM_CTXT_JOINED)
37 ret = 1;
38 spin_unlock(&dlm_domain_lock);
39
40 return ret;
41}
42
43static inline int dlm_shutting_down(struct dlm_ctxt *dlm)
44{
45 int ret = 0;
46
47 spin_lock(&dlm_domain_lock);
48 if (dlm->dlm_state == DLM_CTXT_IN_SHUTDOWN)
49 ret = 1;
50 spin_unlock(&dlm_domain_lock);
51
52 return ret;
53}
54
32void dlm_fire_domain_eviction_callbacks(struct dlm_ctxt *dlm, 55void dlm_fire_domain_eviction_callbacks(struct dlm_ctxt *dlm,
33 int node_num); 56 int node_num);
34 57
diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c
index ec8f75813beb..505ab4281f36 100644
--- a/fs/ocfs2/dlm/dlmrecovery.c
+++ b/fs/ocfs2/dlm/dlmrecovery.c
@@ -1378,6 +1378,15 @@ int dlm_mig_lockres_handler(struct o2net_msg *msg, u32 len, void *data,
1378 if (!dlm_grab(dlm)) 1378 if (!dlm_grab(dlm))
1379 return -EINVAL; 1379 return -EINVAL;
1380 1380
1381 if (!dlm_joined(dlm)) {
1382 mlog(ML_ERROR, "Domain %s not joined! "
1383 "lockres %.*s, master %u\n",
1384 dlm->name, mres->lockname_len,
1385 mres->lockname, mres->master);
1386 dlm_put(dlm);
1387 return -EINVAL;
1388 }
1389
1381 BUG_ON(!(mres->flags & (DLM_MRES_RECOVERY|DLM_MRES_MIGRATION))); 1390 BUG_ON(!(mres->flags & (DLM_MRES_RECOVERY|DLM_MRES_MIGRATION)));
1382 1391
1383 real_master = mres->master; 1392 real_master = mres->master;