Whamcloud - gitweb
LU-7535 mdt: clear the lock handle in mdt_intent_layout() 35/17735/4
authorJohn L. Hammond <john.hammond@intel.com>
Wed, 30 Dec 2015 17:21:27 +0000 (11:21 -0600)
committerOleg Drokin <oleg.drokin@intel.com>
Wed, 6 Jan 2016 01:24:47 +0000 (01:24 +0000)
In mdt_intent_layout() if the object cannot be found then clear the
lock handle. In recover-small add test_130c() to check that this is
handled condition is handled safely.

In recovery-small test_130[ab]() add a synt to avoid having an
unintended layout intent RPC (from writeback) hit the fault injection
point.

Signed-off-by: John L. Hammond <john.hammond@intel.com>
Change-Id: Ic2f401ff2dc8a83467b12d146f4d7ffdf70ef5da
Reviewed-on: http://review.whamcloud.com/17735
Tested-by: Jenkins
Tested-by: Maloo <hpdd-maloo@intel.com>
Reviewed-by: Alex Zhuravlev <alexey.zhuravlev@intel.com>
Reviewed-by: Jinshan Xiong <jinshan.xiong@intel.com>
Reviewed-by: Oleg Drokin <oleg.drokin@intel.com>
lustre/mdt/mdt_handler.c
lustre/tests/recovery-small.sh

index 9c0c406..4be1e72 100644 (file)
@@ -3172,6 +3172,7 @@ static int mdt_intent_layout(enum mdt_it_code opcode,
        struct layout_intent *layout;
        struct lu_fid *fid;
        struct mdt_object *obj = NULL;
+       int layout_size = 0;
        int rc = 0;
        ENTRY;
 
@@ -3181,6 +3182,16 @@ static int mdt_intent_layout(enum mdt_it_code opcode,
                RETURN(-EINVAL);
        }
 
+       layout = req_capsule_client_get(info->mti_pill, &RMF_LAYOUT_INTENT);
+       if (layout == NULL)
+               RETURN(-EPROTO);
+
+       if (layout->li_opc != LAYOUT_INTENT_ACCESS) {
+               CERROR("%s: Unsupported layout intent opc %d\n",
+                      mdt_obd_name(info->mti_mdt), layout->li_opc);
+               RETURN(-EINVAL);
+       }
+
        fid = &info->mti_tmp_fid2;
        fid_extract_from_res_name(fid, &(*lockp)->l_resource->lr_name);
 
@@ -3189,40 +3200,33 @@ static int mdt_intent_layout(enum mdt_it_code opcode,
 
        obj = mdt_object_find(info->mti_env, info->mti_mdt, fid);
        if (IS_ERR(obj))
-               RETURN(PTR_ERR(obj));
+               GOTO(out, rc = PTR_ERR(obj));
 
        if (mdt_object_exists(obj) && !mdt_object_remote(obj)) {
-               /* get the length of lsm */
-               rc = mdt_attr_get_eabuf_size(info, obj);
-               if (rc < 0) {
-                       mdt_object_put(info->mti_env, obj);
-                       RETURN(rc);
-               }
+               layout_size = mdt_attr_get_eabuf_size(info, obj);
+               if (layout_size < 0)
+                       GOTO(out_obj, rc = layout_size);
 
-               if (rc > info->mti_mdt->mdt_max_mdsize)
-                       info->mti_mdt->mdt_max_mdsize = rc;
+               if (layout_size > info->mti_mdt->mdt_max_mdsize)
+                       info->mti_mdt->mdt_max_mdsize = layout_size;
        }
 
-       mdt_object_put(info->mti_env, obj);
-
        (*lockp)->l_lvb_type = LVB_T_LAYOUT;
-       req_capsule_set_size(info->mti_pill, &RMF_DLM_LVB, RCL_SERVER, rc);
+       req_capsule_set_size(info->mti_pill, &RMF_DLM_LVB, RCL_SERVER,
+                            layout_size);
        rc = req_capsule_server_pack(info->mti_pill);
-       if (rc != 0)
-               RETURN(-EINVAL);
+       GOTO(out_obj, rc);
+
+out_obj:
+       mdt_object_put(info->mti_env, obj);
 
-       if (lustre_handle_is_used(&lhc->mlh_reg_lh))
+       if (rc == 0 && lustre_handle_is_used(&lhc->mlh_reg_lh))
                rc = mdt_intent_lock_replace(info, lockp, lhc, flags);
 
-       layout = req_capsule_client_get(info->mti_pill, &RMF_LAYOUT_INTENT);
-       LASSERT(layout != NULL);
-       if (layout->li_opc == LAYOUT_INTENT_ACCESS)
-               /* return to normal/resent ldlm handling */
-               RETURN(rc);
+out:
+       lhc->mlh_reg_lh.cookie = 0;
 
-       CERROR("%s: Unsupported layout intent (%d)\n",
-               mdt_obd_name(info->mti_mdt), layout->li_opc);
-       RETURN(-EINVAL);
+       return rc;
 }
 
 static int mdt_intent_reint(enum mdt_it_code opcode,
index 976ecf6..51f5e1f 100755 (executable)
@@ -2256,6 +2256,10 @@ T130_PID=0
 test_130_base() {
        test_mkdir -p $DIR/$tdir
 
+       # Prevent interference from layout intent RPCs due to
+       # asynchronous writeback. These will be tested in 130c below.
+       sync
+
        # get only LOOKUP lock on $tdir
        cancel_lru_locks mdc
        ls $DIR/$tdir/$tfile 2>/dev/null
@@ -2302,6 +2306,44 @@ test_130b() {
 }
 run_test 130b "enqueue resend on a stale inode"
 
+test_130c() {
+       remote_mds_nodsh && skip "remote MDS with nodsh" && return
+
+       sync
+       echo XXX > $DIR/$tfile
+
+       cancel_lru_locks mdc
+
+       # Trigger writeback on $tfile.
+       #
+       # we need to race with unlink, unlink must complete before we will
+       # take a DLM lock, otherwise unlink will wait until intent will
+       # complete; but later than intent starts so that intent found
+       # the object
+#define OBD_FAIL_MDS_INTENT_DELAY              0x160
+       set_nodes_failloc "$(mdts_nodes)" 0x80000160
+       sync &
+       T130_PID=$!
+       sleep 2
+
+       rm $DIR/$tfile
+
+       # drop the reply so that resend happens on an unlinked file.
+#define OBD_FAIL_MDS_LDLM_REPLY_NET     0x157
+       set_nodes_failloc "$(mdts_nodes)" 0x80000157
+
+       # let the reply to be dropped
+       sleep 10
+
+#define OBD_FAIL_SRV_ENOENT              0x217
+       set_nodes_failloc "$(mdts_nodes)" 0x80000217
+
+       wait $T130_PID
+
+       return 0
+}
+run_test 130c "layout intent resend on a stale inode"
+
 complete $SECONDS
 check_and_cleanup_lustre
 exit_status