21#include <libxml/tree.h>
31struct stonith_action_s {
41 void (*fork_cb) (
int pid,
void *user_data);
46 time_t initial_start_time;
48 int remaining_timeout;
80 if (
action->result.action_stderr != NULL) {
90append_config_arg(gpointer key, gpointer value, gpointer user_data)
103 crm_trace(
"Passing %s=%s with fence action",
104 (
const char *) key, (
const char *) (value? value :
""));
123make_args(
const char *agent,
const char *
action,
const char *
target,
124 GHashTable *device_args, GHashTable *port_map,
125 const char *default_host_arg)
127 GHashTable *arg_list = NULL;
128 const char *value = NULL;
138 snprintf(buffer,
sizeof(buffer),
"pcmk_%s_action",
action);
139 value = g_hash_table_lookup(device_args, buffer);
141 crm_debug(
"Substituting '%s' for fence action %s targeting %s",
153 if ((
target != NULL) && (device_args != NULL)) {
154 const char *param = NULL;
165 param = default_host_arg;
171 value = g_hash_table_lookup(device_args, param);
172 if (pcmk__str_eq(value,
"dynamic",
177 const char *alias = NULL;
180 alias = g_hash_table_lookup(port_map,
target);
185 crm_debug(
"Passing %s='%s' with fence action %s targeting %s",
193 g_hash_table_foreach(device_args, append_config_arg, arg_list);
211 g_hash_table_destroy(
action->args);
236#define FAILURE_MAX_RETRIES 2
254 const char *
target,
int timeout_sec,
255 GHashTable *device_args, GHashTable *port_map,
256 const char *default_host_arg)
260 action->args = make_args(agent, action_name,
target, device_args, port_map,
262 crm_debug(
"Preparing '%s' action targeting %s using agent %s",
263 action_name, pcmk__s(
target,
"no node"), agent);
264 action->agent = strdup(agent);
265 action->action = strdup(action_name);
266 action->timeout =
action->remaining_timeout = timeout_sec;
270 "Initialization bug in fencing library");
274 const char *value = NULL;
276 snprintf(buffer,
sizeof(buffer),
"pcmk_%s_retries", action_name);
277 value = g_hash_table_lookup(device_args, buffer);
280 action->max_retries = atoi(value);
290 int diff = time(NULL) -
action->initial_start_time;
293 crm_info(
"Attempted to execute agent %s (%s) the maximum number of times (%d) allowed",
295 action->remaining_timeout = 0;
297 && (diff < (
action->timeout * 0.7))) {
302 action->remaining_timeout = 0;
304 return action->remaining_timeout ? TRUE : FALSE;
318 if (pcmk__result_ok(
result)) {
424 const char *exit_reason = NULL;
425 const char *action_stdout = NULL;
487 const char *exit_reason = NULL;
488 char *action_stdout = NULL;
498 &execution_status) < 0)) {
506 if ((rc ==
pcmk_ok) || (rc == -EINPROGRESS)) {
514 exit_reason =
"Fencer reply contained neither a full result "
515 "nor a legacy return code (bug?)";
527 set_result_from_svc_action(
action, svc_action);
528 svc_action->
params = NULL;
531 if (!pcmk__result_ok(&(
action->result))
532 && update_remaining_timeout(
action)) {
534 int rc = internal_stonith_action_execute(
action);
544 action->svc_action = NULL;
554 action->svc_action = svc_action;
563 crm_trace(
"Child process %d performing action '%s' successfully forked",
579 static int stonith_sequence = 0;
586 set_result_from_svc_action(
action, svc_action);
597 svc_action->
sequence = stonith_sequence++;
600 svc_action->
flags = pcmk__set_flags_as(__func__, __LINE__,
602 svc_action->
id, svc_action->
flags,
604 "SVC_ACTION_NON_BLOCKED");
619 || (
action->agent == NULL)) {
625 if (
action->tries++ == 0) {
627 action->initial_start_time = time(NULL);
630 crm_info(
"Attempt %d to execute '%s' action of agent %s "
631 "(%ds timeout remaining)",
633 action->remaining_timeout);
637 svc_action = stonith_action_to_svc(
action);
638 if (svc_action == NULL) {
653 &stonith_action_async_done,
654 &stonith_action_async_forked));
661 set_result_from_svc_action(
action, svc_action);
662 svc_action->
params = NULL;
680 void (*done) (
int pid,
683 void (*fork_cb) (
int pid,
void *user_data))
689 action->userdata = userdata;
691 action->fork_cb = fork_cb;
694 return internal_stonith_action_execute(
action);
714 rc = internal_stonith_action_execute(
action);
715 }
while ((rc !=
pcmk_ok) && update_remaining_timeout(
action));
#define PCMK_STONITH_HOST_ARGUMENT
bool pcmk_stonith_param(const char *param)
Check whether a given stonith parameter is handled by Pacemaker.
#define PCMK_RESOURCE_CLASS_STONITH
#define pcmk__assert_alloc(nmemb, size)
#define PCMK__FENCE_BINDIR
struct stonith_action_s stonith_action_t
#define STONITH_ATTR_ACTION_OP
#define crm_info(fmt, args...)
#define crm_log_output(level, prefix, output)
#define CRM_LOG_ASSERT(expr)
#define CRM_CHECK(expr, failure_action)
#define crm_debug(fmt, args...)
#define crm_trace(fmt, args...)
pcmk__action_result_t result
const char * pcmk_strerror(int rc)
@ CRM_EX_PROTOCOL
Protocol violated.
@ CRM_EX_ERROR
Unspecified error.
@ CRM_EX_EXPIRED
Requested item has expired.
@ CRM_EX_INVALID_PARAM
Parameter invalid (in local context)
@ CRM_EX_INSUFFICIENT_PRIV
Insufficient privileges.
@ PCMK_OCF_UNKNOWN_ERROR
Unspecified error.
@ PCMK_OCF_UNKNOWN
Action is pending.
int pcmk_rc2legacy(int rc)
pcmk_exec_status
Execution status.
@ PCMK_EXEC_CANCELLED
Action was cancelled.
@ PCMK_EXEC_NO_SECRETS
Necessary CIB secrets are unavailable.
@ PCMK_EXEC_ERROR_FATAL
Execution failed, do not retry anywhere.
@ PCMK_EXEC_NOT_INSTALLED
Agent or dependency not available locally.
@ PCMK_EXEC_INVALID
Action cannot be attempted (e.g. shutdown)
@ PCMK_EXEC_DONE
Action completed, result is known.
@ PCMK_EXEC_ERROR
Execution failed, may be retried.
@ PCMK_EXEC_NOT_SUPPORTED
Agent does not implement requested action.
@ PCMK_EXEC_TIMEOUT
Action did not complete in time.
@ PCMK_EXEC_PENDING
Action is in progress.
@ PCMK_EXEC_UNKNOWN
Used only to initialize variables.
@ PCMK_EXEC_NO_FENCE_DEVICE
No fence device is configured for target.
@ PCMK_EXEC_NOT_CONNECTED
No connection to executor.
void pcmk__set_result(pcmk__action_result_t *result, int exit_status, enum pcmk_exec_status exec_status, const char *exit_reason)
void void pcmk__set_result_output(pcmk__action_result_t *result, char *out, char *err)
void pcmk__reset_result(pcmk__action_result_t *result)
gboolean services_action_sync(svc_action_t *op)
void services_action_free(svc_action_t *op)
svc_action_t * services_action_create_generic(const char *exec, const char *args[])
Request execution of an arbitrary command.
gboolean services_action_async_fork_notify(svc_action_t *op, void(*action_callback)(svc_action_t *), void(*action_fork_callback)(svc_action_t *))
Run an action asynchronously, with callback after process is forked.
char * services__grab_stdout(svc_action_t *action)
void services__copy_result(const svc_action_t *action, pcmk__action_result_t *result)
char * services__grab_stderr(svc_action_t *action)
int stonith__legacy2status(int rc)
int stonith__execute_async(stonith_action_t *action, void *userdata, void(*done)(int pid, const pcmk__action_result_t *result, void *user_data), void(*fork_cb)(int pid, void *user_data))
void stonith__destroy_action(stonith_action_t *action)
stonith_action_t * stonith__action_create(const char *agent, const char *action_name, const char *target, int timeout_sec, GHashTable *device_args, GHashTable *port_map, const char *default_host_arg)
pcmk__action_result_t * stonith__action_result(stonith_action_t *action)
xmlNode * stonith__find_xe_with_result(xmlNode *xml)
int stonith__execute(stonith_action_t *action)
void stonith__xe_get_result(const xmlNode *xml, pcmk__action_result_t *result)
#define FAILURE_MAX_RETRIES
int stonith__result2rc(const pcmk__action_result_t *result)
void stonith__xe_set_result(xmlNode *xml, const pcmk__action_result_t *result)
char * crm_strdup_printf(char const *format,...) G_GNUC_PRINTF(1
void pcmk__insert_dup(GHashTable *table, const char *name, const char *value)
GHashTable * pcmk__strkey_table(GDestroyNotify key_destroy_func, GDestroyNotify value_destroy_func)
#define pcmk__str_copy(str)
enum pcmk_exec_status execution_status
Object for executing external actions.
void * cb_data
For caller's use (not used by library)
char * agent
Resource agent name for resource actions, otherwise NULL.
char * standard
Resource standard for resource actions, otherwise NULL.
int rc
Exit status of action (set by library upon completion)
enum svc_action_flags flags
Flag group of enum svc_action_flags.
int timeout
Action timeout (in milliseconds)
Wrappers for and extensions to libxml2.
const char * crm_element_value(const xmlNode *data, const char *name)
Retrieve the value of an XML attribute.
int crm_element_value_int(const xmlNode *data, const char *name, int *dest)
Retrieve the integer value of an XML attribute.
const char * crm_xml_add_int(xmlNode *node, const char *name, int value)
Create an XML attribute with specified name and integer value.
char * crm_element_value_copy(const xmlNode *data, const char *name)
Retrieve a copy of the value of an XML attribute.
const char * crm_xml_add(xmlNode *node, const char *name, const char *value)
Create an XML attribute with specified name and value.
#define PCMK_XA_CRM_FEATURE_SET
#define PCMK_XA_EXIT_REASON
#define PCMK__XA_ST_OUTPUT
#define PCMK__XA_OP_STATUS
xmlNode * pcmk__xpath_find_one(xmlDoc *doc, const char *path, uint8_t level)