commit 9a8cb865732feb38a082a03d446c48eb7d461075
Author: Gao,Yan <ygao@suse.com>
Date:   Thu Feb 20 17:51:51 2014 +0800

    Feature: pengine: Support per-resource maintenance mode

diff --git a/include/crm/msg_xml.h b/include/crm/msg_xml.h
index d092285..5872420 100644
--- a/include/crm/msg_xml.h
+++ b/include/crm/msg_xml.h
@@ -205,6 +205,7 @@
 #  define XML_RSC_ATTR_REQUIRES		"requires"
 #  define XML_RSC_ATTR_CONTAINER	"container"
 #  define XML_RSC_ATTR_INTERNAL_RSC	"internal_rsc"
+#  define XML_RSC_ATTR_MAINTENANCE	"maintenance"
 #  define XML_OP_ATTR_ON_FAIL		"on-fail"
 #  define XML_OP_ATTR_START_DELAY	"start-delay"
 #  define XML_OP_ATTR_ALLOW_MIGRATE	"allow-migrate"
diff --git a/include/crm/pengine/status.h b/include/crm/pengine/status.h
index fed2482..6279ff7 100644
--- a/include/crm/pengine/status.h
+++ b/include/crm/pengine/status.h
@@ -188,6 +188,7 @@ struct node_s {
 
 #  define pe_rsc_failure_ignored 0x01000000ULL
 #  define pe_rsc_unexpectedly_running 0x02000000ULL
+#  define pe_rsc_maintenance	0x04000000ULL
 
 #  define pe_rsc_needs_quorum	 0x10000000ULL
 #  define pe_rsc_needs_fencing	 0x20000000ULL
diff --git a/lib/pengine/complex.c b/lib/pengine/complex.c
index a592fc8..315f199 100644
--- a/lib/pengine/complex.c
+++ b/lib/pengine/complex.c
@@ -458,8 +458,19 @@ common_unpack(xmlNode * xml_obj, resource_t ** rsc,
         }
     }
 
-    if (is_set(data_set->flags, pe_flag_maintenance_mode)) {
+    value = g_hash_table_lookup((*rsc)->meta, XML_RSC_ATTR_MAINTENANCE);
+    if (value != NULL && safe_str_neq("default", value)) {
+        gboolean bool_value = FALSE;
+
+        crm_str_to_boolean(value, &bool_value);
+        if (bool_value == TRUE) {
+            clear_bit((*rsc)->flags, pe_rsc_managed);
+            set_bit((*rsc)->flags, pe_rsc_maintenance);
+        }
+
+    } else if (is_set(data_set->flags, pe_flag_maintenance_mode)) {
         clear_bit((*rsc)->flags, pe_rsc_managed);
+        set_bit((*rsc)->flags, pe_rsc_maintenance);
     }
 
     pe_rsc_trace((*rsc), "Options for %s", (*rsc)->id);
diff --git a/pengine/allocate.c b/pengine/allocate.c
index 9a25199..0183701 100644
--- a/pengine/allocate.c
+++ b/pengine/allocate.c
@@ -386,7 +386,7 @@ check_actions_for(xmlNode * rsc_entry, resource_t * rsc, node_t * node, pe_worki
         }
 
         if (interval > 0 &&
-            (is_set(data_set->flags, pe_flag_maintenance_mode) || node->details->maintenance)) {
+            (is_set(rsc->flags, pe_rsc_maintenance) || node->details->maintenance)) {
             CancelXmlOp(rsc, rsc_op, node, "maintenance mode", data_set);
 
         } else if (is_probe || safe_str_eq(task, RSC_START) || interval > 0
@@ -2430,7 +2430,7 @@ stage8(pe_working_set_t * data_set)
         if (action->rsc
             && action->node
             && action->node->details->shutdown
-            && is_not_set(data_set->flags, pe_flag_maintenance_mode)
+            && is_not_set(action->rsc->flags, pe_rsc_maintenance)
             && is_not_set(action->flags, pe_action_optional)
             && is_not_set(action->flags, pe_action_runnable)
             && crm_str_eq(action->task, RSC_STOP, TRUE)
diff --git a/pengine/graph.c b/pengine/graph.c
index 4123569..17be00a 100644
--- a/pengine/graph.c
+++ b/pengine/graph.c
@@ -534,7 +534,7 @@ shutdown_constraints(node_t * node, action_t * shutdown_op, pe_working_set_t * d
             continue;
         } else if (action->node->details != node->details) {
             continue;
-        } else if (is_set(data_set->flags, pe_flag_maintenance_mode)) {
+        } else if (is_set(action->rsc->flags, pe_rsc_maintenance)) {
             pe_rsc_trace(action->rsc, "Skipping %s: maintainence mode", action->uuid);
             continue;
         } else if (node->details->maintenance) {
diff --git a/pengine/native.c b/pengine/native.c
index 8ea1dda..db0434a 100644
--- a/pengine/native.c
+++ b/pengine/native.c
@@ -819,7 +819,7 @@ RecurringOp(resource_t * rsc, action_t * start, node_t * node,
 void
 Recurring(resource_t * rsc, action_t * start, node_t * node, pe_working_set_t * data_set)
 {
-    if (is_not_set(data_set->flags, pe_flag_maintenance_mode) &&
+    if (is_not_set(rsc->flags, pe_rsc_maintenance) &&
         (node == NULL || node->details->maintenance == FALSE)) {
         xmlNode *operation = NULL;
 
@@ -1049,7 +1049,7 @@ RecurringOp_Stopped(resource_t * rsc, action_t * start, node_t * node,
 void
 Recurring_Stopped(resource_t * rsc, action_t * start, node_t * node, pe_working_set_t * data_set)
 {
-    if (is_not_set(data_set->flags, pe_flag_maintenance_mode) && 
+    if (is_not_set(rsc->flags, pe_rsc_maintenance) && 
         (node == NULL || node->details->maintenance == FALSE)) {
         xmlNode *operation = NULL;
 
