From 75f0f0675d0eadc634c098d664b7af78547999c9 Mon Sep 17 00:00:00 2001 From: Li Wei Date: Sat, 29 Nov 2014 11:21:19 +0800 Subject: [PATCH] LU-6027 osd-zfs: Preserve lu_buf when listing EAs Current osd_xattr_list() in osd-zfs modifies its lu_buf argument, leaving lu_buf::lb_buf pointing to the end of the original buffer. This behavior is unnecessary and counter-intuitive. This patch preserves the content of the lu_buf argument and updates OSD API to reduce the chance of future regressions. Change-Id: I0d3e334848734ca6f44778e87b5ff3b044826784 Signed-off-by: Li Wei Reviewed-on: http://review.whamcloud.com/12880 Tested-by: Jenkins Tested-by: Maloo Reviewed-by: Johann Lombardi Reviewed-by: Alex Zhuravlev Reviewed-by: Oleg Drokin --- lustre/include/dt_object.h | 8 ++++---- lustre/lod/lod_object.c | 2 +- lustre/osd-ldiskfs/osd_handler.c | 2 +- lustre/osd-zfs/osd_internal.h | 2 +- lustre/osd-zfs/osd_xattr.c | 28 ++++++++++------------------ 5 files changed, 17 insertions(+), 25 deletions(-) diff --git a/lustre/include/dt_object.h b/lustre/include/dt_object.h index a54157e..b605250 100644 --- a/lustre/include/dt_object.h +++ b/lustre/include/dt_object.h @@ -743,7 +743,7 @@ struct dt_object_operations { */ int (*do_xattr_list)(const struct lu_env *env, struct dt_object *dt, - struct lu_buf *buf, + const struct lu_buf *buf, struct lustre_capa *capa); /** @@ -2622,9 +2622,9 @@ static inline int dt_xattr_get(const struct lu_env *env, return dt->do_ops->do_xattr_get(env, dt, buf, name, capa); } -static inline int dt_xattr_list(const struct lu_env *env, - struct dt_object *dt, struct lu_buf *buf, - struct lustre_capa *capa) +static inline int dt_xattr_list(const struct lu_env *env, struct dt_object *dt, + const struct lu_buf *buf, + struct lustre_capa *capa) { LASSERT(dt); LASSERT(dt->do_ops); diff --git a/lustre/lod/lod_object.c b/lustre/lod/lod_object.c index 086b93c..dba607c 100644 --- a/lustre/lod/lod_object.c +++ b/lustre/lod/lod_object.c @@ -2829,7 +2829,7 @@ static int lod_xattr_del(const struct lu_env *env, struct dt_object *dt, * for details. */ static int lod_xattr_list(const struct lu_env *env, - struct dt_object *dt, struct lu_buf *buf, + struct dt_object *dt, const struct lu_buf *buf, struct lustre_capa *capa) { return dt_xattr_list(env, dt_object_child(dt), buf, capa); diff --git a/lustre/osd-ldiskfs/osd_handler.c b/lustre/osd-ldiskfs/osd_handler.c index e26fb73..af1eb5d 100644 --- a/lustre/osd-ldiskfs/osd_handler.c +++ b/lustre/osd-ldiskfs/osd_handler.c @@ -3087,7 +3087,7 @@ static int osd_xattr_set(const struct lu_env *env, struct dt_object *dt, * Concurrency: @dt is read locked. */ static int osd_xattr_list(const struct lu_env *env, struct dt_object *dt, - struct lu_buf *buf, struct lustre_capa *capa) + const struct lu_buf *buf, struct lustre_capa *capa) { struct osd_object *obj = osd_dt_obj(dt); struct inode *inode = obj->oo_inode; diff --git a/lustre/osd-zfs/osd_internal.h b/lustre/osd-zfs/osd_internal.h index 9bb7f98..40cba11 100644 --- a/lustre/osd-zfs/osd_internal.h +++ b/lustre/osd-zfs/osd_internal.h @@ -490,7 +490,7 @@ int osd_xattr_del(const struct lu_env *env, struct dt_object *dt, const char *name, struct thandle *handle, struct lustre_capa *capa); int osd_xattr_list(const struct lu_env *env, struct dt_object *dt, - struct lu_buf *lb, struct lustre_capa *capa); + const struct lu_buf *lb, struct lustre_capa *capa); void __osd_xattr_declare_set(const struct lu_env *env, struct osd_object *obj, int vallen, const char *name, struct osd_thandle *oh); int __osd_sa_xattr_set(const struct lu_env *env, struct osd_object *obj, diff --git a/lustre/osd-zfs/osd_xattr.c b/lustre/osd-zfs/osd_xattr.c index b20a2aa..6657237 100644 --- a/lustre/osd-zfs/osd_xattr.c +++ b/lustre/osd-zfs/osd_xattr.c @@ -758,10 +758,10 @@ int osd_xattr_del(const struct lu_env *env, struct dt_object *dt, static int osd_sa_xattr_list(const struct lu_env *env, struct osd_object *obj, - struct lu_buf *lb) + const struct lu_buf *lb) { nvpair_t *nvp = NULL; - int len, counted = 0, remain = lb->lb_len; + int len, counted = 0; int rc = 0; if (obj->oo_sa_xattr == NULL) { @@ -780,16 +780,12 @@ osd_sa_xattr_list(const struct lu_env *env, struct osd_object *obj, strcmp(name, POSIX_ACL_XATTR_DEFAULT) == 0)) continue; - len = strlen(nvpair_name(nvp)); + len = strlen(name); if (lb->lb_buf != NULL) { - if (len + 1 > remain) + if (counted + len + 1 > lb->lb_len) return -ERANGE; - memcpy(lb->lb_buf, name, len); - lb->lb_buf += len; - *((char *)lb->lb_buf) = '\0'; - lb->lb_buf++; - remain -= len + 1; + memcpy(lb->lb_buf + counted, name, len + 1); } counted += len + 1; } @@ -797,13 +793,13 @@ osd_sa_xattr_list(const struct lu_env *env, struct osd_object *obj, } int osd_xattr_list(const struct lu_env *env, struct dt_object *dt, - struct lu_buf *lb, struct lustre_capa *capa) + const struct lu_buf *lb, struct lustre_capa *capa) { struct osd_object *obj = osd_dt_obj(dt); struct osd_device *osd = osd_obj2dev(obj); zap_attribute_t *za = &osd_oti_get(env)->oti_za; zap_cursor_t *zc; - int rc, counted = 0, remain = lb->lb_len; + int rc, counted; ENTRY; LASSERT(obj->oo_db != NULL); @@ -815,8 +811,8 @@ int osd_xattr_list(const struct lu_env *env, struct dt_object *dt, rc = osd_sa_xattr_list(env, obj, lb); if (rc < 0) GOTO(out, rc); + counted = rc; - remain -= counted; /* continue with dnode xattr if any */ if (obj->oo_xattr == ZFS_NO_OBJECT) @@ -836,14 +832,10 @@ int osd_xattr_list(const struct lu_env *env, struct dt_object *dt, rc = strlen(za->za_name); if (lb->lb_buf != NULL) { - if (rc + 1 > remain) + if (counted + rc + 1 > lb->lb_len) RETURN(-ERANGE); - memcpy(lb->lb_buf, za->za_name, rc); - lb->lb_buf += rc; - *((char *)lb->lb_buf) = '\0'; - lb->lb_buf++; - remain -= rc + 1; + memcpy(lb->lb_buf + counted, za->za_name, rc + 1); } counted += rc + 1; -- 1.8.3.1