Blob Blame History Raw
From a2b8e75abf42b28ba0a02de4e67da531556543ab Mon Sep 17 00:00:00 2001
From: Chris Lumens <clumens@redhat.com>
Date: Tue, 17 Nov 2020 13:53:57 -0500
Subject: [PATCH 1/6] Refactor: libs: Add a function to set properties on an
 xmlNode.

This takes a va_list so it can be used by other future functions that
will take arguments directly.  It then just walks the list of pairs and
sets them as properties on an xmlNode, until a NULL is found.

Interally, it just uses crm_xml_add so it's useful across the whole
pacemaker code base.
---
 include/crm/common/xml_internal.h |  3 +++
 lib/common/xml.c                  | 20 ++++++++++++++++++++
 2 files changed, 23 insertions(+)

diff --git a/include/crm/common/xml_internal.h b/include/crm/common/xml_internal.h
index 5643be6..c60fa51 100644
--- a/include/crm/common/xml_internal.h
+++ b/include/crm/common/xml_internal.h
@@ -235,4 +235,7 @@ pcmk__xe_next(const xmlNode *child)
     return next;
 }
 
+void
+pcmk__xe_set_propv(xmlNodePtr node, va_list pairs);
+
 #endif // PCMK__XML_INTERNAL__H
diff --git a/lib/common/xml.c b/lib/common/xml.c
index bed6854..61cac9f 100644
--- a/lib/common/xml.c
+++ b/lib/common/xml.c
@@ -2935,6 +2935,26 @@ pcmk__xml_artefact_path(enum pcmk__xml_artefact_ns ns, const char *filespec)
     return ret;
 }
 
+void
+pcmk__xe_set_propv(xmlNodePtr node, va_list pairs)
+{
+    while (true) {
+        const char *name, *value;
+
+        name = va_arg(pairs, const char *);
+        if (name == NULL) {
+            return;
+        }
+
+        value = va_arg(pairs, const char *);
+        if (value == NULL) {
+            return;
+        }
+
+        crm_xml_add(node, name, value);
+    }
+}
+
 // Deprecated functions kept only for backward API compatibility
 
 xmlNode *find_entity(xmlNode *parent, const char *node_name, const char *id);
-- 
1.8.3.1


From b16b24ed049b1a646195e8d8b9bb309c2fa8fe49 Mon Sep 17 00:00:00 2001
From: Chris Lumens <clumens@redhat.com>
Date: Tue, 17 Nov 2020 13:00:44 -0500
Subject: [PATCH 2/6] Refactor: libs: Set XML properties when creating a node.

pcmk__output_create_xml_node can take a NULL-terminated list of
properties that should be set on the node at the same time it's created.
This saves a bunch of calls to xmlSetProp and gets rid of some variables
that are otherwise not needed.

Unfortunately, this can't be used everywhere I'd like but it's a good
start.
---
 include/crm/common/output_internal.h |   4 +-
 lib/common/output_html.c             |   2 +-
 lib/common/output_xml.c              |  32 ++++---
 lib/fencing/st_output.c              |  34 ++++---
 lib/pacemaker/pcmk_output.c          |  77 ++++++++--------
 lib/pengine/bundle.c                 |   4 +-
 lib/pengine/pe_output.c              | 174 +++++++++++++++++------------------
 tools/crm_resource_print.c           |   6 +-
 8 files changed, 173 insertions(+), 160 deletions(-)

diff --git a/include/crm/common/output_internal.h b/include/crm/common/output_internal.h
index e1bd295..1923c1a 100644
--- a/include/crm/common/output_internal.h
+++ b/include/crm/common/output_internal.h
@@ -648,9 +648,11 @@ pcmk__output_xml_add_node(pcmk__output_t *out, xmlNodePtr node);
  *
  * \param[in,out] out  The output functions structure.
  * \param[in]     name The name of the node to be created.
+ * \param[in]     ...     Name/value pairs to set as XML properties.
  */
 xmlNodePtr
-pcmk__output_create_xml_node(pcmk__output_t *out, const char *name);
+pcmk__output_create_xml_node(pcmk__output_t *out, const char *name, ...)
+G_GNUC_NULL_TERMINATED;
 
 /*!
  * \internal
diff --git a/lib/common/output_html.c b/lib/common/output_html.c
index e354b5d..77a5410 100644
--- a/lib/common/output_html.c
+++ b/lib/common/output_html.c
@@ -370,7 +370,7 @@ html_is_quiet(pcmk__output_t *out) {
 
 static void
 html_spacer(pcmk__output_t *out) {
-    pcmk__output_create_xml_node(out, "br");
+    pcmk__output_create_xml_node(out, "br", NULL);
 }
 
 pcmk__output_t *
diff --git a/lib/common/output_xml.c b/lib/common/output_xml.c
index 716d10f..80ee2de 100644
--- a/lib/common/output_xml.c
+++ b/lib/common/output_xml.c
@@ -24,6 +24,7 @@
 
 #include <crm/crm.h>
 #include <crm/common/xml.h>
+#include <crm/common/xml_internal.h>
 #include <crm/common/output_internal.h>
 
 static gboolean legacy_xml = FALSE;
@@ -234,16 +235,16 @@ xml_subprocess_output(pcmk__output_t *out, int exit_status,
 
 static void
 xml_version(pcmk__output_t *out, bool extended) {
-    xmlNodePtr node;
     private_data_t *priv = out->priv;
     CRM_ASSERT(priv != NULL);
 
-    node = pcmk__output_create_xml_node(out, "version");
-    xmlSetProp(node, (pcmkXmlStr) "program", (pcmkXmlStr) "Pacemaker");
-    xmlSetProp(node, (pcmkXmlStr) "version", (pcmkXmlStr) PACEMAKER_VERSION);
-    xmlSetProp(node, (pcmkXmlStr) "author", (pcmkXmlStr) "Andrew Beekhof");
-    xmlSetProp(node, (pcmkXmlStr) "build", (pcmkXmlStr) BUILD_VERSION);
-    xmlSetProp(node, (pcmkXmlStr) "features", (pcmkXmlStr) CRM_FEATURES);
+    pcmk__output_create_xml_node(out, "version",
+                                 "program", "Pacemaker",
+                                 "version", PACEMAKER_VERSION,
+                                 "author", "Andrew Beekhof",
+                                 "build", BUILD_VERSION,
+                                 "features", CRM_FEATURES,
+                                 NULL);
 }
 
 G_GNUC_PRINTF(2, 3)
@@ -277,7 +278,7 @@ xml_output_xml(pcmk__output_t *out, const char *name, const char *buf) {
 
     CRM_ASSERT(priv != NULL);
 
-    parent = pcmk__output_create_xml_node(out, name);
+    parent = pcmk__output_create_xml_node(out, name, NULL);
     cdata_node = xmlNewCDataBlock(getDocPtr(parent), (pcmkXmlStr) buf, strlen(buf));
     xmlAddChild(parent, cdata_node);
 }
@@ -419,7 +420,7 @@ pcmk__mk_xml_output(char **argv) {
 
 xmlNodePtr
 pcmk__output_xml_create_parent(pcmk__output_t *out, const char *name) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, name);
+    xmlNodePtr node = pcmk__output_create_xml_node(out, name, NULL);
     pcmk__output_xml_push_parent(out, node);
     return node;
 }
@@ -435,17 +436,24 @@ pcmk__output_xml_add_node(pcmk__output_t *out, xmlNodePtr node) {
 }
 
 xmlNodePtr
-pcmk__output_create_xml_node(pcmk__output_t *out, const char *name) {
+pcmk__output_create_xml_node(pcmk__output_t *out, const char *name, ...) {
+    xmlNodePtr node = NULL;
     private_data_t *priv = out->priv;
+    va_list args;
 
     CRM_ASSERT(priv != NULL);
 
-    return create_xml_node(g_queue_peek_tail(priv->parent_q), name);
+    node = create_xml_node(g_queue_peek_tail(priv->parent_q), name);
+    va_start(args, name);
+    pcmk__xe_set_propv(node, args);
+    va_end(args);
+
+    return node;
 }
 
 xmlNodePtr
 pcmk__output_create_xml_text_node(pcmk__output_t *out, const char *name, const char *content) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, name);
+    xmlNodePtr node = pcmk__output_create_xml_node(out, name, NULL);
     xmlNodeSetContent(node, (pcmkXmlStr) content);
     return node;
 }
diff --git a/lib/fencing/st_output.c b/lib/fencing/st_output.c
index c3b6b41..82520ee 100644
--- a/lib/fencing/st_output.c
+++ b/lib/fencing/st_output.c
@@ -132,10 +132,11 @@ stonith__full_history_xml(pcmk__output_t *out, va_list args) {
 
         PCMK__OUTPUT_LIST_FOOTER(out, rc);
     } else {
-        xmlNodePtr node = pcmk__output_create_xml_node(out, "fence_history");
         char *rc_s = crm_itoa(history_rc);
 
-        xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) rc_s);
+        pcmk__output_create_xml_node(out, "fence_history",
+                                     "status", rc_s,
+                                     NULL);
         free(rc_s);
 
         rc = pcmk_rc_ok;
@@ -182,11 +183,12 @@ stonith__last_fenced_xml(pcmk__output_t *out, va_list args) {
     time_t when = va_arg(args, time_t);
 
     if (when) {
-        xmlNodePtr node = pcmk__output_create_xml_node(out, "last-fenced");
         char *buf = time_t_string(when);
 
-        xmlSetProp(node, (pcmkXmlStr) "target", (pcmkXmlStr) target);
-        xmlSetProp(node, (pcmkXmlStr) "when", (pcmkXmlStr) buf);
+        pcmk__output_create_xml_node(out, "last-fenced",
+                                     "target", target,
+                                     "when", buf,
+                                     NULL);
 
         free(buf);
         return pcmk_rc_ok;
@@ -313,13 +315,19 @@ stonith__event_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("stonith-event", "stonith_history_t *", "gboolean", "gboolean")
 int
 stonith__event_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "fence_event");
     stonith_history_t *event = va_arg(args, stonith_history_t *);
     gboolean full_history G_GNUC_UNUSED = va_arg(args, gboolean);
     gboolean later_succeeded G_GNUC_UNUSED = va_arg(args, gboolean);
 
     char *buf = NULL;
 
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "fence_event",
+                                                   "action", event->action,
+                                                   "target", event->target,
+                                                   "client", event->client,
+                                                   "origin", event->origin,
+                                                   NULL);
+
     switch (event->state) {
         case st_failed:
             xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) "failed");
@@ -342,11 +350,6 @@ stonith__event_xml(pcmk__output_t *out, va_list args) {
         xmlSetProp(node, (pcmkXmlStr) "delegate", (pcmkXmlStr) event->delegate);
     }
 
-    xmlSetProp(node, (pcmkXmlStr) "action", (pcmkXmlStr) event->action);
-    xmlSetProp(node, (pcmkXmlStr) "target", (pcmkXmlStr) event->target);
-    xmlSetProp(node, (pcmkXmlStr) "client", (pcmkXmlStr) event->client);
-    xmlSetProp(node, (pcmkXmlStr) "origin", (pcmkXmlStr) event->origin);
-
     if (event->state == st_failed || event->state == st_done) {
         buf = time_t_string(event->completed);
         xmlSetProp(node, (pcmkXmlStr) "completed", (pcmkXmlStr) buf);
@@ -412,19 +415,20 @@ stonith__validate_agent_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("validate", "const char *", "const char *", "char *", "char *", "int")
 int
 stonith__validate_agent_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "validate");
-
     const char *agent = va_arg(args, const char *);
     const char *device = va_arg(args, const char *);
     char *output = va_arg(args, char *);
     char *error_output = va_arg(args, char *);
     int rc = va_arg(args, int);
 
-    xmlSetProp(node, (pcmkXmlStr) "agent", (pcmkXmlStr) agent);
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "validate",
+                                                   "agent", agent,
+                                                   "valid", pcmk__btoa(rc),
+                                                   NULL);
+
     if (device != NULL) {
         xmlSetProp(node, (pcmkXmlStr) "device", (pcmkXmlStr) device);
     }
-    xmlSetProp(node, (pcmkXmlStr) "valid", (pcmkXmlStr) pcmk__btoa(rc));
 
     pcmk__output_xml_push_parent(out, node);
     out->subprocess_output(out, rc, output, error_output);
diff --git a/lib/pacemaker/pcmk_output.c b/lib/pacemaker/pcmk_output.c
index fd577c6..08753fb 100644
--- a/lib/pacemaker/pcmk_output.c
+++ b/lib/pacemaker/pcmk_output.c
@@ -157,16 +157,15 @@ static int colocations_list_xml(pcmk__output_t *out, va_list args) {
 
         if (pcmk_is_set(peer->flags, pe_rsc_allocating)) {
             if (dependents == FALSE) {
-                xmlNodePtr node;
-
                 if (!printed_header) {
                     pcmk__output_xml_create_parent(out, "colocations");
                     printed_header = true;
                 }
 
-                node = pcmk__output_create_xml_node(out, "colocation");
-                xmlSetProp(node, (pcmkXmlStr) "peer", (pcmkXmlStr) peer->id);
-                xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) cons->id);
+                pcmk__output_create_xml_node(out, "colocation",
+                                             "peer", peer->id,
+                                             "id", cons->id,
+                                             NULL);
             }
             continue;
         }
@@ -187,18 +186,19 @@ static int colocations_list_xml(pcmk__output_t *out, va_list args) {
 
         score = score2char(cons->score);
         if (cons->role_rh > RSC_ROLE_STARTED) {
-            xmlNodePtr node = pcmk__output_create_xml_node(out, "colocation");
-            xmlSetProp(node, (pcmkXmlStr) "peer", (pcmkXmlStr) peer->id);
-            xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) cons->id);
-            xmlSetProp(node, (pcmkXmlStr) "score", (pcmkXmlStr) score);
-            xmlSetProp(node, (pcmkXmlStr) "dependents",
-                       (pcmkXmlStr) (dependents ? "needs" : "with"));
-            xmlSetProp(node, (pcmkXmlStr) "role", (pcmkXmlStr) role2text(cons->role_rh));
+            pcmk__output_create_xml_node(out, "colocation",
+                                         "peer", peer->id,
+                                         "id", cons->id,
+                                         "score", score,
+                                         "dependents", dependents ? "needs" : "with",
+                                         "role", role2text(cons->role_rh),
+                                         NULL);
         } else {
-            xmlNodePtr node = pcmk__output_create_xml_node(out, "colocation");
-            xmlSetProp(node, (pcmkXmlStr) "peer", (pcmkXmlStr) peer->id);
-            xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) cons->id);
-            xmlSetProp(node, (pcmkXmlStr) "score", (pcmkXmlStr) score);
+            pcmk__output_create_xml_node(out, "colocation",
+                                         "peer", peer->id,
+                                         "id", cons->id,
+                                         "score", score,
+                                         NULL);
         }
 
         free(score);
@@ -263,11 +263,11 @@ static int locations_list_xml(pcmk__output_t *out, va_list args) {
             pe_node_t *node = (pe_node_t *) lpc2->data;
             char *score = score2char(node->weight);
 
-            xmlNodePtr xml_node = pcmk__output_create_xml_node(out, "location");
-            xmlSetProp(xml_node, (pcmkXmlStr) "host", (pcmkXmlStr) node->details->uname);
-            xmlSetProp(xml_node, (pcmkXmlStr) "id", (pcmkXmlStr) cons->id);
-            xmlSetProp(xml_node, (pcmkXmlStr) "score", (pcmkXmlStr) score);
-
+            pcmk__output_create_xml_node(out, "location",
+                                         "host", node->details->uname,
+                                         "id", cons->id,
+                                         "score", score,
+                                         NULL);
             free(score);
         }
     }
@@ -385,11 +385,11 @@ health_xml(pcmk__output_t *out, va_list args)
     char *fsa_state = va_arg(args, char *);
     char *result = va_arg(args, char *);
 
-    xmlNodePtr node = pcmk__output_create_xml_node(out, crm_str(sys_from));
-    xmlSetProp(node, (pcmkXmlStr) "node_name", (pcmkXmlStr) crm_str(host_from));
-    xmlSetProp(node, (pcmkXmlStr) "state", (pcmkXmlStr) crm_str(fsa_state));
-    xmlSetProp(node, (pcmkXmlStr) "result", (pcmkXmlStr) crm_str(result));
-
+    pcmk__output_create_xml_node(out, crm_str(sys_from),
+                                 "node_name", crm_str(host_from),
+                                 "state", crm_str(fsa_state),
+                                 "result", crm_str(result),
+                                 NULL);
     return pcmk_rc_ok;
 }
 
@@ -420,11 +420,10 @@ pacemakerd_health_xml(pcmk__output_t *out, va_list args)
     char *state = va_arg(args, char *);
     char *last_updated = va_arg(args, char *);
 
-
-    xmlNodePtr node = pcmk__output_create_xml_node(out, crm_str(sys_from));
-    xmlSetProp(node, (pcmkXmlStr) "state", (pcmkXmlStr) crm_str(state));
-    xmlSetProp(node, (pcmkXmlStr) "last_updated", (pcmkXmlStr) crm_str(last_updated));
-
+    pcmk__output_create_xml_node(out, crm_str(sys_from),
+                                 "state", crm_str(state),
+                                 "last_updated", crm_str(last_updated),
+                                 NULL);
     return pcmk_rc_ok;
 }
 
@@ -449,9 +448,9 @@ dc_xml(pcmk__output_t *out, va_list args)
 {
     char *dc = va_arg(args, char *);
 
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "dc");
-    xmlSetProp(node, (pcmkXmlStr) "node_name", (pcmkXmlStr) crm_str(dc));
-
+    pcmk__output_create_xml_node(out, "dc",
+                                 "node_name", crm_str(dc),
+                                 NULL);
     return pcmk_rc_ok;
 }
 
@@ -517,11 +516,11 @@ crmadmin_node_xml(pcmk__output_t *out, va_list args)
     char *name = va_arg(args, char *);
     char *id = va_arg(args, char *);
 
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "node");
-    xmlSetProp(node, (pcmkXmlStr) "type", (pcmkXmlStr) (type ? type : "member"));
-    xmlSetProp(node, (pcmkXmlStr) "name", (pcmkXmlStr) crm_str(name));
-    xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) crm_str(id));
-
+    pcmk__output_create_xml_node(out, "node",
+                                 "type", type ? type : "member",
+                                 "name", crm_str(name),
+                                 "id", crm_str(id),
+                                 NULL);
     return pcmk_rc_ok;
 }
 
diff --git a/lib/pengine/bundle.c b/lib/pengine/bundle.c
index 4f6eac3..8a17aad 100644
--- a/lib/pengine/bundle.c
+++ b/lib/pengine/bundle.c
@@ -1663,7 +1663,7 @@ pe__bundle_html(pcmk__output_t *out, va_list args)
             }
 
             if (rc == pcmk_rc_no_output) {
-                pcmk__output_create_xml_node(out, "br");
+                pcmk__output_create_xml_node(out, "br", NULL);
             }
 
             PCMK__OUTPUT_LIST_HEADER(out, FALSE, rc, "Container bundle%s: %s [%s]%s%s",
@@ -1678,7 +1678,7 @@ pe__bundle_html(pcmk__output_t *out, va_list args)
                 snprintf(buffer, LINE_MAX, " Replica[%d]", replica->offset);
                 xmlNodeSetContent(pcmk__output_xml_peek_parent(out), (pcmkXmlStr) buffer);
             }
-            pcmk__output_create_xml_node(out, "br");
+            pcmk__output_create_xml_node(out, "br", NULL);
             out->begin_list(out, NULL, NULL, NULL);
 
             if (print_ip) {
diff --git a/lib/pengine/pe_output.c b/lib/pengine/pe_output.c
index b91348f..a6f5970 100644
--- a/lib/pengine/pe_output.c
+++ b/lib/pengine/pe_output.c
@@ -465,19 +465,19 @@ pe__ban_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("ban", "pe_node_t *", "pe__location_t *", "gboolean")
 int
 pe__ban_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "ban");
     pe_node_t *pe_node = va_arg(args, pe_node_t *);
     pe__location_t *location = va_arg(args, pe__location_t *);
     gboolean print_clone_detail G_GNUC_UNUSED = va_arg(args, gboolean);
 
     char *weight_s = crm_itoa(pe_node->weight);
 
-    xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) location->id);
-    xmlSetProp(node, (pcmkXmlStr) "resource", (pcmkXmlStr) location->rsc_lh->id);
-    xmlSetProp(node, (pcmkXmlStr) "node", (pcmkXmlStr) pe_node->details->uname);
-    xmlSetProp(node, (pcmkXmlStr) "weight", (pcmkXmlStr) weight_s);
-    xmlSetProp(node, (pcmkXmlStr) "master_only",
-               (pcmkXmlStr) pcmk__btoa(location->role_filter == RSC_ROLE_MASTER));
+    pcmk__output_create_xml_node(out, "ban",
+                                 "id", location->id,
+                                 "resource", location->rsc_lh->id,
+                                 "node", pe_node->details->uname,
+                                 "weight", weight_s,
+                                 "master_only", pcmk__btoa(location->role_filter == RSC_ROLE_MASTER),
+                                 NULL);
 
     free(weight_s);
     return pcmk_rc_ok;
@@ -486,8 +486,8 @@ pe__ban_xml(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-counts", "unsigned int", "int", "int", "int")
 int
 pe__cluster_counts_html(pcmk__output_t *out, va_list args) {
-    xmlNodePtr nodes_node = pcmk__output_create_xml_node(out, "li");
-    xmlNodePtr resources_node = pcmk__output_create_xml_node(out, "li");
+    xmlNodePtr nodes_node = pcmk__output_create_xml_node(out, "li", NULL);
+    xmlNodePtr resources_node = pcmk__output_create_xml_node(out, "li", NULL);
 
     unsigned int nnodes = va_arg(args, unsigned int);
     int nresources = va_arg(args, int);
@@ -582,8 +582,8 @@ pe__cluster_counts_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-counts", "unsigned int", "int", "int", "int")
 int
 pe__cluster_counts_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr nodes_node = pcmk__output_create_xml_node(out, "nodes_configured");
-    xmlNodePtr resources_node = pcmk__output_create_xml_node(out, "resources_configured");
+    xmlNodePtr nodes_node = pcmk__output_create_xml_node(out, "nodes_configured", NULL);
+    xmlNodePtr resources_node = pcmk__output_create_xml_node(out, "resources_configured", NULL);
 
     unsigned int nnodes = va_arg(args, unsigned int);
     int nresources = va_arg(args, int);
@@ -612,7 +612,7 @@ pe__cluster_counts_xml(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-dc", "pe_node_t *", "const char *", "const char *", "char *")
 int
 pe__cluster_dc_html(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "li");
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "li", NULL);
 
     pe_node_t *dc = va_arg(args, pe_node_t *);
     const char *quorum = va_arg(args, const char *);
@@ -665,22 +665,23 @@ pe__cluster_dc_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-dc", "pe_node_t *", "const char *", "const char *", "char *")
 int
 pe__cluster_dc_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "current_dc");
-
     pe_node_t *dc = va_arg(args, pe_node_t *);
     const char *quorum = va_arg(args, const char *);
     const char *dc_version_s = va_arg(args, const char *);
     char *dc_name G_GNUC_UNUSED = va_arg(args, char *);
 
     if (dc) {
-        xmlSetProp(node, (pcmkXmlStr) "present", (pcmkXmlStr) "true");
-        xmlSetProp(node, (pcmkXmlStr) "version", (pcmkXmlStr) (dc_version_s ? dc_version_s : ""));
-        xmlSetProp(node, (pcmkXmlStr) "name", (pcmkXmlStr) dc->details->uname);
-        xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) dc->details->id);
-        xmlSetProp(node, (pcmkXmlStr) "with_quorum",
-                   (pcmkXmlStr) pcmk__btoa(crm_is_true(quorum)));
+        pcmk__output_create_xml_node(out, "current_dc",
+                                     "present", "true",
+                                     "version", dc_version_s ? dc_version_s : "",
+                                     "name", dc->details->uname,
+                                     "id", dc->details->id,
+                                     "with_quorum", pcmk__btoa(crm_is_true(quorum)),
+                                     NULL);
     } else {
-        xmlSetProp(node, (pcmkXmlStr) "present", (pcmkXmlStr) "false");
+        pcmk__output_create_xml_node(out, "current_dc",
+                                     "present", "false",
+                                     NULL);
     }
 
     return pcmk_rc_ok;
@@ -741,14 +742,14 @@ pe__cluster_options_html(pcmk__output_t *out, va_list args) {
     }
 
     if (pcmk_is_set(data_set->flags, pe_flag_maintenance_mode)) {
-        xmlNodePtr node = pcmk__output_create_xml_node(out, "li");
+        xmlNodePtr node = pcmk__output_create_xml_node(out, "li", NULL);
 
         pcmk_create_html_node(node, "span", NULL, NULL, "Resource management: ");
         pcmk_create_html_node(node, "span", NULL, "bold", "DISABLED");
         pcmk_create_html_node(node, "span", NULL, NULL,
                               " (the cluster will not attempt to start, stop, or recover services)");
     } else if (pcmk_is_set(data_set->flags, pe_flag_stop_everything)) {
-        xmlNodePtr node = pcmk__output_create_xml_node(out, "li");
+        xmlNodePtr node = pcmk__output_create_xml_node(out, "li", NULL);
 
         pcmk_create_html_node(node, "span", NULL, NULL, "Resource management: ");
         pcmk_create_html_node(node, "span", NULL, "bold", "STOPPED");
@@ -817,48 +818,45 @@ pe__cluster_options_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-options", "pe_working_set_t *")
 int
 pe__cluster_options_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "cluster_options");
     pe_working_set_t *data_set = va_arg(args, pe_working_set_t *);
-
-    xmlSetProp(node, (pcmkXmlStr) "stonith-enabled",
-               (pcmkXmlStr) pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_stonith_enabled)));
-    xmlSetProp(node, (pcmkXmlStr) "symmetric-cluster",
-               (pcmkXmlStr) pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_symmetric_cluster)));
+    const char *no_quorum_policy = NULL;
 
     switch (data_set->no_quorum_policy) {
         case no_quorum_freeze:
-            xmlSetProp(node, (pcmkXmlStr) "no-quorum-policy", (pcmkXmlStr) "freeze");
+            no_quorum_policy = "freeze";
             break;
 
         case no_quorum_stop:
-            xmlSetProp(node, (pcmkXmlStr) "no-quorum-policy", (pcmkXmlStr) "stop");
+            no_quorum_policy = "stop";
             break;
 
         case no_quorum_demote:
-            xmlSetProp(node, (pcmkXmlStr) "no-quorum-policy", (pcmkXmlStr) "demote");
+            no_quorum_policy = "demote";
             break;
 
         case no_quorum_ignore:
-            xmlSetProp(node, (pcmkXmlStr) "no-quorum-policy", (pcmkXmlStr) "ignore");
+            no_quorum_policy = "ignore";
             break;
 
         case no_quorum_suicide:
-            xmlSetProp(node, (pcmkXmlStr) "no-quorum-policy", (pcmkXmlStr) "suicide");
+            no_quorum_policy = "suicide";
             break;
     }
 
-    xmlSetProp(node, (pcmkXmlStr) "maintenance-mode",
-               (pcmkXmlStr) pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_maintenance_mode)));
-    xmlSetProp(node, (pcmkXmlStr) "stop-all-resources",
-               (pcmkXmlStr) pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_stop_everything)));
-
+    pcmk__output_create_xml_node(out, "cluster_options",
+                                 "stonith-enabled", pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_stonith_enabled)),
+                                 "symmetric-cluster", pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_symmetric_cluster)),
+                                 "no-quorum-policy", no_quorum_policy,
+                                 "maintenance-mode", pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_maintenance_mode)),
+                                 "stop-all-resources", pcmk__btoa(pcmk_is_set(data_set->flags, pe_flag_stop_everything)),
+                                 NULL);
     return pcmk_rc_ok;
 }
 
 PCMK__OUTPUT_ARGS("cluster-stack", "const char *")
 int
 pe__cluster_stack_html(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "li");
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "li", NULL);
     const char *stack_s = va_arg(args, const char *);
 
     pcmk_create_html_node(node, "span", NULL, "bold", "Stack: ");
@@ -878,10 +876,11 @@ pe__cluster_stack_text(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-stack", "const char *")
 int
 pe__cluster_stack_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "stack");
     const char *stack_s = va_arg(args, const char *);
 
-    xmlSetProp(node, (pcmkXmlStr) "type", (pcmkXmlStr) stack_s);
+    pcmk__output_create_xml_node(out, "stack",
+                                 "type", stack_s,
+                                 NULL);
 
     return pcmk_rc_ok;
 }
@@ -889,8 +888,8 @@ pe__cluster_stack_xml(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-times", "const char *", "const char *", "const char *", "const char *")
 int
 pe__cluster_times_html(pcmk__output_t *out, va_list args) {
-    xmlNodePtr updated_node = pcmk__output_create_xml_node(out, "li");
-    xmlNodePtr changed_node = pcmk__output_create_xml_node(out, "li");
+    xmlNodePtr updated_node = pcmk__output_create_xml_node(out, "li", NULL);
+    xmlNodePtr changed_node = pcmk__output_create_xml_node(out, "li", NULL);
 
     const char *last_written = va_arg(args, const char *);
     const char *user = va_arg(args, const char *);
@@ -913,20 +912,20 @@ pe__cluster_times_html(pcmk__output_t *out, va_list args) {
 PCMK__OUTPUT_ARGS("cluster-times", "const char *", "const char *", "const char *", "const char *")
 int
 pe__cluster_times_xml(pcmk__output_t *out, va_list args) {
-    xmlNodePtr updated_node = pcmk__output_create_xml_node(out, "last_update");
-    xmlNodePtr changed_node = pcmk__output_create_xml_node(out, "last_change");
-
     const char *last_written = va_arg(args, const char *);
     const char *user = va_arg(args, const char *);
     const char *client = va_arg(args, const char *);
     const char *origin = va_arg(args, const char *);
 
-    xmlSetProp(updated_node, (pcmkXmlStr) "time",
-               (pcmkXmlStr) pcmk__epoch2str(NULL));
-    xmlSetProp(changed_node, (pcmkXmlStr) "time", (pcmkXmlStr) (last_written ? last_written : ""));
-    xmlSetProp(changed_node, (pcmkXmlStr) "user", (pcmkXmlStr) (user ? user : ""));
-    xmlSetProp(changed_node, (pcmkXmlStr) "client", (pcmkXmlStr) (client ? client : ""));
-    xmlSetProp(changed_node, (pcmkXmlStr) "origin", (pcmkXmlStr) (origin ? origin : ""));
+    pcmk__output_create_xml_node(out, "last_update",
+                                 "time", pcmk__epoch2str(NULL),
+                                 NULL);
+    pcmk__output_create_xml_node(out, "last_change",
+                                 "time", last_written ? last_written : "",
+                                 "user", user ? user : "",
+                                 "client", client ? client : "",
+                                 "origin", origin ? origin : "",
+                                 NULL);
 
     return pcmk_rc_ok;
 }
@@ -972,20 +971,15 @@ pe__failed_action_xml(pcmk__output_t *out, va_list args) {
 
     char *rc_s = crm_itoa(rc);
     char *reason_s = crm_xml_escape(exit_reason ? exit_reason : "none");
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "failure");
-
-    xmlSetProp(node, (pcmkXmlStr) (op_key ? "op_key" : "id"),
-               (pcmkXmlStr) (op_key ? op_key : ID(xml_op)));
-    xmlSetProp(node, (pcmkXmlStr) "node",
-               (pcmkXmlStr) crm_element_value(xml_op, XML_ATTR_UNAME));
-    xmlSetProp(node, (pcmkXmlStr) "exitstatus",
-               (pcmkXmlStr) services_ocf_exitcode_str(rc));
-    xmlSetProp(node, (pcmkXmlStr) "exitreason", (pcmkXmlStr) reason_s);
-    xmlSetProp(node, (pcmkXmlStr) "exitcode", (pcmkXmlStr) rc_s);
-    xmlSetProp(node, (pcmkXmlStr) "call",
-               (pcmkXmlStr) crm_element_value(xml_op, XML_LRM_ATTR_CALLID));
-    xmlSetProp(node, (pcmkXmlStr) "status",
-               (pcmkXmlStr) services_lrm_status_str(status));
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "failure",
+                                                   op_key ? "op_key" : "id", op_key ? op_key : ID(xml_op),
+                                                   "node", crm_element_value(xml_op, XML_ATTR_UNAME),
+                                                   "exitstatus", services_ocf_exitcode_str(rc),
+                                                   "exitreason", reason_s,
+                                                   "exitcode", rc_s,
+                                                   "call", crm_element_value(xml_op, XML_LRM_ATTR_CALLID),
+                                                   "status", services_lrm_status_str(status),
+                                                   NULL);
 
     if (last) {
         guint interval_ms = 0;
@@ -1037,7 +1031,7 @@ pe__node_html(pcmk__output_t *out, va_list args) {
     char *buf = crm_strdup_printf("Node: %s", node_name);
 
     if (full) {
-        xmlNodePtr item_node = pcmk__output_create_xml_node(out, "li");
+        xmlNodePtr item_node = pcmk__output_create_xml_node(out, "li", NULL);
 
         pcmk_create_html_node(item_node, "span", NULL, NULL, buf);
 
@@ -1265,7 +1259,7 @@ pe__node_attribute_html(pcmk__output_t *out, va_list args) {
     if (add_extra) {
         int v = crm_parse_int(value, "0");
         char *s = crm_strdup_printf("%s: %s", name, value);
-        xmlNodePtr item_node = pcmk__output_create_xml_node(out, "li");
+        xmlNodePtr item_node = pcmk__output_create_xml_node(out, "li", NULL);
 
         pcmk_create_html_node(item_node, "span", NULL, NULL, s);
         free(s);
@@ -1351,7 +1345,13 @@ pe__node_and_op_xml(pcmk__output_t *out, va_list args) {
     int status = crm_parse_int(status_s, "0");
     time_t last_change = 0;
 
-    xmlNode *node = pcmk__output_create_xml_node(out, "operation");
+    xmlNode *node = pcmk__output_create_xml_node(out, "operation",
+                                                 "op", op_key ? op_key : ID(xml_op),
+                                                 "node", crm_element_value(xml_op, XML_ATTR_UNAME),
+                                                 "call", crm_element_value(xml_op, XML_LRM_ATTR_CALLID),
+                                                 "rc", crm_element_value(xml_op, XML_LRM_ATTR_RC),
+                                                 "status", services_lrm_status_str(status),
+                                                 NULL);
 
     rsc = pe_find_resource(data_set->resources, op_rsc);
 
@@ -1382,8 +1382,6 @@ pe__node_and_op_xml(pcmk__output_t *out, va_list args) {
                    (pcmkXmlStr) crm_element_value(xml_op, XML_RSC_OP_T_EXEC));
     }
 
-    xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) services_lrm_status_str(status));
-
     return pcmk_rc_ok;
 }
 
@@ -1395,9 +1393,10 @@ pe__node_attribute_xml(pcmk__output_t *out, va_list args) {
     gboolean add_extra = va_arg(args, gboolean);
     int expected_score = va_arg(args, int);
 
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "attribute");
-    xmlSetProp(node, (pcmkXmlStr) "name", (pcmkXmlStr) name);
-    xmlSetProp(node, (pcmkXmlStr) "value", (pcmkXmlStr) value);
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "attribute",
+                                                   "name", name,
+                                                   "value", value,
+                                                   NULL);
 
     if (add_extra) {
         char *buf = crm_itoa(expected_score);
@@ -1630,13 +1629,14 @@ pe__op_history_xml(pcmk__output_t *out, va_list args) {
     int rc = va_arg(args, int);
     gboolean print_timing = va_arg(args, gboolean);
 
-    char *rc_s = NULL;
-
-    xmlNodePtr node = pcmk__output_create_xml_node(out, "operation_history");
-
-    xmlSetProp(node, (pcmkXmlStr) "call",
-               (pcmkXmlStr) crm_element_value(xml_op, XML_LRM_ATTR_CALLID));
-    xmlSetProp(node, (pcmkXmlStr) "task", (pcmkXmlStr) task);
+    char *rc_s = crm_itoa(rc);
+    xmlNodePtr node = pcmk__output_create_xml_node(out, "operation_history",
+                                                   "call", crm_element_value(xml_op, XML_LRM_ATTR_CALLID),
+                                                   "task", task,
+                                                   "rc", rc_s,
+                                                   "rc_text", services_ocf_exitcode_str(rc),
+                                                   NULL);
+    free(rc_s);
 
     if (interval_ms_s && !pcmk__str_eq(interval_ms_s, "0", pcmk__str_casei)) {
         char *s = crm_strdup_printf("%sms", interval_ms_s);
@@ -1921,11 +1921,11 @@ pe__ticket_xml(pcmk__output_t *out, va_list args) {
 
     pe_ticket_t *ticket = va_arg(args, pe_ticket_t *);
 
-    node = pcmk__output_create_xml_node(out, "ticket");
-    xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) ticket->id);
-    xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) (ticket->granted ? "granted" : "revoked"));
-    xmlSetProp(node, (pcmkXmlStr) "standby",
-               (pcmkXmlStr) pcmk__btoa(ticket->standby));
+    node = pcmk__output_create_xml_node(out, "ticket",
+                                        "id", ticket->id,
+                                        "status", ticket->granted ? "granted" : "revoked",
+                                        "standby", pcmk__btoa(ticket->standby),
+                                        NULL);
 
     if (ticket->last_granted > -1) {
         xmlSetProp(node, (pcmkXmlStr) "last-granted",
diff --git a/tools/crm_resource_print.c b/tools/crm_resource_print.c
index 6303863..ca8bee2 100644
--- a/tools/crm_resource_print.c
+++ b/tools/crm_resource_print.c
@@ -247,9 +247,9 @@ resource_check_xml(pcmk__output_t *out, va_list args) {
     pe_resource_t *parent = uber_parent(checks->rsc);
     int rc = pcmk_rc_no_output;
 
-    xmlNode *node = pcmk__output_create_xml_node(out, "check");
-
-    xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) parent->id);
+    xmlNode *node = pcmk__output_create_xml_node(out, "check",
+                                                 "id", parent->id,
+                                                 NULL);
 
     if (pcmk_is_set(checks->flags, rsc_remain_stopped)) {
         xmlSetProp(node, (pcmkXmlStr) "remain_stopped", (pcmkXmlStr) "true");
-- 
1.8.3.1


From 859b7f6daaddbbbfc102b968c4076dc03e03c100 Mon Sep 17 00:00:00 2001
From: Chris Lumens <clumens@redhat.com>
Date: Wed, 18 Nov 2020 13:42:40 -0500
Subject: [PATCH 3/6] Refactor: libs: Set multiple XML properties at once.

This just wraps pcmk__xe_set_propv with another function that takes
arguments directly, and then uses that function throughout the libraries
wherever multiple properties are set at once.
---
 include/crm/common/xml_internal.h | 17 ++++++++++++++++
 lib/common/output_html.c          |  6 ++++--
 lib/common/output_xml.c           |  5 +++--
 lib/common/xml.c                  |  9 +++++++++
 lib/fencing/st_output.c           |  6 ++++--
 lib/pengine/pe_output.c           | 42 +++++++++++++++------------------------
 6 files changed, 53 insertions(+), 32 deletions(-)

diff --git a/include/crm/common/xml_internal.h b/include/crm/common/xml_internal.h
index c60fa51..13157c6 100644
--- a/include/crm/common/xml_internal.h
+++ b/include/crm/common/xml_internal.h
@@ -235,7 +235,24 @@ pcmk__xe_next(const xmlNode *child)
     return next;
 }
 
+/*!
+ * \internal
+ * \brief Like pcmk__xe_set_props, but takes a va_list instead of
+ *        arguments directly.
+ */
 void
 pcmk__xe_set_propv(xmlNodePtr node, va_list pairs);
 
+/*!
+ * \internal
+ * \brief Add a NULL-terminated list of name/value pairs to the given
+ *        XML node as properties.
+ *
+ * \param[in,out] node XML node to add properties to
+ * \param[in]     ...  NULL-terminated list of name/value pairs
+ */
+void
+pcmk__xe_set_props(xmlNodePtr node, ...)
+G_GNUC_NULL_TERMINATED;
+
 #endif // PCMK__XML_INTERNAL__H
diff --git a/lib/common/output_html.c b/lib/common/output_html.c
index 77a5410..5daf831 100644
--- a/lib/common/output_html.c
+++ b/lib/common/output_html.c
@@ -20,6 +20,7 @@
 #include <crm/crm.h>
 #include <crm/common/output_internal.h>
 #include <crm/common/xml.h>
+#include <crm/common/xml_internal.h>
 
 static const char *stylesheet_default =
     ".bold { font-weight: bold }\n"
@@ -153,8 +154,9 @@ finish_reset_common(pcmk__output_t *out, crm_exit_t exit_status, bool print) {
 
     if (stylesheet_link != NULL) {
         htmlNodePtr link_node = create_xml_node(head_node, "link");
-        xmlSetProp(link_node, (pcmkXmlStr) "rel", (pcmkXmlStr) "stylesheet");
-        xmlSetProp(link_node, (pcmkXmlStr) "href", (pcmkXmlStr) stylesheet_link);
+        pcmk__xe_set_props(link_node, "rel", "stylesheet",
+                           "href", stylesheet_link,
+                           NULL);
     }
 
     xmlAddPrevSibling(priv->root->children, head_node);
diff --git a/lib/common/output_xml.c b/lib/common/output_xml.c
index 80ee2de..133b892 100644
--- a/lib/common/output_xml.c
+++ b/lib/common/output_xml.c
@@ -157,8 +157,9 @@ finish_reset_common(pcmk__output_t *out, crm_exit_t exit_status, bool print) {
         char *rc_as_str = crm_itoa(exit_status);
 
         node = create_xml_node(priv->root, "status");
-        xmlSetProp(node, (pcmkXmlStr) "code", (pcmkXmlStr) rc_as_str);
-        xmlSetProp(node, (pcmkXmlStr) "message", (pcmkXmlStr) crm_exit_str(exit_status));
+        pcmk__xe_set_props(node, "code", rc_as_str,
+                           "message", crm_exit_str(exit_status),
+                           NULL);
 
         if (g_slist_length(priv->errors) > 0) {
             xmlNodePtr errors_node = create_xml_node(node, "errors");
diff --git a/lib/common/xml.c b/lib/common/xml.c
index 61cac9f..e5de0d4 100644
--- a/lib/common/xml.c
+++ b/lib/common/xml.c
@@ -2955,6 +2955,15 @@ pcmk__xe_set_propv(xmlNodePtr node, va_list pairs)
     }
 }
 
+void
+pcmk__xe_set_props(xmlNodePtr node, ...)
+{
+    va_list pairs;
+    va_start(pairs, node);
+    pcmk__xe_set_propv(node, pairs);
+    va_end(pairs);
+}
+
 // Deprecated functions kept only for backward API compatibility
 
 xmlNode *find_entity(xmlNode *parent, const char *node_name, const char *id);
diff --git a/lib/fencing/st_output.c b/lib/fencing/st_output.c
index 82520ee..65f8ec9 100644
--- a/lib/fencing/st_output.c
+++ b/lib/fencing/st_output.c
@@ -15,6 +15,7 @@
 #include <crm/common/util.h>
 #include <crm/common/xml.h>
 #include <crm/common/output_internal.h>
+#include <crm/common/xml_internal.h>
 #include <crm/fencing/internal.h>
 #include <crm/pengine/internal.h>
 
@@ -339,8 +340,9 @@ stonith__event_xml(pcmk__output_t *out, va_list args) {
 
         default: {
             char *state = crm_itoa(event->state);
-            xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) "pending");
-            xmlSetProp(node, (pcmkXmlStr) "extended-status", (pcmkXmlStr) state);
+            pcmk__xe_set_props(node, "status", "pending",
+                               "extended-status", state,
+                               NULL);
             free(state);
             break;
         }
diff --git a/lib/pengine/pe_output.c b/lib/pengine/pe_output.c
index a6f5970..294f6e1 100644
--- a/lib/pengine/pe_output.c
+++ b/lib/pengine/pe_output.c
@@ -9,6 +9,7 @@
 
 #include <crm_internal.h>
 #include <crm/common/iso8601_internal.h>
+#include <crm/common/xml_internal.h>
 #include <crm/msg_xml.h>
 #include <crm/pengine/internal.h>
 
@@ -994,14 +995,12 @@ pe__failed_action_xml(pcmk__output_t *out, va_list args) {
         crm_time_set_timet(crm_when, &when);
         rc_change = crm_time_as_string(crm_when, crm_time_log_date | crm_time_log_timeofday | crm_time_log_with_timezone);
 
-        xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_LAST_CHANGE, (pcmkXmlStr) rc_change);
-        xmlSetProp(node, (pcmkXmlStr) "queued",
-                   (pcmkXmlStr) crm_element_value(xml_op, XML_RSC_OP_T_QUEUE));
-        xmlSetProp(node, (pcmkXmlStr) "exec",
-                   (pcmkXmlStr) crm_element_value(xml_op, XML_RSC_OP_T_EXEC));
-        xmlSetProp(node, (pcmkXmlStr) "interval", (pcmkXmlStr) s);
-        xmlSetProp(node, (pcmkXmlStr) "task",
-                   (pcmkXmlStr) crm_element_value(xml_op, XML_LRM_ATTR_TASK));
+        pcmk__xe_set_props(node, XML_RSC_OP_LAST_CHANGE, rc_change,
+                           "queued", crm_element_value(xml_op, XML_RSC_OP_T_QUEUE),
+                           "exec", crm_element_value(xml_op, XML_RSC_OP_T_EXEC),
+                           "interval", s,
+                           "task", crm_element_value(xml_op, XML_LRM_ATTR_TASK),
+                           NULL);
 
         free(s);
         free(rc_change);
@@ -1364,22 +1363,17 @@ pe__node_and_op_xml(pcmk__output_t *out, va_list args) {
                                         pcmk_is_set(pcmk_get_ra_caps(class), pcmk_ra_cap_provider) ? crm_element_value(rsc->xml, XML_AGENT_ATTR_PROVIDER) : "",
                                         kind);
 
-        xmlSetProp(node, (pcmkXmlStr) "rsc", (pcmkXmlStr) rsc_printable_id(rsc));
-        xmlSetProp(node, (pcmkXmlStr) "agent", (pcmkXmlStr) agent_tuple);
+        pcmk__xe_set_props(node, "rsc", rsc_printable_id(rsc),
+                           "agent", agent_tuple,
+                           NULL);
         free(agent_tuple);
     }
 
-    xmlSetProp(node, (pcmkXmlStr) "op", (pcmkXmlStr) (op_key ? op_key : ID(xml_op)));
-    xmlSetProp(node, (pcmkXmlStr) "node", (pcmkXmlStr) crm_element_value(xml_op, XML_ATTR_UNAME));
-    xmlSetProp(node, (pcmkXmlStr) "call", (pcmkXmlStr) crm_element_value(xml_op, XML_LRM_ATTR_CALLID));
-    xmlSetProp(node, (pcmkXmlStr) "rc", (pcmkXmlStr) crm_element_value(xml_op, XML_LRM_ATTR_RC));
-
     if (crm_element_value_epoch(xml_op, XML_RSC_OP_LAST_CHANGE,
                                 &last_change) == pcmk_ok) {
-        xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_LAST_CHANGE,
-                   (pcmkXmlStr) crm_strip_trailing_newline(ctime(&last_change)));
-        xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_T_EXEC,
-                   (pcmkXmlStr) crm_element_value(xml_op, XML_RSC_OP_T_EXEC));
+        pcmk__xe_set_props(node, XML_RSC_OP_LAST_CHANGE, crm_strip_trailing_newline(ctime(&last_change)),
+                           XML_RSC_OP_T_EXEC, crm_element_value(xml_op, XML_RSC_OP_T_EXEC),
+                           NULL);
     }
 
     return pcmk_rc_ok;
@@ -1679,10 +1673,6 @@ pe__op_history_xml(pcmk__output_t *out, va_list args) {
         }
     }
 
-    rc_s = crm_itoa(rc);
-    xmlSetProp(node, (pcmkXmlStr) "rc", (pcmkXmlStr) rc_s);
-    xmlSetProp(node, (pcmkXmlStr) "rc_text", (pcmkXmlStr) services_ocf_exitcode_str(rc));
-    free(rc_s);
     return pcmk_rc_ok;
 }
 
@@ -1746,9 +1736,9 @@ pe__resource_history_xml(pcmk__output_t *out, va_list args) {
     } else if (all || failcount || last_failure > 0) {
         char *migration_s = crm_itoa(rsc->migration_threshold);
 
-        xmlSetProp(node, (pcmkXmlStr) "orphan", (pcmkXmlStr) "false");
-        xmlSetProp(node, (pcmkXmlStr) "migration-threshold",
-                   (pcmkXmlStr) migration_s);
+        pcmk__xe_set_props(node, "orphan", "false",
+                           "migration-threshold", migration_s,
+                           NULL);
         free(migration_s);
 
         if (failcount > 0) {
-- 
1.8.3.1


From 1c9b4af53445091c211a48e6027c102133498fbb Mon Sep 17 00:00:00 2001
From: Chris Lumens <clumens@redhat.com>
Date: Tue, 17 Nov 2020 14:26:33 -0500
Subject: [PATCH 4/6] Refactor: libs: Set XML properties when creating a parent
 node.

This is just like what's going on with pcmk__output_create_xml_node,
except for pcmk__output_create_parent.
---
 include/crm/common/output_internal.h |  4 +++-
 lib/common/output_html.c             |  6 +++---
 lib/common/output_xml.c              | 22 ++++++++++++-------
 lib/lrmd/lrmd_output.c               | 17 ++++++++-------
 lib/pacemaker/pcmk_output.c          | 16 +++++++-------
 lib/pengine/bundle.c                 |  2 +-
 lib/pengine/pe_output.c              | 10 +++++----
 tools/crm_resource_print.c           | 41 ++++++++++++++++++------------------
 8 files changed, 64 insertions(+), 54 deletions(-)

diff --git a/include/crm/common/output_internal.h b/include/crm/common/output_internal.h
index 1923c1a..4bf6b3d 100644
--- a/include/crm/common/output_internal.h
+++ b/include/crm/common/output_internal.h
@@ -626,9 +626,11 @@ pcmk__indented_vprintf(pcmk__output_t *out, const char *format, va_list args) G_
  *
  * \param[in,out] out  The output functions structure.
  * \param[in]     name The name of the node to be created.
+ * \param[in]     ...     Name/value pairs to set as XML properties.
  */
 xmlNodePtr
-pcmk__output_xml_create_parent(pcmk__output_t *out, const char *name);
+pcmk__output_xml_create_parent(pcmk__output_t *out, const char *name, ...)
+G_GNUC_NULL_TERMINATED;
 
 /*!
  * \internal
diff --git a/lib/common/output_html.c b/lib/common/output_html.c
index 5daf831..cf51af4 100644
--- a/lib/common/output_html.c
+++ b/lib/common/output_html.c
@@ -102,7 +102,7 @@ html_init(pcmk__output_t *out) {
     g_queue_push_tail(priv->parent_q, priv->root);
     priv->errors = NULL;
 
-    pcmk__output_xml_create_parent(out, "body");
+    pcmk__output_xml_create_parent(out, "body", NULL);
 
     return true;
 }
@@ -294,7 +294,7 @@ html_begin_list(pcmk__output_t *out, const char *singular_noun,
      */
     q_len = g_queue_get_length(priv->parent_q);
     if (q_len > 2) {
-        pcmk__output_xml_create_parent(out, "li");
+        pcmk__output_xml_create_parent(out, "li", NULL);
     }
 
     if (format != NULL) {
@@ -316,7 +316,7 @@ html_begin_list(pcmk__output_t *out, const char *singular_noun,
         free(buf);
     }
 
-    node = pcmk__output_xml_create_parent(out, "ul");
+    node = pcmk__output_xml_create_parent(out, "ul", NULL);
     g_queue_push_tail(priv->parent_q, node);
 }
 
diff --git a/lib/common/output_xml.c b/lib/common/output_xml.c
index 133b892..6d92625 100644
--- a/lib/common/output_xml.c
+++ b/lib/common/output_xml.c
@@ -217,8 +217,9 @@ xml_subprocess_output(pcmk__output_t *out, int exit_status,
 
     rc_as_str = crm_itoa(exit_status);
 
-    node = pcmk__output_xml_create_parent(out, "command");
-    xmlSetProp(node, (pcmkXmlStr) "code", (pcmkXmlStr) rc_as_str);
+    node = pcmk__output_xml_create_parent(out, "command",
+                                          "code", rc_as_str,
+                                          NULL);
 
     if (proc_stdout != NULL) {
         child_node = pcmk_create_xml_text_node(node, "output", proc_stdout);
@@ -312,12 +313,11 @@ xml_begin_list(pcmk__output_t *out, const char *singular_noun, const char *plura
     }
 
     if (legacy_xml || simple_list) {
-        pcmk__output_xml_create_parent(out, name);
+        pcmk__output_xml_create_parent(out, name, NULL);
     } else {
-        xmlNodePtr list_node = NULL;
-
-        list_node = pcmk__output_xml_create_parent(out, "list");
-        xmlSetProp(list_node, (pcmkXmlStr) "name", (pcmkXmlStr) name);
+        pcmk__output_xml_create_parent(out, "list",
+                                       "name", name,
+                                       NULL);
     }
 
     g_free(name);
@@ -420,8 +420,14 @@ pcmk__mk_xml_output(char **argv) {
 }
 
 xmlNodePtr
-pcmk__output_xml_create_parent(pcmk__output_t *out, const char *name) {
+pcmk__output_xml_create_parent(pcmk__output_t *out, const char *name, ...) {
+    va_list args;
     xmlNodePtr node = pcmk__output_create_xml_node(out, name, NULL);
+
+    va_start(args, name);
+    pcmk__xe_set_propv(node, args);
+    va_end(args);
+
     pcmk__output_xml_push_parent(out, node);
     return node;
 }
diff --git a/lib/lrmd/lrmd_output.c b/lib/lrmd/lrmd_output.c
index 7dc0709..c01cc5e 100644
--- a/lib/lrmd/lrmd_output.c
+++ b/lib/lrmd/lrmd_output.c
@@ -46,9 +46,9 @@ lrmd__alternatives_list_xml(pcmk__output_t *out, va_list args) {
     lrmd_list_t *list = va_arg(args, lrmd_list_t *);
     const char *agent_spec = va_arg(args, const char *);
 
-    xmlNodePtr node = pcmk__output_xml_create_parent(out, "providers");
-
-    xmlSetProp(node, (pcmkXmlStr) "for", (pcmkXmlStr) agent_spec);
+    pcmk__output_xml_create_parent(out, "providers",
+                                   "for", agent_spec,
+                                   NULL);
     return xml_list(out, list, "provider");
 }
 
@@ -68,8 +68,9 @@ lrmd__agents_list_xml(pcmk__output_t *out, va_list args) {
     const char *agent_spec = va_arg(args, const char *);
     char *provider = va_arg(args, char *);
 
-    xmlNodePtr node = pcmk__output_xml_create_parent(out, "agents");
-    xmlSetProp(node, (pcmkXmlStr) "standard", (pcmkXmlStr) agent_spec);
+    xmlNodePtr node = pcmk__output_xml_create_parent(out, "agents",
+                                                     "standard", agent_spec,
+                                                     NULL);
 
     if (!pcmk__str_empty(provider)) {
         xmlSetProp(node, (pcmkXmlStr) "provider", (pcmkXmlStr) provider);
@@ -99,9 +100,9 @@ lrmd__providers_list_xml(pcmk__output_t *out, va_list args) {
     lrmd_list_t *list = va_arg(args, lrmd_list_t *);
     const char *agent_spec = va_arg(args, const char *);
 
-    xmlNodePtr node = pcmk__output_xml_create_parent(out, "providers");
-
-    xmlSetProp(node, (pcmkXmlStr) "standard", (pcmkXmlStr) "ocf");
+    xmlNodePtr node = pcmk__output_xml_create_parent(out, "providers",
+                                                     "standard", "ocf",
+                                                     NULL);
 
     if (agent_spec != NULL) {
         xmlSetProp(node, (pcmkXmlStr) "agent", (pcmkXmlStr) agent_spec);
diff --git a/lib/pacemaker/pcmk_output.c b/lib/pacemaker/pcmk_output.c
index 08753fb..74a7c59 100644
--- a/lib/pacemaker/pcmk_output.c
+++ b/lib/pacemaker/pcmk_output.c
@@ -158,7 +158,7 @@ static int colocations_list_xml(pcmk__output_t *out, va_list args) {
         if (pcmk_is_set(peer->flags, pe_rsc_allocating)) {
             if (dependents == FALSE) {
                 if (!printed_header) {
-                    pcmk__output_xml_create_parent(out, "colocations");
+                    pcmk__output_xml_create_parent(out, "colocations", NULL);
                     printed_header = true;
                 }
 
@@ -172,7 +172,7 @@ static int colocations_list_xml(pcmk__output_t *out, va_list args) {
 
         if (dependents && recursive) {
             if (!printed_header) {
-                pcmk__output_xml_create_parent(out, "colocations");
+                pcmk__output_xml_create_parent(out, "colocations", NULL);
                 printed_header = true;
             }
 
@@ -180,7 +180,7 @@ static int colocations_list_xml(pcmk__output_t *out, va_list args) {
         }
 
         if (!printed_header) {
-            pcmk__output_xml_create_parent(out, "colocations");
+            pcmk__output_xml_create_parent(out, "colocations", NULL);
             printed_header = true;
         }
 
@@ -252,7 +252,7 @@ static int locations_list_xml(pcmk__output_t *out, va_list args) {
     GListPtr lpc = NULL;
     GListPtr list = rsc->rsc_location;
 
-    pcmk__output_xml_create_parent(out, "locations");
+    pcmk__output_xml_create_parent(out, "locations", NULL);
 
     for (lpc = list; lpc != NULL; lpc = lpc->next) {
         pe__location_t *cons = lpc->data;
@@ -323,7 +323,6 @@ stacks_and_constraints_xml(pcmk__output_t *out, va_list args) {
     gboolean recursive = va_arg(args, gboolean);
 
     GListPtr lpc = NULL;
-    xmlNodePtr node = NULL;
     xmlNode *cib_constraints = get_object_root(XML_CIB_TAG_CONSTRAINTS,
                                                data_set->input);
 
@@ -338,12 +337,13 @@ stacks_and_constraints_xml(pcmk__output_t *out, va_list args) {
         pe__clear_resource_flags(r, pe_rsc_allocating);
     }
 
-    pcmk__output_xml_create_parent(out, "constraints");
+    pcmk__output_xml_create_parent(out, "constraints", NULL);
 
     out->message(out, "colocations-list", rsc, TRUE, recursive);
 
-    node = pcmk__output_xml_create_parent(out, "resource");
-    xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) rsc->id);
+    pcmk__output_xml_create_parent(out, "resource",
+                                   "id", rsc->id,
+                                   NULL);
     out->message(out, "locations-list", rsc);
     pcmk__output_xml_pop_parent(out);
 
diff --git a/lib/pengine/bundle.c b/lib/pengine/bundle.c
index 8a17aad..543f5dc 100644
--- a/lib/pengine/bundle.c
+++ b/lib/pengine/bundle.c
@@ -1672,7 +1672,7 @@ pe__bundle_html(pcmk__output_t *out, va_list args)
                                      pcmk_is_set(rsc->flags, pe_rsc_unique) ? " (unique)" : "",
                                      pcmk_is_set(rsc->flags, pe_rsc_managed) ? "" : " (unmanaged)");
 
-            pcmk__output_xml_create_parent(out, "li");
+            pcmk__output_xml_create_parent(out, "li", NULL);
 
             if (pcmk__list_of_multiple(bundle_data->replicas)) {
                 snprintf(buffer, LINE_MAX, " Replica[%d]", replica->offset);
diff --git a/lib/pengine/pe_output.c b/lib/pengine/pe_output.c
index 294f6e1..470b025 100644
--- a/lib/pengine/pe_output.c
+++ b/lib/pengine/pe_output.c
@@ -1214,8 +1214,9 @@ pe__node_xml(pcmk__output_t *out, va_list args) {
 
         out->end_list(out);
     } else {
-        xmlNodePtr parent = pcmk__output_xml_create_parent(out, "node");
-        xmlSetProp(parent, (pcmkXmlStr) "name", (pcmkXmlStr) node->details->uname);
+        pcmk__output_xml_create_parent(out, "node",
+                                       "name", node->details->uname,
+                                       NULL);
     }
 
     return pcmk_rc_ok;
@@ -1728,8 +1729,9 @@ pe__resource_history_xml(pcmk__output_t *out, va_list args) {
     time_t last_failure = va_arg(args, int);
     gboolean as_header = va_arg(args, gboolean);
 
-    xmlNodePtr node = pcmk__output_xml_create_parent(out, "resource_history");
-    xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) rsc_id);
+    xmlNodePtr node = pcmk__output_xml_create_parent(out, "resource_history",
+                                                     "id", rsc_id,
+                                                     NULL);
 
     if (rsc == NULL) {
         xmlSetProp(node, (pcmkXmlStr) "orphan", (pcmkXmlStr) "true");
diff --git a/tools/crm_resource_print.c b/tools/crm_resource_print.c
index ca8bee2..a33356f 100644
--- a/tools/crm_resource_print.c
+++ b/tools/crm_resource_print.c
@@ -324,9 +324,9 @@ resource_search_xml(pcmk__output_t *out, va_list args)
     pe_resource_t *rsc = va_arg(args, pe_resource_t *);
     gchar *requested_name = va_arg(args, gchar *);
 
-    xmlNode *xml_node = pcmk__output_xml_create_parent(out, "nodes");
-
-    xmlSetProp(xml_node, (pcmkXmlStr) "resource", (pcmkXmlStr) requested_name);
+    pcmk__output_xml_create_parent(out, "nodes",
+                                   "resource", requested_name,
+                                   NULL);
 
     for (GListPtr lpc = nodes; lpc != NULL; lpc = lpc->next) {
         pe_node_t *node = (pe_node_t *) lpc->data;
@@ -435,24 +435,23 @@ resource_why_xml(pcmk__output_t *out, va_list args)
 
     const char *host_uname = (node == NULL)? NULL : node->details->uname;
 
-    xmlNode *xml_node = pcmk__output_xml_create_parent(out, "reason");
+    xmlNode *xml_node = pcmk__output_xml_create_parent(out, "reason", NULL);
 
     if ((rsc == NULL) && (host_uname == NULL)) {
         GListPtr lpc = NULL;
         GListPtr hosts = NULL;
 
-        pcmk__output_xml_create_parent(out, "resources");
+        pcmk__output_xml_create_parent(out, "resources", NULL);
 
         for (lpc = resources; lpc != NULL; lpc = lpc->next) {
             pe_resource_t *rsc = (pe_resource_t *) lpc->data;
-            xmlNode *rsc_node = NULL;
 
             rsc->fns->location(rsc, &hosts, TRUE);
 
-            rsc_node = pcmk__output_xml_create_parent(out, "resource");
-            xmlSetProp(rsc_node, (pcmkXmlStr) "id", (pcmkXmlStr) rsc->id);
-            xmlSetProp(rsc_node, (pcmkXmlStr) "running",
-                       (pcmkXmlStr) pcmk__btoa(hosts != NULL));
+            pcmk__output_xml_create_parent(out, "resource",
+                                           "id", rsc->id,
+                                           "running", pcmk__btoa(hosts != NULL),
+                                           NULL);
 
             cli_resource_check(out, cib_conn, rsc);
             pcmk__output_xml_pop_parent(out);
@@ -476,16 +475,16 @@ resource_why_xml(pcmk__output_t *out, va_list args)
         GListPtr unactiveResources = pcmk__subtract_lists(allResources, activeResources, (GCompareFunc) strcmp);
         GListPtr lpc = NULL;
 
-        pcmk__output_xml_create_parent(out, "resources");
+        pcmk__output_xml_create_parent(out, "resources", NULL);
 
         for (lpc = activeResources; lpc != NULL; lpc = lpc->next) {
             pe_resource_t *rsc = (pe_resource_t *) lpc->data;
-            xmlNode *rsc_node = NULL;
 
-            rsc_node = pcmk__output_xml_create_parent(out, "resource");
-            xmlSetProp(rsc_node, (pcmkXmlStr) "id", (pcmkXmlStr) rsc->id);
-            xmlSetProp(rsc_node, (pcmkXmlStr) "running", (pcmkXmlStr) "true");
-            xmlSetProp(rsc_node, (pcmkXmlStr) "host", (pcmkXmlStr) host_uname);
+            pcmk__output_xml_create_parent(out, "resource",
+                                           "id", rsc->id,
+                                           "running", "true",
+                                           "host", host_uname,
+                                           NULL);
 
             cli_resource_check(out, cib_conn, rsc);
             pcmk__output_xml_pop_parent(out);
@@ -493,12 +492,12 @@ resource_why_xml(pcmk__output_t *out, va_list args)
 
         for(lpc = unactiveResources; lpc != NULL; lpc = lpc->next) {
             pe_resource_t *rsc = (pe_resource_t *) lpc->data;
-            xmlNode *rsc_node = NULL;
 
-            rsc_node = pcmk__output_xml_create_parent(out, "resource");
-            xmlSetProp(rsc_node, (pcmkXmlStr) "id", (pcmkXmlStr) rsc->id);
-            xmlSetProp(rsc_node, (pcmkXmlStr) "running", (pcmkXmlStr) "false");
-            xmlSetProp(rsc_node, (pcmkXmlStr) "host", (pcmkXmlStr) host_uname);
+            pcmk__output_xml_create_parent(out, "resource",
+                                           "id", rsc->id,
+                                           "running", "false",
+                                           "host", host_uname,
+                                           NULL);
 
             cli_resource_check(out, cib_conn, rsc);
             pcmk__output_xml_pop_parent(out);
-- 
1.8.3.1


From 29cd349a15dff8975499e650d070934aa4c68e3f Mon Sep 17 00:00:00 2001
From: Chris Lumens <clumens@redhat.com>
Date: Wed, 18 Nov 2020 14:21:11 -0500
Subject: [PATCH 5/6] Refactor: libs: Remove most uses of xmlSetProp.

We can use crm_xml_add to do this instead, and that function will take
ACLs in account too (though, none of these call sites actually care
about ACLs).  I've left calls in most of the various XML manipulating
functions because those seem more intentional.
---
 lib/common/output_html.c   | 14 +++++++-------
 lib/common/output_xml.c    | 14 +++++++-------
 lib/common/xml.c           |  4 ++--
 lib/fencing/st_output.c    | 10 +++++-----
 lib/lrmd/lrmd_output.c     |  4 ++--
 lib/pengine/pe_output.c    | 38 ++++++++++++++++----------------------
 tools/crm_resource_print.c | 15 +++++++--------
 7 files changed, 46 insertions(+), 53 deletions(-)

diff --git a/lib/common/output_html.c b/lib/common/output_html.c
index cf51af4..542d863 100644
--- a/lib/common/output_html.c
+++ b/lib/common/output_html.c
@@ -98,7 +98,7 @@ html_init(pcmk__output_t *out) {
     priv->root = create_xml_node(NULL, "html");
     xmlCreateIntSubset(priv->root->doc, (pcmkXmlStr) "html", NULL, NULL);
 
-    xmlSetProp(priv->root, (pcmkXmlStr) "lang", (pcmkXmlStr) "en");
+    crm_xml_add(priv->root, "lang", "en");
     g_queue_push_tail(priv->parent_q, priv->root);
     priv->errors = NULL;
 
@@ -137,7 +137,7 @@ finish_reset_common(pcmk__output_t *out, crm_exit_t exit_status, bool print) {
     }
 
     charset_node = create_xml_node(head_node, "meta");
-    xmlSetProp(charset_node, (pcmkXmlStr) "charset", (pcmkXmlStr) "utf-8");
+    crm_xml_add(charset_node, "charset", "utf-8");
 
     /* Add any extra header nodes the caller might have created. */
     for (int i = 0; i < g_slist_length(extra_headers); i++) {
@@ -275,7 +275,7 @@ html_output_xml(pcmk__output_t *out, const char *name, const char *buf) {
     CRM_ASSERT(priv != NULL);
 
     node = pcmk__output_create_html_node(out, "pre", NULL, NULL, buf);
-    xmlSetProp(node, (pcmkXmlStr) "lang", (pcmkXmlStr) "xml");
+    crm_xml_add(node, "lang", "xml");
 }
 
 G_GNUC_PRINTF(4, 5)
@@ -340,7 +340,7 @@ html_list_item(pcmk__output_t *out, const char *name, const char *format, ...) {
     free(buf);
 
     if (name != NULL) {
-        xmlSetProp(item_node, (pcmkXmlStr) "class", (pcmkXmlStr) name);
+        crm_xml_add(item_node, "class", name);
     }
 }
 
@@ -417,11 +417,11 @@ pcmk__output_create_html_node(pcmk__output_t *out, const char *element_name, con
     htmlNodePtr node = pcmk__output_create_xml_text_node(out, element_name, text);
 
     if (class_name != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "class", (pcmkXmlStr) class_name);
+        crm_xml_add(node, "class", class_name);
     }
 
     if (id != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) id);
+        crm_xml_add(node, "id", id);
     }
 
     return node;
@@ -444,7 +444,7 @@ pcmk__html_add_header(const char *name, ...) {
         }
 
         value = va_arg(ap, char *);
-        xmlSetProp(header_node, (pcmkXmlStr) key, (pcmkXmlStr) value);
+        crm_xml_add(header_node, key, value);
     }
 
     extra_headers = g_slist_append(extra_headers, header_node);
diff --git a/lib/common/output_xml.c b/lib/common/output_xml.c
index 6d92625..0053979 100644
--- a/lib/common/output_xml.c
+++ b/lib/common/output_xml.c
@@ -107,13 +107,13 @@ xml_init(pcmk__output_t *out) {
 
     if (legacy_xml) {
         priv->root = create_xml_node(NULL, "crm_mon");
-        xmlSetProp(priv->root, (pcmkXmlStr) "version", (pcmkXmlStr) VERSION);
+        crm_xml_add(priv->root, "version", VERSION);
     } else {
         priv->root = create_xml_node(NULL, "pacemaker-result");
-        xmlSetProp(priv->root, (pcmkXmlStr) "api-version", (pcmkXmlStr) PCMK__API_VERSION);
+        crm_xml_add(priv->root, "api-version", PCMK__API_VERSION);
 
         if (out->request != NULL) {
-            xmlSetProp(priv->root, (pcmkXmlStr) "request", (pcmkXmlStr) out->request);
+            crm_xml_add(priv->root, "request", out->request);
         }
     }
 
@@ -223,12 +223,12 @@ xml_subprocess_output(pcmk__output_t *out, int exit_status,
 
     if (proc_stdout != NULL) {
         child_node = pcmk_create_xml_text_node(node, "output", proc_stdout);
-        xmlSetProp(child_node, (pcmkXmlStr) "source", (pcmkXmlStr) "stdout");
+        crm_xml_add(child_node, "source", "stdout");
     }
 
     if (proc_stderr != NULL) {
         child_node = pcmk_create_xml_text_node(node, "output", proc_stderr);
-        xmlSetProp(child_node, (pcmkXmlStr) "source", (pcmkXmlStr) "stderr");
+        crm_xml_add(child_node, "source", "stderr");
     }
 
     pcmk__output_xml_add_node(out, node);
@@ -343,7 +343,7 @@ xml_list_item(pcmk__output_t *out, const char *name, const char *format, ...) {
     item_node = pcmk__output_create_xml_text_node(out, "item", buf);
 
     if (name != NULL) {
-        xmlSetProp(item_node, (pcmkXmlStr) "name", (pcmkXmlStr) name);
+        crm_xml_add(item_node, "name", name);
     }
 
     free(buf);
@@ -368,7 +368,7 @@ xml_end_list(pcmk__output_t *out) {
 
         node = g_queue_pop_tail(priv->parent_q);
         buf = crm_strdup_printf("%lu", xmlChildElementCount(node));
-        xmlSetProp(node, (pcmkXmlStr) "count", (pcmkXmlStr) buf);
+        crm_xml_add(node, "count", buf);
         free(buf);
     }
 }
diff --git a/lib/common/xml.c b/lib/common/xml.c
index e5de0d4..abb120c 100644
--- a/lib/common/xml.c
+++ b/lib/common/xml.c
@@ -703,11 +703,11 @@ pcmk_create_html_node(xmlNode * parent, const char *element_name, const char *id
     xmlNode *node = pcmk_create_xml_text_node(parent, element_name, text);
 
     if (class_name != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "class", (pcmkXmlStr) class_name);
+        crm_xml_add(node, "class", class_name);
     }
 
     if (id != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "id", (pcmkXmlStr) id);
+        crm_xml_add(node, "id", id);
     }
 
     return node;
diff --git a/lib/fencing/st_output.c b/lib/fencing/st_output.c
index 65f8ec9..04f4b83 100644
--- a/lib/fencing/st_output.c
+++ b/lib/fencing/st_output.c
@@ -331,11 +331,11 @@ stonith__event_xml(pcmk__output_t *out, va_list args) {
 
     switch (event->state) {
         case st_failed:
-            xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) "failed");
+            crm_xml_add(node, "status", "failed");
             break;
 
         case st_done:
-            xmlSetProp(node, (pcmkXmlStr) "status", (pcmkXmlStr) "success");
+            crm_xml_add(node, "status", "success");
             break;
 
         default: {
@@ -349,12 +349,12 @@ stonith__event_xml(pcmk__output_t *out, va_list args) {
     }
 
     if (event->delegate != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "delegate", (pcmkXmlStr) event->delegate);
+        crm_xml_add(node, "delegate", event->delegate);
     }
 
     if (event->state == st_failed || event->state == st_done) {
         buf = time_t_string(event->completed);
-        xmlSetProp(node, (pcmkXmlStr) "completed", (pcmkXmlStr) buf);
+        crm_xml_add(node, "completed", buf);
         free(buf);
     }
 
@@ -429,7 +429,7 @@ stonith__validate_agent_xml(pcmk__output_t *out, va_list args) {
                                                    NULL);
 
     if (device != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "device", (pcmkXmlStr) device);
+        crm_xml_add(node, "device", device);
     }
 
     pcmk__output_xml_push_parent(out, node);
diff --git a/lib/lrmd/lrmd_output.c b/lib/lrmd/lrmd_output.c
index c01cc5e..dfcf3fa 100644
--- a/lib/lrmd/lrmd_output.c
+++ b/lib/lrmd/lrmd_output.c
@@ -73,7 +73,7 @@ lrmd__agents_list_xml(pcmk__output_t *out, va_list args) {
                                                      NULL);
 
     if (!pcmk__str_empty(provider)) {
-        xmlSetProp(node, (pcmkXmlStr) "provider", (pcmkXmlStr) provider);
+        crm_xml_add(node, "provider", provider);
     }
 
     return xml_list(out, list, "agent");
@@ -105,7 +105,7 @@ lrmd__providers_list_xml(pcmk__output_t *out, va_list args) {
                                                      NULL);
 
     if (agent_spec != NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "agent", (pcmkXmlStr) agent_spec);
+        crm_xml_add(node, "agent", agent_spec);
     }
 
     return xml_list(out, list, "provider");
diff --git a/lib/pengine/pe_output.c b/lib/pengine/pe_output.c
index 470b025..ecb5c2c 100644
--- a/lib/pengine/pe_output.c
+++ b/lib/pengine/pe_output.c
@@ -415,7 +415,7 @@ pe__name_and_nvpairs_xml(pcmk__output_t *out, bool is_list, const char *tag_name
         const char *param_name = va_arg(args, const char *);
         const char *param_value = va_arg(args, const char *);
         if (param_name && param_value) {
-            xmlSetProp(xml_node, (pcmkXmlStr)param_name, (pcmkXmlStr)param_value);
+            crm_xml_add(xml_node, param_name, param_value);
         }
     };
     va_end(args);
@@ -592,19 +592,19 @@ pe__cluster_counts_xml(pcmk__output_t *out, va_list args) {
     int nblocked = va_arg(args, int);
 
     char *s = crm_itoa(nnodes);
-    xmlSetProp(nodes_node, (pcmkXmlStr) "number", (pcmkXmlStr) s);
+    crm_xml_add(nodes_node, "number", s);
     free(s);
 
     s = crm_itoa(nresources);
-    xmlSetProp(resources_node, (pcmkXmlStr) "number", (pcmkXmlStr) s);
+    crm_xml_add(resources_node, "number", s);
     free(s);
 
     s = crm_itoa(ndisabled);
-    xmlSetProp(resources_node, (pcmkXmlStr) "disabled", (pcmkXmlStr) s);
+    crm_xml_add(resources_node, "disabled", s);
     free(s);
 
     s = crm_itoa(nblocked);
-    xmlSetProp(resources_node, (pcmkXmlStr) "blocked", (pcmkXmlStr) s);
+    crm_xml_add(resources_node, "blocked", s);
     free(s);
 
     return pcmk_rc_ok;
@@ -1196,8 +1196,7 @@ pe__node_xml(pcmk__output_t *out, va_list args) {
 
         if (pe__is_guest_node(node)) {
             xmlNodePtr xml_node = pcmk__output_xml_peek_parent(out);
-            xmlSetProp(xml_node, (pcmkXmlStr) "id_as_resource",
-                                 (pcmkXmlStr) node->details->remote_rsc->container->id);
+            crm_xml_add(xml_node, "id_as_resource", node->details->remote_rsc->container->id);
         }
 
         if (group_by_node) {
@@ -1395,7 +1394,7 @@ pe__node_attribute_xml(pcmk__output_t *out, va_list args) {
 
     if (add_extra) {
         char *buf = crm_itoa(expected_score);
-        xmlSetProp(node, (pcmkXmlStr) "expected", (pcmkXmlStr) buf);
+        crm_xml_add(node, "expected", buf);
         free(buf);
     }
 
@@ -1635,7 +1634,7 @@ pe__op_history_xml(pcmk__output_t *out, va_list args) {
 
     if (interval_ms_s && !pcmk__str_eq(interval_ms_s, "0", pcmk__str_casei)) {
         char *s = crm_strdup_printf("%sms", interval_ms_s);
-        xmlSetProp(node, (pcmkXmlStr) "interval", (pcmkXmlStr) s);
+        crm_xml_add(node, "interval", s);
         free(s);
     }
 
@@ -1646,8 +1645,7 @@ pe__op_history_xml(pcmk__output_t *out, va_list args) {
         if (value) {
             time_t int_value = (time_t) crm_parse_int(value, NULL);
             if (int_value > 0) {
-                xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_LAST_CHANGE,
-                           (pcmkXmlStr) pcmk__epoch2str(&int_value));
+                crm_xml_add(node, XML_RSC_OP_LAST_CHANGE, pcmk__epoch2str(&int_value));
             }
         }
 
@@ -1655,21 +1653,20 @@ pe__op_history_xml(pcmk__output_t *out, va_list args) {
         if (value) {
             time_t int_value = (time_t) crm_parse_int(value, NULL);
             if (int_value > 0) {
-                xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_LAST_RUN,
-                           (pcmkXmlStr) pcmk__epoch2str(&int_value));
+                crm_xml_add(node, XML_RSC_OP_LAST_RUN, pcmk__epoch2str(&int_value));
             }
         }
 
         value = crm_element_value(xml_op, XML_RSC_OP_T_EXEC);
         if (value) {
             char *s = crm_strdup_printf("%sms", value);
-            xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_T_EXEC, (pcmkXmlStr) s);
+            crm_xml_add(node, XML_RSC_OP_T_EXEC, s);
             free(s);
         }
         value = crm_element_value(xml_op, XML_RSC_OP_T_QUEUE);
         if (value) {
             char *s = crm_strdup_printf("%sms", value);
-            xmlSetProp(node, (pcmkXmlStr) XML_RSC_OP_T_QUEUE, (pcmkXmlStr) s);
+            crm_xml_add(node, XML_RSC_OP_T_QUEUE, s);
             free(s);
         }
     }
@@ -1734,7 +1731,7 @@ pe__resource_history_xml(pcmk__output_t *out, va_list args) {
                                                      NULL);
 
     if (rsc == NULL) {
-        xmlSetProp(node, (pcmkXmlStr) "orphan", (pcmkXmlStr) "true");
+        crm_xml_add(node, "orphan", "true");
     } else if (all || failcount || last_failure > 0) {
         char *migration_s = crm_itoa(rsc->migration_threshold);
 
@@ -1746,14 +1743,12 @@ pe__resource_history_xml(pcmk__output_t *out, va_list args) {
         if (failcount > 0) {
             char *s = crm_itoa(failcount);
 
-            xmlSetProp(node, (pcmkXmlStr) PCMK__FAIL_COUNT_PREFIX,
-                       (pcmkXmlStr) s);
+            crm_xml_add(node, PCMK__FAIL_COUNT_PREFIX, s);
             free(s);
         }
 
         if (last_failure > 0) {
-            xmlSetProp(node, (pcmkXmlStr) PCMK__LAST_FAILURE_PREFIX,
-                       (pcmkXmlStr) pcmk__epoch2str(&last_failure));
+            crm_xml_add(node, PCMK__LAST_FAILURE_PREFIX, pcmk__epoch2str(&last_failure));
         }
     }
 
@@ -1920,8 +1915,7 @@ pe__ticket_xml(pcmk__output_t *out, va_list args) {
                                         NULL);
 
     if (ticket->last_granted > -1) {
-        xmlSetProp(node, (pcmkXmlStr) "last-granted",
-                   (pcmkXmlStr) pcmk__epoch2str(&ticket->last_granted));
+        crm_xml_add(node, "last-granted", pcmk__epoch2str(&ticket->last_granted));
     }
 
     return pcmk_rc_ok;
diff --git a/tools/crm_resource_print.c b/tools/crm_resource_print.c
index a33356f..cb06879 100644
--- a/tools/crm_resource_print.c
+++ b/tools/crm_resource_print.c
@@ -252,19 +252,19 @@ resource_check_xml(pcmk__output_t *out, va_list args) {
                                                  NULL);
 
     if (pcmk_is_set(checks->flags, rsc_remain_stopped)) {
-        xmlSetProp(node, (pcmkXmlStr) "remain_stopped", (pcmkXmlStr) "true");
+        crm_xml_add(node, "remain_stopped", "true");
     }
 
     if (pcmk_is_set(checks->flags, rsc_unpromotable)) {
-        xmlSetProp(node, (pcmkXmlStr) "promotable", (pcmkXmlStr) "false");
+        crm_xml_add(node, "promotable", "false");
     }
 
     if (pcmk_is_set(checks->flags, rsc_unmanaged)) {
-        xmlSetProp(node, (pcmkXmlStr) "unmanaged", (pcmkXmlStr) "true");
+        crm_xml_add(node, "unmanaged", "true");
     }
 
     if (checks->lock_node) {
-        xmlSetProp(node, (pcmkXmlStr) "locked-to", (pcmkXmlStr) checks->lock_node);
+        crm_xml_add(node, "locked-to", checks->lock_node);
     }
 
     return rc;
@@ -333,7 +333,7 @@ resource_search_xml(pcmk__output_t *out, va_list args)
         xmlNode *sub_node = pcmk__output_create_xml_text_node(out, "node", node->details->uname);
 
         if (!pe_rsc_is_clone(rsc) && rsc->fns->state(rsc, TRUE) == RSC_ROLE_MASTER) {
-            xmlSetProp(sub_node, (pcmkXmlStr) "state", (pcmkXmlStr) "promoted");
+            crm_xml_add(sub_node, "state", "promoted");
         }
     }
 
@@ -463,7 +463,7 @@ resource_why_xml(pcmk__output_t *out, va_list args)
 
     } else if ((rsc != NULL) && (host_uname != NULL)) {
         if (resource_is_running_on(rsc, host_uname)) {
-            xmlSetProp(xml_node, (pcmkXmlStr) "running_on", (pcmkXmlStr) host_uname);
+            crm_xml_add(xml_node, "running_on", host_uname);
         }
 
         cli_resource_check(out, cib_conn, rsc);
@@ -512,8 +512,7 @@ resource_why_xml(pcmk__output_t *out, va_list args)
         GListPtr hosts = NULL;
 
         rsc->fns->location(rsc, &hosts, TRUE);
-        xmlSetProp(xml_node, (pcmkXmlStr) "running",
-                   (pcmkXmlStr) pcmk__btoa(hosts != NULL));
+        crm_xml_add(xml_node, "running", pcmk__btoa(hosts != NULL));
         cli_resource_check(out, cib_conn, rsc);
         g_list_free(hosts);
     }
-- 
1.8.3.1


From 55b4f7a17001280fcf1b8dc7bc4c1afd3a6a46d1 Mon Sep 17 00:00:00 2001
From: Chris Lumens <clumens@redhat.com>
Date: Wed, 18 Nov 2020 14:31:31 -0500
Subject: [PATCH 6/6] Test: cts: Update order of attributes in crm_mon output.

This has changed due to some of the code reorganization as a result of
trying to set as many attributes as possible when an xmlNode is created.
The resulting crm_mon output should still validate, however, since
attribute order should not be enforced by the schema.
---
 cts/cli/regression.crm_mon.exp | 254 ++++++++++++++++++++---------------------
 1 file changed, 127 insertions(+), 127 deletions(-)

diff --git a/cts/cli/regression.crm_mon.exp b/cts/cli/regression.crm_mon.exp
index edcdda6..e9f36ad 100644
--- a/cts/cli/regression.crm_mon.exp
+++ b/cts/cli/regression.crm_mon.exp
@@ -125,39 +125,39 @@ Active Resources:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="18" task="start" exec-time="6020ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="6015ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="18" task="start" rc="0" rc_text="ok" exec-time="6020ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="6015ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Public-IP" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Email" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="24ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="24ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="16" task="stop" exec-time="6048ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="16" task="stop" rc="0" rc_text="ok" exec-time="6048ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -285,39 +285,39 @@ Active Resources:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="18" task="start" exec-time="6020ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="6015ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="18" task="start" rc="0" rc_text="ok" exec-time="6020ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="6015ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Public-IP" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Email" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="24ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="24ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="16" task="stop" exec-time="6048ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="16" task="stop" rc="0" rc_text="ok" exec-time="6048ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -766,39 +766,39 @@ Negative Location Constraints:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="18" task="start" exec-time="6020ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="6015ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="18" task="start" rc="0" rc_text="ok" exec-time="6020ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="6015ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Public-IP" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Email" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="24ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="24ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="16" task="stop" exec-time="6048ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="16" task="stop" rc="0" rc_text="ok" exec-time="6048ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -928,19 +928,19 @@ Negative Location Constraints:
   <node_history>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="24ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="24ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="16" task="stop" exec-time="6048ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="16" task="stop" rc="0" rc_text="ok" exec-time="6048ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1081,22 +1081,22 @@ Negative Location Constraints:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy" orphan="false" migration-threshold="1000000">
-        <operation_history call="18" task="start" exec-time="6020ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="6015ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="18" task="start" rc="0" rc_text="ok" exec-time="6020ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="6015ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Public-IP" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Email" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1171,8 +1171,8 @@ Operations:
   <node_history>
     <node name="cluster01">
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="24ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="24ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1371,8 +1371,8 @@ Operations:
   <node_history>
     <node name="cluster01">
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="19" task="monitor" interval="60000ms" exec-time="24ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="19" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="24ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1452,10 +1452,10 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="Public-IP" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="Email" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1529,7 +1529,7 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="Email" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1611,14 +1611,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1700,14 +1700,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -1786,14 +1786,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="11" task="start" exec-time="2044ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="12" task="monitor" interval="10000ms" exec-time="2031ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="11" task="start" rc="0" rc_text="ok" exec-time="2044ms" queue-time="0ms"/>
+        <operation_history call="12" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2031ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="17" task="start" exec-time="2038ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="18" task="monitor" interval="10000ms" exec-time="2034ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="17" task="start" rc="0" rc_text="ok" exec-time="2038ms" queue-time="0ms"/>
+        <operation_history call="18" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="2034ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -2257,14 +2257,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -2368,14 +2368,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -2457,14 +2457,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -2568,14 +2568,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -2657,14 +2657,14 @@ Operations:
   <node_history>
     <node name="cluster02">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="mysql-proxy" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -2770,46 +2770,46 @@ Active Resources:
   <node_history>
     <node name="cluster02">
       <resource_history id="httpd-bundle-ip-192.168.122.131" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-docker-0" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-0" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="30000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="30000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="dummy-1" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="cluster01">
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="20" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="20" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-ip-192.168.122.132" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-docker-1" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-1" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="30000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="30000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
     <node name="httpd-bundle-0">
       <resource_history id="httpd" orphan="false" migration-threshold="1000000">
-        <operation_history call="1" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="1" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
@@ -3051,24 +3051,24 @@ Full List of Resources:
   <node_history>
     <node name="cluster01">
       <resource_history id="Fencing" orphan="false" migration-threshold="1000000">
-        <operation_history call="15" task="start" exec-time="36ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="20" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="15" task="start" rc="0" rc_text="ok" exec-time="36ms" queue-time="0ms"/>
+        <operation_history call="20" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="ping" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="10000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="10000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-ip-192.168.122.132" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-docker-1" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="60000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="60000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
       <resource_history id="httpd-bundle-1" orphan="false" migration-threshold="1000000">
-        <operation_history call="2" task="start" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
-        <operation_history call="3" task="monitor" interval="30000ms" exec-time="0ms" queue-time="0ms" rc="0" rc_text="ok"/>
+        <operation_history call="2" task="start" rc="0" rc_text="ok" exec-time="0ms" queue-time="0ms"/>
+        <operation_history call="3" task="monitor" rc="0" rc_text="ok" interval="30000ms" exec-time="0ms" queue-time="0ms"/>
       </resource_history>
     </node>
   </node_history>
-- 
1.8.3.1