diff options
| author | Poornima G <pgurusid@redhat.com> | 2018-01-04 19:38:05 +0530 | 
|---|---|---|
| committer | Amar Tumballi <amarts@redhat.com> | 2018-01-19 03:51:27 +0000 | 
| commit | 8fc9c6a8fc7c73b2b4c65a8ddbe988bca10e89b6 (patch) | |
| tree | 82ca0c00f046f09785ba095f0d705fa38245fb70 | |
| parent | 84c5c540b26c8f3dcb9845344dd48df063e57845 (diff) | |
posix: In getxattr, honor the wildcard '*'
Currently, the posix_xattr_fill performas a sys_getxattr
on all the keys requested, there are requirements where
the keys could contain a wildcard, in which case sys_getxattr
would return ENODATA, eg: if the xattr requested is user.*
all the xattrs with prefix user. should be returned, with their
values.
This patch, changes posix_xattr_fill, to honor wildcard in the keys
requested.
Updates #297
Change-Id: I3d52da2957ac386fca3c156e26ff4cdf0b2c79a9
Signed-off-by: Poornima G <pgurusid@redhat.com>
| -rw-r--r-- | xlators/storage/posix/src/posix-helpers.c | 64 | ||||
| -rw-r--r-- | xlators/storage/posix/src/posix.h | 2 | 
2 files changed, 43 insertions, 23 deletions
diff --git a/xlators/storage/posix/src/posix-helpers.c b/xlators/storage/posix/src/posix-helpers.c index fa9a120ebcd..90afced604c 100644 --- a/xlators/storage/posix/src/posix-helpers.c +++ b/xlators/storage/posix/src/posix-helpers.c @@ -422,7 +422,9 @@ _posix_xattr_get_set (dict_t *xattr_req, char *key, data_t *data,          int       _fd      = -1;          loc_t    *loc      = NULL;          ssize_t  req_size  = 0; - +        int32_t  list_offset = 0; +        ssize_t  remaining_size = 0; +        char     *xattr    = NULL;          if (posix_xattr_ignorable (key))                  goto out; @@ -542,13 +544,20 @@ _posix_xattr_get_set (dict_t *xattr_req, char *key, data_t *data,                                                 filler->stbuf->ia_size);                  }          } else { -                ret = _posix_xattr_get_set_from_backend (filler, key); +                remaining_size = filler->list_size; +                while (remaining_size > 0) { +                        xattr = filler->list + list_offset; +                        if (fnmatch (key, xattr, 0) == 0) +                                ret = _posix_xattr_get_set_from_backend (filler, +                                                                         xattr); +                        remaining_size -= strlen (xattr) + 1; +                        list_offset += strlen (xattr) + 1; +                }          }  out:          return 0;  } -  int  posix_fill_gfid_path (xlator_t *this, const char *path, struct iatt *iatt)  { @@ -751,42 +760,50 @@ out:          return ret;  } +  static void -_handle_list_xattr (dict_t *xattr_req, const char *real_path, int fdnum, -                    posix_xattr_filler_t *filler) +_get_list_xattr (posix_xattr_filler_t *filler)  {          ssize_t               size                  = 0; -        char                 *list                  = NULL; -        int32_t               list_offset           = 0; -        ssize_t               remaining_size        = 0; -        char                  *key                  = NULL; -        if ((!real_path) && (fdnum < 0)) +        if ((!filler) && (!filler->real_path) && (filler->fdnum < 0))                  goto out; -        if (real_path) -                size = sys_llistxattr (real_path, NULL, 0); +        if (filler->real_path) +                size = sys_llistxattr (filler->real_path, NULL, 0);          else -                size = sys_flistxattr (fdnum, NULL, 0); +                size = sys_flistxattr (filler->fdnum, NULL, 0);          if (size <= 0)                  goto out; -        list = alloca (size); -        if (!list) +        filler->list = GF_CALLOC (1, size, gf_posix_mt_char); +        if (!filler->list)                  goto out; -        if (real_path) -                remaining_size = sys_llistxattr (real_path, list, size); +        if (filler->real_path) +                size = sys_llistxattr (filler->real_path, filler->list, size);          else -                remaining_size = sys_flistxattr (fdnum, list, size); +                size = sys_flistxattr (filler->fdnum, filler->list, size); -        if (remaining_size <= 0) -                goto out; +        filler->list_size = size; +out: +        return; +} + + +static void +_handle_list_xattr (dict_t *xattr_req, const char *real_path, int fdnum, +                    posix_xattr_filler_t *filler) +{ +        int32_t               list_offset           = 0; +        ssize_t               remaining_size        = 0; +        char                  *key                  = NULL;          list_offset = 0; +        remaining_size = filler->list_size;          while (remaining_size > 0) { -                key = list + list_offset; +                key = filler->list + list_offset;                  if (gf_get_index_by_elem (list_xattr_ignore_xattrs, key) >= 0)                          goto next; @@ -809,7 +826,6 @@ next:                  list_offset += strlen (key) + 1;          } /* while (remaining_size > 0) */ -out:          return;  } @@ -837,12 +853,14 @@ posix_xattr_fill (xlator_t *this, const char *real_path, loc_t *loc, fd_t *fd,          filler.stbuf     = buf;          filler.loc       = loc;          filler.fd        = fd; -        filler.fdnum    = fdnum; +        filler.fdnum     = fdnum; +        _get_list_xattr (&filler);          dict_foreach (xattr_req, _posix_xattr_get_set, &filler);          if (list)                  _handle_list_xattr (xattr_req, real_path, fdnum, &filler); +        GF_FREE (filler.list);  out:          return xattr;  } diff --git a/xlators/storage/posix/src/posix.h b/xlators/storage/posix/src/posix.h index 330ed20b480..720c3011f5a 100644 --- a/xlators/storage/posix/src/posix.h +++ b/xlators/storage/posix/src/posix.h @@ -256,6 +256,8 @@ typedef struct {          int          fdnum;          int          flags;          int32_t     op_errno; +        char        *list; +        size_t       list_size;  } posix_xattr_filler_t;  typedef struct {  | 
