X-Git-Url: https://git.whamcloud.com/?a=blobdiff_plain;f=lustre%2Fmdd%2Fmdd_lov.c;h=e9a1417126ffff23b977c1cd55a0769231e42571;hb=22464d1230ed58461f51d881f512d5e16644a735;hp=9638327ab9aca85801f61dc95b1d28d231e13bbd;hpb=3c55f5cf85fbb790dfea40f3da76d7b0d17f29ba;p=fs%2Flustre-release.git diff --git a/lustre/mdd/mdd_lov.c b/lustre/mdd/mdd_lov.c index 9638327..e9a1417 100644 --- a/lustre/mdd/mdd_lov.c +++ b/lustre/mdd/mdd_lov.c @@ -28,6 +28,9 @@ /* * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved. * Use is subject to license terms. + * + * Copyright (c) 2011 Whamcloud, Inc. + * */ /* * This file is part of Lustre, http://www.lustre.org/ @@ -118,11 +121,11 @@ int mdd_init_obd(const struct lu_env *env, struct mdd_device *mdd, if (!bufs) GOTO(cleanup_mem, rc = -ENOMEM); - snprintf(name, strlen(MDD_OBD_NAME) + 35, "%s-%s-%d", - MDD_OBD_NAME, dev, mds_id); + snprintf(name, strlen(MDD_OBD_NAME) + 35, "%s-%s", + MDD_OBD_NAME, dev); - snprintf(uuid, strlen(MDD_OBD_UUID) + 35, "%s-%s-%d", - MDD_OBD_UUID, dev, mds_id); + snprintf(uuid, strlen(MDD_OBD_UUID) + 35, "%s-%s", + MDD_OBD_UUID, dev); lustre_cfg_bufs_reset(bufs, name); lustre_cfg_bufs_set_string(bufs, 1, MDD_OBD_TYPE); @@ -145,8 +148,13 @@ int mdd_init_obd(const struct lu_env *env, struct mdd_device *mdd, LBUG(); } + cfs_spin_lock(&obd->obd_dev_lock); obd->obd_recovering = 1; + cfs_spin_unlock(&obd->obd_dev_lock); obd->u.mds.mds_id = mds_id; + obd->u.obt.obt_osd_properties.osd_max_ea_size = + mdd->mdd_dt_conf.ddp_max_ea_size; + rc = class_setup(obd, lcfg); if (rc) GOTO(class_detach, rc); @@ -158,6 +166,7 @@ int mdd_init_obd(const struct lu_env *env, struct mdd_device *mdd, obd->obd_upcall.onu_upcall = mdd_notify; obd->obd_upcall.onu_owner = mdd; mdd->mdd_obd_dev = obd; + EXIT; class_detach: if (rc) @@ -360,6 +369,24 @@ int mdd_lov_objid_prepare(struct mdd_device *mdd, struct lov_mds_md *lmm) return mds_lov_prepare_objids(mdd->mdd_obd_dev, lmm); } +int mdd_declare_lov_objid_update(const struct lu_env *env, + struct mdd_device *mdd, + struct thandle *handle) +{ + struct obd_device *obd = mdd2obd_dev(mdd); + int size; + + /* in prepare we create local files */ + if (unlikely(mdd->mdd_capa == NULL)) + return 0; + + /* XXX: this is a temporary solution to declare llog changes + * will be fixed in 2.3 with new llog implementation */ + + size = obd->u.mds.mds_lov_desc.ld_tgt_count * sizeof(obd_id); + return dt_declare_record_write(env, mdd->mdd_capa, size, 0, handle); +} + void mdd_lov_objid_update(struct mdd_device *mdd, struct lov_mds_md *lmm) { /* copy mds_lov code is using wrong layer */ @@ -371,7 +398,7 @@ void mdd_lov_create_finish(const struct lu_env *env, struct mdd_device *mdd, const struct md_op_spec *spec) { if (lmm && !spec->no_create) - OBD_FREE(lmm, lmm_size); + OBD_FREE_LARGE(lmm, lmm_size); } int mdd_lov_create(const struct lu_env *env, struct mdd_device *mdd, @@ -385,7 +412,7 @@ int mdd_lov_create(const struct lu_env *env, struct mdd_device *mdd, struct obdo *oa; struct lov_stripe_md *lsm = NULL; const void *eadata = spec->u.sp_ea.eadata; - __u32 create_flags = spec->sp_cr_flags; + __u64 create_flags = spec->sp_cr_flags; struct obd_trans_info *oti = &mdd_env_info(env)->mti_oti; int rc = 0; ENTRY; @@ -652,6 +679,48 @@ int mdd_lov_destroy(const struct lu_env *env, struct mdd_device *mdd, RETURN(rc); } +int mdd_declare_unlink_log(const struct lu_env *env, struct mdd_object *obj, + struct md_attr *ma, struct thandle *handle) +{ + struct mdd_device *mdd = mdo2mdd(&obj->mod_obj); + int rc, stripe, i; + + LASSERT(obj); + LASSERT(ma); + + if (!S_ISREG(lu_object_attr(&obj->mod_obj.mo_lu))) + return 0; + + rc = mdd_lmm_get_locked(env, obj, ma); + if (rc || !(ma->ma_valid & MA_LOV)) + return rc; + + LASSERT(ma->ma_lmm); + if (le32_to_cpu(ma->ma_lmm->lmm_magic) != LOV_MAGIC_V1 && + le32_to_cpu(ma->ma_lmm->lmm_magic) != LOV_MAGIC_V3) { + CERROR("%s: invalid LOV_MAGIC %08x on object "DFID"\n", + mdd->mdd_obd_dev->obd_name, + le32_to_cpu(ma->ma_lmm->lmm_magic), + PFID(lu_object_fid(&obj->mod_obj.mo_lu))); + return -EINVAL; + } + + if ((int)le32_to_cpu(ma->ma_lmm->lmm_stripe_count) < 0) + stripe = mdd2obd_dev(mdd)->u.mds.mds_lov_desc.ld_tgt_count; + else + stripe = le32_to_cpu(ma->ma_lmm->lmm_stripe_count); + + for (i = 0; i < stripe; i++) { + rc = mdd_declare_llog_record(env, mdd, + sizeof(struct llog_unlink_rec), + handle); + if (rc) + return rc; + } + + return rc; +} + int mdd_unlink_log(const struct lu_env *env, struct mdd_device *mdd, struct mdd_object *mdd_cobj, struct md_attr *ma) { @@ -804,3 +873,167 @@ int mdd_lov_setattr_async(const struct lu_env *env, struct mdd_object *obj, lmm_size, logcookies, fid, NULL); RETURN(rc); } + +static int grouplock_blocking_ast(struct ldlm_lock *lock, + struct ldlm_lock_desc *desc, + void *data, int flag) +{ + struct md_attr *ma = data; + struct lustre_handle lockh; + int rc = 0; + ENTRY; + + switch (flag) + { + case LDLM_CB_BLOCKING : + /* lock is canceled */ + CDEBUG(D_DLMTRACE, "Lock %p is canceled\n", lock); + + ldlm_lock2handle(lock, &lockh); + rc = ldlm_cli_cancel(&lockh); + + break; + case LDLM_CB_CANCELING : + CDEBUG(D_DLMTRACE, + "Lock %p has been canceled, do cleaning\n", + lock); + + if (ma && ma->ma_som) + OBD_FREE_PTR(ma->ma_som); + if (ma) + OBD_FREE_PTR(ma); + break; + default: + LBUG(); + } + RETURN(rc); +} + +static int grouplock_glimpse_ast(struct ldlm_lock *lock, void *data) +{ + struct ptlrpc_request *req = data; + struct ost_lvb *lvb; + int rc; + struct md_attr *ma; + ENTRY; + + ma = lock->l_ast_data; + + req_capsule_extend(&req->rq_pill, &RQF_LDLM_GL_CALLBACK); + req_capsule_set_size(&req->rq_pill, &RMF_DLM_LVB, RCL_SERVER, + sizeof(*lvb)); + rc = req_capsule_server_pack(&req->rq_pill); + if (rc) { + CERROR("failed pack reply: %d\n", rc); + GOTO(out, rc); + } + + lvb = req_capsule_server_get(&req->rq_pill, &RMF_DLM_LVB); + + if ((ma) && (ma->ma_valid & MA_SOM)) { + lvb->lvb_size = ma->ma_som->msd_size; + lvb->lvb_blocks = ma->ma_som->msd_blocks; + } else if ((ma) && (ma->ma_valid & MA_INODE)) { + lvb->lvb_size = ma->ma_attr.la_size; + lvb->lvb_blocks = ma->ma_attr.la_blocks; + } else { + lvb->lvb_size = 0; + rc = -ELDLM_NO_LOCK_DATA; + } + + EXIT; +out: + if (rc == -ELDLM_NO_LOCK_DATA) + lustre_pack_reply(req, 1, NULL, NULL); + + req->rq_status = rc; + return rc; +} + +int mdd_file_lock(const struct lu_env *env, struct md_object *obj, + struct lov_mds_md *lmm, struct ldlm_extent *extent, + struct lustre_handle *lockh) +{ + struct ldlm_enqueue_info einfo = { 0 }; + struct obd_info oinfo = { { { 0 } } }; + struct obd_device *obd; + struct obd_export *lov_exp; + struct lov_stripe_md *lsm = NULL; + struct md_attr *ma = NULL; + int rc; + ENTRY; + + obd = mdo2mdd(obj)->mdd_obd_dev; + lov_exp = obd->u.mds.mds_lov_exp; + + obd_unpackmd(lov_exp, &lsm, lmm, + lov_mds_md_size(lmm->lmm_stripe_count, lmm->lmm_magic)); + + OBD_ALLOC_PTR(ma); + if (ma == NULL) + GOTO(out, rc = -ENOMEM); + + OBD_ALLOC_PTR(ma->ma_som); + if (ma->ma_som == NULL) + GOTO(out, rc = -ENOMEM); + + ma->ma_need = MA_SOM | MA_INODE; + mo_attr_get(env, obj, ma); + + einfo.ei_type = LDLM_EXTENT; + einfo.ei_mode = LCK_GROUP; + einfo.ei_cb_bl = grouplock_blocking_ast; + einfo.ei_cb_cp = ldlm_completion_ast; + einfo.ei_cb_gl = grouplock_glimpse_ast; + + if (ma->ma_valid & (MA_SOM | MA_INODE)) + einfo.ei_cbdata = ma; + else + einfo.ei_cbdata = NULL; + + memset(&oinfo.oi_policy, 0, sizeof(oinfo.oi_policy)); + oinfo.oi_policy.l_extent = *extent; + oinfo.oi_lockh = lockh; + oinfo.oi_md = lsm; + oinfo.oi_flags = 0; + + rc = obd_enqueue(lov_exp, &oinfo, &einfo, NULL); + /* ei_cbdata is used as a free flag at exit */ + if (rc) + einfo.ei_cbdata = NULL; + + obd_unpackmd(lov_exp, &lsm, NULL, 0); + +out: + /* ma is freed if not used as callback data */ + if ((einfo.ei_cbdata == NULL) && ma && ma->ma_som) + OBD_FREE_PTR(ma->ma_som); + if ((einfo.ei_cbdata == NULL) && ma) + OBD_FREE_PTR(ma); + + RETURN(rc); +} + +int mdd_file_unlock(const struct lu_env *env, struct md_object *obj, + struct lov_mds_md *lmm, struct lustre_handle *lockh) +{ + struct obd_device *obd; + struct obd_export *lov_exp; + struct lov_stripe_md *lsm = NULL; + int rc; + ENTRY; + + LASSERT(lustre_handle_is_used(lockh)); + + obd = mdo2mdd(obj)->mdd_obd_dev; + lov_exp = obd->u.mds.mds_lov_exp; + + obd_unpackmd(lov_exp, &lsm, lmm, + lov_mds_md_size(lmm->lmm_stripe_count, lmm->lmm_magic)); + + rc = obd_cancel(lov_exp, lsm, LCK_GROUP, lockh); + + obd_unpackmd(lov_exp, &lsm, NULL, 0); + + RETURN(rc); +}