From 32451a4dd02bdd95ec800d51267d2e6be43914a4 Mon Sep 17 00:00:00 2001 From: Vijay Bellur Date: Wed, 14 Jul 2010 00:20:28 +0000 Subject: Fixes a crash seen in create volume Also includes some re-factoring changes. Signed-off-by: Vijay Bellur Signed-off-by: Anand V. Avati BUG: 1063 (gluster volume create command segfaults) URL: http://bugs.gluster.com/cgi-bin/bugzilla3/show_bug.cgi?id=1063 --- xlators/mgmt/glusterd/src/gd-xdr.c | 43 +++ xlators/mgmt/glusterd/src/gd-xdr.h | 18 ++ xlators/mgmt/glusterd/src/glusterd-ha.c | 17 +- xlators/mgmt/glusterd/src/glusterd-handler.c | 105 ++++--- xlators/mgmt/glusterd/src/glusterd-mem-types.h | 1 + xlators/mgmt/glusterd/src/glusterd-op-sm.c | 410 +++++++++++++------------ xlators/mgmt/glusterd/src/glusterd-op-sm.h | 22 +- xlators/mgmt/glusterd/src/glusterd-sm.c | 80 ++--- xlators/mgmt/glusterd/src/glusterd.c | 10 + xlators/mgmt/glusterd/src/glusterd.h | 43 +-- xlators/mgmt/glusterd/src/glusterd3_1-mops.c | 33 +- 11 files changed, 439 insertions(+), 343 deletions(-) (limited to 'xlators/mgmt') diff --git a/xlators/mgmt/glusterd/src/gd-xdr.c b/xlators/mgmt/glusterd/src/gd-xdr.c index 4e1bfd07e..c70c5697f 100644 --- a/xlators/mgmt/glusterd/src/gd-xdr.c +++ b/xlators/mgmt/glusterd/src/gd-xdr.c @@ -113,6 +113,49 @@ gd_xdr_to_mgmt_commit_op_req (struct iovec inmsg, void *args) return xdr_to_generic (inmsg, (void *)args, (xdrproc_t)xdr_gd1_mgmt_commit_op_req); } + +ssize_t +gd_xdr_to_mgmt_probe_rsp (struct iovec inmsg, void *args) +{ + return xdr_to_generic (inmsg, (void *)args, + (xdrproc_t)xdr_gd1_mgmt_probe_rsp); +} + +ssize_t +gd_xdr_to_mgmt_friend_rsp (struct iovec inmsg, void *args) +{ + return xdr_to_generic (inmsg, (void *)args, + (xdrproc_t)xdr_gd1_mgmt_friend_rsp); +} + +ssize_t +gd_xdr_to_mgmt_cluster_lock_rsp (struct iovec inmsg, void *args) +{ + return xdr_to_generic (inmsg, (void *)args, + (xdrproc_t)xdr_gd1_mgmt_cluster_lock_rsp); +} + +ssize_t +gd_xdr_to_mgmt_cluster_unlock_rsp (struct iovec inmsg, void *args) +{ + return xdr_to_generic (inmsg, (void *)args, + (xdrproc_t)xdr_gd1_mgmt_cluster_unlock_rsp); +} + +ssize_t +gd_xdr_to_mgmt_stage_op_rsp (struct iovec inmsg, void *args) +{ + return xdr_to_generic (inmsg, (void *)args, + (xdrproc_t)xdr_gd1_mgmt_stage_op_rsp); +} + +ssize_t +gd_xdr_to_mgmt_commit_op_rsp (struct iovec inmsg, void *args) +{ + return xdr_to_generic (inmsg, (void *)args, + (xdrproc_t)xdr_gd1_mgmt_commit_op_rsp); +} + ssize_t gd_xdr_from_mgmt_probe_req (struct iovec outmsg, void *req) { diff --git a/xlators/mgmt/glusterd/src/gd-xdr.h b/xlators/mgmt/glusterd/src/gd-xdr.h index 55e2f8e6d..911edcf78 100644 --- a/xlators/mgmt/glusterd/src/gd-xdr.h +++ b/xlators/mgmt/glusterd/src/gd-xdr.h @@ -29,6 +29,9 @@ ssize_t gd_xdr_to_mgmt_probe_req (struct iovec inmsg, void *args); +ssize_t +gd_xdr_to_mgmt_probe_rsp (struct iovec inmsg, void *args); + ssize_t gd_xdr_serialize_mgmt_probe_rsp (struct iovec outmsg, void *rsp); @@ -38,6 +41,9 @@ gd_xdr_from_mgmt_probe_req (struct iovec outmsg, void *req); ssize_t gd_xdr_to_mgmt_friend_req (struct iovec inmsg, void *args); +ssize_t +gd_xdr_to_mgmt_friend_rsp (struct iovec inmsg, void *args); + ssize_t gd_xdr_serialize_mgmt_friend_rsp (struct iovec outmsg, void *rsp); @@ -47,6 +53,9 @@ gd_xdr_from_mgmt_friend_req (struct iovec outmsg, void *req); ssize_t gd_xdr_to_mgmt_cluster_lock_req (struct iovec inmsg, void *args); +ssize_t +gd_xdr_to_mgmt_cluster_lock_rsp (struct iovec inmsg, void *args); + ssize_t gd_xdr_serialize_mgmt_cluster_lock_rsp (struct iovec outmsg, void *rsp); @@ -56,6 +65,9 @@ gd_xdr_from_mgmt_cluster_lock_req (struct iovec outmsg, void *req); ssize_t gd_xdr_to_mgmt_cluster_unlock_req (struct iovec inmsg, void *args); +ssize_t +gd_xdr_to_mgmt_cluster_unlock_rsp (struct iovec inmsg, void *args); + ssize_t gd_xdr_serialize_mgmt_cluster_unlock_rsp (struct iovec outmsg, void *rsp); @@ -65,6 +77,9 @@ gd_xdr_from_mgmt_cluster_unlock_req (struct iovec outmsg, void *req); ssize_t gd_xdr_to_mgmt_stage_op_req (struct iovec inmsg, void *args); +ssize_t +gd_xdr_to_mgmt_stage_op_rsp (struct iovec inmsg, void *args); + ssize_t gd_xdr_serialize_mgmt_stage_op_rsp (struct iovec outmsg, void *rsp); @@ -74,6 +89,9 @@ gd_xdr_from_mgmt_stage_op_req (struct iovec outmsg, void *req); ssize_t gd_xdr_to_mgmt_commit_op_req (struct iovec inmsg, void *args); +ssize_t +gd_xdr_to_mgmt_commit_op_rsp (struct iovec inmsg, void *args); + ssize_t gd_xdr_serialize_mgmt_commit_op_rsp (struct iovec outmsg, void *rsp); diff --git a/xlators/mgmt/glusterd/src/glusterd-ha.c b/xlators/mgmt/glusterd/src/glusterd-ha.c index 26de16b3a..398ecce57 100644 --- a/xlators/mgmt/glusterd/src/glusterd-ha.c +++ b/xlators/mgmt/glusterd/src/glusterd-ha.c @@ -52,14 +52,19 @@ int32_t glusterd_ha_create_volume (glusterd_volinfo_t *volinfo) { - char pathname[PATH_MAX] = {0,}; - int32_t ret = -1; - char filepath[PATH_MAX] = {0,}; - char buf[4096] = {0,}; - int fd = -1; + char pathname[PATH_MAX] = {0,}; + int32_t ret = -1; + char filepath[PATH_MAX] = {0,}; + char buf[4096] = {0,}; + int fd = -1; + glusterd_conf_t *priv = NULL; GF_ASSERT (volinfo); - snprintf (pathname, 1024, "%s/vols/%s", GLUSTERD_DEFAULT_WORKDIR, + priv = THIS->private; + + GF_ASSERT (priv); + + snprintf (pathname, 1024, "%s/vols/%s", priv->workdir, volinfo->volname); ret = mkdir (pathname, 0x777); diff --git a/xlators/mgmt/glusterd/src/glusterd-handler.c b/xlators/mgmt/glusterd/src/glusterd-handler.c index f769693ad..db385d7bb 100644 --- a/xlators/mgmt/glusterd/src/glusterd-handler.c +++ b/xlators/mgmt/glusterd/src/glusterd-handler.c @@ -363,24 +363,19 @@ glusterd_handle_stage_op (rpcsvc_request_t *req) { int32_t ret = -1; char str[50]; - gd1_mgmt_stage_op_req *stage_req = NULL; + gd1_mgmt_stage_op_req stage_req = {{0,}}; glusterd_op_sm_event_t *event = NULL; glusterd_op_stage_ctx_t *ctx = NULL; GF_ASSERT (req); - stage_req = GF_CALLOC (1, sizeof (*stage_req), - gf_gld_mt_mop_stage_req_t); - - GF_ASSERT (stage_req); - - if (!gd_xdr_to_mgmt_stage_op_req (req->msg[0], stage_req)) { + if (!gd_xdr_to_mgmt_stage_op_req (req->msg[0], &stage_req)) { //failed to decode msg; req->rpc_err = GARBAGE_ARGS; goto out; } - uuid_unparse (stage_req->uuid, str); + uuid_unparse (stage_req.uuid, str); gf_log ("glusterd", GF_LOG_NORMAL, "Received stage op from uuid: %s", str); @@ -399,7 +394,18 @@ glusterd_handle_stage_op (rpcsvc_request_t *req) } //CHANGE THIS - ctx->stage_req = &stage_req; + uuid_copy (ctx->stage_req.uuid, stage_req.uuid); + ctx->stage_req.op = stage_req.op; + ctx->stage_req.buf.buf_len = stage_req.buf.buf_len; + ctx->stage_req.buf.buf_val = GF_CALLOC (1, stage_req.buf.buf_len, + gf_gld_mt_string); + if (!ctx->stage_req.buf.buf_val) + goto out; + + memcpy (ctx->stage_req.buf.buf_val, stage_req.buf.buf_val, + stage_req.buf.buf_len); + + ctx->req = req; event->ctx = ctx; @@ -447,7 +453,16 @@ glusterd_handle_commit_op (rpcsvc_request_t *req) ctx->req = req; //CHANGE THIS - ctx->stage_req = &commit_req; + uuid_copy (ctx->stage_req.uuid, commit_req.uuid); + ctx->stage_req.op = commit_req.op; + ctx->stage_req.buf.buf_len = commit_req.buf.buf_len; + ctx->stage_req.buf.buf_val = GF_CALLOC (1, commit_req.buf.buf_len, + gf_gld_mt_string); + if (!ctx->stage_req.buf.buf_val) + goto out; + + memcpy (ctx->stage_req.buf.buf_val, commit_req.buf.buf_val, + commit_req.buf.buf_len); event->ctx = ctx; ret = glusterd_op_sm_inject_event (event); @@ -1531,9 +1546,9 @@ glusterd_create_volume (rpcsvc_request_t *req, dict_t *dict) char *volname = NULL; char *bricks = NULL; int type = 0; - int sub_count = 2; + //int sub_count = 2; int count = 0; - char cmd_str[8192] = {0,}; + //char cmd_str[8192] = {0,}; GF_ASSERT (req); GF_ASSERT (dict); @@ -1558,38 +1573,38 @@ glusterd_create_volume (rpcsvc_request_t *req, dict_t *dict) if (ret) goto out; - switch (type) { - case GF_CLUSTER_TYPE_REPLICATE: - { - ret = dict_get_int32 (dict, "replica-count", &sub_count); - if (ret) - goto out; - snprintf (cmd_str, 8192, - "glusterfs-volgen -n %s -c /etc/glusterd -r 1 %s", - volname, bricks); - ret = system (cmd_str); - break; - } - case GF_CLUSTER_TYPE_STRIPE: - { - ret = dict_get_int32 (dict, "stripe-count", &sub_count); - if (ret) - goto out; - snprintf (cmd_str, 8192, - "glusterfs-volgen -n %s -c /etc/glusterd -r 0 %s", - volname, bricks); - ret = system (cmd_str); - break; - } - case GF_CLUSTER_TYPE_NONE: - { - snprintf (cmd_str, 8192, - "glusterfs-volgen -n %s -c /etc/glusterd %s", - volname, bricks); - ret = system (cmd_str); - break; - } - } + /*switch (type) { + case GF_CLUSTER_TYPE_REPLICATE: + { + ret = dict_get_int32 (dict, "replica-count", &sub_count); + if (ret) + goto out; + snprintf (cmd_str, 8192, + "glusterfs-volgen -n %s -c /etc/glusterd -r 1 %s", + volname, bricks); + ret = system (cmd_str); + break; + } + case GF_CLUSTER_TYPE_STRIPE: + { + ret = dict_get_int32 (dict, "stripe-count", &sub_count); + if (ret) + goto out; + snprintf (cmd_str, 8192, + "glusterfs-volgen -n %s -c /etc/glusterd -r 0 %s", + volname, bricks); + ret = system (cmd_str); + break; + } + case GF_CLUSTER_TYPE_NONE: + { + snprintf (cmd_str, 8192, + "glusterfs-volgen -n %s -c /etc/glusterd %s", + volname, bricks); + ret = system (cmd_str); + break; + } + } */ ret = glusterd_op_txn_begin (); @@ -1698,7 +1713,7 @@ glusterd_rpc_notify (struct rpc_clnt *rpc, void *mydata, rpc_clnt_event_t event, gf_log (this->name, GF_LOG_TRACE, "got RPC_CLNT_DISCONNECT"); - default_notify (this, GF_EVENT_CHILD_DOWN, NULL); + //default_notify (this, GF_EVENT_CHILD_DOWN, NULL); break; default: diff --git a/xlators/mgmt/glusterd/src/glusterd-mem-types.h b/xlators/mgmt/glusterd/src/glusterd-mem-types.h index c72a91d5a..7ede5efec 100644 --- a/xlators/mgmt/glusterd/src/glusterd-mem-types.h +++ b/xlators/mgmt/glusterd/src/glusterd-mem-types.h @@ -29,6 +29,7 @@ enum gf_gld_mem_types_ { gf_gld_mt_glusterd_state_t, gf_gld_mt_glusterd_conf_t, gf_gld_mt_locker, + gf_gld_mt_string, gf_gld_mt_lock_table, gf_gld_mt_char, gf_gld_mt_glusterd_connection_t, diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.c b/xlators/mgmt/glusterd/src/glusterd-op-sm.c index c6aaf7127..a9417d3ff 100644 --- a/xlators/mgmt/glusterd/src/glusterd-op-sm.c +++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.c @@ -29,7 +29,6 @@ #include #include -//#include "transport.h" #include "fnmatch.h" #include "xlator.h" #include "protocol-common.h" @@ -41,11 +40,11 @@ #include "compat.h" #include "compat-errno.h" #include "statedump.h" -//#include "md5.h" #include "glusterd-sm.h" #include "glusterd-op-sm.h" #include "glusterd-utils.h" #include "glusterd-ha.h" +#include "gluster1.h" static struct list_head gd_op_sm_queue; glusterd_op_info_t opinfo; @@ -77,6 +76,22 @@ glusterd_op_get_len (glusterd_op_t op) return 0; } +static int +glusterd_op_sm_inject_all_acc () +{ + glusterd_op_sm_event_t *event = NULL; + int32_t ret = -1; + + ret = glusterd_op_sm_new_event (GD_OP_EVENT_ALL_ACC, &event); + + if (ret) + goto out; + + ret = glusterd_op_sm_inject_event (event); +out: + return ret; +} + int glusterd_op_build_payload (glusterd_op_t op, gd1_mgmt_stage_op_req **req) { @@ -98,17 +113,10 @@ glusterd_op_build_payload (glusterd_op_t op, gd1_mgmt_stage_op_req **req) goto out; } - stage_req->buf.buf_val = GF_CALLOC (1, len, - gf_gld_mt_mop_stage_req_t); - - if (!stage_req->buf.buf_val) { - gf_log ("", GF_LOG_ERROR, "Out of Memory"); - goto out; - } glusterd_get_uuid (&stage_req->uuid); stage_req->op = op; - stage_req->buf.buf_len = len; + //stage_req->buf.buf_len = len; switch (op) { case GD_OP_CREATE_VOLUME: @@ -116,8 +124,9 @@ glusterd_op_build_payload (glusterd_op_t op, gd1_mgmt_stage_op_req **req) dict_t *dict = NULL; dict = glusterd_op_get_ctx (op); GF_ASSERT (dict); - ret = dict_serialize (dict, - stage_req->buf.buf_val); + ret = dict_allocate_and_serialize (dict, + &stage_req->buf.buf_val, + (size_t *)&stage_req->buf.buf_len); if (ret) { goto out; } @@ -137,168 +146,6 @@ out: -/*static int -glusterd_xfer_stage_req (xlator_t *this, int32_t *lock_count) -{ - gf_hdr_common_t *hdr = NULL; - size_t hdrlen = -1; - int ret = -1; - glusterd_conf_t *priv = NULL; - call_frame_t *dummy_frame = NULL; - glusterd_peerinfo_t *peerinfo = NULL; - int pending_lock = 0; - int i = 0; - - GF_ASSERT (this); - GF_ASSERT (lock_count); - - priv = this->private; - GF_ASSERT (priv); - - - for ( i = GD_OP_NONE; i < GD_OP_MAX; i++) { - if (opinfo.pending_op[i]) - break; - } - - if (GD_OP_MAX == i) { - - //No pending ops, inject stage_acc - - glusterd_op_sm_event_t *event = NULL; - - ret = glusterd_op_sm_new_event (GD_OP_EVENT_STAGE_ACC, - &event); - - if (ret) - goto out; - - ret = glusterd_op_sm_inject_event (event); - - return ret; - } - - - ret = glusterd_op_build_payload (i, &hdr, &hdrlen); - - if (ret) - goto out; - - dummy_frame = create_frame (this, this->ctx->pool); - - if (!dummy_frame) - goto out; - - list_for_each_entry (peerinfo, &opinfo.op_peers, op_peers_list) { - GF_ASSERT (peerinfo); - - GF_ASSERT (peerinfo->state.state == GD_FRIEND_STATE_BEFRIENDED); - - - ret = glusterd_xfer (dummy_frame, this, - peerinfo->trans, - GF_OP_TYPE_MOP_REQUEST, - GF_MOP_STAGE_OP, - hdr, hdrlen, NULL, 0, NULL); - if (!ret) - pending_lock++; - } - - gf_log ("glusterd", GF_LOG_NORMAL, "Sent op req to %d peers", - pending_lock); - if (i < GD_OP_MAX) - opinfo.pending_op[i] = 0; - - *lock_count = pending_lock; - -out: - if (hdr) - GF_FREE (hdr); - - return ret; -} */ - -/*static int -glusterd_xfer_commit_req (xlator_t *this, int32_t *lock_count) -{ - gf_hdr_common_t *hdr = NULL; - size_t hdrlen = -1; - int ret = -1; - glusterd_conf_t *priv = NULL; - call_frame_t *dummy_frame = NULL; - glusterd_peerinfo_t *peerinfo = NULL; - int pending_lock = 0; - int i = 0; - - GF_ASSERT (this); - GF_ASSERT (lock_count); - - priv = this->private; - GF_ASSERT (priv); - - - for ( i = GD_OP_NONE; i < GD_OP_MAX; i++) { - if (opinfo.commit_op[i]) - break; - } - - if (GD_OP_MAX == i) { - - //No pending ops, inject stage_acc - - glusterd_op_sm_event_t *event = NULL; - - ret = glusterd_op_sm_new_event (GD_OP_EVENT_COMMIT_ACC, - &event); - - if (ret) - goto out; - - ret = glusterd_op_sm_inject_event (event); - - return ret; - } - - - ret = glusterd_op_build_payload (i, &hdr, &hdrlen); - - if (ret) - goto out; - - dummy_frame = create_frame (this, this->ctx->pool); - - if (!dummy_frame) - goto out; - - list_for_each_entry (peerinfo, &opinfo.op_peers, op_peers_list) { - GF_ASSERT (peerinfo); - - GF_ASSERT (peerinfo->state.state == GD_FRIEND_STATE_BEFRIENDED); - - - ret = glusterd_xfer (dummy_frame, this, - peerinfo->trans, - GF_OP_TYPE_MOP_REQUEST, - GF_MOP_STAGE_OP, - hdr, hdrlen, NULL, 0, NULL); - if (!ret) - pending_lock++; - } - - gf_log ("glusterd", GF_LOG_NORMAL, "Sent op req to %d peers", - pending_lock); - if (i < GD_OP_MAX) - opinfo.pending_op[i] = 0; - - *lock_count = pending_lock; - -out: - if (hdr) - GF_FREE (hdr); - - return ret; -}*/ - static int glusterd_op_stage_create_volume (gd1_mgmt_stage_op_req *req) { @@ -309,6 +156,10 @@ glusterd_op_stage_create_volume (gd1_mgmt_stage_op_req *req) GF_ASSERT (req); + dict = dict_new (); + if (!dict) + goto out; + ret = dict_unserialize (req->buf.buf_val, req->buf.buf_len, &dict); if (ret) { @@ -351,8 +202,14 @@ glusterd_op_create_volume (gd1_mgmt_stage_op_req *req) xlator_t *this = NULL; char *brick = NULL; int32_t count = 0; - int32_t i = 0; - char key[50]; + int32_t i = 1; + //char key[50] = {0,}; + int32_t sub_count = 0; + char path[PATH_MAX] = {0,}; + char cmd_str[8192] = {0,}; + char *bricks = NULL; + char *brick_list = NULL; + char *saveptr = NULL; GF_ASSERT (req); @@ -362,6 +219,10 @@ glusterd_op_create_volume (gd1_mgmt_stage_op_req *req) priv = this->private; GF_ASSERT (priv); + dict = dict_new (); + if (!dict) + goto out; + ret = dict_unserialize (req->buf.buf_val, req->buf.buf_len, &dict); if (ret) { @@ -403,22 +264,81 @@ glusterd_op_create_volume (gd1_mgmt_stage_op_req *req) count = volinfo->brick_count; + ret = dict_get_str (dict, "bricks", &bricks); + + if (ret) { + gf_log ("", GF_LOG_ERROR, "Unable to get bricks"); + goto out; + } + + if (bricks) + brick_list = gf_strdup (bricks); + + if (count) + brick = strtok_r (brick_list+1, " \n", &saveptr); + while ( i <= count) { - snprintf (key, 50, "brick%d", i); - ret = dict_get_str (dict, key, &brick); - if (ret) - goto out; ret = glusterd_brickinfo_from_brick (brick, &brickinfo); if (ret) goto out; list_add_tail (&brickinfo->brick_list, &volinfo->bricks); + brick = strtok_r (NULL, " \n", &saveptr); i++; } ret = glusterd_ha_create_volume (volinfo); + if (ret) + goto out; + + + GLUSTERD_GET_VOLUME_DIR(path, volinfo, priv); + + switch (volinfo->type) { + + case GF_CLUSTER_TYPE_REPLICATE: + { + ret = dict_get_int32 (dict, "replica-count", + &sub_count); + if (ret) + goto out; + snprintf (cmd_str, 8192, + "glusterfs-volgen -n %s -c %s -r 1 %s", + volname, path, bricks); + ret = system (cmd_str); + break; + } + + case GF_CLUSTER_TYPE_STRIPE: + { + ret = dict_get_int32 (dict, "stripe-count", + &sub_count); + if (ret) + goto out; + snprintf (cmd_str, 8192, + "glusterfs-volgen -n %s -c %s -r 0 %s", + volname, path, bricks); + ret = system (cmd_str); + break; + } + + case GF_CLUSTER_TYPE_NONE: + { + snprintf (cmd_str, 8192, + "glusterfs-volgen -n %s -c %s %s", + volname, path, bricks); + ret = system (cmd_str); + break; + } + + default: + gf_log ("", GF_LOG_ERROR, "Unkown type: %d", + volinfo->type); + ret = -1; + } + out: return ret; } @@ -447,9 +367,14 @@ glusterd_op_ac_send_lock (glusterd_op_sm_event_t *event, void *ctx) proc = &priv->mgmt->proctable[GD_MGMT_CLUSTER_LOCK]; if (proc->fn) { ret = proc->fn (NULL, this, NULL); + if (ret) + goto out; } - // TODO: if pending_count = 0, inject ALL_ACC here + if (!opinfo.pending_count) + ret = glusterd_op_sm_inject_all_acc (); + +out: gf_log ("", GF_LOG_DEBUG, "Returning with %d", ret); return ret; @@ -466,12 +391,22 @@ glusterd_op_ac_send_unlock (glusterd_op_sm_event_t *event, void *ctx) this = THIS; priv = this->private; + ret = glusterd_unlock (priv->uuid); + + if (ret) + goto out; + proc = &priv->mgmt->proctable[GD_MGMT_CLUSTER_UNLOCK]; if (proc->fn) { ret = proc->fn (NULL, this, NULL); + if (ret) + goto out; } - // TODO: if pending_count = 0, inject ALL_ACC here + if (!opinfo.pending_count) + ret = glusterd_op_sm_inject_all_acc (); + +out: gf_log ("", GF_LOG_DEBUG, "Returning with %d", ret); return ret; @@ -568,9 +503,14 @@ glusterd_op_ac_send_stage_op (glusterd_op_sm_event_t *event, void *ctx) GF_ASSERT (proc); if (proc->fn) { ret = proc->fn (NULL, this, NULL); + if (ret) + goto out; } - // TODO: if pending_count = 0, inject ALL_ACC here + if (!opinfo.pending_count) + ret = glusterd_op_sm_inject_all_acc (); + +out: gf_log ("", GF_LOG_DEBUG, "Returning with %d", ret); return ret; @@ -595,9 +535,14 @@ glusterd_op_ac_send_commit_op (glusterd_op_sm_event_t *event, void *ctx) GF_ASSERT (proc); if (proc->fn) { ret = proc->fn (NULL, this, NULL); + if (!ret) + goto out; } - // TODO: if pending_count = 0, inject ALL_ACC here + if (!opinfo.pending_count) + ret = glusterd_op_sm_inject_all_acc (); + +out: gf_log ("", GF_LOG_DEBUG, "Returning with %d", ret); return ret; @@ -624,9 +569,9 @@ glusterd_op_ac_rcvd_stage_op_acc (glusterd_op_sm_event_t *event, void *ctx) ret = glusterd_op_sm_inject_event (new_event); +out: gf_log ("", GF_LOG_DEBUG, "Returning %d", ret); -out: return ret; } @@ -704,16 +649,12 @@ glusterd_op_ac_stage_op (glusterd_op_sm_event_t *event, void *ctx) stage_ctx = ctx; - req = stage_ctx->stage_req; + req = &stage_ctx->stage_req; - switch (req->op) { - case GD_OP_CREATE_VOLUME: - status = glusterd_op_stage_create_volume (req); - break; + status = glusterd_op_stage_validate (req); - default: - gf_log ("", GF_LOG_ERROR, "Unknown op %d", - req->op); + if (status) { + gf_log ("", GF_LOG_ERROR, "Validate failed: %d", status); } ret = glusterd_op_stage_send_resp (stage_ctx->req, req->op, status); @@ -735,16 +676,12 @@ glusterd_op_ac_commit_op (glusterd_op_sm_event_t *event, void *ctx) commit_ctx = ctx; - req = commit_ctx->stage_req; + req = &commit_ctx->stage_req; - switch (req->op) { - case GD_OP_CREATE_VOLUME: - ret = glusterd_op_create_volume (req); - break; + status = glusterd_op_commit_perform (req); - default: - gf_log ("", GF_LOG_ERROR, "Unknown op %d", - req->op); + if (status) { + gf_log ("", GF_LOG_ERROR, "Commit failed: %d", status); } ret = glusterd_op_commit_send_resp (commit_ctx->req, req->op, status); @@ -771,7 +708,50 @@ glusterd_op_sm_transition_state (glusterd_op_info_t *opinfo, return 0; } +int32_t +glusterd_op_stage_validate (gd1_mgmt_stage_op_req *req) +{ + int ret = -1; + GF_ASSERT (req); + + switch (req->op) { + case GD_OP_CREATE_VOLUME: + ret = glusterd_op_stage_create_volume (req); + break; + + default: + gf_log ("", GF_LOG_ERROR, "Unknown op %d", + req->op); + } + + gf_log ("", GF_LOG_DEBUG, "Returning %d", ret); + + return ret; +} + + +int32_t +glusterd_op_commit_perform (gd1_mgmt_stage_op_req *req) +{ + int ret = -1; + + GF_ASSERT (req); + + switch (req->op) { + case GD_OP_CREATE_VOLUME: + ret = glusterd_op_create_volume (req); + break; + + default: + gf_log ("", GF_LOG_ERROR, "Unknown op %d", + req->op); + } + + gf_log ("", GF_LOG_DEBUG, "Returning %d", ret); + + return ret; +} glusterd_op_sm_t glusterd_op_state_default [] = { {GD_OP_STATE_DEFAULT, glusterd_op_ac_none}, //EVENT_NONE @@ -853,7 +833,7 @@ glusterd_op_sm_t glusterd_op_state_commit_op_sent [] = { {GD_OP_STATE_COMMIT_OP_SENT, glusterd_op_ac_none},//EVENT_START_LOCK {GD_OP_STATE_COMMIT_OP_SENT, glusterd_op_ac_none}, //EVENT_LOCK {GD_OP_STATE_COMMIT_OP_SENT, glusterd_op_ac_rcvd_commit_op_acc}, //EVENT_RCVD_ACC - {GD_OP_STATE_UNLOCK_SENT, glusterd_op_ac_commit_op}, //EVENT_ALL_ACC + {GD_OP_STATE_UNLOCK_SENT, glusterd_op_ac_send_unlock}, //EVENT_ALL_ACC {GD_OP_STATE_COMMIT_OP_SENT, glusterd_op_ac_none}, //EVENT_STAGE_ACC {GD_OP_STATE_UNLOCK_SENT, glusterd_op_ac_send_unlock}, //EVENT_COMMIT_ACC {GD_OP_STATE_COMMIT_OP_SENT, glusterd_op_ac_commit_error}, //EVENT_RCVD_RJT @@ -1009,6 +989,32 @@ glusterd_op_set_op (glusterd_op_t op) } +int32_t +glusterd_op_clear_pending_op (glusterd_op_t op) +{ + + GF_ASSERT (op < GD_OP_MAX); + GF_ASSERT (op > GD_OP_NONE); + + opinfo.pending_op[op] = 0; + + return 0; + +} + +int32_t +glusterd_op_clear_commit_op (glusterd_op_t op) +{ + + GF_ASSERT (op < GD_OP_MAX); + GF_ASSERT (op > GD_OP_NONE); + + opinfo.commit_op[op] = 0; + + return 0; + +} + int32_t glusterd_op_set_ctx (glusterd_op_t op, void *ctx) { diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.h b/xlators/mgmt/glusterd/src/glusterd-op-sm.h index 61bdc8885..e080acee7 100644 --- a/xlators/mgmt/glusterd/src/glusterd-op-sm.h +++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.h @@ -133,12 +133,17 @@ typedef struct glusterd_op_lock_ctx_ glusterd_op_lock_ctx_t; struct glusterd_op_stage_ctx_ { rpcsvc_request_t *req; - void *stage_req; + gd1_mgmt_stage_op_req stage_req; }; typedef struct glusterd_op_stage_ctx_ glusterd_op_stage_ctx_t; -typedef glusterd_op_stage_ctx_t glusterd_op_commit_ctx_t; +struct glusterd_op_commit_ctx_ { + rpcsvc_request_t *req; + gd1_mgmt_stage_op_req stage_req; +}; + +typedef struct glusterd_op_commit_ctx_ glusterd_op_commit_ctx_t; int glusterd_op_sm_new_event (glusterd_op_sm_event_type_t event_type, @@ -158,9 +163,20 @@ glusterd_op_set_ctx (glusterd_op_t op, void *ctx); int32_t glusterd_op_set_op (glusterd_op_t op); -int +int32_t +glusterd_op_clear_pending_op (glusterd_op_t op); + +int32_t +glusterd_op_clear_commit_op (glusterd_op_t op); + +int glusterd_op_build_payload (glusterd_op_t op, gd1_mgmt_stage_op_req **req); +int32_t +glusterd_op_stage_validate (gd1_mgmt_stage_op_req *req); + +int32_t +glusterd_op_commit_perform (gd1_mgmt_stage_op_req *req); void * glusterd_op_get_ctx (glusterd_op_t op); diff --git a/xlators/mgmt/glusterd/src/glusterd-sm.c b/xlators/mgmt/glusterd/src/glusterd-sm.c index b55fdd567..ba9c75872 100644 --- a/xlators/mgmt/glusterd/src/glusterd-sm.c +++ b/xlators/mgmt/glusterd/src/glusterd-sm.c @@ -430,9 +430,9 @@ glusterd_sm_t *glusterd_friend_state_table [] = { glusterd_state_req_sent, glusterd_state_req_rcvd, glusterd_state_befriended, + glusterd_state_req_accepted, glusterd_state_req_sent_rcvd, glusterd_state_rejected, - glusterd_state_req_accepted, glusterd_state_unfriend_sent, }; @@ -481,54 +481,56 @@ glusterd_friend_sm () glusterd_peerinfo_t *peerinfo = NULL; glusterd_friend_sm_event_type_t event_type = 0; - list_for_each_entry_safe (event, tmp, &gd_friend_sm_queue, list) { - - list_del_init (&event->list); - peerinfo = event->peerinfo; - event_type = event->event; - - if (!peerinfo && - (GD_FRIEND_EVENT_PROBE == event_type || - GD_FRIEND_EVENT_RCVD_FRIEND_REQ == event_type)) { - ret = glusterd_friend_add (NULL, - GD_FRIEND_STATE_DEFAULT, - NULL, NULL, &peerinfo); - - if (ret) { - gf_log ("glusterd", GF_LOG_ERROR, "Unable to add peer, " - "ret = %d", ret); - continue; + while (!list_empty (&gd_friend_sm_queue)) { + list_for_each_entry_safe (event, tmp, &gd_friend_sm_queue, list) { + + list_del_init (&event->list); + peerinfo = event->peerinfo; + event_type = event->event; + + if (!peerinfo && + (GD_FRIEND_EVENT_PROBE == event_type || + GD_FRIEND_EVENT_RCVD_FRIEND_REQ == event_type)) { + ret = glusterd_friend_add (NULL, + GD_FRIEND_STATE_DEFAULT, + NULL, NULL, &peerinfo); + + if (ret) { + gf_log ("glusterd", GF_LOG_ERROR, "Unable to add peer, " + "ret = %d", ret); + continue; + } + GF_ASSERT (peerinfo); + event->peerinfo = peerinfo; } - GF_ASSERT (peerinfo); - event->peerinfo = peerinfo; - } - state = glusterd_friend_state_table[peerinfo->state.state]; + state = glusterd_friend_state_table[peerinfo->state.state]; - GF_ASSERT (state); + GF_ASSERT (state); - handler = state[event_type].handler; - GF_ASSERT (handler); + handler = state[event_type].handler; + GF_ASSERT (handler); - ret = handler (event, event->ctx); + ret = handler (event, event->ctx); - if (ret) { - gf_log ("glusterd", GF_LOG_ERROR, "handler returned: " - "%d", ret); - return ret; - } + if (ret) { + gf_log ("glusterd", GF_LOG_ERROR, "handler returned: " + "%d", ret); + return ret; + } - ret = glusterd_friend_sm_transition_state (peerinfo, state, event_type); + ret = glusterd_friend_sm_transition_state (peerinfo, state, event_type); - if (ret) { - gf_log ("glusterd", GF_LOG_ERROR, "Unable to transition" - "state from %d to %d", peerinfo->state.state, - state[event_type].next_state); - return ret; - } + if (ret) { + gf_log ("glusterd", GF_LOG_ERROR, "Unable to transition" + "state from %d to %d", peerinfo->state.state, + state[event_type].next_state); + return ret; + } - GF_FREE (event); + GF_FREE (event); + } } diff --git a/xlators/mgmt/glusterd/src/glusterd.c b/xlators/mgmt/glusterd/src/glusterd.c index 7ce466a64..436a8d4e1 100644 --- a/xlators/mgmt/glusterd/src/glusterd.c +++ b/xlators/mgmt/glusterd/src/glusterd.c @@ -170,6 +170,7 @@ init (xlator_t *this) struct stat buf = {0,}; char *port_str = NULL; int port_num = 0; + char voldir [PATH_MAX]; dir_data = dict_get (this->options, "working-directory"); @@ -210,6 +211,15 @@ init (xlator_t *this) gf_log (this->name, GF_LOG_NORMAL, "Using %s as working directory", dirname); + snprintf (voldir, PATH_MAX, "%s/vols", dirname); + + ret = mkdir (voldir, 0644); + + if (-1 == ret) { + gf_log (this->name, GF_LOG_CRITICAL, + "Unable to create volume directory %s" + " ,errno = %d", voldir, errno); + } rpc = rpcsvc_init (this->ctx, this->options); if (rpc == NULL) { diff --git a/xlators/mgmt/glusterd/src/glusterd.h b/xlators/mgmt/glusterd/src/glusterd.h index 48fe0fc66..dcc2cd0fd 100644 --- a/xlators/mgmt/glusterd/src/glusterd.h +++ b/xlators/mgmt/glusterd/src/glusterd.h @@ -42,24 +42,6 @@ #include "glusterd1.h" -/*typedef struct glusterd_peer_state_info_ { - glusterd_friend_sm_state_t state; - struct timeval transition_time; -}glusterd_peer_state_info_t; - - -struct glusterd_peerinfo_ { - uuid_t uuid; - glusterd_peer_state_info_t state; - char *hostname; - int port; - struct list_head uuid_list; - struct list_head op_peers_list; - struct rpc_clnt *rpc; -}; - -typedef struct glusterd_peerinfo_ glusterd_peerinfo_t; -*/ typedef struct { struct _volfile_ctx *volfile; @@ -99,21 +81,12 @@ typedef struct glusterd_volinfo_ glusterd_volinfo_t; typedef ssize_t (*gd_serialize_t) (struct iovec outmsg, void *args); -//void glusterd_init (int); - +#define GLUSTERD_GET_VOLUME_DIR(path, volinfo, priv) \ + snprintf (path, PATH_MAX, "%s/vols/%s", priv->workdir,\ + volinfo->volname); int glusterd_probe_begin (rpcsvc_request_t *req, const char *hoststr); -/*int -glusterd_interpret (xlator_t *this, transport_t *trans, - char *hdr_p, size_t hdrlen, struct iobuf *iobuf); - - -int -glusterd_friend_probe (const char *hoststr); -*/ - - int glusterd_xfer_friend_add_resp (rpcsvc_request_t *req, char *hostname); @@ -126,17 +99,7 @@ glusterd_friend_add (const char *hoststr, glusterd_friend_sm_state_t state, uuid_t *uuid, struct rpc_clnt *rpc, glusterd_peerinfo_t **friend); -/* -int -glusterd_xfer_friend_req_msg (glusterd_peerinfo_t *peerinfo, xlator_t *this); -int -glusterd_xfer_cluster_lock_req (xlator_t *this, int32_t *lock_count); -*/ - -/*int -glusterd_xfer_cluster_unlock_req (xlator_t *this, int32_t *unlock_count); -*/ int glusterd_op_lock_send_resp (rpcsvc_request_t *req, int32_t status); diff --git a/xlators/mgmt/glusterd/src/glusterd3_1-mops.c b/xlators/mgmt/glusterd/src/glusterd3_1-mops.c index 1bd33ad1e..5c2bcf250 100644 --- a/xlators/mgmt/glusterd/src/glusterd3_1-mops.c +++ b/xlators/mgmt/glusterd/src/glusterd3_1-mops.c @@ -65,7 +65,7 @@ glusterd3_1_probe_cbk (struct rpc_req *req, struct iovec *iov, goto out; } - ret = gd_xdr_to_mgmt_probe_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_probe_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); //rsp.op_ret = -1; @@ -146,7 +146,7 @@ glusterd3_1_friend_add_cbk (struct rpc_req * req, struct iovec *iov, rsp.op_errno = EINVAL; } - ret = gd_xdr_to_mgmt_friend_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_friend_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); rsp.op_ret = -1; @@ -229,7 +229,7 @@ glusterd3_1_friend_remove_cbk (struct rpc_req * req, struct iovec *iov, goto respond; } - ret = gd_xdr_to_mgmt_friend_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_friend_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); rsp.op_ret = -1; @@ -306,7 +306,7 @@ glusterd3_1_cluster_lock_cbk (struct rpc_req *req, struct iovec *iov, rsp.op_errno = EINVAL; } - ret = gd_xdr_to_mgmt_cluster_lock_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_cluster_lock_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); rsp.op_ret = -1; @@ -374,7 +374,7 @@ glusterd3_1_cluster_unlock_cbk (struct rpc_req *req, struct iovec *iov, rsp.op_errno = EINVAL; } - ret = gd_xdr_to_mgmt_cluster_unlock_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_cluster_unlock_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); rsp.op_ret = -1; @@ -442,7 +442,7 @@ glusterd3_1_stage_op_cbk (struct rpc_req *req, struct iovec *iov, rsp.op_errno = EINVAL; } - ret = gd_xdr_to_mgmt_stage_op_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_stage_op_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); rsp.op_ret = -1; @@ -510,7 +510,7 @@ glusterd3_1_commit_op_cbk (struct rpc_req *req, struct iovec *iov, rsp.op_errno = EINVAL; } - ret = gd_xdr_to_mgmt_commit_op_req (*iov, &rsp); + ret = gd_xdr_to_mgmt_commit_op_rsp (*iov, &rsp); if (ret < 0) { gf_log ("", GF_LOG_ERROR, "error"); rsp.op_ret = -1; @@ -826,12 +826,21 @@ glusterd3_1_stage_op (call_frame_t *frame, xlator_t *this, return ret; } + glusterd_op_clear_pending_op (i); + ret = glusterd_op_build_payload (i, &req); if (ret) goto out; + ret = glusterd_op_stage_validate (req); + + if (ret) { + gf_log ("", GF_LOG_ERROR, "Staging failed"); + goto out; + } + list_for_each_entry (peerinfo, &priv->peers, uuid_list) { GF_ASSERT (peerinfo); @@ -885,7 +894,7 @@ glusterd3_1_commit_op (call_frame_t *frame, xlator_t *this, GF_ASSERT (priv); for ( i = GD_OP_NONE; i < GD_OP_MAX; i++) { - if (opinfo.pending_op[i]) + if (opinfo.commit_op[i]) break; } @@ -906,12 +915,20 @@ glusterd3_1_commit_op (call_frame_t *frame, xlator_t *this, return ret; } + glusterd_op_clear_commit_op (i); ret = glusterd_op_build_payload (i, (gd1_mgmt_stage_op_req **)&req); if (ret) goto out; + ret = glusterd_op_commit_perform ((gd1_mgmt_stage_op_req *)req); + + if (ret) { + gf_log ("", GF_LOG_ERROR, "Commit failed"); + goto out; + } + list_for_each_entry (peerinfo, &priv->peers, uuid_list) { GF_ASSERT (peerinfo); -- cgit