diff options
author | Amar Tumballi <amarts@redhat.com> | 2017-12-22 13:12:42 +0530 |
---|---|---|
committer | Amar Tumballi <amarts@redhat.com> | 2018-01-19 22:48:39 +0530 |
commit | 303cc2b54797bc5371be742543ccb289010c92f2 (patch) | |
tree | cf383488d0edff81b012b5e908f8ebca7affaea3 /xlators/protocol/client | |
parent | 9eefff096fd9b54120e4347b6b00f10a6c502cf4 (diff) |
protocol: make on-wire-change of protocol using new XDR definition.
With this patchset, some major things are changed in XDR, mainly:
* Naming: Instead of gfs3/gfs4 settle for gfx_ for xdr structures
* add iattx as a separate structure, and add conversion methods
* the *_rsp structure is now changed, and is also reduced in number
(ie, no need for different strucutes if it is similar to other response).
* use proper XDR methods for sending dict on wire.
Also, with the change of xdr structure, there are changes needed
outside of xlator protocol layer to handle these properly. Mainly
because the abstraction was broken to support 0-copy RDMA with payload
for write and read FOP. This made transport layer know about the xdr
payload, hence with the change of xdr payload structure, transport layer
needed to know about the change.
Updates #384
Change-Id: I1448fbe9deab0a1b06cb8351f2f37488cefe461f
Signed-off-by: Amar Tumballi <amarts@redhat.com>
Diffstat (limited to 'xlators/protocol/client')
-rw-r--r-- | xlators/protocol/client/src/Makefile.am | 3 | ||||
-rw-r--r-- | xlators/protocol/client/src/client-common.c | 1441 | ||||
-rw-r--r-- | xlators/protocol/client/src/client-common.h | 240 | ||||
-rw-r--r-- | xlators/protocol/client/src/client-helpers.c | 1302 | ||||
-rw-r--r-- | xlators/protocol/client/src/client-rpc-fops.c | 295 | ||||
-rw-r--r-- | xlators/protocol/client/src/client-rpc-fops_v2.c | 5952 | ||||
-rw-r--r-- | xlators/protocol/client/src/client.h | 91 |
7 files changed, 9029 insertions, 295 deletions
diff --git a/xlators/protocol/client/src/Makefile.am b/xlators/protocol/client/src/Makefile.am index 899db91e683..785a51fc3b4 100644 --- a/xlators/protocol/client/src/Makefile.am +++ b/xlators/protocol/client/src/Makefile.am @@ -9,7 +9,8 @@ client_la_LIBADD = $(top_builddir)/libglusterfs/src/libglusterfs.la \ $(top_builddir)/rpc/xdr/src/libgfxdr.la client_la_SOURCES = client.c client-helpers.c client-rpc-fops.c \ - client-handshake.c client-callback.c client-lk.c client-common.c + client-handshake.c client-callback.c client-lk.c client-common.c \ + client-rpc-fops_v2.c noinst_HEADERS = client.h client-mem-types.h client-messages.h client-common.h diff --git a/xlators/protocol/client/src/client-common.c b/xlators/protocol/client/src/client-common.c index 873b0f0f4ae..3b4dea1aff1 100644 --- a/xlators/protocol/client/src/client-common.c +++ b/xlators/protocol/client/src/client-common.c @@ -12,6 +12,7 @@ #include "xlator.h" #include "rpc-common-xdr.h" #include "glusterfs3-xdr.h" +#include "glusterfs4-xdr.h" #include "glusterfs3.h" #include "client.h" @@ -2159,3 +2160,1443 @@ client_post_lease (xlator_t *this, gfs3_lease_rsp *rsp, struct gf_lease *lease, out: return ret; } + + +/* New PRE and POST functions */ + +int +client_post_common_iatt (xlator_t *this, gfx_common_iatt_rsp *rsp, struct iatt *iatt, + dict_t **xdata) +{ + if (-1 != rsp->op_ret) { + gfx_stat_to_iattx (&rsp->stat, iatt); + } + + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_common_2iatt (xlator_t *this, gfx_common_2iatt_rsp *rsp, struct iatt *iatt, + struct iatt *iatt2, dict_t **xdata) +{ + if (-1 != rsp->op_ret) { + gfx_stat_to_iattx (&rsp->prestat, iatt); + gfx_stat_to_iattx (&rsp->poststat, iatt2); + } + + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_common_3iatt (xlator_t *this, gfx_common_3iatt_rsp *rsp, struct iatt *iatt, + struct iatt *iatt2, struct iatt *iatt3, dict_t **xdata) +{ + if (-1 != rsp->op_ret) { + gfx_stat_to_iattx (&rsp->stat, iatt); + gfx_stat_to_iattx (&rsp->preparent, iatt2); + gfx_stat_to_iattx (&rsp->postparent, iatt3); + } + + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_common_dict (xlator_t *this, gfx_common_dict_rsp *rsp, dict_t **dict, + dict_t **xdata) +{ + int ret = 0; + ret = xdr_to_dict (&rsp->dict, dict); + if (ret) + gf_msg_debug (this->name, EINVAL, + "while decoding found empty dictionary"); + xdr_to_dict (&rsp->xdata, xdata); + + return ret; +} + +int +client_post_readv_v2 (xlator_t *this, gfx_read_rsp *rsp, struct iobref **iobref, + struct iobref *rsp_iobref, struct iatt *stat, + struct iovec *vector, struct iovec *rsp_vector, + int *rspcount, dict_t **xdata) +{ + int ret = -1; + + if (rsp->op_ret != -1) { + *iobref = rsp_iobref; + gfx_stat_to_iattx (&rsp->stat, stat); + + vector[0].iov_len = rsp->op_ret; + if (rsp->op_ret > 0) + vector[0].iov_base = rsp_vector->iov_base; + *rspcount = 1; + } + + ret = xdr_to_dict (&rsp->xdata, xdata); + +#ifdef GF_TESTING_IO_XDATA + dict_dump_to_log (xdata); +#endif + return ret; +} + +int +client_pre_stat_v2 (xlator_t *this, gfx_stat_req *req, loc_t *loc, + dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_readlink_v2 (xlator_t *this, gfx_readlink_req *req, loc_t *loc, + size_t size, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->size = size; + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_mknod_v2 (xlator_t *this, gfx_mknod_req *req, loc_t *loc, + mode_t mode, dev_t rdev, mode_t umask, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->parent)) + goto out; + + if (!gf_uuid_is_null (loc->parent->gfid)) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->pargfid)), + out, op_errno, EINVAL); + req->bname = (char *)loc->name; + req->mode = mode; + req->dev = rdev; + req->umask = umask; + + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_mkdir_v2 (xlator_t *this, gfx_mkdir_req *req, loc_t *loc, + mode_t mode, mode_t umask, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->parent)) + goto out; + + if (!gf_uuid_is_null (loc->parent->gfid)) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->pargfid)), + out, op_errno, EINVAL); + + req->bname = (char *)loc->name; + req->mode = mode; + req->umask = umask; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_unlink_v2 (xlator_t *this, gfx_unlink_req *req, loc_t *loc, + int32_t flags, dict_t *xdata) +{ + int op_errno = 0; + + if (!(loc && loc->parent)) + goto out; + + if (!gf_uuid_is_null (loc->parent->gfid)) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->pargfid)), + out, op_errno, EINVAL); + req->bname = (char *)loc->name; + req->xflags = flags; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_rmdir_v2 (xlator_t *this, gfx_rmdir_req *req, loc_t *loc, + int32_t flags, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->parent)) + goto out; + + if (!gf_uuid_is_null (loc->parent->gfid)) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->pargfid)), + out, op_errno, EINVAL); + req->bname = (char *)loc->name; + req->xflags = flags; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_symlink_v2 (xlator_t *this, gfx_symlink_req *req, loc_t *loc, + const char *linkname, mode_t umask, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->parent)) + goto out; + + if (!gf_uuid_is_null (loc->parent->gfid)) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->pargfid)), + out, op_errno, EINVAL); + req->linkname = (char *)linkname; + req->bname = (char *)loc->name; + req->umask = umask; + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_rename_v2 (xlator_t *this, gfx_rename_req *req, loc_t *oldloc, + loc_t *newloc, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(oldloc && newloc && oldloc->parent && + newloc->parent)) + goto out; + + if (!gf_uuid_is_null (oldloc->parent->gfid)) + memcpy (req->oldgfid, oldloc->parent->gfid, 16); + else + memcpy (req->oldgfid, oldloc->pargfid, 16); + + if (!gf_uuid_is_null (newloc->parent->gfid)) + memcpy (req->newgfid, newloc->parent->gfid, 16); + else + memcpy (req->newgfid, newloc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->oldgfid)), + out, op_errno, EINVAL); + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->newgfid)), + out, op_errno, EINVAL); + req->oldbname = (char *)oldloc->name; + req->newbname = (char *)newloc->name; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_link_v2 (xlator_t *this, + gfx_link_req *req, loc_t *oldloc, loc_t *newloc, + dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(oldloc && oldloc->inode && newloc && + newloc->parent)) + goto out; + + if (!gf_uuid_is_null (oldloc->inode->gfid)) + memcpy (req->oldgfid, oldloc->inode->gfid, 16); + else + memcpy (req->oldgfid, oldloc->gfid, 16); + + if (!gf_uuid_is_null (newloc->parent->gfid)) + memcpy (req->newgfid, newloc->parent->gfid, 16); + else + memcpy (req->newgfid, newloc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->oldgfid)), + out, op_errno, EINVAL); + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->newgfid)), + out, op_errno, EINVAL); + req->newbname = (char *)newloc->name; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_truncate_v2 (xlator_t *this, gfx_truncate_req *req, + loc_t *loc, off_t offset, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->offset = offset; + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_open_v2 (xlator_t *this, gfx_open_req *req, loc_t *loc, fd_t *fd, + int32_t flags, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->flags = gf_flags_from_flags (flags); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_readv_v2 (xlator_t *this, gfx_read_req *req, fd_t *fd, size_t size, + off_t offset, int32_t flags, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, FALLBACK_TO_ANON_FD, + remote_fd, op_errno, out); + + req->size = size; + req->offset = offset; + req->fd = remote_fd; + req->flag = flags; + + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_writev_v2 (xlator_t *this, gfx_write_req *req, + fd_t *fd, size_t size, off_t offset, int32_t flags, + dict_t **xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, FALLBACK_TO_ANON_FD, + remote_fd, op_errno, out); + + req->size = size; + req->offset = offset; + req->fd = remote_fd; + req->flag = flags; + + memcpy (req->gfid, fd->inode->gfid, 16); + +#ifdef GF_TESTING_IO_XDATA + if (!*xdata) + *xdata = dict_new (); + + ret = dict_set_str (*xdata, "testing-the-xdata-key", + "testing-the-xdata-value"); +#endif + + dict_to_xdr (*xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_statfs_v2 (xlator_t *this, gfx_statfs_req *req, loc_t *loc, + dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!loc) + goto out; + + if (loc->inode) { + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + } else { + req->gfid[15] = 1; + } + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_flush_v2 (xlator_t *this, gfx_flush_req *req, fd_t *fd, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fsync_v2 (xlator_t *this, gfx_fsync_req *req, fd_t *fd, + int32_t flags, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = 0; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->data = flags; + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_setxattr_v2 (xlator_t *this, gfx_setxattr_req *req, loc_t *loc, + dict_t *xattr, int32_t flags, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + if (xattr) { + dict_to_xdr (xattr, &req->dict); + } + + req->flags = flags; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_getxattr_v2 (xlator_t *this, gfx_getxattr_req *req, loc_t *loc, + const char *name, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!loc) { + op_errno = EINVAL; + goto out; + } + + if (loc->inode && !gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->namelen = 1; /* Use it as a flag */ + + req->name = (char *)name; + if (!req->name) { + req->name = ""; + req->namelen = 0; + } + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_removexattr_v2 (xlator_t *this, gfx_removexattr_req *req, + loc_t *loc, const char *name, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->name = (char *)name; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_opendir_v2 (xlator_t *this, + gfx_opendir_req *req, loc_t *loc, + fd_t *fd, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fsyncdir_v2 (xlator_t *this, gfx_fsyncdir_req *req, fd_t *fd, + int32_t flags, dict_t *xdata) +{ + int32_t op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->data = flags; + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_access_v2 (xlator_t *this, gfx_access_req *req, loc_t *loc, + int32_t mask, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->mask = mask; + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_create_v2 (xlator_t *this, gfx_create_req *req, + loc_t *loc, fd_t *fd, mode_t mode, + int32_t flags, mode_t umask, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->parent)) + goto out; + + if (!gf_uuid_is_null (loc->parent->gfid)) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->pargfid)), + out, op_errno, EINVAL); + req->bname = (char *)loc->name; + req->mode = mode; + req->flags = gf_flags_from_flags (flags); + req->umask = umask; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_ftruncate_v2 (xlator_t *this, gfx_ftruncate_req *req, fd_t *fd, + off_t offset, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = EINVAL; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->offset = offset; + req->fd = remote_fd; + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_fstat_v2 (xlator_t *this, gfx_fstat_req *req, fd_t *fd, + dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_lk_v2 (xlator_t *this, gfx_lk_req *req, + int32_t cmd, struct gf_flock *flock, fd_t *fd, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + int32_t gf_cmd = 0; + int32_t gf_type = 0; + int ret = 0; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + ret = client_cmd_to_gf_cmd (cmd, &gf_cmd); + if (ret) { + op_errno = EINVAL; + gf_msg (this->name, GF_LOG_WARNING, EINVAL, + PC_MSG_INVALID_ENTRY, "Unknown cmd (%d)!", gf_cmd); + goto out; + } + + switch (flock->l_type) { + case F_RDLCK: + gf_type = GF_LK_F_RDLCK; + break; + case F_WRLCK: + gf_type = GF_LK_F_WRLCK; + break; + case F_UNLCK: + gf_type = GF_LK_F_UNLCK; + break; + } + + req->fd = remote_fd; + req->cmd = gf_cmd; + req->type = gf_type; + gf_proto_flock_from_flock (&req->flock, flock); + + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_lookup_v2 (xlator_t *this, gfx_lookup_req *req, loc_t *loc, + dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if ((loc->parent) && (!gf_uuid_is_null (loc->parent->gfid))) + memcpy (req->pargfid, loc->parent->gfid, 16); + else + memcpy (req->pargfid, loc->pargfid, 16); + + if ((loc->inode) && (!gf_uuid_is_null (loc->inode->gfid))) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + + if (loc->name) + req->bname = (char *)loc->name; + else + req->bname = ""; + + if (xdata) { + dict_to_xdr (xdata, &req->xdata); + } + return 0; +out: + return -op_errno; +} + +int +client_pre_readdir_v2 (xlator_t *this, gfx_readdir_req *req, fd_t *fd, + size_t size, off_t offset, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->size = size; + req->offset = offset; + req->fd = remote_fd; + + memcpy (req->gfid, fd->inode->gfid, 16); + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_inodelk_v2 (xlator_t *this, gfx_inodelk_req *req, loc_t *loc, + int cmd, struct gf_flock *flock, const char *volume, + dict_t *xdata) +{ + int op_errno = ESTALE; + int32_t gf_cmd = 0; + int32_t gf_type = 0; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->gfid)) + memcpy (req->gfid, loc->gfid, 16); + else + memcpy (req->gfid, loc->inode->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + if (cmd == F_GETLK || cmd == F_GETLK64) + gf_cmd = GF_LK_GETLK; + else if (cmd == F_SETLK || cmd == F_SETLK64) + gf_cmd = GF_LK_SETLK; + else if (cmd == F_SETLKW || cmd == F_SETLKW64) + gf_cmd = GF_LK_SETLKW; + else { + gf_msg (this->name, GF_LOG_WARNING, EINVAL, + PC_MSG_INVALID_ENTRY, "Unknown cmd (%d)!", gf_cmd); + op_errno = EINVAL; + goto out; + } + + switch (flock->l_type) { + case F_RDLCK: + gf_type = GF_LK_F_RDLCK; + break; + case F_WRLCK: + gf_type = GF_LK_F_WRLCK; + break; + case F_UNLCK: + gf_type = GF_LK_F_UNLCK; + break; + } + + req->volume = (char *)volume; + req->cmd = gf_cmd; + req->type = gf_type; + gf_proto_flock_from_flock (&req->flock, flock); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_finodelk_v2 (xlator_t *this, gfx_finodelk_req *req, fd_t *fd, + int cmd, struct gf_flock *flock, const char *volume, + dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + int32_t gf_type = 0; + int32_t gf_cmd = 0; + + CLIENT_GET_REMOTE_FD (this, fd, FALLBACK_TO_ANON_FD, + remote_fd, op_errno, out); + + if (cmd == F_GETLK || cmd == F_GETLK64) + gf_cmd = GF_LK_GETLK; + else if (cmd == F_SETLK || cmd == F_SETLK64) + gf_cmd = GF_LK_SETLK; + else if (cmd == F_SETLKW || cmd == F_SETLKW64) + gf_cmd = GF_LK_SETLKW; + else { + gf_msg (this->name, GF_LOG_WARNING, EINVAL, + PC_MSG_INVALID_ENTRY, "Unknown cmd (%d)!", gf_cmd); + goto out; + } + + switch (flock->l_type) { + case F_RDLCK: + gf_type = GF_LK_F_RDLCK; + break; + case F_WRLCK: + gf_type = GF_LK_F_WRLCK; + break; + case F_UNLCK: + gf_type = GF_LK_F_UNLCK; + break; + } + + req->volume = (char *)volume; + req->fd = remote_fd; + req->cmd = gf_cmd; + req->type = gf_type; + gf_proto_flock_from_flock (&req->flock, flock); + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_entrylk_v2 (xlator_t *this, gfx_entrylk_req *req, loc_t *loc, + entrylk_cmd cmd_entrylk, entrylk_type type, + const char *volume, const char *basename, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->gfid)) + memcpy (req->gfid, loc->gfid, 16); + else + memcpy (req->gfid, loc->inode->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + req->cmd = cmd_entrylk; + req->type = type; + req->volume = (char *)volume; + req->name = ""; + if (basename) { + req->name = (char *)basename; + req->namelen = 1; + } + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fentrylk_v2 (xlator_t *this, gfx_fentrylk_req *req, fd_t *fd, + entrylk_cmd cmd_entrylk, entrylk_type type, + const char *volume, const char *basename, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->cmd = cmd_entrylk; + req->type = type; + req->volume = (char *)volume; + req->name = ""; + if (basename) { + req->name = (char *)basename; + req->namelen = 1; + } + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_xattrop_v2 (xlator_t *this, gfx_xattrop_req *req, loc_t *loc, + dict_t *xattr, int32_t flags, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + dict_to_xdr (xattr, &req->dict); + + req->flags = flags; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fxattrop_v2 (xlator_t *this, gfx_fxattrop_req *req, fd_t *fd, + dict_t *xattr, int32_t flags, dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, FALLBACK_TO_ANON_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->flags = flags; + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xattr, &req->dict); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fgetxattr_v2 (xlator_t *this, gfx_fgetxattr_req *req, fd_t *fd, + const char *name, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->namelen = 1; /* Use it as a flag */ + req->fd = remote_fd; + req->name = (char *)name; + if (!req->name) { + req->name = ""; + req->namelen = 0; + } + memcpy (req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fsetxattr_v2 (xlator_t *this, gfx_fsetxattr_req *req, fd_t *fd, + int32_t flags, dict_t *xattr, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->flags = flags; + memcpy (req->gfid, fd->inode->gfid, 16); + + if (xattr) { + dict_to_xdr (xattr, &req->dict); + } + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_rchecksum_v2 (xlator_t *this, gfx_rchecksum_req *req, fd_t *fd, + int32_t len, off_t offset, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->len = len; + req->offset = offset; + req->fd = remote_fd; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_setattr_v2 (xlator_t *this, gfx_setattr_req *req, loc_t *loc, + int32_t valid, struct iatt *stbuf, dict_t *xdata) +{ + int op_errno = ESTALE; + + if (!(loc && loc->inode)) + return -op_errno; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + + req->valid = valid; + gfx_stat_from_iattx (&req->stbuf, stbuf); + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fsetattr_v2 (xlator_t *this, gfx_fsetattr_req *req, fd_t *fd, + int32_t valid, struct iatt *stbuf, dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + memcpy (req->gfid, fd->inode->gfid, 16); + req->fd = remote_fd; + req->valid = valid; + gfx_stat_from_iattx (&req->stbuf, stbuf); + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_readdirp_v2 (xlator_t *this, gfx_readdirp_req *req, fd_t *fd, + size_t size, off_t offset, dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->size = size; + req->offset = offset; + req->fd = remote_fd; + memcpy (req->gfid, fd->inode->gfid, 16); + + /* dict itself is 'xdata' here */ + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fremovexattr_v2 (xlator_t *this, gfx_fremovexattr_req *req, fd_t *fd, + const char *name, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + if (!(fd && fd->inode)) + goto out; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + memcpy (req->gfid, fd->inode->gfid, 16); + req->name = (char *)name; + req->fd = remote_fd; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_fallocate_v2 (xlator_t *this, gfx_fallocate_req *req, fd_t *fd, + int32_t flags, off_t offset, size_t size, dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->flags = flags; + req->offset = offset; + req->size = size; + memcpy(req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_discard_v2 (xlator_t *this, gfx_discard_req *req, fd_t *fd, + off_t offset, size_t size, dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->offset = offset; + req->size = size; + memcpy(req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_zerofill_v2 (xlator_t *this, gfx_zerofill_req *req, fd_t *fd, + off_t offset, size_t size, dict_t *xdata) +{ + int op_errno = ESTALE; + int64_t remote_fd = -1; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + req->fd = remote_fd; + req->offset = offset; + req->size = size; + memcpy(req->gfid, fd->inode->gfid, 16); + + dict_to_xdr (xdata, &req->xdata); + return 0; +out: + return -op_errno; +} + +int +client_pre_ipc_v2 (xlator_t *this, gfx_ipc_req *req, int32_t cmd, + dict_t *xdata) +{ + req->op = cmd; + + dict_to_xdr (xdata, &req->xdata); + return 0; +} + +int +client_pre_seek_v2 (xlator_t *this, gfx_seek_req *req, fd_t *fd, + off_t offset, gf_seek_what_t what, dict_t *xdata) +{ + int64_t remote_fd = -1; + int op_errno = ESTALE; + + CLIENT_GET_REMOTE_FD (this, fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, out); + + memcpy (req->gfid, fd->inode->gfid, 16); + req->fd = remote_fd; + req->offset = offset; + req->what = what; + + dict_to_xdr (xdata, &req->xdata); + + return 0; +out: + return -op_errno; +} + +int +client_pre_lease_v2 (xlator_t *this, gfx_lease_req *req, loc_t *loc, + struct gf_lease *lease, dict_t *xdata) +{ + int op_errno = 0; + + if (!(loc && loc->inode)) + goto out; + + if (!gf_uuid_is_null (loc->inode->gfid)) + memcpy (req->gfid, loc->inode->gfid, 16); + else + memcpy (req->gfid, loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req->gfid)), + out, op_errno, EINVAL); + + gf_proto_lease_from_lease (&req->lease, lease); + + dict_to_xdr (xdata, &req->xdata); +out: + return -op_errno; +} + +int +client_post_create_v2 (xlator_t *this, gfx_create_rsp *rsp, + struct iatt *stbuf, struct iatt *preparent, + struct iatt *postparent, + clnt_local_t *local, dict_t **xdata) +{ + if (-1 != rsp->op_ret) { + gfx_stat_to_iattx (&rsp->stat, stbuf); + + gfx_stat_to_iattx (&rsp->preparent, preparent); + gfx_stat_to_iattx (&rsp->postparent, postparent); + gf_uuid_copy (local->loc.gfid, stbuf->ia_gfid); + } + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_lease_v2 (xlator_t *this, gfx_lease_rsp *rsp, struct gf_lease *lease, + dict_t **xdata) +{ + if (rsp->op_ret >= 0) { + gf_proto_lease_to_lease (&rsp->lease, lease); + } + + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_lk_v2 (xlator_t *this, gfx_lk_rsp *rsp, struct gf_flock *lock, + dict_t **xdata) +{ + if (rsp->op_ret >= 0) { + gf_proto_flock_to_flock (&rsp->flock, lock); + } + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_readdir_v2 (xlator_t *this, gfx_readdir_rsp *rsp, + gf_dirent_t *entries, dict_t **xdata) +{ + if (rsp->op_ret > 0) { + unserialize_rsp_dirent_v2 (this, rsp, entries); + } + return xdr_to_dict (&rsp->xdata, xdata); +} + +int +client_post_readdirp_v2 (xlator_t *this, gfx_readdirp_rsp *rsp, + fd_t *fd, gf_dirent_t *entries, + dict_t **xdata) +{ + if (rsp->op_ret > 0) { + unserialize_rsp_direntp_v2 (this, fd, rsp, entries); + } + return xdr_to_dict (&rsp->xdata, xdata); +} + + + +int +client_post_rename_v2 (xlator_t *this, gfx_rename_rsp *rsp, struct iatt *stbuf, + struct iatt *preoldparent, struct iatt *postoldparent, + struct iatt *prenewparent, struct iatt *postnewparent, + dict_t **xdata) +{ + if (-1 != rsp->op_ret) { + gfx_stat_to_iattx (&rsp->stat, stbuf); + + gfx_stat_to_iattx (&rsp->preoldparent, preoldparent); + gfx_stat_to_iattx (&rsp->postoldparent, postoldparent); + + gfx_stat_to_iattx (&rsp->prenewparent, prenewparent); + gfx_stat_to_iattx (&rsp->postnewparent, postnewparent); + } + + return xdr_to_dict (&rsp->xdata, xdata); +} diff --git a/xlators/protocol/client/src/client-common.h b/xlators/protocol/client/src/client-common.h index fd3fba869f5..76ec0e9279d 100644 --- a/xlators/protocol/client/src/client-common.h +++ b/xlators/protocol/client/src/client-common.h @@ -15,6 +15,7 @@ #include "xlator.h" #include "rpc-common-xdr.h" #include "glusterfs3-xdr.h" +#include "glusterfs4-xdr.h" #include "glusterfs3.h" #include "client.h" @@ -400,4 +401,243 @@ client_post_seek (xlator_t *this, gfs3_seek_rsp *rsp, dict_t **xdata); int client_post_lease (xlator_t *this, gfs3_lease_rsp *rsp, struct gf_lease *lease, dict_t **xdata); + +/* New functions for version 4 */ +int +client_post_common_dict (xlator_t *this, gfx_common_dict_rsp *rsp, dict_t **dict, + dict_t **xdata); +int +client_post_common_3iatt (xlator_t *this, gfx_common_3iatt_rsp *rsp, struct iatt *iatt, + struct iatt *iatt2, struct iatt *iatt3, dict_t **xdata); +int +client_post_common_2iatt (xlator_t *this, gfx_common_2iatt_rsp *rsp, struct iatt *iatt, + struct iatt *iatt2, dict_t **xdata); +int +client_post_common_iatt (xlator_t *this, gfx_common_iatt_rsp *rsp, struct iatt *iatt, + dict_t **xdata); +int +client_post_common_rsp (xlator_t *this, gfx_common_rsp *rsp, dict_t **xdata); + + +int +client_pre_stat_v2 (xlator_t *this, gfx_stat_req *req, loc_t *loc, + dict_t *xdata); + +int +client_pre_readlink_v2 (xlator_t *this, gfx_readlink_req *req, loc_t *loc, + size_t size, dict_t *xdata); + +int +client_pre_mknod_v2 (xlator_t *this, gfx_mknod_req *req, loc_t *loc, + mode_t mode, dev_t rdev, mode_t umask, dict_t *xdata); + +int +client_pre_mkdir_v2 (xlator_t *this, gfx_mkdir_req *req, loc_t *loc, + mode_t mode, mode_t umask, dict_t *xdata); + +int +client_pre_unlink_v2 (xlator_t *this, gfx_unlink_req *req, loc_t *loc, + int32_t flags, dict_t *xdata); + +int +client_pre_rmdir_v2 (xlator_t *this, gfx_rmdir_req *req, loc_t *loc, + int32_t flags, dict_t *xdata); + +int +client_pre_symlink_v2 (xlator_t *this, gfx_symlink_req *req, loc_t *loc, + const char *linkname, mode_t umask, dict_t *xdata); + +int +client_pre_rename_v2 (xlator_t *this, gfx_rename_req *req, loc_t *oldloc, + loc_t *newloc, dict_t *xdata); + +int +client_pre_link_v2 (xlator_t *this, + gfx_link_req *req, loc_t *oldloc, loc_t *newloc, + dict_t *xdata); + +int +client_pre_truncate_v2 (xlator_t *this, gfx_truncate_req *req, + loc_t *loc, off_t offset, dict_t *xdata); + +int +client_pre_open_v2 (xlator_t *this, gfx_open_req *req, loc_t *loc, fd_t *fd, + int32_t flags, dict_t *xdata); + +int +client_pre_readv_v2 (xlator_t *this, gfx_read_req *req, fd_t *fd, size_t size, + off_t offset, int32_t flags, dict_t *xdata); + +int +client_pre_writev_v2 (xlator_t *this, gfx_write_req *req, + fd_t *fd, size_t size, off_t offset, int32_t flags, + dict_t **xdata); + +int +client_pre_statfs_v2 (xlator_t *this, gfx_statfs_req *req, loc_t *loc, + dict_t *xdata); + +int +client_pre_flush_v2 (xlator_t *this, gfx_flush_req *req, fd_t *fd, dict_t *xdata); + +int +client_pre_fsync_v2 (xlator_t *this, gfx_fsync_req *req, fd_t *fd, + int32_t flags, dict_t *xdata); + +int +client_pre_setxattr_v2 (xlator_t *this, gfx_setxattr_req *req, loc_t *loc, + dict_t *xattr, int32_t flags, dict_t *xdata); + +int +client_pre_getxattr_v2 (xlator_t *this, gfx_getxattr_req *req, loc_t *loc, + const char *name, dict_t *xdata); + +int +client_pre_removexattr_v2 (xlator_t *this, gfx_removexattr_req *req, + loc_t *loc, const char *name, dict_t *xdata); + +int +client_pre_opendir_v2 (xlator_t *this, + gfx_opendir_req *req, loc_t *loc, + fd_t *fd, dict_t *xdata); + +int +client_pre_fsyncdir_v2 (xlator_t *this, gfx_fsyncdir_req *req, fd_t *fd, + int32_t flags, dict_t *xdata); + +int +client_pre_access_v2 (xlator_t *this, gfx_access_req *req, loc_t *loc, + int32_t mask, dict_t *xdata); + +int +client_pre_create_v2 (xlator_t *this, gfx_create_req *req, + loc_t *loc, fd_t *fd, mode_t mode, + int32_t flags, mode_t umask, dict_t *xdata); + +int +client_pre_ftruncate_v2 (xlator_t *this, gfx_ftruncate_req *req, fd_t *fd, + off_t offset, dict_t *xdata); + +int +client_pre_fstat_v2 (xlator_t *this, gfx_fstat_req *req, fd_t *fd, + dict_t *xdata); + +int +client_pre_lk_v2 (xlator_t *this, gfx_lk_req *req, + int32_t cmd, struct gf_flock *flock, fd_t *fd, dict_t *xdata); + +int +client_pre_lookup_v2 (xlator_t *this, gfx_lookup_req *req, loc_t *loc, + dict_t *xdata); + +int +client_pre_readdir_v2 (xlator_t *this, gfx_readdir_req *req, fd_t *fd, + size_t size, off_t offset, dict_t *xdata); + +int +client_pre_inodelk_v2 (xlator_t *this, gfx_inodelk_req *req, loc_t *loc, + int cmd, struct gf_flock *flock, const char *volume, + dict_t *xdata); + +int +client_pre_finodelk_v2 (xlator_t *this, gfx_finodelk_req *req, fd_t *fd, + int cmd, struct gf_flock *flock, const char *volume, + dict_t *xdata); + +int +client_pre_entrylk_v2 (xlator_t *this, gfx_entrylk_req *req, loc_t *loc, + entrylk_cmd cmd_entrylk, entrylk_type type, + const char *volume, const char *basename, dict_t *xdata); + +int +client_pre_fentrylk_v2 (xlator_t *this, gfx_fentrylk_req *req, fd_t *fd, + entrylk_cmd cmd_entrylk, entrylk_type type, + const char *volume, const char *basename, dict_t *xdata); + +int +client_pre_xattrop_v2 (xlator_t *this, gfx_xattrop_req *req, loc_t *loc, + dict_t *xattr, int32_t flags, dict_t *xdata); + +int +client_pre_fxattrop_v2 (xlator_t *this, gfx_fxattrop_req *req, fd_t *fd, + dict_t *xattr, int32_t flags, dict_t *xdata); + +int +client_pre_fgetxattr_v2 (xlator_t *this, gfx_fgetxattr_req *req, fd_t *fd, + const char *name, dict_t *xdata); + +int +client_pre_fsetxattr_v2 (xlator_t *this, gfx_fsetxattr_req *req, fd_t *fd, + int32_t flags, dict_t *xattr, dict_t *xdata); +int +client_pre_seek_v2 (xlator_t *this, gfx_seek_req *req, fd_t *fd, + off_t offset, gf_seek_what_t what, dict_t *xdata); + +int +client_pre_rchecksum_v2 (xlator_t *this, gfx_rchecksum_req *req, fd_t *fd, + int32_t len, off_t offset, dict_t *xdata); + +int +client_pre_setattr_v2 (xlator_t *this, gfx_setattr_req *req, loc_t *loc, + int32_t valid, struct iatt *stbuf, dict_t *xdata); +int +client_pre_fsetattr_v2 (xlator_t *this, gfx_fsetattr_req *req, fd_t *fd, + int32_t valid, struct iatt *stbuf, dict_t *xdata); + +int +client_pre_readdirp_v2 (xlator_t *this, gfx_readdirp_req *req, fd_t *fd, + size_t size, off_t offset, dict_t *xdata); + +int +client_pre_fremovexattr_v2 (xlator_t *this, gfx_fremovexattr_req *req, fd_t *fd, + const char *name, dict_t *xdata); + +int +client_pre_fallocate_v2 (xlator_t *this, gfx_fallocate_req *req, fd_t *fd, + int32_t flags, off_t offset, size_t size, dict_t *xdata); +int +client_pre_discard_v2 (xlator_t *this, gfx_discard_req *req, fd_t *fd, + off_t offset, size_t size, dict_t *xdata); +int +client_pre_zerofill_v2 (xlator_t *this, gfx_zerofill_req *req, fd_t *fd, + off_t offset, size_t size, dict_t *xdata); +int +client_pre_ipc_v2 (xlator_t *this, gfx_ipc_req *req, int32_t cmd, + dict_t *xdata); + +int +client_pre_lease_v2 (xlator_t *this, gfx_lease_req *req, loc_t *loc, + struct gf_lease *lease, dict_t *xdata); + +int +client_post_readv_v2 (xlator_t *this, gfx_read_rsp *rsp, struct iobref **iobref, + struct iobref *rsp_iobref, struct iatt *stat, + struct iovec *vector, struct iovec *rsp_vector, + int *rspcount, dict_t **xdata); + + +int +client_post_create_v2 (xlator_t *this, gfx_create_rsp *rsp, + struct iatt *stbuf, struct iatt *preparent, + struct iatt *postparent, + clnt_local_t *local, dict_t **xdata); +int +client_post_lease_v2 (xlator_t *this, gfx_lease_rsp *rsp, struct gf_lease *lease, + dict_t **xdata); +int +client_post_lk_v2 (xlator_t *this, gfx_lk_rsp *rsp, struct gf_flock *lock, + dict_t **xdata); +int +client_post_readdir_v2 (xlator_t *this, gfx_readdir_rsp *rsp, + gf_dirent_t *entries, dict_t **xdata); +int +client_post_readdirp_v2 (xlator_t *this, gfx_readdirp_rsp *rsp, + fd_t *fd, gf_dirent_t *entries, + dict_t **xdata); +int +client_post_rename_v2 (xlator_t *this, gfx_rename_rsp *rsp, struct iatt *stbuf, + struct iatt *preoldparent, struct iatt *postoldparent, + struct iatt *prenewparent, struct iatt *postnewparent, + dict_t **xdata); + #endif /* __CLIENT_COMMON_H__ */ diff --git a/xlators/protocol/client/src/client-helpers.c b/xlators/protocol/client/src/client-helpers.c index c078b88b84d..465de2a52d4 100644 --- a/xlators/protocol/client/src/client-helpers.c +++ b/xlators/protocol/client/src/client-helpers.c @@ -142,7 +142,6 @@ client_local_wipe (clnt_local_t *local) return 0; } - int unserialize_rsp_dirent (xlator_t *this, struct gfs3_readdir_rsp *rsp, gf_dirent_t *entries) @@ -272,6 +271,113 @@ clnt_readdirp_rsp_cleanup (gfs3_readdirp_rsp *rsp) } int +unserialize_rsp_dirent_v2 (xlator_t *this, struct gfx_readdir_rsp *rsp, + gf_dirent_t *entries) +{ + struct gfx_dirlist *trav = NULL; + gf_dirent_t *entry = NULL; + int entry_len = 0; + int ret = -1; + clnt_conf_t *conf = NULL; + + conf = this->private; + + trav = rsp->reply; + while (trav) { + entry_len = gf_dirent_size (trav->name); + entry = GF_CALLOC (1, entry_len, gf_common_mt_gf_dirent_t); + if (!entry) + goto out; + + entry->d_ino = trav->d_ino; + gf_itransform (this, trav->d_off, &entry->d_off, + conf->client_id); + entry->d_len = trav->d_len; + entry->d_type = trav->d_type; + + strcpy (entry->d_name, trav->name); + + list_add_tail (&entry->list, &entries->list); + + trav = trav->nextentry; + } + + ret = 0; +out: + return ret; +} + +int +unserialize_rsp_direntp_v2 (xlator_t *this, fd_t *fd, + struct gfx_readdirp_rsp *rsp, gf_dirent_t *entries) +{ + struct gfx_dirplist *trav = NULL; + gf_dirent_t *entry = NULL; + inode_table_t *itable = NULL; + int entry_len = 0; + int ret = -1; + clnt_conf_t *conf = NULL; + + trav = rsp->reply; + + if (fd) + itable = fd->inode->table; + + conf = this->private; + if (!conf) + goto out; + + while (trav) { + entry_len = gf_dirent_size (trav->name); + entry = GF_CALLOC (1, entry_len, gf_common_mt_gf_dirent_t); + if (!entry) + goto out; + + entry->d_ino = trav->d_ino; + gf_itransform (this, trav->d_off, &entry->d_off, + conf->client_id); + entry->d_len = trav->d_len; + entry->d_type = trav->d_type; + + gfx_stat_to_iattx (&trav->stat, &entry->d_stat); + + strcpy (entry->d_name, trav->name); + + xdr_to_dict (&trav->dict, &entry->dict); + + 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; + } + + ret = 0; +out: + return ret; +} + +int +clnt_readdirp_rsp_cleanup_v2 (gfx_readdirp_rsp *rsp) +{ + gfx_dirplist *prev = NULL; + gfx_dirplist *trav = NULL; + + trav = rsp->reply; + prev = trav; + while (trav) { + trav = trav->nextentry; + free (prev->name); + free (prev); + prev = trav; + } + + return 0; +} + +int clnt_readdir_rsp_cleanup (gfs3_readdir_rsp *rsp) { gfs3_dirlist *prev = NULL; @@ -291,6 +397,25 @@ clnt_readdir_rsp_cleanup (gfs3_readdir_rsp *rsp) } int +clnt_readdir_rsp_cleanup_v2 (gfx_readdir_rsp *rsp) +{ + gfx_dirlist *prev = NULL; + gfx_dirlist *trav = NULL; + + trav = rsp->reply; + prev = trav; + while (trav) { + trav = trav->nextentry; + /* on client, the rpc lib allocates this */ + free (prev->name); + free (prev); + prev = trav; + } + + return 0; +} + +int client_get_remote_fd (xlator_t *this, fd_t *fd, int flags, int64_t *remote_fd) { clnt_fd_ctx_t *fdctx = NULL; @@ -1650,6 +1775,21 @@ clnt_getactivelk_rsp_cleanup (gfs3_getactivelk_rsp *rsp) } } +void +clnt_getactivelk_rsp_cleanup_v2 (gfx_getactivelk_rsp *rsp) +{ + gfs3_locklist *trav = NULL; + gfs3_locklist *next = NULL; + + trav = rsp->reply; + + while (trav) { + next = trav->nextentry; + free (trav->client_uid); + free (trav); + trav = next; + } +} int clnt_unserialize_rsp_locklist (xlator_t *this, struct gfs3_getactivelk_rsp *rsp, lock_migration_info_t *lmi) @@ -1689,6 +1829,46 @@ clnt_unserialize_rsp_locklist (xlator_t *this, struct gfs3_getactivelk_rsp *rsp, out: return ret; } +int +clnt_unserialize_rsp_locklist_v2 (xlator_t *this, struct gfx_getactivelk_rsp *rsp, + lock_migration_info_t *lmi) +{ + struct gfs3_locklist *trav = NULL; + lock_migration_info_t *temp = NULL; + int ret = -1; + clnt_conf_t *conf = NULL; + + trav = rsp->reply; + + conf = this->private; + if (!conf) + goto out; + + while (trav) { + temp = GF_CALLOC (1, sizeof (*lmi), gf_common_mt_lock_mig); + if (temp == NULL) { + gf_msg (this->name, GF_LOG_ERROR, 0, 0, "No memory"); + goto out; + } + + INIT_LIST_HEAD (&temp->list); + + gf_proto_flock_to_flock (&trav->flock, &temp->flock); + + temp->lk_flags = trav->lk_flags; + + temp->client_uid = gf_strdup (trav->client_uid); + + list_add_tail (&temp->list, &lmi->list); + + trav = trav->nextentry; + } + + ret = 0; +out: + return ret; +} + void clnt_setactivelk_req_cleanup (gfs3_setactivelk_req *req) @@ -1706,6 +1886,22 @@ clnt_setactivelk_req_cleanup (gfs3_setactivelk_req *req) } } +void +clnt_setactivelk_req_cleanup_v2 (gfx_setactivelk_req *req) +{ + gfs3_locklist *trav = NULL; + gfs3_locklist *next = NULL; + + trav = req->request; + + while (trav) { + next = trav->nextentry; + GF_FREE (trav->client_uid); + GF_FREE (trav); + trav = next; + } +} + int serialize_req_locklist (lock_migration_info_t *locklist, gfs3_setactivelk_req *req) @@ -1770,6 +1966,71 @@ out: return ret; } + +int +serialize_req_locklist_v2 (lock_migration_info_t *locklist, + gfx_setactivelk_req *req) +{ + lock_migration_info_t *tmp = NULL; + gfs3_locklist *trav = NULL; + gfs3_locklist *prev = NULL; + int ret = -1; + + GF_VALIDATE_OR_GOTO ("server", locklist, out); + GF_VALIDATE_OR_GOTO ("server", req, out); + + list_for_each_entry (tmp, &locklist->list, list) { + trav = GF_CALLOC (1, sizeof (*trav), + gf_client_mt_clnt_lock_request_t); + if (!trav) + goto out; + + switch (tmp->flock.l_type) { + case F_RDLCK: + tmp->flock.l_type = GF_LK_F_RDLCK; + break; + case F_WRLCK: + tmp->flock.l_type = GF_LK_F_WRLCK; + break; + case F_UNLCK: + tmp->flock.l_type = GF_LK_F_UNLCK; + break; + + default: + gf_msg (THIS->name, GF_LOG_ERROR, 0, 0, + "Unknown lock type: %"PRId32"!", + tmp->flock.l_type); + break; + } + + gf_proto_flock_from_flock (&trav->flock, &tmp->flock); + + trav->lk_flags = tmp->lk_flags; + + trav->client_uid = gf_strdup (tmp->client_uid); + if (!trav->client_uid) { + gf_msg (THIS->name, GF_LOG_ERROR, 0, 0, + "client_uid could not be allocated"); + ret = -1; + goto out; + } + + if (prev) + prev->nextentry = trav; + else + req->request = trav; + + prev = trav; + trav = NULL; + } + + ret = 0; +out: + GF_FREE (trav); + + return ret; +} + void client_compound_rsp_cleanup (gfs3_compound_rsp *rsp, int len) { @@ -1974,3 +2235,1042 @@ client_compound_rsp_cleanup (gfs3_compound_rsp *rsp, int len) } return; } + +/* compound v2 */ +int +client_handle_fop_requirements_v2 (xlator_t *this, call_frame_t *frame, + gfx_compound_req *req, + clnt_local_t *local, + struct iobref **req_iobref, + struct iobref **rsp_iobref, + struct iovec *req_vector, + struct iovec *rsp_vector, int *req_count, + int *rsp_count, default_args_t *args, + int fop_enum, int index) +{ + int ret = 0; + int op_errno = ENOMEM; + struct iobuf *rsp_iobuf = NULL; + int64_t remote_fd = -1; + compound_req_v2 *this_req = &req->compound_req_array.compound_req_array_val[index]; + + this_req->fop_enum = fop_enum; + + switch (fop_enum) { + case GF_FOP_STAT: + CLIENT4_PRE_FOP (stat, this, + &this_req->compound_req_v2_u.compound_stat_req, + op_errno, out, + &args->loc, args->xdata); + break; + case GF_FOP_READLINK: + CLIENT4_PRE_FOP (readlink, this, + &this_req->compound_req_v2_u.compound_readlink_req, + op_errno, out, + &args->loc, args->size, args->xdata); + break; + case GF_FOP_MKNOD: + CLIENT4_PRE_FOP (mknod, this, + &this_req->compound_req_v2_u.compound_mknod_req, + op_errno, out, + &args->loc, args->mode, args->rdev, + args->umask, args->xdata); + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_MKDIR: + CLIENT4_PRE_FOP (mkdir, this, + &this_req->compound_req_v2_u.compound_mkdir_req, + op_errno, out, + &args->loc, args->mode, + args->umask, args->xdata); + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_UNLINK: + CLIENT4_PRE_FOP (unlink, this, + &this_req->compound_req_v2_u.compound_unlink_req, + op_errno, out, + &args->loc, args->xflag, args->xdata); + break; + case GF_FOP_RMDIR: + CLIENT4_PRE_FOP (rmdir, this, + &this_req->compound_req_v2_u.compound_rmdir_req, + op_errno, out, + &args->loc, args->flags, args->xdata); + break; + case GF_FOP_SYMLINK: + CLIENT4_PRE_FOP (symlink, this, + &this_req->compound_req_v2_u.compound_symlink_req, + op_errno, out, + &args->loc, args->linkname, args->umask, + args->xdata); + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_RENAME: + CLIENT4_PRE_FOP (rename, this, + &this_req->compound_req_v2_u.compound_rename_req, + op_errno, out, + &args->loc, &args->loc2, args->xdata); + break; + case GF_FOP_LINK: + CLIENT4_PRE_FOP (link, this, + &this_req->compound_req_v2_u.compound_link_req, + op_errno, out, + &args->loc, &args->loc2, args->xdata); + break; + case GF_FOP_TRUNCATE: + CLIENT4_PRE_FOP (truncate, this, + &this_req->compound_req_v2_u.compound_truncate_req, + op_errno, out, + &args->loc, args->offset, args->xdata); + break; + case GF_FOP_OPEN: + CLIENT4_PRE_FOP (open, this, + &this_req->compound_req_v2_u.compound_open_req, + op_errno, out, + &args->loc, args->fd, args->flags, + args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + break; + case GF_FOP_READ: + op_errno = client_pre_readv_v2 (this, + &this_req->compound_req_v2_u.compound_read_req, + args->fd, args->size, args->offset, + args->flags, args->xdata); + + if (op_errno) { + op_errno = -op_errno; + goto out; + } + if (!local->fd) + local->fd = fd_ref (args->fd); + local->attempt_reopen = client_is_reopen_needed + (args->fd, this, remote_fd); + rsp_iobuf = iobuf_get2 (this->ctx->iobuf_pool, args->size); + if (rsp_iobuf == NULL) { + op_errno = ENOMEM; + goto out; + } + + if (!*rsp_iobref) { + *rsp_iobref = iobref_new (); + if (*rsp_iobref == NULL) { + op_errno = ENOMEM; + goto out; + } + } + + iobref_add (*rsp_iobref, rsp_iobuf); + iobuf_unref (rsp_iobuf); + + if (*rsp_count + 1 >= MAX_IOVEC) { + op_errno = ENOMEM; + goto out; + } + rsp_vector[*rsp_count].iov_base = iobuf_ptr (rsp_iobuf); + rsp_vector[*rsp_count].iov_len = iobuf_pagesize (rsp_iobuf); + rsp_iobuf = NULL; + if (args->size > rsp_vector[*rsp_count].iov_len) { + gf_msg (this->name, GF_LOG_WARNING, ENOMEM, + PC_MSG_NO_MEMORY, + "read-size (%lu) is bigger than iobuf size " + "(%lu)", + (unsigned long)args->size, + (unsigned long)rsp_vector[*rsp_count].iov_len); + op_errno = EINVAL; + goto out; + } + *rsp_count += 1; + + break; + case GF_FOP_WRITE: + op_errno = client_pre_writev_v2 (this, + &this_req->compound_req_v2_u.compound_write_req, + args->fd, iov_length (args->vector, args->count), + args->offset, args->flags, &args->xdata); + + if (op_errno) { + op_errno = -op_errno; + goto out; + } + if (!local->fd) + local->fd = fd_ref (args->fd); + local->attempt_reopen = client_is_reopen_needed + (args->fd, this, remote_fd); + + if (*req_count + args->count >= MAX_IOVEC) { + op_errno = ENOMEM; + goto out; + } + memcpy (&req_vector[*req_count], args->vector, + (args->count * sizeof(req_vector[0]))); + *req_count += args->count; + + if (!*req_iobref) + *req_iobref = args->iobref; + else + if (iobref_merge (*req_iobref, args->iobref)) + goto out; + break; + case GF_FOP_STATFS: + CLIENT4_PRE_FOP (statfs, this, + &this_req->compound_req_v2_u.compound_statfs_req, + op_errno, out, + &args->loc, args->xdata); + break; + case GF_FOP_FLUSH: + CLIENT4_PRE_FOP (flush, this, + &this_req->compound_req_v2_u.compound_flush_req, + op_errno, out, + args->fd, args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + local->owner = frame->root->lk_owner; + break; + case GF_FOP_FSYNC: + CLIENT4_PRE_FOP (fsync, this, + &this_req->compound_req_v2_u.compound_fsync_req, + op_errno, out, + args->fd, args->datasync, args->xdata); + break; + case GF_FOP_SETXATTR: + CLIENT4_PRE_FOP (setxattr, this, + &this_req->compound_req_v2_u.compound_setxattr_req, + op_errno, out, + &args->loc, args->xattr, args->flags, + args->xdata); + break; + case GF_FOP_GETXATTR: + CLIENT4_PRE_FOP (getxattr, this, + &this_req->compound_req_v2_u.compound_getxattr_req, + op_errno, out, + &args->loc, args->name, args->xdata); + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_REMOVEXATTR: + CLIENT4_PRE_FOP (removexattr, this, + &this_req->compound_req_v2_u.compound_removexattr_req, + op_errno, out, + &args->loc, args->name, args->xdata); + break; + case GF_FOP_OPENDIR: + CLIENT4_PRE_FOP (opendir, this, + &this_req->compound_req_v2_u.compound_opendir_req, + op_errno, out, + &args->loc, args->fd, args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_FSYNCDIR: + CLIENT4_PRE_FOP (fsyncdir, this, + &this_req->compound_req_v2_u.compound_fsyncdir_req, + op_errno, out, + args->fd, args->datasync, args->xdata); + break; + case GF_FOP_ACCESS: + CLIENT4_PRE_FOP (access, this, + &this_req->compound_req_v2_u.compound_access_req, + op_errno, out, + &args->loc, args->mask, args->xdata); + break; + case GF_FOP_CREATE: + CLIENT4_PRE_FOP (create, this, + &this_req->compound_req_v2_u.compound_create_req, + op_errno, out, + &args->loc, args->fd, args->mode, args->flags, + args->umask, args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_FTRUNCATE: + CLIENT4_PRE_FOP (ftruncate, this, + &this_req->compound_req_v2_u.compound_ftruncate_req, + op_errno, out, + args->fd, args->offset, args->xdata); + break; + case GF_FOP_FSTAT: + CLIENT4_PRE_FOP (fstat, this, + &this_req->compound_req_v2_u.compound_fstat_req, + op_errno, out, + args->fd, args->xdata); + break; + case GF_FOP_LK: + CLIENT4_PRE_FOP (lk, this, + &this_req->compound_req_v2_u.compound_lk_req, + op_errno, out, + args->cmd, &args->lock, args->fd, args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + local->owner = frame->root->lk_owner; + break; + case GF_FOP_LOOKUP: + CLIENT4_PRE_FOP (lookup, this, + &this_req->compound_req_v2_u.compound_lookup_req, + op_errno, out, + &args->loc, args->xdata); + loc_copy (&local->loc, &args->loc); + loc_path (&local->loc, NULL); + break; + case GF_FOP_READDIR: + CLIENT4_PRE_FOP (readdir, this, + &this_req->compound_req_v2_u.compound_readdir_req, + op_errno, out, + args->fd, args->size, args->offset, + args->xdata); + break; + case GF_FOP_INODELK: + CLIENT4_PRE_FOP (inodelk, this, + &this_req->compound_req_v2_u.compound_inodelk_req, + op_errno, out, + &args->loc, args->cmd, &args->lock, + args->volume, args->xdata); + break; + case GF_FOP_FINODELK: + CLIENT4_PRE_FOP (finodelk, this, + &this_req->compound_req_v2_u.compound_finodelk_req, + op_errno, out, + args->fd, args->cmd, &args->lock, + args->volume, args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + local->attempt_reopen = client_is_reopen_needed + (args->fd, this, remote_fd); + break; + case GF_FOP_ENTRYLK: + CLIENT4_PRE_FOP (entrylk, this, + &this_req->compound_req_v2_u.compound_entrylk_req, + op_errno, out, + &args->loc, args->entrylkcmd, + args->entrylktype, args->volume, + args->name, args->xdata); + break; + case GF_FOP_FENTRYLK: + CLIENT4_PRE_FOP (fentrylk, this, + &this_req->compound_req_v2_u.compound_fentrylk_req, + op_errno, out, + args->fd, args->entrylkcmd, + args->entrylktype, args->volume, + args->name, args->xdata); + break; + case GF_FOP_XATTROP: + CLIENT4_PRE_FOP (xattrop, this, + &this_req->compound_req_v2_u.compound_xattrop_req, + op_errno, out, + &args->loc, args->xattr, args->optype, + args->xdata); + break; + case GF_FOP_FXATTROP: + CLIENT4_PRE_FOP (fxattrop, this, + &this_req->compound_req_v2_u.compound_fxattrop_req, + op_errno, out, + args->fd, args->xattr, args->optype, + args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + local->attempt_reopen = client_is_reopen_needed + (args->fd, this, remote_fd); + break; + case GF_FOP_FGETXATTR: + CLIENT4_PRE_FOP (fgetxattr, this, + &this_req->compound_req_v2_u.compound_fgetxattr_req, + op_errno, out, + args->fd, args->name, args->xdata); + break; + case GF_FOP_FSETXATTR: + CLIENT4_PRE_FOP (fsetxattr, this, + &this_req->compound_req_v2_u.compound_fsetxattr_req, + op_errno, out, + args->fd, args->flags, args->xattr, + args->xdata); + break; + case GF_FOP_RCHECKSUM: + CLIENT4_PRE_FOP (rchecksum, this, + &this_req->compound_req_v2_u.compound_rchecksum_req, + op_errno, out, + args->fd, args->size, args->offset, + args->xdata); + break; + case GF_FOP_SETATTR: + CLIENT4_PRE_FOP (setattr, this, + &this_req->compound_req_v2_u.compound_setattr_req, + op_errno, out, + &args->loc, args->valid, &args->stat, + args->xdata); + break; + case GF_FOP_FSETATTR: + CLIENT4_PRE_FOP (fsetattr, this, + &this_req->compound_req_v2_u.compound_fsetattr_req, + op_errno, out, + args->fd, args->valid, &args->stat, + args->xdata); + break; + case GF_FOP_READDIRP: + CLIENT4_PRE_FOP (readdirp, this, + &this_req->compound_req_v2_u.compound_readdirp_req, + op_errno, out, + args->fd, args->size, args->offset, + args->xdata); + if (!local->fd) + local->fd = fd_ref (args->fd); + break; + case GF_FOP_FREMOVEXATTR: + CLIENT4_PRE_FOP (fremovexattr, this, + &this_req->compound_req_v2_u.compound_fremovexattr_req, + op_errno, out, + args->fd, args->name, args->xdata); + break; + case GF_FOP_FALLOCATE: + CLIENT4_PRE_FOP (fallocate, this, + &this_req->compound_req_v2_u.compound_fallocate_req, + op_errno, out, + args->fd, args->flags, args->offset, + args->size, args->xdata); + break; + case GF_FOP_DISCARD: + CLIENT4_PRE_FOP (discard, this, + &this_req->compound_req_v2_u.compound_discard_req, + op_errno, out, + args->fd, args->offset, args->size, + args->xdata); + break; + case GF_FOP_ZEROFILL: + CLIENT4_PRE_FOP (zerofill, this, + &this_req->compound_req_v2_u.compound_zerofill_req, + op_errno, out, + args->fd, args->offset, args->size, + args->xdata); + break; + case GF_FOP_IPC: + CLIENT4_PRE_FOP (ipc, this, + &this_req->compound_req_v2_u.compound_ipc_req, + op_errno, out, + args->cmd, args->xdata); + break; + case GF_FOP_SEEK: + CLIENT4_PRE_FOP (seek, this, + &this_req->compound_req_v2_u.compound_seek_req, + op_errno, out, + args->fd, args->offset, args->what, + args->xdata); + break; + case GF_FOP_LEASE: + CLIENT4_PRE_FOP (lease, this, + &this_req->compound_req_v2_u.compound_lease_req, + op_errno, out, &args->loc, &args->lease, + args->xdata); + break; + default: + return ENOTSUP; + } + return 0; +out: + return op_errno; +} + +void +compound_request_cleanup_v2 (gfx_compound_req *req) +{ + int i = 0; + int length = req->compound_req_array.compound_req_array_len; + compound_req_v2 *curr_req = NULL; + + if (!req->compound_req_array.compound_req_array_val) + return; + + for (i = 0; i < length; i++) { + curr_req = &req->compound_req_array.compound_req_array_val[i]; + + switch (curr_req->fop_enum) { + case GF_FOP_STAT: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, stat); + break; + case GF_FOP_READLINK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, readlink); + break; + case GF_FOP_MKNOD: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, mknod); + break; + case GF_FOP_MKDIR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, mkdir); + break; + case GF_FOP_UNLINK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, unlink); + break; + case GF_FOP_RMDIR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, rmdir); + break; + case GF_FOP_SYMLINK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, symlink); + break; + case GF_FOP_RENAME: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, rename); + break; + case GF_FOP_LINK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, link); + break; + case GF_FOP_TRUNCATE: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, truncate); + break; + case GF_FOP_OPEN: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, open); + break; + case GF_FOP_READ: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, read); + break; + case GF_FOP_WRITE: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, write); + break; + case GF_FOP_STATFS: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, statfs); + break; + case GF_FOP_FLUSH: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, flush); + break; + case GF_FOP_FSYNC: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fsync); + break; + case GF_FOP_SETXATTR: + { + gfx_setxattr_req *args = &CPD4_REQ_FIELD (curr_req, + setxattr); + GF_FREE (args->dict.pairs.pairs_val); + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, setxattr); + break; + } + case GF_FOP_GETXATTR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, getxattr); + break; + case GF_FOP_REMOVEXATTR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, removexattr); + break; + case GF_FOP_OPENDIR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, opendir); + break; + case GF_FOP_FSYNCDIR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fsyncdir); + break; + case GF_FOP_ACCESS: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, access); + break; + case GF_FOP_CREATE: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, create); + break; + case GF_FOP_FTRUNCATE: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, ftruncate); + break; + case GF_FOP_FSTAT: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fstat); + break; + case GF_FOP_LK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, lk); + break; + case GF_FOP_LOOKUP: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, lookup); + break; + case GF_FOP_READDIR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, readdir); + break; + case GF_FOP_INODELK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, inodelk); + break; + case GF_FOP_FINODELK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, finodelk); + break; + case GF_FOP_ENTRYLK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, entrylk); + break; + case GF_FOP_FENTRYLK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fentrylk); + break; + case GF_FOP_XATTROP: + { + gfx_xattrop_req *args = &CPD4_REQ_FIELD (curr_req, + xattrop); + GF_FREE (args->dict.pairs.pairs_val); + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, xattrop); + break; + } + case GF_FOP_FXATTROP: + { + gfx_fxattrop_req *args = &CPD4_REQ_FIELD (curr_req, + fxattrop); + GF_FREE (args->dict.pairs.pairs_val); + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fxattrop); + break; + } + case GF_FOP_FGETXATTR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fgetxattr); + break; + case GF_FOP_FSETXATTR: + { + gfx_fsetxattr_req *args = &CPD4_REQ_FIELD(curr_req, + fsetxattr); + GF_FREE (args->dict.pairs.pairs_val); + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fsetxattr); + break; + } + case GF_FOP_RCHECKSUM: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, rchecksum); + break; + case GF_FOP_SETATTR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, setattr); + break; + case GF_FOP_FSETATTR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fsetattr); + break; + case GF_FOP_READDIRP: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, readdirp); + break; + case GF_FOP_FREMOVEXATTR: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fremovexattr); + break; + case GF_FOP_FALLOCATE: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, fallocate); + break; + case GF_FOP_DISCARD: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, discard); + break; + case GF_FOP_ZEROFILL: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, zerofill); + break; + case GF_FOP_IPC: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, ipc); + break; + case GF_FOP_SEEK: + CLIENT4_COMPOUND_FOP_CLEANUP (curr_req, seek); + break; + default: + break; + } + } + + GF_FREE (req->compound_req_array.compound_req_array_val); + return; +} + + +void +client_compound_rsp_cleanup_v2 (gfx_compound_rsp *rsp, int len) +{ + int i = 0; + compound_rsp_v2 *this_rsp = NULL; + + for (i = 0; i < len; i++) { + this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[i]; + switch (this_rsp->fop_enum) { + /* fops that need extra cleanup */ + case GF_FOP_LK: + { + gfx_lk_rsp *tmp_rsp = &CPD4_RSP_FIELD(this_rsp, lk); + free (tmp_rsp->flock.lk_owner.lk_owner_val); + break; + } + case GF_FOP_READLINK: + { + gfx_readlink_rsp *tmp_rsp = &CPD4_RSP_FIELD(this_rsp, + readlink); + free (tmp_rsp->path); + break; + } + case GF_FOP_READDIR: + { + + gfx_readdir_rsp *tmp_rsp = &CPD4_RSP_FIELD(this_rsp, + readdir); + clnt_readdir_rsp_cleanup_v2 (tmp_rsp); + break; + } + case GF_FOP_READDIRP: + { + + gfx_readdirp_rsp *tmp_rsp = &CPD4_RSP_FIELD(this_rsp, + readdirp); + clnt_readdirp_rsp_cleanup_v2 (tmp_rsp); + break; + } + case GF_FOP_RCHECKSUM: + { + + gfx_rchecksum_rsp *rck = &CPD4_RSP_FIELD(this_rsp, + rchecksum); + if (rck->strong_checksum.strong_checksum_val) { + free (rck->strong_checksum.strong_checksum_val); + } + break; + } + default: + break; + } + } + return; +} + +int +client_process_response_v2 (call_frame_t *frame, xlator_t *this, + struct rpc_req *req, gfx_compound_rsp *rsp, + compound_args_cbk_t *args_cbk, + int index) +{ + int ret = 0; + dict_t *xdata = NULL; + dict_t *xattr = NULL; + struct iovec vector[MAX_IOVEC] = {{0}, }; + gf_dirent_t entries; + default_args_cbk_t *this_args_cbk = &args_cbk->rsp_list[index]; + clnt_local_t *local = frame->local; + compound_rsp_v2 *this_rsp = NULL; + compound_args_t *args = local->compound_args; + + this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[index]; + args_cbk->enum_list[index] = this_rsp->fop_enum; + + INIT_LIST_HEAD (&entries.list); + + switch (args_cbk->enum_list[index]) { + + case GF_FOP_STAT: + case GF_FOP_FSTAT: + { + gfx_common_iatt_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_stat_rsp; + + client_post_common_iatt (this, tmp_rsp, &this_args_cbk->stat, &xdata); + + CLIENT4_POST_FOP_TYPE (stat, common_iatt, this_rsp, this_args_cbk, + &this_args_cbk->stat, xdata); + break; + } + case GF_FOP_READLINK: + { + gfx_readlink_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_readlink_rsp; + + gfx_stat_to_iattx (&tmp_rsp->buf, &this_args_cbk->stat); + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP_TYPE (readlink, readlink, this_rsp, this_args_cbk, + tmp_rsp->path, &this_args_cbk->stat, + xdata); + break; + } + case GF_FOP_MKDIR: + case GF_FOP_MKNOD: + case GF_FOP_SYMLINK: + case GF_FOP_LINK: + { + gfx_common_3iatt_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_mknod_rsp; + + client_post_common_3iatt (this, tmp_rsp, &this_args_cbk->stat, + &this_args_cbk->preparent, + &this_args_cbk->postparent, &xdata); + CLIENT4_POST_FOP_TYPE (mknod, common_3iatt, this_rsp, this_args_cbk, + local->loc.inode, &this_args_cbk->stat, + &this_args_cbk->preparent, + &this_args_cbk->postparent, xdata); + break; + } + case GF_FOP_UNLINK: + case GF_FOP_RMDIR: + { + gfx_common_2iatt_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_unlink_rsp; + + client_post_common_2iatt (this, tmp_rsp, &this_args_cbk->preparent, + &this_args_cbk->postparent, &xdata); + CLIENT4_POST_FOP_TYPE (unlink, common_2iatt, this_rsp, this_args_cbk, + &this_args_cbk->preparent, + &this_args_cbk->postparent, xdata); + break; + } + case GF_FOP_RENAME: + { + gfx_rename_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_rename_rsp; + + client_post_rename_v2 (this, tmp_rsp, &this_args_cbk->stat, + &this_args_cbk->preparent, + &this_args_cbk->postparent, + &this_args_cbk->preparent2, + &this_args_cbk->postparent2, &xdata); + CLIENT4_POST_FOP_TYPE (rename, rename, this_rsp, this_args_cbk, + &this_args_cbk->stat, + &this_args_cbk->preparent, + &this_args_cbk->postparent, + &this_args_cbk->preparent2, + &this_args_cbk->postparent2, xdata); + break; + } + case GF_FOP_WRITE: + case GF_FOP_TRUNCATE: + case GF_FOP_FTRUNCATE: + case GF_FOP_FSYNC: + case GF_FOP_ZEROFILL: + case GF_FOP_DISCARD: + case GF_FOP_FALLOCATE: + case GF_FOP_FSETATTR: + case GF_FOP_SETATTR: + { + gfx_common_2iatt_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_truncate_rsp; + + client_post_common_2iatt (this, tmp_rsp, &this_args_cbk->prestat, + &this_args_cbk->poststat, &xdata); + CLIENT4_POST_FOP_TYPE (truncate, common_2iatt, this_rsp, this_args_cbk, + &this_args_cbk->prestat, + &this_args_cbk->poststat, xdata); + break; + } + case GF_FOP_OPEN: + { + gfx_open_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_open_rsp; + + xdr_to_dict (&tmp_rsp->xdata, &xdata); + CLIENT4_POST_FOP_TYPE (open, open, this_rsp, this_args_cbk, local->fd, + xdata); + if (-1 != this_args_cbk->op_ret) + ret = client_add_fd_to_saved_fds (this, local->fd, + &local->loc, + args->req_list[index].flags, + tmp_rsp->fd, + 0); + break; + } + case GF_FOP_READ: + { + gfx_read_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_read_rsp; + + client_post_readv_v2 (this, tmp_rsp, &this_args_cbk->iobref, + req->rsp_iobref, &this_args_cbk->stat, + vector, &req->rsp[1], &this_args_cbk->count, + &xdata); + + /* Each read should be given read response that only + * corresponds to its request. + * Modify the iovecs accordingly. + * After each read, store the length of data already read + * so that the next ones can continue from there. + */ + if (local->read_length) { + vector[0].iov_base += local->read_length; + local->read_length += tmp_rsp->op_ret; + } else { + local->read_length = tmp_rsp->op_ret; + } + + args_readv_cbk_store (this_args_cbk, tmp_rsp->op_ret, + gf_error_to_errno (tmp_rsp->op_errno), + vector, this_args_cbk->count, + &this_args_cbk->stat, + this_args_cbk->iobref, xdata); + + if (tmp_rsp->op_ret >= 0) + if (local->attempt_reopen) + client_attempt_reopen (local->fd, this); + + break; + } + case GF_FOP_STATFS: + { + gfx_statfs_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_statfs_rsp; + + gf_statfs_to_statfs (&tmp_rsp->statfs, &this_args_cbk->statvfs); + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP_TYPE (statfs, statfs, this_rsp, this_args_cbk, + &this_args_cbk->statvfs, xdata); + break; + } + case GF_FOP_FLUSH: + { + gfx_common_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_flush_rsp; + + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP (flush, this_rsp, this_args_cbk, xdata); + if (this_args_cbk->op_ret >= 0 && !fd_is_anonymous (local->fd)) { + /* Delete all saved locks of the owner issuing flush */ + ret = delete_granted_locks_owner (local->fd, &local->owner); + gf_msg_trace (this->name, 0, + "deleting locks of owner (%s) returned %d", + lkowner_utoa (&local->owner), ret); + } + break; + } + case GF_FOP_FSYNCDIR: + case GF_FOP_ACCESS: + case GF_FOP_REMOVEXATTR: + case GF_FOP_FREMOVEXATTR: + case GF_FOP_FSETXATTR: + case GF_FOP_SETXATTR: + case GF_FOP_INODELK: + case GF_FOP_FINODELK: + case GF_FOP_ENTRYLK: + case GF_FOP_FENTRYLK: + case GF_FOP_IPC: + { + gfx_common_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_setxattr_rsp; + + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP (setxattr, this_rsp, this_args_cbk, xdata); + break; + } + case GF_FOP_GETXATTR: + case GF_FOP_FGETXATTR: + case GF_FOP_XATTROP: + case GF_FOP_FXATTROP: + { + gfx_common_dict_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_getxattr_rsp; + + client_post_common_dict (this, tmp_rsp, &xattr, &xdata); + + CLIENT4_POST_FOP_TYPE (getxattr, common_dict, this_rsp, this_args_cbk, xattr, + xdata); + break; + } + case GF_FOP_OPENDIR: + { + gfx_open_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_opendir_rsp; + + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP_TYPE (opendir, open, this_rsp, this_args_cbk, + local->fd, xdata); + if (-1 != this_args_cbk->op_ret) + ret = client_add_fd_to_saved_fds (this, local->fd, + &local->loc, + args->req_list[index].flags, + tmp_rsp->fd, 0); + break; + } + case GF_FOP_CREATE: + { + gfx_create_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_create_rsp; + + client_post_create_v2 (this, tmp_rsp, &this_args_cbk->stat, + &this_args_cbk->preparent, + &this_args_cbk->postparent, local, &xdata); + + CLIENT4_POST_FOP_TYPE (create, create, this_rsp, this_args_cbk, + local->fd, local->loc.inode, + &this_args_cbk->stat, + &this_args_cbk->preparent, + &this_args_cbk->postparent, xdata); + if (-1 != this_args_cbk->op_ret) + ret = client_add_fd_to_saved_fds (this, local->fd, + &local->loc, + args->req_list[index].flags, + tmp_rsp->fd, 0); + break; + } + case GF_FOP_LK: + { + gfx_lk_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_lk_rsp; + + client_post_lk_v2 (this, tmp_rsp, &this_args_cbk->lock, &xdata); + + CLIENT4_POST_FOP_TYPE (lk, lk, this_rsp, this_args_cbk, + &this_args_cbk->lock, xdata); + break; + } + case GF_FOP_LOOKUP: + { + gfx_common_2iatt_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_lookup_rsp; + + client_post_common_2iatt (this, tmp_rsp, &this_args_cbk->stat, + &this_args_cbk->postparent, &xdata); + CLIENT4_POST_FOP_TYPE (lookup, common_2iatt, this_rsp, this_args_cbk, + local->loc.inode, &this_args_cbk->stat, + xdata, &this_args_cbk->postparent); + break; + } + case GF_FOP_READDIR: + { + gfx_readdir_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_readdir_rsp; + + client_post_readdir_v2 (this, tmp_rsp, &entries, &xdata); + + CLIENT4_POST_FOP_TYPE (readdir, readdir, this_rsp, this_args_cbk, + &entries, xdata); + break; + } + case GF_FOP_RCHECKSUM: + { + gfx_rchecksum_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_rchecksum_rsp; + + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP_TYPE (rchecksum, rchecksum, this_rsp, this_args_cbk, + tmp_rsp->weak_checksum, + (uint8_t *)tmp_rsp->strong_checksum.strong_checksum_val, + xdata); + break; + } + case GF_FOP_READDIRP: + { + gfx_readdirp_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_readdirp_rsp; + + client_post_readdirp_v2 (this, tmp_rsp, local->fd, &entries, + &xdata); + + CLIENT4_POST_FOP_TYPE (readdirp, readdirp, this_rsp, this_args_cbk, + &entries, xdata); + break; + } + case GF_FOP_SEEK: + { + gfx_seek_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_seek_rsp; + + xdr_to_dict (&tmp_rsp->xdata, &xdata); + + CLIENT4_POST_FOP_TYPE (seek, seek, this_rsp, this_args_cbk, + tmp_rsp->offset, xdata); + break; + } + case GF_FOP_LEASE: + { + gfx_lease_rsp *tmp_rsp = NULL; + tmp_rsp = &this_rsp->compound_rsp_v2_u.compound_lease_rsp; + + client_post_lease_v2 (this, tmp_rsp, &this_args_cbk->lease, + &xdata); + + CLIENT4_POST_FOP_TYPE (lease, lease, this_rsp, this_args_cbk, + &this_args_cbk->lease, xdata); + break; + } + default: + return -ENOTSUP; + } + + if (xdata) + dict_unref (xdata); + if (xattr) + dict_unref (xattr); + gf_dirent_free (&entries); + return 0; +} diff --git a/xlators/protocol/client/src/client-rpc-fops.c b/xlators/protocol/client/src/client-rpc-fops.c index c8d1cc14f77..ead439eab7e 100644 --- a/xlators/protocol/client/src/client-rpc-fops.c +++ b/xlators/protocol/client/src/client-rpc-fops.c @@ -3150,102 +3150,6 @@ out: return 0; } -int32_t -client3_3_namelink_cbk (struct rpc_req *req, - struct iovec *iov, int count, void *myframe) -{ - int32_t ret = 0; - xlator_t *this = NULL; - struct iatt prebuf = {0,}; - struct iatt postbuf = {0,}; - dict_t *xdata = NULL; - call_frame_t *frame = NULL; - gfs4_namelink_rsp rsp = {0,}; - - this = THIS; - frame = myframe; - - if (req->rpc_status == -1) { - rsp.op_ret = -1; - rsp.op_errno = ENOTCONN; - goto out; - } - - ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfs4_namelink_rsp); - if (ret < 0) { - rsp.op_ret = -1; - rsp.op_errno = EINVAL; - goto out; - } - - if (rsp.op_ret != -1) { - gf_stat_to_iatt (&rsp.preparent, &prebuf); - gf_stat_to_iatt (&rsp.postparent, &postbuf); - } - - GF_PROTOCOL_DICT_UNSERIALIZE (this, xdata, (rsp.xdata.xdata_val), - (rsp.xdata.xdata_len), ret, - rsp.op_errno, out); - - out: - CLIENT_STACK_UNWIND (namelink, frame, rsp.op_ret, - gf_error_to_errno (rsp.op_errno), - &prebuf, &postbuf, xdata); - free (rsp.xdata.xdata_val); - if (xdata) - dict_unref (xdata); - return 0; -} - -int32_t -client3_3_icreate_cbk (struct rpc_req *req, - struct iovec *iov, int count, void *myframe) -{ - int32_t ret = 0; - inode_t *inode = NULL; - clnt_local_t *local = NULL; - xlator_t *this = NULL; - struct iatt stbuf = {0,}; - dict_t *xdata = NULL; - call_frame_t *frame = NULL; - gfs4_icreate_rsp rsp = {0,}; - - this = THIS; - frame = myframe; - local = frame->local; - - inode = local->loc.inode; - - if (req->rpc_status == -1) { - rsp.op_ret = -1; - rsp.op_errno = ENOTCONN; - goto out; - } - - ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfs4_icreate_rsp); - if (ret < 0) { - rsp.op_ret = -1; - rsp.op_errno = EINVAL; - goto out; - } - - if (rsp.op_ret != -1) - gf_stat_to_iatt (&rsp.stat, &stbuf); - - GF_PROTOCOL_DICT_UNSERIALIZE (this, xdata, (rsp.xdata.xdata_val), - (rsp.xdata.xdata_len), ret, - rsp.op_errno, out); - - out: - CLIENT_STACK_UNWIND (icreate, frame, rsp.op_ret, - gf_error_to_errno (rsp.op_errno), - inode, &stbuf, xdata); - free (rsp.xdata.xdata_val); - if (xdata) - dict_unref (xdata); - return 0; -} - int client_fdctx_destroy (xlator_t *this, clnt_fd_ctx_t *fdctx) { @@ -6345,197 +6249,6 @@ unwind: return 0; } -int32_t -client3_3_namelink (call_frame_t *frame, xlator_t *this, void *data) -{ - int32_t ret = 0; - int32_t op_errno = EINVAL; - clnt_conf_t *conf = NULL; - clnt_args_t *args = NULL; - gfs4_namelink_req req = {{0,},}; - - GF_ASSERT (frame); - - args = data; - conf = this->private; - - if (!(args->loc && args->loc->parent)) - goto unwind; - - if (!gf_uuid_is_null (args->loc->parent->gfid)) - memcpy (req.pargfid, args->loc->parent->gfid, sizeof (uuid_t)); - else - memcpy (req.pargfid, args->loc->pargfid, sizeof (uuid_t)); - - GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, - !gf_uuid_is_null (*((uuid_t *)req.pargfid)), - unwind, op_errno, EINVAL); - - req.bname = (char *)args->loc->name; - - GF_PROTOCOL_DICT_SERIALIZE (this, args->xdata, (&req.xdata.xdata_val), - req.xdata.xdata_len, op_errno, unwind); - - ret = client_submit_request (this, &req, frame, conf->fops, - GFS3_OP_NAMELINK, client3_3_namelink_cbk, - NULL, NULL, 0, NULL, 0, NULL, - (xdrproc_t)xdr_gfs4_namelink_req); - if (ret) { - gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, - "failed to send the fop"); - } - - GF_FREE (req.xdata.xdata_val); - return 0; - - unwind: - CLIENT_STACK_UNWIND (namelink, frame, -1, op_errno, NULL, NULL, NULL); - return 0; -} - -int32_t -client3_3_icreate (call_frame_t *frame, xlator_t *this, void *data) -{ - int32_t ret = 0; - int32_t op_errno = EINVAL; - clnt_conf_t *conf = NULL; - clnt_args_t *args = NULL; - clnt_local_t *local = NULL; - gfs4_icreate_req req = {{0,},}; - - GF_ASSERT (frame); - - args = data; - conf = this->private; - - if (!(args->loc && args->loc->inode)) - goto unwind; - - local = mem_get0 (this->local_pool); - if (!local) { - op_errno = ENOMEM; - goto unwind; - } - frame->local = local; - - loc_copy (&local->loc, args->loc); - - req.mode = args->mode; - memcpy (req.gfid, args->loc->gfid, sizeof (uuid_t)); - - op_errno = ESTALE; - GF_PROTOCOL_DICT_SERIALIZE (this, args->xdata, (&req.xdata.xdata_val), - req.xdata.xdata_len, op_errno, unwind); - ret = client_submit_request (this, &req, frame, conf->fops, - GFS3_OP_ICREATE, client3_3_icreate_cbk, - NULL, NULL, 0, NULL, 0, NULL, - (xdrproc_t) xdr_gfs4_icreate_req); - if (ret) - goto free_reqdata; - GF_FREE (req.xdata.xdata_val); - return 0; - - free_reqdata: - GF_FREE (req.xdata.xdata_val); - unwind: - CLIENT_STACK_UNWIND (icreate, frame, - -1, op_errno, NULL, NULL, NULL); - return 0; -} - -int32_t -client4_0_fsetattr (call_frame_t *frame, xlator_t *this, void *data) -{ - clnt_args_t *args = NULL; - int64_t remote_fd = -1; - clnt_conf_t *conf = NULL; - gfs3_fsetattr_req_v2 req = {{0},}; - int op_errno = ESTALE; - int ret = 0; - - if (!frame || !this || !data) - goto unwind; - - args = data; - conf = this->private; - - CLIENT_GET_REMOTE_FD(this, args->fd, DEFAULT_REMOTE_FD, - remote_fd, op_errno, unwind); - - req.fd = remote_fd; - req.valid = args->valid; - gf_stat_from_iatt (&req.stbuf, args->stbuf); - memcpy (req.gfid, args->fd->inode->gfid, 16); - - GF_PROTOCOL_DICT_SERIALIZE (this, args->xdata, (&req.xdata.xdata_val), - req.xdata.xdata_len, op_errno, unwind); - - ret = client_submit_request (this, &req, frame, conf->fops, - GFS3_OP_FSETATTR, - client3_3_fsetattr_cbk, NULL, - NULL, 0, NULL, 0, - NULL, (xdrproc_t)xdr_gfs3_fsetattr_req_v2); - if (ret) { - gf_log (this->name, GF_LOG_WARNING, "failed to send the fop"); - } - - GF_FREE (req.xdata.xdata_val); - - return 0; -unwind: - CLIENT_STACK_UNWIND (fsetattr, frame, -1, op_errno, NULL, NULL, NULL); - GF_FREE (req.xdata.xdata_val); - - return 0; -} - -int32_t -client4_0_rchecksum (call_frame_t *frame, xlator_t *this, - void *data) -{ - clnt_args_t *args = NULL; - int64_t remote_fd = -1; - clnt_conf_t *conf = NULL; - gfs3_rchecksum_req_v2 req = {{0},}; - int op_errno = ESTALE; - int ret = 0; - - if (!frame || !this || !data) - goto unwind; - - args = data; - conf = this->private; - - CLIENT_GET_REMOTE_FD(this, args->fd, DEFAULT_REMOTE_FD, - remote_fd, op_errno, unwind); - - req.len = args->len; - req.offset = args->offset; - req.fd = remote_fd; - memcpy (req.gfid, args->fd->inode->gfid, 16); - - GF_PROTOCOL_DICT_SERIALIZE (this, args->xdata, (&req.xdata.xdata_val), - req.xdata.xdata_len, op_errno, unwind); - - ret = client_submit_request (this, &req, frame, conf->fops, - GFS3_OP_RCHECKSUM, - client3_3_rchecksum_cbk, NULL, - NULL, 0, NULL, - 0, NULL, - (xdrproc_t)xdr_gfs3_rchecksum_req_v2); - if (ret) { - gf_log (this->name, GF_LOG_WARNING, "failed to send the fop"); - } - - GF_FREE (req.xdata.xdata_val); - - return 0; -unwind: - CLIENT_STACK_UNWIND (rchecksum, frame, -1, op_errno, 0, NULL, NULL); - GF_FREE (req.xdata.xdata_val); - - return 0; -} /* Table Specific to FOPS */ rpc_clnt_procedure_t clnt3_3_fop_actors[GF_FOP_MAXVALUE] = { @@ -6650,8 +6363,6 @@ char *clnt3_3_fop_names[GFS3_OP_MAXVALUE] = { [GFS3_OP_GETACTIVELK] = "GETACTIVELK", [GFS3_OP_SETACTIVELK] = "SETACTIVELK", [GFS3_OP_COMPOUND] = "COMPOUND", - [GFS3_OP_ICREATE] = "ICREATE", - [GFS3_OP_NAMELINK] = "NAMELINK", }; rpc_clnt_prog_t clnt3_3_fop_prog = { @@ -6701,9 +6412,9 @@ rpc_clnt_procedure_t clnt4_0_fop_actors[GF_FOP_MAXVALUE] = { [GF_FOP_FXATTROP] = { "FXATTROP", client3_3_fxattrop }, [GF_FOP_FGETXATTR] = { "FGETXATTR", client3_3_fgetxattr }, [GF_FOP_FSETXATTR] = { "FSETXATTR", client3_3_fsetxattr }, - [GF_FOP_RCHECKSUM] = { "RCHECKSUM", client4_0_rchecksum }, + [GF_FOP_RCHECKSUM] = { "RCHECKSUM", client3_3_rchecksum }, [GF_FOP_SETATTR] = { "SETATTR", client3_3_setattr }, - [GF_FOP_FSETATTR] = { "FSETATTR", client4_0_fsetattr }, + [GF_FOP_FSETATTR] = { "FSETATTR", client3_3_fsetattr }, [GF_FOP_READDIRP] = { "READDIRP", client3_3_readdirp }, [GF_FOP_FALLOCATE] = { "FALLOCATE", client3_3_fallocate }, [GF_FOP_DISCARD] = { "DISCARD", client3_3_discard }, @@ -6718,8 +6429,6 @@ rpc_clnt_procedure_t clnt4_0_fop_actors[GF_FOP_MAXVALUE] = { [GF_FOP_GETACTIVELK] = { "GETACTIVELK", client3_3_getactivelk}, [GF_FOP_SETACTIVELK] = { "SETACTIVELK", client3_3_setactivelk}, [GF_FOP_COMPOUND] = { "COMPOUND", client3_3_compound }, - [GF_FOP_ICREATE] = { "ICREATE", client3_3_icreate}, - [GF_FOP_NAMELINK] = { "NAMELINK", client3_3_namelink}, }; diff --git a/xlators/protocol/client/src/client-rpc-fops_v2.c b/xlators/protocol/client/src/client-rpc-fops_v2.c new file mode 100644 index 00000000000..4a4df478a67 --- /dev/null +++ b/xlators/protocol/client/src/client-rpc-fops_v2.c @@ -0,0 +1,5952 @@ +/* + Copyright (c) 2008-2012 Red Hat, Inc. <http://www.redhat.com> + This file is part of GlusterFS. + + This file is licensed to you under your choice of the GNU Lesser + General Public License, version 3 or any later version (LGPLv3 or + later), or the GNU General Public License, version 2 (GPLv2), in all + cases as published by the Free Software Foundation. +*/ + +#include "client.h" +#include "rpc-common-xdr.h" +#include "glusterfs4-xdr.h" +#include "glusterfs3.h" +#include "compat-errno.h" +#include "client-messages.h" +#include "defaults.h" +#include "client-common.h" +#include "compound-fop-utils.h" + +extern int32_t +client3_getspec (call_frame_t *frame, xlator_t *this, void *data); + +extern int +client_submit_vec_request (xlator_t *this, void *req, call_frame_t *frame, + rpc_clnt_prog_t *prog, int procnum, + fop_cbk_fn_t cbkfn, + struct iovec *payload, int payloadcnt, + struct iobref *iobref, xdrproc_t xdrproc); + +int +client4_0_symlink_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_3iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt stbuf = {0,}; + struct iatt preparent = {0,}; + struct iatt postparent = {0,}; + int ret = 0; + clnt_local_t *local = NULL; + inode_t *inode = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + local = frame->local; + inode = local->loc.inode; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_3iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_3iatt (this, &rsp, &stbuf, &preparent, + &postparent, &xdata); + +out: + if (rsp.op_ret == -1) { + if (GF_IGNORE_IF_GSYNCD_SAFE_ERROR(frame, rsp.op_errno)) { + /* no need to print the gfid, because it will be null, + * since symlink operation failed. + */ + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed. Path: (%s to %s)", + local->loc.path, local->loc2.path); + } + } + + CLIENT_STACK_UNWIND (symlink, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), inode, &stbuf, + &preparent, &postparent, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_mknod_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_3iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt stbuf = {0,}; + struct iatt preparent = {0,}; + struct iatt postparent = {0,}; + int ret = 0; + clnt_local_t *local = NULL; + inode_t *inode = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + local = frame->local; + + inode = local->loc.inode; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_3iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_3iatt (this, &rsp, &stbuf, &preparent, &postparent, + &xdata); + +out: + if (rsp.op_ret == -1 && + GF_IGNORE_IF_GSYNCD_SAFE_ERROR(frame, rsp.op_errno)) { + gf_msg (this->name, fop_log_level (GF_FOP_MKNOD, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed. Path: %s", + local->loc.path); + } + + CLIENT_STACK_UNWIND (mknod, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), inode, + &stbuf, &preparent, &postparent, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_mkdir_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_3iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt stbuf = {0,}; + struct iatt preparent = {0,}; + struct iatt postparent = {0,}; + int ret = 0; + clnt_local_t *local = NULL; + inode_t *inode = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + local = frame->local; + inode = local->loc.inode; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_3iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_3iatt (this, &rsp, &stbuf, &preparent, &postparent, + &xdata); + +out: + if (rsp.op_ret == -1 && + GF_IGNORE_IF_GSYNCD_SAFE_ERROR(frame, rsp.op_errno)) { + gf_msg (this->name, fop_log_level (GF_FOP_MKDIR, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed. Path: %s", + local->loc.path); + } + + CLIENT_STACK_UNWIND (mkdir, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), inode, + &stbuf, &preparent, &postparent, xdata); + + + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_open_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + clnt_local_t *local = NULL; + call_frame_t *frame = NULL; + fd_t *fd = NULL; + int ret = 0; + gfx_open_rsp rsp = {0,}; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + + this = THIS; + + frame = myframe; + local = frame->local; + + fd = local->fd; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_open_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (-1 != rsp.op_ret) { + ret = client_add_fd_to_saved_fds (frame->this, fd, &local->loc, + local->flags, rsp.fd, 0); + if (ret) { + rsp.op_ret = -1; + rsp.op_errno = -ret; + goto out; + } + } + + ret = xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_OPEN, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed. Path: %s (%s)", + local->loc.path, loc_gfid_utoa (&local->loc)); + } + + CLIENT_STACK_UNWIND (open, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), fd, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_stat_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt iatt = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_iatt (this, &rsp, &iatt, &xdata); +out: + if (rsp.op_ret == -1) { + /* stale filehandles are possible during normal operations, no + * need to spam the logs with these */ + if (rsp.op_errno == ESTALE) { + gf_msg_debug (this->name, 0, + "remote operation failed: %s", + strerror (gf_error_to_errno + (rsp.op_errno))); + } else { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + } + + CLIENT_STACK_UNWIND (stat, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &iatt, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_readlink_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_readlink_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt iatt = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_readlink_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + gfx_stat_to_iattx (&rsp.buf, &iatt); + + ret = xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + if (gf_error_to_errno(rsp.op_errno) == ENOENT) { + gf_msg_debug (this->name, 0, "remote operation failed:" + " %s", strerror + (gf_error_to_errno (rsp.op_errno))); + } else { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed"); + } + } + + CLIENT_STACK_UNWIND (readlink, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), rsp.path, + &iatt, xdata); + + /* This is allocated by the libc while decoding RPC msg */ + /* Hence no 'GF_FREE', but just 'free' */ + free (rsp.path); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_unlink_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_2iatt_rsp rsp = {0,}; + struct iatt preparent = {0,}; + struct iatt postparent = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &preparent, &postparent, + &xdata); + +out: + if (rsp.op_ret == -1) { + if (gf_error_to_errno(rsp.op_errno) == ENOENT) { + gf_msg_debug (this->name, 0, "remote operation failed:" + " %s", strerror + (gf_error_to_errno (rsp.op_errno))); + } else { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed"); + } + } + + CLIENT_STACK_UNWIND (unlink, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &preparent, + &postparent, xdata); + + + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_rmdir_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt preparent = {0,}; + struct iatt postparent = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &preparent, &postparent, + &xdata); + +out: + if (rsp.op_ret == -1) { + if (GF_IGNORE_IF_GSYNCD_SAFE_ERROR(frame, rsp.op_errno)) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + } + CLIENT_STACK_UNWIND (rmdir, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &preparent, + &postparent, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_truncate_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, + &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (truncate, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_statfs_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_statfs_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct statvfs statfs = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_statfs_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (-1 != rsp.op_ret) { + gf_statfs_to_statfs (&rsp.statfs, &statfs); + } + ret = xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (statfs, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &statfs, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_writev_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + clnt_local_t *local = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, &xdata); + if (ret < 0) + goto out; +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } else if (rsp.op_ret >= 0) { + if (local->attempt_reopen) + client_attempt_reopen (local->fd, this); + } + CLIENT_STACK_UNWIND (writev, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_flush_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + clnt_local_t *local = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + + frame = myframe; + this = THIS; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (rsp.op_ret >= 0 && !fd_is_anonymous (local->fd)) { + /* Delete all saved locks of the owner issuing flush */ + ret = delete_granted_locks_owner (local->fd, &local->owner); + gf_msg_trace (this->name, 0, + "deleting locks of owner (%s) returned %d", + lkowner_utoa (&local->owner), ret); + } + + xdr_to_dict (&rsp.xdata, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_FLUSH, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (flush, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fsync_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, + &xdata); + if (ret < 0) + goto out; + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (fsync, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_setxattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + int op_errno = EINVAL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); + if (ret < 0) + goto out; + +out: + op_errno = gf_error_to_errno (rsp.op_errno); + if (rsp.op_ret == -1) { + if (op_errno == ENOTSUP) { + gf_msg_debug (this->name, 0, "remote operation failed:" + " %s", strerror (op_errno)); + } else { + gf_msg (this->name, GF_LOG_WARNING, op_errno, + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed"); + } + } + + CLIENT_STACK_UNWIND (setxattr, frame, rsp.op_ret, op_errno, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_getxattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_dict_rsp rsp = {0,}; + call_frame_t *frame = NULL; + dict_t *dict = NULL; + int op_errno = EINVAL; + int ret = 0; + clnt_local_t *local = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + + this = THIS; + + frame = myframe; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_dict_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + op_errno = EINVAL; + goto out; + } + + op_errno = gf_error_to_errno (rsp.op_errno); + ret = client_post_common_dict (this, &rsp, &dict, &xdata); + if (ret) { + op_errno = -ret; + goto out; + } + +out: + if (rsp.op_ret == -1) { + if ((op_errno == ENOTSUP) || (op_errno == ENODATA) || + (op_errno == ESTALE) || (op_errno == ENOENT)) { + gf_msg_debug (this->name, 0, + "remote operation failed: %s. Path: %s " + "(%s). Key: %s", strerror (op_errno), + local->loc.path, + loc_gfid_utoa (&local->loc), + (local->name) ? local->name : "(null)"); + } else { + gf_msg (this->name, GF_LOG_WARNING, op_errno, + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed. Path: %s (%s). Key: %s", + local->loc.path, + loc_gfid_utoa (&local->loc), + (local->name) ? local->name : "(null)"); + } + } + + CLIENT_STACK_UNWIND (getxattr, frame, rsp.op_ret, op_errno, dict, xdata); + + if (xdata) + dict_unref (xdata); + + if (dict) + dict_unref (dict); + + return 0; +} + +int +client4_0_fgetxattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_dict_rsp rsp = {0,}; + call_frame_t *frame = NULL; + dict_t *dict = NULL; + int ret = 0; + int op_errno = EINVAL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_dict_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + op_errno = EINVAL; + goto out; + } + + op_errno = gf_error_to_errno (rsp.op_errno); + ret = client_post_common_dict (this, &rsp, &dict, &xdata); + if (ret) { + op_errno = -ret; + goto out; + } +out: + if (rsp.op_ret == -1) { + if ((op_errno == ENOTSUP) || (op_errno == ERANGE) || + (op_errno == ENODATA) || (op_errno == ENOENT)) { + gf_msg_debug (this->name, 0, + "remote operation failed: %s", + strerror (op_errno)); + } else { + gf_msg (this->name, GF_LOG_WARNING, op_errno, + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed"); + } + } + + CLIENT_STACK_UNWIND (fgetxattr, frame, rsp.op_ret, op_errno, dict, xdata); + + if (xdata) + dict_unref (xdata); + + if (dict) + dict_unref (dict); + + return 0; +} + +int +client4_0_removexattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + gf_loglevel_t loglevel = GF_LOG_NONE; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + if ((ENODATA == rsp.op_errno) || (ENOATTR == rsp.op_errno)) + loglevel = GF_LOG_DEBUG; + else + loglevel = GF_LOG_WARNING; + + gf_msg (this->name, loglevel, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (removexattr, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fremovexattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (fremovexattr, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fsyncdir_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (fsyncdir, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_access_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (access, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_ftruncate_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, + &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (ftruncate, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fstat_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt stat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_iatt (this, &rsp, &stat, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (fstat, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &stat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_inodelk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_INODELK, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation failed"); + } + CLIENT_STACK_UNWIND (inodelk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_finodelk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + clnt_local_t *local = NULL; + + frame = myframe; + this = frame->this; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_FINODELK, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation failed"); + } else if (rsp.op_ret == 0) { + if (local->attempt_reopen) + client_attempt_reopen (local->fd, this); + } + CLIENT_STACK_UNWIND (finodelk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_entrylk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_ENTRYLK, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation failed"); + } + + CLIENT_STACK_UNWIND (entrylk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fentrylk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); + +out: + if ((rsp.op_ret == -1) && + (EAGAIN != gf_error_to_errno (rsp.op_errno))) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (fentrylk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_xattrop_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + dict_t *dict = NULL; + gfx_common_dict_rsp rsp = {0,}; + int ret = 0; + int op_errno = EINVAL; + clnt_local_t *local = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_dict_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + op_errno = EINVAL; + goto out; + } + + op_errno = rsp.op_errno; + ret = client_post_common_dict (this, &rsp, &dict, &xdata); + if (ret) { + op_errno = -ret; + goto out; + } +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_XATTROP, op_errno), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation failed. " + "Path: %s (%s)", + local->loc.path, loc_gfid_utoa (&local->loc)); + } + + CLIENT_STACK_UNWIND (xattrop, frame, rsp.op_ret, + gf_error_to_errno (op_errno), dict, xdata); + + if (xdata) + dict_unref (xdata); + + if (dict) + dict_unref (dict); + + return 0; +} + +int +client4_0_fxattrop_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + dict_t *dict = NULL; + dict_t *xdata = NULL; + gfx_common_dict_rsp rsp = {0,}; + int ret = 0; + int op_errno = 0; + clnt_local_t *local = NULL; + xlator_t *this = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_dict_rsp); + if (ret < 0) { + rsp.op_ret = -1; + op_errno = EINVAL; + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + goto out; + } + op_errno = rsp.op_errno; + ret = client_post_common_dict (this, &rsp, &dict, &xdata); + if (ret) { + rsp.op_ret = -1; + op_errno = -ret; + goto out; + } +out: + + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } else if (rsp.op_ret == 0) { + if (local->attempt_reopen) + client_attempt_reopen (local->fd, this); + } + CLIENT_STACK_UNWIND (fxattrop, frame, rsp.op_ret, + gf_error_to_errno (op_errno), dict, xdata); + if (xdata) + dict_unref (xdata); + + if (dict) + dict_unref (dict); + + return 0; +} + +int +client4_0_fsetxattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + int op_errno = EINVAL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); + +out: + op_errno = gf_error_to_errno (rsp.op_errno); + if (rsp.op_ret == -1) { + if (op_errno == ENOTSUP) { + gf_msg_debug (this->name, 0, "remote operation failed:" + " %s", strerror (op_errno)); + } else { + gf_msg (this->name, GF_LOG_WARNING, rsp.op_errno, + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed"); + } + } + + CLIENT_STACK_UNWIND (fsetxattr, frame, rsp.op_ret, op_errno, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fallocate_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_2iatt_rsp rsp = {0,}; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, &xdata); + if (ret < 0) + goto out; + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (fallocate, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_discard_cbk(struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic(*iov, &rsp, (xdrproc_t) xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (discard, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_zerofill_cbk(struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_2iatt_rsp rsp = {0,}; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic(*iov, &rsp, (xdrproc_t) xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (zerofill, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_ipc_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic(*iov, &rsp, (xdrproc_t) xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (ipc, frame, + rsp.op_ret, gf_error_to_errno (rsp.op_errno), + xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_seek_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + struct gfx_seek_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + ret = xdr_to_generic(*iov, &rsp, (xdrproc_t) xdr_gfx_seek_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (seek, frame, + rsp.op_ret, gf_error_to_errno (rsp.op_errno), + rsp.offset, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_setattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (setattr, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_fsetattr_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt prestat = {0,}; + struct iatt poststat = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_2iatt (this, &rsp, &prestat, &poststat, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (fsetattr, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &prestat, + &poststat, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_create_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + fd_t *fd = NULL; + inode_t *inode = NULL; + struct iatt stbuf = {0, }; + struct iatt preparent = {0, }; + struct iatt postparent = {0, }; + int32_t ret = -1; + clnt_local_t *local = NULL; + gfx_create_rsp rsp = {0,}; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + fd = local->fd; + inode = local->loc.inode; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_create_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (-1 != rsp.op_ret) { + ret = client_post_create_v2 (this, &rsp, &stbuf, + &preparent, &postparent, + local, &xdata); + if (ret < 0) + goto out; + ret = client_add_fd_to_saved_fds (frame->this, fd, &local->loc, + local->flags, rsp.fd, 0); + if (ret) { + rsp.op_ret = -1; + rsp.op_errno = -ret; + goto out; + } + } + + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed. Path: %s", + local->loc.path); + } + + CLIENT_STACK_UNWIND (create, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), fd, inode, + &stbuf, &preparent, &postparent, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_lease_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + struct gf_lease lease = {0,}; + gfx_lease_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + gf_msg (this->name, GF_LOG_ERROR, ENOTCONN, + PC_MSG_REMOTE_OP_FAILED, "Lease fop failed"); + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_lease_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_lease_v2 (this, &rsp, &lease, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (lease, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &lease, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_lk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + struct gf_flock lock = {0,}; + gfx_lk_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_lk_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (rsp.op_ret >= 0) { + ret = client_post_lk_v2 (this, &rsp, &lock, &xdata); + if (ret < 0) + goto out; + } + + /* Save the lock to the client lock cache to be able + to recover in the case of server reboot.*/ + /* + temporarily + if (local->cmd == F_SETLK || local->cmd == F_SETLKW) { + ret = client_add_lock_for_recovery (local->fd, &lock, + local->owner, local->cmd); + if (ret < 0) { + rsp.op_ret = -1; + rsp.op_errno = -ret; + } + } + */ + +out: + if ((rsp.op_ret == -1) && + (EAGAIN != gf_error_to_errno (rsp.op_errno))) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (lk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &lock, xdata); + + free (rsp.flock.lk_owner.lk_owner_val); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_readdir_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_readdir_rsp rsp = {0,}; + int32_t ret = 0; + clnt_local_t *local = NULL; + gf_dirent_t entries; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + + INIT_LIST_HEAD (&entries.list); + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_readdir_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_readdir_v2 (this, &rsp, &entries, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed: remote_fd = %d", + local->cmd); + } + CLIENT_STACK_UNWIND (readdir, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &entries, xdata); + + if (rsp.op_ret != -1) { + gf_dirent_free (&entries); + } + + if (xdata) + dict_unref (xdata); + + clnt_readdir_rsp_cleanup_v2 (&rsp); + + return 0; +} + +int +client4_0_readdirp_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_readdirp_rsp rsp = {0,}; + int32_t ret = 0; + clnt_local_t *local = NULL; + gf_dirent_t entries; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + + INIT_LIST_HEAD (&entries.list); + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_readdirp_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_readdirp_v2 (this, &rsp, local->fd, &entries, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (readdirp, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &entries, xdata); + + if (rsp.op_ret != -1) { + gf_dirent_free (&entries); + } + + + if (xdata) + dict_unref (xdata); + + clnt_readdirp_rsp_cleanup_v2 (&rsp); + + return 0; +} + +int +client4_0_rename_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_rename_rsp rsp = {0,}; + struct iatt stbuf = {0,}; + struct iatt preoldparent = {0,}; + struct iatt postoldparent = {0,}; + struct iatt prenewparent = {0,}; + struct iatt postnewparent = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_rename_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + client_post_rename_v2 (this, &rsp, &stbuf, &preoldparent, + &postoldparent, &prenewparent, + &postnewparent, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (rename, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), + &stbuf, &preoldparent, &postoldparent, + &prenewparent, &postnewparent, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_link_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_3iatt_rsp rsp = {0,}; + call_frame_t *frame = NULL; + struct iatt stbuf = {0,}; + struct iatt preparent = {0,}; + struct iatt postparent = {0,}; + int ret = 0; + clnt_local_t *local = NULL; + inode_t *inode = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + local = frame->local; + inode = local->loc.inode; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_3iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_common_3iatt (this, &rsp, &stbuf, &preparent, + &postparent, &xdata); +out: + if (rsp.op_ret == -1) { + if (GF_IGNORE_IF_GSYNCD_SAFE_ERROR(frame, rsp.op_errno)) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed: (%s -> %s)", + local->loc.path, local->loc2.path); + } + } + + CLIENT_STACK_UNWIND (link, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), inode, + &stbuf, &preparent, &postparent, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_opendir_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + clnt_local_t *local = NULL; + call_frame_t *frame = NULL; + fd_t *fd = NULL; + int ret = 0; + gfx_open_rsp rsp = {0,}; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + + fd = local->fd; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + /* open and opendir are two operations dealing with same thing, + but separated by fop number only */ + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_open_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (-1 != rsp.op_ret) { + ret = client_add_fd_to_saved_fds (frame->this, fd, &local->loc, + 0, rsp.fd, 1); + if (ret) { + rsp.op_ret = -1; + rsp.op_errno = -ret; + goto out; + } + } + + ret = xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, fop_log_level (GF_FOP_OPENDIR, + gf_error_to_errno (rsp.op_errno)), + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, "remote operation failed." + " Path: %s (%s)", + local->loc.path, loc_gfid_utoa (&local->loc)); + } + CLIENT_STACK_UNWIND (opendir, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), fd, xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int +client4_0_lookup_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_common_2iatt_rsp rsp = {0,}; + clnt_local_t *local = NULL; + call_frame_t *frame = NULL; + int ret = 0; + struct iatt stbuf = {0,}; + struct iatt postparent = {0,}; + int op_errno = EINVAL; + dict_t *xdata = NULL; + inode_t *inode = NULL; + xlator_t *this = NULL; + + this = THIS; + + frame = myframe; + local = frame->local; + inode = local->loc.inode; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + op_errno = EINVAL; + goto out; + } + + /* Preserve the op_errno received from the server */ + op_errno = gf_error_to_errno (rsp.op_errno); + + ret = client_post_common_2iatt (this, &rsp, &stbuf, &postparent, &xdata); + if (ret < 0) { + /* Don't change the op_errno if the fop failed on server */ + if (rsp.op_ret == 0) + op_errno = rsp.op_errno; + rsp.op_ret = -1; + goto out; + } + + if (rsp.op_ret < 0) + goto out; + + if ((!gf_uuid_is_null (inode->gfid)) + && (gf_uuid_compare (stbuf.ia_gfid, inode->gfid) != 0)) { + gf_msg_debug (frame->this->name, 0, + "gfid changed for %s", local->loc.path); + + rsp.op_ret = -1; + op_errno = ESTALE; + if (xdata) + ret = dict_set_int32 (xdata, "gfid-changed", 1); + + goto out; + } + + rsp.op_ret = 0; + +out: + /* Restore the correct op_errno to rsp.op_errno */ + rsp.op_errno = op_errno; + if (rsp.op_ret == -1) { + /* any error other than ENOENT */ + if (!(local->loc.name && rsp.op_errno == ENOENT) && + !(rsp.op_errno == ESTALE)) + gf_msg (this->name, GF_LOG_WARNING, rsp.op_errno, + PC_MSG_REMOTE_OP_FAILED, "remote operation " + "failed. Path: %s (%s)", + local->loc.path, + loc_gfid_utoa (&local->loc)); + else + gf_msg_trace (this->name, 0, "not found on remote " + "node"); + + } + + CLIENT_STACK_UNWIND (lookup, frame, rsp.op_ret, rsp.op_errno, inode, + &stbuf, xdata, &postparent); + + if (xdata) + dict_unref (xdata); + + + + return 0; +} + +int +client4_0_readv_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + struct iobref *iobref = NULL; + struct iovec vector[MAX_IOVEC] = {{0}, }; + struct iatt stat = {0,}; + gfx_read_rsp rsp = {0,}; + int ret = 0, rspcount = 0; + clnt_local_t *local = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + memset (vector, 0, sizeof (vector)); + + frame = myframe; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_read_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + ret = client_post_readv_v2 (this, &rsp, &iobref, req->rsp_iobref, + &stat, vector, &req->rsp[1], + &rspcount, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } else if (rsp.op_ret >= 0) { + if (local->attempt_reopen) + client_attempt_reopen (local->fd, this); + } + CLIENT_STACK_UNWIND (readv, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), vector, rspcount, + &stat, iobref, xdata); + + + + if (xdata) + dict_unref (xdata); + + return 0; +} + +int +client4_0_release_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + + frame = myframe; + STACK_DESTROY (frame->root); + return 0; +} +int +client4_0_releasedir_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + + frame = myframe; + STACK_DESTROY (frame->root); + return 0; +} + +int +client4_0_getactivelk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_getactivelk_rsp rsp = {0,}; + int32_t ret = 0; + lock_migration_info_t locklist; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_getactivelk_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + INIT_LIST_HEAD (&locklist.list); + + if (rsp.op_ret > 0) { + clnt_unserialize_rsp_locklist_v2 (this, &rsp, &locklist); + } + + xdr_to_dict (&rsp.xdata, &xdata); + +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (getactivelk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), &locklist, + xdata); + if (xdata) + dict_unref (xdata); + + clnt_getactivelk_rsp_cleanup_v2 (&rsp); + + return 0; +} + +int +client4_0_setactivelk_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_common_rsp rsp = {0,}; + int32_t ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (setactivelk, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), xdata); + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int32_t +client4_0_releasedir (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_fd_ctx_t *fdctx = NULL; + clnt_args_t *args = NULL; + int64_t remote_fd = -1; + gf_boolean_t destroy = _gf_false; + + if (!this || !data) + goto out; + + args = data; + conf = this->private; + + pthread_mutex_lock (&conf->lock); + { + fdctx = this_fd_del_ctx (args->fd, this); + if (fdctx != NULL) { + remote_fd = fdctx->remote_fd; + + /* fdctx->remote_fd == -1 indicates a reopen attempt + in progress. Just mark ->released = 1 and let + reopen_cbk handle releasing + */ + + if (remote_fd == -1) { + fdctx->released = 1; + } else { + list_del_init (&fdctx->sfd_pos); + destroy = _gf_true; + } + } + } + pthread_mutex_unlock (&conf->lock); + + if (destroy) + client_fdctx_destroy (this, fdctx); + +out: + + return 0; +} + +int32_t +client4_0_release (call_frame_t *frame, xlator_t *this, + void *data) +{ + int64_t remote_fd = -1; + clnt_conf_t *conf = NULL; + clnt_fd_ctx_t *fdctx = NULL; + clnt_args_t *args = NULL; + lk_heal_state_t lk_heal_state = GF_LK_HEAL_DONE; + gf_boolean_t destroy = _gf_false; + + if (!this || !data) + goto out; + + args = data; + conf = this->private; + + pthread_mutex_lock (&conf->lock); + { + fdctx = this_fd_del_ctx (args->fd, this); + if (fdctx != NULL) { + remote_fd = fdctx->remote_fd; + lk_heal_state = fdctx->lk_heal_state; + + /* fdctx->remote_fd == -1 indicates a reopen attempt + in progress. Just mark ->released = 1 and let + reopen_cbk handle releasing + */ + if (remote_fd == -1) { + fdctx->released = 1; + } else if (lk_heal_state == GF_LK_HEAL_DONE) { + list_del_init (&fdctx->sfd_pos); + destroy = _gf_true; + } + } + } + pthread_mutex_unlock (&conf->lock); + + if (destroy) + client_fdctx_destroy (this, fdctx); +out: + return 0; +} + + +int32_t +client4_0_lookup (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_local_t *local = NULL; + clnt_args_t *args = NULL; + gfx_lookup_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + data_t *content = NULL; + struct iovec vector[MAX_IOVEC] = {{0}, }; + int count = 0; + struct iobref *rsp_iobref = NULL; + struct iobuf *rsp_iobuf = NULL; + struct iovec *rsphdr = NULL; + + if (!frame || !this || !data) + goto unwind; + + memset (vector, 0, sizeof (vector)); + + conf = this->private; + args = data; + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + if (!(args->loc && args->loc->inode)) + goto unwind; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + if (args->xdata) { + content = dict_get (args->xdata, GF_CONTENT_KEY); + if (content != NULL) { + rsp_iobref = iobref_new (); + if (rsp_iobref == NULL) { + goto unwind; + } + + /* TODO: what is the size we should send ? */ + /* This change very much depends on quick-read + changes */ + rsp_iobuf = iobuf_get (this->ctx->iobuf_pool); + if (rsp_iobuf == NULL) { + goto unwind; + } + + iobref_add (rsp_iobref, rsp_iobuf); + rsphdr = &vector[0]; + rsphdr->iov_base = iobuf_ptr (rsp_iobuf); + rsphdr->iov_len = iobuf_pagesize (rsp_iobuf); + count = 1; + local->iobref = rsp_iobref; + iobuf_unref (rsp_iobuf); + rsp_iobuf = NULL; + rsp_iobref = NULL; + } + } + + ret = client_pre_lookup_v2 (this, &req, args->loc, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_LOOKUP, client4_0_lookup_cbk, + NULL, rsphdr, count, + NULL, 0, local->iobref, + (xdrproc_t)xdr_gfx_lookup_req); + + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (lookup, frame, -1, op_errno, NULL, NULL, NULL, + NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + if (rsp_iobref) + iobref_unref (rsp_iobref); + + return 0; +} + +int32_t +client4_0_stat (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_stat_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_stat_v2 (this, &req, args->loc, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_STAT, client4_0_stat_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_stat_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (stat, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_truncate (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_truncate_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_truncate_v2 (this, &req, args->loc, args->offset, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_TRUNCATE, + client4_0_truncate_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_truncate_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (truncate, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_ftruncate (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_ftruncate_req req = {{0,},}; + int op_errno = EINVAL; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + ret = client_pre_ftruncate_v2 (this, &req, args->fd, args->offset, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FTRUNCATE, + client4_0_ftruncate_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_ftruncate_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (ftruncate, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_access (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_access_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + + ret = client_pre_access_v2 (this, &req, args->loc, args->mask, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_ACCESS, + client4_0_access_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_access_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (access, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_readlink (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_readlink_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + clnt_local_t *local = NULL; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + + frame->local = local; + + ret = client_pre_readlink_v2 (this, &req, args->loc, args->size, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_READLINK, + client4_0_readlink_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_readlink_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + + CLIENT_STACK_UNWIND (readlink, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_unlink (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_unlink_req req = {{0,},}; + int ret = 0; + int op_errno = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_unlink_v2 (this, &req, args->loc, args->flags, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_UNLINK, + client4_0_unlink_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_unlink_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (unlink, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_rmdir (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_rmdir_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_rmdir_v2 (this, &req, args->loc, args->flags, + args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_RMDIR, client4_0_rmdir_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_rmdir_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (rmdir, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_symlink (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_symlink_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + + frame->local = local; + + if (!(args->loc && args->loc->parent)) + goto unwind; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + local->loc2.path = gf_strdup (args->linkname); + + ret = client_pre_symlink_v2 (this, &req, args->loc, + args->linkname, args->umask, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_SYMLINK, client4_0_symlink_cbk, + NULL, NULL, 0, NULL, + 0, NULL, (xdrproc_t)xdr_gfx_symlink_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + + CLIENT_STACK_UNWIND (symlink, frame, -1, op_errno, NULL, NULL, NULL, + NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_rename (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_rename_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_rename_v2 (this, &req, args->oldloc, args->newloc, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_RENAME, client4_0_rename_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_rename_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (rename, frame, -1, op_errno, NULL, NULL, NULL, + NULL, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_link (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_link_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + + frame->local = local; + + ret = client_pre_link_v2 (this, &req, args->oldloc, args->newloc, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + loc_copy (&local->loc, args->oldloc); + loc_path (&local->loc, NULL); + loc_copy (&local->loc2, args->newloc); + loc_path (&local->loc2, NULL); + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_LINK, client4_0_link_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_link_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (link, frame, -1, op_errno, NULL, NULL, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_mknod (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_mknod_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + ret = client_pre_mknod_v2 (this, &req, args->loc, + args->mode, args->rdev, args->umask, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_MKNOD, client4_0_mknod_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_mknod_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (mknod, frame, -1, op_errno, NULL, NULL, NULL, + NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_mkdir (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_mkdir_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + if (!args->xdata || !dict_get (args->xdata, "gfid-req")) { + op_errno = EPERM; + gf_msg_callingfn (this->name, GF_LOG_WARNING, op_errno, + PC_MSG_GFID_NULL, "mkdir: %s is received " + "without gfid-req %p", args->loc->path, + args->xdata); + goto unwind; + } + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + if (!(args->loc && args->loc->parent)) + goto unwind; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + ret = client_pre_mkdir_v2 (this, &req, args->loc, args->mode, + args->umask, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_MKDIR, client4_0_mkdir_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_mkdir_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (mkdir, frame, -1, op_errno, NULL, NULL, NULL, + NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_create (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_create_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + local->fd = fd_ref (args->fd); + local->flags = args->flags; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + ret = client_pre_create_v2 (this, &req, args->loc, + args->fd, args->mode, + args->flags, args->umask, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_CREATE, client4_0_create_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_create_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (create, frame, -1, op_errno, NULL, NULL, NULL, + NULL, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_open (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_open_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + local->flags = args->flags; + + local->fd = fd_ref (args->fd); + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + ret = client_pre_open_v2 (this, &req, args->loc, args->fd, args->flags, + args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_OPEN, client4_0_open_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_open_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (open, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_readv (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + clnt_local_t *local = NULL; + int op_errno = ESTALE; + gfx_read_req req = {{0,},}; + int ret = 0; + struct iovec rsp_vec = {0, }; + struct iobuf *rsp_iobuf = NULL; + struct iobref *rsp_iobref = NULL; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_readv_v2 (this, &req, args->fd, args->size, + args->offset, args->flags, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_fd_fop_prepare_local (frame, args->fd, req.fd); + if (ret) { + op_errno = -ret; + goto unwind; + } + local = frame->local; + + rsp_iobuf = iobuf_get2 (this->ctx->iobuf_pool, args->size); + if (rsp_iobuf == NULL) { + op_errno = ENOMEM; + goto unwind; + } + + rsp_iobref = iobref_new (); + if (rsp_iobref == NULL) { + op_errno = ENOMEM; + goto unwind; + } + + iobref_add (rsp_iobref, rsp_iobuf); + rsp_vec.iov_base = iobuf_ptr (rsp_iobuf); + rsp_vec.iov_len = iobuf_pagesize (rsp_iobuf); + local->iobref = rsp_iobref; + iobuf_unref (rsp_iobuf); + rsp_iobref = NULL; + rsp_iobuf = NULL; + + if (args->size > rsp_vec.iov_len) { + gf_msg (this->name, GF_LOG_WARNING, ENOMEM, PC_MSG_NO_MEMORY, + "read-size (%lu) is bigger than iobuf size (%lu)", + (unsigned long)args->size, + (unsigned long)rsp_vec.iov_len); + op_errno = EINVAL; + goto unwind; + } + + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_READ, client4_0_readv_cbk, NULL, + NULL, 0, &rsp_vec, 1, + local->iobref, + (xdrproc_t)xdr_gfx_read_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + if (rsp_iobuf) + iobuf_unref (rsp_iobuf); + + if (rsp_iobref) + iobref_unref (rsp_iobref); + + CLIENT_STACK_UNWIND (readv, frame, -1, op_errno, NULL, 0, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_writev (call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_write_req req = {{0,},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_writev_v2 (this, &req, args->fd, args->size, + args->offset, args->flags, &args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_fd_fop_prepare_local (frame, args->fd, req.fd); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_vec_request (this, &req, frame, conf->fops, + GFS3_OP_WRITE, client4_0_writev_cbk, + args->vector, args->count, + args->iobref, + (xdrproc_t)xdr_gfx_write_req); + if (ret) { + /* + * If the lower layers fail to submit a request, they'll also + * do the unwind for us (see rpc_clnt_submit), so don't unwind + * here in such cases. + */ + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (writev, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_flush (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_flush_req req = {{0,},}; + clnt_conf_t *conf = NULL; + clnt_local_t *local = NULL; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + + frame->local = local; + + local->fd = fd_ref (args->fd); + local->owner = frame->root->lk_owner; + ret = client_pre_flush_v2 (this, &req, args->fd, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FLUSH, client4_0_flush_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_flush_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + + return 0; + +unwind: + CLIENT_STACK_UNWIND (flush, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_fsync (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_fsync_req req = {{0,},}; + clnt_conf_t *conf = NULL; + int op_errno = 0; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fsync_v2 (this, &req, args->fd, args->flags, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FSYNC, client4_0_fsync_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_fsync_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (fsync, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_fstat (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_fstat_req req = {{0,},}; + clnt_conf_t *conf = NULL; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fstat_v2 (this, &req, args->fd, args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FSTAT, client4_0_fstat_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_fstat_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (fstat, frame, -1, op_errno, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_opendir (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_opendir_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + local->fd = fd_ref (args->fd); + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + ret = client_pre_opendir_v2 (this, &req, args->loc, args->fd, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_OPENDIR, client4_0_opendir_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_opendir_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (opendir, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_fsyncdir (call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_fsyncdir_req req = {{0,},}; + int ret = 0; + int32_t op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fsyncdir_v2 (this, &req, args->fd, args->flags, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FSYNCDIR, client4_0_fsyncdir_cbk, + NULL, NULL, 0, + NULL, 0, NULL, + (xdrproc_t)xdr_gfx_fsyncdir_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (fsyncdir, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_statfs (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_statfs_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + ret = client_pre_statfs_v2 (this, &req, args->loc, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_STATFS, client4_0_statfs_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_statfs_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + CLIENT_STACK_UNWIND (statfs, frame, -1, op_errno, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_setxattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_setxattr_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_setxattr_v2 (this, &req, args->loc, args->xattr, + args->flags, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_SETXATTR, client4_0_setxattr_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_setxattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + GF_FREE (req.dict.pairs.pairs_val); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (setxattr, frame, -1, op_errno, NULL); + GF_FREE (req.dict.pairs.pairs_val); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_fsetxattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_fsetxattr_req req = {{0,},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fsetxattr_v2 (this, &req, args->fd, args->flags, + args->xattr, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FSETXATTR, client4_0_fsetxattr_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_fsetxattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.dict.pairs.pairs_val); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fsetxattr, frame, -1, op_errno, NULL); + GF_FREE (req.dict.pairs.pairs_val); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_fgetxattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_fgetxattr_req req = {{0,},}; + int op_errno = ESTALE; + int ret = 0; + clnt_local_t *local = NULL; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + ret = client_pre_fgetxattr_v2 (this, &req, args->fd, args->name, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FGETXATTR, + client4_0_fgetxattr_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_fgetxattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fgetxattr, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_getxattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_getxattr_req req = {{0,},}; + dict_t *dict = NULL; + int ret = 0; + int32_t op_ret = -1; + int op_errno = ESTALE; + clnt_local_t *local = NULL; + + if (!frame || !this || !data) { + op_errno = 0; + goto unwind; + } + args = data; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + + frame->local = local; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + + if (args->name) + local->name = gf_strdup (args->name); + + conf = this->private; + + if (args && args->name) { + if (is_client_dump_locks_cmd ((char *)args->name)) { + dict = dict_new (); + + if (!dict) { + op_errno = ENOMEM; + goto unwind; + } + + ret = client_dump_locks ((char *)args->name, + args->loc->inode, + dict); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, EINVAL, + PC_MSG_INVALID_ENTRY, "Client dump " + "locks failed"); + op_errno = ENOMEM; + goto unwind; + } + + GF_ASSERT (dict); + op_ret = 0; + op_errno = 0; + goto unwind; + } + } + + ret = client_pre_getxattr_v2 (this, &req, args->loc, args->name, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_GETXATTR, + client4_0_getxattr_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_getxattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (getxattr, frame, op_ret, op_errno, dict, NULL); + + if (dict) { + dict_unref(dict); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_xattrop (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_xattrop_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + clnt_local_t *local = NULL; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + if (!(args->loc && args->loc->inode)) + goto unwind; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + loc_copy (&local->loc, args->loc); + loc_path (&local->loc, NULL); + conf = this->private; + + ret = client_pre_xattrop_v2 (this, &req, args->loc, args->xattr, + args->flags, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_XATTROP, + client4_0_xattrop_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_xattrop_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.dict.pairs.pairs_val); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (xattrop, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.dict.pairs.pairs_val); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_fxattrop (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_fxattrop_req req = {{0,},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fxattrop_v2 (this, &req, args->fd, args->xattr, + args->flags, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_fd_fop_prepare_local (frame, args->fd, req.fd); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FXATTROP, + client4_0_fxattrop_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_fxattrop_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.dict.pairs.pairs_val); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fxattrop, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.dict.pairs.pairs_val); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_removexattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_removexattr_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_removexattr_v2 (this, &req, args->loc, args->name, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_REMOVEXATTR, + client4_0_removexattr_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_removexattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (removexattr, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_fremovexattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_fremovexattr_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + ret = client_pre_fremovexattr_v2 (this, &req, args->fd, args->name, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FREMOVEXATTR, + client4_0_fremovexattr_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_fremovexattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fremovexattr, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_lease (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_lease_req req = {{0,},}; + clnt_conf_t *conf = NULL; + int op_errno = ESTALE; + int ret = 0; + + GF_VALIDATE_OR_GOTO ("client", this, unwind); + GF_VALIDATE_OR_GOTO (this->name, frame, unwind); + GF_VALIDATE_OR_GOTO (this->name, data, unwind); + + args = data; + conf = this->private; + + ret = client_pre_lease_v2 (this, &req, args->loc, args->lease, + args->xdata); + if (ret < 0) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, GFS3_OP_LEASE, + client4_0_lease_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_lease_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (lease, frame, -1, op_errno, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_lk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_lk_req req = {{0,},}; + int32_t gf_cmd = 0; + clnt_local_t *local = NULL; + clnt_conf_t *conf = NULL; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + ret = client_cmd_to_gf_cmd (args->cmd, &gf_cmd); + if (ret) { + op_errno = EINVAL; + gf_msg (this->name, GF_LOG_WARNING, EINVAL, + PC_MSG_INVALID_ENTRY, "Unknown cmd (%d)!", gf_cmd); + goto unwind; + } + + local->owner = frame->root->lk_owner; + local->cmd = args->cmd; + local->fd = fd_ref (args->fd); + + ret = client_pre_lk_v2 (this, &req, args->cmd, args->flock, + args->fd, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, GFS3_OP_LK, + client4_0_lk_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_lk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (lk, frame, -1, op_errno, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_inodelk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_inodelk_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_inodelk_v2 (this, &req, args->loc, args->cmd, + args->flock, args->volume, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_INODELK, + client4_0_inodelk_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_inodelk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (inodelk, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_finodelk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_finodelk_req req = {{0,},}; + clnt_conf_t *conf = NULL; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_finodelk_v2 (this, &req, args->fd, + args->cmd, args->flock, args->volume, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_fd_fop_prepare_local (frame, args->fd, req.fd); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FINODELK, + client4_0_finodelk_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_finodelk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + return 0; +unwind: + CLIENT_STACK_UNWIND (finodelk, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_entrylk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_entrylk_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + + conf = this->private; + + ret = client_pre_entrylk_v2 (this, &req, args->loc, args->cmd_entrylk, + args->type, args->volume, args->basename, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_ENTRYLK, + client4_0_entrylk_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_entrylk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (entrylk, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + + +int32_t +client4_0_fentrylk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_fentrylk_req req = {{0,},}; + clnt_conf_t *conf = NULL; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fentrylk_v2 (this, &req, args->fd, args->cmd_entrylk, + args->type, args->volume, args->basename, + args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FENTRYLK, + client4_0_fentrylk_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_fentrylk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fentrylk, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_readdir (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + int64_t remote_fd = -1; + clnt_conf_t *conf = NULL; + gfx_readdir_req req = {{0,},}; + gfx_readdir_rsp rsp = {0, }; + clnt_local_t *local = NULL; + int op_errno = ESTALE; + int ret = 0; + int count = 0; + struct iobref *rsp_iobref = NULL; + struct iobuf *rsp_iobuf = NULL; + struct iovec *rsphdr = NULL; + struct iovec vector[MAX_IOVEC] = {{0}, }; + int readdir_rsp_size = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + readdir_rsp_size = xdr_sizeof ((xdrproc_t) xdr_gfx_readdir_rsp, &rsp) + + args->size; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + local->cmd = remote_fd; + + if ((readdir_rsp_size + GLUSTERFS_RPC_REPLY_SIZE + GLUSTERFS_RDMA_MAX_HEADER_SIZE) + > (GLUSTERFS_RDMA_INLINE_THRESHOLD)) { + rsp_iobref = iobref_new (); + if (rsp_iobref == NULL) { + goto unwind; + } + + /* TODO: what is the size we should send ? */ + /* This iobuf will live for only receiving the response, + so not harmful */ + rsp_iobuf = iobuf_get (this->ctx->iobuf_pool); + if (rsp_iobuf == NULL) { + goto unwind; + } + + iobref_add (rsp_iobref, rsp_iobuf); + + rsphdr = &vector[0]; + rsphdr->iov_base = iobuf_ptr (rsp_iobuf); + rsphdr->iov_len = iobuf_pagesize (rsp_iobuf); + count = 1; + local->iobref = rsp_iobref; + iobuf_unref (rsp_iobuf); + rsp_iobuf = NULL; + rsp_iobref = NULL; + } + + ret = client_pre_readdir_v2 (this, &req, args->fd, args->size, + args->offset, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_READDIR, + client4_0_readdir_cbk, NULL, + rsphdr, count, + NULL, 0, rsp_iobref, + (xdrproc_t)xdr_gfx_readdir_req); + + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + if (rsp_iobref) + iobref_unref (rsp_iobref); + + CLIENT_STACK_UNWIND (readdir, frame, -1, op_errno, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_readdirp (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + gfx_readdirp_req req = {{0,},}; + gfx_readdirp_rsp rsp = {0,}; + clnt_conf_t *conf = NULL; + int op_errno = ESTALE; + int ret = 0; + int count = 0; + int readdirp_rsp_size = 0; + struct iobref *rsp_iobref = NULL; + struct iobuf *rsp_iobuf = NULL; + struct iovec *rsphdr = NULL; + struct iovec vector[MAX_IOVEC] = {{0}, }; + clnt_local_t *local = NULL; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + ret = client_pre_readdirp_v2 (this, &req, args->fd, args->size, + args->offset, args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + + readdirp_rsp_size = xdr_sizeof ((xdrproc_t) xdr_gfx_readdirp_rsp, &rsp) + + args->size; + + if ((readdirp_rsp_size + GLUSTERFS_RPC_REPLY_SIZE + + GLUSTERFS_RDMA_MAX_HEADER_SIZE) + > (GLUSTERFS_RDMA_INLINE_THRESHOLD)) { + rsp_iobref = iobref_new (); + if (rsp_iobref == NULL) { + goto unwind; + } + + /* TODO: what is the size we should send ? */ + /* This iobuf will live for only receiving the response, + so not harmful */ + rsp_iobuf = iobuf_get (this->ctx->iobuf_pool); + if (rsp_iobuf == NULL) { + goto unwind; + } + + iobref_add (rsp_iobref, rsp_iobuf); + iobuf_unref (rsp_iobuf); + + rsphdr = &vector[0]; + rsphdr->iov_base = iobuf_ptr (rsp_iobuf); + rsphdr->iov_len = iobuf_pagesize (rsp_iobuf); + count = 1; + local->iobref = rsp_iobref; + rsp_iobuf = NULL; + rsp_iobref = NULL; + } + + local->fd = fd_ref (args->fd); + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_READDIRP, + client4_0_readdirp_cbk, NULL, + rsphdr, count, NULL, + 0, rsp_iobref, + (xdrproc_t)xdr_gfx_readdirp_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + if (rsp_iobref) + iobref_unref (rsp_iobref); + + GF_FREE (req.xdata.pairs.pairs_val); + + CLIENT_STACK_UNWIND (readdirp, frame, -1, op_errno, NULL, NULL); + return 0; +} + + +int32_t +client4_0_setattr (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_setattr_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_setattr_v2 (this, &req, args->loc, args->valid, + args->stbuf, args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_SETATTR, + client4_0_setattr_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_setattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (setattr, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_fallocate(call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_fallocate_req req = {{0},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fallocate_v2 (this, &req, args->fd, args->flags, + args->offset, args->size, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FALLOCATE, + client4_0_fallocate_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_fallocate_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fallocate, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_discard(call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_discard_req req = {{0},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_discard_v2 (this, &req, args->fd, args->offset, + args->size, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + + ret = client_submit_request(this, &req, frame, conf->fops, + GFS3_OP_DISCARD, client4_0_discard_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t) xdr_gfx_discard_req); + if (ret) + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND(discard, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_zerofill(call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_zerofill_req req = {{0},}; + int op_errno = ESTALE; + int ret = 0; + + GF_ASSERT (frame); + + if (!this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_zerofill_v2 (this, &req, args->fd, args->offset, + args->size, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request(this, &req, frame, conf->fops, + GFS3_OP_ZEROFILL, client4_0_zerofill_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t) xdr_gfx_zerofill_req); + if (ret) + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND(zerofill, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_ipc (call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_ipc_req req = {0,}; + int op_errno = ESTALE; + int ret = 0; + + GF_ASSERT (frame); + + if (!this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_ipc_v2 (this, &req, args->cmd, args->xdata); + + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request(this, &req, frame, conf->fops, + GFS3_OP_IPC, client4_0_ipc_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t) xdr_gfx_ipc_req); + if (ret) + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND(ipc, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_seek (call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + struct gfx_seek_req req = {{0,},}; + int op_errno = ESTALE; + int ret = 0; + + GF_ASSERT (frame); + + if (!this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_seek_v2 (this, &req, args->fd, + args->offset, args->what, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + + ret = client_submit_request(this, &req, frame, conf->fops, + GFS3_OP_SEEK, client4_0_seek_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t) xdr_gfx_seek_req); + if (ret) + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND(ipc, frame, -1, op_errno, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + + +int32_t +client4_0_getactivelk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_getactivelk_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + if (!(args->loc && args->loc->inode)) + goto unwind; + + if (!gf_uuid_is_null (args->loc->inode->gfid)) + memcpy (req.gfid, args->loc->inode->gfid, 16); + else + memcpy (req.gfid, args->loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req.gfid)), + unwind, op_errno, EINVAL); + conf = this->private; + + dict_to_xdr (args->xdata, &req.xdata); + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_GETACTIVELK, + client4_0_getactivelk_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_getactivelk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (getactivelk, frame, -1, op_errno, NULL, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_setactivelk (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_setactivelk_req req = {{0,},}; + int ret = 0; + int op_errno = ESTALE; + + if (!frame || !this || !data) + goto unwind; + + args = data; + if (!(args->loc && args->loc->inode && args->locklist)) + goto unwind; + + if (!gf_uuid_is_null (args->loc->inode->gfid)) + memcpy (req.gfid, args->loc->inode->gfid, 16); + else + memcpy (req.gfid, args->loc->gfid, 16); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req.gfid)), + unwind, op_errno, EINVAL); + conf = this->private; + + dict_to_xdr (args->xdata, &req.xdata); + ret = serialize_req_locklist_v2 (args->locklist, &req); + + if (ret) + goto unwind; + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_SETACTIVELK, client4_0_setactivelk_cbk, NULL, + NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_setactivelk_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + + clnt_setactivelk_req_cleanup_v2 (&req); + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; + +unwind: + + CLIENT_STACK_UNWIND (setactivelk, frame, -1, op_errno, NULL); + + GF_FREE (req.xdata.pairs.pairs_val); + + clnt_setactivelk_req_cleanup_v2 (&req); + + return 0; +} + + +int +client4_rchecksum_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + call_frame_t *frame = NULL; + gfx_rchecksum_rsp rsp = {0,}; + int ret = 0; + xlator_t *this = NULL; + dict_t *xdata = NULL; + + this = THIS; + + frame = myframe; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_rchecksum_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + xdr_to_dict (&rsp.xdata, &xdata); +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + + CLIENT_STACK_UNWIND (rchecksum, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), + rsp.weak_checksum, + (uint8_t *)rsp.strong_checksum.strong_checksum_val, + xdata); + + if (rsp.strong_checksum.strong_checksum_val) { + /* This is allocated by the libc while decoding RPC msg */ + /* Hence no 'GF_FREE', but just 'free' */ + free (rsp.strong_checksum.strong_checksum_val); + } + + if (xdata) + dict_unref (xdata); + + return 0; +} + + +int32_t +client4_namelink_cbk (struct rpc_req *req, + struct iovec *iov, int count, void *myframe) +{ + int32_t ret = 0; + struct iatt prebuf = {0,}; + struct iatt postbuf = {0,}; + dict_t *xdata = NULL; + call_frame_t *frame = NULL; + gfx_common_2iatt_rsp rsp = {0,}; + + frame = myframe; + + if (req->rpc_status == -1) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_2iatt_rsp); + if (ret < 0) { + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (rsp.op_ret != -1) { + gfx_stat_to_iattx (&rsp.prestat, &prebuf); + gfx_stat_to_iattx (&rsp.poststat, &postbuf); + } + + xdr_to_dict (&rsp.xdata, &xdata); + out: + CLIENT_STACK_UNWIND (namelink, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), + &prebuf, &postbuf, xdata); + if (xdata) + dict_unref (xdata); + return 0; +} + +int32_t +client4_icreate_cbk (struct rpc_req *req, + struct iovec *iov, int count, void *myframe) +{ + int32_t ret = 0; + inode_t *inode = NULL; + clnt_local_t *local = NULL; + struct iatt stbuf = {0,}; + dict_t *xdata = NULL; + call_frame_t *frame = NULL; + gfx_common_iatt_rsp rsp = {0,}; + + frame = myframe; + local = frame->local; + + inode = local->loc.inode; + + if (req->rpc_status == -1) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_common_iatt_rsp); + if (ret < 0) { + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + if (rsp.op_ret != -1) + gfx_stat_to_iattx (&rsp.stat, &stbuf); + + xdr_to_dict (&rsp.xdata, &xdata); + out: + CLIENT_STACK_UNWIND (icreate, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), + inode, &stbuf, xdata); + if (xdata) + dict_unref (xdata); + return 0; +} +int32_t +client4_namelink (call_frame_t *frame, xlator_t *this, void *data) +{ + int32_t ret = 0; + int32_t op_errno = EINVAL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + gfx_namelink_req req = {{0,},}; + + GF_ASSERT (frame); + + args = data; + conf = this->private; + + if (!(args->loc && args->loc->parent)) + goto unwind; + + if (!gf_uuid_is_null (args->loc->parent->gfid)) + memcpy (req.pargfid, args->loc->parent->gfid, sizeof (uuid_t)); + else + memcpy (req.pargfid, args->loc->pargfid, sizeof (uuid_t)); + + GF_ASSERT_AND_GOTO_WITH_ERROR (this->name, + !gf_uuid_is_null (*((uuid_t *)req.pargfid)), + unwind, op_errno, EINVAL); + + req.bname = (char *)args->loc->name; + + dict_to_xdr (args->xdata, &req.xdata); + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_NAMELINK, client4_namelink_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t)xdr_gfx_namelink_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + return 0; + + unwind: + CLIENT_STACK_UNWIND (namelink, frame, -1, op_errno, NULL, NULL, NULL); + return 0; +} + +int32_t +client4_icreate (call_frame_t *frame, xlator_t *this, void *data) +{ + int32_t ret = 0; + int32_t op_errno = EINVAL; + clnt_conf_t *conf = NULL; + clnt_args_t *args = NULL; + clnt_local_t *local = NULL; + gfx_icreate_req req = {{0,},}; + + GF_ASSERT (frame); + + args = data; + conf = this->private; + + if (!(args->loc && args->loc->inode)) + goto unwind; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + loc_copy (&local->loc, args->loc); + + req.mode = args->mode; + memcpy (req.gfid, args->loc->gfid, sizeof (uuid_t)); + + op_errno = ESTALE; + dict_to_xdr (args->xdata, &req.xdata); + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_ICREATE, client4_icreate_cbk, + NULL, NULL, 0, NULL, 0, NULL, + (xdrproc_t) xdr_gfx_icreate_req); + if (ret) + goto free_reqdata; + GF_FREE (req.xdata.pairs.pairs_val); + return 0; + + free_reqdata: + GF_FREE (req.xdata.pairs.pairs_val); + unwind: + CLIENT_STACK_UNWIND (icreate, frame, + -1, op_errno, NULL, NULL, NULL); + return 0; +} + +int32_t +client4_0_fsetattr (call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_args_t *args = NULL; + clnt_conf_t *conf = NULL; + gfx_fsetattr_req req = {{0},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + ret = client_pre_fsetattr_v2 (this, &req, args->fd, args->valid, + args->stbuf, args->xdata); + if (ret) { + op_errno = -ret; + goto unwind; + } + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_FSETATTR, + client4_0_fsetattr_cbk, NULL, + NULL, 0, NULL, 0, + NULL, (xdrproc_t)xdr_gfx_fsetattr_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (fsetattr, frame, -1, op_errno, NULL, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int32_t +client4_0_rchecksum (call_frame_t *frame, xlator_t *this, + void *data) +{ + clnt_args_t *args = NULL; + int64_t remote_fd = -1; + clnt_conf_t *conf = NULL; + gfx_rchecksum_req req = {{0},}; + int op_errno = ESTALE; + int ret = 0; + + if (!frame || !this || !data) + goto unwind; + + args = data; + conf = this->private; + + CLIENT_GET_REMOTE_FD(this, args->fd, DEFAULT_REMOTE_FD, + remote_fd, op_errno, unwind); + + req.len = args->len; + req.offset = args->offset; + req.fd = remote_fd; + memcpy (req.gfid, args->fd->inode->gfid, 16); + + dict_to_xdr (args->xdata, &req.xdata); + + ret = client_submit_request (this, &req, frame, conf->fops, + GFS3_OP_RCHECKSUM, + client4_rchecksum_cbk, NULL, + NULL, 0, NULL, + 0, NULL, + (xdrproc_t)xdr_gfx_rchecksum_req); + if (ret) { + gf_msg (this->name, GF_LOG_WARNING, 0, PC_MSG_FOP_SEND_FAILED, + "failed to send the fop"); + } + + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +unwind: + CLIENT_STACK_UNWIND (rchecksum, frame, -1, op_errno, 0, NULL, NULL); + GF_FREE (req.xdata.pairs.pairs_val); + + return 0; +} + +int +client4_0_compound_cbk (struct rpc_req *req, struct iovec *iov, int count, + void *myframe) +{ + gfx_compound_rsp rsp = {0,}; + compound_args_cbk_t *args_cbk = NULL; + call_frame_t *frame = NULL; + xlator_t *this = NULL; + dict_t *xdata = NULL; + clnt_local_t *local = NULL; + int i = 0; + int length = 0; + int ret = -1; + + this = THIS; + + frame = myframe; + local = frame->local; + + if (-1 == req->rpc_status) { + rsp.op_ret = -1; + rsp.op_errno = ENOTCONN; + goto out; + } + + ret = xdr_to_generic (*iov, &rsp, (xdrproc_t)xdr_gfx_compound_rsp); + if (ret < 0) { + gf_msg (this->name, GF_LOG_ERROR, EINVAL, + PC_MSG_XDR_DECODING_FAILED, "XDR decoding failed"); + rsp.op_ret = -1; + rsp.op_errno = EINVAL; + goto out; + } + + length = local->length; + + xdr_to_dict (&rsp.xdata, &xdata); + + args_cbk = compound_args_cbk_alloc (length, xdata); + if (!args_cbk) { + rsp.op_ret = -1; + rsp.op_errno = ENOMEM; + goto out; + } + + /* TODO: see https://bugzilla.redhat.com/show_bug.cgi?id=1376328 */ + for (i = 0; i < args_cbk->fop_length; i++) { + ret = client_process_response_v2 (frame, this, req, &rsp, + args_cbk, i); + if (ret) { + rsp.op_ret = -1; + rsp.op_errno = -ret; + goto out; + } + + } + rsp.op_ret = 0; +out: + if (rsp.op_ret == -1) { + gf_msg (this->name, GF_LOG_WARNING, + gf_error_to_errno (rsp.op_errno), + PC_MSG_REMOTE_OP_FAILED, + "remote operation failed"); + } + CLIENT_STACK_UNWIND (compound, frame, rsp.op_ret, + gf_error_to_errno (rsp.op_errno), args_cbk, xdata); + + client_compound_rsp_cleanup_v2 (&rsp, length); + free (rsp.compound_rsp_array.compound_rsp_array_val); + + if (xdata) + dict_unref (xdata); + + compound_args_cbk_cleanup (args_cbk); + return 0; +} + + +/* Brief explanation of gfs3_compound_req structure : + * 1) It consists of version of compounding. + * 2) A compound-fop enum, new enum for compound fops + * 3) A 'compound_req_arrray' structure that has + * a) array len - based on the number of fops compounded + * b) compound_req_array_val - pointer to an array of compound_req's + * 4) compound_req - structure that contains: + * a) fop enum of type glusterfs_fop_t + * b) union of structures of xdr requests of all fops. + */ + +int32_t +client4_0_compound (call_frame_t *frame, xlator_t *this, void *data) +{ + clnt_conf_t *conf = NULL; + compound_args_t *c_args = data; + gfx_compound_req req = {0,}; + clnt_local_t *local = NULL; + int op_errno = ENOMEM; + int ret = 0; + int i = 0; + int rsp_count = 0; + struct iovec rsp_vector[MAX_IOVEC] = {{0}, }; + struct iovec req_vector[MAX_IOVEC] = {{0}, }; + struct iovec vector[MAX_IOVEC] = {{0}, }; + struct iovec *rsphdr = NULL; + struct iobref *req_iobref = NULL; + struct iobref *rsp_iobref = NULL; + struct iobref *rsphdr_iobref = NULL; + struct iobuf *rsphdr_iobuf = NULL; + int rsphdr_count = 0; + int req_count = 0; + dict_t *xdata = c_args->xdata; + + GF_ASSERT (frame); + + if (!this) + goto unwind; + + memset (req_vector, 0, sizeof (req_vector)); + memset (rsp_vector, 0, sizeof (rsp_vector)); + + conf = this->private; + + local = mem_get0 (this->local_pool); + if (!local) { + op_errno = ENOMEM; + goto unwind; + } + frame->local = local; + + local->length = c_args->fop_length; + local->compound_args = c_args; + + rsphdr_iobref = iobref_new (); + if (rsphdr_iobref == NULL) { + goto unwind; + } + + /* TODO: what is the size we should send ? */ + rsphdr_iobuf = iobuf_get (this->ctx->iobuf_pool); + if (rsphdr_iobuf == NULL) { + goto unwind; + } + + iobref_add (rsphdr_iobref, rsphdr_iobuf); + iobuf_unref (rsphdr_iobuf); + rsphdr = &vector[0]; + rsphdr->iov_base = iobuf_ptr (rsphdr_iobuf); + rsphdr->iov_len = iobuf_pagesize (rsphdr_iobuf); + rsphdr_count = 1; + rsphdr_iobuf = NULL; + + req.compound_fop_enum = c_args->fop_enum; + req.compound_req_array.compound_req_array_len = c_args->fop_length; + req.compound_version = 0; + dict_to_xdr (xdata, &req.xdata); + + req.compound_req_array.compound_req_array_val = GF_CALLOC (local->length, + sizeof (compound_req_v2), + gf_client_mt_compound_req_t); + + if (!req.compound_req_array.compound_req_array_val) { + op_errno = ENOMEM; + goto unwind; + } + + for (i = 0; i < local->length; i++) { + ret = client_handle_fop_requirements_v2 (this, frame, + &req, local, + &req_iobref, &rsp_iobref, + req_vector, + rsp_vector, &req_count, + &rsp_count, + &c_args->req_list[i], + c_args->enum_list[i], + i); + if (ret) { + op_errno = ret; + goto unwind; + } + } + + local->iobref = rsp_iobref; + rsp_iobref = NULL; + + ret = client_submit_compound_request (this, &req, frame, conf->fops, + GFS3_OP_COMPOUND, client4_0_compound_cbk, + req_vector, req_count, req_iobref, + rsphdr, rsphdr_count, + rsp_vector, rsp_count, + local->iobref, + (xdrproc_t) xdr_gfx_compound_req); + + GF_FREE (req.xdata.pairs.pairs_val); + + iobref_unref (rsphdr_iobref); + + compound_request_cleanup_v2 (&req); + return 0; +unwind: + CLIENT_STACK_UNWIND (compound, frame, -1, op_errno, NULL, NULL); + + if (rsp_iobref) + iobref_unref (rsp_iobref); + + if (rsphdr_iobref) + iobref_unref (rsphdr_iobref); + + GF_FREE (req.xdata.pairs.pairs_val); + + compound_request_cleanup_v2 (&req); + return 0; +} + +/* Used From RPC-CLNT library to log proper name of procedure based on number */ +char *clnt4_0_fop_names[GFS3_OP_MAXVALUE] = { + [GFS3_OP_NULL] = "NULL", + [GFS3_OP_STAT] = "STAT", + [GFS3_OP_READLINK] = "READLINK", + [GFS3_OP_MKNOD] = "MKNOD", + [GFS3_OP_MKDIR] = "MKDIR", + [GFS3_OP_UNLINK] = "UNLINK", + [GFS3_OP_RMDIR] = "RMDIR", + [GFS3_OP_SYMLINK] = "SYMLINK", + [GFS3_OP_RENAME] = "RENAME", + [GFS3_OP_LINK] = "LINK", + [GFS3_OP_TRUNCATE] = "TRUNCATE", + [GFS3_OP_OPEN] = "OPEN", + [GFS3_OP_READ] = "READ", + [GFS3_OP_WRITE] = "WRITE", + [GFS3_OP_STATFS] = "STATFS", + [GFS3_OP_FLUSH] = "FLUSH", + [GFS3_OP_FSYNC] = "FSYNC", + [GFS3_OP_SETXATTR] = "SETXATTR", + [GFS3_OP_GETXATTR] = "GETXATTR", + [GFS3_OP_REMOVEXATTR] = "REMOVEXATTR", + [GFS3_OP_OPENDIR] = "OPENDIR", + [GFS3_OP_FSYNCDIR] = "FSYNCDIR", + [GFS3_OP_ACCESS] = "ACCESS", + [GFS3_OP_CREATE] = "CREATE", + [GFS3_OP_FTRUNCATE] = "FTRUNCATE", + [GFS3_OP_FSTAT] = "FSTAT", + [GFS3_OP_LK] = "LK", + [GFS3_OP_LOOKUP] = "LOOKUP", + [GFS3_OP_READDIR] = "READDIR", + [GFS3_OP_INODELK] = "INODELK", + [GFS3_OP_FINODELK] = "FINODELK", + [GFS3_OP_ENTRYLK] = "ENTRYLK", + [GFS3_OP_FENTRYLK] = "FENTRYLK", + [GFS3_OP_XATTROP] = "XATTROP", + [GFS3_OP_FXATTROP] = "FXATTROP", + [GFS3_OP_FGETXATTR] = "FGETXATTR", + [GFS3_OP_FSETXATTR] = "FSETXATTR", + [GFS3_OP_RCHECKSUM] = "RCHECKSUM", + [GFS3_OP_SETATTR] = "SETATTR", + [GFS3_OP_FSETATTR] = "FSETATTR", + [GFS3_OP_READDIRP] = "READDIRP", + [GFS3_OP_RELEASE] = "RELEASE", + [GFS3_OP_RELEASEDIR] = "RELEASEDIR", + [GFS3_OP_FREMOVEXATTR] = "FREMOVEXATTR", + [GFS3_OP_FALLOCATE] = "FALLOCATE", + [GFS3_OP_DISCARD] = "DISCARD", + [GFS3_OP_ZEROFILL] = "ZEROFILL", + [GFS3_OP_IPC] = "IPC", + [GFS3_OP_SEEK] = "SEEK", + [GFS3_OP_LEASE] = "LEASE", + [GFS3_OP_GETACTIVELK] = "GETACTIVELK", + [GFS3_OP_SETACTIVELK] = "SETACTIVELK", + [GFS3_OP_COMPOUND] = "COMPOUND", + [GFS3_OP_ICREATE] = "ICREATE", + [GFS3_OP_NAMELINK] = "NAMELINK", +}; diff --git a/xlators/protocol/client/src/client.h b/xlators/protocol/client/src/client.h index dd3ee4dd4f0..003a2bef397 100644 --- a/xlators/protocol/client/src/client.h +++ b/xlators/protocol/client/src/client.h @@ -134,6 +134,54 @@ typedef enum { client_local_wipe (__local); \ } while (0) +/* compound v2 */ +#define CPD4_REQ_FIELD(v, f) ((v)->compound_req_v2_u.compound_##f##_req) +#define CPD4_RSP_FIELD(v, f) ((v)->compound_rsp_v2_u.compound_##f##_rsp) + +#define CLIENT4_POST_FOP(fop, this_rsp_u, this_args_cbk, params ...) \ + do { \ + gfx_common_rsp *_this_rsp = &CPD4_RSP_FIELD(this_rsp_u, fop); \ + int _op_ret = 0; \ + int _op_errno = 0; \ + \ + _op_ret = _this_rsp->op_ret; \ + _op_errno = gf_error_to_errno (_this_rsp->op_errno); \ + args_##fop##_cbk_store (this_args_cbk, _op_ret, _op_errno, \ + params); \ + } while (0) + +#define CLIENT4_POST_FOP_TYPE(fop, rsp_type, this_rsp_u, this_args_cbk, params ...) \ + do { \ + gfx_##rsp_type##_rsp *_this_rsp = &CPD4_RSP_FIELD(this_rsp_u, fop); \ + int _op_ret = 0; \ + int _op_errno = 0; \ + \ + _op_ret = _this_rsp->op_ret; \ + _op_errno = gf_error_to_errno (_this_rsp->op_errno); \ + args_##fop##_cbk_store (this_args_cbk, _op_ret, _op_errno, \ + params); \ + } while (0) + +#define CLIENT4_PRE_FOP(fop, xl, compound_req, op_errno, label, params ...) \ + do { \ + gfx_##fop##_req *_req = (gfx_##fop##_req *)compound_req; \ + int _ret = 0; \ + \ + _ret = client_pre_##fop##_v2 (xl, _req, params); \ + if (_ret < 0) { \ + op_errno = -ret; \ + goto label; \ + } \ + } while (0) + +#define CLIENT4_COMPOUND_FOP_CLEANUP(curr_req, fop) \ + do { \ + gfx_##fop##_req *_req = &CPD4_REQ_FIELD(curr_req, fop); \ + \ + GF_FREE (_req->xdata.pairs.pairs_val); \ + } while (0) + + struct clnt_options { char *remote_subvolume; @@ -402,4 +450,47 @@ serialize_req_locklist (lock_migration_info_t *locklist, void client_compound_rsp_cleanup (gfs3_compound_rsp *rsp, int len); + +void +clnt_getactivelk_rsp_cleanup_v2 (gfx_getactivelk_rsp *rsp); + +void +clnt_setactivelk_req_cleanup_v2 (gfx_setactivelk_req *req); + +int +serialize_req_locklist_v2 (lock_migration_info_t *locklist, + gfx_setactivelk_req *req); + +int +clnt_unserialize_rsp_locklist_v2 (xlator_t *this, struct gfx_getactivelk_rsp *rsp, + lock_migration_info_t *lmi); + +int unserialize_rsp_dirent_v2 (xlator_t *this, struct gfx_readdir_rsp *rsp, + gf_dirent_t *entries); +int unserialize_rsp_direntp_v2 (xlator_t *this, fd_t *fd, + struct gfx_readdirp_rsp *rsp, gf_dirent_t *entries); + +int clnt_readdir_rsp_cleanup_v2 (gfx_readdir_rsp *rsp); +int clnt_readdirp_rsp_cleanup_v2 (gfx_readdirp_rsp *rsp); + +int +client_handle_fop_requirements_v2 (xlator_t *this, call_frame_t *frame, + gfx_compound_req *req, + clnt_local_t *local, + struct iobref **req_iobref, + struct iobref **rsp_iobref, + struct iovec *req_vector, + struct iovec *rsp_vector, int *req_count, + int *rsp_count, default_args_t *args, + int fop_enum, int index); +int +client_process_response_v2 (call_frame_t *frame, xlator_t *this, + struct rpc_req *req, + gfx_compound_rsp *rsp, compound_args_cbk_t *args_cbk, + int index); +void +compound_request_cleanup_v2 (gfx_compound_req *req); +void +client_compound_rsp_cleanup_v2 (gfx_compound_rsp *rsp, int len); + #endif /* !_CLIENT_H */ |