Commit 18578808 authored by Lai Siyao's avatar Lai Siyao Committed by Oleg Drokin
Browse files

LU-13437 llite: pass name in getattr by FID

Now parent FID is packed in getattr_by_FID request
(see https://review.whamcloud.com/39290), it should also pass in name
from llite, so that lmv can replace fid1 with stripe FID, otherwise
MDS may treat sub files under striped directory as remote object.

Note, the name is not packed in request, because if it's packed, MDS
will getattr by name instead of FID.

Lustre-change: https://review.whamcloud.com/40219
Lustre-commit: 90ebab58

Fixes: 5f2c44bf

 ("LU-13437 llite: pack parent FID in getattr")
Signed-off-by: default avatarLai Siyao <lai.siyao@whamcloud.com>
Change-Id: If8215667bcb10ea3c4c5cd2c9034d81fd1cda3b5
Reviewed-by: default avatarAndreas Dilger <adilger@whamcloud.com>
Reviewed-by: default avatarMike Pershin <mpershin@whamcloud.com>
Reviewed-by: default avatarOleg Drokin <green@whamcloud.com>
Reviewed-on: https://review.whamcloud.com/40482

Tested-by: default avatarjenkins <devops@whamcloud.com>
Tested-by: default avatarMaloo <maloo@whamcloud.com>
parent 23c05e82
......@@ -822,6 +822,7 @@ enum md_op_flags {
MF_MDC_CANCEL_FID3 = 1 << 2,
MF_MDC_CANCEL_FID4 = 1 << 3,
MF_GET_MDT_IDX = 1 << 4,
MF_GETATTR_BY_FID = 1 << 5,
};
enum md_cli_flags {
......
......@@ -4356,23 +4356,30 @@ static int ll_inode_revalidate(struct dentry *dentry, enum ldlm_intent_flags op)
};
struct ptlrpc_request *req = NULL;
struct md_op_data *op_data;
const char *name = NULL;
size_t namelen = 0;
int rc = 0;
ENTRY;
CDEBUG(D_VFSTRACE, "VFS Op:inode="DFID"(%p),name=%s\n",
PFID(ll_inode2fid(inode)), inode, dentry->d_name.name);
if (exp_connect_flags2(exp) & OBD_CONNECT2_GETATTR_PFID)
if (exp_connect_flags2(exp) & OBD_CONNECT2_GETATTR_PFID) {
parent = dentry->d_parent->d_inode;
else
name = dentry->d_name.name;
namelen = dentry->d_name.len;
} else {
parent = inode;
}
/* Call getattr by fid, so do not provide name at all. */
op_data = ll_prep_md_op_data(NULL, parent, inode, NULL, 0, 0,
op_data = ll_prep_md_op_data(NULL, parent, inode, name, namelen, 0,
LUSTRE_OPC_ANY, NULL);
if (IS_ERR(op_data))
RETURN(PTR_ERR(op_data));
/* Call getattr by fid */
if (exp_connect_flags2(exp) & OBD_CONNECT2_GETATTR_PFID)
op_data->op_flags = MF_GETATTR_BY_FID;
rc = md_intent_lock(exp, op_data, &oit, &req, &ll_md_blocking_ast, 0);
ll_finish_md_op_data(op_data);
if (rc < 0) {
......
......@@ -2552,7 +2552,9 @@ struct md_op_data *ll_prep_md_op_data(struct md_op_data *op_data,
if (namelen > ll_i2sbi(i1)->ll_namelen)
return ERR_PTR(-ENAMETOOLONG);
if (!lu_name_is_valid_2(name, namelen))
/* "/" is not valid name, but it's allowed */
if (!lu_name_is_valid_2(name, namelen) &&
strncmp("/", name, namelen) != 0)
return ERR_PTR(-EINVAL);
}
......
......@@ -429,13 +429,29 @@ lmv_intent_lookup(struct obd_export *exp, struct md_op_data *op_data,
ENTRY;
retry:
if (op_data->op_name) {
if (op_data->op_flags & MF_GETATTR_BY_FID) {
/* getattr by FID, replace fid1 with stripe FID */
LASSERT(op_data->op_name);
tgt = lmv_locate_tgt(lmv, op_data, &op_data->op_fid1);
if (IS_ERR(tgt))
RETURN(PTR_ERR(tgt));
/* name is used to locate stripe target, clear it here
* to avoid packing name in request, so that MDS knows
* it's getattr by FID.
*/
op_data->op_name = NULL;
op_data->op_namelen = 0;
/* getattr request is sent to MDT where fid2 inode is */
tgt = lmv_find_target(lmv, &op_data->op_fid2);
} else if (op_data->op_name) {
/* getattr by name */
tgt = lmv_locate_tgt(lmv, op_data, &op_data->op_fid1);
if (!fid_is_sane(&op_data->op_fid2))
fid_zero(&op_data->op_fid2);
} else if (fid_is_sane(&op_data->op_fid2)) {
tgt = lmv_find_target(lmv, &op_data->op_fid2);
} else {
/* old way to getattr by FID, parent FID not packed */
tgt = lmv_find_target(lmv, &op_data->op_fid1);
}
if (IS_ERR(tgt))
......
......@@ -1619,10 +1619,11 @@ __lmv_locate_tgt(struct lmv_obd *lmv, struct lmv_stripe_md *lsm,
*
* For normal direcotry, it will locate MDS by FID directly.
*
* \param[in] lmv LMV device
* \param[in] op_data client MD stack parameters, name, namelen
* mds_num etc.
* \param[in] fid object FID used to locate MDS.
* \param[in] lmv LMV device
* \param[in/out] op_data client MD stack parameters, name, namelen etc,
* op_mds and op_fid1 will be updated if op_mea1
* indicates fid1 represents a striped directory.
* \param[out] fid object FID used to locate MDS.
*
* retval pointer to the lmv_tgt_desc if succeed.
* ERR_PTR(errno) if failed.
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment