return o->do_ops->do_object_sync(env, o, start, end);
}
+static inline int dt_fid_alloc(const struct lu_env *env,
+ struct dt_device *d,
+ struct lu_fid *fid,
+ struct lu_object *parent,
+ const struct lu_name *name)
+{
+ struct lu_device *l = dt2lu_dev(d);
+
+ return l->ld_ops->ldo_fid_alloc(env, l, fid, parent, name);
+}
+
int dt_declare_version_set(const struct lu_env *env, struct dt_object *o,
struct thandle *th);
void dt_version_set(const struct lu_env *env, struct dt_object *o,
struct lu_object_header;
struct lu_context;
struct lu_env;
+struct lu_name;
/**
* Operations common for data and meta-data devices.
struct lu_device *parent,
struct lu_device *dev);
+
+ /**
+ * Allocate new FID for file with @name under @parent
+ *
+ * \param[in] env execution environment for this thread
+ * \param[in] dev dt device
+ * \param[out] fid new FID allocated
+ * \param[in] parent parent object
+ * \param[in] name lu_name
+ *
+ * \retval 0 on success
+ * \retval 0 0 FID allocated successfully.
+ * \retval 1 1 FID allocated successfully and new sequence
+ * requested from seq meta server
+ * \retval negative negative errno if FID allocation failed.
+ */
+ int (*ldo_fid_alloc)(const struct lu_env *env,
+ struct lu_device *dev,
+ struct lu_fid *fid,
+ struct lu_object *parent,
+ const struct lu_name *name);
};
/**
#include <uapi/linux/lustre/lustre_param.h>
#include <lustre_update.h>
#include <lustre_log.h>
+#include <lustre_lmv.h>
#include "lod_internal.h"
RETURN(rc);
}
+/**
+ * Implementation of lu_device_operations::ldo_fid_alloc() for LOD
+ *
+ * Find corresponding device by passed parent and name, and allocate FID from
+ * there.
+ *
+ * see include/lu_object.h for the details.
+ */
+static int lod_fid_alloc(const struct lu_env *env, struct lu_device *d,
+ struct lu_fid *fid, struct lu_object *parent,
+ const struct lu_name *name)
+{
+ struct lod_device *lod = lu2lod_dev(d);
+ struct lod_object *lo = lu2lod_obj(parent);
+ struct dt_device *next;
+ int rc;
+
+ ENTRY;
+
+ /* if @parent is remote, we don't know whether its layout was changed,
+ * always reload layout.
+ */
+ if (lu_object_remote(parent))
+ lod_striping_free(env, lo);
+
+ rc = lod_striping_load(env, lo);
+ if (rc)
+ RETURN(rc);
+
+ if (lo->ldo_dir_stripe_count > 0 && name) {
+ struct dt_object *stripe;
+ int idx;
+
+ idx = __lmv_name_to_stripe_index(lo->ldo_dir_hash_type,
+ lo->ldo_dir_stripe_count,
+ lo->ldo_dir_migrate_hash,
+ lo->ldo_dir_migrate_offset,
+ name->ln_name,
+ name->ln_namelen, true);
+ if (idx < 0)
+ RETURN(idx);
+
+ stripe = lo->ldo_stripe[idx];
+ if (!stripe || !dt_object_exists(stripe))
+ RETURN(-ENODEV);
+
+ next = lu2dt_dev(stripe->do_lu.lo_dev);
+ } else {
+ next = lod->lod_child;
+ }
+
+ rc = dt_fid_alloc(env, next, fid, parent, name);
+
+ RETURN(rc);
+}
+
const struct lu_device_operations lod_lu_ops = {
.ldo_object_alloc = lod_object_alloc,
.ldo_process_config = lod_process_config,
.ldo_recovery_complete = lod_recovery_complete,
.ldo_prepare = lod_prepare,
+ .ldo_fid_alloc = lod_fid_alloc,
};
/**
if (idx == master_index) {
/* Allocate the FID locally */
- rc = obd_fid_alloc(env, lod->lod_child_exp,
- &fid, NULL);
+ tgt_dt = lod->lod_child;
+ rc = dt_fid_alloc(env, tgt_dt, &fid, NULL,
+ NULL);
if (rc < 0)
continue;
- tgt_dt = lod->lod_child;
break;
}
/* this OSP doesn't feel well */
continue;
- rc = obd_fid_alloc(env, tgt->ltd_exp, &fid, NULL);
+ rc = dt_fid_alloc(env, tgt_dt, &fid, NULL, NULL);
if (rc < 0)
continue;
RETURN(-ENOMEM);
/* Allocate the first stripe locally */
- rc = obd_fid_alloc(env, lod->lod_child_exp, &fid, NULL);
+ rc = dt_fid_alloc(env, lod->lod_child, &fid, NULL, NULL);
if (rc < 0)
GOTO(out, rc);
}
spin_unlock(&lqr->lqr_alloc);
- rc = obd_fid_alloc(env, mdt->ltd_exp, &fid, NULL);
+ rc = dt_fid_alloc(env, mdt->ltd_tgt, &fid, NULL, NULL);
if (rc < 0) {
QOS_DEBUG("#%d: alloc FID failed: %dl\n", mdt_idx, rc);
spin_lock(&lqr->lqr_alloc);
if (lod_qos_is_tgt_used(env, mdt_idx, stripe_idx))
continue;
- rc2 = obd_fid_alloc(env, mdt->ltd_exp, &fid, NULL);
+ rc2 = dt_fid_alloc(env, mdt->ltd_tgt, &fid, NULL, NULL);
if (rc2 < 0) {
QOS_DEBUG("can't alloc FID on #%u: %d\n",
mdt_idx, rc2);
return rc;
}
+/**
+ * Implementation of lu_device_operations::ldo_fid_alloc() for MDD.
+ *
+ * Find corresponding device by passed parent and name, and allocate FID from
+ * there.
+ *
+ * see include/lu_object.h for the details.
+ */
+static int mdd_fid_alloc(const struct lu_env *env, struct lu_device *d,
+ struct lu_fid *fid, struct lu_object *parent,
+ const struct lu_name *name)
+{
+ struct mdd_device *mdd = lu2mdd_dev(d);
+ struct lu_object *o = lu_object_next(parent);
+
+ return dt_fid_alloc(env, mdd->mdd_child, fid, o, name);
+}
+
const struct lu_device_operations mdd_lu_ops = {
.ldo_object_alloc = mdd_object_alloc,
.ldo_process_config = mdd_process_config,
.ldo_recovery_complete = mdd_recovery_complete,
.ldo_prepare = mdd_prepare,
+ .ldo_fid_alloc = mdd_fid_alloc,
};
static int mdd_root_get(const struct lu_env *env,
} else {
/* If logid == NULL, then it means the caller needs
* to allocate new FID (llog_cat_declare_add_rec()). */
- rc = obd_fid_alloc(env, ctxt->loc_exp,
- &lgi->lgi_fid, NULL);
+ rc = dt_fid_alloc(env, dt, &lgi->lgi_fid, NULL, NULL);
if (rc < 0)
RETURN(rc);
rc = 0;
RETURN(result);
}
-static int osd_fid_alloc(const struct lu_env *env, struct obd_export *exp,
- struct lu_fid *fid, struct md_op_data *op_data)
+/**
+ * Implementation of lu_device_operations::ldo_fid_alloc() for OSD
+ *
+ * Allocate FID.
+ *
+ * see include/lu_object.h for the details.
+ */
+static int osd_fid_alloc(const struct lu_env *env, struct lu_device *d,
+ struct lu_fid *fid, struct lu_object *parent,
+ const struct lu_name *name)
{
- struct osd_device *osd = osd_dev(exp->exp_obd->obd_lu_dev);
+ struct osd_device *osd = osd_dev(d);
return seq_client_alloc_fid(env, osd->od_cl_seq, fid);
}
.ldo_process_config = osd_process_config,
.ldo_recovery_complete = osd_recovery_complete,
.ldo_prepare = osd_prepare,
+ .ldo_fid_alloc = osd_fid_alloc,
};
static const struct lu_device_type_operations osd_device_type_ops = {
.o_owner = THIS_MODULE,
.o_connect = osd_obd_connect,
.o_disconnect = osd_obd_disconnect,
- .o_fid_alloc = osd_fid_alloc,
.o_health_check = osd_health_check,
};
RETURN(rc);
}
+/**
+ * Implementation of lu_device_operations::ldo_fid_alloc() for OSD
+ *
+ * Allocate FID.
+ *
+ * see include/lu_object.h for the details.
+ */
+static int osd_fid_alloc(const struct lu_env *env, struct lu_device *d,
+ struct lu_fid *fid, struct lu_object *parent,
+ const struct lu_name *name)
+{
+ struct osd_device *osd = osd_dev(d);
+
+ return seq_client_alloc_fid(env, osd->od_cl_seq, fid);
+}
+
struct lu_device_operations osd_lu_ops = {
.ldo_object_alloc = osd_object_alloc,
.ldo_process_config = osd_process_config,
.ldo_recovery_complete = osd_recovery_complete,
.ldo_prepare = osd_prepare,
+ .ldo_fid_alloc = osd_fid_alloc,
};
static void osd_type_start(struct lu_device_type *t)
{
}
-int osd_fid_alloc(const struct lu_env *env, struct obd_export *exp,
- struct lu_fid *fid, struct md_op_data *op_data)
-{
- struct osd_device *osd = osd_dev(exp->exp_obd->obd_lu_dev);
-
- return seq_client_alloc_fid(env, osd->od_cl_seq, fid);
-}
-
static struct lu_device_type_operations osd_device_type_ops = {
.ldto_init = osd_type_init,
.ldto_fini = osd_type_fini,
.o_owner = THIS_MODULE,
.o_connect = osd_obd_connect,
.o_disconnect = osd_obd_disconnect,
- .o_fid_alloc = osd_fid_alloc
};
static int __init osd_init(void)
RETURN(0);
}
+/**
+ * Implementation of lu_device_operations::ldo_fid_alloc() for OSP
+ *
+ * Allocate FID from remote MDT.
+ *
+ * see include/lu_object.h for the details.
+ */
+static int osp_fid_alloc(const struct lu_env *env, struct lu_device *d,
+ struct lu_fid *fid, struct lu_object *parent,
+ const struct lu_name *name)
+{
+ struct osp_device *osp = lu2osp_dev(d);
+ struct client_obd *cli = &osp->opd_obd->u.cli;
+ struct lu_client_seq *seq = cli->cl_seq;
+ int rc;
+
+ ENTRY;
+
+ /* Sigh, fid client is not ready yet */
+ if (!osp->opd_obd->u.cli.cl_seq)
+ RETURN(-ENOTCONN);
+
+ if (!osp->opd_obd->u.cli.cl_seq->lcs_exp)
+ RETURN(-ENOTCONN);
+
+ rc = seq_client_alloc_fid(env, seq, fid);
+
+ RETURN(rc);
+}
+
const struct lu_device_operations osp_lu_ops = {
.ldo_object_alloc = osp_object_alloc,
.ldo_process_config = osp_process_config,
.ldo_recovery_complete = osp_recovery_complete,
+ .ldo_fid_alloc = osp_fid_alloc,
};
/**
RETURN(0);
}
-/**
- * Implementation of obd_ops: o_fid_alloc
- *
- * Allocate a FID. There are two cases in which OSP performs
- * FID allocation.
- *
- * 1. FID precreation for data objects, which is done in
- * osp_precreate_fids() instead of this function.
- * 2. FID allocation for each sub-stripe of a striped directory.
- * Similar to other FID clients, OSP requests the sequence
- * from its corresponding remote MDT, which in turn requests
- * sequences from the sequence controller (MDT0).
- *
- * \param[in] env execution environment
- * \param[in] exp export of the OSP
- * \param[out] fid FID being allocated
- * \param[in] unused necessary for the interface but unused.
- *
- * \retval 0 0 FID allocated successfully.
- * \retval 1 1 FID allocated successfully and new sequence
- * requested from seq meta server
- * \retval negative negative errno if FID allocation failed.
- */
-static int osp_fid_alloc(const struct lu_env *env, struct obd_export *exp,
- struct lu_fid *fid, struct md_op_data *unused)
-{
- struct client_obd *cli = &exp->exp_obd->u.cli;
- struct osp_device *osp = lu2osp_dev(exp->exp_obd->obd_lu_dev);
- struct lu_client_seq *seq = cli->cl_seq;
- ENTRY;
-
- LASSERT(osp->opd_obd->u.cli.cl_seq != NULL);
- /* Sigh, fid client is not ready yet */
- LASSERT(osp->opd_obd->u.cli.cl_seq->lcs_exp != NULL);
-
- RETURN(seq_client_alloc_fid(env, seq, fid));
-}
-
/* context key constructor/destructor: mdt_key_init, mdt_key_fini */
LU_KEY_INIT_FINI(osp, struct osp_thread_info);
static void osp_key_exit(const struct lu_context *ctx,
.o_statfs = osp_obd_statfs,
.o_fid_init = client_fid_init,
.o_fid_fini = client_fid_fini,
- .o_fid_alloc = osp_fid_alloc,
};
/**