diff options
author | Anand Avati <avati@redhat.com> | 2013-09-11 00:49:57 -0700 |
---|---|---|
committer | Anand Avati <avati@redhat.com> | 2013-09-17 11:41:42 -0700 |
commit | 8eb3898578a4fe359934da57c0e51cfaa21685d4 (patch) | |
tree | ac3a141a243ea17e27addebef5ed9aa4008753f1 /api/src | |
parent | a5b74203589f1c06d86d50fb56940571bfc13e20 (diff) |
gfapi: use native STACK_WIND for read _async() calls
There is little value in using synctask wrappers for async IO
requests, as STACK_WIND is asynchronous by nature already.
Skip going through synctask for read/write async calls.
Change-Id: Ifde331d7c97e0f33426da6ef4377c5ba70dddc06
BUG: 1009134
Signed-off-by: Anand Avati <avati@redhat.com>
Reviewed-on: http://review.gluster.org/5897
Diffstat (limited to 'api/src')
-rw-r--r-- | api/src/glfs-fops.c | 91 |
1 files changed, 81 insertions, 10 deletions
diff --git a/api/src/glfs-fops.c b/api/src/glfs-fops.c index 8df237fd37b..e411f5a8304 100644 --- a/api/src/glfs-fops.c +++ b/api/src/glfs-fops.c @@ -587,10 +587,6 @@ glfs_io_async_task (void *data) ssize_t ret = 0; switch (gio->op) { - case GF_FOP_READ: - ret = glfs_preadv (gio->glfd, gio->iov, gio->count, - gio->offset, gio->flags); - break; case GF_FOP_WRITE: ret = glfs_pwritev (gio->glfd, gio->iov, gio->count, gio->offset, gio->flags); @@ -614,23 +610,90 @@ glfs_io_async_task (void *data) int +glfs_preadv_async_cbk (call_frame_t *frame, void *cookie, xlator_t *this, + int op_ret, int op_errno, struct iovec *iovec, + int count, struct iatt *stbuf, struct iobref *iobref, + dict_t *xdata) +{ + struct glfs_io *gio = NULL; + xlator_t *subvol = NULL; + struct glfs *fs = NULL; + struct glfs_fd *glfd = NULL; + + + gio = frame->local; + frame->local = NULL; + subvol = cookie; + glfd = gio->glfd; + fs = glfd->fs; + + if (op_ret <= 0) + goto out; + + op_ret = iov_copy (gio->iov, gio->count, iovec, count); + + glfd->offset = gio->offset + op_ret; +out: + errno = op_errno; + gio->fn (gio->glfd, op_ret, gio->data); + + GF_FREE (gio->iov); + GF_FREE (gio); + STACK_DESTROY (frame->root); + glfs_subvol_done (fs, subvol); + + return 0; +} + + +int glfs_preadv_async (struct glfs_fd *glfd, const struct iovec *iovec, int count, off_t offset, int flags, glfs_io_cbk fn, void *data) { struct glfs_io *gio = NULL; int ret = 0; + call_frame_t *frame = NULL; + xlator_t *subvol = NULL; + glfs_t *fs = NULL; + fd_t *fd = NULL; + + __glfs_entry_fd (glfd); + + subvol = glfs_active_subvol (glfd->fs); + if (!subvol) { + ret = -1; + errno = EIO; + goto out; + } + + fd = glfs_resolve_fd (glfd->fs, subvol, glfd); + if (!fd) { + ret = -1; + errno = EBADFD; + goto out; + } + + fs = glfd->fs; + + frame = syncop_create_frame (THIS); + if (!frame) { + ret = -1; + errno = ENOMEM; + goto out; + } gio = GF_CALLOC (1, sizeof (*gio), glfs_mt_glfs_io_t); if (!gio) { + ret = -1; errno = ENOMEM; - return -1; + goto out; } gio->iov = iov_dup (iovec, count); if (!gio->iov) { - GF_FREE (gio); + ret = -1; errno = ENOMEM; - return -1; + goto out; } gio->op = GF_FOP_READ; @@ -641,15 +704,23 @@ glfs_preadv_async (struct glfs_fd *glfd, const struct iovec *iovec, int count, gio->fn = fn; gio->data = data; - ret = synctask_new (glfs_from_glfd (glfd)->ctx->env, - glfs_io_async_task, glfs_io_async_cbk, - NULL, gio); + frame->local = gio; + STACK_WIND_COOKIE (frame, glfs_preadv_async_cbk, subvol, subvol, + subvol->fops->readv, fd, iov_length (iovec, count), + offset, flags, NULL); + +out: if (ret) { GF_FREE (gio->iov); GF_FREE (gio); + STACK_DESTROY (frame->root); + glfs_subvol_done (fs, subvol); } + if (fd) + fd_unref (fd); + return ret; } |