From 6689104ce7eed29c7878c124fa13caecaa1245ef Mon Sep 17 00:00:00 2001 From: Pranith K Date: Wed, 29 Sep 2010 03:59:19 +0000 Subject: mgmt/glusterd: volume start force Signed-off-by: Pranith Kumar K Signed-off-by: Vijay Bellur BUG: 1736 (implement volume start force) URL: http://bugs.gluster.com/cgi-bin/bugzilla3/show_bug.cgi?id=1736 --- cli/src/cli-cmd-volume.c | 33 ++-- cli/src/cli.h | 1 + cli/src/cli3_1-cops.c | 10 +- rpc/xdr/src/cli1-xdr.c | 4 +- rpc/xdr/src/cli1-xdr.h | 1 + rpc/xdr/src/cli1.x | 1 + xlators/mgmt/glusterd/src/glusterd-handler.c | 46 ++--- xlators/mgmt/glusterd/src/glusterd-op-sm.c | 258 ++++++++++----------------- xlators/mgmt/glusterd/src/glusterd-op-sm.h | 26 +-- xlators/mgmt/glusterd/src/glusterd-pmap.c | 2 +- xlators/mgmt/glusterd/src/glusterd-utils.c | 174 ++++++++++++++---- xlators/mgmt/glusterd/src/glusterd-utils.h | 12 +- xlators/mgmt/glusterd/src/glusterd-volgen.c | 4 +- xlators/mgmt/glusterd/src/glusterd.c | 2 +- xlators/mgmt/glusterd/src/glusterd.h | 34 +++- 15 files changed, 317 insertions(+), 291 deletions(-) diff --git a/cli/src/cli-cmd-volume.c b/cli/src/cli-cmd-volume.c index c7a027a187c..8d846d8732c 100644 --- a/cli/src/cli-cmd-volume.c +++ b/cli/src/cli-cmd-volume.c @@ -44,7 +44,7 @@ cli_cmd_volume_help_cbk (struct cli_state *state, struct cli_cmd_word *in_word, void cli_cmd_volume_start_usage () { - cli_out ("Usage: volume start "); + cli_out ("Usage: volume start [force]"); } void @@ -71,11 +71,12 @@ cli_cmd_volume_info_usage () cli_out ("Usage: volume info [all|]"); } -void +void cli_cmd_volume_set_usage () { cli_out ("Usage: volume set "); } + int cli_cmd_volume_info_cbk (struct cli_state *state, struct cli_cmd_word *word, const char **words, int wordcount) @@ -252,7 +253,6 @@ out: return ret; } - int cli_cmd_volume_start_cbk (struct cli_state *state, struct cli_cmd_word *word, const char **words, int wordcount) @@ -260,29 +260,40 @@ cli_cmd_volume_start_cbk (struct cli_state *state, struct cli_cmd_word *word, int ret = -1; rpc_clnt_procedure_t *proc = NULL; call_frame_t *frame = NULL; - char *volname = NULL; - + gf1_cli_start_vol_req req = {0,}; frame = create_frame (THIS, THIS->ctx->pool); if (!frame) goto out; - if (wordcount != 3) { + if (wordcount < 3 || wordcount > 4) { cli_cmd_volume_start_usage (); goto out; } - volname = (char *)words[2]; + req.volname = (char *)words[2]; + if (!req.volname) + goto out; + + if (wordcount == 4) { + if (!strcmp("force", words[3])) { + req.flags |= GF_CLI_FLAG_OP_FORCE; + } else { + ret = -1; + cli_cmd_volume_start_usage (); + goto out; + } + } proc = &cli_rpc_prog->proctable[GF1_CLI_START_VOLUME]; if (proc->fn) { - ret = proc->fn (frame, THIS, volname); + ret = proc->fn (frame, THIS, &req); } out: - if (!proc && ret && volname) - cli_out ("Starting Volume %s failed", volname); + if (!proc && ret && req.volname) + cli_out ("Starting Volume %s failed", req.volname); return ret; } @@ -812,7 +823,7 @@ struct cli_cmd volume_cmds[] = { cli_cmd_volume_delete_cbk, "delete volume specified by "}, - { "volume start ", + { "volume start [force]", cli_cmd_volume_start_cbk, "start volume specified by "}, diff --git a/cli/src/cli.h b/cli/src/cli.h index b8aa985b8ce..216b743fdd1 100644 --- a/cli/src/cli.h +++ b/cli/src/cli.h @@ -111,6 +111,7 @@ struct cli_local { struct { char *volname; + int flags; } start_vol; struct { diff --git a/cli/src/cli3_1-cops.c b/cli/src/cli3_1-cops.c index 0984a793694..2c64f115e23 100644 --- a/cli/src/cli3_1-cops.c +++ b/cli/src/cli3_1-cops.c @@ -1409,7 +1409,7 @@ int32_t gf_cli3_1_start_volume (call_frame_t *frame, xlator_t *this, void *data) { - gf1_cli_start_vol_req req = {0,}; + gf1_cli_start_vol_req *req = NULL; int ret = 0; cli_local_t *local = NULL; @@ -1418,16 +1418,16 @@ gf_cli3_1_start_volume (call_frame_t *frame, xlator_t *this, goto out; } + req = data; local = cli_local_get (); if (local) { - local->u.start_vol.volname = data; + local->u.start_vol.volname = req->volname; + local->u.start_vol.flags = req->flags; frame->local = local; } - req.volname = data; - - ret = cli_cmd_submit (&req, frame, cli_rpc_prog, + ret = cli_cmd_submit (req, frame, cli_rpc_prog, GD_MGMT_CLI_START_VOLUME, NULL, gf_xdr_from_cli_start_vol_req, this, gf_cli3_1_start_volume_cbk); diff --git a/rpc/xdr/src/cli1-xdr.c b/rpc/xdr/src/cli1-xdr.c index ca2bc09f3a4..cdf7be28d84 100644 --- a/rpc/xdr/src/cli1-xdr.c +++ b/rpc/xdr/src/cli1-xdr.c @@ -93,9 +93,9 @@ xdr_gf1_cli_probe_req (XDR *xdrs, gf1_cli_probe_req *objp) bool_t xdr_gf1_cli_probe_rsp (XDR *xdrs, gf1_cli_probe_rsp *objp) { - register int32_t *buf; + if (xdrs->x_op == XDR_ENCODE) { buf = XDR_INLINE (xdrs, 3 * BYTES_PER_XDR_UNIT); if (buf == NULL) { @@ -275,6 +275,8 @@ xdr_gf1_cli_start_vol_req (XDR *xdrs, gf1_cli_start_vol_req *objp) if (!xdr_string (xdrs, &objp->volname, ~0)) return FALSE; + if (!xdr_int (xdrs, &objp->flags)) + return FALSE; return TRUE; } diff --git a/rpc/xdr/src/cli1-xdr.h b/rpc/xdr/src/cli1-xdr.h index 0225acefe2f..9988d54f9c5 100644 --- a/rpc/xdr/src/cli1-xdr.h +++ b/rpc/xdr/src/cli1-xdr.h @@ -171,6 +171,7 @@ typedef struct gf1_cli_delete_vol_rsp gf1_cli_delete_vol_rsp; struct gf1_cli_start_vol_req { char *volname; + int flags; }; typedef struct gf1_cli_start_vol_req gf1_cli_start_vol_req; diff --git a/rpc/xdr/src/cli1.x b/rpc/xdr/src/cli1.x index ba4288be535..31a996861c8 100644 --- a/rpc/xdr/src/cli1.x +++ b/rpc/xdr/src/cli1.x @@ -102,6 +102,7 @@ struct gf1_cli_get_vol_rsp { struct gf1_cli_start_vol_req { string volname<>; + int flags; } ; diff --git a/xlators/mgmt/glusterd/src/glusterd-handler.c b/xlators/mgmt/glusterd/src/glusterd-handler.c index cfd40ed0da3..f66a5b3d28c 100644 --- a/xlators/mgmt/glusterd/src/glusterd-handler.c +++ b/xlators/mgmt/glusterd/src/glusterd-handler.c @@ -54,6 +54,12 @@ #include "defaults.c" #include "common-utils.h" +#define glusterd_start_volume(req, volname, flags) \ + glusterd_volume_txn (req, volname, flags, GD_OP_START_VOLUME) + +#define glusterd_stop_volume(req, volname, flags) \ + glusterd_volume_txn (req, volname, flags, GD_OP_STOP_VOLUME) + static int glusterd_friend_find_by_uuid (uuid_t uuid, glusterd_peerinfo_t **peerinfo) @@ -1281,7 +1287,6 @@ glusterd_handle_cli_start_volume (rpcsvc_request_t *req) { int32_t ret = -1; gf1_cli_start_vol_req cli_req = {0,}; - int32_t flags = 0; GF_ASSERT (req); @@ -1294,7 +1299,7 @@ glusterd_handle_cli_start_volume (rpcsvc_request_t *req) gf_log ("glusterd", GF_LOG_NORMAL, "Received start vol req" "for volume %s", cli_req.volname); - ret = glusterd_start_volume (req, cli_req.volname, flags); + ret = glusterd_start_volume (req, cli_req.volname, cli_req.flags); gf_cmd_log ("volume start","on volname: %s %s", cli_req.volname, ((ret == 0) ? "SUCCESS": "FAILED")); @@ -2980,35 +2985,8 @@ out: } int32_t -glusterd_start_volume (rpcsvc_request_t *req, char *volname, int flags) -{ - int32_t ret = -1; - glusterd_op_start_volume_ctx_t *ctx = NULL; - - GF_ASSERT (req); - GF_ASSERT (volname); - - ctx = GF_CALLOC (1, sizeof (*ctx), gf_gld_mt_start_volume_ctx_t); - - if (!ctx) - goto out; - - strncpy (ctx->volume_name, volname, GD_VOLUME_NAME_MAX); - - glusterd_op_set_op (GD_OP_START_VOLUME); - - glusterd_op_set_ctx (GD_OP_START_VOLUME, ctx); - glusterd_op_set_ctx_free (GD_OP_START_VOLUME, _gf_true); - glusterd_op_set_req (req); - - ret = glusterd_op_txn_begin (); - -out: - return ret; -} - -int32_t -glusterd_stop_volume (rpcsvc_request_t *req, char *volname, int flags) +glusterd_volume_txn (rpcsvc_request_t *req, char *volname, int flags, + glusterd_op_t op) { int32_t ret = -1; dict_t *ctx = NULL; @@ -3034,10 +3012,10 @@ glusterd_stop_volume (rpcsvc_request_t *req, char *volname, int flags) if (ret) goto out; - glusterd_op_set_op (GD_OP_STOP_VOLUME); + glusterd_op_set_op (op); - glusterd_op_set_ctx (GD_OP_STOP_VOLUME, ctx); - glusterd_op_set_ctx_free (GD_OP_STOP_VOLUME, _gf_true); + glusterd_op_set_ctx (op, ctx); + glusterd_op_set_ctx_free (op, _gf_true); glusterd_op_set_req (req); ret = glusterd_op_txn_begin (); diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.c b/xlators/mgmt/glusterd/src/glusterd-op-sm.c index fae89f7dd18..e5cf57514db 100644 --- a/xlators/mgmt/glusterd/src/glusterd-op-sm.c +++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.c @@ -50,6 +50,9 @@ #include #include +#define glusterd_op_start_volume_args_get(req, dict, volname, flags) \ + glusterd_op_stop_volume_args_get (req, dict, volname, flags) + static struct list_head gd_op_sm_queue; pthread_mutex_t gd_op_sm_lock; glusterd_op_info_t opinfo = {{0},}; @@ -224,16 +227,6 @@ glusterd_op_build_payload (glusterd_op_t op, gd1_mgmt_stage_op_req **req) } break; - case GD_OP_START_VOLUME: - { - glusterd_op_start_volume_ctx_t *ctx1 = ctx; - stage_req->buf.buf_len = - strlen (ctx1->volume_name); - stage_req->buf.buf_val = - gf_strdup (ctx1->volume_name); - } - break; - case GD_OP_DELETE_VOLUME: { glusterd_op_delete_volume_ctx_t *ctx1 = ctx; @@ -244,6 +237,7 @@ glusterd_op_build_payload (glusterd_op_t op, gd1_mgmt_stage_op_req **req) } break; + case GD_OP_START_VOLUME: case GD_OP_STOP_VOLUME: case GD_OP_ADD_BRICK: case GD_OP_REPLACE_BRICK: @@ -412,11 +406,45 @@ out: return ret; } +static int +glusterd_op_stop_volume_args_get (gd1_mgmt_stage_op_req *req, + dict_t *dict, char** volname, + int *flags) +{ + int ret = -1; + + if (!req || !dict || !volname || !flags) + goto out; + + ret = dict_unserialize (req->buf.buf_val, req->buf.buf_len, &dict); + + if (ret) { + gf_log ("", GF_LOG_ERROR, "Unable to unserialize dict"); + goto out; + } + + ret = dict_get_str (dict, "volname", volname); + if (ret) { + gf_log ("", GF_LOG_ERROR, "Unable to get volume name"); + goto out; + } + + ret = dict_get_int32 (dict, "flags", flags); + if (ret) { + gf_log ("", GF_LOG_ERROR, "Unable to get flags"); + goto out; + } +out: + return ret; +} + static int glusterd_op_stage_start_volume (gd1_mgmt_stage_op_req *req, char **op_errstr) { int ret = 0; - char volname [1024] = {0,}; + dict_t *dict = NULL; + char *volname = NULL; + int flags = 0; gf_boolean_t exists = _gf_false; glusterd_volinfo_t *volinfo = NULL; glusterd_brickinfo_t *brickinfo = NULL; @@ -434,8 +462,13 @@ glusterd_op_stage_start_volume (gd1_mgmt_stage_op_req *req, char **op_errstr) goto out; } - strncpy (volname, req->buf.buf_val, req->buf.buf_len); - //volname = req->buf.buf_val; + dict = dict_new (); + if (!dict) + goto out; + + ret = glusterd_op_start_volume_args_get (req, dict, &volname, &flags); + if (ret) + goto out; exists = glusterd_check_volume_exists (volname); @@ -476,52 +509,29 @@ glusterd_op_stage_start_volume (gd1_mgmt_stage_op_req *req, char **op_errstr) } } - if (GLUSTERD_STATUS_STARTED == volinfo->status) { - snprintf (msg, 2048, "Volume %s already started", - volname); - gf_log ("glusterd", GF_LOG_ERROR, - "%s", msg); - *op_errstr = gf_strdup (msg); - ret = -1; + if (!(flags & GF_CLI_FLAG_OP_FORCE)) { + ret = glusterd_is_volume_started (volinfo); + if (!ret) { + snprintf (msg, 2048, "Volume %s already started", + volname); + gf_log ("glusterd", GF_LOG_ERROR, + "%s", msg); + *op_errstr = gf_strdup (msg); + ret = -1; + goto out; + } } } + + ret = 0; out: + if (dict) + dict_unref (dict); gf_log ("", GF_LOG_DEBUG, "Returning %d", ret); return ret; } -static int -glusterd_op_stop_volume_args_get (gd1_mgmt_stage_op_req *req, - dict_t *dict, char** volname, - int *flags) -{ - int ret = -1; - - if (!req || !dict || !volname || !flags) - goto out; - - ret = dict_unserialize (req->buf.buf_val, req->buf.buf_len, &dict); - - if (ret) { - gf_log ("", GF_LOG_ERROR, "Unable to unserialize dict"); - goto out; - } - - ret = dict_get_str (dict, "volname", volname); - if (ret) { - gf_log ("", GF_LOG_ERROR, "Unable to get volume name"); - goto out; - } - - ret = dict_get_int32 (dict, "flags", flags); - if (ret) { - gf_log ("", GF_LOG_ERROR, "Unable to get flags"); - goto out; - } -out: - return ret; -} static int glusterd_op_stage_stop_volume (gd1_mgmt_stage_op_req *req) { @@ -1166,13 +1176,8 @@ glusterd_op_perform_remove_brick (glusterd_volinfo_t *volinfo, char *brick) if (ret) goto out; - if ((!uuid_compare (brickinfo->uuid, priv->uuid)) && - (GLUSTERD_STATUS_STARTED == volinfo->status)) { - gf_log ("", GF_LOG_NORMAL, "About to stop glusterfs" - " for brick %s:%s", brickinfo->hostname, - brickinfo->path); - ret = glusterd_volume_stop_glusterfs - (volinfo, brickinfo, 0); + if (GLUSTERD_STATUS_STARTED == volinfo->status) { + ret = glusterd_brick_stop (volinfo, brickinfo); if (ret) { gf_log ("", GF_LOG_ERROR, "Unable to stop " "glusterfs, ret: %d", ret); @@ -1201,7 +1206,6 @@ glusterd_op_perform_add_bricks (glusterd_volinfo_t *volinfo, int32_t count, char *free_ptr1 = NULL; char *free_ptr2 = NULL; char *saveptr = NULL; - gf_boolean_t glfs_started = _gf_false; int32_t ret = -1; glusterd_conf_t *priv = NULL; @@ -1237,42 +1241,25 @@ glusterd_op_perform_add_bricks (glusterd_volinfo_t *volinfo, int32_t count, if (count) brick = strtok_r (brick_list+1, " \n", &saveptr); + ret = glusterd_create_volfiles (volinfo); + if (ret) + goto out; + while (i <= count) { ret = glusterd_brickinfo_get (brick, volinfo, &brickinfo); if (ret) goto out; - ret = glusterd_resolve_brick (brickinfo); - - if (!ret && (!uuid_compare (brickinfo->uuid, priv->uuid)) && - (GLUSTERD_STATUS_STARTED == volinfo->status)) { - ret = glusterd_create_volfiles (volinfo); + if (GLUSTERD_STATUS_STARTED == volinfo->status) { + ret = glusterd_brick_start (volinfo, brickinfo); if (ret) goto out; - - gf_log ("", GF_LOG_NORMAL, "About to start glusterfs" - " for brick %s:%s", brickinfo->hostname, - brickinfo->path); - ret = glusterd_volume_start_glusterfs - (volinfo, brickinfo, 0); - if (ret) { - gf_log ("", GF_LOG_ERROR, "Unable to start " - "glusterfs, ret: %d", ret); - goto out; - } - glfs_started = _gf_true; } i++; brick = strtok_r (NULL, " \n", &saveptr); } - if (!glfs_started) { - ret = glusterd_create_volfiles (volinfo); - if (ret) - goto out; - } - volinfo->brick_count += count; out: @@ -1717,8 +1704,7 @@ rb_src_brick_restart (glusterd_volinfo_t *volinfo, gf_log ("", GF_LOG_DEBUG, "Attempting to kill src"); - ret = glusterd_volume_stop_glusterfs - (volinfo, src_brickinfo, 0); + ret = glusterd_volume_stop_glusterfs (volinfo, src_brickinfo); if (ret) { gf_log ("", GF_LOG_ERROR, "Unable to stop " "glusterfs, ret: %d", ret); @@ -1745,8 +1731,7 @@ rb_src_brick_restart (glusterd_volinfo_t *volinfo, } sleep (2); - ret = glusterd_volume_start_glusterfs - (volinfo, src_brickinfo, 0); + ret = glusterd_volume_start_glusterfs (volinfo, src_brickinfo); if (ret) { gf_log ("", GF_LOG_ERROR, "Unable to start " "glusterfs, ret: %d", ret); @@ -2833,9 +2818,7 @@ glusterd_op_remove_brick (gd1_mgmt_stage_op_req *req) int ret = -1; dict_t *dict = NULL; char *volname = NULL; - glusterd_conf_t *priv = NULL; glusterd_volinfo_t *volinfo = NULL; - xlator_t *this = NULL; char *brick = NULL; int32_t count = 0; int32_t i = 1; @@ -2843,12 +2826,6 @@ glusterd_op_remove_brick (gd1_mgmt_stage_op_req *req) GF_ASSERT (req); - this = THIS; - GF_ASSERT (this); - - priv = this->private; - GF_ASSERT (priv); - dict = dict_new (); if (!dict) goto out; @@ -2891,12 +2868,8 @@ glusterd_op_remove_brick (gd1_mgmt_stage_op_req *req) } ret = glusterd_op_perform_remove_brick (volinfo, brick); - if (ret) { - gf_log ("", GF_LOG_CRITICAL, "Unable to remove" - " brick: %s", brick); + if (ret) goto out; - } - i++; } @@ -2967,50 +2940,30 @@ static int glusterd_op_start_volume (gd1_mgmt_stage_op_req *req, char **op_errstr) { int ret = 0; - char volname[1024] = {0,}; + char *volname = NULL; + int flags = 0; glusterd_volinfo_t *volinfo = NULL; - glusterd_conf_t *priv = NULL; glusterd_brickinfo_t *brickinfo = NULL; - xlator_t *this = NULL; - int32_t mybrick = 0; + dict_t *dict = NULL; - this = THIS; - GF_ASSERT (this); - priv = this->private; - GF_ASSERT (priv); GF_ASSERT (req); - strncpy (volname, req->buf.buf_val, req->buf.buf_len); + dict = dict_new (); + if (!dict) + goto out; + + ret = glusterd_op_start_volume_args_get (req, dict, &volname, &flags); + if (ret) + goto out; ret = glusterd_volinfo_find (volname, &volinfo); if (ret) goto out; list_for_each_entry (brickinfo, &volinfo->bricks, brick_list) { - if (uuid_is_null (brickinfo->uuid)) { - ret = glusterd_resolve_brick (brickinfo); - if (ret) { - gf_log ("glusterd", GF_LOG_ERROR, - "cannot resolve brick: %s:%s", - brickinfo->hostname, brickinfo->path); - goto out; - } - - } - - if (!uuid_compare (brickinfo->uuid, priv->uuid)) { - gf_log ("", GF_LOG_NORMAL, "About to start glusterfs" - " for brick %s:%s", brickinfo->hostname, - brickinfo->path); - ret = glusterd_volume_start_glusterfs - (volinfo, brickinfo, mybrick); - if (ret) { - gf_log ("", GF_LOG_ERROR, "Unable to start " - "glusterfs, ret: %d", ret); - goto out; - } - mybrick++; - } + ret = glusterd_brick_start (volinfo, brickinfo); + if (ret) + goto out; } glusterd_set_volume_status (volinfo, GLUSTERD_STATUS_STARTED); @@ -3026,6 +2979,9 @@ glusterd_op_start_volume (gd1_mgmt_stage_op_req *req, char **op_errstr) ret = glusterd_check_generate_start_nfs (volinfo); out: + if (dict) + dict_unref (dict); + gf_log ("", GF_LOG_DEBUG, "returning %d ", ret); return ret; } @@ -3246,17 +3202,9 @@ glusterd_op_stop_volume (gd1_mgmt_stage_op_req *req) int ret = 0; int flags = 0; char *volname = NULL; - glusterd_conf_t *priv = NULL; glusterd_volinfo_t *volinfo = NULL; - xlator_t *this = NULL; dict_t *dict = NULL; glusterd_brickinfo_t *brickinfo = NULL; - int32_t mybrick = 0; - - this = THIS; - GF_ASSERT (this); - priv = this->private; - GF_ASSERT (priv); dict = dict_new (); if (!dict) @@ -3272,29 +3220,9 @@ glusterd_op_stop_volume (gd1_mgmt_stage_op_req *req) goto out; list_for_each_entry (brickinfo, &volinfo->bricks, brick_list) { - if (uuid_is_null (brickinfo->uuid)) { - ret = glusterd_resolve_brick (brickinfo); - if (ret) { - gf_log ("glusterd", GF_LOG_ERROR, - "cannot resolve brick: %s:%s", - brickinfo->hostname, brickinfo->path); - goto out; - } - - } - if (!uuid_compare (brickinfo->uuid, priv->uuid)) { - gf_log ("", GF_LOG_NORMAL, "About to stop glusterfs" - " for brick %s:%s", brickinfo->hostname, - brickinfo->path); - ret = glusterd_volume_stop_glusterfs - (volinfo, brickinfo, mybrick); - if (ret) { - gf_log ("", GF_LOG_ERROR, "Unable to stop " - "glusterfs, ret: %d", ret); - goto out; - } - mybrick++; - } + ret = glusterd_brick_stop (volinfo, brickinfo); + if (ret) + goto out; } glusterd_set_volume_status (volinfo, GLUSTERD_STATUS_STOPPED); @@ -3315,8 +3243,6 @@ glusterd_op_stop_volume (gd1_mgmt_stage_op_req *req) ret = glusterd_check_generate_start_nfs (volinfo); } out: - if (flags & GF_CLI_FLAG_OP_FORCE) - ret = 0; if (dict) dict_unref (dict); return ret; @@ -4794,10 +4720,10 @@ glusterd_op_free_ctx (glusterd_op_t op, void *ctx, gf_boolean_t ctx_free) case GD_OP_LOG_ROTATE: case GD_OP_SYNC_VOLUME: case GD_OP_SET_VOLUME: + case GD_OP_START_VOLUME: dict_unref (ctx); break; case GD_OP_DELETE_VOLUME: - case GD_OP_START_VOLUME: GF_FREE (ctx); break; default: diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.h b/xlators/mgmt/glusterd/src/glusterd-op-sm.h index c0b3249e9b5..04867da2ef3 100644 --- a/xlators/mgmt/glusterd/src/glusterd-op-sm.h +++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.h @@ -83,27 +83,6 @@ typedef struct glusterd_op_sm_ { glusterd_op_sm_ac_fn handler; } glusterd_op_sm_t; -typedef enum glusterd_op_ { - GD_OP_NONE = 0, - GD_OP_CREATE_VOLUME, - GD_OP_START_BRICK, - GD_OP_STOP_BRICK, - GD_OP_DELETE_VOLUME, - GD_OP_START_VOLUME, - GD_OP_STOP_VOLUME, - GD_OP_RENAME_VOLUME, - GD_OP_DEFRAG_VOLUME, - GD_OP_ADD_BRICK, - GD_OP_REMOVE_BRICK, - GD_OP_REPLACE_BRICK, - GD_OP_SET_VOLUME, - GD_OP_SYNC_VOLUME, - GD_OP_LOG_FILENAME, - GD_OP_LOG_LOCATE, - GD_OP_LOG_ROTATE, - GD_OP_MAX, -} glusterd_op_t; - typedef struct glusterd_op_sm_state_info_ { glusterd_op_sm_state_t state; struct timeval time; @@ -129,12 +108,11 @@ struct glusterd_op_info_ { typedef struct glusterd_op_info_ glusterd_op_info_t; -struct glusterd_op_start_volume_ctx_ { +struct glusterd_op_delete_volume_ctx_ { char volume_name[GD_VOLUME_NAME_MAX]; }; -typedef struct glusterd_op_start_volume_ctx_ glusterd_op_start_volume_ctx_t; -typedef struct glusterd_op_start_volume_ctx_ glusterd_op_delete_volume_ctx_t; +typedef struct glusterd_op_delete_volume_ctx_ glusterd_op_delete_volume_ctx_t; struct glusterd_op_log_filename_ctx_ { char volume_name[GD_VOLUME_NAME_MAX]; diff --git a/xlators/mgmt/glusterd/src/glusterd-pmap.c b/xlators/mgmt/glusterd/src/glusterd-pmap.c index cae9341f0db..3ea09aad965 100644 --- a/xlators/mgmt/glusterd/src/glusterd-pmap.c +++ b/xlators/mgmt/glusterd/src/glusterd-pmap.c @@ -419,7 +419,7 @@ gluster_pmap_signin (rpcsvc_request_t *req) ret = glusterd_get_brickinfo (THIS, args.brick, args.port, _gf_true, &brickinfo); if (!ret) - glusterd_set_brick_status (brickinfo, GF_BRICK_STARTED); + glusterd_set_brick_status (brickinfo, GF_BRICK_STARTED); fail: glusterd_submit_reply (req, &rsp, NULL, 0, NULL, diff --git a/xlators/mgmt/glusterd/src/glusterd-utils.c b/xlators/mgmt/glusterd/src/glusterd-utils.c index d1d45a75c9c..66e11fa7b30 100644 --- a/xlators/mgmt/glusterd/src/glusterd-utils.c +++ b/xlators/mgmt/glusterd/src/glusterd-utils.c @@ -816,8 +816,7 @@ out: int32_t glusterd_volume_start_glusterfs (glusterd_volinfo_t *volinfo, - glusterd_brickinfo_t *brickinfo, - int32_t count) + glusterd_brickinfo_t *brickinfo) { int32_t ret = -1; xlator_t *this = NULL; @@ -886,8 +885,7 @@ out: int32_t glusterd_volume_stop_glusterfs (glusterd_volinfo_t *volinfo, - glusterd_brickinfo_t *brickinfo, - int32_t count) + glusterd_brickinfo_t *brickinfo) { xlator_t *this = NULL; glusterd_conf_t *priv = NULL; @@ -1739,14 +1737,91 @@ out: } int -glusterd_restart_bricks (glusterd_conf_t *conf, xlator_t *this) +glusterd_brick_start (glusterd_volinfo_t *volinfo, + glusterd_brickinfo_t *brickinfo) +{ + int ret = -1; + xlator_t *this = NULL; + glusterd_conf_t *conf = NULL; + char path[PATH_MAX] = {0,}; + char pidfile[PATH_MAX] = {0,}; + struct stat stbuf = {0,}; + + if ((!brickinfo) || (!volinfo)) + goto out; + + this = THIS; + GF_ASSERT (this); + conf = this->private; + GF_ASSERT (conf); + + if (uuid_is_null (brickinfo->uuid)) { + ret = glusterd_resolve_brick (brickinfo); + if (ret) { + gf_log ("glusterd", GF_LOG_ERROR, + "cannot resolve brick: %s:%s", + brickinfo->hostname, brickinfo->path); + goto out; + } + } + + if (uuid_compare (brickinfo->uuid, conf->uuid)) { + ret = 0; + goto out; + } + + if (!glusterd_is_brick_started (brickinfo)) { + gf_log ("", GF_LOG_DEBUG, "brick: %s:%s, of volume: %s already" + " started", brickinfo->hostname, brickinfo->path, + volinfo->volname); + ret = 0; + goto out; + } + + GLUSTERD_GET_VOLUME_DIR (path, volinfo, conf); + GLUSTERD_GET_BRICK_PIDFILE (pidfile, path, brickinfo->hostname, + brickinfo->path); + ret = stat (pidfile, &stbuf); + if (ret && errno == ENOENT) { + gf_log ("", GF_LOG_NORMAL, "About to start glusterfs" + " for brick %s:%s", brickinfo->hostname, + brickinfo->path); + ret = glusterd_volume_start_glusterfs (volinfo, brickinfo); + if (ret) { + gf_log ("", GF_LOG_ERROR, "Unable to start " + "glusterfs, ret: %d", ret); + goto out; + } + } else if (!ret) { + ret = pmap_registry_search (this, brickinfo->path, + GF_PMAP_PORT_BRICKSERVER); + if (ret) { + ret = 0; + goto out; + } + ret = unlink (pidfile); + gf_log ("", GF_LOG_NORMAL, "About to start glusterfs" + " for brick %s:%s", brickinfo->hostname, + brickinfo->path); + ret = glusterd_volume_start_glusterfs (volinfo, brickinfo); + if (ret) { + gf_log ("", GF_LOG_ERROR, "Unable to start " + "glusterfs, ret: %d", ret); + goto out; + } + } + +out: + gf_log ("", GF_LOG_DEBUG, "returning %d ", ret); + return ret; +} + +int +glusterd_restart_bricks (glusterd_conf_t *conf) { glusterd_volinfo_t *volinfo = NULL; glusterd_brickinfo_t *brickinfo = NULL; - char pidfile[PATH_MAX] = {0,}; - char path[PATH_MAX] = {0,}; int ret = -1; - struct stat stbuf = {0,}; struct timespec timeout; sigset_t mask; @@ -1762,39 +1837,13 @@ glusterd_restart_bricks (glusterd_conf_t *conf, xlator_t *this) sigtimedwait(&mask, NULL, &timeout); GF_ASSERT (conf); - GF_ASSERT (this); list_for_each_entry (volinfo, &conf->volumes, vol_list) { //If volume status is not started, do not proceed if (volinfo->status == GLUSTERD_STATUS_STARTED) { list_for_each_entry (brickinfo, &volinfo->bricks, brick_list) { - //Only bricks on localhost to started - if (glusterd_is_local_addr (brickinfo->hostname)) - continue; - //if started, implies already registered with pmap - if (!glusterd_is_brick_started(brickinfo)) - continue; - GLUSTERD_GET_VOLUME_DIR (path, volinfo, conf); - GLUSTERD_GET_BRICK_PIDFILE (pidfile, path, - brickinfo->hostname, brickinfo->path); - ret = stat (pidfile, &stbuf); - //pid file not found, proceed to start - if (ret && errno == ENOENT) { - glusterd_volume_start_glusterfs ( - volinfo, brickinfo, 0); - } else if (!ret) { - ret = pmap_registry_search (this, - brickinfo->path, - GF_PMAP_PORT_BRICKSERVER); - if (ret) - continue; - //might be a stale pid file - ret = unlink (pidfile); - //goto out; - glusterd_volume_start_glusterfs ( - volinfo, brickinfo, 0); - } + glusterd_brick_start (volinfo, brickinfo); } glusterd_check_generate_start_nfs (volinfo); } @@ -2007,3 +2056,58 @@ out: gf_log ("", GF_LOG_DEBUG, "returning %d", ret); return ret; } + +int +glusterd_brick_stop (glusterd_volinfo_t *volinfo, + glusterd_brickinfo_t *brickinfo) +{ + int ret = -1; + xlator_t *this = NULL; + glusterd_conf_t *conf = NULL; + + if ((!brickinfo) || (!volinfo)) + goto out; + + this = THIS; + GF_ASSERT (this); + conf = this->private; + GF_ASSERT (conf); + + if (uuid_is_null (brickinfo->uuid)) { + ret = glusterd_resolve_brick (brickinfo); + if (ret) { + gf_log ("glusterd", GF_LOG_ERROR, + "cannot resolve brick: %s:%s", + brickinfo->hostname, brickinfo->path); + goto out; + } + } + + if (uuid_compare (brickinfo->uuid, conf->uuid)) { + ret = 0; + goto out; + } + + if (glusterd_is_brick_started (brickinfo)) { + gf_log ("", GF_LOG_DEBUG, "brick: %s:%s, of volume: %s not" + " started", brickinfo->hostname, brickinfo->path, + volinfo->volname); + ret = 0; + goto out; + } + + gf_log ("", GF_LOG_NORMAL, "About to stop glusterfs" + " for brick %s:%s", brickinfo->hostname, + brickinfo->path); + ret = glusterd_volume_stop_glusterfs (volinfo, brickinfo); + if (ret) { + gf_log ("", GF_LOG_CRITICAL, "Unable to remove" + " brick: %s:%s", brickinfo->hostname, + brickinfo->path); + goto out; + } + +out: + gf_log ("", GF_LOG_DEBUG, "returning %d ", ret); + return ret; +} diff --git a/xlators/mgmt/glusterd/src/glusterd-utils.h b/xlators/mgmt/glusterd/src/glusterd-utils.h index 9fa272a69f3..4660a26874a 100644 --- a/xlators/mgmt/glusterd/src/glusterd-utils.h +++ b/xlators/mgmt/glusterd/src/glusterd-utils.h @@ -103,13 +103,11 @@ glusterd_resolve_brick (glusterd_brickinfo_t *brickinfo); int32_t glusterd_volume_start_glusterfs (glusterd_volinfo_t *volinfo, - glusterd_brickinfo_t *brickinfo, - int32_t count); + glusterd_brickinfo_t *brickinfo); int32_t glusterd_volume_stop_glusterfs (glusterd_volinfo_t *volinfo, - glusterd_brickinfo_t *brickinfo, - int32_t count); + glusterd_brickinfo_t *brickinfo); int32_t glusterd_volinfo_delete (glusterd_volinfo_t *volinfo); @@ -189,4 +187,10 @@ glusterd_friend_brick_belongs (glusterd_volinfo_t *volinfo, int glusterd_all_volume_cond_check (glusterd_condition_func func, int status, void *ctx); +int +glusterd_brick_start (glusterd_volinfo_t *volinfo, + glusterd_brickinfo_t *brickinfo); +int +glusterd_brick_stop (glusterd_volinfo_t *volinfo, + glusterd_brickinfo_t *brickinfo); #endif diff --git a/xlators/mgmt/glusterd/src/glusterd-volgen.c b/xlators/mgmt/glusterd/src/glusterd-volgen.c index 782170c9a3a..bed21b30030 100644 --- a/xlators/mgmt/glusterd/src/glusterd-volgen.c +++ b/xlators/mgmt/glusterd/src/glusterd-volgen.c @@ -2561,14 +2561,14 @@ glusterd_create_volfiles (glusterd_volinfo_t *volinfo) ret = generate_brick_volfiles (volinfo); if (ret) { - gf_log ("", GF_LOG_DEBUG, + gf_log ("", GF_LOG_ERROR, "Could not generate volfiles for bricks"); goto out; } ret = generate_client_volfiles (volinfo); if (ret) { - gf_log ("", GF_LOG_DEBUG, + gf_log ("", GF_LOG_ERROR, "Could not generate volfile for client"); goto out; } diff --git a/xlators/mgmt/glusterd/src/glusterd.c b/xlators/mgmt/glusterd/src/glusterd.c index c9db4b09d8d..7ec5cafbbd3 100644 --- a/xlators/mgmt/glusterd/src/glusterd.c +++ b/xlators/mgmt/glusterd/src/glusterd.c @@ -412,7 +412,7 @@ init (xlator_t *this) glusterd_op_sm_init (); glusterd_opinfo_init (); - glusterd_restart_bricks(conf, this); + glusterd_restart_bricks (conf); ret = 0; out: if (ret == -1) { diff --git a/xlators/mgmt/glusterd/src/glusterd.h b/xlators/mgmt/glusterd/src/glusterd.h index 9769a95ad2b..bc319cd06d5 100644 --- a/xlators/mgmt/glusterd/src/glusterd.h +++ b/xlators/mgmt/glusterd/src/glusterd.h @@ -50,6 +50,28 @@ #define GLUSTERD_MAX_VOLUME_NAME 1000 #define DEFAULT_LOG_FILE_DIRECTORY DATADIR "/log/glusterfs" +typedef enum glusterd_op_ { + GD_OP_NONE = 0, + GD_OP_CREATE_VOLUME, + GD_OP_START_BRICK, + GD_OP_STOP_BRICK, + GD_OP_DELETE_VOLUME, + GD_OP_START_VOLUME, + GD_OP_STOP_VOLUME, + GD_OP_RENAME_VOLUME, + GD_OP_DEFRAG_VOLUME, + GD_OP_ADD_BRICK, + GD_OP_REMOVE_BRICK, + GD_OP_REPLACE_BRICK, + GD_OP_SET_VOLUME, + GD_OP_SYNC_VOLUME, + GD_OP_LOG_FILENAME, + GD_OP_LOG_LOCATE, + GD_OP_LOG_ROTATE, + GD_OP_MAX, +} glusterd_op_t; + + struct glusterd_store_iter_ { int fd; FILE *file; @@ -329,18 +351,12 @@ glusterd_handle_cli_list_friends (rpcsvc_request_t *req); int glusterd_handle_cli_start_volume (rpcsvc_request_t *req); -int32_t -glusterd_start_volume (rpcsvc_request_t *req, char *volname, int flags); - int glusterd_handle_friend_update (rpcsvc_request_t *req); int glusterd_handle_cli_stop_volume (rpcsvc_request_t *req); -int -glusterd_stop_volume (rpcsvc_request_t *req, char *volname, int flags); - int32_t glusterd_delete_volume (rpcsvc_request_t *req, char *volname, int flags); @@ -408,5 +424,9 @@ glusterd_add_volume_detail_to_dict (glusterd_volinfo_t *volinfo, dict_t *volumes, int count); int -glusterd_restart_bricks(glusterd_conf_t *conf, xlator_t *this); +glusterd_restart_bricks(glusterd_conf_t *conf); + +int32_t +glusterd_volume_txn (rpcsvc_request_t *req, char *volname, int flags, + glusterd_op_t op); #endif -- cgit