can't find the correct one during replay because mfd handle is changed.
Current fix add old_handle field in mfd so during replay it is possible to find
it comparing old handle.
__u32 cr_cap;
__u32 cr_flags; /* for use with open */
__u32 cr_mode;
+ struct lustre_handle cr_old_handle; /* u64 handle in case of open replay */
struct lu_fid cr_fid1;
struct lu_fid cr_fid2;
__u64 cr_time;
__u64 cr_ioepoch;
__u32 cr_suppgid;
__u32 cr_bias;
- __u32 cr_padding_2; /* also fix lustre_swab_mds_rec_create */
- __u32 cr_padding_3; /* also fix lustre_swab_mds_rec_create */
};
extern void lustre_swab_mdt_rec_create (struct mdt_rec_create *cr);
memcpy(&old, file_fh, sizeof(old));
memcpy(file_fh, &body->handle, sizeof(*file_fh));
}
-
close_req = mod->mod_close_req;
+/* XXX comment that out due to old_handle in mfd to solve the same issue */
+#if 0
if (close_req != NULL) {
struct mdt_epoch *epoch;
DEBUG_REQ(D_HA, close_req, "updating close body with new fh");
memcpy(&epoch->handle, &body->handle, sizeof(epoch->handle));
}
-
+#endif
EXIT;
}
rec->cr_fid2 = body->fid1;
rec->cr_ioepoch = body->ioepoch;
+ rec->cr_old_handle.cookie = body->handle.cookie;
open_req->rq_replay_cb = mdc_replay_open;
if (!fid_is_sane(&body->fid1)) {
DEBUG_REQ(D_ERROR, open_req, "Saving replay request with "
__u64 mcd_last_xid; /* xid for the last transaction */
__u32 mcd_last_result; /* result from last RPC */
__u32 mcd_last_data; /* per-op data (disposition for open &c.) */
- /* for MDS_CLOSE requests */
+ /* for MDS_CLOSE and MDS_DONE_WRITTING requests */
__u64 mcd_last_close_transno; /* last completed transaction ID */
__u64 mcd_last_close_xid; /* xid for the last transaction */
__u32 mcd_last_close_result; /* result from last RPC */
struct portals_handle mfd_handle; /* must be first */
struct list_head mfd_list; /* protected by med_open_lock */
__u64 mfd_xid; /* xid of the open request */
+ struct lustre_handle mfd_old_handle; /* old handle in replay case */
int mfd_mode; /* open mode provided by client */
struct mdt_object *mfd_object; /* point to opened object */
};
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 mdt_reint_open(struct mdt_thread_info *info,
struct mdt_lock_handle *lhc);
-struct mdt_file_data *mdt_handle2mfd(const struct lustre_handle *handle);
+struct mdt_file_data *mdt_handle2mfd(struct mdt_thread_info *,
+ const struct lustre_handle *);
int mdt_epoch_open(struct mdt_thread_info *info, struct mdt_object *o);
void mdt_sizeonmds_enable(struct mdt_thread_info *info, struct mdt_object *mo);
int mdt_sizeonmds_enabled(struct mdt_object *mo);
rr->rr_fid1 = &rec->cr_fid1;
rr->rr_fid2 = &rec->cr_fid2;
+ rr->rr_handle = &rec->cr_old_handle;
attr->la_mode = rec->cr_mode;
attr->la_rdev = rec->cr_rdev;
attr->la_uid = rec->cr_fsuid;
RETURN(mfd);
}
-/* Find the mfd pointed to by handle in global hash table. */
-struct mdt_file_data *mdt_handle2mfd(const struct lustre_handle *handle)
+/*
+ * Find the mfd pointed to by handle in global hash table.
+ * In case of replay the handle is obsoleted
+ * but mfd can be found in mfd list by that handle
+ */
+struct mdt_file_data *mdt_handle2mfd(struct mdt_thread_info *info,
+ const struct lustre_handle *handle)
{
+ struct ptlrpc_request *req = mdt_info_req(info);
+ struct mdt_file_data *mfd;
+
ENTRY;
LASSERT(handle != NULL);
- RETURN(class_handle2object(handle->cookie));
+ if (lustre_msg_get_flags(req->rq_reqmsg) & MSG_REPLAY) {
+ struct mdt_export_data *med = &req->rq_export->exp_mdt_data;
+ list_for_each_entry(mfd, &med->med_open_head, mfd_list) {
+ if (mfd->mfd_old_handle.cookie == handle->cookie)
+ RETURN (mfd);
+ }
+ mfd = NULL;
+ } else {
+ mfd = class_handle2object(handle->cookie);
+ }
+ RETURN (mfd);
}
/* free mfd */
mfd->mfd_mode = flags;
mfd->mfd_object = o;
mfd->mfd_xid = req->rq_xid;
-
+ /* replay handle */
+ if (info->mti_rr.rr_handle)
+ mfd->mfd_old_handle = *info->mti_rr.rr_handle;
spin_lock(&med->med_open_lock);
list_add(&mfd->mfd_list, &med->med_open_head);
spin_unlock(&med->med_open_lock);
med = &mdt_info_req(info)->rq_export->exp_mdt_data;
spin_lock(&med->med_open_lock);
- mfd = mdt_handle2mfd(&(info->mti_epoch->handle));
+ mfd = mdt_handle2mfd(info, &info->mti_epoch->handle);
if (mdt_mfd_closed(mfd)) {
spin_unlock(&med->med_open_lock);
+
CDEBUG(D_INODE, "no handle for file close: fid = "DFID
": cookie = "LPX64"\n", PFID(info->mti_rr.rr_fid1),
info->mti_epoch->handle.cookie);
med = &mdt_info_req(info)->rq_export->exp_mdt_data;
spin_lock(&med->med_open_lock);
- mfd = mdt_handle2mfd(&(info->mti_epoch->handle));
+ mfd = mdt_handle2mfd(info, &info->mti_epoch->handle);
if (mfd == NULL) {
spin_unlock(&med->med_open_lock);
CDEBUG(D_INODE, "no handle for file close: fid = "DFID
if (info->mti_epoch && (info->mti_epoch->flags & MF_SOM_CHANGE)) {
LASSERT(info->mti_epoch);
- /* Size-on-MDS Update. Find and free mfd. */
spin_lock(&med->med_open_lock);
- mfd = mdt_handle2mfd(&(info->mti_epoch->handle));
+ /* Size-on-MDS Update. Find and free mfd. */
+ mfd = mdt_handle2mfd(info, &info->mti_epoch->handle);
if (mfd == NULL) {
spin_unlock(&med->med_open_lock);
CDEBUG(D_INODE, "no handle for file close: "
- "fid = "DFID": cookie = "LPX64"\n",
- PFID(info->mti_rr.rr_fid1),
- info->mti_epoch->handle.cookie);
+ "fid = "DFID": cookie = "LPX64"\n",
+ PFID(info->mti_rr.rr_fid1),
+ info->mti_epoch->handle.cookie);
GOTO(out_put, rc = -ESTALE);
}
-
LASSERT(mfd->mfd_mode == FMODE_SOM);
LASSERT(ma->ma_attr.la_valid & LA_SIZE);
LASSERT(!(info->mti_epoch->flags & MF_EPOCH_CLOSE));
class_handle_unhash(&mfd->mfd_handle);
list_del_init(&mfd->mfd_list);
spin_unlock(&med->med_open_lock);
+
mdt_mfd_close(info, mfd);
}
__swab32s (&cr->cr_cap);
__swab32s (&cr->cr_flags); /* for use with open */
__swab32s (&cr->cr_mode);
+ /* handle is opaque */
lustre_swab_lu_fid (&cr->cr_fid1);
lustre_swab_lu_fid (&cr->cr_fid2);
__swab64s (&cr->cr_time);
__swab64s (&cr->cr_ioepoch);
__swab32s (&cr->cr_suppgid);
__swab32s (&cr->cr_bias);
- CLASSERT(offsetof(typeof(*cr), cr_padding_2) != 0);
- CLASSERT(offsetof(typeof(*cr), cr_padding_3) != 0);
}
void lustre_swab_mds_rec_link (struct mds_rec_link *lk)