Whamcloud - gitweb
LU-5530 mdt: Properly match open lock and unlock 41/11841/2
authorOleg Drokin <oleg.drokin@intel.com>
Wed, 10 Sep 2014 01:38:35 +0000 (21:38 -0400)
committerOleg Drokin <oleg.drokin@intel.com>
Sat, 11 Oct 2014 03:56:46 +0000 (03:56 +0000)
It seems that when request resend with a corresponding lock match is
in play (thanks to large striping + llnl patch for the client to send
small requests only), after all the suffering and fixing coming from
LU-2827, here is another casualty in in open/lease locking.
mdt_reint_open() and mdt_open_by_fid_lock() might match the lock
on resend and not call mdt_object_open_lock(), yet call
mdt_object_open_unlock() before exit.
Since mdt_object_open_lock/unlock also plays with a semaphore,
hilarity ensues usually most visible as a rw_sem lockup
in mdt_object_open_lock.

This patch adds tracking whenever we actually called mdt_object_open_lock
or not and only calls mdt_object_open_unlock if we did.

Change-Id: I73c529229acec98cac4ad73f7b487e759ad9a763
Signed-off-by: Oleg Drokin <oleg.drokin@intel.com>
Reviewed-on: http://review.whamcloud.com/11841
Tested-by: Jenkins
Reviewed-by: Jinshan Xiong <jinshan.xiong@intel.com>
Tested-by: Maloo <hpdd-maloo@intel.com>
Reviewed-by: James Simmons <uja.ornl@gmail.com>
Reviewed-by: Faccini Bruno <bruno.faccini@intel.com>
lustre/mdt/mdt_open.c

index 50a8e61..4aacc8c 100644 (file)
@@ -1440,6 +1440,7 @@ int mdt_open_by_fid_lock(struct mdt_thread_info *info, struct ldlm_reply *rep,
         struct mdt_object       *parent= NULL;
         struct mdt_object       *o;
         int                      rc;
+       int                      object_locked = 0;
        __u64                    ibits = 0;
         ENTRY;
 
@@ -1494,6 +1495,7 @@ int mdt_open_by_fid_lock(struct mdt_thread_info *info, struct ldlm_reply *rep,
                GOTO(out, rc);
        } else if (rc > 0) {
                rc = mdt_object_open_lock(info, o, lhc, &ibits);
+               object_locked = 1;
                if (rc)
                        GOTO(out_unlock, rc);
        }
@@ -1520,7 +1522,8 @@ int mdt_open_by_fid_lock(struct mdt_thread_info *info, struct ldlm_reply *rep,
        GOTO(out_unlock, rc);
 
 out_unlock:
-       mdt_object_open_unlock(info, o, lhc, ibits, rc);
+       if (object_locked)
+               mdt_object_open_unlock(info, o, lhc, ibits, rc);
 out:
        mdt_object_put(env, o);
 out_parent_put:
@@ -1599,6 +1602,7 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc)
         struct mdt_reint_record *rr = &info->mti_rr;
         int                      result, rc;
         int                      created = 0;
+       int                      object_locked = 0;
         __u32                    msg_flags;
         ENTRY;
 
@@ -1849,6 +1853,7 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc)
                /* get openlock if this isn't replay and client requested it */
                if (!req_is_replay(req)) {
                        rc = mdt_object_open_lock(info, child, lhc, &ibits);
+                       object_locked = 1;
                        if (rc != 0)
                                GOTO(out_child_unlock, result = rc);
                        else if (create_flags & MDS_OPEN_LOCK)
@@ -1889,7 +1894,8 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc)
        }
        EXIT;
 out_child_unlock:
-       mdt_object_open_unlock(info, child, lhc, ibits, result);
+       if (object_locked)
+               mdt_object_open_unlock(info, child, lhc, ibits, result);
 out_child:
        mdt_object_put(info->mti_env, child);
 out_parent: