summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--cli/gluster-block.c204
-rw-r--r--docs/gluster-block.85
-rw-r--r--rpc/block_svc_routines.c805
-rw-r--r--rpc/glfs-operations.c3
-rw-r--r--rpc/glfs-operations.h1
-rw-r--r--rpc/rpcl/block.x17
-rwxr-xr-xtests/basic.t12
-rw-r--r--utils/common.h2
-rw-r--r--utils/utils.h47
9 files changed, 903 insertions, 193 deletions
diff --git a/cli/gluster-block.c b/cli/gluster-block.c
index d5f9c02..3020587 100644
--- a/cli/gluster-block.c
+++ b/cli/gluster-block.c
@@ -12,6 +12,7 @@
# include "common.h"
# include "block.h"
# include "config.h"
+# include <ctype.h>
@@ -19,7 +20,8 @@ typedef enum clioperations {
CREATE_CLI = 1,
LIST_CLI = 2,
INFO_CLI = 3,
- DELETE_CLI = 4
+ DELETE_CLI = 4,
+ MODIFY_CLI = 5
} clioperations;
const char *argp_program_version = "" \
@@ -36,6 +38,8 @@ const char *argp_program_version = "" \
"[ha <count>] <HOST1[,HOST2,...]> <size> [--json*]"
#define GB_DELETE_HELP_STR "gluster-block delete <volname/blockname> [--json*]"
+#define GB_MODIFY_HELP_STR "gluster-block modify <volname/blockname> "\
+ "<auth enable|disable> [--json*]"
#define GB_INFO_HELP_STR "gluster-block info <volname/blockname> [--json*]"
#define GB_LIST_HELP_STR "gluster-block list <volname> [--json*]"
@@ -50,6 +54,7 @@ glusterBlockCliRPC_1(void *cobj, clioperations opt, char **out)
blockDeleteCli *delete_obj;
blockInfoCli *info_obj;
blockListCli *list_obj;
+ blockModifyCli *modify_obj;
blockResponse *reply = NULL;
@@ -133,6 +138,15 @@ glusterBlockCliRPC_1(void *cobj, clioperations opt, char **out)
goto out;
}
break;
+ case MODIFY_CLI:
+ modify_obj = cobj;
+ reply = block_modify_cli_1(modify_obj, clnt);
+ if (!reply) {
+ LOG("cli", GB_LOG_ERROR, "%sblock modify on volume %s failed",
+ clnt_sperror(clnt, "block_modify_cli_1"), modify_obj->volume);
+ goto out;
+ }
+ break;
}
if (reply) {
@@ -180,6 +194,9 @@ glusterBlockHelp(void)
" delete <volname/blockname>\n"
" delete block device.\n"
"\n"
+ " modify <volname/blockname> <auth enable|disable>\n"
+ " modify block device.\n"
+ "\n"
" help\n"
" show this message and exit.\n"
"\n"
@@ -191,6 +208,116 @@ glusterBlockHelp(void)
);
}
+static bool
+glusterBlockIsNameAcceptable (char *name)
+{
+ int i = 0;
+ if (!name || strlen(name) == 0)
+ return FALSE;
+ for (i = 0; i < strlen(name); i++) {
+ if (!isalnum (name[i]) && (name[i] != '_') && (name[i] != '-'))
+ return FALSE;
+ }
+ return TRUE;
+}
+
+static int
+glusterBlockParseVolumeBlock(char *volumeblock, char *volume, char *block,
+ char *helpstr, char *op)
+{
+ int ret = -1;
+ size_t len = 0;
+ char *sep = NULL;
+
+ /* part before '/' is the volume name */
+ sep = strchr(volumeblock, '/');
+ if (!sep) {
+ MSG("argument '<volname/blockname>'(%s) doesn't seems to be right",
+ volumeblock);
+ MSG("%s\n", helpstr);
+ LOG("cli", GB_LOG_ERROR, "%s failed while parsing <volname/blockname>", op);
+ goto out;
+ }
+ len = sep - volumeblock;
+ if (len >= 255 || strlen(sep+1) >= 255) {
+ MSG("%s\n", "Both volname and blockname should be less than 255 "
+ "characters long");
+ MSG("%s\n", helpstr);
+ LOG("cli", GB_LOG_ERROR, "%s failed while parsing <volname/blockname>", op);
+ goto out;
+ }
+ strncpy(volume, volumeblock, len);
+ /* part after / is blockname */
+ strncpy(block, sep+1, strlen(sep+1));
+ if (!glusterBlockIsNameAcceptable (volume)) {
+ MSG("volume name(%s) should contain only aplhanumeric,'-' "
+ "and '_' characters", volume);
+ goto out;
+ }
+ if (!glusterBlockIsNameAcceptable (block)) {
+ MSG("block name(%s) should contain only aplhanumeric,'-' "
+ "and '_' characters", block);
+ goto out;
+ }
+ ret = 0;
+ out:
+ return ret;
+}
+
+static int
+glusterBlockModify(int argcount, char **options, int json)
+{
+ size_t optind = 2;
+ blockModifyCli mobj = {0, };
+ int ret = -1;
+ char *out = NULL;
+
+ mobj.json_resp = json;
+ if (argcount != 5) {
+ MSG("%s\n", "Insufficient arguments for modify:");
+ MSG("%s\n", GB_MODIFY_HELP_STR);
+ return -1;
+ }
+
+ if (glusterBlockParseVolumeBlock (options[optind++], mobj.volume,
+ mobj.block_name, GB_MODIFY_HELP_STR,
+ "modify")) {
+ goto out;
+ }
+
+ /* if auth given then collect status which is next by 'auth' arg */
+ if (!strcmp(options[optind], "auth")) {
+ optind++;
+ if(strcmp (options[optind], "enable") == 0) {
+ mobj.auth_mode = 1;
+ } else if (strcmp (options[optind], "disable") == 0) {
+ mobj.auth_mode = 0;
+ } else {
+ MSG("%s\n", "argument to 'auth' doesn't seems to be right");
+ MSG("%s\n", GB_MODIFY_HELP_STR);
+ LOG("cli", GB_LOG_ERROR, "Modify failed while parsing argument "
+ "to auth for <%s/%s>",
+ mobj.volume, mobj.block_name);
+ goto out;
+ }
+ }
+
+ ret = glusterBlockCliRPC_1(&mobj, MODIFY_CLI, &out);
+ if (ret) {
+ LOG("cli", GB_LOG_ERROR,
+ "failed getting info of block %s on volume %s",
+ mobj.block_name, mobj.volume);
+ }
+
+ if (out) {
+ MSG("%s", out);
+ }
+
+ out:
+ GB_FREE(out);
+
+ return ret;
+}
static int
glusterBlockCreate(int argcount, char **options, int json)
@@ -200,8 +327,6 @@ glusterBlockCreate(int argcount, char **options, int json)
ssize_t sparse_ret;
char *out = NULL;
blockCreateCli cobj = {0, };
- char *argcopy;
- char *sep;
cobj.json_resp = json;
@@ -214,24 +339,11 @@ glusterBlockCreate(int argcount, char **options, int json)
/* default mpath */
cobj.mpath = 1;
- if (GB_STRDUP (argcopy, options[optind++]) < 0) {
- goto out;
- }
- /* part before '/' is the volume name */
- sep = strchr(argcopy, '/');
- if (!sep) {
- MSG("%s\n",
- "first argument '<volname/blockname>' doesn't seems to be right");
- MSG("%s\n", GB_CREATE_HELP_STR);
- LOG("cli", GB_LOG_ERROR, "%s",
- "create failed while parsing <volname/blockname>");
+ if (glusterBlockParseVolumeBlock (options[optind++], cobj.volume,
+ cobj.block_name, GB_CREATE_HELP_STR,
+ "create")) {
goto out;
}
- *sep = '\0';
- strcpy(cobj.volume, argcopy);
-
- /* part after / is blockname */
- strcpy(cobj.block_name, sep + 1);
if (argcount - optind >= 2) { /* atleast 2 needed */
/* if ha given then collect count which is next by 'ha' arg */
@@ -280,7 +392,6 @@ glusterBlockCreate(int argcount, char **options, int json)
}
out:
- GB_FREE(argcopy);
GB_FREE(cobj.block_hosts);
GB_FREE(out);
@@ -291,7 +402,7 @@ glusterBlockCreate(int argcount, char **options, int json)
static int
glusterBlockList(int argcount, char **options, int json)
{
- blockListCli cobj;
+ blockListCli cobj = {0};
char *out = NULL;
int ret = -1;
@@ -324,10 +435,8 @@ glusterBlockList(int argcount, char **options, int json)
static int
glusterBlockDelete(int argcount, char **options, int json)
{
- blockDeleteCli cobj;
+ blockDeleteCli cobj = {0};
char *out = NULL;
- char *argcopy;
- char *sep;
int ret = -1;
@@ -339,23 +448,11 @@ glusterBlockDelete(int argcount, char **options, int json)
}
- if (GB_STRDUP (argcopy, options[2]) < 0) {
- goto out;
- }
- /* part before '/' is the volume name */
- sep = strchr(argcopy, '/');
- if (!sep) {
- MSG("%s\n", "argument '<volname/blockname>' doesn't seems to be right");
- MSG("%s\n", GB_DELETE_HELP_STR);
- LOG("cli", GB_LOG_ERROR, "%s",
- "delete failed while parsing <volname/blockname>");
+ if (glusterBlockParseVolumeBlock (options[2], cobj.volume,
+ cobj.block_name, GB_DELETE_HELP_STR,
+ "delete")) {
goto out;
}
- *sep = '\0';
- strcpy(cobj.volume, argcopy);
-
- /* part after / is blockname */
- strcpy(cobj.block_name, sep + 1);
ret = glusterBlockCliRPC_1(&cobj, DELETE_CLI, &out);
if (ret) {
@@ -368,7 +465,6 @@ glusterBlockDelete(int argcount, char **options, int json)
}
out:
- GB_FREE(argcopy);
GB_FREE(out);
return ret;
@@ -378,10 +474,8 @@ glusterBlockDelete(int argcount, char **options, int json)
static int
glusterBlockInfo(int argcount, char **options, int json)
{
- blockInfoCli cobj;
+ blockInfoCli cobj = {0};
char *out = NULL;
- char *argcopy;
- char *sep;
int ret = -1;
@@ -393,23 +487,11 @@ glusterBlockInfo(int argcount, char **options, int json)
}
- if (GB_STRDUP (argcopy, options[2]) < 0) {
- goto out;
- }
- /* part before '/' is the volume name */
- sep = strchr(argcopy, '/');
- if (!sep) {
- MSG("%s\n", "argument '<volname/blockname>' doesn't seems to be right");
- MSG("%s\n", GB_INFO_HELP_STR);
- LOG("cli", GB_LOG_ERROR, "%s",
- "info failed while parsing <volname/blockname>");
+ if (glusterBlockParseVolumeBlock (options[2], cobj.volume,
+ cobj.block_name, GB_INFO_HELP_STR,
+ "info")) {
goto out;
}
- *sep = '\0';
- strcpy(cobj.volume, argcopy);
-
- /* part after / is blockname */
- strcpy(cobj.block_name, sep + 1);
ret = glusterBlockCliRPC_1(&cobj, INFO_CLI, &out);
if (ret) {
@@ -423,7 +505,6 @@ glusterBlockInfo(int argcount, char **options, int json)
}
out:
- GB_FREE(argcopy);
GB_FREE(out);
return ret;
@@ -479,7 +560,10 @@ glusterBlockParseArgs(int count, char **options)
goto out;
case GB_CLI_MODIFY:
- MSG("option '%s' is not supported yet.\n", options[1]);
+ ret = glusterBlockModify(count, options, json);
+ if (ret) {
+ LOG("cli", GB_LOG_ERROR, "%s", FAILED_MODIFY);
+ }
goto out;
case GB_CLI_DELETE:
diff --git a/docs/gluster-block.8 b/docs/gluster-block.8
index 66d29e7..1ae08af 100644
--- a/docs/gluster-block.8
+++ b/docs/gluster-block.8
@@ -54,6 +54,11 @@ delete block device.
.PP
.SS
+\fBmodify\fR <VOLNAME/BLOCKNAME> <auth enable|disable>
+modify block device.
+.PP
+
+.SS
.BR help
show this message and exit.
.PP
diff --git a/rpc/block_svc_routines.c b/rpc/block_svc_routines.c
index b966e05..8b3eaea 100644
--- a/rpc/block_svc_routines.c
+++ b/rpc/block_svc_routines.c
@@ -19,6 +19,7 @@
# define UUID_BUF_SIZE 38
+# define GB_DEFAULT_ERRCODE 255
# define GB_CREATE "create"
# define GB_DELETE "delete"
@@ -42,7 +43,8 @@ pthread_mutex_t lock = PTHREAD_MUTEX_INITIALIZER;
typedef enum operations {
CREATE_SRV = 1,
- DELETE_SRV = 2
+ DELETE_SRV = 2,
+ MODIFY_SRV = 3
} operations;
@@ -56,6 +58,14 @@ typedef struct blockRemoteObj {
} blockRemoteObj;
+typedef struct blockRemoteModifyResp {
+ char *attempt;
+ char *success;
+ char *rb_attempt;
+ char *rb_success;
+} blockRemoteModifyResp;
+
+
typedef struct blockRemoteDeleteResp {
char *d_attempt;
char *d_success;
@@ -326,6 +336,14 @@ glusterBlockCallRPC_1(char *host, void *cobj,
goto out;
}
break;
+ case MODIFY_SRV:
+ reply = block_modify_1((blockModify *)cobj, clnt);
+ if (!reply) {
+ LOG("mgmt", GB_LOG_ERROR, "%son host %s",
+ clnt_sperror(clnt, "block remote modify failed"), host);
+ goto out;
+ }
+ break;
}
if (reply) {
@@ -466,7 +484,7 @@ glusterBlockCreateRemote(void *data)
out:
if (!args->reply) {
- if (GB_ASPRINTF(&args->reply, "failed to config on %s %s\n", args->addr,
+ if (GB_ASPRINTF(&args->reply, "failed to configure on %s %s\n", args->addr,
errMsg?errMsg:"") == -1) {
ret = -1;
}
@@ -577,8 +595,8 @@ glusterBlockDeleteRemote(void *data)
out:
if (!args->reply) {
- if (GB_ASPRINTF(&args->reply, "failed to delete config on %s",
- args->addr) == -1) {
+ if (GB_ASPRINTF(&args->reply, "failed to delete config on %s %s",
+ args->addr, errMsg?errMsg:"") == -1) {
ret = -1;
}
}
@@ -589,6 +607,76 @@ glusterBlockDeleteRemote(void *data)
}
+static size_t
+glusterBlockDeleteFillArgs(MetaInfo *info, bool deleteall, blockRemoteObj *args,
+ struct glfs *glfs, blockDelete *dobj)
+{
+ int i = 0;
+ size_t count = 0;
+
+ for (i = 0, count = 0; i < info->nhosts; i++) {
+ switch (blockMetaStatusEnumParse(info->list[i]->status)) {
+ case GB_CONFIG_SUCCESS:
+ case GB_AUTH_ENFORCEING:
+ case GB_AUTH_ENFORCED:
+ case GB_AUTH_ENFORCE_FAIL:
+ case GB_AUTH_CLEAR_ENFORCED:
+ case GB_AUTH_CLEAR_ENFORCEING:
+ case GB_AUTH_CLEAR_ENFORCE_FAIL:
+ if (!deleteall)
+ break;
+ case GB_CLEANUP_INPROGRESS:
+ case GB_CLEANUP_FAIL:
+ case GB_CONFIG_FAIL:
+ if (args) {
+ args[count].glfs = glfs;
+ args[count].obj = (void *)dobj;
+ args[count].volume = info->volume;
+ args[count].addr = info->list[i]->addr;
+ }
+ count++;
+ break;
+ }
+ }
+ return count;
+}
+
+
+static int
+glusterBlockCollectAttemptSuccess (blockRemoteObj *args, size_t count,
+ char **attempt, char **success)
+{
+ char *a_tmp = NULL;
+ char *s_tmp = NULL;
+ int i = 0;
+
+ for (i = 0; i < count; i++) {
+ if (args[i].exit) {
+ if (GB_ASPRINTF(attempt, "%s %s",
+ (a_tmp==NULL?"":a_tmp), args[i].addr) == -1) {
+ goto fail;
+ }
+ GB_FREE(a_tmp);
+ a_tmp = *attempt;
+ } else {
+ if (GB_ASPRINTF(success, "%s %s",
+ (s_tmp==NULL?"":s_tmp), args[i].addr) == -1) {
+ goto fail;
+ }
+ GB_FREE(s_tmp);
+ s_tmp = *success;
+ }
+ }
+ return 0;
+ fail:
+ GB_FREE(a_tmp);
+ GB_FREE(s_tmp);
+ *attempt = NULL;
+ *success = NULL;
+ return -1;
+}
+
+
static int
glusterBlockDeleteRemoteAsync(MetaInfo *info,
struct glfs *glfs,
@@ -599,7 +687,7 @@ glusterBlockDeleteRemoteAsync(MetaInfo *info,
{
pthread_t *tid = NULL;
blockRemoteDeleteResp *local = *savereply;
- static blockRemoteObj *args = NULL;
+ blockRemoteObj *args = NULL;
char *d_attempt = NULL;
char *d_success = NULL;
char *a_tmp = NULL;
@@ -616,27 +704,7 @@ glusterBlockDeleteRemoteAsync(MetaInfo *info,
goto out;
}
- for (i = 0, count = 0; i < info->nhosts; i++) {
- switch (blockMetaStatusEnumParse(info->list[i]->status)) {
- case GB_CLEANUP_INPROGRESS:
- case GB_CLEANUP_FAIL:
- case GB_CONFIG_FAIL:
- args[count].glfs = glfs;
- args[count].obj = (void *)dobj;
- args[count].volume = info->volume;
- args[count].addr = info->list[i]->addr;
- count++;
- break;
- }
- if (deleteall &&
- blockMetaStatusEnumParse(info->list[i]->status) == GB_CONFIG_SUCCESS) {
- args[count].glfs = glfs;
- args[count].obj = (void *)dobj;
- args[count].volume = info->volume;
- args[count].addr = info->list[i]->addr;
- count++;
- }
- }
+ count = glusterBlockDeleteFillArgs(info, deleteall, args, glfs, dobj);
for (i = 0; i < count; i++) {
pthread_create(&tid[i], NULL, glusterBlockDeleteRemote, &args[i]);
@@ -646,23 +714,9 @@ glusterBlockDeleteRemoteAsync(MetaInfo *info,
pthread_join(tid[i], NULL);
}
- /* collect return */
- for (i = 0; i < count; i++) {
- if (args[i].exit) {
- if (GB_ASPRINTF(&d_attempt, "%s %s",
- (a_tmp==NULL?"":a_tmp), args[i].addr) == -1) {
- goto out;
- }
- GB_FREE(a_tmp);
- a_tmp = d_attempt;
- } else {
- if (GB_ASPRINTF(&d_success, "%s %s",
- (s_tmp==NULL?"":s_tmp), args[i].addr) == -1) {
- goto out;
- }
- GB_FREE(s_tmp);
- s_tmp = d_success;
- }
+ ret = glusterBlockCollectAttemptSuccess (args, count, &d_attempt, &d_success);
+ if (ret) {
+ goto out;
}
if (d_attempt) {
@@ -707,6 +761,172 @@ glusterBlockDeleteRemoteAsync(MetaInfo *info,
}
+void *
+glusterBlockModifyRemote(void *data)
+{
+ int ret;
+ blockRemoteObj *args = (blockRemoteObj *)data;
+ blockModify cobj = *(blockModify *)args->obj;
+ char *errMsg = NULL;
+
+ GB_METAUPDATE_OR_GOTO(lock, args->glfs, cobj.block_name, cobj.volume,
+ ret, errMsg, out, "%s: AUTH%sENFORCEING\n", args->addr,
+ cobj.auth_mode?"":"CLEAR");
+
+ ret = glusterBlockCallRPC_1(args->addr, &cobj, MODIFY_SRV, &args->reply);
+ if (ret) {
+ if (errno == ENETUNREACH || errno == ECONNREFUSED || errno == ETIMEDOUT) {
+ LOG("mgmt", GB_LOG_ERROR, "%s hence %s for block %s on"
+ "host %s volume %s", strerror(errno), FAILED_REMOTE_MODIFY,
+ cobj.block_name, args->addr, args->volume);
+ goto out;
+ }
+
+ if (ret == EKEYEXPIRED) {
+ LOG("mgmt", GB_LOG_ERROR, "%s [%s] hence modify block %s on"
+ "host %s volume %s failed", FAILED_DEPENDENCY, strerror(errno),
+ cobj.block_name, args->addr, args->volume);
+ goto out;
+ }
+
+ GB_METAUPDATE_OR_GOTO(lock, args->glfs, cobj.block_name, cobj.volume,
+ ret, errMsg, out, "%s: AUTH%sENFORCEFAIL\n",
+ args->addr, cobj.auth_mode?"":"CLEAR");
+ LOG("mgmt", GB_LOG_ERROR, "%s for block %s on host %s volume %s",
+ FAILED_REMOTE_MODIFY, cobj.block_name, args->addr, args->volume);
+ goto out;
+ }
+
+ GB_METAUPDATE_OR_GOTO(lock, args->glfs, cobj.block_name, cobj.volume,
+ ret, errMsg, out, "%s: AUTH%sENFORCED\n", args->addr,
+ cobj.auth_mode?"":"CLEAR");
+
+ out:
+ if (!args->reply) {
+ if (GB_ASPRINTF(&args->reply, "failed to configure auth on %s %s",
+ args->addr, errMsg?errMsg:"") == -1) {
+ ret = -1;
+ }
+ }
+ GB_FREE(errMsg);
+ args->exit = ret;
+
+ return NULL;
+}
+
+static size_t
+glusterBlockModifyArgsFill(blockModify *mobj, MetaInfo *info,
+ blockRemoteObj *args, struct glfs *glfs)
+{
+ int i = 0;
+ size_t count = 0;
+ bool fill = FALSE;
+
+ for (i = 0, count = 0; i < info->nhosts; i++) {
+ switch (blockMetaStatusEnumParse(info->list[i]->status)) {
+ case GB_CONFIG_SUCCESS:
+ /* case GB_AUTH_ENFORCED: this is not required to be configured */
+ case GB_AUTH_ENFORCE_FAIL:
+ case GB_AUTH_CLEAR_ENFORCED:
+ if (mobj->auth_mode) {
+ fill = TRUE;
+ }
+ break;
+ case GB_AUTH_ENFORCED:
+ if (!mobj->auth_mode) {
+ fill = TRUE;
+ }
+ break;
+ case GB_AUTH_ENFORCEING:
+ case GB_AUTH_CLEAR_ENFORCEING:
+ case GB_AUTH_CLEAR_ENFORCE_FAIL:
+ fill = TRUE;
+ break;
+ }
+ if (fill) {
+ if (args) {
+ args[count].glfs = glfs;
+ args[count].obj = (void *)mobj;
+ args[count].addr = info->list[i]->addr;
+ }
+ count++;
+ }
+ fill = FALSE;
+ }
+ return count;
+}
+
+
+static int
+glusterBlockModifyRemoteAsync(MetaInfo *info,
+ struct glfs *glfs,
+ blockModify *mobj,
+ blockRemoteModifyResp **savereply,
+ bool rollback)
+{
+ pthread_t *tid = NULL;
+ blockRemoteModifyResp *local = *savereply;
+ blockRemoteObj *args = NULL;
+ int ret = -1;
+ size_t i;
+ size_t count = 0;
+
+
+ /* get all (configured - already auth enforced) node count */
+ count = glusterBlockModifyArgsFill(mobj, info, NULL, glfs);
+
+ if (GB_ALLOC_N(tid, count) < 0) {
+ goto out;
+ }
+
+ if (GB_ALLOC_N(args, count) < 0) {
+ goto out;
+ }
+
+ count = glusterBlockModifyArgsFill(mobj, info, args, glfs);
+
+ for (i = 0; i < count; i++) {
+ pthread_create(&tid[i], NULL, glusterBlockModifyRemote, &args[i]);
+ }
+
+ for (i = 0; i < count; i++) {
+ /* collect exit code */
+ pthread_join(tid[i], NULL);
+ }
+
+ if (!rollback) {
+ /* collect return */
+ ret = glusterBlockCollectAttemptSuccess (args, count, &local->attempt,
+ &local->success);
+ if (ret)
+ goto out;
+ } else {
+ /* collect return */
+ ret = glusterBlockCollectAttemptSuccess (args, count,
+ &local->rb_attempt,
+ &local->rb_success);
+ if (ret)
+ goto out;
+ }
+ for (i = 0; i < count; i++) {
+ if (args[i].exit == EKEYEXPIRED) {
+ ret = EKEYEXPIRED;
+ break; /* important to catch */
+ } else if (args[i].exit) {
+ ret = -1;
+ }
+ }
+
+ *savereply = local;
+
+ out:
+ GB_FREE(args);
+ GB_FREE(tid);
+
+ return ret;
+}
+
+
static int
glusterBlockCleanUp(operations opt, struct glfs *glfs, char *blockname,
bool deleteall, void *reply)
@@ -747,20 +967,7 @@ glusterBlockCleanUp(operations opt, struct glfs *glfs, char *blockname,
strcpy(dobj.block_name, blockname);
strcpy(dobj.gbid, info->gbid);
- for (i = 0; i < info->nhosts; i++) {
- switch (blockMetaStatusEnumParse(info->list[i]->status)) {
- case GB_CLEANUP_INPROGRESS:
- case GB_CLEANUP_FAIL:
- case GB_CONFIG_FAIL:
- count++;
- break;
- }
- if (deleteall &&
- blockMetaStatusEnumParse(info->list[i]->status) == GB_CONFIG_SUCCESS) {
- count++;
- }
- }
-
+ count = glusterBlockDeleteFillArgs(info, deleteall, NULL, NULL, NULL);
asyncret = glusterBlockDeleteRemoteAsync(info, glfs, &dobj, count,
deleteall, &drobj);
if (asyncret) {
@@ -873,7 +1080,7 @@ glusterBlockAuditRequest(struct glfs *glfs,
morereq = blk->mpath - successcnt; /* needed nodes to complete req */
if (spare == 0) {
LOG("mgmt", GB_LOG_WARNING,
- "No Spare nodes to create (%s): rewinding creation of target"
+ "No Spare nodes to create (%s): rollingback creation of target"
" on volume %s with given hosts %s",
blk->block_name, blk->volume, blk->block_hosts);
glusterBlockCleanUp(CREATE_SRV, glfs,
@@ -883,7 +1090,7 @@ glusterBlockAuditRequest(struct glfs *glfs,
goto out;
} else if (spare < morereq) {
LOG("mgmt", GB_LOG_WARNING,
- "Not enough Spare nodes for (%s): rewinding creation of target"
+ "Not enough Spare nodes for (%s): rollingback creation of target"
" on volume %s with given hosts %s",
blk->block_name, blk->volume, blk->block_hosts);
glusterBlockCleanUp(CREATE_SRV, glfs,
@@ -927,8 +1134,8 @@ glusterBlockAuditRequest(struct glfs *glfs,
}
void
-block_format_error_response (int json_resp, int errCode, char *errMsg,
- struct blockResponse *reply)
+blockFormatErrorResponse (int json_resp, int errCode, char *errMsg,
+ struct blockResponse *reply)
{
json_object *json_obj = NULL;
reply->exit = errCode;
@@ -946,10 +1153,277 @@ block_format_error_response (int json_resp, int errCode, char *errMsg,
}
}
+static void
+blockStr2arrayAddToJsonObj (json_object *json_obj, char *string, char *label,
+ json_object **json_array)
+{
+ char *tmp = NULL;
+ json_object *json_array1 = NULL;
+
+ if (!string)
+ return;
+
+ json_array1 = json_object_new_array();
+ tmp = strtok (string, " ");
+ while (tmp != NULL)
+ {
+ json_object_array_add(json_array1, json_object_new_string(tmp));
+ tmp = strtok (NULL, " ");
+ }
+ json_object_object_add(json_obj, label, json_array1);
+ *json_array = json_array1;
+}
+
+static void
+blockModifyCliFormatResponse (blockModifyCli *blk, struct blockModify *mobj,
+ int errCode, char *errMsg,
+ blockRemoteModifyResp *savereply,
+ MetaInfo *info, struct blockResponse *reply,
+ bool rollback)
+{
+ json_object *json_obj = NULL;
+ json_object *json_array[4] = {0};
+ char *tmp2 = NULL;
+ char *tmp3 = NULL;
+ char *tmp = NULL;
+ int i = 0;
+
+ if (!reply) {
+ return;
+ }
+
+ if (errCode < 0) {
+ errCode = GB_DEFAULT_ERRCODE;
+ }
+
+ if (errMsg) {
+ blockFormatErrorResponse(blk->json_resp, errCode, errMsg, reply);
+ return;
+ }
+
+ if (blk->json_resp) {
+ json_obj = json_object_new_object();
+
+ blockStr2arrayAddToJsonObj (json_obj, savereply->attempt, "FAILED ON",
+ &json_array[0]);
+
+ if (savereply->success) {
+ blockStr2arrayAddToJsonObj (json_obj, savereply->success,
+ "SUCCESSFUL ON", &json_array[1]);
+ tmp = NULL;
+
+ GB_ASPRINTF(&tmp, "%s%s", GB_TGCLI_IQN_PREFIX, info->gbid);
+ json_object_object_add(json_obj, "IQN",
+ json_object_new_string(tmp?tmp:""));
+ if (mobj->auth_mode) {
+ json_object_object_add(json_obj, "USERNAME",
+ json_object_new_string(info->gbid));
+ json_object_object_add(json_obj, "PASSWORD",
+ json_object_new_string(mobj->passwd));
+ }
+ }
+
+ json_object_object_add(json_obj, "RESULT",
+ errCode?json_object_new_string("FAIL"):json_object_new_string("SUCCESS"));
+
+ if (rollback) {
+ blockStr2arrayAddToJsonObj (json_obj, savereply->rb_attempt,
+ "ROLLBACK FAILED ON", &json_array[2]);
+
+ blockStr2arrayAddToJsonObj (json_obj, savereply->rb_success,
+ "ROLLBACK SUCCESS ON", &json_array[3]);
+ }
+
+ GB_ASPRINTF(&reply->out, "%s\n", json_object_to_json_string_ext(json_obj,
+ mapJsonFlagToJsonCstring(blk->json_resp)));
+
+ for (i = 0; i < 4; i++) {
+ if (json_array[i]) {
+ json_object_put(json_array[i]);
+ }
+ }
+ json_object_put(json_obj);
+ } else {
+ /* save 'failed on'*/
+ if (savereply->attempt)
+ GB_ASPRINTF(&tmp, "FAILED ON: %s\n", savereply->attempt);
+
+ if (savereply->success) {
+ if (mobj->auth_mode) {
+ GB_ASPRINTF(&tmp2, "%s\nIQN: %s%s\nUSERNAME: %s\nPASSWORD: %s",
+ savereply->success, GB_TGCLI_IQN_PREFIX, info->gbid,
+ info->gbid, mobj->passwd);
+ } else {
+ GB_ASPRINTF(&tmp2, "%s\nIQN: %s%s",
+ savereply->success, GB_TGCLI_IQN_PREFIX, info->gbid);
+ }
+ }
+
+ GB_ASPRINTF(&tmp3, "%sSUCCESSFUL ON: %s\n" "RESULT: %s\n", tmp?tmp:"",
+ savereply->success?tmp2:"None", errCode?"FAIL":"SUCCESS");
+
+ GB_FREE(tmp);
+ GB_FREE(tmp2);
+
+ if (rollback) {
+ if (savereply->rb_attempt) {
+ GB_ASPRINTF(&tmp, "ROLLBACK FAILED ON: %s\n", savereply->rb_attempt);
+ }
+ if (savereply->rb_success) {
+ GB_ASPRINTF(&tmp2, "ROLLBACK SUCCESS ON: %s\n", savereply->rb_attempt);
+ }
+ }
+
+ GB_ASPRINTF(&reply->out, "%s%s%s", tmp3, savereply->rb_attempt?tmp:"",
+ savereply->rb_success?tmp2:"");
+ GB_FREE(tmp2);
+ GB_FREE(tmp3);
+ }
+ GB_FREE(tmp);
+}
+
+blockResponse *
+block_modify_cli_1_svc(blockModifyCli *blk, struct svc_req *rqstp)
+{
+ int ret = -1;
+ static blockModify mobj;
+ static blockRemoteModifyResp *savereply = NULL;
+ static blockResponse *reply = NULL;
+ struct glfs *glfs;
+ struct glfs_fd *lkfd = NULL;
+ MetaInfo *info = NULL;
+ uuid_t uuid;
+ char passwd[UUID_BUF_SIZE];
+ int asyncret;
+ bool rollback = false;
+ int errCode = 0;
+ char *errMsg = NULL;
+
+
+ if ((GB_ALLOC(reply) < 0) || (GB_ALLOC(savereply) < 0) ||
+ (GB_ALLOC (info) < 0)) {
+ GB_FREE (reply);
+ GB_FREE (savereply);
+ GB_FREE (info);
+ return NULL;
+ }
+
+ glfs = glusterBlockVolumeInit(blk->volume, &errCode, &errMsg);
+ if (!glfs) {
+ LOG("mgmt", GB_LOG_ERROR,
+ "glusterBlockVolumeInit(%s) for block %s failed [%s]",
+ blk->volume, blk->block_name, strerror(errno));
+ goto initfail;
+ }
+
+ lkfd = glusterBlockCreateMetaLockFile(glfs, blk->volume, &errCode, &errMsg);
+ if (!lkfd) {
+ LOG("mgmt", GB_LOG_ERROR, "%s %s for block %s",
+ FAILED_CREATING_META, blk->volume, blk->block_name);
+ goto nolock;
+ }
+
+ GB_METALOCK_OR_GOTO(lkfd, blk->volume, ret, errMsg, nolock);
+
+ if (glfs_access(glfs, blk->block_name, F_OK)) {
+ LOG("mgmt", GB_LOG_ERROR,
+ "block with name %s doesn't exist in the volume %s",
+ blk->block_name, blk->volume);
+ GB_ASPRINTF(&errMsg, "block %s/%s doesn't exist", blk->volume,
+ blk->block_name);
+ errCode = ENOENT;
+ goto out;
+ }
+
+ ret = blockGetMetaInfo(glfs, blk->block_name, info, NULL);
+ if (ret) {
+ goto out;
+ }
+
+ strcpy(mobj.block_name, blk->block_name);
+ strcpy(mobj.volume, blk->volume);
+ strcpy(mobj.gbid, info->gbid);
+
+ if (blk->auth_mode) {
+ if(info->passwd[0] == '\0') {
+ uuid_generate(uuid);
+ uuid_unparse(uuid, passwd);
+ GB_METAUPDATE_OR_GOTO(lock, glfs, blk->block_name, blk->volume,
+ ret, errMsg, out, "PASSWORD: %s\n", passwd);
+ strcpy(mobj.passwd, passwd);
+ } else {
+ strcpy(mobj.passwd, info->passwd);
+ }
+ mobj.auth_mode = 1;
+ } else {
+ GB_METAUPDATE_OR_GOTO(lock, glfs, blk->block_name, blk->volume,
+ ret, errMsg, out, "PASSWORD: \n");
+ mobj.auth_mode = 0;
+ }
+
+ asyncret = glusterBlockModifyRemoteAsync(info, glfs, &mobj,
+ &savereply, rollback);
+ if (asyncret) {
+ LOG("mgmt", GB_LOG_WARNING,
+ "glusterBlockModifyRemoteAsync(auth=%d): return %d %s for block %s on volume %s",
+ blk->auth_mode, asyncret, FAILED_REMOTE_AYNC_MODIFY, blk->block_name, info->volume);
+ /* Unwind by removing authentication */
+ if (blk->auth_mode) {
+ GB_METAUPDATE_OR_GOTO(lock, glfs, blk->block_name, blk->volume,
+ ret, errMsg, out, "PASSWORD: \n");
+ }
+
+ /* toggle */
+ mobj.auth_mode = !mobj.auth_mode;
+
+ rollback = true;
+ /* undo */
+ asyncret = glusterBlockModifyRemoteAsync(info, glfs, &mobj,
+ &savereply, rollback);
+ if (asyncret) {
+ LOG("mgmt", GB_LOG_WARNING,
+ "glusterBlockModifyRemoteAsync(auth=%d): on rollback return %d %s "
+ "for block %s on volume %s", blk->auth_mode, asyncret, FAILED_REMOTE_AYNC_MODIFY,
+ blk->block_name, info->volume);
+ /* do nothing ? */
+ }
+ }
+
+ out:
+ if (ret == EKEYEXPIRED) {
+ GB_ASPRINTF(&errMsg, "Looks like targetcli and tcmu-runner are not "
+ "installed on " "few nodes.\n");
+ }
+
+ GB_METAUNLOCK(lkfd, blk->volume, ret, errMsg);
+
+ nolock:
+ if (lkfd && glfs_close(lkfd) != 0) {
+ LOG("mgmt", GB_LOG_ERROR,
+ "glfs_close(%s): for block %s on volume %s failed[%s]",
+ GB_TXLOCKFILE, blk->block_name, blk->volume, strerror(errno));
+ }
+
+ initfail:
+ blockModifyCliFormatResponse (blk, &mobj, errCode, errMsg, savereply, info,
+ reply, rollback);
+ glfs_fini(glfs);
+
+ if (savereply) {
+ GB_FREE(savereply->attempt);
+ GB_FREE(savereply->success);
+ GB_FREE(savereply->rb_attempt);
+ GB_FREE(savereply->rb_success);
+ GB_FREE(savereply);
+ }
+
+ return reply;
+}
+
void
-block_create_cli_format_response(blockCreateCli *blk, int errCode,
- char *errMsg, blockRemoteCreateResp *savereply,
- struct blockResponse *reply)
+blockCreateCliFormatResponse(blockCreateCli *blk, int errCode,
+ char *errMsg, blockRemoteCreateResp *savereply,
+ struct blockResponse *reply)
{
json_object *json_obj = NULL;
json_object *json_array = NULL;
@@ -962,11 +1436,11 @@ block_create_cli_format_response(blockCreateCli *blk, int errCode,
}
if (errCode < 0) {
- errCode = 255;
+ errCode = GB_DEFAULT_ERRCODE;
}
if (errMsg) {
- block_format_error_response(blk->json_resp, errCode, errMsg, reply);
+ blockFormatErrorResponse(blk->json_resp, errCode, errMsg, reply);
return;
}
@@ -1006,7 +1480,7 @@ block_create_cli_format_response(blockCreateCli *blk, int errCode,
}
}
tmp = NULL;
- json_object_object_add(json_obj, "REWIND ON", json_array);
+ json_object_object_add(json_obj, "ROLLBACK ON", json_array);
}
json_object_object_add(json_obj, "RESULT",
@@ -1030,7 +1504,7 @@ block_create_cli_format_response(blockCreateCli *blk, int errCode,
/* save 'failed on'*/
tmp = NULL;
if (savereply->obj->d_attempt || savereply->obj->d_success) {
- if (GB_ASPRINTF(&tmp, "REWIND ON: %s %s\n",
+ if (GB_ASPRINTF(&tmp, "ROLLBACK ON: %s %s\n",
savereply->obj->d_attempt?savereply->obj->d_attempt:"",
savereply->obj->d_success?savereply->obj->d_success:"") == -1) {
goto out;
@@ -1062,7 +1536,7 @@ block_create_cli_1_svc(blockCreateCli *blk, struct svc_req *rqstp)
if (GB_ALLOC(reply) < 0) {
- goto out;
+ return NULL;
}
list = blockServerParse(blk->block_hosts);
@@ -1141,7 +1615,7 @@ block_create_cli_1_svc(blockCreateCli *blk, struct svc_req *rqstp)
if (errCode) {
if (errCode == EKEYEXPIRED) {
LOG("mgmt", GB_LOG_ERROR, "glusterBlockCreateRemoteAsync: return %d"
- " rewinding the create request for block %s on volume %s with hosts %s",
+ " rollingback the create request for block %s on volume %s with hosts %s",
errCode, blk->block_name, blk->volume, blk->block_hosts);
glusterBlockCleanUp(CREATE_SRV, glfs, blk->block_name, TRUE, &savereply);
@@ -1178,7 +1652,7 @@ block_create_cli_1_svc(blockCreateCli *blk, struct svc_req *rqstp)
}
optfail:
- block_create_cli_format_response(blk, errCode, errMsg, savereply, reply);
+ blockCreateCliFormatResponse(blk, errCode, errMsg, savereply, reply);
GB_FREE(errMsg);
blockServerDefFree(list);
glfs_fini(glfs);
@@ -1289,9 +1763,9 @@ block_create_1_svc(blockCreate *blk, struct svc_req *rqstp)
}
void
-block_delete_cli_format_response(blockDeleteCli *blk, int errCode, char *errMsg,
- blockRemoteDeleteResp *savereply,
- struct blockResponse *reply)
+blockDeleteCliFormatResponse(blockDeleteCli *blk, int errCode, char *errMsg,
+ blockRemoteDeleteResp *savereply,
+ struct blockResponse *reply)
{
json_object *json_obj = NULL;
json_object *json_array1 = NULL;
@@ -1303,42 +1777,23 @@ block_delete_cli_format_response(blockDeleteCli *blk, int errCode, char *errMsg,
}
if (errCode < 0) {
- errCode = 255;
+ errCode = GB_DEFAULT_ERRCODE;
}
reply->exit = errCode;
if (errMsg) {
- block_format_error_response(blk->json_resp, errCode, errMsg, reply);
+ blockFormatErrorResponse(blk->json_resp, errCode, errMsg, reply);
return;
}
if (blk->json_resp) {
json_obj = json_object_new_object();
- if (savereply->d_attempt) {
- json_array1 = json_object_new_array();
- tmp = strtok (savereply->d_attempt, " ");
- while (tmp!= NULL)
- {
- json_object_array_add(json_array1, json_object_new_string(tmp));
- tmp = strtok (NULL, " ");
- }
- tmp = NULL;
- json_object_object_add(json_obj, "FAILED ON", json_array1);
- }
-
- if (savereply->d_success) {
- json_array2 = json_object_new_array();
- tmp = strtok (savereply->d_success, " ");
- while (tmp!= NULL)
- {
- json_object_array_add(json_array2, json_object_new_string(tmp));
- tmp = strtok (NULL, " ");
- }
- tmp = NULL;
- json_object_object_add(json_obj, "SUCCESSFUL ON", json_array2);
- }
+ blockStr2arrayAddToJsonObj (json_obj, savereply->d_attempt,
+ "FAILED ON", &json_array1);
+ blockStr2arrayAddToJsonObj (json_obj, savereply->d_success,
+ "SUCCESSFUL ON", &json_array2);
json_object_object_add(json_obj, "RESULT",
errCode?json_object_new_string("FAIL"):json_object_new_string("SUCCESS"));
@@ -1347,8 +1802,10 @@ block_delete_cli_format_response(blockDeleteCli *blk, int errCode, char *errMsg,
json_object_to_json_string_ext(json_obj,
mapJsonFlagToJsonCstring(blk->json_resp)));
- json_object_put(json_array1);
- json_object_put(json_array2);
+ if (json_array1)
+ json_object_put(json_array1);
+ if (json_array2)
+ json_object_put(json_array2);
json_object_put(json_obj);
} else {
/* save 'failed on'*/
@@ -1438,7 +1895,7 @@ block_delete_cli_1_svc(blockDeleteCli *blk, struct svc_req *rqstp)
}
- block_delete_cli_format_response(blk, errCode, errMsg, savereply, reply);
+ blockDeleteCliFormatResponse(blk, errCode, errMsg, savereply, reply);
glfs_fini(glfs);
if (savereply) {
@@ -1539,6 +1996,98 @@ block_delete_1_svc(blockDelete *blk, struct svc_req *rqstp)
blockResponse *
+block_modify_1_svc(blockModify *blk, struct svc_req *rqstp)
+{
+ int ret;
+ char *authattr = NULL;
+ char *authcred = NULL;
+ char *exec = NULL;
+ blockResponse *reply = NULL;
+
+
+ if (GB_ALLOC(reply) < 0) {
+ return NULL;
+ }
+ reply->exit = -1;
+
+ /* Check if targetcli and tcmu-runner installed ? */
+ ret = WEXITSTATUS(system(GB_TGCLI_GLFS_CHECK));
+ if (ret == EKEYEXPIRED || ret == 1) {
+ reply->exit = EKEYEXPIRED;
+ if (GB_ASPRINTF(&reply->out,
+ "check if targetcli and tcmu-runner are installed.") == -1) {
+ goto out;
+ }
+ goto out;
+ }
+
+ if (GB_ASPRINTF(&exec, GB_TGCLI_CHECK, blk->block_name) == -1) {
+ goto out;
+ }
+
+ /* Check if block exist on this node ? */
+ if (WEXITSTATUS(system(exec)) == 1) {
+ reply->exit = 0;
+ if (GB_ASPRINTF(&reply->out, "No %s.", blk->block_name) == -1) {
+ goto out;
+ }
+ goto out;
+ }
+ GB_FREE(exec);
+
+ if (blk->auth_mode) {
+ if (GB_ASPRINTF(&authattr, "%s/%s%s/tpg1 set attribute authentication=1",
+ GB_TGCLI_ISCSI, GB_TGCLI_IQN_PREFIX, blk->gbid) == -1) {
+ goto out;
+ }
+
+ if (GB_ASPRINTF(&authcred, "%s/%s%s/tpg1 set auth userid=%s password=%s",
+ GB_TGCLI_ISCSI, GB_TGCLI_IQN_PREFIX, blk->gbid,
+ blk->gbid, blk->passwd) == -1) {
+ goto out;
+ }
+
+ if (GB_ASPRINTF(&exec, "%s && %s && %s", authattr, authcred, GB_TGCLI_SAVE) == -1) {
+ goto out;
+ }
+ } else {
+ if (GB_ASPRINTF(&exec, "%s/%s%s/tpg1 set attribute authentication=0 && %s",
+ GB_TGCLI_ISCSI, GB_TGCLI_IQN_PREFIX, blk->gbid, GB_TGCLI_SAVE) == -1) {
+ goto out;
+ }
+ }
+
+ if (GB_ALLOC_N(reply->out, 4096) < 0) {
+ GB_FREE(reply);
+ goto out;
+ }
+
+ ret = WEXITSTATUS(system(exec));
+ if (ret) {
+ LOG("mgmt", GB_LOG_ERROR,
+ "system(): for block %s executing command %s failed(%s)",
+ blk->block_name, exec, strerror(errno));
+ reply->exit = ret;
+ if (GB_ASPRINTF(&reply->out,
+ "cannot execute auth commands.") == -1) {
+ goto out;
+ }
+ goto out;
+ }
+
+ /* command execution success */
+ reply->exit = 0;
+
+ out:
+ GB_FREE(exec);
+ GB_FREE(authattr);
+ GB_FREE(authcred);
+
+ return reply;
+}
+
+
+blockResponse *
block_list_cli_1_svc(blockListCli *blk, struct svc_req *rqstp)
{
blockResponse *reply;
@@ -1624,7 +2173,7 @@ block_list_cli_1_svc(blockListCli *blk, struct svc_req *rqstp)
}
if (errCode < 0) {
- errCode = 255;
+ errCode = GB_DEFAULT_ERRCODE;
}
reply->exit = errCode;
@@ -1669,10 +2218,27 @@ block_list_cli_1_svc(blockListCli *blk, struct svc_req *rqstp)
return reply;
}
+static bool
+blockhostIsValid (char *status)
+{
+ switch (blockMetaStatusEnumParse(status)) {
+ case GB_CONFIG_SUCCESS:
+ case GB_AUTH_ENFORCEING:
+ case GB_AUTH_ENFORCED:
+ case GB_AUTH_ENFORCE_FAIL:
+ case GB_AUTH_CLEAR_ENFORCED:
+ case GB_AUTH_CLEAR_ENFORCEING:
+ case GB_AUTH_CLEAR_ENFORCE_FAIL:
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
void
-block_info_cli_format_response(blockInfoCli *blk, int errCode,
- char *errMsg, MetaInfo *info,
- struct blockResponse *reply)
+blockInfoCliFormatResponse(blockInfoCli *blk, int errCode,
+ char *errMsg, MetaInfo *info,
+ struct blockResponse *reply)
{
json_object *json_obj = NULL;
json_object *json_array = NULL;
@@ -1685,10 +2251,10 @@ block_info_cli_format_response(blockInfoCli *blk, int errCode,
}
if (errCode < 0) {
- errCode = 255;
+ errCode = GB_DEFAULT_ERRCODE;
}
if (errMsg) {
- block_format_error_response(blk->json_resp, errCode, errMsg, reply);
+ blockFormatErrorResponse(blk->json_resp, errCode, errMsg, reply);
return;
}
@@ -1699,11 +2265,12 @@ block_info_cli_format_response(blockInfoCli *blk, int errCode,
json_object_object_add(json_obj, "GBID", json_object_new_string(info->gbid));
json_object_object_add(json_obj, "SIZE", json_object_new_int64(info->size));
json_object_object_add(json_obj, "HA", json_object_new_int(info->mpath));
+ json_object_object_add(json_obj, "PASSWORD", json_object_new_string(info->passwd));
json_array = json_object_new_array();
for (i = 0; i < info->nhosts; i++) {
- if (blockMetaStatusEnumParse(info->list[i]->status) == GB_CONFIG_SUCCESS) {
+ if (blockhostIsValid (info->list[i]->status)) {
json_object_array_add(json_array, json_object_new_string(info->list[i]->addr));
}
}
@@ -1717,18 +2284,18 @@ block_info_cli_format_response(blockInfoCli *blk, int errCode,
json_object_put(json_obj);
} else {
if (GB_ASPRINTF(&tmp, "NAME: %s\nVOLUME: %s\nGBID: %s\nSIZE: %zu\n"
- "HA: %zu\nBLOCK CONFIG NODE(S):",
- blk->block_name, info->volume, info->gbid,
- info->size, info->mpath) == -1) {
+ "HA: %zu\nPASSWORD: %s\nBLOCK CONFIG NODE(S):",
+ blk->block_name, info->volume, info->gbid, info->size, info->mpath,
+ info->passwd) == -1) {
goto out;
}
for (i = 0; i < info->nhosts; i++) {
- if (blockMetaStatusEnumParse(info->list[i]->status) == GB_CONFIG_SUCCESS) {
- if (GB_ASPRINTF(&out, "%s %s", tmp, info->list[i]->addr) == -1) {
- GB_FREE (tmp);
- goto out;
- }
- tmp = out;
+ if (blockhostIsValid (info->list[i]->status)) {
+ if (GB_ASPRINTF(&out, "%s %s", tmp, info->list[i]->addr) == -1) {
+ GB_FREE (tmp);
+ goto out;
+ }
+ tmp = out;
}
}
if (GB_ASPRINTF(&reply->out, "%s\n", tmp) == -1) {
@@ -1799,7 +2366,7 @@ block_info_cli_1_svc(blockInfoCli *blk, struct svc_req *rqstp)
}
- block_info_cli_format_response(blk, errCode, errMsg, info, reply);
+ blockInfoCliFormatResponse(blk, errCode, errMsg, info, reply);
glfs_fini(glfs);
GB_FREE(errMsg);
blockFreeMetaInfo(info);
diff --git a/rpc/glfs-operations.c b/rpc/glfs-operations.c
index 98de51c..71dd0d2 100644
--- a/rpc/glfs-operations.c
+++ b/rpc/glfs-operations.c
@@ -291,6 +291,9 @@ blockStuffMetaInfo(MetaInfo *info, char *line)
case GB_META_ENTRYCREATE:
strcpy(info->entry, strchr(line, ' ')+1);
break;
+ case GB_META_PASSWD:
+ strcpy(info->passwd, strchr(line, ' ')+1);
+ break;
default:
if(!info->list) {
diff --git a/rpc/glfs-operations.h b/rpc/glfs-operations.h
index 47aced2..f639d86 100644
--- a/rpc/glfs-operations.h
+++ b/rpc/glfs-operations.h
@@ -34,6 +34,7 @@ typedef struct MetaInfo {
size_t size;
size_t mpath;
char entry[16];
+ char passwd[38];
size_t nhosts;
NodeInfo **list;
diff --git a/rpc/rpcl/block.x b/rpc/rpcl/block.x
index 5d9c2a5..df29542 100644
--- a/rpc/rpcl/block.x
+++ b/rpc/rpcl/block.x
@@ -22,6 +22,14 @@ struct blockCreate {
char block_name[255];
};
+struct blockModify {
+ char volume[255];
+ char block_name[255];
+ char gbid[127];
+ char passwd[127];
+ bool auth_mode;
+};
+
struct blockCreateCli {
char volume[255];
u_quad_t size;
@@ -54,6 +62,13 @@ struct blockListCli {
enum JsonResponseFormat json_resp;
};
+struct blockModifyCli {
+ char block_name[255];
+ char volume[255];
+ bool auth_mode;
+ enum JsonResponseFormat json_resp;
+};
+
struct blockResponse {
int exit; /* exit code of the command */
string out<>; /* output; TODO: return respective objects */
@@ -65,6 +80,7 @@ program GLUSTER_BLOCK {
version GLUSTER_BLOCK_VERS {
blockResponse BLOCK_CREATE(blockCreate) = 1;
blockResponse BLOCK_DELETE(blockDelete) = 2;
+ blockResponse BLOCK_MODIFY(blockModify) = 3;
} = 1;
} = 21215311; /* B2 L12 O15 C3 K11 */
@@ -74,5 +90,6 @@ program GLUSTER_BLOCK_CLI {
blockResponse BLOCK_LIST_CLI(blockListCli) = 2;
blockResponse BLOCK_INFO_CLI(blockInfoCli) = 3;
blockResponse BLOCK_DELETE_CLI(blockDeleteCli) = 4;
+ blockResponse BLOCK_MODIFY_CLI(blockModifyCli) = 5;
} = 1;
} = 212153113; /* B2 L12 O15 C3 K11 C3 */
diff --git a/tests/basic.t b/tests/basic.t
index 8514cfb..6d8aa1a 100755
--- a/tests/basic.t
+++ b/tests/basic.t
@@ -79,12 +79,18 @@ sleep 1;
# Block create
TEST gluster-block create ${VOLNAME}/${BLKNAME} ha 1 ${HOST} 1GiB
+# Modify Block with auth enable
+TEST gluster-block modify ${VOLNAME}/${BLKNAME} auth enable
+
# Block list
TEST gluster-block list ${VOLNAME}
# Block info
TEST gluster-block info ${VOLNAME}/${BLKNAME}
+# Modify Block with auth disable
+TEST gluster-block modify ${VOLNAME}/${BLKNAME} auth disable
+
# Block delete
gluster-block delete ${VOLNAME}/${BLKNAME}
@@ -93,10 +99,16 @@ echo -e "\n*** JSON responses ***\n"
# Block create and expect json response
TEST gluster-block create ${VOLNAME}/${BLKNAME} ha 1 ${HOST} 1GiB --json-pretty
+# Modify Block with auth enable and expect json response
+TEST gluster-block modify ${VOLNAME}/${BLKNAME} auth enable --json-pretty
+
# Block list and expect json response
TEST gluster-block list ${VOLNAME} --json-pretty
# Block info and expect json response
TEST gluster-block info ${VOLNAME}/${BLKNAME} --json-pretty
+# Modify Block with auth disable and expect json response
+TEST gluster-block modify ${VOLNAME}/${BLKNAME} auth disable --json-pretty
+
cleanup;
diff --git a/utils/common.h b/utils/common.h
index b43220f..21bf855 100644
--- a/utils/common.h
+++ b/utils/common.h
@@ -52,6 +52,8 @@ static const char *const JsonResponseFormatLookup[] = {
enum JsonResponseFormat jsonResponseFormatParse(const char *opt);
+int convertStringToTrillianParse(const char *opt);
+
ssize_t glusterBlockCreateParseSize(const char *dom, char *value);
# endif /* _COMMON_H */
diff --git a/utils/utils.h b/utils/utils.h
index b0cf778..8cbf128 100644
--- a/utils/utils.h
+++ b/utils/utils.h
@@ -37,6 +37,11 @@
/* Target Info */
# define FAILED_INFO "failed in info"
+/* Target Modify */
+# define FAILED_MODIFY "failed in modify"
+# define FAILED_REMOTE_MODIFY "failed in remote modify"
+# define FAILED_REMOTE_AYNC_MODIFY "failed in remote async modify"
+
/* Target Delete */
# define FAILED_DELETE "failed in delete"
# define FAILED_REMOTE_DELETE "failed in remote delete"
@@ -281,6 +286,7 @@ typedef enum Metakey {
GB_META_HA = 3,
GB_META_ENTRYCREATE = 4,
GB_META_ENTRYDELETE = 5,
+ GB_META_PASSWD = 6,
GB_METAKEY_MAX
} Metakey;
@@ -292,30 +298,43 @@ static const char *const MetakeyLookup[] = {
[GB_META_HA] = "HA",
[GB_META_ENTRYCREATE] = "ENTRYCREATE",
[GB_META_ENTRYDELETE] = "ENTRYDELETE",
+ [GB_META_PASSWD] = "PASSWORD",
[GB_METAKEY_MAX] = NULL
};
typedef enum MetaStatus {
- GB_CONFIG_SUCCESS = 0,
- GB_CONFIG_FAIL = 1,
- GB_CONFIG_INPROGRESS = 2,
- GB_CLEANUP_SUCCESS = 3,
- GB_CLEANUP_FAIL = 4,
- GB_CLEANUP_INPROGRESS = 5,
+ GB_CONFIG_SUCCESS = 0,
+ GB_CONFIG_FAIL = 1,
+ GB_CONFIG_INPROGRESS = 2,
+ GB_AUTH_ENFORCEING = 3,
+ GB_AUTH_ENFORCED = 4,
+ GB_AUTH_ENFORCE_FAIL = 5,
+ GB_AUTH_CLEAR_ENFORCEING = 6,
+ GB_AUTH_CLEAR_ENFORCED = 7,
+ GB_AUTH_CLEAR_ENFORCE_FAIL = 8,
+ GB_CLEANUP_SUCCESS = 9,
+ GB_CLEANUP_FAIL = 10,
+ GB_CLEANUP_INPROGRESS = 11,
GB_METASTATUS_MAX
} MetaStatus;
static const char *const MetaStatusLookup[] = {
- [GB_CONFIG_SUCCESS] = "CONFIGSUCCESS",
- [GB_CONFIG_FAIL] = "CONFIGFAIL",
- [GB_CONFIG_INPROGRESS] = "CONFIGINPROGRESS",
- [GB_CLEANUP_INPROGRESS] = "CLEANUPINPROGRESS",
- [GB_CLEANUP_SUCCESS] = "CLEANUPSUCCESS",
- [GB_CLEANUP_FAIL] = "CLEANUPFAIL",
-
- [GB_METASTATUS_MAX] = NULL,
+ [GB_CONFIG_SUCCESS] = "CONFIGSUCCESS",
+ [GB_CONFIG_FAIL] = "CONFIGFAIL",
+ [GB_CONFIG_INPROGRESS] = "CONFIGINPROGRESS",
+ [GB_AUTH_ENFORCEING] = "AUTHENFORCEING",
+ [GB_AUTH_ENFORCED] = "AUTHENFORCED",
+ [GB_AUTH_ENFORCE_FAIL] = "AUTHENFORCEFAIL",
+ [GB_AUTH_CLEAR_ENFORCEING] = "AUTHCLEARENFORCEING",
+ [GB_AUTH_CLEAR_ENFORCED] = "AUTHCLEARENFORCED",
+ [GB_AUTH_CLEAR_ENFORCE_FAIL] = "AUTHCLEARENFORCEFAIL",
+ [GB_CLEANUP_INPROGRESS] = "CLEANUPINPROGRESS",
+ [GB_CLEANUP_SUCCESS] = "CLEANUPSUCCESS",
+ [GB_CLEANUP_FAIL] = "CLEANUPFAIL",
+
+ [GB_METASTATUS_MAX] = NULL,
};
typedef enum RemoteCreateResp {