};
struct echo_object {
- struct cl_object eo_cl;
- struct cl_object_header eo_hdr;
-
- struct echo_device *eo_dev;
+ struct cl_object eo_cl;
+ struct cl_object_header eo_hdr;
+ struct echo_device *eo_dev;
struct list_head eo_obj_chain;
- struct lov_stripe_md *eo_lsm;
+ struct lov_oinfo *eo_oinfo;
atomic_t eo_npages;
- int eo_deleted;
+ int eo_deleted;
};
struct echo_object_conf {
- struct cl_object_conf eoc_cl;
- struct lov_stripe_md **eoc_md;
+ struct cl_object_conf eoc_cl;
+ struct lov_oinfo **eoc_oinfo;
};
struct echo_page {
/** @} echo_helpers */
-static struct echo_object *cl_echo_object_find(struct echo_device *d,
- struct lov_stripe_md **lsm);
static int cl_echo_object_put(struct echo_object *eco);
static int cl_echo_object_brw(struct echo_object *eco, int rw, obd_off offset,
struct page **pages, int npages, int async);
const struct cl_object_conf *cconf = lu2cl_conf(conf);
struct echo_object_conf *econf = cl2echo_conf(cconf);
- LASSERT(econf->eoc_md);
- eco->eo_lsm = *econf->eoc_md;
- /* clear the lsm pointer so that it won't get freed. */
- *econf->eoc_md = NULL;
- } else {
- eco->eo_lsm = NULL;
- }
+ LASSERT(econf->eoc_oinfo != NULL);
+
+ /* Transfer the oinfo pointer to eco that it won't be
+ * freed. */
+ eco->eo_oinfo = *econf->eoc_oinfo;
+ *econf->eoc_oinfo = NULL;
+ } else {
+ eco->eo_oinfo = NULL;
+ }
eco->eo_dev = ed;
atomic_set(&eco->eo_npages, 0);
RETURN(0);
}
-/* taken from osc_unpackmd() */
-static int echo_alloc_memmd(struct echo_device *ed,
- struct lov_stripe_md **lsmp)
-{
- int lsm_size;
-
- ENTRY;
-
- /* If export is lov/osc then use their obd method */
- if (ed->ed_next != NULL)
- return obd_alloc_memmd(ed->ed_ec->ec_exp, lsmp);
- /* OFD has no unpackmd method, do everything here */
- lsm_size = lov_stripe_md_size(1);
-
- LASSERT(*lsmp == NULL);
- OBD_ALLOC(*lsmp, lsm_size);
- if (*lsmp == NULL)
- RETURN(-ENOMEM);
-
- OBD_ALLOC((*lsmp)->lsm_oinfo[0], sizeof(struct lov_oinfo));
- if ((*lsmp)->lsm_oinfo[0] == NULL) {
- OBD_FREE(*lsmp, lsm_size);
- RETURN(-ENOMEM);
- }
-
- loi_init((*lsmp)->lsm_oinfo[0]);
- (*lsmp)->lsm_maxbytes = LUSTRE_EXT3_STRIPE_MAXBYTES;
- ostid_set_seq_echo(&(*lsmp)->lsm_oi);
-
- RETURN(lsm_size);
-}
-
-static int echo_free_memmd(struct echo_device *ed, struct lov_stripe_md **lsmp)
-{
- int lsm_size;
-
- ENTRY;
-
- /* If export is lov/osc then use their obd method */
- if (ed->ed_next != NULL)
- return obd_free_memmd(ed->ed_ec->ec_exp, lsmp);
- /* OFD has no unpackmd method, do everything here */
- lsm_size = lov_stripe_md_size(1);
-
- LASSERT(*lsmp != NULL);
- OBD_FREE((*lsmp)->lsm_oinfo[0], sizeof(struct lov_oinfo));
- OBD_FREE(*lsmp, lsm_size);
- *lsmp = NULL;
- RETURN(0);
-}
-
static void echo_object_free(const struct lu_env *env, struct lu_object *obj)
{
struct echo_object *eco = cl2echo_obj(lu2cl(obj));
lu_object_fini(obj);
lu_object_header_fini(obj->lo_header);
- if (eco->eo_lsm)
- echo_free_memmd(eco->eo_dev, &eco->eo_lsm);
+ if (eco->eo_oinfo != NULL)
+ OBD_FREE_PTR(eco->eo_oinfo);
+
OBD_SLAB_FREE_PTR(eco, echo_object_kmem);
EXIT;
}
*/
/* Interfaces to echo client obd device */
-static struct echo_object *cl_echo_object_find(struct echo_device *d,
- struct lov_stripe_md **lsmp)
+static struct echo_object *
+cl_echo_object_find(struct echo_device *d, const struct ost_id *oi)
{
- struct lu_env *env;
- struct echo_thread_info *info;
- struct echo_object_conf *conf;
- struct lov_stripe_md *lsm;
- struct echo_object *eco;
- struct cl_object *obj;
- struct lu_fid *fid;
- int refcheck;
+ struct lu_env *env;
+ struct echo_thread_info *info;
+ struct echo_object_conf *conf;
+ struct echo_object *eco;
+ struct cl_object *obj;
+ struct lov_oinfo *oinfo = NULL;
+ struct lu_fid *fid;
+ int refcheck;
int rc;
ENTRY;
- LASSERT(lsmp);
- lsm = *lsmp;
- LASSERT(lsm);
- LASSERTF(ostid_id(&lsm->lsm_oi) != 0, DOSTID"\n", POSTID(&lsm->lsm_oi));
- LASSERTF(ostid_seq(&lsm->lsm_oi) == FID_SEQ_ECHO, DOSTID"\n",
- POSTID(&lsm->lsm_oi));
+ LASSERTF(ostid_id(oi) != 0, DOSTID"\n", POSTID(oi));
+ LASSERTF(ostid_seq(oi) == FID_SEQ_ECHO, DOSTID"\n", POSTID(oi));
/* Never return an object if the obd is to be freed. */
if (echo_dev2cl(d)->cd_lu_dev.ld_obd->obd_stopping)
info = echo_env_info(env);
conf = &info->eti_conf;
if (d->ed_next) {
- struct lov_oinfo *oinfo = lsm->lsm_oinfo[0];
+ OBD_ALLOC_PTR(oinfo);
+ if (oinfo == NULL)
+ GOTO(out, eco = ERR_PTR(-ENOMEM));
- LASSERT(oinfo != NULL);
- oinfo->loi_oi = lsm->lsm_oi;
+ oinfo->loi_oi = *oi;
conf->eoc_cl.u.coc_oinfo = oinfo;
- }
- conf->eoc_md = lsmp;
+ }
+
+ /* If echo_object_init() is successful then ownership of oinfo
+ * is transferred to the object. */
+ conf->eoc_oinfo = &oinfo;
- fid = &info->eti_fid;
- rc = ostid_to_fid(fid, &lsm->lsm_oi, 0);
+ fid = &info->eti_fid;
+ rc = ostid_to_fid(fid, oi, 0);
if (rc != 0)
GOTO(out, eco = ERR_PTR(rc));
}
out:
+ if (oinfo != NULL)
+ OBD_FREE_PTR(oinfo);
+
cl_env_put(env, &refcheck);
RETURN(eco);
}
static int echo_create_object(const struct lu_env *env, struct echo_device *ed,
struct obdo *oa, struct obd_trans_info *oti)
{
- struct echo_object *eco;
- struct echo_client_obd *ec = ed->ed_ec;
- struct lov_stripe_md *lsm = NULL;
- int rc;
- int created = 0;
- ENTRY;
-
- if ((oa->o_valid & OBD_MD_FLID) == 0) { /* no obj id */
- CERROR ("No valid oid\n");
- RETURN(-EINVAL);
- }
-
- rc = echo_alloc_memmd(ed, &lsm);
- if (rc < 0) {
- CERROR("Cannot allocate md: rc = %d\n", rc);
- GOTO(failed, rc);
- }
+ struct echo_object *eco;
+ struct echo_client_obd *ec = ed->ed_ec;
+ int created = 0;
+ int rc;
+ ENTRY;
- /* setup object ID here */
- if (oa->o_valid & OBD_MD_FLID) {
- LASSERT(oa->o_valid & OBD_MD_FLGROUP);
- lsm->lsm_oi = oa->o_oi;
+ if (!(oa->o_valid & OBD_MD_FLID) ||
+ !(oa->o_valid & OBD_MD_FLGROUP) ||
+ !fid_seq_is_echo(ostid_seq(&oa->o_oi))) {
+ CERROR("invalid oid "DOSTID"\n", POSTID(&oa->o_oi));
+ RETURN(-EINVAL);
}
- if (ostid_id(&lsm->lsm_oi) == 0)
- ostid_set_id(&lsm->lsm_oi, ++last_object_id);
+ if (ostid_id(&oa->o_oi) == 0)
+ ostid_set_id(&oa->o_oi, ++last_object_id);
- /* Only echo objects are allowed to be created */
- LASSERT((oa->o_valid & OBD_MD_FLGROUP) &&
- (ostid_seq(&oa->o_oi) == FID_SEQ_ECHO));
-
- rc = obd_create(env, ec->ec_exp, oa, &lsm, oti);
+ rc = obd_create(env, ec->ec_exp, oa, oti);
if (rc != 0) {
CERROR("Cannot create objects: rc = %d\n", rc);
GOTO(failed, rc);
created = 1;
- /* See what object ID we were given */
- oa->o_oi = lsm->lsm_oi;
- oa->o_valid |= OBD_MD_FLID;
+ oa->o_valid |= OBD_MD_FLID;
- eco = cl_echo_object_find(ed, &lsm);
+ eco = cl_echo_object_find(ed, &oa->o_oi);
if (IS_ERR(eco))
GOTO(failed, rc = PTR_ERR(eco));
cl_echo_object_put(eco);
CDEBUG(D_INFO, "oa oid "DOSTID"\n", POSTID(&oa->o_oi));
EXIT;
- failed:
- if (created && rc)
- obd_destroy(env, ec->ec_exp, oa, lsm, oti, NULL, NULL);
- if (lsm)
- echo_free_memmd(ed, &lsm);
- if (rc)
- CERROR("create object failed with: rc = %d\n", rc);
- return (rc);
+failed:
+ if (created && rc != 0)
+ obd_destroy(env, ec->ec_exp, oa, NULL, oti, NULL, NULL);
+
+ if (rc != 0)
+ CERROR("create object failed with: rc = %d\n", rc);
+
+ return rc;
}
static int echo_get_object(struct echo_object **ecop, struct echo_device *ed,
- struct obdo *oa)
+ struct obdo *oa)
{
- struct lov_stripe_md *lsm = NULL;
- struct echo_object *eco;
- int rc;
- ENTRY;
+ struct echo_object *eco;
+ int rc;
+ ENTRY;
- if ((oa->o_valid & OBD_MD_FLID) == 0 || ostid_id(&oa->o_oi) == 0) {
- /* disallow use of object id 0 */
- CERROR ("No valid oid\n");
- RETURN(-EINVAL);
- }
+ if (!(oa->o_valid & OBD_MD_FLID) ||
+ !(oa->o_valid & OBD_MD_FLGROUP) ||
+ ostid_id(&oa->o_oi) == 0) {
+ CERROR("invalid oid "DOSTID"\n", POSTID(&oa->o_oi));
+ RETURN(-EINVAL);
+ }
- rc = echo_alloc_memmd(ed, &lsm);
- if (rc < 0)
- RETURN(rc);
+ rc = 0;
+ eco = cl_echo_object_find(ed, &oa->o_oi);
+ if (!IS_ERR(eco))
+ *ecop = eco;
+ else
+ rc = PTR_ERR(eco);
- lsm->lsm_oi = oa->o_oi;
- if (!(oa->o_valid & OBD_MD_FLGROUP))
- ostid_set_seq_echo(&lsm->lsm_oi);
-
- rc = 0;
- eco = cl_echo_object_find(ed, &lsm);
- if (!IS_ERR(eco))
- *ecop = eco;
- else
- rc = PTR_ERR(eco);
- if (lsm)
- echo_free_memmd(ed, &lsm);
- RETURN(rc);
+ RETURN(rc);
}
static void echo_put_object(struct echo_object *eco)
static int brw_interpret(const struct lu_env *env, struct ptlrpc_request *req,
void *data, int rc);
-/* Unpack OSC object metadata from disk storage (LE byte order). */
-static int osc_unpackmd(struct obd_export *exp, struct lov_stripe_md **lsmp,
- struct lov_mds_md *lmm, int lmm_bytes)
-{
- int lsm_size;
- struct obd_import *imp = class_exp2cliimp(exp);
- ENTRY;
-
- if (lmm != NULL) {
- if (lmm_bytes < sizeof(*lmm)) {
- CERROR("%s: lov_mds_md too small: %d, need %d\n",
- exp->exp_obd->obd_name, lmm_bytes,
- (int)sizeof(*lmm));
- RETURN(-EINVAL);
- }
- /* XXX LOV_MAGIC etc check? */
-
- if (unlikely(ostid_id(&lmm->lmm_oi) == 0)) {
- CERROR("%s: zero lmm_object_id: rc = %d\n",
- exp->exp_obd->obd_name, -EINVAL);
- RETURN(-EINVAL);
- }
- }
-
- lsm_size = lov_stripe_md_size(1);
- if (lsmp == NULL)
- RETURN(lsm_size);
-
- if (*lsmp != NULL && lmm == NULL) {
- OBD_FREE((*lsmp)->lsm_oinfo[0], sizeof(struct lov_oinfo));
- OBD_FREE(*lsmp, lsm_size);
- *lsmp = NULL;
- RETURN(0);
- }
-
- if (*lsmp == NULL) {
- OBD_ALLOC(*lsmp, lsm_size);
- if (unlikely(*lsmp == NULL))
- RETURN(-ENOMEM);
- OBD_ALLOC((*lsmp)->lsm_oinfo[0], sizeof(struct lov_oinfo));
- if (unlikely((*lsmp)->lsm_oinfo[0] == NULL)) {
- OBD_FREE(*lsmp, lsm_size);
- RETURN(-ENOMEM);
- }
- loi_init((*lsmp)->lsm_oinfo[0]);
- } else if (unlikely(ostid_id(&(*lsmp)->lsm_oi) == 0)) {
- RETURN(-EBADF);
- }
-
- if (lmm != NULL)
- /* XXX zero *lsmp? */
- ostid_le_to_cpu(&lmm->lmm_oi, &(*lsmp)->lsm_oi);
-
- if (imp != NULL &&
- (imp->imp_connect_data.ocd_connect_flags & OBD_CONNECT_MAXBYTES))
- (*lsmp)->lsm_maxbytes = imp->imp_connect_data.ocd_maxbytes;
- else
- (*lsmp)->lsm_maxbytes = LUSTRE_EXT3_STRIPE_MAXBYTES;
-
- RETURN(lsm_size);
-}
-
static inline void osc_pack_capa(struct ptlrpc_request *req,
struct ost_body *body, void *capa)
{
oinfo->oi_cb_up, oinfo, rqset);
}
-int osc_real_create(struct obd_export *exp, struct obdo *oa,
- struct lov_stripe_md **ea, struct obd_trans_info *oti)
+static int osc_create(const struct lu_env *env, struct obd_export *exp,
+ struct obdo *oa, struct obd_trans_info *oti)
{
struct ptlrpc_request *req;
struct ost_body *body;
- struct lov_stripe_md *lsm;
int rc;
ENTRY;
- LASSERT(oa);
- LASSERT(ea);
-
- lsm = *ea;
- if (!lsm) {
- rc = obd_alloc_memmd(exp, &lsm);
- if (rc < 0)
- RETURN(rc);
- }
+ LASSERT(oa != NULL);
+ LASSERT(oa->o_valid & OBD_MD_FLGROUP);
+ LASSERT(fid_seq_is_echo(ostid_seq(&oa->o_oi)));
req = ptlrpc_request_alloc(class_exp2cliimp(exp), &RQF_OST_CREATE);
if (req == NULL)
oa->o_blksize = cli_brw_size(exp->exp_obd);
oa->o_valid |= OBD_MD_FLBLKSZ;
- /* XXX LOV STACKING: the lsm that is passed to us from LOV does not
- * have valid lsm_oinfo data structs, so don't go touching that.
- * This needs to be fixed in a big way.
- */
- lsm->lsm_oi = oa->o_oi;
- *ea = lsm;
-
if (oti != NULL) {
if (oa->o_valid & OBD_MD_FLCOOKIE) {
if (oti->oti_logcookies == NULL)
out_req:
ptlrpc_req_finished(req);
out:
- if (rc && !*ea)
- obd_free_memmd(exp, &lsm);
- RETURN(rc);
+ RETURN(rc);
}
int osc_punch_base(struct obd_export *exp, struct obd_info *oinfo,
return 0;
}
-int osc_create(const struct lu_env *env, struct obd_export *exp,
- struct obdo *oa, struct lov_stripe_md **ea,
- struct obd_trans_info *oti)
-{
- int rc = 0;
- ENTRY;
-
- LASSERT(oa);
- LASSERT(ea);
- LASSERT(oa->o_valid & OBD_MD_FLGROUP);
-
- if (!fid_seq_is_mdt(ostid_seq(&oa->o_oi)))
- RETURN(osc_real_create(exp, oa, ea, oti));
-
- /* we should not get here anymore */
- LBUG();
-
- RETURN(rc);
-}
-
/* Destroy requests can be async always on the client, and we don't even really
* care about the return code since the client cannot do anything at all about
* a destroy failure.
.o_disconnect = osc_disconnect,
.o_statfs = osc_statfs,
.o_statfs_async = osc_statfs_async,
- .o_unpackmd = osc_unpackmd,
.o_create = osc_create,
.o_destroy = osc_destroy,
.o_getattr = osc_getattr,