summaryrefslogtreecommitdiffstats
path: root/gluster-blockd.c
diff options
context:
space:
mode:
Diffstat (limited to 'gluster-blockd.c')
-rw-r--r--gluster-blockd.c386
1 files changed, 357 insertions, 29 deletions
diff --git a/gluster-blockd.c b/gluster-blockd.c
index 6b73c8b..8807b19 100644
--- a/gluster-blockd.c
+++ b/gluster-blockd.c
@@ -1,6 +1,6 @@
#define _GNU_SOURCE /* See feature_test_macros(7) */
#include <stdio.h>
-#include <netdb.h>
+#include <netdb.h>
#include <sys/socket.h>
# include <uuid/uuid.h>
@@ -31,14 +31,103 @@
# define MSERVER_DELIMITER ","
-blockResponse *
-block_create_cli_1_svc(blockCreateCli *blk, struct svc_req *rqstp)
+typedef enum opterations {
+ CREATE_SRV = 1,
+ LIST_SRV = 2,
+ INFO_SRV = 3,
+ DELETE_SRV = 4,
+ EXEC_SRV = 5
+} opterations;
+
+static void
+gluster_block_1(char *host, void *cobj, opterations opt, blockResponse **reply)
{
- //FILE *fp;
CLIENT *clnt;
int sockfd;
struct hostent *server;
struct sockaddr_in sain;
+
+ if ((sockfd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
+ perror("gluster-blockd: socket");
+ exit(1);
+ }
+ server = gethostbyname(host);
+ if (server == NULL) {
+ fprintf(stderr,"ERROR, no such host\n");
+ exit(0);
+ }
+
+ bzero((char *) &sain, sizeof(sain));
+ sain.sin_family = AF_INET;
+ bcopy((char *)server->h_addr, (char *)&sain.sin_addr.s_addr, server->h_length);
+ sain.sin_port = htons(24006);
+
+ if (connect(sockfd, (struct sockaddr *) &sain, sizeof(sain)) < 0) {
+ perror("gluster-blockd: connect");
+ exit(1);
+ }
+
+ clnt = clnttcp_create ((struct sockaddr_in *) &sain, GLUSTER_BLOCK, GLUSTER_BLOCK_VERS, &sockfd, 0, 0);
+ if (clnt == NULL) {
+ clnt_pcreateerror ("localhost");
+ exit (1);
+ }
+
+ switch(opt) {
+ case CREATE_SRV:
+ *reply = block_create_1((blockCreate *)cobj, clnt);
+ if (*reply == NULL) {
+ clnt_perror (clnt, "call failed gluster-block");
+ }
+ break;
+ case DELETE_SRV:
+ *reply = block_delete_1((blockDelete *)cobj, clnt);
+ if (*reply == NULL) {
+ clnt_perror (clnt, "call failed gluster-block");
+ }
+ break;
+ case INFO_SRV:
+ case LIST_SRV:
+ break;
+ case EXEC_SRV:
+ *reply = block_exec_1((char **)&cobj, clnt);
+ if (*reply == NULL) {
+ clnt_perror (clnt, "call failed gluster-block");
+ }
+ break;
+ }
+ clnt_destroy (clnt);
+}
+
+static char *
+getCfgstring(char* name, char *blkServer)
+{
+ char *cmd;
+ char *exec;
+ char *buf = NULL;
+ blockResponse *reply = NULL;
+
+ asprintf(&cmd, "%s %s", TARGETCLI_GLFS, BACKEND_CFGSTR);
+ asprintf(&exec, cmd, name);
+
+ gluster_block_1(blkServer, exec, EXEC_SRV, &reply);
+ if (!reply || reply->exit) {
+ ERROR("%s on host: %s",
+ FAILED_GATHERING_CFGSTR, blkServer);
+ }
+
+ GB_FREE(cmd);
+ GB_FREE(exec);
+
+ if(reply->out)
+ buf = strdup(reply->out);
+
+ return buf;
+}
+
+blockResponse *
+block_create_cli_1_svc(blockCreateCli *blk, struct svc_req *rqstp)
+{
int ret;
uuid_t out;
static blockCreate *cobj;
@@ -66,43 +155,161 @@ block_create_cli_1_svc(blockCreateCli *blk, struct svc_req *rqstp)
//for
- if ((sockfd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
- perror("gluster-blockd: socket");
- exit(1);
+ gluster_block_1(blk->block_hosts, cobj, CREATE_SRV, &reply);
+
+out:
+ return reply;
+}
+
+static size_t
+glusterBlockCreateParseSize(char *value)
+{
+ char *postfix;
+ char *tmp;
+ size_t sizef;
+
+ if (!value)
+ return -1;
+
+ sizef = strtod(value, &postfix);
+ if (sizef < 0) {
+ ERROR("%s", "size cannot be negative number\n");
+ return -1;
}
- server = gethostbyname(blk->block_hosts);
- if (server == NULL) {
- fprintf(stderr,"ERROR, no such host\n");
- exit(0);
+
+ tmp = postfix;
+ if (*postfix == ' ')
+ tmp = tmp + 1;
+
+ switch (*tmp) {
+ case 'Y':
+ sizef *= 1024;
+ /* fall through */
+ case 'Z':
+ sizef *= 1024;
+ /* fall through */
+ case 'E':
+ sizef *= 1024;
+ /* fall through */
+ case 'P':
+ sizef *= 1024;
+ /* fall through */
+ case 'T':
+ sizef *= 1024;
+ /* fall through */
+ case 'G':
+ sizef *= 1024;
+ /* fall through */
+ case 'M':
+ sizef *= 1024;
+ /* fall through */
+ case 'K':
+ case 'k':
+ sizef *= 1024;
+ /* fall through */
+ case 'b':
+ case '\0':
+ return sizef;
+ break;
+ default:
+ ERROR("%s", "You may use k/K, M, G or T suffixes for "
+ "kilobytes, megabytes, gigabytes and terabytes.");
+ return -1;
}
+}
- bzero((char *) &sain, sizeof(sain));
- sain.sin_family = AF_INET;
- bcopy((char *)server->h_addr, (char *)&sain.sin_addr.s_addr, server->h_length);
- sain.sin_port = htons(24006);
+static int
+glusterBlockParseCfgStringToDef(char* cfgstring,
+ blockCreate *blk)
+{
+ int ret = 0;
+ char *p, *sep;
+
+ /* part before '@' is the volume name */
+ p = cfgstring;
+ sep = strchr(p, '@');
+ if (!sep) {
+ ret = -1;
+ goto fail;
+ }
- if (connect(sockfd, (struct sockaddr *) &sain, sizeof(sain)) < 0) {
- perror("gluster-blockd: connect");
- exit(1);
+ *sep = '\0';
+ /*if (GB_STRDUP(blk->volume, p) < 0) {
+ ret = -1;
+ goto fail;
+ }
+ */
+ strcpy(blk->volume, p);
+
+ /* part between '@' and '/' is the server name */
+ p = sep + 1;
+ sep = strchr(p, '/');
+ if (!sep) {
+ ret = -1;
+ goto fail;
}
- clnt = clnttcp_create ((struct sockaddr_in *) &sain, GLUSTER_BLOCK, GLUSTER_BLOCK_VERS, &sockfd, 0, 0);
- if (clnt == NULL) {
- clnt_pcreateerror ("localhost");
- exit (1);
+ *sep = '\0';
+ /*if (GB_STRDUP(blk->volfileserver, p) < 0) {
+ ret = -1;
+ goto fail;
+ }
+ */
+ strcpy(blk->volfileserver, p);
+
+ /* part between '/' and '(' is the filename */
+ p = sep + 1;
+ sep = strchr(p, '(');
+ if (!sep) {
+ ret = -1;
+ goto fail;
}
- reply = block_create_1(cobj, clnt);
- if (reply == NULL) {
- clnt_perror (clnt, "call failed gluster-blockd");
+ *(sep - 1) = '\0'; /* discard extra space at end of filename */
+ /*if (GB_STRDUP(blk->gbid, p) < 0) {
+ ret = -1;
+ goto fail;
+ }
+ */
+ strcpy(blk->gbid, p);
+
+ /* part between '(' and ')' is the size */
+ p = sep + 1;
+ sep = strchr(p, ')');
+ if (!sep) {
+ ret = -1;
+ goto fail;
}
- clnt_destroy (clnt);
+ *sep = '\0';
+ blk->size = glusterBlockCreateParseSize(p);
+ if (blk->size < 0) {
+ ERROR("%s", "failed while parsing size");
+ ret = -1;
+ goto fail;
+ }
-out:
- return reply;
-}
+ /* part between ')' and '\n' is the status */
+/*
+ p = sep + 1;
+ sep = strchr(p, '\n');
+ if (!sep) {
+ ret = -1;
+ goto fail;
+ }
+
+ *sep = '\0';
+ if (!strcmp(p, " activated"))
+ blk->status = true;
+*/
+ return 0;
+
+ fail:
+// glusterBlockDefFree(blk);
+
+ return ret;
+}
blockResponse *
block_create_1_svc(blockCreate *blk, struct svc_req *rqstp)
@@ -153,3 +360,124 @@ block_create_1_svc(blockCreate *blk, struct svc_req *rqstp)
return obj;
}
+blockResponse *
+block_delete_cli_1_svc(blockDeleteCli *blk, struct svc_req *rqstp)
+{
+ char *cfgstring;
+ static blockCreate *blkcfg;
+ static blockDelete *cobj;
+ static blockResponse *reply;
+
+ if(GB_ALLOC(cobj) < 0)
+ goto out;
+
+ strcpy(cobj->block_name, blk->block_name);
+
+ //for
+ cfgstring = getCfgstring(blk->block_name, blk->block_hosts);
+ if (!cfgstring) {
+ ERROR("%s", "failed while gathering CfgString");
+ goto out;
+ }
+
+ if (GB_ALLOC(blkcfg) < 0)
+ goto out;
+
+ if(glusterBlockParseCfgStringToDef(cfgstring, blkcfg)) {
+ ERROR("%s", "failed while parsing CfgString to glusterBlockDef");
+ goto out;
+ }
+
+ strcpy(cobj->gbid, blkcfg->gbid);
+ gluster_block_1(blk->block_hosts, cobj, DELETE_SRV, &reply);
+
+ if (glusterBlockDeleteEntry(blkcfg)) {
+ ERROR("%s volume: %s host: %s",
+ FAILED_DELETING_FILE, blkcfg->volume, blkcfg->volfileserver);
+ }
+out:
+ return reply;
+}
+
+
+blockResponse *
+block_delete_1_svc(blockDelete *blk, struct svc_req *rqstp)
+{
+ FILE *fp;
+ char *backstore = NULL;
+ char *iqn = NULL;
+ char *exec = NULL;
+ blockResponse *obj = NULL;
+
+ asprintf(&iqn, "%s %s %s%s", TARGETCLI_ISCSI, DELETE, IQN_PREFIX, blk->gbid);
+
+ asprintf(&backstore, "%s %s %s", TARGETCLI_GLFS,
+ DELETE, blk->block_name);
+
+ asprintf(&exec, "%s && %s", backstore, iqn);
+
+ if(GB_ALLOC(obj) < 0)
+ return NULL;
+
+ if (GB_ALLOC_N(obj->out, 4096) < 0) {
+ GB_FREE(obj);
+ return NULL;
+ }
+
+ fp = popen(exec, "r");
+ if (fp != NULL) {
+ size_t newLen = fread(obj->out, sizeof(char), 4096, fp);
+ if (ferror( fp ) != 0) {
+ ERROR("%s", "Error reading command output\n");
+ } else {
+ obj->out[newLen++] = '\0';
+ }
+ obj->exit = WEXITSTATUS(pclose(fp));
+ }
+
+ return obj;
+}
+
+blockResponse *
+block_exec_1_svc(char **cmd, struct svc_req *rqstp)
+{
+ FILE *fp;
+ static blockResponse *obj;
+
+ if(GB_ALLOC(obj) < 0)
+ return NULL;
+
+ if (GB_ALLOC_N(obj->out, 4096) < 0) {
+ GB_FREE(obj);
+ return NULL;
+ }
+
+ fp = popen(*cmd, "r");
+ if (fp != NULL) {
+ size_t newLen = fread(obj->out, sizeof(char), 4996, fp);
+ if (ferror( fp ) != 0) {
+ ERROR("%s", "Error reading command output\n");
+ } else {
+ obj->out[newLen++] = '\0';
+ }
+ obj->exit = WEXITSTATUS(pclose(fp));
+ }
+
+ return obj;
+}
+
+blockResponse *
+block_list_cli_1_svc(blockListCli *blk, struct svc_req *rqstp)
+{
+
+
+ return NULL;
+}
+
+blockResponse *
+block_info_cli_1_svc(blockInfoCli *blk, struct svc_req *rqstp)
+{
+
+
+ return NULL;
+}