X-Git-Url: https://git.whamcloud.com/?a=blobdiff_plain;f=lustre%2Fcobd%2Fcache_obd.c;h=9025798b27f55e4cb35cf025708f5bc870409545;hb=f0cf9fa9e22717eb407bea671b99b5c420d43325;hp=622b4b48c10270409747d09c7777e6a31300fe46;hpb=f63ae8e8a6f27d4454ceef553143fb67300fe6d8;p=fs%2Flustre-release.git diff --git a/lustre/cobd/cache_obd.c b/lustre/cobd/cache_obd.c index 622b4b4..9025798 100644 --- a/lustre/cobd/cache_obd.c +++ b/lustre/cobd/cache_obd.c @@ -31,8 +31,10 @@ #include #include #include +#include -static int cobd_attach(struct obd_device *obd, obd_count len, void *buf) +static int cobd_attach(struct obd_device *obd, + obd_count len, void *buf) { struct lprocfs_static_vars lvars; @@ -45,161 +47,199 @@ static int cobd_detach(struct obd_device *obd) return lprocfs_obd_detach(obd); } -static int connect_to_obd(char *name, struct lustre_handle *conn) -{ - struct obd_uuid obd_uuid; - struct obd_device *obd; - int rc = 0; - ENTRY; - - obd = class_name2obd(name); - if (obd == NULL) { - CERROR("%s: unable to find a client for obd: %s\n", - obd->obd_name, name); - RETURN(-EINVAL); - } - rc = obd_connect(conn, obd, &obd_uuid, 0); - RETURN(rc); -} - static int cobd_setup(struct obd_device *obd, obd_count len, void *buf) { struct lustre_cfg *lcfg = (struct lustre_cfg *)buf; struct cache_obd *cobd = &obd->u.cobd; -#if 0 - struct lustre_handle master_conn = {0,}; -#endif - struct lustre_handle cache_conn = {0,}; struct obd_device *master; - struct obd_device *cache; - int rc; + int rc = 0; ENTRY; - if (lcfg->lcfg_inllen1 == 0 || lcfg->lcfg_inlbuf1 == NULL) { + if (LUSTRE_CFG_BUFLEN(lcfg, 1) < 1 || + lustre_cfg_buf(lcfg, 1) == NULL) { CERROR("%s: setup requires master device name\n", obd->obd_name); RETURN(-EINVAL); } - master = class_name2obd(lcfg->lcfg_inlbuf1); - if (master == NULL) { - CERROR("%s: unable to find a client for master: %s\n", - obd->obd_name, lcfg->lcfg_inlbuf1); + if (LUSTRE_CFG_BUFLEN(lcfg, 2) < 1 || + lustre_cfg_buf(lcfg, 2) == NULL) { + CERROR("%s: setup requires cache device name\n", + obd->obd_name); RETURN(-EINVAL); } - if (lcfg->lcfg_inllen2 == 0 || lcfg->lcfg_inlbuf2 == NULL) { - CERROR("%s: setup requires cache device name\n", obd->obd_name); + master = class_name2obd(lustre_cfg_string(lcfg, 1)); + if (!master) { + CERROR("%s: unable to find master: %s\n", + obd->obd_name, lustre_cfg_string(lcfg, 1)); RETURN(-EINVAL); } - cache = class_name2obd(lcfg->lcfg_inlbuf2); - if (cache == NULL) { - CERROR("%s: unable to find a client for cache: %s\n", - obd->obd_name, lcfg->lcfg_inlbuf2); - RETURN(-EINVAL); - } + sema_init(&cobd->sem, 1); - OBD_ALLOC(cobd->master_name, strlen(lcfg->lcfg_inlbuf1) + 1); + OBD_ALLOC(cobd->master_name, LUSTRE_CFG_BUFLEN(lcfg, 1)); if (!cobd->master_name) - GOTO(exit, rc = -ENOMEM); - memcpy(cobd->master_name, lcfg->lcfg_inlbuf1, - strlen(lcfg->lcfg_inlbuf1)); + RETURN(-ENOMEM); + memcpy(cobd->master_name, lustre_cfg_string(lcfg, 1), + LUSTRE_CFG_BUFLEN(lcfg, 1)); - OBD_ALLOC(cobd->cache_name, strlen(lcfg->lcfg_inlbuf2) + 1); + OBD_ALLOC(cobd->cache_name, LUSTRE_CFG_BUFLEN(lcfg, 2)); if (!cobd->cache_name) - GOTO(exit, rc = -ENOMEM); - memcpy(cobd->cache_name, lcfg->lcfg_inlbuf2, - strlen(lcfg->lcfg_inlbuf2)); - -#if 0 - /* don't bother checking attached/setup; obd_connect() should, and it - * can change underneath us */ - rc = connect_to_obd(cobd->master_name, &master_conn); - if (rc != 0) - GOTO(exit, rc); - cobd->master_exp = class_conn2export(&master_conn); -#endif - rc = connect_to_obd(cobd->cache_name, &cache_conn); - if (rc != 0) { - obd_disconnect(cobd->cache_exp, 0); - GOTO(exit, rc); - } - cobd->cache_exp = class_conn2export(&cache_conn); - cobd->cache_on = 1; + GOTO(put_names, rc = -ENOMEM); + memcpy(cobd->cache_name, lustre_cfg_string(lcfg, 2), + LUSTRE_CFG_BUFLEN(lcfg, 2)); - if (!strcmp(master->obd_type->typ_name, LUSTRE_MDC_NAME)) { - int mds_type; - - mds_type = MDS_MASTER_OBD; - obd_set_info(cobd->master_exp, strlen("mds_type"), - "mds_type", sizeof(mds_type), &mds_type); - - mds_type = MDS_CACHE_OBD; - obd_set_info(cobd->cache_exp, strlen("mds_type"), - "mds_type", sizeof(mds_type), &mds_type); - } -exit: + EXIT; +put_names: if (rc) { - if (cobd->cache_name) - OBD_FREE(cobd->cache_name, - strlen(cobd->cache_name) + 1); - if (cobd->master_name) - OBD_FREE(cobd->master_name, - strlen(cobd->master_name) + 1); + OBD_FREE(cobd->master_name, LUSTRE_CFG_BUFLEN(lcfg, 1)); + cobd->master_name = NULL; } - RETURN(rc); + return rc; } static int cobd_cleanup(struct obd_device *obd, int flags) { struct cache_obd *cobd = &obd->u.cobd; - int rc; + ENTRY; if (!list_empty(&obd->obd_exports)) - return (-EBUSY); - + RETURN(-EBUSY); + if (cobd->cache_name) OBD_FREE(cobd->cache_name, strlen(cobd->cache_name) + 1); if (cobd->master_name) OBD_FREE(cobd->master_name, strlen(cobd->master_name) + 1); - if (cobd->cache_on) { - rc = obd_disconnect(cobd->cache_exp, flags); - if (rc != 0) - CERROR("error %d disconnecting cache\n", rc); - } - rc = obd_disconnect(cobd->master_exp, flags); - if (rc != 0) - CERROR("error %d disconnecting master\n", rc); - return (rc); + RETURN(0); } -struct obd_export *cobd_get_exp(struct obd_device *obd) +static inline struct obd_export * +cobd_get_exp(struct obd_device *obd) { - struct cache_obd *cobd = &obd->u.cobd; - + struct cache_obd *cobd = &obd->u.cobd; if (cobd->cache_on) return cobd->cache_exp; - else - return cobd->master_exp; + return cobd->master_exp; +} + +static int client_obd_connect(struct obd_device *obd, char *name, + struct lustre_handle *conn, + struct obd_connect_data *data, + unsigned long flags) +{ + struct obd_device *cli_obd; + int rc = 0; + ENTRY; + + LASSERT(obd); + LASSERT(name); + LASSERT(conn); + + cli_obd = class_name2obd(name); + if (cli_obd == NULL) { + CERROR("%s: unable to find a client for obd: %s\n", + obd->obd_name, name); + RETURN(-EINVAL); + } + rc = obd_connect(conn, cli_obd, &obd->obd_uuid, data, flags); + if (rc) { + CERROR("error connecting to %s, err %d\n", + name, rc); + } + RETURN(rc); +} + +static int client_obd_disconnect(struct obd_device *obd, + struct obd_export *exp, + unsigned long flags) +{ + struct obd_device *cli_obd; + int rc = 0; + ENTRY; + + cli_obd = class_exp2obd(exp); + cli_obd->obd_no_recov = obd->obd_no_recov; + + rc = obd_disconnect(exp, flags); + if (rc) { + CERROR("error disconnecting from %s, err %d\n", + cli_obd->obd_name, rc); + class_export_put(exp); + } + RETURN(rc); } static int cobd_connect(struct lustre_handle *conn, struct obd_device *obd, - struct obd_uuid *cluuid, unsigned long connect_flags) + struct obd_uuid *cluuid, struct obd_connect_data *data, + unsigned long flags) { - return class_connect(conn, obd, cluuid); + struct lustre_handle cache_conn = { 0 }; + struct cache_obd *cobd = &obd->u.cobd; + struct obd_export *exp; + int rc = 0; + ENTRY; + + /* connecting class */ + rc = class_connect(conn, obd, cluuid); + if (rc) + RETURN(rc); + exp = class_conn2export(conn); + + /* connecting cache */ + rc = client_obd_connect(obd, cobd->cache_name, + &cache_conn, data, flags); + if (rc) + GOTO(err_discon, rc); + cobd->cache_exp = class_conn2export(&cache_conn); + cobd->cache_on = 1; + + EXIT; +err_discon: + if (rc) + class_disconnect(exp, 0); + else + class_export_put(exp); + return rc; } -static int cobd_disconnect(struct obd_export *exp, int flags) +static int +cobd_disconnect(struct obd_export *exp, unsigned long flags) { - return class_disconnect(exp, 0); + struct obd_device *obd; + struct cache_obd *cobd; + int rc = 0; + ENTRY; + + LASSERT(exp != NULL); + obd = class_exp2obd(exp); + if (obd == NULL) { + CDEBUG(D_IOCTL, "invalid client cookie "LPX64"\n", + exp->exp_handle.h_cookie); + RETURN(-EINVAL); + } + + cobd = &obd->u.cobd; + + if (cobd->cache_on) { + rc = client_obd_disconnect(obd, cobd->cache_exp, + flags); + cobd->cache_exp = NULL; + } else { + rc = client_obd_disconnect(obd, cobd->master_exp, + flags); + cobd->master_exp = NULL; + } + + rc = class_disconnect(exp, flags); + RETURN(rc); } -static int cobd_get_info(struct obd_export *exp, obd_count keylen, +static int cobd_get_info(struct obd_export *exp, __u32 keylen, void *key, __u32 *vallen, void *val) { struct obd_device *obd = class_exp2obd(exp); @@ -277,6 +317,7 @@ static int cobd_unpackmd(struct obd_export *exp, } static int cobd_create(struct obd_export *exp, struct obdo *obdo, + void *acl, int acl_size, struct lov_stripe_md **ea, struct obd_trans_info *oti) { @@ -289,7 +330,7 @@ static int cobd_create(struct obd_export *exp, struct obdo *obdo, return -EINVAL; } cobd_exp = cobd_get_exp(obd); - return obd_create(cobd_exp, obdo, ea, oti); + return obd_create(cobd_exp, obdo, acl, acl_size, ea, oti); } static int cobd_destroy(struct obd_export *exp, struct obdo *obdo, @@ -315,7 +356,7 @@ static int cobd_precleanup(struct obd_device *obd, int flags) } static int cobd_getattr(struct obd_export *exp, struct obdo *oa, - struct lov_stripe_md *lsm) + struct lov_stripe_md *ea) { struct obd_device *obd = class_exp2obd(exp); struct obd_export *cobd_exp; @@ -326,7 +367,7 @@ static int cobd_getattr(struct obd_export *exp, struct obdo *oa, return -EINVAL; } cobd_exp = cobd_get_exp(obd); - return obd_getattr(cobd_exp, oa, lsm); + return obd_getattr(cobd_exp, oa, ea); } static int cobd_getattr_async(struct obd_export *exp, @@ -435,7 +476,7 @@ static int cobd_queue_async_io(struct obd_export *exp, struct lov_stripe_md *lsm, struct lov_oinfo *loi, void *cookie, int cmd, obd_off off, int count, - obd_flag brw_flags, obd_flag async_flags) + obd_flags brw_flags, obd_flags async_flags) { struct obd_device *obd = class_exp2obd(exp); struct obd_export *cobd_exp; @@ -453,7 +494,7 @@ static int cobd_queue_async_io(struct obd_export *exp, static int cobd_set_async_flags(struct obd_export *exp, struct lov_stripe_md *lsm, struct lov_oinfo *loi, void *cookie, - obd_flag async_flags) + obd_flags async_flags) { struct obd_device *obd = class_exp2obd(exp); struct obd_export *cobd_exp; @@ -472,8 +513,8 @@ static int cobd_queue_group_io(struct obd_export *exp, struct lov_oinfo *loi, struct obd_io_group *oig, void *cookie, int cmd, obd_off off, - int count, obd_flag brw_flags, - obd_flag async_flags) + int count, obd_flags brw_flags, + obd_flags async_flags) { struct obd_device *obd = class_exp2obd(exp); struct obd_export *cobd_exp; @@ -675,57 +716,55 @@ static int cobd_commitrw(int cmd, struct obd_export *exp, struct obdo *oa, static int cobd_flush(struct obd_device *obd) { - /* flush the filesystem from the cache to the real device. */ return 0; } -static int cobd_iocontrol(unsigned int cmd, struct obd_export *exp, int len, - void *karg, void *uarg) +static int cobd_iocontrol(unsigned int cmd, struct obd_export *exp, + int len, void *karg, void *uarg) { struct obd_device *obd = class_exp2obd(exp); struct cache_obd *cobd = &obd->u.cobd; - struct obd_device *master_dev = NULL; struct obd_export *cobd_exp; int rc = 0; - + ENTRY; + + down(&cobd->sem); + switch (cmd) { case OBD_IOC_COBD_CON: if (!cobd->cache_on) { - struct lustre_handle cache_conn = {0,}; - - rc = obd_disconnect(cobd->master_exp, 0); - if (rc != 0) - CERROR("error %d disconnecting master\n", rc); - rc = connect_to_obd(cobd->cache_name, &cache_conn); - if (rc != 0) - RETURN(rc); - cobd->cache_exp = class_conn2export(&cache_conn); - + struct lustre_handle conn = {0}; + + rc = client_obd_disconnect(obd, cobd->master_exp, 0); + rc = client_obd_connect(obd, cobd->cache_name, &conn, + NULL, 0); + if (rc) + GOTO(out, rc); + cobd->cache_exp = class_conn2export(&conn); cobd->cache_on = 1; } break; case OBD_IOC_COBD_COFF: if (cobd->cache_on) { - struct lustre_handle master_conn = {0,}; - struct obd_device *cache_dev = NULL; - int m_easize, m_cooksize; - - cache_dev = class_exp2obd(cobd->cache_exp); - m_easize = cache_dev->u.cli.cl_max_mds_easize; - m_cooksize = cache_dev->u.cli.cl_max_mds_cookiesize; - rc = obd_disconnect(cobd->cache_exp, 0); - if (rc != 0) - CERROR("error %d disconnecting master\n", rc); - - /* FIXME-WANGDI: should we read from master_dev? */ + struct lustre_handle conn = {0,}; + struct obd_device *master = NULL; + struct obd_device *cache = NULL; + int easize, cooksize; + + cache = class_exp2obd(cobd->cache_exp); + easize = cache->u.cli.cl_max_mds_easize; + cooksize = cache->u.cli.cl_max_mds_cookiesize; - rc = connect_to_obd(cobd->master_name, &master_conn); - if (rc != 0) - RETURN(rc); - cobd->master_exp = class_conn2export(&master_conn); - master_dev = class_exp2obd(cobd->master_exp); - master_dev->u.cli.cl_max_mds_easize = m_easize; - master_dev->u.cli.cl_max_mds_cookiesize = m_cooksize; + rc = client_obd_disconnect(obd, cobd->cache_exp, 0); + rc = client_obd_connect(obd, cobd->master_name, &conn, + NULL, 0); + if (rc) + GOTO(out, rc); + cobd->master_exp = class_conn2export(&conn); + + master = class_exp2obd(cobd->master_exp); + master->u.cli.cl_max_mds_easize = easize; + master->u.cli.cl_max_mds_cookiesize = cooksize; cobd->cache_on = 0; } break; @@ -733,13 +772,18 @@ static int cobd_iocontrol(unsigned int cmd, struct obd_export *exp, int len, if (cobd->cache_on) { cobd->cache_on = 0; cobd_flush(obd); + } else { + CERROR("%s: cache is turned off\n", obd->obd_name); } break; default: cobd_exp = cobd_get_exp(obd); rc = obd_iocontrol(cmd, cobd_exp, len, karg, uarg); } - + + EXIT; +out: + up(&cobd->sem); return rc; } @@ -833,8 +877,8 @@ static int cobd_import_event(struct obd_device *obd, } static int cobd_md_getattr(struct obd_export *exp, struct lustre_id *id, - unsigned long valid, unsigned int ea_size, - struct ptlrpc_request **request) + __u64 valid, const char *ea_name, int ea_namelen, + unsigned int ea_size, struct ptlrpc_request **request) { struct obd_device *obd = class_exp2obd(exp); struct obd_export *cobd_exp; @@ -845,7 +889,7 @@ static int cobd_md_getattr(struct obd_export *exp, struct lustre_id *id, return -EINVAL; } cobd_exp = cobd_get_exp(obd); - return md_getattr(cobd_exp, id, valid, ea_size, request); + return md_getattr(cobd_exp, id, valid, NULL, 0, ea_size, request); } static int cobd_md_req2lustre_md (struct obd_export *mdc_exp, @@ -880,7 +924,7 @@ static int cobd_md_change_cbdata(struct obd_export *exp, struct lustre_id *id, } static int cobd_md_getattr_lock(struct obd_export *exp, struct lustre_id *id, - char *filename, int namelen, unsigned long valid, + char *filename, int namelen, __u64 valid, unsigned int ea_size, struct ptlrpc_request **request) { struct obd_device *obd = class_exp2obd(exp); @@ -1160,7 +1204,7 @@ static int cobd_md_intent_lock(struct obd_export *exp, struct lustre_id *pid, } static struct obd_device *cobd_md_get_real_obd(struct obd_export *exp, - char *name, int len) + struct lustre_id *id) { struct obd_device *obd = class_exp2obd(exp); struct obd_export *cobd_exp; @@ -1171,7 +1215,7 @@ static struct obd_device *cobd_md_get_real_obd(struct obd_export *exp, return NULL; } cobd_exp = cobd_get_exp(obd); - return md_get_real_obd(cobd_exp, name, len); + return md_get_real_obd(cobd_exp, id); } static int cobd_md_change_cbdata_name(struct obd_export *exp,