From 9fdbfed4ce20aaf7ac0e6b5001f323428d9d3893 Mon Sep 17 00:00:00 2001 From: Fan Yong Date: Tue, 25 Jul 2017 14:09:21 +0800 Subject: [PATCH 1/1] LU-7991 osd-zfs: remove obsolete quota code Directly use ZFS backend quota accounting objects, no need be mapped from Lustre own account objects. Related obsolete logic is removed totally. Signed-off-by: Fan Yong Change-Id: I2c6aeb1ccac52348d8d163017f73ef0fd9133551 Reviewed-on: https://review.whamcloud.com/27661 Tested-by: Jenkins Tested-by: Maloo Reviewed-by: Nathaniel Clark Reviewed-by: Niu Yawei Reviewed-by: Oleg Drokin --- lustre/osd-zfs/osd_internal.h | 4 --- lustre/osd-zfs/osd_object.c | 75 +++++++++++++++++++++++++++++++++---------- lustre/osd-zfs/osd_oi.c | 63 +++++++----------------------------- lustre/osd-zfs/osd_quota.c | 65 ++++++++++++++++++------------------- 4 files changed, 101 insertions(+), 106 deletions(-) diff --git a/lustre/osd-zfs/osd_internal.h b/lustre/osd-zfs/osd_internal.h index 63f19c0..12702e2 100644 --- a/lustre/osd-zfs/osd_internal.h +++ b/lustre/osd-zfs/osd_internal.h @@ -297,9 +297,6 @@ struct osd_device { int od_connects; struct lu_site od_site; - /* object IDs of the inode accounting indexes */ - uint64_t od_iusr_oid; - uint64_t od_igrp_oid; dnode_t *od_groupused_dn; dnode_t *od_userused_dn; @@ -378,7 +375,6 @@ struct osd_object { int osd_statfs(const struct lu_env *, struct dt_device *, struct obd_statfs *); extern const struct dt_index_operations osd_acct_index_ops; -dnode_t *osd_quota_fid2dmu(const struct osd_device *, const struct lu_fid *fid); extern struct lu_device_operations osd_lu_ops; extern struct dt_index_operations osd_dir_ops; int osd_declare_quota(const struct lu_env *env, struct osd_device *osd, diff --git a/lustre/osd-zfs/osd_object.c b/lustre/osd-zfs/osd_object.c index 2f1d2f2..2ed4a18 100644 --- a/lustre/osd-zfs/osd_object.c +++ b/lustre/osd-zfs/osd_object.c @@ -371,6 +371,30 @@ static int osd_check_lma(const struct lu_env *env, struct osd_object *obj) RETURN(rc); } +/** + * Helper function to retrieve DMU object id from fid for accounting object + */ +static dnode_t *osd_quota_fid2dmu(const struct osd_device *osd, + const struct lu_fid *fid) +{ + dnode_t *dn = NULL; + + LASSERT(fid_is_acct(fid)); + + switch (fid_oid(fid)) { + case ACCT_USER_OID: + dn = osd->od_userused_dn; + break; + case ACCT_GROUP_OID: + dn = osd->od_groupused_dn; + break; + default: + break; + } + + return dn; +} + /* * Concurrency: no concurrent access is possible that early in object * life-cycle. @@ -378,10 +402,11 @@ static int osd_check_lma(const struct lu_env *env, struct osd_object *obj) static int osd_object_init(const struct lu_env *env, struct lu_object *l, const struct lu_object_conf *conf) { - struct osd_object *obj = osd_obj(l); - struct osd_device *osd = osd_obj2dev(obj); - uint64_t oid; - int rc; + struct osd_object *obj = osd_obj(l); + struct osd_device *osd = osd_obj2dev(obj); + const struct lu_fid *fid = lu_object_fid(l); + uint64_t oid; + int rc = 0; ENTRY; LASSERT(osd_invariant(obj)); @@ -395,7 +420,17 @@ static int osd_object_init(const struct lu_env *env, struct lu_object *l, if (conf != NULL && conf->loc_flags & LOC_F_NEW) GOTO(out, rc = 0); - rc = osd_fid_lookup(env, osd, lu_object_fid(l), &oid); + if (unlikely(fid_is_acct(fid))) { + obj->oo_dn = osd_quota_fid2dmu(osd, fid); + if (obj->oo_dn) { + obj->oo_dt.do_index_ops = &osd_acct_index_ops; + l->lo_header->loh_attr |= LOHA_EXISTS; + } + + GOTO(out, rc = 0); + } + + rc = osd_fid_lookup(env, osd, fid, &oid); if (rc == 0) { LASSERT(obj->oo_dn == NULL); rc = __osd_obj2dnode(osd->od_os, oid, &obj->oo_dn); @@ -616,15 +651,18 @@ out: static void osd_object_delete(const struct lu_env *env, struct lu_object *l) { struct osd_object *obj = osd_obj(l); - - if (obj->oo_dn != NULL) { - osd_object_sa_fini(obj); - if (obj->oo_sa_xattr) { - nvlist_free(obj->oo_sa_xattr); - obj->oo_sa_xattr = NULL; + const struct lu_fid *fid = lu_object_fid(l); + + if (obj->oo_dn) { + if (likely(!fid_is_acct(fid))) { + osd_object_sa_fini(obj); + if (obj->oo_sa_xattr) { + nvlist_free(obj->oo_sa_xattr); + obj->oo_sa_xattr = NULL; + } + osd_dnode_rele(obj->oo_dn); + list_del(&obj->oo_sa_linkage); } - osd_dnode_rele(obj->oo_dn); - list_del(&obj->oo_sa_linkage); obj->oo_dn = NULL; } } @@ -712,6 +750,9 @@ static int osd_attr_get(const struct lu_env *env, if (unlikely(!dt_object_exists(dt) || obj->oo_destroyed)) GOTO(out, rc = -ENOENT); + if (unlikely(fid_is_acct(lu_object_fid(&dt->do_lu)))) + GOTO(out, rc = 0); + LASSERT(osd_invariant(obj)); LASSERT(obj->oo_dn); @@ -1445,6 +1486,8 @@ static int osd_create(const struct lu_env *env, struct dt_object *dt, ENTRY; + LASSERT(!fid_is_acct(fid)); + /* concurrent create declarations should not see * the object inconsistent (db, attr, etc). * in regular cases acquisition should be cheap */ @@ -1502,16 +1545,14 @@ static int osd_create(const struct lu_env *env, struct dt_object *dt, /* XXX: oo_lma_flags */ obj->oo_dt.do_lu.lo_header->loh_attr |= obj->oo_attr.la_mode & S_IFMT; - if (likely(!fid_is_acct(lu_object_fid(&obj->oo_dt.do_lu)))) - /* no body operations for accounting objects */ - obj->oo_dt.do_body_ops = &osd_body_ops; + obj->oo_dt.do_body_ops = &osd_body_ops; rc = -nvlist_alloc(&obj->oo_sa_xattr, NV_UNIQUE_NAME, KM_SLEEP); if (rc) GOTO(out, rc); /* initialize LMA */ - lustre_lma_init(lma, lu_object_fid(&obj->oo_dt.do_lu), 0, 0); + lustre_lma_init(lma, fid, 0, 0); lustre_lma_swab(lma); rc = -nvlist_add_byte_array(obj->oo_sa_xattr, XATTR_NAME_LMA, (uchar_t *)lma, sizeof(*lma)); diff --git a/lustre/osd-zfs/osd_oi.c b/lustre/osd-zfs/osd_oi.c index d8190a8..92d5452 100644 --- a/lustre/osd-zfs/osd_oi.c +++ b/lustre/osd-zfs/osd_oi.c @@ -88,9 +88,6 @@ static const struct named_oid oids[] = { { .oid = FLD_INDEX_OID, .name = "fld" }, { .oid = MDD_LOV_OBJ_OID, .name = LOV_OBJID }, { .oid = OFD_HEALTH_CHECK_OID, .name = HEALTH_CHECK }, - { .oid = ACCT_USER_OID, .name = "acct_usr_inode" }, - { .oid = ACCT_GROUP_OID, .name = "acct_grp_inode" }, - { .oid = ACCT_PROJECT_OID, .name = "acct_prj_inode" }, { .oid = REPLY_DATA_OID, .name = REPLY_DATA }, { .oid = 0 } }; @@ -455,6 +452,8 @@ uint64_t osd_get_name_n_idx(const struct lu_env *env, struct osd_device *osd, uint64_t zapid; LASSERT(fid); + LASSERT(!fid_is_acct(fid)); + if (zdn != NULL) *zdn = NULL; @@ -468,8 +467,6 @@ uint64_t osd_get_name_n_idx(const struct lu_env *env, struct osd_device *osd, zapid = osd->od_root; if (buf) strncpy(buf, name, bufsize); - if (fid_is_acct(fid)) - zapid = MASTER_NODE_OBJ; } else { zapid = osd_get_idx_for_fid(osd, fid, buf, NULL); } @@ -487,26 +484,6 @@ static inline int fid_is_fs_root(const struct lu_fid *fid) fid_oid(fid) == OSD_FS_ROOT_OID; } -static inline int osd_oid(struct osd_device *dev, __u32 local_oid, - uint64_t *oid) -{ - switch (local_oid) { - case ACCT_USER_OID: - *oid = dev->od_iusr_oid; - return 0; - case ACCT_GROUP_OID: - *oid = dev->od_igrp_oid; - return 0; - case ACCT_PROJECT_OID: - /* TODO: real oid */ - CERROR("%s: unsupported quota oid: %#x\n", - osd_name(dev), local_oid); - return -ENOTSUPP; - } - - return -ENOTSUPP; -} - int osd_fid_lookup(const struct lu_env *env, struct osd_device *dev, const struct lu_fid *fid, uint64_t *oid) { @@ -520,11 +497,9 @@ int osd_fid_lookup(const struct lu_env *env, struct osd_device *dev, if (OBD_FAIL_CHECK(OBD_FAIL_SRV_ENOENT)) RETURN(-ENOENT); - if (unlikely(fid_is_acct(fid))) { - rc = osd_oid(dev, fid_oid(fid), oid); - if (rc) - RETURN(rc); - } else if (unlikely(fid_is_fs_root(fid))) { + LASSERT(!fid_is_acct(fid)); + + if (unlikely(fid_is_fs_root(fid))) { *oid = dev->od_root; } else { zapid = osd_get_name_n_idx(env, dev, fid, buf, @@ -694,31 +669,13 @@ static void osd_ost_seq_fini(const struct lu_env *env, struct osd_device *osd) static int osd_oi_init_compat(const struct lu_env *env, struct osd_device *o) { - uint64_t odb, sdb; - int rc; + uint64_t sdb; + int rc; ENTRY; rc = osd_oi_find_or_create(env, o, o->od_root, "O", &sdb); - if (rc) - RETURN(rc); - - o->od_O_id = sdb; - - /* Create on-disk indexes to maintain per-UID/GID inode usage. - * Those new indexes are created in the top-level ZAP outside the - * namespace in order not to confuse ZPL which might interpret those - * indexes as directories and assume the values are object IDs */ - rc = osd_oi_find_or_create(env, o, MASTER_NODE_OBJ, - oid2name(ACCT_USER_OID), &odb); - if (rc) - RETURN(rc); - o->od_iusr_oid = odb; - - rc = osd_oi_find_or_create(env, o, MASTER_NODE_OBJ, - oid2name(ACCT_GROUP_OID), &odb); - if (rc) - RETURN(rc); - o->od_igrp_oid = odb; + if (!rc) + o->od_O_id = sdb; RETURN(rc); } @@ -876,6 +833,8 @@ struct osd_idmap_cache *osd_idc_find_or_init(const struct lu_env *env, struct osd_idmap_cache *idc; int rc; + LASSERT(!fid_is_acct(fid)); + idc = osd_idc_find(env, osd, fid); if (idc != NULL) return idc; diff --git a/lustre/osd-zfs/osd_quota.c b/lustre/osd-zfs/osd_quota.c index 9a425e7..b3d45af 100644 --- a/lustre/osd-zfs/osd_quota.c +++ b/lustre/osd-zfs/osd_quota.c @@ -32,20 +32,8 @@ #include "osd_internal.h" /** - * Helper function to retrieve DMU object id from fid for accounting object - */ -dnode_t *osd_quota_fid2dmu(const struct osd_device *osd, - const struct lu_fid *fid) -{ - LASSERT(fid_is_acct(fid)); - if (fid_oid(fid) == ACCT_GROUP_OID) - return osd->od_groupused_dn; - return osd->od_userused_dn; -} - -/** - * Helper function to estimate the number of inodes in use for a give uid/gid - * from the block usage + * Helper function to estimate the number of inodes in use for the given + * uid/gid from the block usage */ static uint64_t osd_objset_user_iused(struct osd_device *osd, uint64_t uidbytes) { @@ -91,23 +79,26 @@ static int osd_acct_index_lookup(const struct lu_env *env, struct dt_rec *dtrec, const struct dt_key *dtkey) { - struct osd_thread_info *info = osd_oti_get(env); - char *buf = info->oti_buf; - size_t buflen = sizeof(info->oti_buf); - struct lquota_acct_rec *rec = (struct lquota_acct_rec *)dtrec; - struct osd_object *obj = osd_dt_obj(dtobj); - struct osd_device *osd = osd_obj2dev(obj); - int rc; - dnode_t *dn; + struct osd_thread_info *info = osd_oti_get(env); + char *buf = info->oti_buf; + struct lquota_acct_rec *rec = (struct lquota_acct_rec *)dtrec; + struct osd_object *obj = osd_dt_obj(dtobj); + struct osd_device *osd = osd_obj2dev(obj); + dnode_t *dn = obj->oo_dn; + size_t buflen = sizeof(info->oti_buf); + int rc; ENTRY; rec->bspace = rec->ispace = 0; /* convert the 64-bit uid/gid into a string */ snprintf(buf, buflen, "%llx", *((__u64 *)dtkey)); - /* fetch DMU object (DMU_USERUSED_OBJECT/DMU_GROUPUSED_OBJECT) to be - * used */ - dn = osd_quota_fid2dmu(osd, lu_object_fid(&dtobj->do_lu)); + if (unlikely(!dn)) { + CDEBUG(D_QUOTA, "%s: miss accounting obj for %s\n", + osd->od_svname, buf); + + RETURN(-ENOENT); + } /* disk usage (in bytes) is maintained by DMU. * DMU_USERUSED_OBJECT/DMU_GROUPUSED_OBJECT are special objects which @@ -118,6 +109,8 @@ static int osd_acct_index_lookup(const struct lu_env *env, /* user/group has not created anything yet */ CDEBUG(D_QUOTA, "%s: id %s not found in DMU accounting ZAP\n", osd->od_svname, buf); + /* -ENOENT is normal case, convert it as 1. */ + rc = 1; } else if (rc) { RETURN(rc); } @@ -136,6 +129,8 @@ static int osd_acct_index_lookup(const struct lu_env *env, CDEBUG(D_QUOTA, "%s: id %s not found dnode accounting\n", osd->od_svname, buf); + /* -ENOENT is normal case, convert it as 1. */ + rc = 1; } else if (rc == 0) { rc = 1; } @@ -154,15 +149,20 @@ static struct dt_it *osd_it_acct_init(const struct lu_env *env, struct dt_object *dt, __u32 attr) { - struct osd_thread_info *info = osd_oti_get(env); - struct osd_it_quota *it; - struct lu_object *lo = &dt->do_lu; - struct osd_device *osd = osd_dev(lo->lo_dev); - dnode_t *dn; + struct osd_thread_info *info = osd_oti_get(env); + struct osd_it_quota *it; + struct osd_object *obj = osd_dt_obj(dt); + struct osd_device *osd = osd_obj2dev(obj); + dnode_t *dn = obj->oo_dn; int rc; ENTRY; - LASSERT(lu_object_exists(lo)); + if (unlikely(!dn)) { + CDEBUG(D_QUOTA, "%s: Not found in DMU accounting ZAP\n", + osd->od_svname); + + RETURN(ERR_PTR(-ENOENT)); + } if (info == NULL) RETURN(ERR_PTR(-ENOMEM)); @@ -172,7 +172,6 @@ static struct dt_it *osd_it_acct_init(const struct lu_env *env, RETURN(ERR_PTR(-ENOMEM)); memset(it, 0, sizeof(*it)); - dn = osd_quota_fid2dmu(osd, lu_object_fid(lo)); it->oiq_oid = dn->dn_object; /* initialize zap cursor */ @@ -183,7 +182,7 @@ static struct dt_it *osd_it_acct_init(const struct lu_env *env, } /* take object reference */ - lu_object_get(lo); + lu_object_get(&dt->do_lu); it->oiq_obj = osd_dt_obj(dt); it->oiq_reset = 1; -- 1.8.3.1