]> Pileus Git - ~andy/linux/blobdiff - fs/dlm/recoverd.c
vxlan: fix nonfunctional neigh_reduce()
[~andy/linux] / fs / dlm / recoverd.c
index 88ce65ff021ed35848b30ae129e9334930413cc3..32f9f8926ec3f17a3a69433402e8a0fecb07a1f6 100644 (file)
@@ -41,6 +41,7 @@ static int enable_locking(struct dlm_ls *ls, uint64_t seq)
                set_bit(LSFL_RUNNING, &ls->ls_flags);
                /* unblocks processes waiting to enter the dlm */
                up_write(&ls->ls_in_recovery);
+               clear_bit(LSFL_RECOVER_LOCK, &ls->ls_flags);
                error = 0;
        }
        spin_unlock(&ls->ls_recover_lock);
@@ -262,7 +263,7 @@ static void do_ls_recovery(struct dlm_ls *ls)
        rv = ls->ls_recover_args;
        ls->ls_recover_args = NULL;
        if (rv && ls->ls_recover_seq == rv->seq)
-               clear_bit(LSFL_RECOVERY_STOP, &ls->ls_flags);
+               clear_bit(LSFL_RECOVER_STOP, &ls->ls_flags);
        spin_unlock(&ls->ls_recover_lock);
 
        if (rv) {
@@ -282,26 +283,34 @@ static int dlm_recoverd(void *arg)
                return -1;
        }
 
+       down_write(&ls->ls_in_recovery);
+       set_bit(LSFL_RECOVER_LOCK, &ls->ls_flags);
+       wake_up(&ls->ls_recover_lock_wait);
+
        while (!kthread_should_stop()) {
                set_current_state(TASK_INTERRUPTIBLE);
-               if (!test_bit(LSFL_WORK, &ls->ls_flags))
+               if (!test_bit(LSFL_RECOVER_WORK, &ls->ls_flags) &&
+                   !test_bit(LSFL_RECOVER_DOWN, &ls->ls_flags))
                        schedule();
                set_current_state(TASK_RUNNING);
 
-               if (test_and_clear_bit(LSFL_WORK, &ls->ls_flags))
+               if (test_and_clear_bit(LSFL_RECOVER_DOWN, &ls->ls_flags)) {
+                       down_write(&ls->ls_in_recovery);
+                       set_bit(LSFL_RECOVER_LOCK, &ls->ls_flags);
+                       wake_up(&ls->ls_recover_lock_wait);
+               }
+
+               if (test_and_clear_bit(LSFL_RECOVER_WORK, &ls->ls_flags))
                        do_ls_recovery(ls);
        }
 
+       if (test_bit(LSFL_RECOVER_LOCK, &ls->ls_flags))
+               up_write(&ls->ls_in_recovery);
+
        dlm_put_lockspace(ls);
        return 0;
 }
 
-void dlm_recoverd_kick(struct dlm_ls *ls)
-{
-       set_bit(LSFL_WORK, &ls->ls_flags);
-       wake_up_process(ls->ls_recoverd_task);
-}
-
 int dlm_recoverd_start(struct dlm_ls *ls)
 {
        struct task_struct *p;