diff --git a/crm/tengine/unpack.c b/crm/tengine/unpack.c index e2ac25577e..60f629c2ff 100644 --- a/crm/tengine/unpack.c +++ b/crm/tengine/unpack.c @@ -1,334 +1,347 @@ -/* $Id: unpack.c,v 1.47 2005/09/26 07:44:49 andrew Exp $ */ +/* $Id: unpack.c,v 1.48 2005/10/12 19:01:35 andrew Exp $ */ /* * Copyright (C) 2004 Andrew Beekhof * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ #include #include #include #include #include #include #include #include #include #include #include #include #include cib_t *te_cib_conn = NULL; action_t* unpack_action(crm_data_t *xml_action); void set_timer_value(te_timer_t *timer, const char *time, int time_default); extern int transition_counter; void set_timer_value(te_timer_t *timer, const char *time, int time_default) { int tmp_time; if(timer == NULL) { return; } timer->timeout = time_default; tmp_time = crm_get_msec(time); if(tmp_time > 0) { timer->timeout = tmp_time; } } gboolean unpack_graph(crm_data_t *xml_graph) { /* timeout = crm_get_msec(time); transition_idle_timeout = transition_timer->timeout; transition_counter = crm_atoi(t_id, "-1"); crm_info("Beginning transition %d : timeout set to %dms", transition_counter, transition_timer->timeout); xml_child_iter( xml_graph, synapse, "synapse", synapse_t *new_synapse = NULL; crm_debug_3("looking in synapse %s", crm_element_value(synapse, XML_ATTR_ID)); crm_malloc0(new_synapse, sizeof(synapse_t)); new_synapse->id = num_synapses++; new_synapse->complete = FALSE; new_synapse->confirmed = FALSE; new_synapse->actions = NULL; new_synapse->inputs = NULL; graph = g_list_append(graph, new_synapse); crm_debug_3("look for actions in synapse %s", crm_element_value(synapse, XML_ATTR_ID)); xml_child_iter( synapse, actions, "action_set", xml_child_iter( actions, action, NULL, action_t *new_action = unpack_action(action); num_actions++; if(new_action == NULL) { continue; } crm_debug_3("Adding action %d to synapse %d", new_action->id, new_synapse->id); new_synapse->actions = g_list_append( new_synapse->actions, new_action); ); ); crm_debug_3("look for inputs in synapse %s", crm_element_value(synapse, XML_ATTR_ID)); xml_child_iter( synapse, inputs, "inputs", xml_child_iter( inputs, trigger, NULL, xml_child_iter( trigger, input, NULL, action_t *new_input = unpack_action(input); if(new_input == NULL) { continue; } crm_debug_3("Adding input %d to synapse %d", new_input->id, new_synapse->id); new_synapse->inputs = g_list_append( new_synapse->inputs, new_input); ); ); ); ); crm_info("Unpacked %d actions in %d synapses", num_actions, num_synapses); if(num_actions > 0) { return TRUE; } else { /* indicate to caller that there's nothing to do */ return FALSE; } } action_t* unpack_action(crm_data_t *xml_action) { action_t *action = NULL; crm_data_t *action_copy = NULL; const char *value = crm_element_value(xml_action, XML_ATTR_ID); if(value == NULL) { crm_err("Actions must have an id!"); crm_log_xml_debug_3(xml_action, "Action with missing id"); return NULL; } action_copy = copy_xml(xml_action); crm_malloc0(action, sizeof(action_t)); if(action == NULL) { return NULL; } action->id = atoi(value); action->timeout = 0; action->interval = 0; action->timer = NULL; action->invoked = FALSE; action->sent_update = FALSE; action->complete = FALSE; action->can_fail = FALSE; action->type = action_type_rsc; action->xml = action_copy; if(safe_str_eq(crm_element_name(action_copy), XML_GRAPH_TAG_RSC_OP)) { action->type = action_type_rsc; } else if(safe_str_eq(crm_element_name(action_copy), XML_GRAPH_TAG_PSEUDO_EVENT)) { action->type = action_type_pseudo; } else if(safe_str_eq(crm_element_name(action_copy), XML_GRAPH_TAG_CRM_EVENT)) { action->type = action_type_crm; } action->params = xml2list(action_copy); value = g_hash_table_lookup(action->params, "timeout"); if(value != NULL) { action->timeout = atoi(value); } value = g_hash_table_lookup(action->params, "interval"); if(value != NULL) { action->interval = atoi(value); } value = g_hash_table_lookup(action->params, "can_fail"); if(value != NULL) { cl_str_to_boolean(value, &(action->can_fail)); } crm_debug_3("Action %d has timer set to %dms", action->id, action->timeout); crm_malloc0(action->timer, sizeof(te_timer_t)); action->timer->timeout = 2 * action->timeout; action->timer->source_id = -1; action->timer->reason = timeout_action; action->timer->action = action; return action; } gboolean extract_event(crm_data_t *msg) { const char *event_node = NULL; struct abort_blob_s { const char *text; crm_data_t *update; te_reason_t reason; }; struct abort_blob_s blob = { NULL, NULL, 0 }; blob.reason = te_update; /* [cib fragment] ... */ crm_debug_4("Extracting event from %s", crm_element_name(msg)); xml_child_iter( msg, node_state, XML_CIB_TAG_STATE, + crm_data_t *attrs = NULL; crm_data_t *resources = NULL; const char *ccm_state = crm_element_value( node_state, XML_CIB_ATTR_INCCM); const char *crmd_state = crm_element_value( node_state, XML_CIB_ATTR_CRMDSTATE); - blob.update = node_state; - + /* Transient node attribute changes... */ event_node = crm_element_value(node_state, XML_ATTR_ID); - + crm_info("Processing state update from %s", event_node); crm_log_xml_debug_3(node_state,"Processing"); - if(crm_element_value(node_state, XML_CIB_ATTR_SHUTDOWN) != NULL) { - blob.text = "Aborting on "XML_CIB_ATTR_SHUTDOWN" attribute"; - break; - + if(blob.text == NULL) { + blob.update = node_state; } + + attrs = find_xml_node( + node_state, XML_TAG_TRANSIENT_NODEATTRS, FALSE); + if(attrs != NULL) { + crm_info("Aborting on "XML_TAG_TRANSIENT_NODEATTRS" changes"); + if(blob.text == NULL) { + blob.text = "Aborting on "XML_TAG_TRANSIENT_NODEATTRS" changes"; + } + } + resources = find_xml_node(node_state, XML_CIB_TAG_LRM, FALSE); resources = find_xml_node( resources, XML_LRM_TAG_RESOURCES, FALSE); + /* LRM resource update... */ + xml_child_iter( + resources, rsc, NULL, + xml_child_iter( + rsc, rsc_op, NULL, + + crm_log_xml_debug_3( + rsc_op, "Processing resource update"); + process_graph_event(rsc_op, event_node); + ); + ); + /* * node state update... possibly from a shutdown we requested */ - crm_debug_3("Processing state update"); if(safe_str_eq(ccm_state, XML_BOOLEAN_FALSE) || safe_str_eq(crmd_state, CRMD_JOINSTATE_DOWN)) { int action_id = -1; crm_debug_3("A shutdown we requested?"); action_id = match_down_event( event_node, NULL, LRM_OP_DONE); if(action_id >= 0) { process_trigger(action_id); check_for_completion(); + } else { - blob.text="Stonith/shutdown event not matched"; - break; + crm_info("Stonith/shutdown event not matched"); + if(blob.text == NULL) { + blob.text="Stonith/shutdown event not matched"; + } } } - /* LRM resource update... */ - xml_child_iter( - resources, rsc, NULL, - xml_child_iter( - rsc, rsc_op, NULL, - - crm_log_xml_debug_3( - rsc_op, "Processing resource update"); - if(!process_graph_event(rsc_op, event_node)) { - /* the transition has already been - * aborted and with better details - */ - return TRUE; - } - ); - ); + if(crm_element_value(node_state, XML_CIB_ATTR_SHUTDOWN) != NULL) { + crm_info("Aborting on "XML_CIB_ATTR_SHUTDOWN" attribute"); + if(blob.text == NULL) { + blob.text = "Aborting on "XML_CIB_ATTR_SHUTDOWN" attribute"; + } + + } ); if(blob.text != NULL) { send_complete(blob.text, blob.update, blob.reason, i_cancel); } return TRUE; }