pacemaker 2.1.8-2.1.8
Scalable High-Availability cluster resource manager
Loading...
Searching...
No Matches
crm_xml_init_test.c
Go to the documentation of this file.
1/*
2 * Copyright 2023-2024 the Pacemaker project contributors
3 *
4 * The version control history for this file may have further details.
5 *
6 * This source code is licensed under the GNU General Public License version 2
7 * or later (GPLv2+) WITHOUT ANY WARRANTY.
8 */
9
10#include <crm_internal.h>
11
12#include <crm/common/xml.h>
15
16#include "crmcommon_private.h"
17
18/* Copied from lib/common/xml.c */
19#define XML_DOC_PRIVATE_MAGIC 0x81726354UL
20#define XML_NODE_PRIVATE_MAGIC 0x54637281UL
21
22static int
23setup(void **state) {
25 return 0;
26}
27
28static int
29teardown(void **state) {
31 return 0;
32}
33
34static void
35buffer_scheme_test(void **state) {
36 assert_int_equal(XML_BUFFER_ALLOC_DOUBLEIT, xmlGetBufferAllocationScheme());
37}
38
39/* These functions also serve as unit tests of the static new_private_data
40 * function. We can't test free_private_data because libxml will call that as
41 * part of freeing everything else. By the time we'd get back into a unit test
42 * where we could check that private members are NULL, the structure containing
43 * the private data would have been freed.
44 *
45 * This could probably be tested with a lot of function mocking, but that
46 * doesn't seem worth it.
47 */
48
49static void
50create_document_node(void **state) {
51 xml_doc_private_t *docpriv = NULL;
52 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
53
54 /* Double check things */
55 assert_non_null(doc);
56 assert_int_equal(doc->type, XML_DOCUMENT_NODE);
57
58 /* Check that the private data is initialized correctly */
59 docpriv = doc->_private;
60 assert_non_null(docpriv);
61 assert_int_equal(docpriv->check, XML_DOC_PRIVATE_MAGIC);
62 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty|pcmk__xf_created));
63
64 /* Clean up */
65 xmlFreeDoc(doc);
66}
67
68static void
69create_element_node(void **state) {
70 xml_doc_private_t *docpriv = NULL;
71 xml_node_private_t *priv = NULL;
72 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
73 xmlNodePtr node = xmlNewDocNode(doc, NULL, (pcmkXmlStr) "test", NULL);
74
75 /* Adding a node to the document marks it as dirty */
76 docpriv = doc->_private;
77 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty));
78
79 /* Double check things */
80 assert_non_null(node);
81 assert_int_equal(node->type, XML_ELEMENT_NODE);
82
83 /* Check that the private data is initialized correctly */
84 priv = node->_private;
85 assert_non_null(priv);
86 assert_int_equal(priv->check, XML_NODE_PRIVATE_MAGIC);
87 assert_true(pcmk_all_flags_set(priv->flags, pcmk__xf_dirty|pcmk__xf_created));
88
89 /* Clean up */
90 xmlFreeNode(node);
91 xmlFreeDoc(doc);
92}
93
94static void
95create_attr_node(void **state) {
96 xml_doc_private_t *docpriv = NULL;
97 xml_node_private_t *priv = NULL;
98 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
99 xmlNodePtr node = xmlNewDocNode(doc, NULL, (pcmkXmlStr) "test", NULL);
100 xmlAttrPtr attr = xmlNewProp(node, (pcmkXmlStr) PCMK_XA_NAME,
101 (pcmkXmlStr) "dummy-value");
102
103 /* Adding a node to the document marks it as dirty */
104 docpriv = doc->_private;
105 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty));
106
107 /* Double check things */
108 assert_non_null(attr);
109 assert_int_equal(attr->type, XML_ATTRIBUTE_NODE);
110
111 /* Check that the private data is initialized correctly */
112 priv = attr->_private;
113 assert_non_null(priv);
114 assert_int_equal(priv->check, XML_NODE_PRIVATE_MAGIC);
115 assert_true(pcmk_all_flags_set(priv->flags, pcmk__xf_dirty|pcmk__xf_created));
116
117 /* Clean up */
118 xmlFreeNode(node);
119 xmlFreeDoc(doc);
120}
121
122static void
123create_comment_node(void **state) {
124 xml_doc_private_t *docpriv = NULL;
125 xml_node_private_t *priv = NULL;
126 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
127 xmlNodePtr node = xmlNewDocComment(doc, (pcmkXmlStr) "blahblah");
128
129 /* Adding a node to the document marks it as dirty */
130 docpriv = doc->_private;
131 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty));
132
133 /* Double check things */
134 assert_non_null(node);
135 assert_int_equal(node->type, XML_COMMENT_NODE);
136
137 /* Check that the private data is initialized correctly */
138 priv = node->_private;
139 assert_non_null(priv);
140 assert_int_equal(priv->check, XML_NODE_PRIVATE_MAGIC);
141 assert_true(pcmk_all_flags_set(priv->flags, pcmk__xf_dirty|pcmk__xf_created));
142
143 /* Clean up */
144 xmlFreeNode(node);
145 xmlFreeDoc(doc);
146}
147
148static void
149create_text_node(void **state) {
150 xml_doc_private_t *docpriv = NULL;
151 xml_node_private_t *priv = NULL;
152 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
153 xmlNodePtr node = xmlNewDocText(doc, (pcmkXmlStr) "blahblah");
154
155 /* Adding a node to the document marks it as dirty */
156 docpriv = doc->_private;
157 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty));
158
159 /* Double check things */
160 assert_non_null(node);
161 assert_int_equal(node->type, XML_TEXT_NODE);
162
163 /* Check that no private data was created */
164 priv = node->_private;
165 assert_null(priv);
166
167 /* Clean up */
168 xmlFreeNode(node);
169 xmlFreeDoc(doc);
170}
171
172static void
173create_dtd_node(void **state) {
174 xml_doc_private_t *docpriv = NULL;
175 xml_node_private_t *priv = NULL;
176 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
177 xmlDtdPtr dtd = xmlNewDtd(doc, (pcmkXmlStr) PCMK_XA_NAME,
178 (pcmkXmlStr) "externalId",
179 (pcmkXmlStr) "systemId");
180
181 /* Adding a node to the document marks it as dirty */
182 docpriv = doc->_private;
183 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty));
184
185 /* Double check things */
186 assert_non_null(dtd);
187 assert_int_equal(dtd->type, XML_DTD_NODE);
188
189 /* Check that no private data was created */
190 priv = dtd->_private;
191 assert_null(priv);
192
193 /* Clean up */
194 /* If you call xmlFreeDtd before xmlFreeDoc, you get a segfault */
195 xmlFreeDoc(doc);
196}
197
198static void
199create_cdata_node(void **state) {
200 xml_doc_private_t *docpriv = NULL;
201 xml_node_private_t *priv = NULL;
202 xmlDocPtr doc = xmlNewDoc(PCMK__XML_VERSION);
203 xmlNodePtr node = xmlNewCDataBlock(doc, (pcmkXmlStr) "blahblah", 8);
204
205 /* Adding a node to the document marks it as dirty */
206 docpriv = doc->_private;
207 assert_true(pcmk_all_flags_set(docpriv->flags, pcmk__xf_dirty));
208
209 /* Double check things */
210 assert_non_null(node);
211 assert_int_equal(node->type, XML_CDATA_SECTION_NODE);
212
213 /* Check that no private data was created */
214 priv = node->_private;
215 assert_null(priv);
216
217 /* Clean up */
218 xmlFreeNode(node);
219 xmlFreeDoc(doc);
220}
221
222PCMK__UNIT_TEST(setup, teardown,
223 cmocka_unit_test(buffer_scheme_test),
224 cmocka_unit_test(create_document_node),
225 cmocka_unit_test(create_element_node),
226 cmocka_unit_test(create_attr_node),
227 cmocka_unit_test(create_comment_node),
228 cmocka_unit_test(create_text_node),
229 cmocka_unit_test(create_dtd_node),
230 cmocka_unit_test(create_cdata_node));
#define XML_NODE_PRIVATE_MAGIC
#define XML_DOC_PRIVATE_MAGIC
#define PCMK__XML_VERSION
libxml2 supports only XML version 1.0, at least as of libxml2-2.12.5
#define PCMK__UNIT_TEST(group_setup, group_teardown,...)
Wrappers for and extensions to libxml2.
const xmlChar * pcmkXmlStr
Definition xml.h:41
void crm_xml_init(void)
Initialize the CRM XML subsystem.
Definition xml.c:2121
void crm_xml_cleanup(void)
Definition xml.c:2143
@ pcmk__xf_created
@ pcmk__xf_dirty
#define PCMK_XA_NAME
Definition xml_names.h:325