diff options
| author | Amar Tumballi <amar@gluster.com> | 2012-01-18 18:06:44 +0530 | 
|---|---|---|
| committer | Anand Avati <avati@gluster.com> | 2012-01-25 02:03:44 -0800 | 
| commit | cf8486cbef329ef66868f658fa35f470f97db462 (patch) | |
| tree | 18cf37bd7cf65ac820d435fb1ee43dc205a2917b /xlators | |
| parent | b02afc6d008f9959db28244eb2b9dd3b9ef92393 (diff) | |
core: get xattrs also as part of readdirp
readdirp_req() call sends a dict_t * as an argument, which
contains all the xattr keys for which the entries got in
readdirp_rsp() are having xattr value filled dictionary.
Change-Id: I8b7e1290740ea3e884e67d19156ce849227167c0
Signed-off-by: Amar Tumballi <amar@gluster.com>
BUG: 765785
Reviewed-on: http://review.gluster.com/771
Tested-by: Gluster Build System <jenkins@build.gluster.com>
Reviewed-by: Anand Avati <avati@gluster.com>
Diffstat (limited to 'xlators')
33 files changed, 515 insertions, 110 deletions
diff --git a/xlators/cluster/afr/src/afr-common.c b/xlators/cluster/afr/src/afr-common.c index 83b91cd3ed1..c9a8b59554a 100644 --- a/xlators/cluster/afr/src/afr-common.c +++ b/xlators/cluster/afr/src/afr-common.c @@ -957,6 +957,11 @@ afr_local_cleanup (afr_local_t *local, xlator_t *this)                  if (local->cont.opendir.checksum)                          GF_FREE (local->cont.opendir.checksum);          } + +        { /* readdirp */ +                if (local->cont.readdir.dict) +                        dict_unref (local->cont.readdir.dict); +        }  } diff --git a/xlators/cluster/afr/src/afr-dir-read.c b/xlators/cluster/afr/src/afr-dir-read.c index d41102e7eea..389515e3c36 100644 --- a/xlators/cluster/afr/src/afr-dir-read.c +++ b/xlators/cluster/afr/src/afr-dir-read.c @@ -570,7 +570,8 @@ afr_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,                                             children[next_call_child],                                             children[next_call_child]->fops->readdirp,                                             local->fd, -                                           local->cont.readdir.size, 0); +                                           local->cont.readdir.size, 0, +                                           local->cont.readdir.dict);                          return 0;                  }          } @@ -612,7 +613,8 @@ afr_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,                                                     (void *) (long) read_child,                                                     children[call_child],                                                     children[call_child]->fops->readdirp, -                                                   local->fd, local->cont.readdir.size, offset); +                                                   local->fd, local->cont.readdir.size, offset, +                                                   local->cont.readdir.dict);                                  return 0;                          }                  } else { @@ -628,7 +630,7 @@ out:  int32_t  afr_do_readdir (call_frame_t *frame, xlator_t *this, -                fd_t *fd, size_t size, off_t offset, int whichop) +                fd_t *fd, size_t size, off_t offset, int whichop, dict_t *dict)  {          afr_private_t *  priv       = NULL;          xlator_t **      children   = NULL; @@ -673,6 +675,7 @@ afr_do_readdir (call_frame_t *frame, xlator_t *this,          local->fd                  = fd_ref (fd);          local->cont.readdir.size   = size; +        local->cont.readdir.dict   = (dict)? dict_ref (dict) : NULL;          if (priv->strict_readdir) {                  ret = fd_ctx_get (fd, this, &ctx); @@ -709,7 +712,7 @@ afr_do_readdir (call_frame_t *frame, xlator_t *this,                                     (void *) (long) call_child,                                     children[call_child],                                     children[call_child]->fops->readdirp, fd, -                                   size, offset); +                                   size, offset, dict);          ret = 0;  out: @@ -723,16 +726,16 @@ int32_t  afr_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,               off_t offset)  { -        afr_do_readdir (frame, this, fd, size, offset, GF_FOP_READDIR); +        afr_do_readdir (frame, this, fd, size, offset, GF_FOP_READDIR, NULL);          return 0;  }  int32_t  afr_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -              off_t offset) +              off_t offset, dict_t *dict)  { -        afr_do_readdir (frame, this, fd, size, offset, GF_FOP_READDIRP); +        afr_do_readdir (frame, this, fd, size, offset, GF_FOP_READDIRP, dict);          return 0;  } diff --git a/xlators/cluster/afr/src/afr-dir-read.h b/xlators/cluster/afr/src/afr-dir-read.h index 6a6bc635414..7e50a1c8cc8 100644 --- a/xlators/cluster/afr/src/afr-dir-read.h +++ b/xlators/cluster/afr/src/afr-dir-read.h @@ -35,7 +35,7 @@ afr_readdir (call_frame_t *frame, xlator_t *this,  int32_t  afr_readdirp (call_frame_t *frame, xlator_t *this, -	     fd_t *fd, size_t size, off_t offset); +              fd_t *fd, size_t size, off_t offset, dict_t *dict);  int32_t  afr_checksum (call_frame_t *frame, xlator_t *this, diff --git a/xlators/cluster/afr/src/afr-self-heal-entry.c b/xlators/cluster/afr/src/afr-self-heal-entry.c index ba29656e2cd..ed1c51a2172 100644 --- a/xlators/cluster/afr/src/afr-self-heal-entry.c +++ b/xlators/cluster/afr/src/afr-self-heal-entry.c @@ -832,7 +832,7 @@ afr_sh_entry_expunge_subvol (call_frame_t *frame, xlator_t *this,          STACK_WIND (frame, afr_sh_entry_expunge_readdir_cbk,                      priv->children[active_src],                      priv->children[active_src]->fops->readdirp, -                    sh->healing_fd, sh->block_size, sh->offset); +                    sh->healing_fd, sh->block_size, sh->offset, NULL);          return 0;  } @@ -1889,7 +1889,7 @@ afr_sh_entry_impunge_subvol (call_frame_t *frame, xlator_t *this,          STACK_WIND (frame, afr_sh_entry_impunge_readdir_cbk,                      priv->children[active_src],                      priv->children[active_src]->fops->readdirp, -                    sh->healing_fd, sh->block_size, sh->offset); +                    sh->healing_fd, sh->block_size, sh->offset, 0);          return 0;  } diff --git a/xlators/cluster/afr/src/afr-self-heald.c b/xlators/cluster/afr/src/afr-self-heald.c index f360ec33df8..186d7dd26a5 100644 --- a/xlators/cluster/afr/src/afr-self-heald.c +++ b/xlators/cluster/afr/src/afr-self-heald.c @@ -177,7 +177,7 @@ _crawl_directory (loc_t *loc, pid_t pid)                  goto out;          } -        while (syncop_readdirp (this, fd, 131072, offset, &entries)) { +        while (syncop_readdirp (this, fd, 131072, offset, NULL, &entries)) {                  ret = 0;                  free_entries = _gf_true;                  if (afr_up_children_count (priv->child_up, diff --git a/xlators/cluster/afr/src/afr.h b/xlators/cluster/afr/src/afr.h index 0ff3000857c..889828a6fa6 100644 --- a/xlators/cluster/afr/src/afr.h +++ b/xlators/cluster/afr/src/afr.h @@ -495,7 +495,7 @@ typedef struct _afr_local {                          int32_t op_errno;                          size_t size;                          off_t offset; - +                        dict_t *dict;                          gf_boolean_t failed;                          int last_index;                  } readdir; diff --git a/xlators/cluster/afr/src/pump.c b/xlators/cluster/afr/src/pump.c index 73389009d68..357aa9f295f 100644 --- a/xlators/cluster/afr/src/pump.c +++ b/xlators/cluster/afr/src/pump.c @@ -362,7 +362,7 @@ gf_pump_traverse_directory (loc_t *loc)                  "pump opendir on %s returned=%d",                  loc->path, ret); -        while (syncop_readdirp (this, fd, 131072, offset, &entries)) { +        while (syncop_readdirp (this, fd, 131072, offset, NULL, &entries)) {                  free_entries = _gf_true;                  if (list_empty (&entries.list)) { @@ -2195,11 +2195,8 @@ pump_readdir (call_frame_t *frame,  static int32_t -pump_readdirp (call_frame_t *frame, -               xlator_t *this, -               fd_t *fd, -               size_t size, -               off_t off) +pump_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, +               size_t size, off_t off, dict_t *dict)  {          afr_private_t *priv  = NULL;  	priv = this->private; @@ -2208,10 +2205,10 @@ pump_readdirp (call_frame_t *frame,                              default_readdirp_cbk,                              FIRST_CHILD(this),                              FIRST_CHILD(this)->fops->readdirp, -                            fd, size, off); +                            fd, size, off, dict);                  return 0;          } -        afr_readdirp (frame, this, fd, size, off); +        afr_readdirp (frame, this, fd, size, off, dict);          return 0;  } diff --git a/xlators/cluster/dht/src/dht-common.c b/xlators/cluster/dht/src/dht-common.c index d371fc442da..a16ed7b6c50 100644 --- a/xlators/cluster/dht/src/dht-common.c +++ b/xlators/cluster/dht/src/dht-common.c @@ -2616,7 +2616,8 @@ done:                  STACK_WIND (frame, dht_readdirp_cbk,                              next_subvol, next_subvol->fops->readdirp, -                            local->fd, local->size, next_offset); +                            local->fd, local->size, next_offset, +                            local->xattr_req);                  return 0;          } @@ -2730,7 +2731,7 @@ unwind:  int  dht_do_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -                off_t yoff, int whichop) +                off_t yoff, int whichop, dict_t *dict)  {          dht_local_t  *local  = NULL;          int           op_errno = -1; @@ -2750,6 +2751,7 @@ dht_do_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,          local->fd = fd_ref (fd);          local->size = size; +        local->xattr_req = (dict)? dict_ref (dict) : NULL;          dht_deitransform (this, yoff, &xvol, (uint64_t *)&xoff); @@ -2759,7 +2761,7 @@ dht_do_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,                              fd, size, xoff);          else                  STACK_WIND (frame, dht_readdirp_cbk, xvol, xvol->fops->readdirp, -                            fd, size, xoff); +                            fd, size, xoff, dict);          return 0; @@ -2794,15 +2796,15 @@ dht_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,                  op = GF_FOP_READDIRP;  out: -        dht_do_readdir (frame, this, fd, size, yoff, op); +        dht_do_readdir (frame, this, fd, size, yoff, op, 0);          return 0;  }  int  dht_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -              off_t yoff) +              off_t yoff, dict_t *dict)  { -        dht_do_readdir (frame, this, fd, size, yoff, GF_FOP_READDIRP); +        dht_do_readdir (frame, this, fd, size, yoff, GF_FOP_READDIRP, dict);          return 0;  } @@ -3988,7 +3990,7 @@ dht_rmdir_opendir_cbk (call_frame_t *frame, void *cookie, xlator_t *this,          STACK_WIND (frame, dht_rmdir_readdirp_cbk,                      prev->this, prev->this->fops->readdirp, -                    local->fd, 4096, 0); +                    local->fd, 4096, 0, NULL);          return 0; diff --git a/xlators/cluster/dht/src/dht-common.h b/xlators/cluster/dht/src/dht-common.h index 791cf633507..8a0765b63f9 100644 --- a/xlators/cluster/dht/src/dht-common.h +++ b/xlators/cluster/dht/src/dht-common.h @@ -555,7 +555,7 @@ int32_t dht_readdir (call_frame_t  *frame,  int32_t dht_readdirp (call_frame_t *frame,                        xlator_t *this,                        fd_t     *fd, -                      size_t    size, off_t off); +                      size_t    size, off_t off, dict_t *dict);  int32_t dht_xattrop (call_frame_t           *frame,                       xlator_t           *this, diff --git a/xlators/cluster/stripe/src/stripe.c b/xlators/cluster/stripe/src/stripe.c index 15cfb8f60e9..086f07f92ca 100644 --- a/xlators/cluster/stripe/src/stripe.c +++ b/xlators/cluster/stripe/src/stripe.c @@ -3563,6 +3563,7 @@ stripe_readv_cbk (call_frame_t *frame, void *cookie, xlator_t *this,          stripe_local_t *local = NULL;          struct iovec   *final_vec = NULL;          struct iatt     tmp_stbuf = {0,}; +        struct iatt    *tmp_stbuf_p = NULL; //need it for a warning          struct iobref  *tmp_iobref = NULL;          stripe_fd_ctx_t  *fctx = NULL; @@ -3660,7 +3661,8 @@ stripe_readv_cbk (call_frame_t *frame, void *cookie, xlator_t *this,                  GF_FREE (mlocal->replies);                  tmp_iobref = mlocal->iobref;                  /* work around for nfs truncated read. Bug 3774 */ -                WIPE (&tmp_stbuf); +                tmp_stbuf_p = &tmp_stbuf; +                WIPE (tmp_stbuf_p);                  STRIPE_STACK_UNWIND (readv, mframe, op_ret, op_errno, final_vec,                                       final_count, &tmp_stbuf, tmp_iobref); @@ -4348,7 +4350,7 @@ out:  }  int32_t  stripe_readdirp (call_frame_t *frame, xlator_t *this, -                 fd_t *fd, size_t size, off_t off) +                 fd_t *fd, size_t size, off_t off, dict_t *dict)  {          stripe_local_t  *local  = NULL;          stripe_private_t *priv = NULL; @@ -4390,7 +4392,7 @@ stripe_readdirp (call_frame_t *frame, xlator_t *this,                  goto err;          STACK_WIND (frame, stripe_readdirp_cbk, trav->xlator, -                    trav->xlator->fops->readdirp, fd, size, off); +                    trav->xlator->fops->readdirp, fd, size, off, dict);          return 0;  err:          op_errno = (op_errno == -1) ? errno : op_errno; diff --git a/xlators/debug/error-gen/src/error-gen.c b/xlators/debug/error-gen/src/error-gen.c index 909dc681ebe..7e776332f09 100644 --- a/xlators/debug/error-gen/src/error-gen.c +++ b/xlators/debug/error-gen/src/error-gen.c @@ -1807,7 +1807,7 @@ error_gen_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,  int  error_gen_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -                    off_t off) +                    off_t off, dict_t *dict)  {  	int              op_errno = 0;          eg_t            *egp = NULL; @@ -1828,7 +1828,7 @@ error_gen_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,  	STACK_WIND (frame, error_gen_readdirp_cbk,                      FIRST_CHILD(this),                      FIRST_CHILD(this)->fops->readdirp, -                    fd, size, off); +                    fd, size, off, dict);  	return 0;  } diff --git a/xlators/debug/io-stats/src/io-stats.c b/xlators/debug/io-stats/src/io-stats.c index d216cc549ec..923470b8757 100644 --- a/xlators/debug/io-stats/src/io-stats.c +++ b/xlators/debug/io-stats/src/io-stats.c @@ -2220,7 +2220,7 @@ io_stats_opendir (call_frame_t *frame, xlator_t *this,  int  io_stats_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -                   off_t offset) +                   off_t offset, dict_t *dict)  {          frame->local = fd->inode;          START_FOP_LATENCY (frame); @@ -2228,7 +2228,7 @@ io_stats_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,          STACK_WIND (frame, io_stats_readdirp_cbk,                      FIRST_CHILD(this),                      FIRST_CHILD(this)->fops->readdirp, -                    fd, size, offset); +                    fd, size, offset, dict);          return 0;  } diff --git a/xlators/debug/trace/src/trace.c b/xlators/debug/trace/src/trace.c index 88e413c1d71..91d069fd1eb 100644 --- a/xlators/debug/trace/src/trace.c +++ b/xlators/debug/trace/src/trace.c @@ -1986,20 +1986,21 @@ trace_opendir (call_frame_t *frame, xlator_t *this, loc_t *loc, fd_t *fd)  int  trace_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -                off_t offset) +                off_t offset, dict_t *dict)  {          if (trace_fop_names[GF_FOP_READDIRP].enabled) {                  gf_log (this->name, GF_LOG_INFO, -                        "%"PRId64": gfid=%s fd=%p, size=%"GF_PRI_SIZET", offset=%"PRId64, +                        "%"PRId64": gfid=%s fd=%p, size=%"GF_PRI_SIZET", " +                        "offset=%"PRId64" dict=%p",                          frame->root->unique, uuid_utoa (fd->inode->gfid), -                        fd, size, offset); +                        fd, size, offset, dict);                  frame->local = fd->inode->gfid;          }          STACK_WIND (frame, trace_readdirp_cbk,                      FIRST_CHILD(this),                      FIRST_CHILD(this)->fops->readdirp, -                    fd, size, offset); +                    fd, size, offset, dict);          return 0;  } diff --git a/xlators/features/locks/src/posix.c b/xlators/features/locks/src/posix.c index 0914d16df41..9025feb950a 100644 --- a/xlators/features/locks/src/posix.c +++ b/xlators/features/locks/src/posix.c @@ -1496,6 +1496,67 @@ out:          return 0;  } +int +pl_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this, +                 int op_ret, int op_errno, gf_dirent_t *entries) +{ +        pl_local_t *local  = NULL; +        gf_dirent_t *entry = NULL; + +        local = frame->local; + +        if (op_ret <= 0) +                goto unwind; + +        list_for_each_entry (entry, &entries->list, list) { +                if (local->entrylk_count_req) +                        pl_entrylk_xattr_fill (this, entry->inode, entry->dict); +                if (local->inodelk_count_req) +                        pl_inodelk_xattr_fill (this, entry->inode, entry->dict); +                if (local->posixlk_count_req) +                        pl_posixlk_xattr_fill (this, entry->inode, entry->dict); +        } + +unwind: +        frame->local = NULL; +        STACK_UNWIND_STRICT (readdirp, frame, op_ret, op_errno, entries); + +        if (local) +                GF_FREE (local); + +        return 0; +} + +int +pl_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, +             off_t offset, dict_t *dict) +{ +        pl_local_t *local  = NULL; + +        local = GF_CALLOC (1, sizeof (*local), gf_locks_mt_pl_local_t); +        GF_VALIDATE_OR_GOTO (this->name, local, out); + +        if (dict) { +                if (dict_get (dict, GLUSTERFS_ENTRYLK_COUNT)) +                        local->entrylk_count_req = 1; +                if (dict_get (dict, GLUSTERFS_INODELK_COUNT)) +                        local->inodelk_count_req = 1; +                if (dict_get (dict, GLUSTERFS_POSIXLK_COUNT)) +                        local->posixlk_count_req = 1; +        } + +        frame->local = local; + +        STACK_WIND (frame, pl_readdirp_cbk, +                    FIRST_CHILD(this), FIRST_CHILD(this)->fops->readdirp, +                    fd, size, offset, dict); + +        return 0; +out: +        STACK_UNWIND_STRICT (readdirp, frame, -1, ENOMEM, NULL); +        return 0; +} +  void  pl_dump_lock (char *str, int size, struct gf_flock *flock, @@ -1920,6 +1981,8 @@ struct xlator_fops fops = {          .fentrylk    = pl_fentrylk,          .flush       = pl_flush,          .opendir     = pl_opendir, + +        .readdirp    = pl_readdirp,  };  struct xlator_dumpops dumpops = { diff --git a/xlators/features/marker/src/marker-quota.c b/xlators/features/marker/src/marker-quota.c index 227c4951b35..6f324aca361 100644 --- a/xlators/features/marker/src/marker-quota.c +++ b/xlators/features/marker/src/marker-quota.c @@ -2129,9 +2129,11 @@ mq_req_xattr (xlator_t *this,          int32_t               ret       = -1;          GF_VALIDATE_OR_GOTO ("marker", this, out); -        GF_VALIDATE_OR_GOTO ("marker", loc, out);          GF_VALIDATE_OR_GOTO ("marker", dict, out); +        if (!loc) +                goto set_size; +          //if not "/" then request contribution          if (strcmp (loc->path, "/") == 0)                  goto set_size; diff --git a/xlators/features/marker/src/marker.c b/xlators/features/marker/src/marker.c index 93b1518cb7e..291e24bdc6b 100644 --- a/xlators/features/marker/src/marker.c +++ b/xlators/features/marker/src/marker.c @@ -2188,6 +2188,47 @@ err:          return 0;  } +int +marker_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this, +                     int op_ret, int op_errno, gf_dirent_t *entries) +{ +        gf_dirent_t *entry = NULL; + +        if (op_ret <= 0) +                goto unwind; + +        list_for_each_entry (entry, &entries->list, list) { +                /* TODO: fill things */ +        } + +unwind: +        STACK_UNWIND_STRICT (readdirp, frame, op_ret, op_errno, entries); + +        return 0; +} +int +marker_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, +                 off_t offset, dict_t *dict) +{ +        marker_conf_t  *priv    = NULL; + +        priv = this->private; + +        if (priv->feature_enabled == 0) +                goto wind; + +        if ((priv->feature_enabled & GF_QUOTA) && dict) +                mq_req_xattr (this, NULL, dict); + +wind: +        STACK_WIND (frame, marker_readdirp_cbk, +                    FIRST_CHILD(this), FIRST_CHILD(this)->fops->readdirp, +                    fd, size, offset, dict); + +        return 0; +} + +  int32_t  mem_acct_init (xlator_t *this)  { @@ -2479,7 +2520,8 @@ struct xlator_fops fops = {          .setattr     = marker_setattr,          .fsetattr    = marker_fsetattr,          .removexattr = marker_removexattr, -        .getxattr    = marker_getxattr +        .getxattr    = marker_getxattr, +        .readdirp    = marker_readdirp,  };  struct xlator_cbks cbks = { diff --git a/xlators/features/quiesce/src/quiesce.c b/xlators/features/quiesce/src/quiesce.c index 84df12a31ff..57b2cdeacb0 100644 --- a/xlators/features/quiesce/src/quiesce.c +++ b/xlators/features/quiesce/src/quiesce.c @@ -661,7 +661,8 @@ quiesce_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,          if ((op_ret == -1) && (op_errno == ENOTCONN)) {                  /* Re-transmit (by putting in the queue) */                  stub = fop_readdirp_stub (frame, default_readdirp_resume, -                                          local->fd, local->size, local->offset); +                                          local->fd, local->size, local->offset, +                                          local->dict);                  if (!stub) {                          STACK_UNWIND_STRICT (readdirp, frame, -1, ENOMEM,                                               NULL); @@ -2257,7 +2258,7 @@ quiesce_readdirp (call_frame_t *frame,  		  xlator_t *this,  		  fd_t *fd,  		  size_t size, -		  off_t off) +		  off_t off, dict_t *dict)  {  	quiesce_priv_t *priv = NULL;          call_stub_t    *stub = NULL; @@ -2270,17 +2271,19 @@ quiesce_readdirp (call_frame_t *frame,                  local->fd = fd_ref (fd);                  local->size = size;                  local->offset = off; +                local->dict = dict_ref (dict);                  frame->local = local;                  STACK_WIND (frame,                              quiesce_readdirp_cbk,                              FIRST_CHILD(this),                              FIRST_CHILD(this)->fops->readdirp, -                            fd, size, off); +                            fd, size, off, dict);  	        return 0;          } -        stub = fop_readdirp_stub (frame, default_readdirp_resume, fd, size, off); +        stub = fop_readdirp_stub (frame, default_readdirp_resume, fd, size, +                                  off, dict);          if (!stub) {                  STACK_UNWIND_STRICT (readdirp, frame, -1, ENOMEM, NULL);                  return 0; diff --git a/xlators/features/quota/src/quota.c b/xlators/features/quota/src/quota.c index b2f53048f84..79172999ac7 100644 --- a/xlators/features/quota/src/quota.c +++ b/xlators/features/quota/src/quota.c @@ -2815,6 +2815,47 @@ quota_statfs (call_frame_t *frame, xlator_t *this, loc_t *loc)  } +int +quota_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this, +                    int op_ret, int op_errno, gf_dirent_t *entries) +{ +        gf_dirent_t *entry = NULL; + +        if (op_ret <= 0) +                goto unwind; + +        list_for_each_entry (entry, &entries->list, list) { +                /* TODO: fill things */ +        } + +unwind: +        STACK_UNWIND_STRICT (readdirp, frame, op_ret, op_errno, entries); + +        return 0; +} +int +quota_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, +                off_t offset, dict_t *dict) +{ +        int ret = 0; + +        if (dict) { +                ret = dict_set_uint64 (dict, QUOTA_SIZE_KEY, 0); +                if (ret < 0) { +                        goto err; +                } +        } + +        STACK_WIND (frame, quota_readdirp_cbk, +                    FIRST_CHILD(this), FIRST_CHILD(this)->fops->readdirp, +                    fd, size, offset, dict); +        return 0; +err: +        STACK_UNWIND_STRICT (readdirp, frame, -1, EINVAL, NULL); +        return 0; +} + +  int32_t  mem_acct_init (xlator_t *this)  { @@ -3020,7 +3061,8 @@ struct xlator_fops fops = {          .fsetattr  = quota_fsetattr,          .mknod     = quota_mknod,          .setxattr  = quota_setxattr, -        .fsetxattr = quota_fsetxattr +        .fsetxattr = quota_fsetxattr, +        .readdirp  = quota_readdirp,  };  struct xlator_cbks cbks = { diff --git a/xlators/mount/fuse/src/fuse-bridge.c b/xlators/mount/fuse/src/fuse-bridge.c index 7409488c1f9..4aee4963761 100644 --- a/xlators/mount/fuse/src/fuse-bridge.c +++ b/xlators/mount/fuse/src/fuse-bridge.c @@ -2385,6 +2385,9 @@ fuse_readdir_cbk (call_frame_t *frame, void *cookie, xlator_t *this,          send_fuse_data (this, finh, buf, size); +        /* TODO: */ +        /* gf_link_inodes_from_dirent (this, state->fd->inode, entries); */ +  out:          free_fuse_state (state);          STACK_DESTROY (frame->root); diff --git a/xlators/nfs/server/src/nfs-fops.c b/xlators/nfs/server/src/nfs-fops.c index c6199d129eb..5c4ce2f96f4 100644 --- a/xlators/nfs/server/src/nfs-fops.c +++ b/xlators/nfs/server/src/nfs-fops.c @@ -610,7 +610,7 @@ nfs_fop_readdirp (xlator_t *nfsx, xlator_t *xl, nfs_user_t *nfu, fd_t *dirfd,          nfs_fop_handle_local_init (frame, nfsx, nfl, cbk, local, ret, err);          STACK_WIND_COOKIE (frame, nfs_fop_readdirp_cbk, xl, xl, -                           xl->fops->readdirp, dirfd, bufsize, offset); +                           xl->fops->readdirp, dirfd, bufsize, offset, 0);          ret = 0;  err: diff --git a/xlators/performance/io-cache/src/io-cache.c b/xlators/performance/io-cache/src/io-cache.c index 009e7cf28e1..65df006cfe4 100644 --- a/xlators/performance/io-cache/src/io-cache.c +++ b/xlators/performance/io-cache/src/io-cache.c @@ -1409,6 +1409,35 @@ ioc_lk (call_frame_t *frame, xlator_t *this, fd_t *fd, int32_t cmd,          return 0;  } +int +ioc_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this, +                  int op_ret, int op_errno, gf_dirent_t *entries) +{ +        gf_dirent_t *entry = NULL; + +        if (op_ret <= 0) +                goto unwind; + +        list_for_each_entry (entry, &entries->list, list) { +                /* TODO: fill things */ +        } + +unwind: +        STACK_UNWIND_STRICT (readdirp, frame, op_ret, op_errno, entries); + +        return 0; +} +int +ioc_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, +              off_t offset, dict_t *dict) +{ +        STACK_WIND (frame, ioc_readdirp_cbk, +                    FIRST_CHILD(this), FIRST_CHILD(this)->fops->readdirp, +                    fd, size, offset, dict); + +        return 0; +} +  int32_t  ioc_get_priority_list (const char *opt_str, struct list_head *first)  { @@ -1924,7 +1953,9 @@ struct xlator_fops fops = {          .lookup      = ioc_lookup,          .lk          = ioc_lk,          .setattr     = ioc_setattr, -        .mknod       = ioc_mknod +        .mknod       = ioc_mknod, + +        .readdirp    = ioc_readdirp,  }; diff --git a/xlators/performance/io-threads/src/io-threads.c b/xlators/performance/io-threads/src/io-threads.c index d6d0ada23e4..e4077478182 100644 --- a/xlators/performance/io-threads/src/io-threads.c +++ b/xlators/performance/io-threads/src/io-threads.c @@ -1840,23 +1840,23 @@ iot_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,  int  iot_readdirp_wrapper (call_frame_t *frame, xlator_t *this, fd_t *fd, -                      size_t size, off_t offset) +                      size_t size, off_t offset, dict_t *dict)  {          STACK_WIND (frame, iot_readdirp_cbk, FIRST_CHILD (this), -                    FIRST_CHILD (this)->fops->readdirp, fd, size, offset); +                    FIRST_CHILD (this)->fops->readdirp, fd, size, offset, dict);          return 0;  }  int  iot_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -              off_t offset) +              off_t offset, dict_t *dict)  {          call_stub_t     *stub = NULL;          int             ret = -1;          stub = fop_readdirp_stub (frame, iot_readdirp_wrapper, fd, size, -                                  offset); +                                  offset, dict);          if (!stub) {                  gf_log (this->private, GF_LOG_ERROR,"cannot get readdir stub"                          "(out of memory)"); diff --git a/xlators/performance/stat-prefetch/src/stat-prefetch.c b/xlators/performance/stat-prefetch/src/stat-prefetch.c index 73cc3a955d8..827a9f99d28 100644 --- a/xlators/performance/stat-prefetch/src/stat-prefetch.c +++ b/xlators/performance/stat-prefetch/src/stat-prefetch.c @@ -1351,8 +1351,8 @@ out:  int32_t -sp_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -            off_t off) +sp_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, +             off_t off, dict_t *dict)  {          sp_cache_t *cache    = NULL;          sp_local_t *local    = NULL; @@ -1401,7 +1401,7 @@ sp_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size,          }          STACK_WIND (frame, sp_readdir_cbk, FIRST_CHILD(this), -                    FIRST_CHILD(this)->fops->readdirp, fd, size, off); +                    FIRST_CHILD(this)->fops->readdirp, fd, size, off, dict);          return 0; @@ -1414,6 +1414,12 @@ unwind:          return 0;  } +int32_t +sp_readdir (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, +            off_t off) +{ +        return sp_readdirp (frame, this, fd, size, off, NULL); +}  int32_t  sp_truncate_cbk (call_frame_t *frame, void *cookie, xlator_t *this, @@ -4215,7 +4221,7 @@ out:  struct xlator_fops fops = {          .lookup      = sp_lookup,          .readdir     = sp_readdir, -        .readdirp    = sp_readdir, +        .readdirp    = sp_readdirp,          .open        = sp_open,          .create      = sp_create,          .opendir     = sp_opendir, diff --git a/xlators/protocol/client/src/client-helpers.c b/xlators/protocol/client/src/client-helpers.c index 2a12573e2bb..5759f30624e 100644 --- a/xlators/protocol/client/src/client-helpers.c +++ b/xlators/protocol/client/src/client-helpers.c @@ -154,15 +154,21 @@ out:  }  int -unserialize_rsp_direntp (struct gfs3_readdirp_rsp *rsp, gf_dirent_t *entries) +unserialize_rsp_direntp (xlator_t *this, fd_t *fd, +                         struct gfs3_readdirp_rsp *rsp, gf_dirent_t *entries)  {          struct gfs3_dirplist *trav      = NULL; +        char                 *buf       = NULL;  	gf_dirent_t          *entry     = NULL; +        inode_table_t        *itable    = NULL;          int                   entry_len = 0;          int                   ret       = -1;          trav = rsp->reply; +        if (fd) +                itable = fd->inode->table; +          while (trav) {                  entry_len = gf_dirent_size (trav->name);                  entry = GF_CALLOC (1, entry_len, gf_common_mt_gf_dirent_t); @@ -178,6 +184,28 @@ unserialize_rsp_direntp (struct gfs3_readdirp_rsp *rsp, gf_dirent_t *entries)                  strcpy (entry->d_name, trav->name); +                if (trav->dict.dict_val) { +                        /* Dictionary is sent along with response */ +                        buf = memdup (trav->dict.dict_val, trav->dict.dict_len); +                        if (!buf) +                                goto out; + +                        ret = dict_unserialize (buf, trav->dict.dict_len, +                                                &entry->dict); +                        if (ret < 0) { +                                gf_log (THIS->name, GF_LOG_WARNING, +                                        "failed to unserialize xattr dict"); +                                errno = EINVAL; +                                goto out; +                        } +                        entry->dict->extra_free = buf; +                        buf = NULL; +                } + +                entry->inode = inode_find (itable, entry->d_stat.ia_gfid); +                if (!entry->inode) +                        entry->inode = inode_new (itable); +  		list_add_tail (&entry->list, &entries->list);                  trav = trav->nextentry; diff --git a/xlators/protocol/client/src/client.c b/xlators/protocol/client/src/client.c index 87a4603c191..8e823bec4e8 100644 --- a/xlators/protocol/client/src/client.c +++ b/xlators/protocol/client/src/client.c @@ -1671,7 +1671,7 @@ out:  int32_t  client_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, -                 size_t size, off_t off) +                 size_t size, off_t off, dict_t *dict)  {          int          ret  = -1;          clnt_conf_t *conf = NULL; @@ -1685,6 +1685,7 @@ client_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd,          args.fd = fd;          args.size = size;          args.offset = off; +        args.xattr_req = dict;          proc = &conf->fops->proctable[GF_FOP_READDIRP];          if (!proc) { diff --git a/xlators/protocol/client/src/client.h b/xlators/protocol/client/src/client.h index 6d0b6491a10..00b743a3c70 100644 --- a/xlators/protocol/client/src/client.h +++ b/xlators/protocol/client/src/client.h @@ -184,7 +184,8 @@ int protocol_client_reopendir (xlator_t *this, clnt_fd_ctx_t *fdctx);  int protocol_client_reopen (xlator_t *this, clnt_fd_ctx_t *fdctx);  int unserialize_rsp_dirent (struct gfs3_readdir_rsp *rsp, gf_dirent_t *entries); -int unserialize_rsp_direntp (struct gfs3_readdirp_rsp *rsp, gf_dirent_t *entries); +int unserialize_rsp_direntp (xlator_t *this, fd_t *fd, +                             struct gfs3_readdirp_rsp *rsp, gf_dirent_t *entries);  int clnt_readdir_rsp_cleanup (gfs3_readdir_rsp *rsp);  int clnt_readdirp_rsp_cleanup (gfs3_readdirp_rsp *rsp); diff --git a/xlators/protocol/client/src/client3_1-fops.c b/xlators/protocol/client/src/client3_1-fops.c index 036e297de38..d34ffc20031 100644 --- a/xlators/protocol/client/src/client3_1-fops.c +++ b/xlators/protocol/client/src/client3_1-fops.c @@ -1914,12 +1914,12 @@ int  client3_1_readdirp_cbk (struct rpc_req *req, struct iovec *iov, int count,                          void *myframe)  { -        call_frame_t           *frame = NULL; -        gfs3_readdirp_rsp       rsp   = {0,}; -        int32_t                 ret   = 0; -        clnt_local_t         *local = NULL; -        gf_dirent_t             entries; -        xlator_t         *this       = NULL; +        call_frame_t      *frame = NULL; +        gfs3_readdirp_rsp  rsp   = {0,}; +        int32_t            ret   = 0; +        clnt_local_t      *local = NULL; +        gf_dirent_t        entries; +        xlator_t          *this  = NULL;          this = THIS; @@ -1943,7 +1943,7 @@ client3_1_readdirp_cbk (struct rpc_req *req, struct iovec *iov, int count,          INIT_LIST_HEAD (&entries.list);          if (rsp.op_ret > 0) { -                unserialize_rsp_direntp (&rsp, &entries); +                unserialize_rsp_direntp (this, local->fd, &rsp, &entries);          }  out: @@ -5073,6 +5073,7 @@ client3_1_readdirp (call_frame_t *frame, xlator_t *this,          struct iovec     *rsphdr            = NULL;          struct iovec      vector[MAX_IOVEC] = {{0}, };          clnt_local_t     *local             = NULL; +        size_t            dict_len          = 0;          if (!frame || !this || !data)                  goto unwind; @@ -5085,23 +5086,23 @@ client3_1_readdirp (call_frame_t *frame, xlator_t *this,          readdirp_rsp_size = xdr_sizeof ((xdrproc_t) xdr_gfs3_readdirp_rsp, &rsp)                  + args->size; +        local = GF_CALLOC (1, sizeof (*local), +                           gf_client_mt_clnt_local_t); +        if (!local) { +                op_errno = ENOMEM; +                goto unwind; +        } +        frame->local = local; +          if ((readdirp_rsp_size + GLUSTERFS_RPC_REPLY_SIZE               + GLUSTERFS_RDMA_MAX_HEADER_SIZE)              > (GLUSTERFS_RDMA_INLINE_THRESHOLD)) { -                local = GF_CALLOC (1, sizeof (*local), -                                   gf_client_mt_clnt_local_t); -                if (!local) { -                        op_errno = ENOMEM; -                        goto unwind; -                } -                frame->local = local; -                  rsp_iobref = iobref_new ();                  if (rsp_iobref == NULL) {                          goto unwind;                  } -                        /* TODO: what is the size we should send ? */ +                /* TODO: what is the size we should send ? */                  rsp_iobuf = iobuf_get (this->ctx->iobuf_pool);                  if (rsp_iobuf == NULL) {                          goto unwind; @@ -5111,19 +5112,33 @@ client3_1_readdirp (call_frame_t *frame, xlator_t *this,                  iobuf_unref (rsp_iobuf);                  rsphdr = &vector[0];                  rsphdr->iov_base = iobuf_ptr (rsp_iobuf); -                rsphdr->iov_len -                        = iobuf_pagesize (rsp_iobuf); +                rsphdr->iov_len  = iobuf_pagesize (rsp_iobuf);                  count = 1;                  rsp_iobuf = NULL;                  local->iobref = rsp_iobref;                  rsp_iobref = NULL;          } +        local->fd = fd_ref (args->fd); +          req.size = args->size;          req.offset = args->offset;          req.fd = remote_fd;          memcpy (req.gfid, args->fd->inode->gfid, 16); +        if (args->dict) { +                ret = dict_allocate_and_serialize (args->dict, +                                                   &req.dict.dict_val, +                                                   &dict_len); +                if (ret < 0) { +                        gf_log (this->name, GF_LOG_WARNING, +                                "failed to get serialized dict"); +                        op_errno = EINVAL; +                        goto unwind; +                } +                req.dict.dict_len = dict_len; +        } +          ret = client_submit_request (this, &req, frame, conf->fops,                                       GFS3_OP_READDIRP,                                       client3_1_readdirp_cbk, NULL, diff --git a/xlators/protocol/server/src/server-helpers.c b/xlators/protocol/server/src/server-helpers.c index 43f60e0e2e4..4980424d350 100644 --- a/xlators/protocol/server/src/server-helpers.c +++ b/xlators/protocol/server/src/server-helpers.c @@ -1327,11 +1327,40 @@ serialize_rsp_direntp (gf_dirent_t *entries, gfs3_readdirp_rsp *rsp)                  trav->d_off  = entry->d_off;                  trav->d_len  = entry->d_len;                  trav->d_type = entry->d_type; -                //trav->name   = memdup (entry->d_name, entry->d_len + 1);                  trav->name   = entry->d_name;                  gf_stat_from_iatt (&trav->stat, &entry->d_stat); +                /* if 'dict' is present, pack it */ +                if (entry->dict) { +                        trav->dict.dict_len = dict_serialized_length (entry->dict); +                        if (trav->dict.dict_len < 0) { +                                gf_log (THIS->name, GF_LOG_ERROR, +                                        "failed to get serialized length " +                                        "of reply dict"); +                                errno = EINVAL; +                                trav->dict.dict_len = 0; +                                goto out; +                        } + +                        trav->dict.dict_val = GF_CALLOC (1, trav->dict.dict_len, +                                                         gf_server_mt_rsp_buf_t); +                        if (!trav->dict.dict_val) { +                                errno = ENOMEM; +                                trav->dict.dict_len = 0; +                                goto out; +                        } + +                        ret = dict_serialize (entry->dict, trav->dict.dict_val); +                        if (ret < 0) { +                                gf_log (THIS->name, GF_LOG_ERROR, +                                        "failed to serialize reply dict"); +                                errno = -ret; +                                trav->dict.dict_len = 0; +                                goto out; +                        } +                } +                  if (prev)                          prev->nextentry = trav;                  else diff --git a/xlators/protocol/server/src/server.h b/xlators/protocol/server/src/server.h index f261752171d..92785c5a9d6 100644 --- a/xlators/protocol/server/src/server.h +++ b/xlators/protocol/server/src/server.h @@ -154,7 +154,7 @@ struct _server_state {          fd_t             *fd;          dict_t           *params; -        int               flags; +        int32_t           flags;          int               wbflags;          struct iovec      payload_vector[MAX_IOVEC];          int               payload_count; diff --git a/xlators/protocol/server/src/server3_1-fops.c b/xlators/protocol/server/src/server3_1-fops.c index c2ab3590ed2..482c242d5ce 100644 --- a/xlators/protocol/server/src/server3_1-fops.c +++ b/xlators/protocol/server/src/server3_1-fops.c @@ -1038,7 +1038,6 @@ server_link_cbk (call_frame_t *frame, void *cookie, xlator_t *this,                  gf_stat_from_iatt (&rsp.preparent, preparent);                  gf_stat_from_iatt (&rsp.postparent, postparent); -                  link_inode = inode_link (inode, state->loc2.parent,                                           state->loc2.name, stbuf);                  inode_unref (link_inode); @@ -1738,6 +1737,10 @@ server_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,                          op_errno = ENOMEM;                          goto out;                  } + +                /* TODO: need more clear thoughts before calling this function. */ +                /* gf_link_inodes_from_dirent (this, state->fd->inode, entries); */ +          } else {                  /* (op_ret == 0) is valid, and means EOF, don't log for that */                  gf_log (this->name, (op_ret) ? GF_LOG_INFO : GF_LOG_TRACE, @@ -2132,7 +2135,7 @@ server_readdirp_resume (call_frame_t *frame, xlator_t *bound_xl)          STACK_WIND (frame, server_readdirp_cbk, bound_xl,                      bound_xl->fops->readdirp, state->fd, state->size, -                    state->offset); +                    state->offset, state->dict);          return 0;  err: @@ -3979,10 +3982,10 @@ server_readdirp (rpcsvc_request_t *req)  {          server_state_t      *state        = NULL;          call_frame_t        *frame        = NULL; +        char                *buf          = NULL;          gfs3_readdirp_req    args         = {{0,},};          size_t               headers_size = 0;          int                  ret          = -1; -          if (!req)                  return ret; @@ -4023,6 +4026,29 @@ server_readdirp (rpcsvc_request_t *req)          state->offset = args.offset;          memcpy (state->resolve.gfid, args.gfid, 16); +        if (args.dict.dict_len) { +                /* Unserialize the dictionary */ +                state->dict = dict_new (); + +                buf = memdup (args.dict.dict_val, args.dict.dict_len); +                if (buf == NULL) { +                        goto out; +                } + +                ret = dict_unserialize (buf, args.dict.dict_len, +                                        &state->dict); +                if (ret < 0) { +                        gf_log (state->conn->bound_xl->name, GF_LOG_ERROR, +                                "%"PRId64": failed to unserialize req-buffer " +                                " to dictionary", frame->root->unique); +                        goto out; +                } + +                state->dict->extra_free = buf; + +                buf = NULL; +        } +          ret = 0;          resolve_and_resume (frame, server_readdirp_resume);  out: diff --git a/xlators/storage/posix/src/posix-helpers.c b/xlators/storage/posix/src/posix-helpers.c index 31a4e667d17..346e6a7a640 100644 --- a/xlators/storage/posix/src/posix-helpers.c +++ b/xlators/storage/posix/src/posix-helpers.c @@ -170,7 +170,7 @@ _posix_xattr_get_set (dict_t *xattr_req,                  }          } else if (!strcmp (key, GLUSTERFS_OPEN_FD_COUNT)) {                  loc = filler->loc; -                if (!list_empty (&loc->inode->fd_list)) { +                if (loc && !list_empty (&loc->inode->fd_list)) {                          ret = dict_set_uint32 (filler->xattr, key, 1);                          if (ret < 0)                                  gf_log (filler->this->name, GF_LOG_WARNING, diff --git a/xlators/storage/posix/src/posix.c b/xlators/storage/posix/src/posix.c index 7f82431e88b..f895aec2b06 100644 --- a/xlators/storage/posix/src/posix.c +++ b/xlators/storage/posix/src/posix.c @@ -3386,10 +3386,27 @@ out:          return count;  } +dict_t * +posix_entry_xattr_fill (xlator_t *this, inode_t *inode, +                        fd_t *fd, char *name, dict_t *dict, +                        struct iatt *stbuf) +{ +        loc_t  tmp_loc    = {0,}; +        char  *entry_path = NULL; + +        /* if we don't send the 'loc', open-fd-count be a problem. */ +        tmp_loc.inode = inode; + +        MAKE_HANDLE_PATH (entry_path, this, fd->inode->gfid, name); + +        return posix_lookup_xattr_fill (this, entry_path, +                                        &tmp_loc, dict, stbuf); + +}  int32_t  posix_do_readdir (call_frame_t *frame, xlator_t *this, -                  fd_t *fd, size_t size, off_t off, int whichop) +                  fd_t *fd, size_t size, off_t off, int whichop, dict_t *dict)  {          struct posix_fd      *pfd            = NULL;          DIR                  *dir            = NULL; @@ -3400,6 +3417,7 @@ posix_do_readdir (call_frame_t *frame, xlator_t *this,          gf_dirent_t           entries;          struct iatt           stbuf          = {0, };          gf_dirent_t          *tmp_entry      = NULL; +        inode_table_t        *itable         = NULL;  #ifdef IGNORE_READDIRP_ATTRS          uuid_t                gfid;          ia_type_t             entry_type     = 0; @@ -3432,33 +3450,47 @@ posix_do_readdir (call_frame_t *frame, xlator_t *this,          /* pick ENOENT to indicate EOF */          op_errno = errno; +        op_ret = count; + +        if (whichop != GF_FOP_READDIRP) +                goto out; -        if (whichop == GF_FOP_READDIRP) { -                list_for_each_entry (tmp_entry, &entries.list, list) { +        itable = fd->inode->table; + +        list_for_each_entry (tmp_entry, &entries.list, list) {  #ifdef IGNORE_READDIRP_ATTRS -                        ret = inode_grep_for_gfid (fd->inode->table, fd->inode, -                                                   tmp_entry->d_name, gfid, -                                                   &entry_type); -                        if (ret == 0) { -                                memset (&stbuf, 0, sizeof (stbuf)); -                                uuid_copy (stbuf.ia_gfid, gfid); -                                posix_fill_ino_from_gfid (this, &stbuf); -                                stbuf.ia_type = entry_type; -                        } else { -                                posix_istat (this, fd->inode->gfid, -                                             tmp_entry->d_name, &stbuf); -                        } -#else +                ret = inode_grep_for_gfid (fd->inode->table, fd->inode, +                                           tmp_entry->d_name, gfid, +                                           &entry_type); +                if (ret == 0) { +                        memset (&stbuf, 0, sizeof (stbuf)); +                        uuid_copy (stbuf.ia_gfid, gfid); +                        posix_fill_ino_from_gfid (this, &stbuf); +                        stbuf.ia_type = entry_type; +                } else {                          posix_istat (this, fd->inode->gfid,                                       tmp_entry->d_name, &stbuf); +                } +#else +                posix_istat (this, fd->inode->gfid, +                             tmp_entry->d_name, &stbuf);  #endif -                        if (stbuf.ia_ino) -                                tmp_entry->d_ino = stbuf.ia_ino; -                        tmp_entry->d_stat = stbuf; +                if (stbuf.ia_ino) +                        tmp_entry->d_ino = stbuf.ia_ino; + +                if (dict) { +                        tmp_entry->inode = inode_find (itable, stbuf.ia_gfid); +                        if (!tmp_entry->inode) +                                tmp_entry->inode = inode_new (itable); + +                        tmp_entry->dict = +                                posix_entry_xattr_fill (this, tmp_entry->inode, +                                                        fd, tmp_entry->d_name, +                                                        dict, &stbuf);                  } -        } -        op_ret = count; +                tmp_entry->d_stat = stbuf; +        }  out:          STACK_UNWIND_STRICT (readdir, frame, op_ret, op_errno, &entries); @@ -3473,16 +3505,16 @@ int32_t  posix_readdir (call_frame_t *frame, xlator_t *this,                 fd_t *fd, size_t size, off_t off)  { -        posix_do_readdir (frame, this, fd, size, off, GF_FOP_READDIR); +        posix_do_readdir (frame, this, fd, size, off, GF_FOP_READDIR, NULL);          return 0;  }  int32_t  posix_readdirp (call_frame_t *frame, xlator_t *this, -                fd_t *fd, size_t size, off_t off) +                fd_t *fd, size_t size, off_t off, dict_t *dict)  { -        posix_do_readdir (frame, this, fd, size, off, GF_FOP_READDIRP); +        posix_do_readdir (frame, this, fd, size, off, GF_FOP_READDIRP, dict);          return 0;  } diff --git a/xlators/system/posix-acl/src/posix-acl.c b/xlators/system/posix-acl/src/posix-acl.c index 9a425ff13dd..8c84231476e 100644 --- a/xlators/system/posix-acl/src/posix-acl.c +++ b/xlators/system/posix-acl/src/posix-acl.c @@ -1427,8 +1427,62 @@ int  posix_acl_readdirp_cbk (call_frame_t *frame, void *cookie, xlator_t *this,                          int op_ret, int op_errno, gf_dirent_t *entries)  { -        if (op_ret != 0) +        gf_dirent_t      *entry       = NULL; +        struct posix_acl *acl_access  = NULL; +        struct posix_acl *acl_default = NULL; +        struct posix_acl *old_access  = NULL; +        struct posix_acl *old_default = NULL; +        data_t           *data        = NULL; +        int               ret         = 0; + +        if (op_ret <= 0)                  goto unwind; + +        list_for_each_entry (entry, &entries->list, list) { +                /* Update the inode ctx */ +                if (!entry->dict || !entry->inode) +                        continue; + +                ret = posix_acl_get (entry->inode, this, +                                     &old_access, &old_default); + +                data = dict_get (entry->dict, POSIX_ACL_ACCESS_XATTR); +                if (!data) +                        goto acl_default; + +                if (old_access && +                    posix_acl_matches_xattr (this, old_access, data->data, +                                             data->len)) { +                        acl_access = posix_acl_ref (this, old_access); +                } else { +                        acl_access = posix_acl_from_xattr (this, data->data, +                                                           data->len); +                } + +        acl_default: +                data = dict_get (entry->dict, POSIX_ACL_DEFAULT_XATTR); +                if (!data) +                        goto acl_set; + +                if (old_default && +                    posix_acl_matches_xattr (this, old_default, data->data, +                                             data->len)) { +                        acl_default = posix_acl_ref (this, old_default); +                } else { +                        acl_default = posix_acl_from_xattr (this, data->data, +                                                            data->len); +                } + +        acl_set: +                posix_acl_ctx_update (entry->inode, this, &entry->d_stat); + +                ret = posix_acl_set (entry->inode, this, +                                     acl_access, acl_default); +                if (ret) +                        gf_log (this->name, GF_LOG_WARNING, +                                "failed to set ACL in context"); +        } +  unwind:          STACK_UNWIND_STRICT (readdirp, frame, op_ret, op_errno, entries);          return 0; @@ -1437,16 +1491,33 @@ unwind:  int  posix_acl_readdirp (call_frame_t *frame, xlator_t *this, fd_t *fd, size_t size, -                   off_t offset) +                    off_t offset, dict_t *dict)  { +        int ret = 0; +          if (acl_permits (frame, fd->inode, POSIX_ACL_READ))                  goto green;          else                  goto red;  green: +        if (dict) { +                ret = dict_set_int8 (dict, POSIX_ACL_ACCESS_XATTR, 0); +                if (ret) +                        gf_log (this->name, GF_LOG_WARNING, +                                "failed to set key %s", +                                POSIX_ACL_ACCESS_XATTR); + +                ret = dict_set_int8 (dict, POSIX_ACL_DEFAULT_XATTR, 0); +                if (ret) +                        gf_log (this->name, GF_LOG_WARNING, +                                "failed to set key %s", +                                POSIX_ACL_DEFAULT_XATTR); +        } +          STACK_WIND (frame, posix_acl_readdirp_cbk,                      FIRST_CHILD(this), FIRST_CHILD(this)->fops->readdirp, -                    fd, size, offset); +                    fd, size, offset, dict); +          return 0;  red:          STACK_UNWIND_STRICT (readdirp, frame, -1, EACCES, NULL);  | 
