This source file includes following definitions.
- setup
- teardown
- assert_attr_expression
- null_invalid
- id_missing
- attr_missing
- attr_with_submatch_passes
- attr_with_submatch_fails
- source_missing
- source_invalid
- source_literal_passes
- source_literal_value_fails
- source_literal_attr_fails
- source_params_missing
- source_params_passes
- source_params_fails
- source_meta_missing
- source_meta_passes
- source_meta_fails
- type_default_number
- type_default_int
- type_invalid
- type_string_passes
- type_string_fails
- type_integer_passes
- type_integer_fails
- type_integer_truncation
- type_number_passes
- type_number_fails
- type_version_passes
- type_version_equality
- type_version_fails
- op_missing
- op_invalid
- op_lt_passes
- op_lt_fails
- op_gt_passes
- op_gt_fails
- op_lte_lt_passes
- op_lte_eq_passes
- op_lte_fails
- op_gte_gt_passes
- op_gte_eq_passes
- op_gte_fails
- op_eq_passes
- op_eq_empty_vs_empty_passes
- op_eq_fails
- op_eq_undefined_vs_empty_fails
- op_ne_passes
- op_ne_fails
- op_defined_passes
- op_defined_empty_passes
- op_defined_fails
- op_defined_with_value
- op_undefined_passes
- op_undefined_fails
- op_undefined_empty_fails
- value_missing_defined_ok
- value_missing_eq_fails
1
2
3
4
5
6
7
8
9
10 #include <crm_internal.h>
11
12 #include <stdio.h>
13 #include <glib.h>
14
15 #include <crm/common/xml.h>
16 #include <crm/common/rules_internal.h>
17 #include <crm/common/unittest_internal.h>
18 #include "crmcommon_private.h"
19
20
21
22
23
24 #define MATCHED_STRING "server-north"
25
26 static const regmatch_t submatches[] = {
27 { .rm_so = 0, .rm_eo = 12 },
28 { .rm_so = 7, .rm_eo = 12 },
29 };
30
31 static pcmk_rule_input_t rule_input = {
32
33
34
35 .rsc_id = MATCHED_STRING,
36 .rsc_id_submatches = submatches,
37 .rsc_id_nmatches = 2,
38
39
40 .rsc_params = NULL,
41
42
43 .rsc_meta = NULL,
44
45
46 .node_attrs = NULL,
47 };
48
49 static int
50 setup(void **state)
51 {
52 rule_input.rsc_params = pcmk__strkey_table(free, free);
53 pcmk__insert_dup(rule_input.rsc_params, "foo-param", "bar");
54 pcmk__insert_dup(rule_input.rsc_params, "myparam", "different");
55
56 rule_input.rsc_meta = pcmk__strkey_table(free, free);
57 pcmk__insert_dup(rule_input.rsc_meta, "foo-meta", "bar");
58 pcmk__insert_dup(rule_input.rsc_params, "mymeta", "different");
59
60 rule_input.node_attrs = pcmk__strkey_table(free, free);
61 pcmk__insert_dup(rule_input.node_attrs, "foo", "bar");
62 pcmk__insert_dup(rule_input.node_attrs, "num", "10");
63 pcmk__insert_dup(rule_input.node_attrs, "ver", "3.5.0");
64 pcmk__insert_dup(rule_input.node_attrs, "prefer-north", "100");
65 pcmk__insert_dup(rule_input.node_attrs, "empty", "");
66
67 return 0;
68 }
69
70 static int
71 teardown(void **state)
72 {
73 g_hash_table_destroy(rule_input.rsc_params);
74 g_hash_table_destroy(rule_input.rsc_meta);
75 g_hash_table_destroy(rule_input.node_attrs);
76 return 0;
77 }
78
79
80
81
82
83
84
85
86 static void
87 assert_attr_expression(const char *xml_string, int reference_rc)
88 {
89 xmlNode *xml = pcmk__xml_parse(xml_string);
90
91 assert_int_equal(pcmk__evaluate_attr_expression(xml, &rule_input),
92 reference_rc);
93 pcmk__xml_free(xml);
94 }
95
96
97
98
99
100
101 #define EXPR_SOURCE_LITERAL_PASSES \
102 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
103 PCMK_XA_ATTRIBUTE "='foo' " \
104 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
105 PCMK_XA_VALUE "='bar' " \
106 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_LITERAL "' />"
107
108 static void
109 null_invalid(void **state)
110 {
111 xmlNode *xml = pcmk__xml_parse(EXPR_SOURCE_LITERAL_PASSES);
112
113 assert_int_equal(pcmk__evaluate_attr_expression(NULL, NULL), EINVAL);
114 assert_int_equal(pcmk__evaluate_attr_expression(xml, NULL), EINVAL);
115 assert_int_equal(pcmk__evaluate_attr_expression(NULL, &rule_input), EINVAL);
116
117 pcmk__xml_free(xml);
118 }
119
120
121
122
123
124
125 #define EXPR_ID_MISSING \
126 "<" PCMK_XE_EXPRESSION " " \
127 PCMK_XA_ATTRIBUTE "='foo' " \
128 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
129 PCMK_XA_VALUE "='bar' />"
130
131 static void
132 id_missing(void **state)
133 {
134 assert_attr_expression(EXPR_ID_MISSING, pcmk_rc_unpack_error);
135 }
136
137
138
139
140
141
142 #define EXPR_ATTR_MISSING \
143 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
144 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
145 PCMK_XA_VALUE "='bar' />"
146
147 static void
148 attr_missing(void **state)
149 {
150 assert_attr_expression(EXPR_ATTR_MISSING, pcmk_rc_unpack_error);
151 }
152
153 #define EXPR_ATTR_SUBMATCH_PASSES \
154 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
155 PCMK_XA_ATTRIBUTE "='prefer-%1' " \
156 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
157
158 static void
159 attr_with_submatch_passes(void **state)
160 {
161 assert_attr_expression(EXPR_ATTR_SUBMATCH_PASSES, pcmk_rc_ok);
162 }
163
164 #define EXPR_ATTR_SUBMATCH_FAILS \
165 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
166 PCMK_XA_ATTRIBUTE "='undefined-%1' " \
167 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
168
169 static void
170 attr_with_submatch_fails(void **state)
171 {
172 assert_attr_expression(EXPR_ATTR_SUBMATCH_FAILS, pcmk_rc_op_unsatisfied);
173 }
174
175
176
177
178
179
180 #define EXPR_SOURCE_MISSING \
181 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
182 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
183 PCMK_XA_ATTRIBUTE "='foo' " \
184 PCMK_XA_VALUE "='bar' />"
185
186 static void
187 source_missing(void **state)
188 {
189
190 assert_attr_expression(EXPR_SOURCE_MISSING, pcmk_rc_ok);
191 }
192
193 #define EXPR_SOURCE_INVALID \
194 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
195 PCMK_XA_ATTRIBUTE "='foo' " \
196 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
197 PCMK_XA_VALUE "='bar' " \
198 PCMK_XA_VALUE_SOURCE "='not-a-source' />"
199
200 static void
201 source_invalid(void **state)
202 {
203 assert_attr_expression(EXPR_SOURCE_INVALID, pcmk_rc_unpack_error);
204 }
205
206 static void
207 source_literal_passes(void **state)
208 {
209 assert_attr_expression(EXPR_SOURCE_LITERAL_PASSES, pcmk_rc_ok);
210 }
211
212 #define EXPR_SOURCE_LITERAL_VALUE_FAILS \
213 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
214 PCMK_XA_ATTRIBUTE "='foo' " \
215 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
216 PCMK_XA_VALUE "='wrong-value' " \
217 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_LITERAL "' />"
218
219 static void
220 source_literal_value_fails(void **state)
221 {
222 assert_attr_expression(EXPR_SOURCE_LITERAL_VALUE_FAILS,
223 pcmk_rc_op_unsatisfied);
224 }
225
226 #define EXPR_SOURCE_LITERAL_ATTR_FAILS \
227 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
228 PCMK_XA_ATTRIBUTE "='not-an-attribute' " \
229 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
230 PCMK_XA_VALUE "='bar' " \
231 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_LITERAL "' />"
232
233 static void
234 source_literal_attr_fails(void **state)
235 {
236 assert_attr_expression(EXPR_SOURCE_LITERAL_ATTR_FAILS,
237 pcmk_rc_op_unsatisfied);
238 }
239
240 #define EXPR_SOURCE_PARAM_MISSING \
241 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
242 PCMK_XA_ATTRIBUTE "='foo' " \
243 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
244 PCMK_XA_VALUE "='not-a-param' " \
245 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_PARAM "' />"
246
247 static void
248 source_params_missing(void **state)
249 {
250 assert_attr_expression(EXPR_SOURCE_PARAM_MISSING, pcmk_rc_op_unsatisfied);
251 }
252
253 #define EXPR_SOURCE_PARAM_PASSES \
254 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
255 PCMK_XA_ATTRIBUTE "='foo' " \
256 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
257 PCMK_XA_VALUE "='foo-param' " \
258 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_PARAM "' />"
259
260 static void
261 source_params_passes(void **state)
262 {
263 assert_attr_expression(EXPR_SOURCE_PARAM_PASSES, pcmk_rc_ok);
264 }
265
266 #define EXPR_SOURCE_PARAM_FAILS \
267 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
268 PCMK_XA_ATTRIBUTE "='foo' " \
269 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
270 PCMK_XA_VALUE "='myparam' " \
271 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_PARAM "' />"
272
273 static void
274 source_params_fails(void **state)
275 {
276 assert_attr_expression(EXPR_SOURCE_PARAM_FAILS, pcmk_rc_op_unsatisfied);
277 }
278
279 #define EXPR_SOURCE_META_MISSING \
280 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
281 PCMK_XA_ATTRIBUTE "='foo' " \
282 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
283 PCMK_XA_VALUE "='not-a-meta' " \
284 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_META "' />"
285
286 static void
287 source_meta_missing(void **state)
288 {
289 assert_attr_expression(EXPR_SOURCE_META_MISSING, pcmk_rc_op_unsatisfied);
290 }
291
292 #define EXPR_SOURCE_META_PASSES \
293 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
294 PCMK_XA_ATTRIBUTE "='foo' " \
295 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
296 PCMK_XA_VALUE "='foo-meta' " \
297 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_META "' />"
298
299 static void
300 source_meta_passes(void **state)
301 {
302 assert_attr_expression(EXPR_SOURCE_META_PASSES, pcmk_rc_ok);
303 }
304
305 #define EXPR_SOURCE_META_FAILS \
306 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
307 PCMK_XA_ATTRIBUTE "='foo' " \
308 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
309 PCMK_XA_VALUE "='mymeta' " \
310 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_META "' />"
311
312 static void
313 source_meta_fails(void **state)
314 {
315 assert_attr_expression(EXPR_SOURCE_META_FAILS, pcmk_rc_op_unsatisfied);
316 }
317
318
319
320
321
322
323 #define EXPR_TYPE_DEFAULT_NUMBER \
324 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
325 PCMK_XA_OPERATION "='" PCMK_VALUE_GT "' " \
326 PCMK_XA_ATTRIBUTE "='num' " \
327 PCMK_XA_VALUE "='2.5' />"
328
329 static void
330 type_default_number(void **state)
331 {
332
333 assert_attr_expression(EXPR_TYPE_DEFAULT_NUMBER, pcmk_rc_ok);
334 }
335
336 #define EXPR_TYPE_DEFAULT_INT \
337 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
338 PCMK_XA_OPERATION "='" PCMK_VALUE_GT "' " \
339 PCMK_XA_ATTRIBUTE "='num' " \
340 PCMK_XA_VALUE "='2' />"
341
342 static void
343 type_default_int(void **state)
344 {
345
346 assert_attr_expression(EXPR_TYPE_DEFAULT_INT, pcmk_rc_ok);
347 }
348
349 #define EXPR_TYPE_INVALID \
350 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
351 PCMK_XA_TYPE "='not-a-value' " \
352 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
353 PCMK_XA_ATTRIBUTE "='foo' " \
354 PCMK_XA_VALUE "='bar' />"
355
356 static void
357 type_invalid(void **state)
358 {
359 assert_attr_expression(EXPR_TYPE_INVALID, pcmk_rc_unpack_error);
360 }
361
362 #define EXPR_TYPE_STRING_PASSES \
363 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
364 PCMK_XA_TYPE "='" PCMK_VALUE_STRING "' " \
365 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
366 PCMK_XA_ATTRIBUTE "='foo' " \
367 PCMK_XA_VALUE "='bar' />"
368
369 static void
370 type_string_passes(void **state)
371 {
372 assert_attr_expression(EXPR_TYPE_STRING_PASSES, pcmk_rc_ok);
373 }
374
375 #define EXPR_TYPE_STRING_FAILS \
376 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
377 PCMK_XA_TYPE "='" PCMK_VALUE_STRING "' " \
378 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
379 PCMK_XA_ATTRIBUTE "='foo' " \
380 PCMK_XA_VALUE "='bat' />"
381
382 static void
383 type_string_fails(void **state)
384 {
385 assert_attr_expression(EXPR_TYPE_STRING_FAILS, pcmk_rc_op_unsatisfied);
386 }
387
388 #define EXPR_TYPE_INTEGER_PASSES \
389 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
390 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
391 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
392 PCMK_XA_ATTRIBUTE "='num' " \
393 PCMK_XA_VALUE "='10' />"
394
395 static void
396 type_integer_passes(void **state)
397 {
398 assert_attr_expression(EXPR_TYPE_INTEGER_PASSES, pcmk_rc_ok);
399 }
400
401 #define EXPR_TYPE_INTEGER_FAILS \
402 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
403 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
404 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
405 PCMK_XA_ATTRIBUTE "='num' " \
406 PCMK_XA_VALUE "='11' />"
407
408 static void
409 type_integer_fails(void **state)
410 {
411 assert_attr_expression(EXPR_TYPE_INTEGER_FAILS, pcmk_rc_op_unsatisfied);
412 }
413
414 #define EXPR_TYPE_INTEGER_TRUNCATION \
415 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
416 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
417 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
418 PCMK_XA_ATTRIBUTE "='num' " \
419 PCMK_XA_VALUE "='10.5' />"
420
421 static void
422 type_integer_truncation(void **state)
423 {
424 assert_attr_expression(EXPR_TYPE_INTEGER_TRUNCATION, pcmk_rc_ok);
425 }
426
427 #define EXPR_TYPE_NUMBER_PASSES \
428 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
429 PCMK_XA_TYPE "='" PCMK_VALUE_NUMBER "' " \
430 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
431 PCMK_XA_ATTRIBUTE "='num' " \
432 PCMK_XA_VALUE "='10.0' />"
433
434 static void
435 type_number_passes(void **state)
436 {
437 assert_attr_expression(EXPR_TYPE_NUMBER_PASSES, pcmk_rc_ok);
438 }
439
440 #define EXPR_TYPE_NUMBER_FAILS \
441 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
442 PCMK_XA_TYPE "='" PCMK_VALUE_NUMBER "' " \
443 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
444 PCMK_XA_ATTRIBUTE "='num' " \
445 PCMK_XA_VALUE "='10.1' />"
446
447 static void
448 type_number_fails(void **state)
449 {
450 assert_attr_expression(EXPR_TYPE_NUMBER_FAILS, pcmk_rc_op_unsatisfied);
451 }
452
453 #define EXPR_TYPE_VERSION_PASSES \
454 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
455 PCMK_XA_TYPE "='" PCMK_VALUE_VERSION "' " \
456 PCMK_XA_OPERATION "='" PCMK_VALUE_GT "' " \
457 PCMK_XA_ATTRIBUTE "='ver' " \
458 PCMK_XA_VALUE "='3.4.9' />"
459
460 static void
461 type_version_passes(void **state)
462 {
463 assert_attr_expression(EXPR_TYPE_VERSION_PASSES, pcmk_rc_ok);
464 }
465
466 #define EXPR_TYPE_VERSION_EQUALITY \
467 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
468 PCMK_XA_TYPE "='" PCMK_VALUE_VERSION "' " \
469 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
470 PCMK_XA_ATTRIBUTE "='ver' " \
471 PCMK_XA_VALUE "='3.5' />"
472
473 static void
474 type_version_equality(void **state)
475 {
476 assert_attr_expression(EXPR_TYPE_VERSION_EQUALITY, pcmk_rc_ok);
477 }
478
479 #define EXPR_TYPE_VERSION_FAILS \
480 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
481 PCMK_XA_TYPE "='" PCMK_VALUE_VERSION "' " \
482 PCMK_XA_OPERATION "='" PCMK_VALUE_GTE "' " \
483 PCMK_XA_ATTRIBUTE "='ver' " \
484 PCMK_XA_VALUE "='4.0' />"
485
486 static void
487 type_version_fails(void **state)
488 {
489 assert_attr_expression(EXPR_TYPE_VERSION_FAILS, pcmk_rc_before_range);
490 }
491
492
493
494
495
496 #define EXPR_OP_MISSING \
497 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
498 PCMK_XA_ATTRIBUTE "='foo' " \
499 PCMK_XA_VALUE "='bar' />"
500
501 static void
502 op_missing(void **state)
503 {
504 assert_attr_expression(EXPR_OP_MISSING, pcmk_rc_unpack_error);
505 }
506
507 #define EXPR_OP_INVALID \
508 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
509 PCMK_XA_ATTRIBUTE "='foo' " \
510 PCMK_XA_OPERATION "='not-an-operation' " \
511 PCMK_XA_VALUE "='bar' />"
512
513 static void
514 op_invalid(void **state)
515 {
516 assert_attr_expression(EXPR_OP_INVALID, pcmk_rc_unpack_error);
517 }
518
519 #define EXPR_OP_LT_PASSES \
520 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
521 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
522 PCMK_XA_OPERATION "='" PCMK_VALUE_LT "' " \
523 PCMK_XA_ATTRIBUTE "='num' " \
524 PCMK_XA_VALUE "='20' />"
525
526 static void
527 op_lt_passes(void **state)
528 {
529 assert_attr_expression(EXPR_OP_LT_PASSES, pcmk_rc_ok);
530 }
531
532 #define EXPR_OP_LT_FAILS \
533 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
534 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
535 PCMK_XA_OPERATION "='" PCMK_VALUE_LT "' " \
536 PCMK_XA_ATTRIBUTE "='num' " \
537 PCMK_XA_VALUE "='2' />"
538
539 static void
540 op_lt_fails(void **state)
541 {
542 assert_attr_expression(EXPR_OP_LT_FAILS, pcmk_rc_after_range);
543 }
544
545 #define EXPR_OP_GT_PASSES \
546 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
547 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
548 PCMK_XA_OPERATION "='" PCMK_VALUE_GT "' " \
549 PCMK_XA_ATTRIBUTE "='num' " \
550 PCMK_XA_VALUE "='2' />"
551
552 static void
553 op_gt_passes(void **state)
554 {
555 assert_attr_expression(EXPR_OP_GT_PASSES, pcmk_rc_ok);
556 }
557
558 #define EXPR_OP_GT_FAILS \
559 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
560 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
561 PCMK_XA_OPERATION "='" PCMK_VALUE_GT "' " \
562 PCMK_XA_ATTRIBUTE "='num' " \
563 PCMK_XA_VALUE "='20' />"
564
565 static void
566 op_gt_fails(void **state)
567 {
568 assert_attr_expression(EXPR_OP_GT_FAILS, pcmk_rc_before_range);
569 }
570
571 #define EXPR_OP_LTE_LT_PASSES \
572 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
573 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
574 PCMK_XA_OPERATION "='" PCMK_VALUE_LTE "' " \
575 PCMK_XA_ATTRIBUTE "='num' " \
576 PCMK_XA_VALUE "='20' />"
577
578 static void
579 op_lte_lt_passes(void **state)
580 {
581 assert_attr_expression(EXPR_OP_LTE_LT_PASSES, pcmk_rc_ok);
582 }
583
584 #define EXPR_OP_LTE_EQ_PASSES \
585 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
586 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
587 PCMK_XA_OPERATION "='" PCMK_VALUE_LTE "' " \
588 PCMK_XA_ATTRIBUTE "='num' " \
589 PCMK_XA_VALUE "='10' />"
590
591 static void
592 op_lte_eq_passes(void **state)
593 {
594 assert_attr_expression(EXPR_OP_LTE_EQ_PASSES, pcmk_rc_ok);
595 }
596
597 #define EXPR_OP_LTE_FAILS \
598 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
599 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
600 PCMK_XA_OPERATION "='" PCMK_VALUE_LTE "' " \
601 PCMK_XA_ATTRIBUTE "='num' " \
602 PCMK_XA_VALUE "='9' />"
603
604 static void
605 op_lte_fails(void **state)
606 {
607 assert_attr_expression(EXPR_OP_LTE_FAILS, pcmk_rc_after_range);
608 }
609
610 #define EXPR_OP_GTE_GT_PASSES \
611 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
612 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
613 PCMK_XA_OPERATION "='" PCMK_VALUE_GTE "' " \
614 PCMK_XA_ATTRIBUTE "='num' " \
615 PCMK_XA_VALUE "='1' />"
616
617 static void
618 op_gte_gt_passes(void **state)
619 {
620 assert_attr_expression(EXPR_OP_GTE_GT_PASSES, pcmk_rc_ok);
621 }
622
623 #define EXPR_OP_GTE_EQ_PASSES \
624 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
625 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
626 PCMK_XA_OPERATION "='" PCMK_VALUE_GTE "' " \
627 PCMK_XA_ATTRIBUTE "='num' " \
628 PCMK_XA_VALUE "='10' />"
629
630 static void
631 op_gte_eq_passes(void **state)
632 {
633 assert_attr_expression(EXPR_OP_GTE_EQ_PASSES, pcmk_rc_ok);
634 }
635
636 #define EXPR_OP_GTE_FAILS \
637 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
638 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
639 PCMK_XA_OPERATION "='" PCMK_VALUE_GTE "' " \
640 PCMK_XA_ATTRIBUTE "='num' " \
641 PCMK_XA_VALUE "='11' />"
642
643 static void
644 op_gte_fails(void **state)
645 {
646 assert_attr_expression(EXPR_OP_GTE_FAILS, pcmk_rc_before_range);
647 }
648
649
650 #define EXPR_OP_EQ_PASSES \
651 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
652 PCMK_XA_TYPE "='" PCMK_VALUE_NUMBER "' " \
653 PCMK_XA_ATTRIBUTE "='foo' " \
654 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
655 PCMK_XA_VALUE "='bar' " \
656 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_LITERAL "' />"
657
658 static void
659 op_eq_passes(void **state)
660 {
661 assert_attr_expression(EXPR_OP_EQ_PASSES, pcmk_rc_ok);
662 }
663
664 #define EXPR_EQ_EMPTY_VS_EMPTY_PASSES \
665 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
666 PCMK_XA_ATTRIBUTE "='empty' " \
667 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
668 PCMK_XA_VALUE "='' />"
669
670 static void
671 op_eq_empty_vs_empty_passes(void **state)
672 {
673 assert_attr_expression(EXPR_EQ_EMPTY_VS_EMPTY_PASSES, pcmk_rc_ok);
674 }
675
676 #define EXPR_OP_EQ_FAILS \
677 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
678 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
679 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
680 PCMK_XA_ATTRIBUTE "='num' " \
681 PCMK_XA_VALUE "='bar' />"
682
683 static void
684 op_eq_fails(void **state)
685 {
686 assert_attr_expression(EXPR_OP_EQ_FAILS, pcmk_rc_op_unsatisfied);
687 }
688
689 #define EXPR_EQ_UNDEFINED_VS_EMPTY_FAILS \
690 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
691 PCMK_XA_ATTRIBUTE "='boo' " \
692 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' " \
693 PCMK_XA_VALUE "='' />"
694
695 static void
696 op_eq_undefined_vs_empty_fails(void **state)
697 {
698 assert_attr_expression(EXPR_EQ_UNDEFINED_VS_EMPTY_FAILS,
699 pcmk_rc_op_unsatisfied);
700 }
701
702 #define EXPR_OP_NE_PASSES \
703 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
704 PCMK_XA_TYPE "='" PCMK_VALUE_STRING "' " \
705 PCMK_XA_ATTRIBUTE "='foo' " \
706 PCMK_XA_OPERATION "='" PCMK_VALUE_NE "' " \
707 PCMK_XA_VALUE "='bat' " \
708 PCMK_XA_VALUE_SOURCE "='" PCMK_VALUE_LITERAL "' />"
709
710 static void
711 op_ne_passes(void **state)
712 {
713 assert_attr_expression(EXPR_OP_NE_PASSES, pcmk_rc_ok);
714 }
715
716 #define EXPR_OP_NE_FAILS \
717 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
718 PCMK_XA_TYPE "='" PCMK_VALUE_INTEGER "' " \
719 PCMK_XA_OPERATION "='" PCMK_VALUE_NE "' " \
720 PCMK_XA_ATTRIBUTE "='num' " \
721 PCMK_XA_VALUE "='10' />"
722
723 static void
724 op_ne_fails(void **state)
725 {
726 assert_attr_expression(EXPR_OP_NE_FAILS, pcmk_rc_op_unsatisfied);
727 }
728
729 #define EXPR_OP_DEFINED_PASSES \
730 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
731 PCMK_XA_ATTRIBUTE "='foo' " \
732 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
733
734 static void
735 op_defined_passes(void **state)
736 {
737 assert_attr_expression(EXPR_OP_DEFINED_PASSES, pcmk_rc_ok);
738 }
739
740 #define EXPR_OP_DEFINED_EMPTY_PASSES \
741 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
742 PCMK_XA_ATTRIBUTE "='empty' " \
743 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
744
745 static void
746 op_defined_empty_passes(void **state)
747 {
748 assert_attr_expression(EXPR_OP_DEFINED_EMPTY_PASSES, pcmk_rc_ok);
749 }
750
751 #define EXPR_OP_DEFINED_FAILS \
752 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
753 PCMK_XA_ATTRIBUTE "='boo' " \
754 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
755
756 static void
757 op_defined_fails(void **state)
758 {
759 assert_attr_expression(EXPR_OP_DEFINED_FAILS, pcmk_rc_op_unsatisfied);
760 }
761
762 #define EXPR_OP_DEFINED_WITH_VALUE \
763 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
764 PCMK_XA_ATTRIBUTE "='foo' " \
765 PCMK_XA_VALUE "='bar' " \
766 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
767
768 static void
769 op_defined_with_value(void **state)
770 {
771 assert_attr_expression(EXPR_OP_DEFINED_WITH_VALUE, pcmk_rc_unpack_error);
772 }
773
774 #define EXPR_OP_UNDEFINED_PASSES \
775 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
776 PCMK_XA_ATTRIBUTE "='boo' " \
777 PCMK_XA_OPERATION "='" PCMK_VALUE_NOT_DEFINED "' />"
778
779 static void
780 op_undefined_passes(void **state)
781 {
782 assert_attr_expression(EXPR_OP_UNDEFINED_PASSES, pcmk_rc_ok);
783 }
784
785 #define EXPR_OP_UNDEFINED_FAILS \
786 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
787 PCMK_XA_ATTRIBUTE "='foo' " \
788 PCMK_XA_OPERATION "='" PCMK_VALUE_NOT_DEFINED "' />"
789
790 static void
791 op_undefined_fails(void **state)
792 {
793 assert_attr_expression(EXPR_OP_UNDEFINED_FAILS, pcmk_rc_op_unsatisfied);
794 }
795
796 #define EXPR_OP_UNDEFINED_EMPTY_FAILS \
797 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
798 PCMK_XA_ATTRIBUTE "='empty' " \
799 PCMK_XA_OPERATION "='" PCMK_VALUE_NOT_DEFINED "' />"
800
801 static void
802 op_undefined_empty_fails(void **state)
803 {
804 assert_attr_expression(EXPR_OP_UNDEFINED_EMPTY_FAILS,
805 pcmk_rc_op_unsatisfied);
806 }
807
808
809
810
811
812
813 #define EXPR_VALUE_MISSING_DEFINED_OK \
814 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
815 PCMK_XA_ATTRIBUTE "='num' " \
816 PCMK_XA_OPERATION "='" PCMK_VALUE_DEFINED "' />"
817
818 static void
819 value_missing_defined_ok(void **state)
820 {
821 assert_attr_expression(EXPR_VALUE_MISSING_DEFINED_OK, pcmk_rc_ok);
822 }
823
824 #define EXPR_VALUE_MISSING_EQ_FAILS \
825 "<" PCMK_XE_EXPRESSION " " PCMK_XA_ID "='e' " \
826 PCMK_XA_ATTRIBUTE "='not-an-attr' " \
827 PCMK_XA_OPERATION "='" PCMK_VALUE_EQ "' />"
828
829 static void
830 value_missing_eq_fails(void **state)
831 {
832 assert_attr_expression(EXPR_VALUE_MISSING_EQ_FAILS, pcmk_rc_unpack_error);
833 }
834
835
836 #define expr_test(f) cmocka_unit_test_setup_teardown(f, setup, teardown)
837
838 PCMK__UNIT_TEST(pcmk__xml_test_setup_group, pcmk__xml_test_teardown_group,
839 cmocka_unit_test(null_invalid),
840 expr_test(id_missing),
841 expr_test(attr_missing),
842 expr_test(attr_with_submatch_passes),
843 expr_test(attr_with_submatch_fails),
844 expr_test(source_missing),
845 expr_test(source_invalid),
846 expr_test(source_literal_passes),
847 expr_test(source_literal_value_fails),
848 expr_test(source_literal_attr_fails),
849 expr_test(source_params_missing),
850 expr_test(source_params_passes),
851 expr_test(source_params_fails),
852 expr_test(source_meta_missing),
853 expr_test(source_meta_passes),
854 expr_test(source_meta_fails),
855 expr_test(type_default_number),
856 expr_test(type_default_int),
857 expr_test(type_invalid),
858 expr_test(type_string_passes),
859 expr_test(type_string_fails),
860 expr_test(type_integer_passes),
861 expr_test(type_integer_fails),
862 expr_test(type_integer_truncation),
863 expr_test(type_number_passes),
864 expr_test(type_number_fails),
865 expr_test(type_version_passes),
866 expr_test(type_version_equality),
867 expr_test(type_version_fails),
868 expr_test(op_missing),
869 expr_test(op_invalid),
870 expr_test(op_lt_passes),
871 expr_test(op_lt_fails),
872 expr_test(op_gt_passes),
873 expr_test(op_gt_fails),
874 expr_test(op_lte_lt_passes),
875 expr_test(op_lte_eq_passes),
876 expr_test(op_lte_fails),
877 expr_test(op_gte_gt_passes),
878 expr_test(op_gte_eq_passes),
879 expr_test(op_gte_fails),
880 expr_test(op_eq_passes),
881 expr_test(op_eq_empty_vs_empty_passes),
882 expr_test(op_eq_fails),
883 expr_test(op_eq_undefined_vs_empty_fails),
884 expr_test(op_ne_passes),
885 expr_test(op_ne_fails),
886 expr_test(op_defined_passes),
887 expr_test(op_defined_empty_passes),
888 expr_test(op_defined_fails),
889 expr_test(op_defined_with_value),
890 expr_test(op_undefined_passes),
891 expr_test(op_undefined_fails),
892 expr_test(op_undefined_empty_fails),
893 expr_test(value_missing_defined_ok),
894 expr_test(value_missing_eq_fails))