CERROR("%s: migrate %s , but fid "DFID" is insane\n",
ll_get_fsname(parent->i_sb, NULL, 0), name,
PFID(&op_data->op_fid3));
- GOTO(out_free, rc = -EINVAL);
+ GOTO(out_unlock, rc = -EINVAL);
}
rc = ll_get_mdt_idx_by_fid(ll_i2sbi(parent), &op_data->op_fid3);
if (rc < 0)
- GOTO(out_free, rc);
+ GOTO(out_unlock, rc);
if (rc == mdtidx) {
CDEBUG(D_INFO, "%s:"DFID" is already on MDT%d.\n", name,
PFID(&op_data->op_fid3), mdtidx);
- GOTO(out_free, rc = 0);
+ GOTO(out_unlock, rc = 0);
}
again:
if (S_ISREG(child_inode->i_mode)) {
if (IS_ERR(och)) {
rc = PTR_ERR(och);
och = NULL;
- GOTO(out_free, rc);
+ GOTO(out_unlock, rc);
}
rc = ll_data_version(child_inode, &data_version,
LL_DV_WR_FLUSH);
if (rc != 0)
- GOTO(out_free, rc);
+ GOTO(out_close, rc);
op_data->op_handle = och->och_fh;
op_data->op_data = och->och_mod;
body = req_capsule_server_get(&request->rq_pill, &RMF_MDT_BODY);
if (body == NULL) {
ptlrpc_req_finished(request);
- GOTO(out_free, rc = -EPROTO);
+ GOTO(out_close, rc = -EPROTO);
}
/* If the server does release layout lock, then we cleanup
- * the client och here, otherwise release it in out_free: */
+ * the client och here, otherwise release it in out_close: */
if (och != NULL &&
body->mbo_valid & OBD_MD_CLOSE_INTENT_EXECED) {
obd_mod_put(och->och_mod);
request = NULL;
goto again;
}
-out_free:
- if (child_inode != NULL) {
- if (och != NULL) /* close the file */
- ll_lease_close(och, child_inode, NULL);
+out_close:
+ if (och != NULL) /* close the file */
+ ll_lease_close(och, child_inode, NULL);
+ if (rc == 0)
clear_nlink(child_inode);
- mutex_unlock(&child_inode->i_mutex);
- iput(child_inode);
- }
-
+out_unlock:
+ mutex_unlock(&child_inode->i_mutex);
+ iput(child_inode);
+out_free:
ll_finish_md_op_data(op_data);
RETURN(rc);
}
int mdd_links_write(const struct lu_env *env, struct mdd_object *mdd_obj,
struct linkea_data *ldata, struct thandle *handle)
{
- const struct lu_buf *buf = mdd_buf_get_const(env, ldata->ld_buf->lb_buf,
- ldata->ld_leh->leh_len);
+ const struct lu_buf *buf;
int rc;
+ if (ldata == NULL || ldata->ld_buf == NULL ||
+ ldata->ld_leh == NULL)
+ return 0;
+
+ buf = mdd_buf_get_const(env, ldata->ld_buf->lb_buf,
+ ldata->ld_leh->leh_len);
if (OBD_FAIL_CHECK(OBD_FAIL_LFSCK_NO_LINKEA))
return 0;
ENTRY;
/* EEXIST check */
- if (mdd_is_dead_obj(obj))
+ if (mdd_is_dead_obj(obj) ||
+ pattr->la_flags & LUSTRE_SLAVE_DEAD_FL)
RETURN(-ENOENT);
/*
buf, 0, handle);
if (rc != 0)
return rc;
- } else if (S_ISDIR(la->la_mode)) {
+ } else if (S_ISDIR(la->la_mode) && ldata != NULL) {
rc = mdd_declare_links_add(env, mdd_tobj, handle, ldata,
MLAO_IGNORE);
if (rc != 0)
}
} else if (S_ISDIR(la->la_mode)) {
rc = mdd_links_read(env, mdd_sobj, ldata);
- if (rc < 0 && rc != -ENODATA)
+ if (rc == -ENODATA) {
+ /* ignore the non-linkEA error */
+ ldata = NULL;
+ rc = 0;
+ }
+ if (rc < 0)
RETURN(rc);
}
if (rc != 0)
GOTO(stop_trans, rc);
- if (S_ISDIR(la->la_mode)) {
+ if (S_ISDIR(la->la_mode) && ldata != NULL) {
rc = mdd_links_write(env, mdd_tobj, ldata, handle);
if (rc != 0)
GOTO(stop_trans, rc);
if (!fid_is_md_operative(old_fid))
GOTO(out_unlock_parent, rc = -EPERM);
+ if (lu_fid_eq(old_fid, &info->mti_mdt->mdt_md_root_fid))
+ GOTO(out_unlock_parent, rc = -EPERM);
+
mold = mdt_object_find(info->mti_env, info->mti_mdt, old_fid);
if (IS_ERR(mold))
GOTO(out_unlock_parent, rc = PTR_ERR(mold));
}
run_test 230g "migrate dir to non-exist MDT"
+test_230h() {
+ [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
+ [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
+ [ $(lustre_version_code $SINGLEMDS) -lt $(version_code 2.7.64) ] &&
+ skip "Need MDS version at least 2.7.64" && return
+ local mdt_index
+
+ mkdir -p $DIR/$tdir/migrate_dir
+
+ $LFS migrate -m1 $DIR &&
+ error "migrating mountpoint1 should fail"
+
+ $LFS migrate -m1 $DIR/$tdir/.. &&
+ error "migrating mountpoint2 should fail"
+
+ $LFS migrate -m1 $DIR/$tdir/migrate_dir/.. ||
+ error "migrating $tdir fail"
+
+ mdt_index=$($LFS getstripe -M $DIR/$tdir)
+ [ $mdt_index == 1 ] || error "$mdt_index != 1 after migration"
+
+ mdt_index=$($LFS getstripe -M $DIR/$tdir/migrate_dir)
+ [ $mdt_index == 1 ] || error "$mdt_index != 1 after migration"
+
+}
+run_test 230h "migrate .. and root"
+
test_231a()
{
# For simplicity this test assumes that max_pages_per_rpc