From 78e16f885cd76bfe8e2ed3d2a15995959eee7a6f Mon Sep 17 00:00:00 2001 From: "John L. Hammond" Date: Wed, 16 Oct 2013 09:15:56 -0500 Subject: [PATCH] LU-2875 mdt: use lu_name for rr_name and rr_tgt In mdt_reint_record, use a struct lu_name for rr_name and rr_tgt. Rename the rename target name rr_tgt to rr_tgt_name. Add a function lu_name_is_valid() to check the validity of names. Remove various assertions on the validity of names in MDT requests and replace them with calls to mdt_reint_record() and returns of -EPROTO on failure. Signed-off-by: John L. Hammond Change-Id: I6e0e207522a72eb8cec5d7918795c4aed5b9c4c2 Reviewed-on: http://review.whamcloud.com/7961 Tested-by: Jenkins Tested-by: Maloo Reviewed-by: Fan Yong Reviewed-by: Andreas Dilger Reviewed-by: Oleg Drokin --- lustre/include/lu_object.h | 13 +++++ lustre/mdt/mdt_handler.c | 113 +++++++++++++++++++++--------------------- lustre/mdt/mdt_internal.h | 63 ++++++++---------------- lustre/mdt/mdt_lib.c | 93 +++++++++++++++++++++-------------- lustre/mdt/mdt_open.c | 86 ++++++++++++++++---------------- lustre/mdt/mdt_reint.c | 119 +++++++++++++++++++++------------------------ lustre/mdt/mdt_xattr.c | 2 +- 7 files changed, 244 insertions(+), 245 deletions(-) diff --git a/lustre/include/lu_object.h b/lustre/include/lu_object.h index 94c0b47..e5a977f 100644 --- a/lustre/include/lu_object.h +++ b/lustre/include/lu_object.h @@ -1289,6 +1289,19 @@ struct lu_name { int ln_namelen; }; +static inline bool lu_name_is_valid(const struct lu_name *ln) +{ + return ln->ln_name != NULL && + ln->ln_namelen > 0 && + ln->ln_name[0] != '\0' && + ln->ln_name[ln->ln_namelen] == '\0'; +} + +#define DNAME "%.*s" +#define PNAME(ln) \ + (lu_name_is_valid(ln) ? (ln)->ln_namelen : 0), \ + (lu_name_is_valid(ln) ? (ln)->ln_name : "") + /** * Common buffer structure to be passed around for various xattr_{s,g}et() * methods. diff --git a/lustre/mdt/mdt_handler.c b/lustre/mdt/mdt_handler.c index 1ad4f40..bd23719 100644 --- a/lustre/mdt/mdt_handler.c +++ b/lustre/mdt/mdt_handler.c @@ -164,27 +164,28 @@ void mdt_lock_reg_init(struct mdt_lock_handle *lh, ldlm_mode_t lm) lh->mlh_type = MDT_REG_LOCK; } -void mdt_lock_pdo_init(struct mdt_lock_handle *lh, ldlm_mode_t lm, - const char *name, int namelen) +void mdt_lock_pdo_init(struct mdt_lock_handle *lh, ldlm_mode_t lock_mode, + const struct lu_name *lname) { - lh->mlh_reg_mode = lm; - lh->mlh_rreg_mode = lm; - lh->mlh_type = MDT_PDO_LOCK; + lh->mlh_reg_mode = lock_mode; + lh->mlh_rreg_mode = lock_mode; + lh->mlh_type = MDT_PDO_LOCK; - if (name != NULL && (name[0] != '\0')) { - LASSERT(namelen > 0); - lh->mlh_pdo_hash = full_name_hash(name, namelen); + if (lu_name_is_valid(lname)) { + lh->mlh_pdo_hash = full_name_hash(lname->ln_name, + lname->ln_namelen); /* XXX Workaround for LU-2856 - * Zero is a valid return value of full_name_hash, but several - * users of mlh_pdo_hash assume a non-zero hash value. We - * therefore map zero onto an arbitrary, but consistent - * value (1) to avoid problems further down the road. */ - if (unlikely(!lh->mlh_pdo_hash)) + * + * Zero is a valid return value of full_name_hash, but + * several users of mlh_pdo_hash assume a non-zero + * hash value. We therefore map zero onto an + * arbitrary, but consistent value (1) to avoid + * problems further down the road. */ + if (unlikely(lh->mlh_pdo_hash == 0)) lh->mlh_pdo_hash = 1; - } else { - LASSERT(namelen == 0); - lh->mlh_pdo_hash = 0ull; - } + } else { + lh->mlh_pdo_hash = 0; + } } static void mdt_lock_pdo_mode(struct mdt_thread_info *info, struct mdt_object *o, @@ -1221,8 +1222,6 @@ static int mdt_getattr_name_lock(struct mdt_thread_info *info, struct md_object *next = mdt_object_child(parent); struct lu_fid *child_fid = &info->mti_tmp_fid1; struct lu_name *lname = NULL; - const char *name = NULL; - int namelen = 0; struct mdt_lock_handle *lhp = NULL; struct ldlm_lock *lock; struct ldlm_res_id *res_id; @@ -1237,43 +1236,40 @@ static int mdt_getattr_name_lock(struct mdt_thread_info *info, lustre_msg_get_flags(req->rq_reqmsg) & MSG_RESENT)); LASSERT(parent != NULL); - name = req_capsule_client_get(info->mti_pill, &RMF_NAME); - if (name == NULL) - RETURN(err_serious(-EFAULT)); - namelen = req_capsule_get_size(info->mti_pill, &RMF_NAME, - RCL_CLIENT) - 1; - if (!info->mti_cross_ref) { - /* - * XXX: Check for "namelen == 0" is for getattr by fid - * (OBD_CONNECT_ATTRFID), otherwise do not allow empty name, - * that is the name must contain at least one character and - * the terminating '\0' - */ - if (namelen == 0) { - reqbody = req_capsule_client_get(info->mti_pill, - &RMF_MDT_BODY); - if (unlikely(reqbody == NULL)) - RETURN(err_serious(-EFAULT)); - - if (unlikely(!fid_is_sane(&reqbody->fid2))) - RETURN(err_serious(-EINVAL)); - - name = NULL; - CDEBUG(D_INODE, "getattr with lock for "DFID"/"DFID", " - "ldlm_rep = %p\n", - PFID(mdt_object_fid(parent)), - PFID(&reqbody->fid2), ldlm_rep); - } else { - lname = mdt_name(info->mti_env, (char *)name, namelen); - CDEBUG(D_INODE, "getattr with lock for "DFID"/%s, " - "ldlm_rep = %p\n", PFID(mdt_object_fid(parent)), - name, ldlm_rep); - } - } + lname = &info->mti_name; + mdt_name_unpack(info->mti_pill, &RMF_NAME, lname, MNF_FIX_ANON); + + if (!info->mti_cross_ref) { + /* + * XXX: Check for anonymous name is for getattr by fid + * (OBD_CONNECT_ATTRFID), otherwise do not allow empty name, + * that is the name must contain at least one character and + * the terminating '\0'. + */ + if (!lu_name_is_valid(lname)) { + reqbody = req_capsule_client_get(info->mti_pill, + &RMF_MDT_BODY); + if (unlikely(reqbody == NULL)) + RETURN(err_serious(-EFAULT)); + + if (unlikely(!fid_is_sane(&reqbody->fid2))) + RETURN(err_serious(-EINVAL)); + + CDEBUG(D_INODE, "getattr with lock for "DFID"/"DFID", " + "ldlm_rep = %p\n", + PFID(mdt_object_fid(parent)), + PFID(&reqbody->fid2), ldlm_rep); + } else { + CDEBUG(D_INODE, "getattr with lock for "DFID"/"DNAME", " + "ldlm_rep = %p\n", PFID(mdt_object_fid(parent)), + PNAME(lname), ldlm_rep); + } + } + mdt_set_disposition(info, ldlm_rep, DISP_LOOKUP_EXECD); - if (unlikely(!mdt_object_exists(parent)) && lname) { + if (unlikely(!mdt_object_exists(parent)) && lu_name_is_valid(lname)) { LU_OBJECT_DEBUG(D_INODE, info->mti_env, &parent->mot_obj, "Parent doesn't exist!\n"); @@ -1283,7 +1279,8 @@ static int mdt_getattr_name_lock(struct mdt_thread_info *info, "Parent "DFID" is on remote server\n", PFID(mdt_object_fid(parent))); } - if (lname) { + + if (lu_name_is_valid(lname)) { rc = mdt_raw_lookup(info, parent, lname, ldlm_rep); if (rc != 0) { if (rc > 0) @@ -1342,11 +1339,11 @@ static int mdt_getattr_name_lock(struct mdt_thread_info *info, RETURN(rc); } - if (lname) { - /* step 1: lock parent only if parent is a directory */ + if (lu_name_is_valid(lname)) { + /* step 1: lock parent only if parent is a directory */ if (S_ISDIR(lu_object_attr(&parent->mot_obj))) { - lhp = &info->mti_lh[MDT_LH_PARENT]; - mdt_lock_pdo_init(lhp, LCK_PR, name, namelen); + lhp = &info->mti_lh[MDT_LH_PARENT]; + mdt_lock_pdo_init(lhp, LCK_PR, lname); rc = mdt_object_lock(info, parent, lhp, MDS_INODELOCK_UPDATE, MDT_LOCAL_LOCK); diff --git a/lustre/mdt/mdt_internal.h b/lustre/mdt/mdt_internal.h index dd36201..6c9d9fe 100644 --- a/lustre/mdt/mdt_internal.h +++ b/lustre/mdt/mdt_internal.h @@ -316,19 +316,15 @@ enum { }; struct mdt_reint_record { - mdt_reint_t rr_opcode; - const struct lustre_handle *rr_handle; - const struct lu_fid *rr_fid1; - const struct lu_fid *rr_fid2; - const char *rr_name; - int rr_namelen; - const char *rr_tgt; - int rr_tgtlen; - const void *rr_eadata; - int rr_eadatalen; - int rr_logcookielen; - const struct llog_cookie *rr_logcookies; - __u32 rr_flags; + mdt_reint_t rr_opcode; + const struct lustre_handle *rr_handle; + const struct lu_fid *rr_fid1; + const struct lu_fid *rr_fid2; + struct lu_name rr_name; + struct lu_name rr_tgt_name; + const void *rr_eadata; + int rr_eadatalen; + __u32 rr_flags; }; enum mdt_reint_flag { @@ -638,8 +634,8 @@ void mdt_clear_disposition(struct mdt_thread_info *info, struct ldlm_reply *rep, int flag); void mdt_lock_pdo_init(struct mdt_lock_handle *lh, - ldlm_mode_t lm, const char *name, - int namelen); + ldlm_mode_t lock_mode, + const struct lu_name *lname); void mdt_lock_reg_init(struct mdt_lock_handle *lh, ldlm_mode_t lm); @@ -683,6 +679,15 @@ void mdt_client_compatibility(struct mdt_thread_info *info); int mdt_remote_object_lock(struct mdt_thread_info *mti, struct mdt_object *o, struct lustre_handle *lh, ldlm_mode_t mode, __u64 ibits); + +enum mdt_name_flags { + MNF_FIX_ANON = 1, +}; + +int mdt_name_unpack(struct req_capsule *pill, + const struct req_msg_field *field, + struct lu_name *ln, + enum mdt_name_flags flags); int mdt_close_unpack(struct mdt_thread_info *info); int mdt_reint_unpack(struct mdt_thread_info *info, __u32 op); int mdt_reint_rec(struct mdt_thread_info *, struct mdt_lock_handle *); @@ -1034,34 +1039,6 @@ static inline ldlm_mode_t mdt_mdl_mode2dlm_mode(mdl_mode_t mode) /* mdt_lvb.c */ extern struct ldlm_valblock_ops mdt_lvbo; -static inline struct lu_name *mdt_name(const struct lu_env *env, - char *name, int namelen) -{ - struct lu_name *lname; - struct mdt_thread_info *mti; - - LASSERT(namelen > 0); - /* trailing '\0' in buffer */ - LASSERT(name[namelen] == '\0'); - - mti = lu_context_key_get(&env->le_ctx, &mdt_thread_key); - lname = &mti->mti_name; - lname->ln_name = name; - lname->ln_namelen = namelen; - return lname; -} - -static inline struct lu_name *mdt_name_copy(struct lu_name *tlname, - struct lu_name *slname) -{ - LASSERT(tlname); - LASSERT(slname); - - tlname->ln_name = slname->ln_name; - tlname->ln_namelen = slname->ln_namelen; - return tlname; -} - void mdt_enable_cos(struct mdt_device *, int); int mdt_cos_is_enabled(struct mdt_device *); diff --git a/lustre/mdt/mdt_lib.c b/lustre/mdt/mdt_lib.c index c611462..aa4c2cb 100644 --- a/lustre/mdt/mdt_lib.c +++ b/lustre/mdt/mdt_lib.c @@ -801,6 +801,33 @@ void mdt_dump_capainfo(struct mdt_thread_info *info) /* unpacking */ +int mdt_name_unpack(struct req_capsule *pill, + const struct req_msg_field *field, + struct lu_name *ln, + enum mdt_name_flags flags) +{ + ln->ln_name = req_capsule_client_get(pill, field); + ln->ln_namelen = req_capsule_get_size(pill, field, RCL_CLIENT) - 1; + + if (!lu_name_is_valid(ln)) { + ln->ln_name = NULL; + ln->ln_namelen = 0; + + return -EPROTO; + } + + if ((flags & MNF_FIX_ANON) && + ln->ln_namelen == 1 && ln->ln_name[0] == '/') { + /* Newer (3.x) kernels use a name of "/" for the + * "anonymous" disconnected dentries from NFS + * filehandle conversion. See d_obtain_alias(). */ + ln->ln_name = NULL; + ln->ln_namelen = 0; + } + + return 0; +} + static int mdt_setattr_unpack_rec(struct mdt_thread_info *info) { struct lu_ucred *uc = mdt_ucred(info); @@ -1003,10 +1030,9 @@ static int mdt_create_unpack(struct mdt_thread_info *info) req_capsule_client_get(pill, &RMF_CAPA1)); mdt_set_capainfo(info, 1, rr->rr_fid2, BYPASS_CAPA); - rr->rr_name = req_capsule_client_get(pill, &RMF_NAME); - rr->rr_namelen = req_capsule_get_size(pill, &RMF_NAME, - RCL_CLIENT) - 1; - LASSERT(rr->rr_name && rr->rr_namelen > 0); + rc = mdt_name_unpack(pill, &RMF_NAME, &rr->rr_name, 0); + if (rc < 0) + RETURN(rc); if (S_ISLNK(attr->la_mode)) { const char *tgt = NULL; @@ -1063,15 +1089,13 @@ static int mdt_link_unpack(struct mdt_thread_info *info) mdt_set_capainfo(info, 1, rr->rr_fid2, req_capsule_client_get(pill, &RMF_CAPA2)); - rr->rr_name = req_capsule_client_get(pill, &RMF_NAME); - if (rr->rr_name == NULL) - RETURN(-EFAULT); - rr->rr_namelen = req_capsule_get_size(pill, &RMF_NAME, RCL_CLIENT) - 1; + rc = mdt_name_unpack(pill, &RMF_NAME, &rr->rr_name, 0); + if (rc < 0) + RETURN(rc); - LASSERT(rr->rr_namelen > 0); + rc = mdt_dlmreq_unpack(info); - rc = mdt_dlmreq_unpack(info); - RETURN(rc); + RETURN(rc); } static int mdt_unlink_unpack(struct mdt_thread_info *info) @@ -1110,10 +1134,9 @@ static int mdt_unlink_unpack(struct mdt_thread_info *info) mdt_set_capainfo(info, 0, rr->rr_fid1, req_capsule_client_get(pill, &RMF_CAPA1)); - rr->rr_name = req_capsule_client_get(pill, &RMF_NAME); - rr->rr_namelen = req_capsule_get_size(pill, &RMF_NAME, RCL_CLIENT) - 1; - if (rr->rr_name == NULL || rr->rr_namelen == 0) - RETURN(-EFAULT); + rc = mdt_name_unpack(pill, &RMF_NAME, &rr->rr_name, 0); + if (rc < 0) + RETURN(rc); if (rec->ul_bias & MDS_VTX_BYPASS) ma->ma_attr_flags |= MDS_VTX_BYPASS; @@ -1172,13 +1195,13 @@ static int mdt_rename_unpack(struct mdt_thread_info *info) mdt_set_capainfo(info, 1, rr->rr_fid2, req_capsule_client_get(pill, &RMF_CAPA2)); - rr->rr_name = req_capsule_client_get(pill, &RMF_NAME); - rr->rr_tgt = req_capsule_client_get(pill, &RMF_SYMTGT); - if (rr->rr_name == NULL || rr->rr_tgt == NULL) - RETURN(-EFAULT); - rr->rr_namelen = req_capsule_get_size(pill, &RMF_NAME, RCL_CLIENT) - 1; - rr->rr_tgtlen = req_capsule_get_size(pill, &RMF_SYMTGT, RCL_CLIENT) - 1; - LASSERT(rr->rr_namelen > 0 && rr->rr_tgtlen > 0); + rc = mdt_name_unpack(pill, &RMF_NAME, &rr->rr_name, 0); + if (rc < 0) + RETURN(rc); + + rc = mdt_name_unpack(pill, &RMF_SYMTGT, &rr->rr_tgt_name, 0); + if (rc < 0) + RETURN(rc); if (rec->rn_bias & MDS_VTX_BYPASS) ma->ma_attr_flags |= MDS_VTX_BYPASS; @@ -1278,10 +1301,7 @@ static int mdt_open_unpack(struct mdt_thread_info *info) #endif } - rr->rr_name = req_capsule_client_get(pill, &RMF_NAME); - if (rr->rr_name == NULL) - RETURN(-EFAULT); - rr->rr_namelen = req_capsule_get_size(pill, &RMF_NAME, RCL_CLIENT) - 1; + mdt_name_unpack(pill, &RMF_NAME, &rr->rr_name, MNF_FIX_ANON); if (req_capsule_field_present(pill, &RMF_EADATA, RCL_CLIENT)) { rr->rr_eadatalen = req_capsule_get_size(pill, &RMF_EADATA, @@ -1310,12 +1330,13 @@ static int mdt_open_unpack(struct mdt_thread_info *info) static int mdt_setxattr_unpack(struct mdt_thread_info *info) { - struct mdt_reint_record *rr = &info->mti_rr; - struct lu_ucred *uc = mdt_ucred(info); - struct lu_attr *attr = &info->mti_attr.ma_attr; - struct req_capsule *pill = info->mti_pill; - struct mdt_rec_setxattr *rec; - ENTRY; + struct mdt_reint_record *rr = &info->mti_rr; + struct lu_ucred *uc = mdt_ucred(info); + struct lu_attr *attr = &info->mti_attr.ma_attr; + struct req_capsule *pill = info->mti_pill; + struct mdt_rec_setxattr *rec; + int rc; + ENTRY; CLASSERT(sizeof(struct mdt_rec_setxattr) == @@ -1345,11 +1366,9 @@ static int mdt_setxattr_unpack(struct mdt_thread_info *info) else mdt_set_capainfo(info, 0, rr->rr_fid1, BYPASS_CAPA); - rr->rr_name = req_capsule_client_get(pill, &RMF_NAME); - if (rr->rr_name == NULL) - RETURN(-EFAULT); - rr->rr_namelen = req_capsule_get_size(pill, &RMF_NAME, RCL_CLIENT) - 1; - LASSERT(rr->rr_namelen > 0); + rc = mdt_name_unpack(pill, &RMF_NAME, &rr->rr_name, 0); + if (rc < 0) + RETURN(rc); if (req_capsule_field_present(pill, &RMF_EADATA, RCL_CLIENT)) { rr->rr_eadatalen = req_capsule_get_size(pill, &RMF_EADATA, diff --git a/lustre/mdt/mdt_open.c b/lustre/mdt/mdt_open.c index 4e4a2c3..30c80e7 100644 --- a/lustre/mdt/mdt_open.c +++ b/lustre/mdt/mdt_open.c @@ -1569,7 +1569,6 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) __u64 create_flags = info->mti_spec.sp_cr_flags; __u64 ibits = 0; struct mdt_reint_record *rr = &info->mti_rr; - struct lu_name *lname; int result, rc; int created = 0; __u32 msg_flags; @@ -1603,11 +1602,12 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) info->mti_spec.u.sp_ea.eadata == NULL) GOTO(out, result = err_serious(-EINVAL)); - CDEBUG(D_INODE, "I am going to open "DFID"/(%s->"DFID") " - "cr_flag="LPO64" mode=0%06o msg_flag=0x%x\n", - PFID(rr->rr_fid1), rr->rr_name, - PFID(rr->rr_fid2), create_flags, - ma->ma_attr.la_mode, msg_flags); + CDEBUG(D_INODE, "I am going to open "DFID"/("DNAME"->"DFID") " + "cr_flag="LPO64" mode=0%06o msg_flag=0x%x\n", + PFID(rr->rr_fid1), PNAME(&rr->rr_name), + PFID(rr->rr_fid2), create_flags, + ma->ma_attr.la_mode, msg_flags); + if (info->mti_cross_ref) { /* This is cross-ref open */ mdt_set_disposition(info, ldlm_rep, @@ -1635,7 +1635,8 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) GOTO(out, result = -EFAULT); } CDEBUG(D_INFO, "No object(1), continue as regular open.\n"); - } else if ((rr->rr_namelen == 0 && create_flags & MDS_OPEN_LOCK) || + } else if ((!lu_name_is_valid(&rr->rr_name) && + (create_flags & MDS_OPEN_LOCK)) || (create_flags & MDS_OPEN_BY_FID)) { result = mdt_open_by_fid_lock(info, ldlm_rep, lhc); /* If result is 0 then open by FID has found the file @@ -1650,9 +1651,6 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) result != -EREMOTE) GOTO(out, result); - if (unlikely(rr->rr_namelen == 0)) - GOTO(out, result = -EINVAL); - CDEBUG(D_INFO, "No object(2), continue as regular open.\n"); } @@ -1662,9 +1660,13 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) mdt_set_disposition(info, ldlm_rep, (DISP_IT_EXECD | DISP_LOOKUP_EXECD)); + if (!lu_name_is_valid(&rr->rr_name)) + GOTO(out, result = -EPROTO); + lh = &info->mti_lh[MDT_LH_PARENT]; - mdt_lock_pdo_init(lh, (create_flags & MDS_OPEN_CREAT) ? - LCK_PW : LCK_PR, rr->rr_name, rr->rr_namelen); + mdt_lock_pdo_init(lh, + (create_flags & MDS_OPEN_CREAT) ? LCK_PW : LCK_PR, + &rr->rr_name); parent = mdt_object_find_lock(info, rr->rr_fid1, lh, MDS_INODELOCK_UPDATE); @@ -1678,12 +1680,13 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) fid_zero(child_fid); - lname = mdt_name(info->mti_env, (char *)rr->rr_name, rr->rr_namelen); - result = mdo_lookup(info->mti_env, mdt_object_child(parent), - lname, child_fid, &info->mti_spec); - LASSERTF(ergo(result == 0, fid_is_sane(child_fid)), - "looking for "DFID"/%s, result fid="DFID"\n", - PFID(mdt_object_fid(parent)), rr->rr_name, PFID(child_fid)); + result = mdo_lookup(info->mti_env, mdt_object_child(parent), + &rr->rr_name, child_fid, &info->mti_spec); + + LASSERTF(ergo(result == 0, fid_is_sane(child_fid)), + "looking for "DFID"/"DNAME", found FID = "DFID"\n", + PFID(mdt_object_fid(parent)), PNAME(&rr->rr_name), + PFID(child_fid)); if (result != 0 && result != -ENOENT && result != -ESTALE) GOTO(out_parent, result); @@ -1752,12 +1755,12 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) info->mti_spec.sp_cr_lookup = 0; info->mti_spec.sp_feat = &dt_directory_features; - result = mdo_create(info->mti_env, - mdt_object_child(parent), - lname, - mdt_object_child(child), - &info->mti_spec, - &info->mti_attr); + result = mdo_create(info->mti_env, + mdt_object_child(parent), + &rr->rr_name, + mdt_object_child(child), + &info->mti_spec, + &info->mti_attr); if (result == -ERESTART) { mdt_clear_disposition(info, ldlm_rep, DISP_OPEN_CREATE); GOTO(out_child, result); @@ -1813,19 +1816,18 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) else result = -EREMOTE; GOTO(out_child, result); + } else if (mdt_object_exists(child)) { + /* We have to get attr & LOV EA & HSM for this + * object. */ + ma->ma_need |= MA_HSM; + result = mdt_attr_get_complex(info, child, ma); } else { - if (mdt_object_exists(child)) { - /* We have to get attr & LOV EA & HSM for this - * object */ - ma->ma_need |= MA_HSM; - result = mdt_attr_get_complex(info, child, ma); - } else { - /*object non-exist!!! Likely an fs corruption*/ - CERROR("%s: name %s present, but fid " DFID - " invalid\n",mdt_obd_name(info->mti_mdt), - rr->rr_name, PFID(child_fid)); - GOTO(out_child, result = -EIO); - } + /* Object does not exist. Likely FS corruption. */ + CERROR("%s: name '"DNAME"' present, but FID " + DFID" is invalid\n", + mdt_obd_name(info->mti_mdt), + PNAME(&rr->rr_name), PFID(child_fid)); + GOTO(out_child, result = -EIO); } } @@ -1869,7 +1871,7 @@ int mdt_reint_open(struct mdt_thread_info *info, struct mdt_lock_handle *lhc) rc = mdo_unlink(info->mti_env, mdt_object_child(parent), mdt_object_child(child), - lname, + &rr->rr_name, &info->mti_attr, 0); if (rc != 0) CERROR("%s: "DFID" cleanup of open: rc = %d\n", @@ -1904,8 +1906,10 @@ static struct mdt_object *mdt_orphan_open(struct mdt_thread_info *info, struct lu_fid *local_root_fid = &info->mti_tmp_fid1; struct mdt_object *obj = NULL; struct mdt_object *local_root; - static const char name[] = "i_am_nobody"; - struct lu_name *lname; + static const struct lu_name lname = { + .ln_name = "i_am_nobody", + .ln_namelen = sizeof("i_am_nobody") - 1, + }; struct lu_ucred *uc; cfs_cap_t uc_cap_save; int rc; @@ -1935,12 +1939,10 @@ static struct mdt_object *mdt_orphan_open(struct mdt_thread_info *info, spec->sp_cr_flags |= MDS_OPEN_DELAY_CREATE; } - lname = mdt_name(env, (char *)name, sizeof(name) - 1); - uc = lu_ucred(env); uc_cap_save = uc->uc_cap; uc->uc_cap |= 1 << CFS_CAP_DAC_OVERRIDE; - rc = mdo_create(env, mdt_object_child(local_root), lname, + rc = mdo_create(env, mdt_object_child(local_root), &lname, mdt_object_child(obj), spec, attr); uc->uc_cap = uc_cap_save; if (rc < 0) { diff --git a/lustre/mdt/mdt_reint.c b/lustre/mdt/mdt_reint.c index 50f3efa..c7436c8 100644 --- a/lustre/mdt/mdt_reint.c +++ b/lustre/mdt/mdt_reint.c @@ -219,8 +219,8 @@ int mdt_version_get_check_save(struct mdt_thread_info *info, * FID, therefore we need to get object by name and check its version. */ int mdt_lookup_version_check(struct mdt_thread_info *info, - struct mdt_object *p, struct lu_name *lname, - struct lu_fid *fid, int idx) + struct mdt_object *p, const struct lu_name *lname, + struct lu_fid *fid, int idx) { int rc, vbrc; @@ -261,20 +261,20 @@ static int mdt_md_create(struct mdt_thread_info *info) struct mdt_body *repbody; struct md_attr *ma = &info->mti_attr; struct mdt_reint_record *rr = &info->mti_rr; - struct lu_name *lname; int rc; ENTRY; - DEBUG_REQ(D_INODE, mdt_info_req(info), "Create (%s->"DFID") in "DFID, - rr->rr_name, PFID(rr->rr_fid2), PFID(rr->rr_fid1)); + DEBUG_REQ(D_INODE, mdt_info_req(info), "Create ("DNAME"->"DFID") " + "in "DFID, + PNAME(&rr->rr_name), PFID(rr->rr_fid2), PFID(rr->rr_fid1)); if (fid_is_obf(rr->rr_fid1) || fid_is_dot_lustre(rr->rr_fid1)) RETURN(-EPERM); repbody = req_capsule_server_get(info->mti_pill, &RMF_MDT_BODY); - lh = &info->mti_lh[MDT_LH_PARENT]; - mdt_lock_pdo_init(lh, LCK_PW, rr->rr_name, rr->rr_namelen); + lh = &info->mti_lh[MDT_LH_PARENT]; + mdt_lock_pdo_init(lh, LCK_PW, &rr->rr_name); parent = mdt_object_find_lock(info, rr->rr_fid1, lh, MDS_INODELOCK_UPDATE); @@ -289,9 +289,8 @@ static int mdt_md_create(struct mdt_thread_info *info) * Check child name version during replay. * During create replay a file may exist with same name. */ - lname = mdt_name(info->mti_env, (char *)rr->rr_name, rr->rr_namelen); - rc = mdt_lookup_version_check(info, parent, lname, - &info->mti_tmp_fid1, 1); + rc = mdt_lookup_version_check(info, parent, &rr->rr_name, + &info->mti_tmp_fid1, 1); if (rc == 0) GOTO(out_put_parent, rc = -EEXIST); @@ -365,9 +364,8 @@ static int mdt_md_create(struct mdt_thread_info *info) info->mti_spec.sp_cr_lookup = 0; info->mti_spec.sp_feat = &dt_directory_features; - rc = mdo_create(info->mti_env, next, lname, - mdt_object_child(child), - &info->mti_spec, ma); + rc = mdo_create(info->mti_env, next, &rr->rr_name, + mdt_object_child(child), &info->mti_spec, ma); if (rc == 0) rc = mdt_attr_get_complex(info, child, ma); @@ -653,8 +651,10 @@ static int mdt_reint_create(struct mdt_thread_info *info, if (info->mti_dlm_req) ldlm_request_cancel(mdt_info_req(info), info->mti_dlm_req, 0); - LASSERT(info->mti_rr.rr_namelen > 0); - switch (info->mti_attr.ma_attr.la_mode & S_IFMT) { + if (!lu_name_is_valid(&info->mti_rr.rr_name)) + RETURN(-EPROTO); + + switch (info->mti_attr.ma_attr.la_mode & S_IFMT) { case S_IFDIR: mdt_counter_incr(req, LPROC_MDT_MKDIR); break; @@ -693,13 +693,12 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, struct mdt_object *mc; struct mdt_lock_handle *parent_lh; struct mdt_lock_handle *child_lh; - struct lu_name *lname; int rc; int no_name = 0; ENTRY; - DEBUG_REQ(D_INODE, req, "unlink "DFID"/%s", PFID(rr->rr_fid1), - rr->rr_name); + DEBUG_REQ(D_INODE, req, "unlink "DFID"/"DNAME"", PFID(rr->rr_fid1), + PNAME(&rr->rr_name)); if (info->mti_dlm_req) ldlm_request_cancel(req, info->mti_dlm_req, 0); @@ -719,7 +718,7 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, } parent_lh = &info->mti_lh[MDT_LH_PARENT]; - lname = mdt_name(info->mti_env, (char *)rr->rr_name, rr->rr_namelen); + if (mdt_object_remote(mp)) { mdt_lock_reg_init(parent_lh, LCK_EX); rc = mdt_remote_object_lock(info, mp, &parent_lh->mlh_rreg_lh, @@ -729,8 +728,7 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, GOTO(put_parent, rc); } else { - mdt_lock_pdo_init(parent_lh, LCK_PW, rr->rr_name, - rr->rr_namelen); + mdt_lock_pdo_init(parent_lh, LCK_PW, &rr->rr_name); rc = mdt_object_lock(info, mp, parent_lh, MDS_INODELOCK_UPDATE, MDT_LOCAL_LOCK); if (rc) @@ -744,7 +742,7 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, /* step 2: find & lock the child */ /* lookup child object along with version checking */ fid_zero(child_fid); - rc = mdt_lookup_version_check(info, mp, lname, child_fid, 1); + rc = mdt_lookup_version_check(info, mp, &rr->rr_name, child_fid, 1); if (rc != 0) { /* Name might not be able to find during resend of * remote unlink, considering following case. @@ -786,14 +784,14 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, struct mdt_body *repbody; if (!fid_is_zero(rr->rr_fid2)) { - CDEBUG(D_INFO, "%s: name %s can not find "DFID"\n", + CDEBUG(D_INFO, "%s: name "DNAME" cannot find "DFID"\n", mdt_obd_name(info->mti_mdt), - (char *)rr->rr_name, PFID(mdt_object_fid(mc))); + PNAME(&rr->rr_name), PFID(mdt_object_fid(mc))); GOTO(put_child, rc = -ENOENT); } - CDEBUG(D_INFO, "%s: name %s: "DFID" is another MDT\n", + CDEBUG(D_INFO, "%s: name "DNAME": "DFID" is on another MDT\n", mdt_obd_name(info->mti_mdt), - (char *)rr->rr_name, PFID(mdt_object_fid(mc))); + PNAME(&rr->rr_name), PFID(mdt_object_fid(mc))); if (!mdt_is_dne_client(req->rq_export)) /* Return -EIO for old client */ @@ -814,7 +812,7 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, ma->ma_valid = 0; mdt_set_capainfo(info, 1, child_fid, BYPASS_CAPA); rc = mdo_unlink(info->mti_env, mdt_object_child(mp), - NULL, lname, ma, no_name); + NULL, &rr->rr_name, ma, no_name); GOTO(put_child, rc); } /* Revoke the LOOKUP lock of the remote object granted by @@ -831,8 +829,9 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, GOTO(unlock_child, rc = -EREMOTE); } else if (info->mti_spec.sp_rm_entry) { rc = -EPERM; - CDEBUG(D_INFO, "%s: no rm_entry on local dir '%s': rc = %d\n", - mdt_obd_name(info->mti_mdt), (char *)rr->rr_name, rc); + CDEBUG(D_INFO, "%s: no rm_entry on local dir '"DNAME"': " + "rc = %d\n", + mdt_obd_name(info->mti_mdt), PNAME(&rr->rr_name), rc); GOTO(put_child, rc); } @@ -860,7 +859,7 @@ static int mdt_reint_unlink(struct mdt_thread_info *info, mutex_lock(&mc->mot_lov_mutex); rc = mdo_unlink(info->mti_env, mdt_object_child(mp), - mdt_object_child(mc), lname, ma, no_name); + mdt_object_child(mc), &rr->rr_name, ma, no_name); mutex_unlock(&mc->mot_lov_mutex); @@ -915,12 +914,11 @@ static int mdt_reint_link(struct mdt_thread_info *info, struct mdt_object *mp; struct mdt_lock_handle *lhs; struct mdt_lock_handle *lhp; - struct lu_name *lname; int rc; ENTRY; - DEBUG_REQ(D_INODE, req, "link "DFID" to "DFID"/%s", - PFID(rr->rr_fid1), PFID(rr->rr_fid2), rr->rr_name); + DEBUG_REQ(D_INODE, req, "link "DFID" to "DFID"/"DNAME, + PFID(rr->rr_fid1), PFID(rr->rr_fid2), PNAME(&rr->rr_name)); if (OBD_FAIL_CHECK(OBD_FAIL_MDS_REINT_LINK)) RETURN(err_serious(-ENOENT)); @@ -939,8 +937,7 @@ static int mdt_reint_link(struct mdt_thread_info *info, /* step 1: find & lock the target parent dir */ lhp = &info->mti_lh[MDT_LH_PARENT]; - mdt_lock_pdo_init(lhp, LCK_PW, rr->rr_name, - rr->rr_namelen); + mdt_lock_pdo_init(lhp, LCK_PW, &rr->rr_name); mp = mdt_object_find_lock(info, rr->rr_fid2, lhp, MDS_INODELOCK_UPDATE); if (IS_ERR(mp)) @@ -989,24 +986,24 @@ static int mdt_reint_link(struct mdt_thread_info *info, if (rc) GOTO(out_unlock_child, rc); - lname = mdt_name(info->mti_env, (char *)rr->rr_name, rr->rr_namelen); /** check target version by name during replay */ - rc = mdt_lookup_version_check(info, mp, lname, &info->mti_tmp_fid1, 2); + rc = mdt_lookup_version_check(info, mp, &rr->rr_name, + &info->mti_tmp_fid1, 2); if (rc != 0 && rc != -ENOENT) GOTO(out_unlock_child, rc); /* save version of file name for replay, it must be ENOENT here */ if (!req_is_replay(mdt_info_req(info))) { if (rc != -ENOENT) { - CDEBUG(D_INFO, "link target %.*s existed!\n", - rr->rr_namelen, (char *)rr->rr_name); + CDEBUG(D_INFO, "link target "DNAME" existed!\n", + PNAME(&rr->rr_name)); GOTO(out_unlock_child, rc = -EEXIST); } info->mti_ver[2] = ENOENT_VERSION; mdt_version_save(mdt_info_req(info), info->mti_ver[2], 2); } - rc = mdo_link(info->mti_env, mdt_object_child(mp), - mdt_object_child(ms), lname, ma); + rc = mdo_link(info->mti_env, mdt_object_child(mp), + mdt_object_child(ms), &rr->rr_name, ma); if (rc == 0) mdt_counter_incr(req, LPROC_MDT_LINK); @@ -1162,17 +1159,15 @@ static int mdt_reint_rename(struct mdt_thread_info *info, struct lu_fid *old_fid = &info->mti_tmp_fid1; struct lu_fid *new_fid = &info->mti_tmp_fid2; struct lustre_handle rename_lh = { 0 }; - struct lu_name slname = { 0 }; - struct lu_name *lname; int rc; ENTRY; if (info->mti_dlm_req) ldlm_request_cancel(req, info->mti_dlm_req, 0); - DEBUG_REQ(D_INODE, req, "rename "DFID"/%s to "DFID"/%s", - PFID(rr->rr_fid1), rr->rr_name, - PFID(rr->rr_fid2), rr->rr_tgt); + DEBUG_REQ(D_INODE, req, "rename "DFID"/"DNAME" to "DFID"/"DNAME, + PFID(rr->rr_fid1), PNAME(&rr->rr_name), + PFID(rr->rr_fid2), PNAME(&rr->rr_tgt_name)); if (fid_is_obf(rr->rr_fid1) || fid_is_dot_lustre(rr->rr_fid1) || fid_is_obf(rr->rr_fid2) || fid_is_dot_lustre(rr->rr_fid2)) @@ -1188,8 +1183,7 @@ static int mdt_reint_rename(struct mdt_thread_info *info, /* step 1: lock the source dir. */ lh_srcdirp = &info->mti_lh[MDT_LH_PARENT]; - mdt_lock_pdo_init(lh_srcdirp, LCK_PW, rr->rr_name, - rr->rr_namelen); + mdt_lock_pdo_init(lh_srcdirp, LCK_PW, &rr->rr_name); msrcdir = mdt_object_find_lock(info, rr->rr_fid1, lh_srcdirp, MDS_INODELOCK_UPDATE); if (IS_ERR(msrcdir)) @@ -1201,8 +1195,7 @@ static int mdt_reint_rename(struct mdt_thread_info *info, /* step 2: find & lock the target dir. */ lh_tgtdirp = &info->mti_lh[MDT_LH_CHILD]; - mdt_lock_pdo_init(lh_tgtdirp, LCK_PW, rr->rr_tgt, - rr->rr_tgtlen); + mdt_lock_pdo_init(lh_tgtdirp, LCK_PW, &rr->rr_tgt_name); if (lu_fid_eq(rr->rr_fid1, rr->rr_fid2)) { mdt_object_get(info->mti_env, msrcdir); mtgtdir = msrcdir; @@ -1245,16 +1238,14 @@ static int mdt_reint_rename(struct mdt_thread_info *info, } } - /* step 3: find & lock the old object. */ - lname = mdt_name(info->mti_env, (char *)rr->rr_name, rr->rr_namelen); - mdt_name_copy(&slname, lname); - fid_zero(old_fid); - rc = mdt_lookup_version_check(info, msrcdir, &slname, old_fid, 2); - if (rc != 0) - GOTO(out_unlock_target, rc); + /* step 3: find & lock the old object. */ + fid_zero(old_fid); + rc = mdt_lookup_version_check(info, msrcdir, &rr->rr_name, old_fid, 2); + if (rc != 0) + GOTO(out_unlock_target, rc); - if (lu_fid_eq(old_fid, rr->rr_fid1) || lu_fid_eq(old_fid, rr->rr_fid2)) - GOTO(out_unlock_target, rc = -EINVAL); + if (lu_fid_eq(old_fid, rr->rr_fid1) || lu_fid_eq(old_fid, rr->rr_fid2)) + GOTO(out_unlock_target, rc = -EINVAL); if (fid_is_obf(old_fid) || fid_is_dot_lustre(old_fid)) GOTO(out_unlock_target, rc = -EPERM); @@ -1279,10 +1270,10 @@ static int mdt_reint_rename(struct mdt_thread_info *info, /* step 4: find & lock the new object. */ /* new target object may not exist now */ - lname = mdt_name(info->mti_env, (char *)rr->rr_tgt, rr->rr_tgtlen); /* lookup with version checking */ fid_zero(new_fid); - rc = mdt_lookup_version_check(info, mtgtdir, lname, new_fid, 3); + rc = mdt_lookup_version_check(info, mtgtdir, &rr->rr_tgt_name, new_fid, + 3); if (rc == 0) { /* the new_fid should have been filled at this moment */ if (lu_fid_eq(old_fid, new_fid)) @@ -1356,9 +1347,9 @@ static int mdt_reint_rename(struct mdt_thread_info *info, mutex_lock(&mnew->mot_lov_mutex); rc = mdo_rename(info->mti_env, mdt_object_child(msrcdir), - mdt_object_child(mtgtdir), old_fid, &slname, - (mnew ? mdt_object_child(mnew) : NULL), - lname, ma); + mdt_object_child(mtgtdir), old_fid, &rr->rr_name, + mnew != NULL ? mdt_object_child(mnew) : NULL, + &rr->rr_tgt_name, ma); if (mnew != NULL) mutex_unlock(&mnew->mot_lov_mutex); diff --git a/lustre/mdt/mdt_xattr.c b/lustre/mdt/mdt_xattr.c index ecbf3b7..1abef7e 100644 --- a/lustre/mdt/mdt_xattr.c +++ b/lustre/mdt/mdt_xattr.c @@ -368,7 +368,7 @@ int mdt_reint_setxattr(struct mdt_thread_info *info, struct mdt_object *obj; struct md_object *child; __u64 valid = attr->la_valid; - const char *xattr_name = rr->rr_name; + const char *xattr_name = rr->rr_name.ln_name; int xattr_len = rr->rr_eadatalen; __u64 lockpart; int rc; -- 1.8.3.1