From: Martin Schwenke Date: Tue, 16 Feb 2016 05:39:40 +0000 (+1100) Subject: ctdb-recovery: Recovery lock setting can now include helper command X-Git-Tag: talloc-2.1.7~105 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=46684867b187469f7827a3e3cd213443d44034bf;p=thirdparty%2Fsamba.git ctdb-recovery: Recovery lock setting can now include helper command The underlying change is to allow the cluster mutex argstring to optionally contain a helper command. When the argument string starts with '!' then the first word is the helper command to run. This is now the standard way of changing the helper from the default. CTDB_CLUSTER_MUTEX_HELPER show now only be used to change the location of the default helper when testing. Signed-off-by: Martin Schwenke Reviewed-by: Amitay Isaacs --- diff --git a/ctdb/config/events.d/01.reclock b/ctdb/config/events.d/01.reclock index d3dd612471f..e2d4d124bc3 100755 --- a/ctdb/config/events.d/01.reclock +++ b/ctdb/config/events.d/01.reclock @@ -7,6 +7,12 @@ . $CTDB_BASE/functions loadconfig +# If CTDB_RECOVERY_LOCK specifies a helper then exit because this +# script can't do anything useful. +case "$CTDB_RECOVERY_LOCK" in +!*) exit 0 ;; +esac + case "$1" in init) ctdb_counter_init diff --git a/ctdb/doc/ctdb.7.xml b/ctdb/doc/ctdb.7.xml index 51222ad48a4..14211435363 100644 --- a/ctdb/doc/ctdb.7.xml +++ b/ctdb/doc/ctdb.7.xml @@ -98,14 +98,26 @@ - The recovery lock is implemented using a file residing in shared - storage (usually) on a cluster filesystem. To support a - recovery lock the cluster filesystem must support lock - coherence. See + By default, the recovery lock is implemented using a file + (specified by CTDB_RECOVERY_LOCK) + residing in shared storage (usually) on a cluster filesystem. + To support a recovery lock the cluster filesystem must support + lock coherence. See ping_pong 1 for more details. + + The recovery lock can also be implemented using an arbitrary + cluster mutex call-out by using an exclamation point ('!') as + the first character of + CTDB_RECOVERY_LOCK. For example, a value + of !/usr/local/bin/myhelper recovery would + run the given helper with the specified arguments. See the + source code relating to cluster mutexes for clues about writing + call-outs. + + If a cluster becomes partitioned (for example, due to a communication failure) and a different recovery master is diff --git a/ctdb/doc/ctdbd.1.xml b/ctdb/doc/ctdbd.1.xml index 0f75f77a5df..7b8cc667afc 100644 --- a/ctdb/doc/ctdbd.1.xml +++ b/ctdb/doc/ctdbd.1.xml @@ -365,12 +365,11 @@ - --reclock=FILE + --reclock=LOCK - FILE is the name of the recovery lock file, stored in - shared storage, that CTDB uses to - prevent split brains. + LOCK specifies the cluster-wide mutex used to detect and + prevent a partitioned cluster (or "split brain"). For information about the recovery lock please see the diff --git a/ctdb/doc/ctdbd.conf.5.xml b/ctdb/doc/ctdbd.conf.5.xml index 324be050135..a364c9f0fc1 100644 --- a/ctdb/doc/ctdbd.conf.5.xml +++ b/ctdb/doc/ctdbd.conf.5.xml @@ -379,10 +379,14 @@ - CTDB_RECOVERY_LOCK=FILENAME + CTDB_RECOVERY_LOCK=LOCK - Defaults to + LOCK specifies the cluster-wide mutex used to detect and + prevent a partitioned cluster (or "split brain"). + + + No default, but the default configuration file specifies /some/place/on/shared/storage, which should be change to a useful value. Corresponds to . diff --git a/ctdb/server/ctdb_recover.c b/ctdb/server/ctdb_recover.c index 0699528d0cc..b2037addc07 100644 --- a/ctdb/server/ctdb_recover.c +++ b/ctdb/server/ctdb_recover.c @@ -906,11 +906,21 @@ static bool cluster_mutex_helper_args(TALLOC_CTX *mem_ctx, const char *argstring, char ***argv) { int nargs, i, ret, n; + bool is_command = false; char **args = NULL; char *strv = NULL; char *t = NULL; - ret = strv_split(mem_ctx, &strv, argstring, " \t"); + if (argstring != NULL && argstring[0] == '!') { + /* This is actually a full command */ + is_command = true; + t = discard_const(&argstring[1]); + } else { + is_command = false; + t = discard_const(argstring); + } + + ret = strv_split(mem_ctx, &strv, t, " \t"); if (ret != 0) { DEBUG(DEBUG_ERR, ("Unable to parse mutex helper string \"%s\" (%s)\n", @@ -919,7 +929,8 @@ static bool cluster_mutex_helper_args(TALLOC_CTX *mem_ctx, } n = strv_count(strv); - args = talloc_array(mem_ctx, char *, n + 2); + args = talloc_array(mem_ctx, char *, n + (is_command ? 1 : 2)); + if (args == NULL) { DEBUG(DEBUG_ERR,(__location__ " out of memory\n")); return false; @@ -927,17 +938,21 @@ static bool cluster_mutex_helper_args(TALLOC_CTX *mem_ctx, nargs = 0; - if (!ctdb_set_helper("cluster mutex helper", - cluster_mutex_helper, - sizeof(cluster_mutex_helper), - "CTDB_CLUSTER_MUTEX_HELPER", - CTDB_HELPER_BINDIR, "ctdb_mutex_fcntl_helper")) { - DEBUG(DEBUG_ERR,("ctdb exiting with error: %s\n", - __location__ - " Unable to set cluster mutex helper\n")); - exit(1); + if (! is_command) { + if (!ctdb_set_helper("cluster mutex helper", + cluster_mutex_helper, + sizeof(cluster_mutex_helper), + "CTDB_CLUSTER_MUTEX_HELPER", + CTDB_HELPER_BINDIR, + "ctdb_mutex_fcntl_helper")) { + DEBUG(DEBUG_ERR,("ctdb exiting with error: %s\n", + __location__ + " Unable to set cluster mutex helper\n")); + exit(1); + } + + args[nargs++] = cluster_mutex_helper; } - args[nargs++] = cluster_mutex_helper; t = NULL; for (i = 0; i < n; i++) {