summaryrefslogtreecommitdiffstats
path: root/xlators/protocol
diff options
context:
space:
mode:
authorAnuradha Talur <atalur@redhat.com>2016-08-29 16:41:09 +0530
committerRaghavendra G <rgowdapp@redhat.com>2016-08-30 23:50:40 -0700
commit7cbc10037ecc873d60c3a970d00faf2819019525 (patch)
tree35026d258fa4bb9aad89f7a504954bb566ffa4fc /xlators/protocol
parentfe929224c47d5c82da5650e9e1041645a8d7f244 (diff)
compound fops: Some fixes to compound fops framework
Change-Id: I808fd5f9f002a35bff94d310c5d61a781e49570b BUG: 1360169 Signed-off-by: Anuradha Talur <atalur@redhat.com> Reviewed-on: http://review.gluster.org/15010 Smoke: Gluster Build System <jenkins@build.gluster.org> NetBSD-regression: NetBSD Build System <jenkins@build.gluster.org> CentOS-regression: Gluster Build System <jenkins@build.gluster.org> Reviewed-by: Raghavendra G <rgowdapp@redhat.com>
Diffstat (limited to 'xlators/protocol')
-rw-r--r--xlators/protocol/client/src/client-common.c1
-rw-r--r--xlators/protocol/client/src/client-helpers.c298
-rw-r--r--xlators/protocol/client/src/client-rpc-fops.c56
-rw-r--r--xlators/protocol/client/src/client.h25
-rw-r--r--xlators/protocol/server/src/server-helpers.c528
-rw-r--r--xlators/protocol/server/src/server-helpers.h5
-rw-r--r--xlators/protocol/server/src/server-rpc-fops.c64
-rw-r--r--xlators/protocol/server/src/server.h28
8 files changed, 873 insertions, 132 deletions
diff --git a/xlators/protocol/client/src/client-common.c b/xlators/protocol/client/src/client-common.c
index 05939b8aa0b..4fff7e6e64f 100644
--- a/xlators/protocol/client/src/client-common.c
+++ b/xlators/protocol/client/src/client-common.c
@@ -1402,6 +1402,7 @@ client_post_readlink (xlator_t *this, gfs3_readlink_rsp *rsp,
rsp->op_errno, out);
out:
+
return ret;
}
diff --git a/xlators/protocol/client/src/client-helpers.c b/xlators/protocol/client/src/client-helpers.c
index 4bdb364a9a3..a7e46b55546 100644
--- a/xlators/protocol/client/src/client-helpers.c
+++ b/xlators/protocol/client/src/client-helpers.c
@@ -135,10 +135,6 @@ client_local_wipe (clnt_local_t *local)
iobref_unref (local->iobref);
}
- if (local->iobref2) {
- iobref_unref (local->iobref2);
- }
-
GF_FREE (local->name);
local->compound_args = NULL;
@@ -1126,8 +1122,8 @@ int
client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
gfs3_compound_req *req,
clnt_local_t *local,
- struct iobref *req_iobref,
- struct iobref *rsp_iobref,
+ 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,
@@ -1160,10 +1156,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
op_errno, out,
&args->loc, args->mode, args->rdev,
args->umask, args->xdata);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_MKDIR:
CLIENT_PRE_FOP (mkdir, this,
@@ -1171,10 +1165,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
op_errno, out,
&args->loc, args->mode,
args->umask, args->xdata);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_UNLINK:
CLIENT_PRE_FOP (unlink, this,
@@ -1194,10 +1186,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
op_errno, out,
&args->loc, args->linkname, args->umask,
args->xdata);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_RENAME:
CLIENT_PRE_FOP (rename, this,
@@ -1246,15 +1236,15 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
goto out;
}
- if (!rsp_iobref) {
- rsp_iobref = iobref_new ();
- if (rsp_iobref == NULL) {
+ if (!*rsp_iobref) {
+ *rsp_iobref = iobref_new ();
+ if (*rsp_iobref == NULL) {
op_errno = ENOMEM;
goto out;
}
}
- iobref_add (rsp_iobref, rsp_iobuf);
+ iobref_add (*rsp_iobref, rsp_iobuf);
iobuf_unref (rsp_iobuf);
if (*rsp_count + 1 >= MAX_IOVEC) {
@@ -1280,7 +1270,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
case GF_FOP_WRITE:
op_errno = client_pre_writev (this,
&this_req->compound_req_u.compound_write_req,
- args->fd, args->count, args->offset,
+ args->fd, iov_length (args->vector, args->count),
+ args->offset,
args->flags, args->xdata);
if (op_errno) {
@@ -1292,7 +1283,7 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
local->attempt_reopen = client_is_reopen_needed
(args->fd, this, remote_fd);
- if (*req_count + 1 >= MAX_IOVEC) {
+ if (*req_count + args->count >= MAX_IOVEC) {
op_errno = ENOMEM;
goto out;
}
@@ -1300,10 +1291,10 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
(args->count * sizeof(req_vector[0])));
*req_count += args->count;
- if (!req_iobref)
- req_iobref = args->iobref;
+ if (!*req_iobref)
+ *req_iobref = args->iobref;
else
- if (iobref_merge (req_iobref, args->iobref))
+ if (iobref_merge (*req_iobref, args->iobref))
goto out;
break;
case GF_FOP_STATFS:
@@ -1339,10 +1330,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
&this_req->compound_req_u.compound_getxattr_req,
op_errno, out,
&args->loc, args->name, args->xdata);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_REMOVEXATTR:
CLIENT_PRE_FOP (removexattr, this,
@@ -1357,10 +1346,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
&args->loc, args->fd, args->xdata);
if (!local->fd)
local->fd = fd_ref (args->fd);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_FSYNCDIR:
CLIENT_PRE_FOP (fsyncdir, this,
@@ -1383,10 +1370,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
if (!local->fd)
local->fd = fd_ref (args->fd);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_FTRUNCATE:
CLIENT_PRE_FOP (ftruncate, this,
@@ -1414,10 +1399,8 @@ client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
&this_req->compound_req_u.compound_lookup_req,
op_errno, out,
&args->loc, args->xdata);
- if (!&local->loc) {
- loc_copy (&local->loc, &args->loc);
- loc_path (&local->loc, NULL);
- }
+ loc_copy (&local->loc, &args->loc);
+ loc_path (&local->loc, NULL);
break;
case GF_FOP_READDIR:
CLIENT_PRE_FOP (readdir, this,
@@ -1582,6 +1565,9 @@ compound_request_cleanup (gfs3_compound_req *req)
compound_req *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];
@@ -1636,8 +1622,9 @@ compound_request_cleanup (gfs3_compound_req *req)
break;
case GF_FOP_SETXATTR:
{
- gfs3_setxattr_req args = curr_req->compound_req_u.compound_setxattr_req;
- GF_FREE (args.dict.dict_val);
+ gfs3_setxattr_req *args = &CPD_REQ_FIELD (curr_req,
+ setxattr);
+ GF_FREE (args->dict.dict_val);
CLIENT_COMPOUND_FOP_CLEANUP (curr_req, setxattr);
break;
}
@@ -1688,15 +1675,17 @@ compound_request_cleanup (gfs3_compound_req *req)
break;
case GF_FOP_XATTROP:
{
- gfs3_xattrop_req args = curr_req->compound_req_u.compound_xattrop_req;
- GF_FREE (args.dict.dict_val);
+ gfs3_xattrop_req *args = &CPD_REQ_FIELD (curr_req,
+ xattrop);
+ GF_FREE (args->dict.dict_val);
CLIENT_COMPOUND_FOP_CLEANUP (curr_req, xattrop);
break;
}
case GF_FOP_FXATTROP:
{
- gfs3_fxattrop_req args = curr_req->compound_req_u.compound_fxattrop_req;
- GF_FREE (args.dict.dict_val);
+ gfs3_fxattrop_req *args = &CPD_REQ_FIELD (curr_req,
+ fxattrop);
+ GF_FREE (args->dict.dict_val);
CLIENT_COMPOUND_FOP_CLEANUP (curr_req, fxattrop);
break;
}
@@ -1705,8 +1694,9 @@ compound_request_cleanup (gfs3_compound_req *req)
break;
case GF_FOP_FSETXATTR:
{
- gfs3_fsetxattr_req args = curr_req->compound_req_u.compound_fsetxattr_req;
- GF_FREE (args.dict.dict_val);
+ gfs3_fsetxattr_req *args = &CPD_REQ_FIELD(curr_req,
+ fsetxattr);
+ GF_FREE (args->dict.dict_val);
CLIENT_COMPOUND_FOP_CLEANUP (curr_req, fsetxattr);
break;
}
@@ -1721,8 +1711,9 @@ compound_request_cleanup (gfs3_compound_req *req)
break;
case GF_FOP_READDIRP:
{
- gfs3_readdirp_req args = curr_req->compound_req_u.compound_readdirp_req;
- GF_FREE (args.dict.dict_val);
+ gfs3_readdirp_req *args = &CPD_REQ_FIELD(curr_req,
+ readdirp);
+ GF_FREE (args->dict.dict_val);
break;
}
case GF_FOP_FREMOVEXATTR:
@@ -1888,3 +1879,204 @@ out:
return ret;
}
+
+void
+client_compound_rsp_cleanup (gfs3_compound_rsp *rsp, int len)
+{
+ int i = 0;
+ compound_rsp *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) {
+ case GF_FOP_STAT:
+ CLIENT_FOP_RSP_CLEANUP (rsp, stat, i);
+ break;
+ case GF_FOP_MKNOD:
+ CLIENT_FOP_RSP_CLEANUP (rsp, mknod, i);
+ break;
+ case GF_FOP_MKDIR:
+ CLIENT_FOP_RSP_CLEANUP (rsp, mkdir, i);
+ break;
+ case GF_FOP_UNLINK:
+ CLIENT_FOP_RSP_CLEANUP (rsp, unlink, i);
+ break;
+ case GF_FOP_RMDIR:
+ CLIENT_FOP_RSP_CLEANUP (rsp, rmdir, i);
+ break;
+ case GF_FOP_SYMLINK:
+ CLIENT_FOP_RSP_CLEANUP (rsp, symlink, i);
+ break;
+ case GF_FOP_RENAME:
+ CLIENT_FOP_RSP_CLEANUP (rsp, rename, i);
+ break;
+ case GF_FOP_LINK:
+ CLIENT_FOP_RSP_CLEANUP (rsp, link, i);
+ break;
+ case GF_FOP_TRUNCATE:
+ CLIENT_FOP_RSP_CLEANUP (rsp, truncate, i);
+ break;
+ case GF_FOP_OPEN:
+ CLIENT_FOP_RSP_CLEANUP (rsp, open, i);
+ break;
+ case GF_FOP_READ:
+ CLIENT_FOP_RSP_CLEANUP (rsp, read, i);
+ break;
+ case GF_FOP_WRITE:
+ CLIENT_FOP_RSP_CLEANUP (rsp, write, i);
+ break;
+ case GF_FOP_STATFS:
+ CLIENT_FOP_RSP_CLEANUP (rsp, statfs, i);
+ break;
+ case GF_FOP_FSYNC:
+ CLIENT_FOP_RSP_CLEANUP (rsp, fsync, i);
+ break;
+ case GF_FOP_OPENDIR:
+ CLIENT_FOP_RSP_CLEANUP (rsp, opendir, i);
+ break;
+ case GF_FOP_CREATE:
+ CLIENT_FOP_RSP_CLEANUP (rsp, create, i);
+ break;
+ case GF_FOP_FTRUNCATE:
+ CLIENT_FOP_RSP_CLEANUP (rsp, ftruncate, i);
+ break;
+ case GF_FOP_FSTAT:
+ CLIENT_FOP_RSP_CLEANUP (rsp, fstat, i);
+ break;
+ case GF_FOP_LK:
+ CLIENT_FOP_RSP_CLEANUP (rsp, lk, i);
+ break;
+ case GF_FOP_LOOKUP:
+ CLIENT_FOP_RSP_CLEANUP (rsp, lookup, i);
+ break;
+ case GF_FOP_SETATTR:
+ CLIENT_FOP_RSP_CLEANUP (rsp, setattr, i);
+ break;
+ case GF_FOP_FSETATTR:
+ CLIENT_FOP_RSP_CLEANUP (rsp, fsetattr, i);
+ break;
+ case GF_FOP_FALLOCATE:
+ CLIENT_FOP_RSP_CLEANUP (rsp, fallocate, i);
+ break;
+ case GF_FOP_DISCARD:
+ CLIENT_FOP_RSP_CLEANUP (rsp, discard, i);
+ break;
+ case GF_FOP_ZEROFILL:
+ CLIENT_FOP_RSP_CLEANUP (rsp, zerofill, i);
+ break;
+ case GF_FOP_IPC:
+ CLIENT_FOP_RSP_CLEANUP (rsp, ipc, i);
+ break;
+ case GF_FOP_SEEK:
+ CLIENT_FOP_RSP_CLEANUP (rsp, seek, i);
+ break;
+ case GF_FOP_LEASE:
+ CLIENT_FOP_RSP_CLEANUP (rsp, lease, i);
+ break;
+ /* fops that use gf_common_rsp */
+ case GF_FOP_FLUSH:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, flush, i);
+ break;
+ case GF_FOP_SETXATTR:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, setxattr, i);
+ break;
+ case GF_FOP_REMOVEXATTR:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, removexattr, i);
+ break;
+ case GF_FOP_FSETXATTR:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, fsetxattr, i);
+ break;
+ case GF_FOP_FREMOVEXATTR:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, fremovexattr, i);
+ break;
+ case GF_FOP_FSYNCDIR:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, fsyncdir, i);
+ break;
+ case GF_FOP_ACCESS:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, access, i);
+ break;
+ case GF_FOP_INODELK:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, inodelk, i);
+ break;
+ case GF_FOP_FINODELK:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, finodelk, i);
+ break;
+ case GF_FOP_ENTRYLK:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, entrylk, i);
+ break;
+ case GF_FOP_FENTRYLK:
+ CLIENT_COMMON_RSP_CLEANUP (rsp, fentrylk, i);
+ break;
+ /* fops that need extra cleanup */
+ case GF_FOP_READLINK:
+ {
+ CLIENT_FOP_RSP_CLEANUP (rsp, readlink, i);
+ gfs3_readlink_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ readlink);
+ free (tmp_rsp->path);
+ break;
+ }
+ case GF_FOP_XATTROP:
+ {
+ gfs3_xattrop_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ xattrop);
+ CLIENT_FOP_RSP_CLEANUP (rsp, xattrop, i);
+ free (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_FXATTROP:
+ {
+ gfs3_fxattrop_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ fxattrop);
+ CLIENT_FOP_RSP_CLEANUP (rsp, fxattrop, i);
+ free (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_READDIR:
+ {
+ CLIENT_FOP_RSP_CLEANUP (rsp, readdir, i);
+ gfs3_readdir_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ readdir);
+ clnt_readdir_rsp_cleanup (tmp_rsp);
+ break;
+ }
+ case GF_FOP_READDIRP:
+ {
+ CLIENT_FOP_RSP_CLEANUP (rsp, readdirp, i);
+ gfs3_readdirp_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ readdirp);
+ clnt_readdirp_rsp_cleanup (tmp_rsp);
+ break;
+ }
+ case GF_FOP_GETXATTR:
+ {
+ gfs3_getxattr_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ getxattr);
+ CLIENT_FOP_RSP_CLEANUP (rsp, getxattr, i);
+ free (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_FGETXATTR:
+ {
+ gfs3_fgetxattr_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ fgetxattr);
+ CLIENT_FOP_RSP_CLEANUP (rsp, fgetxattr, i);
+ free (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_RCHECKSUM:
+ {
+ gfs3_rchecksum_rsp *rck = &CPD_RSP_FIELD(this_rsp,
+ rchecksum);
+ CLIENT_FOP_RSP_CLEANUP (rsp, rchecksum, i);
+ if (rck->strong_checksum.strong_checksum_val) {
+ free (rck->strong_checksum.strong_checksum_val);
+ }
+ break;
+ }
+ default:
+ break;
+ }
+ }
+ return;
+}
diff --git a/xlators/protocol/client/src/client-rpc-fops.c b/xlators/protocol/client/src/client-rpc-fops.c
index b26c4946d7f..c122941cf4e 100644
--- a/xlators/protocol/client/src/client-rpc-fops.c
+++ b/xlators/protocol/client/src/client-rpc-fops.c
@@ -16,6 +16,7 @@
#include "client-messages.h"
#include "defaults.h"
#include "client-common.h"
+#include "compound-fop-utils.h"
int32_t client3_getspec (call_frame_t *frame, xlator_t *this, void *data);
rpc_clnt_prog_t clnt3_3_fop_prog;
@@ -3161,12 +3162,12 @@ client3_3_compound_cbk (struct rpc_req *req, struct iovec *iov, int count,
gfs3_compound_rsp rsp = {0,};
compound_args_cbk_t *args_cbk = NULL;
call_frame_t *frame = NULL;
- int ret = -1;
xlator_t *this = NULL;
dict_t *xdata = NULL;
clnt_local_t *local = NULL;
int op_errno = 0;
int i,length = 0;
+ int ret = -1;
this = THIS;
@@ -3186,55 +3187,40 @@ client3_3_compound_cbk (struct rpc_req *req, struct iovec *iov, int count,
goto out;
}
- args_cbk = GF_CALLOC (1, sizeof (compound_args_cbk_t), gf_mt_compound_rsp_t);
- if (!args_cbk) {
- op_errno = ENOMEM;
- goto out;
- }
+ GF_PROTOCOL_DICT_UNSERIALIZE (this, xdata, (rsp.xdata.xdata_val),
+ (rsp.xdata.xdata_len), rsp.op_ret,
+ rsp.op_errno, out);
- length = args_cbk->fop_length = local->length;
+ length = local->length;
- args_cbk->rsp_list = GF_CALLOC (length, sizeof (default_args_cbk_t),
- gf_mt_default_args_cbk_t);
- if (!args_cbk->rsp_list) {
+ args_cbk = compound_args_cbk_alloc (length, xdata);
+ if (!args_cbk) {
op_errno = ENOMEM;
goto out;
}
- op_errno = rsp.op_errno;
-
for (i = 0; i < args_cbk->fop_length; i++) {
ret = client_process_response (frame, this, req, &rsp,
args_cbk, i);
if (ret) {
op_errno = -ret;
- ret = -1;
goto out;
}
}
-
- GF_PROTOCOL_DICT_UNSERIALIZE (this, xdata, (rsp.xdata.xdata_val),
- (rsp.xdata.xdata_len), ret,
- rsp.op_errno, out);
-
- ret = 0;
+ rsp.op_ret = 0;
out:
- CLIENT_STACK_UNWIND (compound, frame, ret,
- gf_error_to_errno (op_errno), args_cbk, xdata);
+ CLIENT_STACK_UNWIND (compound, frame, rsp.op_ret,
+ gf_error_to_errno (rsp.op_errno), args_cbk, xdata);
free (rsp.xdata.xdata_val);
+ client_compound_rsp_cleanup (&rsp, local->length);
+
if (xdata)
dict_unref (xdata);
- if (args_cbk->rsp_list) {
- for (i = 0; i < length; i++) {
- args_cbk_wipe (&args_cbk->rsp_list[i]);
- }
- }
- GF_FREE (args_cbk->rsp_list);
- GF_FREE (args_cbk);
+ compound_args_cbk_cleanup (args_cbk);
return 0;
}
@@ -6131,7 +6117,6 @@ client3_3_compound (call_frame_t *frame, xlator_t *this, void *data)
struct iobuf *rsphdr_iobuf = NULL;
int rsphdr_count = 0;
int req_count = 0;
- int index = 0;
dict_t *xdata = c_args->xdata;
GF_ASSERT (frame);
@@ -6171,13 +6156,11 @@ client3_3_compound (call_frame_t *frame, xlator_t *this, void *data)
rsphdr->iov_base = iobuf_ptr (rsphdr_iobuf);
rsphdr->iov_len = iobuf_pagesize (rsphdr_iobuf);
rsphdr_count = 1;
- local->iobref = rsp_iobref;
rsphdr_iobuf = NULL;
rsphdr_iobref = NULL;
req.compound_fop_enum = c_args->fop_enum;
req.compound_req_array.compound_req_array_len = c_args->fop_length;
- /*TODO : Talk to Sowmya about this */
req.compound_version = 0;
if (xdata) {
GF_PROTOCOL_DICT_SERIALIZE (this, xdata,
@@ -6198,29 +6181,28 @@ client3_3_compound (call_frame_t *frame, xlator_t *this, void *data)
for (i = 0; i < local->length; i++) {
ret = client_handle_fop_requirements (this, frame,
&req, local,
- req_iobref, rsp_iobref,
+ &req_iobref, &rsp_iobref,
req_vector,
rsp_vector, &req_count,
&rsp_count,
&c_args->req_list[i],
c_args->enum_list[i],
- index);
+ i);
if (ret) {
op_errno = ret;
goto unwind;
}
- index++;
}
- local->iobref2 = rsp_iobref;
+ local->iobref = rsp_iobref;
rsp_iobref = NULL;
ret = client_submit_compound_request (this, &req, frame, conf->fops,
GFS3_OP_COMPOUND, client3_3_compound_cbk,
- req_vector, req_count, local->iobref,
+ req_vector, req_count, req_iobref,
rsphdr, rsphdr_count,
rsp_vector, rsp_count,
- local->iobref2,
+ local->iobref,
(xdrproc_t) xdr_gfs3_compound_req);
GF_FREE (req.xdata.xdata_val);
diff --git a/xlators/protocol/client/src/client.h b/xlators/protocol/client/src/client.h
index 61409d1fc79..f7453bedc47 100644
--- a/xlators/protocol/client/src/client.h
+++ b/xlators/protocol/client/src/client.h
@@ -89,6 +89,24 @@ typedef enum {
GF_FREE (_req->xdata.xdata_val); \
} while (0)
+#define CLIENT_COMMON_RSP_CLEANUP(rsp, fop, i) \
+ do { \
+ compound_rsp *this_rsp = NULL; \
+ this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[i];\
+ gf_common_rsp *_this_rsp = &CPD_RSP_FIELD (this_rsp, fop); \
+ \
+ free (_this_rsp->xdata.xdata_val); \
+ } while (0)
+
+#define CLIENT_FOP_RSP_CLEANUP(rsp, fop, i) \
+ do { \
+ compound_rsp *this_rsp = NULL; \
+ this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[i];\
+ gfs3_##fop##_rsp *_this_rsp = &CPD_RSP_FIELD (this_rsp, fop); \
+ \
+ free (_this_rsp->xdata.xdata_val); \
+ } while (0)
+
#define CLIENT_GET_REMOTE_FD(xl, fd, flags, remote_fd, op_errno, label) \
do { \
int _ret = 0; \
@@ -233,7 +251,6 @@ typedef struct client_local {
char *name;
gf_boolean_t attempt_reopen;
/* required for compound fops */
- struct iobref *iobref2;
compound_args_t *compound_args;
unsigned int length; /* length of a compound fop */
unsigned int read_length; /* defines the last processed length for a compound read */
@@ -353,8 +370,8 @@ int
client_handle_fop_requirements (xlator_t *this, call_frame_t *frame,
gfs3_compound_req *req,
clnt_local_t *local,
- struct iobref *req_iobref,
- struct iobref *rsp_iobref,
+ 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,
@@ -380,4 +397,6 @@ int
serialize_req_locklist (lock_migration_info_t *locklist,
gfs3_setactivelk_req *req);
+void
+client_compound_rsp_cleanup (gfs3_compound_rsp *rsp, int len);
#endif /* !_CLIENT_H */
diff --git a/xlators/protocol/server/src/server-helpers.c b/xlators/protocol/server/src/server-helpers.c
index 1ec6024269c..06fc3ce6c97 100644
--- a/xlators/protocol/server/src/server-helpers.c
+++ b/xlators/protocol/server/src/server-helpers.c
@@ -20,6 +20,7 @@
#include <fnmatch.h>
#include <pwd.h>
#include <grp.h>
+#include "compound-fop-utils.h"
/* based on nfs_fix_aux_groups() */
int
@@ -230,6 +231,8 @@ free_state (server_state_t *state)
server_resolve_wipe (&state->resolve);
server_resolve_wipe (&state->resolve2);
+ compound_args_cleanup (state->args);
+
GF_FREE (state);
}
@@ -1575,12 +1578,23 @@ server_populate_compound_request (gfs3_compound_req *req, call_frame_t *frame,
args->xdata.xdata_val,
args->xdata.xdata_len, ret,
op_errno, out);
+ /* The way writev fop works :
+ * xdr args of write along with other args contains
+ * write length not count. But when the call is wound to posix,
+ * this length is not used. It is taken from the request
+ * write vector that is passed down. Posix needs the vector
+ * count to determine the amount of write to be done.
+ * This count for writes that come as part of compound fops
+ * will be 1. The vectors are merged into one under
+ * GF_FOP_WRITE section of client_handle_fop_requirements()
+ * in protocol client.
+ */
args_writev_store (this_args, state->fd,
req_iovec,
- args->size, args->offset,
+ 1, args->offset,
args->flag,
- this_args->iobref, this_args->xdata);
- state->write_length += args->size;
+ state->iobref, this_args->xdata);
+ state->write_length += req_iovec[0].iov_len;
break;
}
case GF_FOP_STATFS:
@@ -2264,23 +2278,19 @@ server_populate_compound_response (xlator_t *this, gfs3_compound_rsp *rsp,
call_frame_t *frame,
compound_args_cbk_t *args_cbk, int index)
{
- int op_errno = ENOMEM;
+ int op_errno = EINVAL;
+ int op_ret = -1;
default_args_cbk_t *this_args_cbk = NULL;
compound_rsp *this_rsp = NULL;
server_state_t *state = NULL;
int ret = 0;
state = CALL_STATE (frame);
- rsp->compound_rsp_array.compound_rsp_array_val = GF_CALLOC
- (args_cbk->fop_length,
- sizeof (compound_rsp),
- gf_server_mt_compound_rsp_t);
-
- rsp->compound_rsp_array.compound_rsp_array_len = args_cbk->fop_length;
-
this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[index];
this_args_cbk = &args_cbk->rsp_list[index];
+ this_rsp->fop_enum = args_cbk->enum_list[index];
+
switch (this_rsp->fop_enum) {
case GF_FOP_STAT:
{
@@ -3219,6 +3229,7 @@ server_populate_compound_response (xlator_t *this, gfs3_compound_rsp *rsp,
default:
return ENOTSUP;
}
+ op_errno = 0;
out:
return op_errno;
}
@@ -3231,8 +3242,8 @@ out:
int
server_get_compound_resolve (server_state_t *state, gfs3_compound_req *req)
{
- int i = 0;
- compound_req *array = &req->compound_req_array.compound_req_array_val[i];
+ int i = 0;
+ compound_req *array = &req->compound_req_array.compound_req_array_val[i];
switch (array->fop_enum) {
case GF_FOP_STAT:
@@ -3787,3 +3798,494 @@ server_get_compound_resolve (server_state_t *state, gfs3_compound_req *req)
}
return 0;
}
+
+void
+server_compound_rsp_cleanup (gfs3_compound_rsp *rsp, compound_args_cbk_t *args)
+{
+ int i, len = 0;
+ compound_rsp *this_rsp = NULL;
+
+ if (!rsp->compound_rsp_array.compound_rsp_array_val)
+ return;
+
+ len = rsp->compound_rsp_array.compound_rsp_array_len;
+ return;
+
+ for (i = 0; i < len; i++) {
+ this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[i];
+ switch (args->enum_list[i]) {
+ case GF_FOP_STAT:
+ SERVER_FOP_RSP_CLEANUP (rsp, stat, i);
+ break;
+ case GF_FOP_MKNOD:
+ SERVER_FOP_RSP_CLEANUP (rsp, mknod, i);
+ break;
+ case GF_FOP_MKDIR:
+ SERVER_FOP_RSP_CLEANUP (rsp, mkdir, i);
+ break;
+ case GF_FOP_UNLINK:
+ SERVER_FOP_RSP_CLEANUP (rsp, unlink, i);
+ break;
+ case GF_FOP_RMDIR:
+ SERVER_FOP_RSP_CLEANUP (rsp, rmdir, i);
+ break;
+ case GF_FOP_SYMLINK:
+ SERVER_FOP_RSP_CLEANUP (rsp, symlink, i);
+ break;
+ case GF_FOP_RENAME:
+ SERVER_FOP_RSP_CLEANUP (rsp, rename, i);
+ break;
+ case GF_FOP_LINK:
+ SERVER_FOP_RSP_CLEANUP (rsp, link, i);
+ break;
+ case GF_FOP_TRUNCATE:
+ SERVER_FOP_RSP_CLEANUP (rsp, truncate, i);
+ break;
+ case GF_FOP_OPEN:
+ SERVER_FOP_RSP_CLEANUP (rsp, open, i);
+ break;
+ case GF_FOP_READ:
+ SERVER_FOP_RSP_CLEANUP (rsp, read, i);
+ break;
+ case GF_FOP_WRITE:
+ SERVER_FOP_RSP_CLEANUP (rsp, write, i);
+ break;
+ case GF_FOP_STATFS:
+ SERVER_FOP_RSP_CLEANUP (rsp, statfs, i);
+ break;
+ case GF_FOP_FSYNC:
+ SERVER_FOP_RSP_CLEANUP (rsp, fsync, i);
+ break;
+ case GF_FOP_OPENDIR:
+ SERVER_FOP_RSP_CLEANUP (rsp, opendir, i);
+ break;
+ case GF_FOP_CREATE:
+ SERVER_FOP_RSP_CLEANUP (rsp, create, i);
+ break;
+ case GF_FOP_FTRUNCATE:
+ SERVER_FOP_RSP_CLEANUP (rsp, ftruncate, i);
+ break;
+ case GF_FOP_FSTAT:
+ SERVER_FOP_RSP_CLEANUP (rsp, fstat, i);
+ break;
+ case GF_FOP_LK:
+ SERVER_FOP_RSP_CLEANUP (rsp, lk, i);
+ break;
+ case GF_FOP_LOOKUP:
+ SERVER_FOP_RSP_CLEANUP (rsp, lookup, i);
+ break;
+ case GF_FOP_SETATTR:
+ SERVER_FOP_RSP_CLEANUP (rsp, setattr, i);
+ break;
+ case GF_FOP_FSETATTR:
+ SERVER_FOP_RSP_CLEANUP (rsp, fsetattr, i);
+ break;
+ case GF_FOP_FALLOCATE:
+ SERVER_FOP_RSP_CLEANUP (rsp, fallocate, i);
+ break;
+ case GF_FOP_DISCARD:
+ SERVER_FOP_RSP_CLEANUP (rsp, discard, i);
+ break;
+ case GF_FOP_ZEROFILL:
+ SERVER_FOP_RSP_CLEANUP (rsp, zerofill, i);
+ break;
+ case GF_FOP_IPC:
+ SERVER_FOP_RSP_CLEANUP (rsp, ipc, i);
+ break;
+ case GF_FOP_SEEK:
+ SERVER_FOP_RSP_CLEANUP (rsp, seek, i);
+ break;
+ case GF_FOP_LEASE:
+ SERVER_FOP_RSP_CLEANUP (rsp, lease, i);
+ break;
+ /* fops that use gf_common_rsp */
+ case GF_FOP_FLUSH:
+ SERVER_COMMON_RSP_CLEANUP (rsp, flush, i);
+ break;
+ case GF_FOP_SETXATTR:
+ SERVER_COMMON_RSP_CLEANUP (rsp, setxattr, i);
+ break;
+ case GF_FOP_REMOVEXATTR:
+ SERVER_COMMON_RSP_CLEANUP (rsp, removexattr, i);
+ break;
+ case GF_FOP_FSETXATTR:
+ SERVER_COMMON_RSP_CLEANUP (rsp, fsetxattr, i);
+ break;
+ case GF_FOP_FREMOVEXATTR:
+ SERVER_COMMON_RSP_CLEANUP (rsp, fremovexattr, i);
+ break;
+ case GF_FOP_FSYNCDIR:
+ SERVER_COMMON_RSP_CLEANUP (rsp, fsyncdir, i);
+ break;
+ case GF_FOP_ACCESS:
+ SERVER_COMMON_RSP_CLEANUP (rsp, access, i);
+ break;
+ case GF_FOP_INODELK:
+ SERVER_COMMON_RSP_CLEANUP (rsp, inodelk, i);
+ break;
+ case GF_FOP_FINODELK:
+ SERVER_COMMON_RSP_CLEANUP (rsp, finodelk, i);
+ break;
+ case GF_FOP_ENTRYLK:
+ SERVER_COMMON_RSP_CLEANUP (rsp, entrylk, i);
+ break;
+ case GF_FOP_FENTRYLK:
+ SERVER_COMMON_RSP_CLEANUP (rsp, fentrylk, i);
+ break;
+ case GF_FOP_READLINK:
+ SERVER_FOP_RSP_CLEANUP (rsp, readlink, i);
+ break;
+ case GF_FOP_RCHECKSUM:
+ SERVER_FOP_RSP_CLEANUP (rsp, rchecksum, i);
+ break;
+ /* fops that need extra cleanup */
+ case GF_FOP_XATTROP:
+ {
+ gfs3_xattrop_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ xattrop);
+ SERVER_FOP_RSP_CLEANUP (rsp, xattrop, i);
+ GF_FREE (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_FXATTROP:
+ {
+ gfs3_fxattrop_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ fxattrop);
+ SERVER_FOP_RSP_CLEANUP (rsp, fxattrop, i);
+ GF_FREE (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_READDIR:
+ {
+ gfs3_readdir_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ readdir);
+ SERVER_FOP_RSP_CLEANUP (rsp, readdir, i);
+ readdir_rsp_cleanup (tmp_rsp);
+ break;
+ }
+ case GF_FOP_READDIRP:
+ {
+ gfs3_readdirp_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ readdirp);
+ SERVER_FOP_RSP_CLEANUP (rsp, readdir, i);
+ readdirp_rsp_cleanup (tmp_rsp);
+ break;
+ }
+ case GF_FOP_GETXATTR:
+ {
+ gfs3_getxattr_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ getxattr);
+ SERVER_FOP_RSP_CLEANUP (rsp, getxattr, i);
+ GF_FREE (tmp_rsp->dict.dict_val);
+ break;
+ }
+ case GF_FOP_FGETXATTR:
+ {
+ gfs3_fgetxattr_rsp *tmp_rsp = &CPD_RSP_FIELD(this_rsp,
+ fgetxattr);
+ SERVER_FOP_RSP_CLEANUP (rsp, fgetxattr, i);
+ GF_FREE (tmp_rsp->dict.dict_val);
+ break;
+ }
+ default:
+ break;
+ }
+ }
+ return;
+}
+
+void
+server_compound_req_cleanup (gfs3_compound_req *req, int len)
+{
+ int i = 0;
+ compound_req *curr_req = NULL;
+
+
+ if (!req->compound_req_array.compound_req_array_val)
+ return;
+
+ for (i = 0; i < len; i++) {
+ curr_req = &req->compound_req_array.compound_req_array_val[i];
+
+ switch (curr_req->fop_enum) {
+ case GF_FOP_STAT:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, stat);
+ break;
+ case GF_FOP_READLINK:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, readlink);
+ break;
+ case GF_FOP_MKNOD:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, mknod);
+ break;
+ case GF_FOP_MKDIR:
+ {
+ gfs3_mkdir_req *args = &CPD_REQ_FIELD (curr_req, mkdir);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, mkdir);
+ free (args->bname);
+ break;
+ }
+ case GF_FOP_UNLINK:
+ {
+ gfs3_unlink_req *args = &CPD_REQ_FIELD (curr_req,
+ unlink);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, unlink);
+ free (args->bname);
+ break;
+ }
+ case GF_FOP_RMDIR:
+ {
+ gfs3_rmdir_req *args = &CPD_REQ_FIELD (curr_req,
+ rmdir);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, rmdir);
+ free (args->bname);
+ break;
+ }
+ case GF_FOP_SYMLINK:
+ {
+ gfs3_symlink_req *args = &CPD_REQ_FIELD (curr_req,
+ symlink);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, symlink);
+ free (args->bname);
+ free (args->linkname);
+ break;
+ }
+ case GF_FOP_RENAME:
+ {
+ gfs3_rename_req *args = &CPD_REQ_FIELD (curr_req,
+ rename);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, rename);
+ free (args->oldbname);
+ free (args->newbname);
+ break;
+ }
+ case GF_FOP_LINK:
+ {
+ gfs3_link_req *args = &CPD_REQ_FIELD (curr_req,
+ link);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, link);
+ free (args->newbname);
+ break;
+ }
+ case GF_FOP_TRUNCATE:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, truncate);
+ break;
+ case GF_FOP_OPEN:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, open);
+ break;
+ case GF_FOP_READ:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, read);
+ break;
+ case GF_FOP_WRITE:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, write);
+ break;
+ case GF_FOP_STATFS:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, statfs);
+ break;
+ case GF_FOP_FLUSH:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, flush);
+ break;
+ case GF_FOP_FSYNC:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fsync);
+ break;
+ case GF_FOP_SETXATTR:
+ {
+ gfs3_setxattr_req *args = &CPD_REQ_FIELD (curr_req,
+ setxattr);
+
+ free (args->dict.dict_val);
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, setxattr);
+ break;
+ }
+ case GF_FOP_GETXATTR:
+ {
+ gfs3_getxattr_req *args = &CPD_REQ_FIELD (curr_req,
+ getxattr);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, getxattr);
+ free (args->name);
+ break;
+ }
+ case GF_FOP_REMOVEXATTR:
+ {
+ gfs3_removexattr_req *args = &CPD_REQ_FIELD (curr_req,
+ removexattr);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, removexattr);
+ free (args->name);
+ break;
+ }
+ case GF_FOP_OPENDIR:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, opendir);
+ break;
+ case GF_FOP_FSYNCDIR:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fsyncdir);
+ break;
+ case GF_FOP_ACCESS:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, access);
+ break;
+ case GF_FOP_CREATE:
+ {
+ gfs3_create_req *args = &CPD_REQ_FIELD (curr_req,
+ create);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, create);
+ free (args->bname);
+ break;
+ }
+ case GF_FOP_FTRUNCATE:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, ftruncate);
+ break;
+ case GF_FOP_FSTAT:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fstat);
+ break;
+ case GF_FOP_LK:
+ {
+ gfs3_lk_req *args = &CPD_REQ_FIELD (curr_req, lk);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, lk);
+ free (args->flock.lk_owner.lk_owner_val);
+ break;
+ }
+ case GF_FOP_LOOKUP:
+ {
+ gfs3_lookup_req *args = &CPD_REQ_FIELD (curr_req,
+ lookup);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, lookup);
+ free (args->bname);
+ break;
+ }
+ case GF_FOP_READDIR:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, readdir);
+ break;
+ case GF_FOP_INODELK:
+ {
+ gfs3_inodelk_req *args = &CPD_REQ_FIELD (curr_req,
+ inodelk);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, inodelk);
+ free (args->volume);
+ free (args->flock.lk_owner.lk_owner_val);
+ break;
+ }
+ case GF_FOP_FINODELK:
+ {
+ gfs3_finodelk_req *args = &CPD_REQ_FIELD (curr_req,
+ finodelk);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, finodelk);
+ free (args->volume);
+ free (args->flock.lk_owner.lk_owner_val);
+ break;
+ }
+ case GF_FOP_ENTRYLK:
+ {
+ gfs3_entrylk_req *args = &CPD_REQ_FIELD (curr_req,
+ entrylk);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, entrylk);
+ free (args->volume);
+ free (args->name);
+ break;
+ }
+ case GF_FOP_FENTRYLK:
+ {
+ gfs3_fentrylk_req *args = &CPD_REQ_FIELD (curr_req,
+ fentrylk);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fentrylk);
+ free (args->volume);
+ free (args->name);
+ break;
+ }
+ case GF_FOP_XATTROP:
+ {
+ gfs3_xattrop_req *args = &CPD_REQ_FIELD (curr_req,
+ xattrop);
+
+ free (args->dict.dict_val);
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, xattrop);
+ break;
+ }
+ case GF_FOP_FXATTROP:
+ {
+ gfs3_fxattrop_req *args = &CPD_REQ_FIELD (curr_req,
+ fxattrop);
+
+ free (args->dict.dict_val);
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fxattrop);
+ break;
+ }
+ case GF_FOP_FGETXATTR:
+ {
+ gfs3_fgetxattr_req *args = &CPD_REQ_FIELD (curr_req,
+ fgetxattr);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fgetxattr);
+ free (args->name);
+ break;
+ }
+ case GF_FOP_FSETXATTR:
+ {
+ gfs3_fsetxattr_req *args = &CPD_REQ_FIELD(curr_req,
+ fsetxattr);
+
+ free (args->dict.dict_val);
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fsetxattr);
+ break;
+ }
+ case GF_FOP_RCHECKSUM:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, rchecksum);
+ break;
+ case GF_FOP_SETATTR:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, setattr);
+ break;
+ case GF_FOP_FSETATTR:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fsetattr);
+ break;
+ case GF_FOP_READDIRP:
+ {
+ gfs3_readdirp_req *args = &CPD_REQ_FIELD (curr_req,
+ readdirp);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fremovexattr);
+ free (args->dict.dict_val);
+ break;
+ }
+ case GF_FOP_FREMOVEXATTR:
+ {
+ gfs3_fremovexattr_req *args = &CPD_REQ_FIELD(curr_req,
+ fremovexattr);
+
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fremovexattr);
+ free (args->name);
+ break;
+ }
+ case GF_FOP_FALLOCATE:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, fallocate);
+ break;
+ case GF_FOP_DISCARD:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, discard);
+ break;
+ case GF_FOP_ZEROFILL:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, zerofill);
+ break;
+ case GF_FOP_IPC:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, ipc);
+ break;
+ case GF_FOP_SEEK:
+ SERVER_COMPOUND_FOP_CLEANUP (curr_req, seek);
+ break;
+ default:
+ break;
+ }
+ }
+
+ return;
+}
diff --git a/xlators/protocol/server/src/server-helpers.h b/xlators/protocol/server/src/server-helpers.h
index 200b383e67e..02e092b9956 100644
--- a/xlators/protocol/server/src/server-helpers.h
+++ b/xlators/protocol/server/src/server-helpers.h
@@ -81,4 +81,9 @@ int
server_populate_compound_request (gfs3_compound_req *req, call_frame_t *frame,
default_args_t *this_args,
int index);
+void
+server_compound_rsp_cleanup (gfs3_compound_rsp *rsp, compound_args_cbk_t *args);
+
+void
+server_compound_req_cleanup (gfs3_compound_req *req, int len);
#endif /* !_SERVER_HELPERS_H */
diff --git a/xlators/protocol/server/src/server-rpc-fops.c b/xlators/protocol/server/src/server-rpc-fops.c
index 4dd7ad90e6a..43061b03c56 100644
--- a/xlators/protocol/server/src/server-rpc-fops.c
+++ b/xlators/protocol/server/src/server-rpc-fops.c
@@ -21,6 +21,8 @@
#include "defaults.h"
#include "default-args.h"
#include "server-common.h"
+#include "xlator.h"
+#include "compound-fop-utils.h"
#include "xdr-nfs3.h"
@@ -2075,8 +2077,19 @@ server_compound_cbk (call_frame_t *frame, void *cookie, xlator_t *this,
frame->root->unique, state->resolve.fd_no,
uuid_utoa (state->resolve.gfid),
strerror (op_errno));
+ }
+
+ rsp.compound_rsp_array.compound_rsp_array_val = GF_CALLOC
+ (args_cbk->fop_length,
+ sizeof (compound_rsp),
+ gf_server_mt_compound_rsp_t);
+
+ if (!rsp.compound_rsp_array.compound_rsp_array_val) {
+ op_ret = -1;
+ op_errno = ENOMEM;
goto out;
}
+ rsp.compound_rsp_array.compound_rsp_array_len = args_cbk->fop_length;
for (i = 0; i < args_cbk->fop_length; i++) {
op_ret = server_populate_compound_response (this, &rsp,
@@ -2096,11 +2109,7 @@ out:
server_submit_reply (frame, req, &rsp, NULL, 0, NULL,
(xdrproc_t) xdr_gfs3_compound_rsp);
- for (i = 0; i < state->args->fop_length; i++)
- args_wipe (&state->args->req_list[i]);
-
- GF_FREE (state->args->req_list);
- GF_FREE (state->args);
+ server_compound_rsp_cleanup (&rsp, args_cbk);
GF_FREE (rsp.xdata.xdata_val);
return 0;
@@ -3303,8 +3312,12 @@ server_compound_resume (call_frame_t *frame, xlator_t *bound_xl)
int ret = -1;
int length = 0;
int op_errno = ENOMEM;
+ compound_req *c_req = NULL;
+ xlator_t *this = NULL;
state = CALL_STATE (frame);
+ this = frame->this;
+
if (state->resolve.op_ret != 0) {
ret = state->resolve.op_ret;
op_errno = state->resolve.op_errno;
@@ -3313,20 +3326,18 @@ server_compound_resume (call_frame_t *frame, xlator_t *bound_xl)
req = state->req;
- args = GF_CALLOC (1, sizeof (*args), gf_mt_compound_req_t);
- state->args = args;
- if (!args)
- goto err;
-
length = req->compound_req_array.compound_req_array_len;
+ state->args = compound_fop_alloc (length, req->compound_fop_enum,
+ state->xdata);
+ args = state->args;
- args->req_list = GF_CALLOC (length,
- sizeof (*args->req_list),
- gf_mt_default_args_t);
- if (!args->req_list)
+ if (!args)
goto err;
for (i = 0; i < length; i++) {
+ c_req = &req->compound_req_array.compound_req_array_val[i];
+ args->enum_list[i] = c_req->fop_enum;
+
ret = server_populate_compound_request (req, frame,
&args->req_list[i],
i);
@@ -3339,7 +3350,8 @@ server_compound_resume (call_frame_t *frame, xlator_t *bound_xl)
}
STACK_WIND (frame, server_compound_cbk,
- bound_xl, bound_xl->fops->compound,
+ FIRST_CHILD(this),
+ FIRST_CHILD(this)->fops->compound,
args, state->xdata);
return 0;
@@ -3347,11 +3359,6 @@ err:
server_compound_cbk (frame, NULL, frame->this, ret, op_errno,
NULL, NULL);
- for (i = 0; i < length; i++)
- args_wipe (&args->req_list[i]);
-
- GF_FREE (args->req_list);
- GF_FREE (args);
return ret;
}
/* Fop section */
@@ -6684,12 +6691,13 @@ out:
int
server3_3_compound (rpcsvc_request_t *req)
{
- server_state_t *state = NULL;
- call_frame_t *frame = NULL;
- gfs3_compound_req args = {0,};
- ssize_t len = 0;
- int i = 0;
- int ret = -1;
+ server_state_t *state = NULL;
+ call_frame_t *frame = NULL;
+ gfs3_compound_req args = {0,};
+ ssize_t len = 0;
+ int length = 0;
+ int i = 0;
+ int ret = -1;
int op_errno = 0;
if (!req)
@@ -6702,6 +6710,7 @@ server3_3_compound (rpcsvc_request_t *req)
goto out;
}
+ len = ret;
frame = get_frame_from_request (req);
if (!frame) {
SERVER_REQ_SET_ERROR (req, ret);
@@ -6754,6 +6763,9 @@ server3_3_compound (rpcsvc_request_t *req)
out:
free (args.xdata.xdata_val);
+ length = args.compound_req_array.compound_req_array_len;
+ server_compound_req_cleanup (&args, length);
+
if (op_errno)
SERVER_REQ_SET_ERROR (req, ret);
diff --git a/xlators/protocol/server/src/server.h b/xlators/protocol/server/src/server.h
index fb9cd45db8a..c87dbe67b12 100644
--- a/xlators/protocol/server/src/server.h
+++ b/xlators/protocol/server/src/server.h
@@ -30,6 +30,34 @@
#define GF_MAX_SOCKET_WINDOW_SIZE (1 * GF_UNIT_MB)
#define GF_MIN_SOCKET_WINDOW_SIZE (0)
+#define CPD_REQ_FIELD(v, f) ((v)->compound_req_u.compound_##f##_req)
+#define CPD_RSP_FIELD(v, f) ((v)->compound_rsp_u.compound_##f##_rsp)
+
+#define SERVER_COMMON_RSP_CLEANUP(rsp, fop, i) \
+ do { \
+ compound_rsp *this_rsp = NULL; \
+ this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[i];\
+ gf_common_rsp *_this_rsp = &CPD_RSP_FIELD(this_rsp, fop); \
+ \
+ GF_FREE (_this_rsp->xdata.xdata_val); \
+ } while (0)
+
+#define SERVER_FOP_RSP_CLEANUP(rsp, fop, i) \
+ do { \
+ compound_rsp *this_rsp = NULL; \
+ this_rsp = &rsp->compound_rsp_array.compound_rsp_array_val[i];\
+ gfs3_##fop##_rsp *_this_rsp = &CPD_RSP_FIELD(this_rsp, fop); \
+ \
+ GF_FREE (_this_rsp->xdata.xdata_val); \
+ } while (0)
+
+#define SERVER_COMPOUND_FOP_CLEANUP(curr_req, fop) \
+ do { \
+ gfs3_##fop##_req *_req = &CPD_REQ_FIELD(curr_req, fop); \
+ \
+ free (_req->xdata.xdata_val); \
+ } while (0)
+
typedef enum {
INTERNAL_LOCKS = 1,
POSIX_LOCKS = 2,