summaryrefslogtreecommitdiffstats
path: root/xlators/mgmt/glusterd
diff options
context:
space:
mode:
Diffstat (limited to 'xlators/mgmt/glusterd')
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-ganesha.c184
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-op-sm.c2
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-utils.c30
-rw-r--r--xlators/mgmt/glusterd/src/glusterd-volume-ops.c2
-rw-r--r--xlators/mgmt/glusterd/src/glusterd.h3
5 files changed, 154 insertions, 67 deletions
diff --git a/xlators/mgmt/glusterd/src/glusterd-ganesha.c b/xlators/mgmt/glusterd/src/glusterd-ganesha.c
index 821cd6feb39..8d26216d908 100644
--- a/xlators/mgmt/glusterd/src/glusterd-ganesha.c
+++ b/xlators/mgmt/glusterd/src/glusterd-ganesha.c
@@ -456,23 +456,42 @@ create_export_config (char *volname, char **op_errstr)
CONFDIR, volname, NULL);
ret = runner_run(&runner);
- if (ret)
+ if (ret && op_errstr)
gf_asprintf (op_errstr, "Failed to create"
" NFS-Ganesha export config file.");
return ret;
}
+int
+copy_export_config (char *volname, char **op_errstr)
+{
+ runner_t runner = {0,};
+ int ret = -1;
+
+ GF_ASSERT(volname);
+ runinit (&runner);
+ runner_add_args (&runner, "sh",
+ GANESHA_PREFIX"/copy-export-ganesha.sh",
+ CONFDIR, volname, NULL);
+ ret = runner_run(&runner);
+
+ if (ret && op_errstr)
+ gf_asprintf (op_errstr, "Failed to copy"
+ " NFS-Ganesha export config file.");
+
+ return ret;
+}
/* Exports and unexports a particular volume via NFS-Ganesha */
int
-ganesha_manage_export (dict_t *dict, char *value, char **op_errstr)
+ganesha_manage_export (char *volname, char *value, char **op_errstr,
+ gf_boolean_t reboot)
{
runner_t runner = {0,};
int ret = -1;
char str[1024];
glusterd_volinfo_t *volinfo = NULL;
dict_t *vol_opts = NULL;
- char *volname = NULL;
xlator_t *this = NULL;
glusterd_conf_t *priv = NULL;
gf_boolean_t option = _gf_false;
@@ -484,16 +503,10 @@ ganesha_manage_export (dict_t *dict, char *value, char **op_errstr)
priv = this->private;
GF_ASSERT (value);
- GF_ASSERT (dict);
GF_ASSERT (priv);
+ GF_VALIDATE_OR_GOTO (this->name, volname, out);
+
- ret = dict_get_str (dict, "volname", &volname);
- if (ret) {
- gf_msg (this->name, GF_LOG_ERROR, errno,
- GD_MSG_DICT_GET_FAILED,
- "Unable to get volume name");
- goto out;
- }
ret = gf_string2boolean (value, &option);
if (ret == -1) {
gf_msg (this->name, GF_LOG_ERROR, EINVAL,
@@ -501,54 +514,77 @@ ganesha_manage_export (dict_t *dict, char *value, char **op_errstr)
goto out;
}
- ret = glusterd_volinfo_find (volname, &volinfo);
- if (ret) {
- gf_msg (this->name, GF_LOG_ERROR, EINVAL,
- GD_MSG_VOL_NOT_FOUND,
- FMTSTR_CHECK_VOL_EXISTS, volname);
- goto out;
- }
+ /* *
+ * Incase of reboot, following checks are already made before calling
+ * ganesha_manage_export. So it will be reductant do it again
+ */
+ if (!reboot) {
+ ret = glusterd_volinfo_find (volname, &volinfo);
+ if (ret) {
+ gf_msg (this->name, GF_LOG_ERROR, EINVAL,
+ GD_MSG_VOL_NOT_FOUND,
+ FMTSTR_CHECK_VOL_EXISTS, volname);
+ goto out;
+ }
- ret = glusterd_check_ganesha_export (volinfo);
- if (ret && option) {
- gf_asprintf (op_errstr, "ganesha.enable "
- "is already 'on'.");
- ret = -1;
- goto out;
+ ret = glusterd_check_ganesha_export (volinfo);
+ if (ret && option) {
+ if (op_errstr)
+ gf_asprintf (op_errstr, "ganesha.enable "
+ "is already 'on'.");
+ ret = -1;
+ goto out;
- } else if (!option && !ret) {
- gf_asprintf (op_errstr, "ganesha.enable "
- "is already 'off'.");
- ret = -1;
- goto out;
+ } else if (!option && !ret) {
+ if (op_errstr)
+ gf_asprintf (op_errstr, "ganesha.enable "
+ "is already 'off'.");
+ ret = -1;
+ goto out;
+ }
}
- /* Check if global option is enabled, proceed only then */
- ret = dict_get_str_boolean (priv->opts,
+ ret = 0;
+
+ /* *
+ * Incase of restart, there is chance that global option turned off
+ * with volume set command. Still we may need to clean up the
+ * configuration files.
+ * Otherwise check if global option is enabled, only then proceed
+ * */
+ if (!(reboot && !option)) {
+ ret = dict_get_str_boolean (priv->opts,
GLUSTERD_STORE_KEY_GANESHA_GLOBAL, _gf_false);
- if (ret == -1) {
- gf_msg_debug (this->name, 0, "Failed to get "
- "global option dict.");
- gf_asprintf (op_errstr, "The option "
- "nfs-ganesha should be "
- "enabled before setting ganesha.enable.");
- goto out;
- }
- if (!ret) {
- gf_asprintf (op_errstr, "The option "
- "nfs-ganesha should be "
- "enabled before setting ganesha.enable.");
- ret = -1;
- goto out;
+ if (ret == -1) {
+ gf_msg_debug (this->name, 0, "Failed to get "
+ "global option dict.");
+ if (op_errstr)
+ gf_asprintf (op_errstr, "The option "
+ "nfs-ganesha should be "
+ "enabled before setting "
+ "ganesha.enable.");
+ goto out;
+ }
+ if (!ret) {
+ if (op_errstr)
+ gf_asprintf (op_errstr, "The option "
+ "nfs-ganesha should be "
+ "enabled before setting "
+ "ganesha.enable.");
+ ret = -1;
+ goto out;
+ }
}
-
/* Create the export file only when ganesha.enable "on" is executed */
if (option) {
- ret = create_export_config (volname, op_errstr);
+ if (reboot)
+ ret = copy_export_config (volname, op_errstr);
+ else
+ ret = create_export_config (volname, op_errstr);
if (ret) {
gf_msg (this->name, GF_LOG_ERROR, 0,
GD_MSG_EXPORT_FILE_CREATE_FAIL,
- "Failed to create"
+ "Failed to create/copy "
"export file for NFS-Ganesha\n");
goto out;
}
@@ -559,21 +595,36 @@ ganesha_manage_export (dict_t *dict, char *value, char **op_errstr)
CONFDIR, value, volname, NULL);
ret = runner_run (&runner);
if (ret) {
- gf_asprintf(op_errstr, "Dynamic export"
- " addition/deletion failed."
- " Please see log file for details");
- goto out;
+ if (op_errstr)
+ gf_asprintf(op_errstr, "Dynamic export"
+ " addition/deletion failed."
+ " Please see log file for details");
+ /* *
+ * Incase of reboot scenarios, we cannot guarantee
+ * nfs-ganesha to be running on that node, so that
+ * dynamic export may fail
+ */
+ if (reboot)
+ ret = 0;
+ else
+ goto out;
}
}
- vol_opts = volinfo->dict;
- /* cache-invalidation should be on when a volume is exported
- * and off when a volume is unexported. */
- ret = dict_set_dynstr_with_alloc (vol_opts,
+
+ /* *
+ * cache-invalidation should be on when a volume is exported
+ * and off when a volume is unexported. It is not required
+ * for reboot scenarios, already it will be copied.
+ * */
+ if (!reboot) {
+ vol_opts = volinfo->dict;
+ ret = dict_set_dynstr_with_alloc (vol_opts,
"features.cache-invalidation", value);
- if (ret)
- gf_asprintf (op_errstr, "Cache-invalidation could not"
- " be set to %s.", value);
+ if (ret && op_errstr)
+ gf_asprintf (op_errstr, "Cache-invalidation could not"
+ " be set to %s.", value);
+ }
out:
return ret;
}
@@ -759,12 +810,9 @@ glusterd_handle_ganesha_op (dict_t *dict, char **op_errstr,
char *key, char *value)
{
- int32_t ret = -1;
+ int32_t ret = -1;
char *volname = NULL;
- xlator_t *this = NULL;
gf_boolean_t option = _gf_false;
- static int export_id = 1;
- glusterd_volinfo_t *volinfo = NULL;
GF_ASSERT (dict);
GF_ASSERT (op_errstr);
@@ -773,7 +821,15 @@ glusterd_handle_ganesha_op (dict_t *dict, char **op_errstr,
if (strcmp (key, "ganesha.enable") == 0) {
- ret = ganesha_manage_export (dict, value, op_errstr);
+ ret = dict_get_str (dict, "volname", &volname);
+ if (ret) {
+ gf_msg (THIS->name, GF_LOG_ERROR, errno,
+ GD_MSG_DICT_GET_FAILED,
+ "Unable to get volume name");
+ goto out;
+ }
+ ret = ganesha_manage_export (volname, value, op_errstr,
+ _gf_false);
if (ret < 0)
goto out;
}
diff --git a/xlators/mgmt/glusterd/src/glusterd-op-sm.c b/xlators/mgmt/glusterd/src/glusterd-op-sm.c
index f3c0f1a5216..033fc5759f2 100644
--- a/xlators/mgmt/glusterd/src/glusterd-op-sm.c
+++ b/xlators/mgmt/glusterd/src/glusterd-op-sm.c
@@ -2153,7 +2153,7 @@ glusterd_op_reset_volume (dict_t *dict, char **op_rspstr)
quorum_action = _gf_true;
ret = glusterd_check_ganesha_export (volinfo);
if (ret) {
- ret = ganesha_manage_export (dict, "off", op_rspstr);
+ ret = ganesha_manage_export (volname, "off", op_rspstr, _gf_false);
if (ret) {
gf_msg (THIS->name, GF_LOG_WARNING, 0,
GD_MSG_NFS_GNS_RESET_FAIL,
diff --git a/xlators/mgmt/glusterd/src/glusterd-utils.c b/xlators/mgmt/glusterd/src/glusterd-utils.c
index 5c28ec942ca..313ae89f3e6 100644
--- a/xlators/mgmt/glusterd/src/glusterd-utils.c
+++ b/xlators/mgmt/glusterd/src/glusterd-utils.c
@@ -4060,6 +4060,9 @@ glusterd_import_friend_volume (dict_t *peer_data, size_t count)
glusterd_volinfo_t *old_volinfo = NULL;
glusterd_volinfo_t *new_volinfo = NULL;
glusterd_svc_t *svc = NULL;
+ gf_boolean_t newexportvalue;
+ gf_boolean_t oldexportvalue;
+ char *value = NULL;
GF_ASSERT (peer_data);
@@ -4080,6 +4083,8 @@ glusterd_import_friend_volume (dict_t *peer_data, size_t count)
ret = glusterd_volinfo_find (new_volinfo->volname, &old_volinfo);
if (0 == ret) {
+ oldexportvalue = glusterd_check_ganesha_export (old_volinfo);
+
/* Ref count the old_volinfo such that deleting it doesn't crash
* if its been already in use by other thread
*/
@@ -4106,6 +4111,31 @@ glusterd_import_friend_volume (dict_t *peer_data, size_t count)
}
}
+ ret = glusterd_volinfo_get (new_volinfo, "ganesha.enable", &value);
+ if (ret)
+ goto out;
+ ret = gf_string2boolean (value, &newexportvalue);
+ if (ret)
+ goto out;
+
+ /* *
+ * if new and old export value is off, then there is no point in calling
+ * ganesha_manage_export
+ */
+ if (!((newexportvalue == oldexportvalue) &&
+ newexportvalue == _gf_false)) {
+ ret = ganesha_manage_export (new_volinfo->volname, value,
+ NULL, _gf_true);
+ if (ret) {
+ gf_msg (this->name, GF_LOG_ERROR, 0,
+ GD_MSG_NFS_GNS_OP_HANDLE_FAIL,
+ "Returning from ganesha_manage_export with"
+ " ret: %d for volume %s ganesha.enable %s",
+ ret, new_volinfo->volname,
+ value);
+ goto out;
+ }
+ }
ret = glusterd_store_volinfo (new_volinfo, GLUSTERD_VOLINFO_VER_AC_NONE);
if (ret) {
gf_msg (this->name, GF_LOG_ERROR, 0,
diff --git a/xlators/mgmt/glusterd/src/glusterd-volume-ops.c b/xlators/mgmt/glusterd/src/glusterd-volume-ops.c
index befe618454a..dabbdfc2e9f 100644
--- a/xlators/mgmt/glusterd/src/glusterd-volume-ops.c
+++ b/xlators/mgmt/glusterd/src/glusterd-volume-ops.c
@@ -1697,7 +1697,7 @@ glusterd_op_stage_stop_volume (dict_t *dict, char **op_errstr)
}
ret = glusterd_check_ganesha_export (volinfo);
if (ret) {
- ret = ganesha_manage_export(dict, "off", op_errstr);
+ ret = ganesha_manage_export (volname, "off", op_errstr, _gf_false);
if (ret) {
gf_msg (THIS->name, GF_LOG_WARNING, 0,
GD_MSG_NFS_GNS_UNEXPRT_VOL_FAIL, "Could not "
diff --git a/xlators/mgmt/glusterd/src/glusterd.h b/xlators/mgmt/glusterd/src/glusterd.h
index 65ab156e41b..3c7f27bb03a 100644
--- a/xlators/mgmt/glusterd/src/glusterd.h
+++ b/xlators/mgmt/glusterd/src/glusterd.h
@@ -1067,7 +1067,8 @@ int glusterd_check_ganesha_cmd (char *key, char *value,
char **errstr, dict_t *dict);
int glusterd_op_stage_set_ganesha (dict_t *dict, char **op_errstr);
int glusterd_op_set_ganesha (dict_t *dict, char **errstr);
-int ganesha_manage_export (dict_t *dict, char *value, char **op_errstr);
+int ganesha_manage_export (char *volname, char *value, char **op_errstr,
+ gf_boolean_t reboot);
gf_boolean_t glusterd_check_ganesha_export (glusterd_volinfo_t *volinfo);
int stop_ganesha (char **op_errstr);
int tear_down_cluster (void);