summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKaushik BV <kaushikbv@gluster.com>2011-07-12 05:33:29 +0000
committerAnand Avati <avati@gluster.com>2011-07-12 09:03:03 -0700
commit1d0cb953bb117689fb8381d65932ead486d13b05 (patch)
tree50e87fcca9bcbac92e116c53dd7bb918ee6b031c
parentf9e0638b7597f4b1a4245f63c94d3d6bd3158136 (diff)
mgmt/Glusterd: Implementation volume set help/help-xml
Signed-off-by: Kaushik BV <kaushikbv@gluster.com> Signed-off-by: Anand Avati <avati@gluster.com> BUG: 2041 (volume set help option) URL: http://bugs.gluster.com/cgi-bin/bugzilla3/show_bug.cgi?id=2041
-rw-r--r--cli/src/cli-cmd-parser.c8
-rw-r--r--cli/src/cli-rpc-ops.c19
-rw-r--r--configure.ac10
-rw-r--r--libglusterfs/src/xlator.c105
-rw-r--r--libglusterfs/src/xlator.h8
-rw-r--r--xlators/mgmt/glusterd/src/Makefile.am4
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-handler.c17
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-op-sm.c98
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-rpc-ops.c10
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-volgen.c331
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-volgen.h1
11 files changed, 545 insertions, 66 deletions
diff --git a/cli/src/cli-cmd-parser.c b/cli/src/cli-cmd-parser.c
index 2c1897550ec..a8aebaeb03c 100644
--- a/cli/src/cli-cmd-parser.c
+++ b/cli/src/cli-cmd-parser.c
@@ -657,7 +657,7 @@ cli_cmd_volume_set_parse (const char **words, int wordcount, dict_t **options)
if (!dict)
goto out;
- if (wordcount < 4)
+ if (wordcount < 3)
goto out;
volname = (char *)words[2];
@@ -666,6 +666,12 @@ cli_cmd_volume_set_parse (const char **words, int wordcount, dict_t **options)
ret = dict_set_str (dict, "volname", volname);
+ if (!strcmp (volname, "help") && !words[3] && !words[4])
+ ret = dict_set_str (dict, "help", volname);
+
+ if (!strcmp (volname, "help-xml") && !words[3] && !words[4])
+ ret = dict_set_str (dict, "help-xml", volname);
+
if (ret)
goto out;
diff --git a/cli/src/cli-rpc-ops.c b/cli/src/cli-rpc-ops.c
index 5b1f7f62993..92e5a32cc44 100644
--- a/cli/src/cli-rpc-ops.c
+++ b/cli/src/cli-rpc-ops.c
@@ -984,6 +984,8 @@ gf_cli3_1_set_volume_cbk (struct rpc_req *req, struct iovec *iov,
{
gf1_cli_set_vol_rsp rsp = {0,};
int ret = 0;
+ dict_t *dict = NULL;
+ char *help_str = NULL;
if (-1 == req->rpc_status) {
goto out;
@@ -999,9 +1001,24 @@ gf_cli3_1_set_volume_cbk (struct rpc_req *req, struct iovec *iov,
if (rsp.op_ret && strcmp (rsp.op_errstr, ""))
cli_out ("%s", rsp.op_errstr);
- else
+
+ dict = dict_new ();
+
+ if (!dict) {
+ ret = -1;
+ goto out;
+ }
+
+ ret = dict_unserialize (rsp.dict.dict_val, rsp.dict.dict_len, &dict);
+
+ if (ret)
+ goto out;
+
+ if (dict_get_str (dict, "help-str", &help_str))
cli_out ("Set volume %s", (rsp.op_ret) ? "unsuccessful":
"successful");
+ else
+ cli_out (help_str);
ret = rsp.op_ret;
diff --git a/configure.ac b/configure.ac
index 8e2fbb1dffa..a0112e0e985 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1,4 +1,5 @@
dnl Copyright (c) 2006-2010 Gluster, Inc. <http://www.gluster.com>
+
dnl This file is part of GlusterFS.
dnl
dnl GlusterFS is free software; you can redistribute it and/or modify
@@ -323,6 +324,15 @@ AC_SUBST(SYNCDAEMON_COMPILE)
AC_SUBST(SYNCDAEMON_SUBDIR)
# end SYNCDAEMON section
+#check if libxml is present if so enable HAVE_LIB_XML
+echo -n "checking if libxml2 is present... "
+
+PKG_CHECK_MODULES([LIBXML2], [libxml-2.0 >= 2.6.19],
+ [echo "yes (features requiring libxml2 enabled)" AC_DEFINE(HAVE_LIB_XML, 1, [define if libxml2 is present])],
+ [echo "no"] )
+
+AC_SUBST(LIBXML2_CFLAGS)
+AC_SUBST(LIBXML2_LIBS)
dnl FreeBSD > 5 has execinfo as a Ported library for giving a workaround
dnl solution to GCC backtrace functionality
diff --git a/libglusterfs/src/xlator.c b/libglusterfs/src/xlator.c
index 9b91729ecae..ccc32b71118 100644
--- a/libglusterfs/src/xlator.c
+++ b/libglusterfs/src/xlator.c
@@ -1178,7 +1178,64 @@ xlator_set_type_virtual (xlator_t *xl, const char *type)
out:
return -1;
}
+int32_t
+xlator_volopt_dynload (char *xlator_type, void **dl_handle,
+ volume_opt_list_t *opt_list)
+{
+ int ret = -1;
+ char *name = NULL;
+ void *handle = NULL;
+ volume_opt_list_t *vol_opt = NULL;
+
+ GF_VALIDATE_OR_GOTO ("xlator", xlator_type, out);
+
+ GF_ASSERT (dl_handle);
+
+ if (*dl_handle)
+ if (dlclose (*dl_handle))
+ gf_log ("xlator", GF_LOG_WARNING, "Unable to close "
+ "previously opened handle( may be stale)."
+ "Ignoring the invalid handle");
+
+ ret = gf_asprintf (&name, "%s/%s.so", XLATORDIR, xlator_type);
+ if (-1 == ret) {
+ gf_log ("xlator", GF_LOG_ERROR, "asprintf failed");
+ goto out;
+ }
+
+ ret = -1;
+
+ gf_log ("xlator", GF_LOG_TRACE, "attempt to load file %s", name);
+
+ handle = dlopen (name, RTLD_NOW|RTLD_GLOBAL);
+ if (!handle) {
+ gf_log ("xlator", GF_LOG_WARNING, "%s", dlerror ());
+ goto out;
+ }
+ *dl_handle = handle;
+
+ INIT_LIST_HEAD (&opt_list->list);
+
+ vol_opt = GF_CALLOC (1, sizeof (volume_opt_list_t),
+ gf_common_mt_volume_opt_list_t);
+ if (!vol_opt) {
+ goto out;
+ }
+
+ if (!(vol_opt->given_opt = dlsym (handle, "options"))) {
+ dlerror ();
+ gf_log ("xlator", GF_LOG_DEBUG,
+ "Strict option validation not enforced -- neglecting");
+ }
+ list_add_tail (&vol_opt->list, &opt_list->list);
+
+ ret = 0;
+ out:
+ gf_log ("xlator", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+
+}
int32_t
xlator_dynload (xlator_t *xl)
@@ -1853,3 +1910,51 @@ glusterd_check_log_level (const char *value)
return log_level;
}
+
+int
+xlator_get_volopt_info (struct list_head *opt_list, char *key, char **def_val,
+ char **descr)
+{
+
+ int index = 0;
+ int ret = -1;
+ volume_opt_list_t *vol_list = NULL;
+ volume_option_t *opt = NULL;
+
+ if (!opt_list || !key || !def_val ) {
+ gf_log ("", GF_LOG_WARNING, " Parameters to the function not "
+ "valid");
+ ret = -1;
+ goto out;
+ }
+
+ if (list_empty (opt_list)) {
+ gf_log ("xlator", GF_LOG_WARNING, "No elements in Volume option"
+ " list");
+ ret = -1;
+ goto out;
+ }
+
+
+ vol_list = list_entry (opt_list->next, volume_opt_list_t, list);
+
+ opt = vol_list->given_opt;
+
+ for (index = 0; opt[index].key && opt[index].key[0] ; index++) {
+ if (strncmp (key, opt[index].key[0], strlen (key)))
+ continue;
+
+ *def_val = opt[index].default_value;
+ if (descr)
+ *descr = opt[index].description;
+ ret = 0;
+ goto out;
+ }
+
+ ret = -1;
+
+out:
+ gf_log ("", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+
+}
diff --git a/libglusterfs/src/xlator.h b/libglusterfs/src/xlator.h
index 60fd777614a..23fb3192ab1 100644
--- a/libglusterfs/src/xlator.h
+++ b/libglusterfs/src/xlator.h
@@ -786,6 +786,7 @@ typedef struct volume_options {
char *value[ZR_OPTION_MAX_ARRAY_SIZE];
/* If specified, will check for one of
the value from this array */
+ char *default_value;
char *description; /* about the key */
} volume_option_t;
@@ -881,7 +882,8 @@ int _volume_option_value_validate_attacherr (xlator_t *xl,
data_pair_t *pair,
volume_option_t *opt,
char **op_errstr);
-
-
-
+int32_t xlator_volopt_dynload (char *xlator_type, void **dl_handle,
+ volume_opt_list_t *vol_opt_handle);
+int xlator_get_volopt_info (struct list_head *opt_list, char *key,
+ char **def_val, char **descr);
#endif /* _XLATOR_H */
diff --git a/xlators/mgmt/glusterd/src/Makefile.am b/xlators/mgmt/glusterd/src/Makefile.am
index 1c89dba9776..714b78e6244 100644
--- a/xlators/mgmt/glusterd/src/Makefile.am
+++ b/xlators/mgmt/glusterd/src/Makefile.am
@@ -1,6 +1,6 @@
xlator_LTLIBRARIES = glusterd.la
xlatordir = $(libdir)/glusterfs/$(PACKAGE_VERSION)/xlator/mgmt
-glusterd_la_LDFLAGS = -module -avoidversion
+glusterd_la_LDFLAGS = -module -avoidversion $(LIBXML2_LIBS)
glusterd_la_SOURCES = glusterd.c glusterd-handler.c glusterd-sm.c glusterd-op-sm.c \
glusterd-utils.c glusterd-rpc-ops.c glusterd-store.c glusterd-handshake.c \
glusterd-pmap.c glusterd-volgen.c glusterd-rebalance.c
@@ -17,7 +17,7 @@ AM_CFLAGS = -fPIC -D_FILE_OFFSET_BITS=64 -D_GNU_SOURCE -Wall -D$(GF_HOST_OS)\
-I$(rpclibdir) -L$(xlatordir)/ -I$(CONTRIBDIR)/rbtree -I$(top_srcdir)/rpc/xdr/src\
-I$(top_srcdir)/rpc/rpc-lib/src -I$(CONTRIBDIR)/uuid -I$(top_srcdir)/contrib/md5 -DGFS_PREFIX=\"$(prefix)\" \
-DDATADIR=\"$(localstatedir)\" -DGSYNCD_PREFIX=\"$(libexecdir)/glusterfs\"\
- -DSYNCDAEMON_COMPILE=$(SYNCDAEMON_COMPILE)
+ -DSYNCDAEMON_COMPILE=$(SYNCDAEMON_COMPILE) $(LIBXML2_CFLAGS)
CLEANFILES =
diff --git a/xlators/mgmt/glusterd/src/glusterd-handler.c b/xlators/mgmt/glusterd/src/glusterd-handler.c
index 5f2460d5ee9..8acd85cc378 100644
--- a/xlators/mgmt/glusterd/src/glusterd-handler.c
+++ b/xlators/mgmt/glusterd/src/glusterd-handler.c
@@ -1938,18 +1938,23 @@ glusterd_handle_set_volume (rpcsvc_request_t *req)
ret = dict_get_str (dict, "key1", &key);
if (ret) {
- gf_log ("", GF_LOG_WARNING, "Unable to get key, while"
- "handling volume set for %s",volname);
- goto out;
+ if (strcmp (volname, "help-xml") && strcmp (volname, "help")) {
+ gf_log ("", GF_LOG_WARNING, "Unable to get key, while"
+ "handling volume set for %s",volname);
+ goto out;
+ }
}
ret = dict_get_str (dict, "value1", &value);
if (ret) {
- gf_log ("", GF_LOG_WARNING, "Unable to get value, while"
- "handling volume set for %s",volname);
- goto out;
+ if (strcmp (volname, "help-xml") && strcmp (volname, "help")) {
+ gf_log ("", GF_LOG_WARNING, "Unable to get value, while"
+ "handling volume set for %s",volname);
+ goto out;
+ }
}
+
gf_cmd_log ("volume set", "volume-name:%s: key:%s, value:%s",volname,
key, value);
ret = glusterd_op_begin (req, GD_OP_SET_VOLUME, dict, _gf_true);
diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.c b/xlators/mgmt/glusterd/src/glusterd-op-sm.c
index 831e6bbdc40..83f64bf9d26 100644
--- a/xlators/mgmt/glusterd/src/glusterd-op-sm.c
+++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.c
@@ -1345,6 +1345,39 @@ glusterd_op_stage_set_volume (dict_t *dict, char **op_errstr)
if (!val_dict)
goto out;
+ ret = dict_get_int32 (dict, "count", &dict_count);
+
+ if (ret) {
+ gf_log ("", GF_LOG_ERROR, "Count(dict),not set in Volume-Set");
+ goto out;
+ }
+
+ if ( dict_count == 0 ) {
+ /*No options would be specified of volume set help */
+ if (dict_get (dict, "help" )) {
+ ret = 0;
+ goto out;
+ }
+
+ if (dict_get (dict, "help-xml" )) {
+
+#if (HAVE_LIB_XML)
+ ret = 0;
+ goto out;
+#else
+ ret = -1;
+ gf_log ("", GF_LOG_ERROR, "libxml not present in the"
+ "system");
+ *op_errstr = gf_strdup ("Error: xml libraries not "
+ "present to produce xml-output");
+ goto out;
+#endif
+ }
+ gf_log ("", GF_LOG_ERROR, "No options received ");
+ *op_errstr = gf_strdup ("Options not specified");
+ ret = -1;
+ goto out;
+ }
ret = dict_get_str (dict, "volname", &volname);
if (ret) {
@@ -1353,7 +1386,6 @@ glusterd_op_stage_set_volume (dict_t *dict, char **op_errstr)
}
exists = glusterd_check_volume_exists (volname);
-
if (!exists) {
snprintf (errstr, sizeof (errstr), "Volume %s does not exist",
volname);
@@ -1369,27 +1401,6 @@ glusterd_op_stage_set_volume (dict_t *dict, char **op_errstr)
goto out;
}
- ret = dict_get_int32 (dict, "count", &dict_count);
-
- if (ret) {
- gf_log ("", GF_LOG_ERROR, "Count(dict),not set in Volume-Set");
- goto out;
- }
-
- if ( dict_count == 1 ) {
- if (dict_get (dict, "history" )) {
- ret = 0;
- goto out;
- }
-
- gf_log ("", GF_LOG_ERROR, "No options received ");
- *op_errstr = gf_strdup ("Options not specified");
- ret = -1;
- goto out;
- }
-
-
-
for ( count = 1; ret != 1 ; count++ ) {
global_opt = _gf_false;
sprintf (str, "key%d", count);
@@ -5609,6 +5620,25 @@ glusterd_op_log_level (dict_t *dict)
}
static int
+glusterd_volset_help (dict_t *dict)
+{
+ int ret = -1;
+ gf_boolean_t xml_out = _gf_false;
+
+ if (dict_get (dict, "help" ))
+ xml_out = _gf_false;
+ else if (dict_get (dict, "help-xml" ))
+ xml_out = _gf_true;
+ else
+ goto out;
+
+ ret = glusterd_get_volopt_content (xml_out);
+ out:
+ gf_log ("glusterd", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+}
+
+static int
glusterd_op_set_volume (dict_t *dict)
{
int ret = 0;
@@ -5623,7 +5653,8 @@ glusterd_op_set_volume (dict_t *dict)
char *value = NULL;
char str[50] = {0, };
gf_boolean_t global_opt = _gf_false;
- glusterd_volinfo_t *voliter = NULL;
+ glusterd_volinfo_t *voliter = NULL;
+ int32_t dict_count = 0;
this = THIS;
GF_ASSERT (this);
@@ -5631,8 +5662,21 @@ glusterd_op_set_volume (dict_t *dict)
priv = this->private;
GF_ASSERT (priv);
- ret = dict_get_str (dict, "volname", &volname);
+ ret = dict_get_int32 (dict, "count", &dict_count);
+ if (ret) {
+ gf_log ("", GF_LOG_ERROR, "Count(dict),not set in Volume-Set");
+ goto out;
+ }
+
+ if ( dict_count == 0 ) {
+ ret = glusterd_volset_help (dict);
+ if (ret)
+ gf_log ("glusterd", GF_LOG_ERROR, "Volume set help"
+ "internal error");
+ goto out;
+ }
+ ret = dict_get_str (dict, "volname", &volname);
if (ret) {
gf_log ("", GF_LOG_ERROR, "Unable to get volume name");
goto out;
@@ -5711,7 +5755,6 @@ glusterd_op_set_volume (dict_t *dict)
}
}
-
if ( count == 1 ) {
gf_log ("", GF_LOG_ERROR, "No options received ");
ret = -1;
@@ -5782,11 +5825,8 @@ glusterd_op_set_volume (dict_t *dict)
}
}
-
-
ret = 0;
-
-out:
+ out:
if (key_fixed)
GF_FREE (key_fixed);
gf_log ("", GF_LOG_DEBUG, "returning %d", ret);
diff --git a/xlators/mgmt/glusterd/src/glusterd-rpc-ops.c b/xlators/mgmt/glusterd/src/glusterd-rpc-ops.c
index 6dc6be593ff..b7d800ffcdc 100644
--- a/xlators/mgmt/glusterd/src/glusterd-rpc-ops.c
+++ b/xlators/mgmt/glusterd/src/glusterd-rpc-ops.c
@@ -191,10 +191,20 @@ glusterd_op_send_cli_response (glusterd_op_t op, int32_t op_ret,
rsp.op_ret = op_ret;
rsp.op_errno = op_errno;
rsp.volname = "";
+ ctx = op_ctx;
+
if (op_errstr)
rsp.op_errstr = op_errstr;
else
rsp.op_errstr = "";
+ if (ctx) {
+ ret = dict_allocate_and_serialize (ctx,
+ &rsp.dict.dict_val,
+ (size_t*)&rsp.dict.dict_len);
+ if (ret == 0)
+ free_ptr = rsp.dict.dict_val;
+ }
+
cli_rsp = &rsp;
sfunc = gf_xdr_serialize_cli_set_vol_rsp;
break;
diff --git a/xlators/mgmt/glusterd/src/glusterd-volgen.c b/xlators/mgmt/glusterd/src/glusterd-volgen.c
index fc4ffa8c31b..ad8b610cc59 100644
--- a/xlators/mgmt/glusterd/src/glusterd-volgen.c
+++ b/xlators/mgmt/glusterd/src/glusterd-volgen.c
@@ -25,6 +25,11 @@
#include <fnmatch.h>
+#if (HAVE_LIB_XML)
+#include <libxml/encoding.h>
+#include <libxml/xmlwriter.h>
+#endif
+
#include "xlator.h"
#include "glusterd.h"
#include "defaults.h"
@@ -122,8 +127,9 @@ static struct volopt_map_entry glusterd_volopt_map[] = {
{VKEY_DIAG_LAT_MEASUREMENT, "debug/io-stats", "latency-measurement", "off", NO_DOC, 0 },
{"diagnostics.dump-fd-stats", "debug/io-stats", NULL, NULL, NO_DOC, 0 },
{VKEY_DIAG_CNT_FOP_HITS, "debug/io-stats", "count-fop-hits", "off", NO_DOC, 0 },
- {"diagnostics.brick-log-level", "debug/io-stats", "!log-level", NULL, DOC, 0},
- {"diagnostics.client-log-level", "debug/io-stats", "!log-level", NULL, DOC, 0},
+
+ {"diagnostics.brick-log-level", "debug/io-stats", "!brick-log-level", NULL, DOC, 0},
+ {"diagnostics.client-log-level", "debug/io-stats", "!client-log-level", NULL, DOC, 0},
{"diagnostics.brick-sys-log-level", "debug/io-stats", "!sys-log-level", NULL, DOC, 0},
{"diagnostics.client-sys-log-level", "debug/io-stats", "!sys-log-level", NULL, DOC, 0},
@@ -166,26 +172,26 @@ static struct volopt_map_entry glusterd_volopt_map[] = {
{"nfs.export-dirs", "nfs/server", "nfs3.export-dirs", NULL, GLOBAL_DOC, 0},
{"nfs.export-volumes", "nfs/server", "nfs3.export-volumes", NULL, GLOBAL_DOC, 0},
{"nfs.addr-namelookup", "nfs/server", "rpc-auth.addr.namelookup", NULL, GLOBAL_DOC, 0},
- {"nfs.dynamic-volumes", "nfs/server", "nfs.dynamic-volumes", NULL, GLOBAL_DOC, 0},
+ {"nfs.dynamic-volumes", "nfs/server", "nfs.dynamic-volumes", NULL, GLOBAL_NO_DOC, 0},
{"nfs.register-with-portmap", "nfs/server", "rpc.register-with-portmap", NULL, GLOBAL_DOC, 0},
{"nfs.port", "nfs/server", "nfs.port", NULL, GLOBAL_DOC, 0},
- {"nfs.rpc-auth-unix", "nfs/server", "!nfs.rpc-auth-auth-unix", NULL, DOC, 0},
- {"nfs.rpc-auth-null", "nfs/server", "!nfs.rpc-auth-auth-null", NULL, DOC, 0},
- {"nfs.rpc-auth-allow", "nfs/server", "!nfs.rpc-auth.addr.allow", NULL, DOC, 0},
- {"nfs.rpc-auth-reject", "nfs/server", "!nfs.rpc-auth.addr.reject", NULL, DOC, 0},
- {"nfs.ports-insecure", "nfs/server", "!nfs.auth.ports.insecure", NULL, DOC, 0},
+ {"nfs.rpc-auth-unix", "nfs/server", "!rpc-auth.auth-unix.*", NULL, DOC, 0},
+ {"nfs.rpc-auth-null", "nfs/server", "!rpc-auth.auth.null.*", NULL, DOC, 0},
+ {"nfs.rpc-auth-allow", "nfs/server", "!rpc-auth.addr.*.allow", NULL, DOC, 0},
+ {"nfs.rpc-auth-reject", "nfs/server", "!rpc-auth.addr.*.reject", NULL, DOC, 0},
+ {"nfs.ports-insecure", "nfs/server", "!rpc-auth.ports.*.insecure", NULL, DOC, 0},
{"nfs.transport-type", "nfs/server", "!nfs.transport-type", NULL, DOC, 0},
- {"nfs.trusted-sync", "nfs/server", "!nfs-trusted-sync", NULL, DOC, 0},
- {"nfs.trusted-write", "nfs/server", "!nfs-trusted-write", NULL, DOC, 0},
- {"nfs.volume-access", "nfs/server", "!nfs-volume-access", NULL, DOC, 0},
- {"nfs.export-dir", "nfs/server", "!nfs-export-dir", NULL, DOC, 0},
+ {"nfs.trusted-sync", "nfs/server", "!nfs3.*.trusted-sync", NULL, DOC, 0},
+ {"nfs.trusted-write", "nfs/server", "!nfs3.*.trusted-write", NULL, DOC, 0},
+ {"nfs.volume-access", "nfs/server", "!nfs3.*.volume-access", NULL, DOC, 0},
+ {"nfs.export-dir", "nfs/server", "!nfs3.*.export-dir", NULL, DOC, 0},
{"nfs.disable", "nfs/server", "!nfs-disable", NULL, DOC, 0},
{VKEY_FEATURES_QUOTA, "features/marker", "quota", "off", NO_DOC, OPT_FLAG_FORCE},
{VKEY_FEATURES_LIMIT_USAGE, "features/quota", "limit-set", NULL, NO_DOC, 0},
- {"features.quota-timeout", "features/quota", "timeout", "0", NO_DOC, 0},
+ {"features.quota-timeout", "features/quota", "timeout", "0", DOC, 0},
{NULL, }
};
@@ -1225,8 +1231,9 @@ loglevel_option_handler (volgen_graph_t *graph,
char *role = param;
struct volopt_map_entry vme2 = {0,};
- if (strcmp (vme->option, "!log-level") != 0 ||
- !strstr (vme->key, role))
+ if ( (strcmp (vme->option, "!client-log-level") != 0 &&
+ strcmp (vme->option, "!brick-log-level") != 0)
+ || !strstr (vme->key, role))
return 0;
memcpy (&vme2, vme, sizeof (vme2));
@@ -1532,6 +1539,282 @@ perfxl_option_handler (volgen_graph_t *graph, struct volopt_map_entry *vme,
return -1;
}
+#if (HAVE_LIB_XML)
+static int
+end_sethelp_xml_doc (xmlTextWriterPtr writer)
+{
+ int ret = -1;
+
+ ret = xmlTextWriterEndElement(writer);
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not end an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+ ret = xmlTextWriterEndDocument (writer);
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not end an "
+ "xmlDocument");
+ ret = -1;
+ goto out;
+ }
+ ret = 0;
+ out:
+ gf_log ("glusterd", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+
+}
+
+static int
+init_sethelp_xml_doc (xmlTextWriterPtr *writer, xmlBufferPtr *buf)
+{
+ int ret;
+
+ *buf = xmlBufferCreateSize (8192);
+ if (buf == NULL) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Error creating the xml "
+ "buffer");
+ ret = -1;
+ goto out;
+ }
+
+ xmlBufferSetAllocationScheme (*buf,XML_BUFFER_ALLOC_DOUBLEIT);
+
+ *writer = xmlNewTextWriterMemory(*buf, 0);
+ if (writer == NULL) {
+ gf_log ("glusterd", GF_LOG_ERROR, " Error creating the xml "
+ "writer");
+ ret = -1;
+ goto out;
+ }
+
+ ret = xmlTextWriterStartDocument(*writer, "1.0", "UTF-8", "yes");
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Error While starting the "
+ "xmlDoc");
+ goto out;
+ }
+
+ ret = xmlTextWriterStartElement(*writer,
+ (xmlChar *)"volumeOptionsDefaults");
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not create an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+
+
+ ret = 0;
+
+ out:
+ gf_log ("glusterd", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+
+}
+
+static int
+xml_add_volset_element (xmlTextWriterPtr writer, const char *name,
+ const char *def_val, const char *dscrpt)
+{
+
+ int ret = -1;
+
+ GF_ASSERT (name);
+
+ ret = xmlTextWriterStartElement(writer, (xmlChar *) "volumeOption");
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not create an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+
+ ret = xmlTextWriterWriteFormatElement(writer, (xmlChar*)"defaultValue",
+ "%s", def_val);
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not create an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+
+ ret = xmlTextWriterWriteFormatElement(writer, (xmlChar *)"Description",
+ "%s", dscrpt );
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not create an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+
+ ret = xmlTextWriterWriteFormatElement(writer, (xmlChar *) "name", "%s",
+ name);
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not create an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+
+ ret = xmlTextWriterEndElement(writer);
+ if (ret < 0) {
+ gf_log ("glusterd", GF_LOG_ERROR, "Could not end an "
+ "xmlElemetnt");
+ ret = -1;
+ goto out;
+ }
+
+ ret = 0;
+ out:
+ gf_log ("glusterd", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+
+}
+
+#endif
+
+static int
+get_key_from_volopt ( struct volopt_map_entry *vme, char **key)
+{
+ int ret = 0;
+
+ GF_ASSERT (vme);
+ GF_ASSERT (key);
+
+
+ if (vme->option) {
+ if (vme->option[0] == '!') {
+ *key = vme->option + 1;
+ if (!*key[0])
+ ret = -1;
+ } else {
+ *key = vme->option;
+ }
+ } else {
+ *key = strchr (vme->key, '.');
+ if (*key) {
+ (*key) ++;
+ if (!*key[0])
+ ret = -1;
+ } else {
+ ret = -1;
+ }
+ }
+
+ if (ret)
+ gf_log ("glusterd", GF_LOG_ERROR, "Wrong entry found in "
+ "glusterd_volopt_map entry %s", vme->key);
+ else
+ gf_log ("glusterd", GF_LOG_DEBUG, "Returning %d", ret);
+
+ return ret;
+}
+
+
+int
+glusterd_get_volopt_content (gf_boolean_t xml_out)
+{
+
+ char *xlator_type = NULL;
+ void *dl_handle = NULL;
+ volume_opt_list_t vol_opt_handle;
+ char *key = NULL;
+ struct volopt_map_entry *vme = NULL;
+ int ret = -1;
+ char *def_val = NULL;
+ char *descr = NULL;
+ char output_string[8192] = {0, };
+ char *output = NULL;
+ char tmp_str[1024] = {0, };
+ dict_t *ctx = NULL;
+#if (HAVE_LIB_XML)
+ xmlTextWriterPtr writer = NULL;
+ xmlBufferPtr buf = NULL;
+
+ if (xml_out) {
+ ret = init_sethelp_xml_doc (&writer, &buf);
+ if (ret) /*logging done in init_xml_lib*/
+ goto out;
+ }
+#endif
+
+ ctx = glusterd_op_get_ctx (GD_OP_SET_VOLUME);
+
+ if (!ctx) {
+ /*extract the vol-set-help output only in host glusterd*/
+ ret = 0;
+ goto out;
+ }
+
+ for (vme = &glusterd_volopt_map[0]; vme->key; vme++) {
+
+ if ( ( vme->type == NO_DOC) || (vme->type == GLOBAL_NO_DOC) )
+ continue;
+
+ if (get_key_from_volopt (vme, &key))
+ goto out; /*Some error while getin key*/
+
+ if (!xlator_type || strcmp (vme->voltype, xlator_type)){
+ ret = xlator_volopt_dynload (vme->voltype,
+ &dl_handle,
+ &vol_opt_handle);
+ if (ret)
+ continue;
+ }
+
+ ret = xlator_get_volopt_info (&vol_opt_handle.list, key,
+ &def_val, &descr);
+ if (ret) /*Swallow Error i.e if option not found*/
+ continue;
+
+ if (xml_out) {
+#if (HAVE_LIB_XML)
+ if (xml_add_volset_element (writer,vme->key,
+ def_val, descr))
+ goto out;
+#else
+ gf_log ("glusterd", GF_LOG_ERROR, "Libxml not present");
+#endif
+ } else {
+ snprintf (tmp_str, 1024, "Option: %s\nDefault "
+ "Value: %s\nDescription: %s\n\n",
+ vme->key, def_val, descr);
+ strcat (output_string, tmp_str);
+ }
+ }
+
+#if (HAVE_LIB_XML)
+ if ((xml_out) &&
+ (ret = end_sethelp_xml_doc (writer)))
+ goto out;
+#else
+ if (xml_out)
+ gf_log ("glusterd", GF_LOG_ERROR, "Libxml not present");
+#endif
+
+ if (!xml_out)
+ output = gf_strdup (output_string);
+ else
+#if (HAVE_LIB_XML)
+ output = gf_strdup ((char *)buf->content);
+#else
+ gf_log ("glusterd", GF_LOG_ERROR, "Libxml not present");
+#endif
+
+ if (NULL == output) {
+ ret = -1;
+ goto out;
+ }
+
+ ret = dict_set_dynstr (ctx, "help-str", output);
+ out:
+ gf_log ("glusterd", GF_LOG_DEBUG, "Returning %d", ret);
+ return ret;
+
+}
+
static int
client_graph_builder (volgen_graph_t *graph, glusterd_volinfo_t *volinfo,
dict_t *set_dict, void *param)
@@ -1762,7 +2045,7 @@ nfs_option_handler (volgen_graph_t *graph,
if ( !volinfo || !volinfo->volname)
return 0;
- if (! strcmp (vme->option, "!nfs.rpc-auth.addr.allow")) {
+ if (! strcmp (vme->option, "!rpc-auth.addr.*.allow")) {
ret = gf_asprintf (&aa, "rpc-auth.addr.%s.allow",
volinfo->volname);
@@ -1775,7 +2058,7 @@ nfs_option_handler (volgen_graph_t *graph,
return -1;
}
- if (! strcmp (vme->option, "!nfs.rpc-auth.addr.reject")) {
+ if (! strcmp (vme->option, "!rpc-auth.addr.%s.reject")) {
ret = gf_asprintf (&aa, "rpc-auth.addr.%s.reject",
volinfo->volname);
@@ -1788,7 +2071,7 @@ nfs_option_handler (volgen_graph_t *graph,
return -1;
}
- if (! strcmp (vme->option, "!nfs.rpc-auth-auth-unix")) {
+ if (! strcmp (vme->option, "!rpc-auth.auth-unix.*")) {
ret = gf_asprintf (&aa, "rpc-auth.auth.unix.%s",
volinfo->volname);
@@ -1800,7 +2083,7 @@ nfs_option_handler (volgen_graph_t *graph,
if (ret)
return -1;
}
- if (! strcmp (vme->option, "!nfs.rpc-auth-auth-null")) {
+ if (! strcmp (vme->option, "!rpc-auth.auth.null.*")) {
ret = gf_asprintf (&aa, "rpc-auth.auth.null.%s",
volinfo->volname);
@@ -1813,7 +2096,7 @@ nfs_option_handler (volgen_graph_t *graph,
return -1;
}
- if (! strcmp (vme->option, "!nfs-trusted-sync")) {
+ if (! strcmp (vme->option, "!nfs3.%s.trusted-sync")) {
ret = gf_asprintf (&aa, "nfs3.%s.trusted-sync",
volinfo->volname);
@@ -1826,7 +2109,7 @@ nfs_option_handler (volgen_graph_t *graph,
return -1;
}
- if (! strcmp (vme->option, "!nfs-trusted-write")) {
+ if (! strcmp (vme->option, "!nfs3.*.trusted-write")) {
ret = gf_asprintf (&aa, "nfs3.%s.trusted-write",
volinfo->volname);
@@ -1839,7 +2122,7 @@ nfs_option_handler (volgen_graph_t *graph,
return -1;
}
- if (! strcmp (vme->option, "!nfs-volume-access")) {
+ if (! strcmp (vme->option, "!nfs3.*.volume-access")) {
ret = gf_asprintf (&aa, "nfs3.%s.volume-access",
volinfo->volname);
@@ -1852,7 +2135,7 @@ nfs_option_handler (volgen_graph_t *graph,
return -1;
}
- if (! strcmp (vme->option, "!nfs-export-dir")) {
+ if (! strcmp (vme->option, "!nfs3.*.export-dir")) {
ret = gf_asprintf (&aa, "nfs3.%s.export-dir",
volinfo->volname);
@@ -1867,7 +2150,7 @@ nfs_option_handler (volgen_graph_t *graph,
- if (! strcmp (vme->option, "!nfs.ports-insecure")) {
+ if (! strcmp (vme->option, "!rpc-auth.ports.*.insecure")) {
ret = gf_asprintf (&aa, "rpc-auth.ports.%s.insecure",
volinfo->volname);
diff --git a/xlators/mgmt/glusterd/src/glusterd-volgen.h b/xlators/mgmt/glusterd/src/glusterd-volgen.h
index b98b399dfff..f06655312b7 100644
--- a/xlators/mgmt/glusterd/src/glusterd-volgen.h
+++ b/xlators/mgmt/glusterd/src/glusterd-volgen.h
@@ -65,5 +65,6 @@ glusterd_check_voloption_flags (char *key, int32_t flags);
gf_boolean_t
glusterd_is_valid_volfpath (char *volname, char *brick);
int generate_brick_volfiles (glusterd_volinfo_t *volinfo);
+int glusterd_get_volopt_content (gf_boolean_t xml_out);
#endif