blob: c976532ee3f39826602e01c7e63c28da06101972 [file] [log] [blame]
David Sedlákb1ce3f82019-06-05 14:37:26 +02001/**
2 * @file test_parser_yin.c
3 * @author David Sedlák <xsedla1d@stud.fit.vutbr.cz>
4 * @brief unit tests for functions from parser_yin.c
5 *
6 * Copyright (c) 2015 - 2019 CESNET, z.s.p.o.
7 *
8 * This source code is licensed under BSD 3-Clause License (the "License").
9 * You may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
11 *
12 * https://opensource.org/licenses/BSD-3-Clause
13 */
14
David Sedlák3b4db242018-10-19 16:11:01 +020015#include <stdarg.h>
16#include <stddef.h>
17#include <setjmp.h>
18#include <cmocka.h>
19
20#include <stdio.h>
21#include <string.h>
David Sedlák79e50cb2019-06-05 16:33:09 +020022#include <stdbool.h>
David Sedlák3b4db242018-10-19 16:11:01 +020023
David Sedlákecf5eb82019-06-03 14:12:44 +020024#include "../../src/common.h"
25#include "../../src/tree_schema.h"
26#include "../../src/tree_schema_internal.h"
27#include "../../src/parser_yin.h"
David Sedlák8f5bce02019-06-03 16:41:08 +020028#include "../../src/xml.h"
David Sedlák3b4db242018-10-19 16:11:01 +020029
David Sedlák555c7202019-07-04 12:14:12 +020030/* prototypes of static functions */
31void lysp_ext_instance_free(struct ly_ctx *ctx, struct lysp_ext_instance *ext);
David Sedlák986cb412019-07-04 13:10:11 +020032void lysp_ext_free(struct ly_ctx *ctx, struct lysp_ext *ext);
David Sedlák32eee7b2019-07-09 12:38:44 +020033void lysp_when_free(struct ly_ctx *ctx, struct lysp_when *when);
David Sedlák32488102019-07-15 17:44:10 +020034void lysp_type_free(struct ly_ctx *ctx, struct lysp_type *type);
David Sedlák8a83bbb2019-07-18 14:46:00 +020035void lysp_node_free(struct ly_ctx *ctx, struct lysp_node *node);
David Sedlák555c7202019-07-04 12:14:12 +020036
David Sedlák68a1af12019-03-08 13:46:54 +010037struct state {
David Sedlák3b4db242018-10-19 16:11:01 +020038 struct ly_ctx *ctx;
David Sedlák3017da42019-02-15 09:48:04 +010039 struct lys_module *mod;
David Sedlák619db942019-07-03 14:47:30 +020040 struct lysp_module *lysp_mod;
David Sedlákda8ffa32019-07-08 14:17:10 +020041 struct yin_parser_ctx *yin_ctx;
David Sedlák79e50cb2019-06-05 16:33:09 +020042 bool finished_correctly;
David Sedlák68a1af12019-03-08 13:46:54 +010043};
David Sedlák872c7b42018-10-26 13:15:20 +020044
David Sedlák79e50cb2019-06-05 16:33:09 +020045#define BUFSIZE 1024
46char logbuf[BUFSIZE] = {0};
47int store = -1; /* negative for infinite logging, positive for limited logging */
48
49/* set to 0 to printing error messages to stderr instead of checking them in code */
David Sedlák203ca3a2019-07-18 15:26:25 +020050#define ENABLE_LOGGER_CHECKING 1
David Sedlák79e50cb2019-06-05 16:33:09 +020051
52#if ENABLE_LOGGER_CHECKING
53static void
54logger(LY_LOG_LEVEL level, const char *msg, const char *path)
55{
56 (void) level; /* unused */
57 if (store) {
58 if (path && path[0]) {
59 snprintf(logbuf, BUFSIZE - 1, "%s %s", msg, path);
60 } else {
61 strncpy(logbuf, msg, BUFSIZE - 1);
62 }
63 if (store > 0) {
64 --store;
65 }
66 }
67}
68#endif
69
70#if ENABLE_LOGGER_CHECKING
71# define logbuf_assert(str) assert_string_equal(logbuf, str)
72#else
73# define logbuf_assert(str)
74#endif
75
76#define TEST_DUP_GENERIC(PREFIX, MEMBER, VALUE1, VALUE2, FUNC, RESULT, LINE, CLEANUP) \
77 str = PREFIX MEMBER" "VALUE1";"MEMBER" "VALUE2";} ..."; \
78 assert_int_equal(LY_EVALID, FUNC(&ctx, &str, RESULT)); \
79 logbuf_assert("Duplicate keyword \""MEMBER"\". Line number "LINE"."); \
80 CLEANUP
81
David Sedlák8e7bda82019-07-16 17:57:50 +020082int
83setup_ly_ctx(void **state)
David Sedlák68a1af12019-03-08 13:46:54 +010084{
85 struct state *st = NULL;
David Sedlák3b4db242018-10-19 16:11:01 +020086
David Sedlák68a1af12019-03-08 13:46:54 +010087 /* allocate state variable */
88 (*state) = st = calloc(1, sizeof(*st));
89 if (!st) {
90 fprintf(stderr, "Memmory allocation failed");
91 return EXIT_FAILURE;
92 }
David Sedlák872c7b42018-10-26 13:15:20 +020093
David Sedlák68a1af12019-03-08 13:46:54 +010094 /* create new libyang context */
95 ly_ctx_new(NULL, 0, &st->ctx);
David Sedlák872c7b42018-10-26 13:15:20 +020096
David Sedlák8e7bda82019-07-16 17:57:50 +020097 return EXIT_SUCCESS;
98}
99
100int
101destroy_ly_ctx(void **state)
102{
103 struct state *st = *state;
104 ly_ctx_destroy(st->ctx, NULL);
105 free(st);
106
107 return EXIT_SUCCESS;
108}
109
110static int
111setup_f(void **state)
112{
113 struct state *st = *state;
114
115#if ENABLE_LOGGER_CHECKING
116 /* setup logger */
117 ly_set_log_clb(logger, 1);
118#endif
119
David Sedlák68a1af12019-03-08 13:46:54 +0100120 /* allocate new module */
121 st->mod = calloc(1, sizeof(*st->mod));
122 st->mod->ctx = st->ctx;
123
David Sedlák619db942019-07-03 14:47:30 +0200124 /* allocate new parsed module */
125 st->lysp_mod = calloc(1, sizeof(*st->lysp_mod));
126 st->lysp_mod->mod = calloc(1, sizeof(*st->lysp_mod->mod));
127 st->lysp_mod->mod->ctx = st->ctx;
128
129 /* allocate parser context */
David Sedlákda8ffa32019-07-08 14:17:10 +0200130 st->yin_ctx = calloc(1, sizeof(*st->yin_ctx));
131 st->yin_ctx->xml_ctx.ctx = st->ctx;
132 st->yin_ctx->xml_ctx.line = 1;
David Sedlák8f5bce02019-06-03 16:41:08 +0200133
David Sedlák68a1af12019-03-08 13:46:54 +0100134 return EXIT_SUCCESS;
David Sedlák3b4db242018-10-19 16:11:01 +0200135}
136
137static int
David Sedlák68a1af12019-03-08 13:46:54 +0100138teardown_f(void **state)
139{
140 struct state *st = *(struct state **)state;
David Sedlák619db942019-07-03 14:47:30 +0200141 struct lys_module *temp;
David Sedlák68a1af12019-03-08 13:46:54 +0100142
David Sedlák79e50cb2019-06-05 16:33:09 +0200143#if ENABLE_LOGGER_CHECKING
144 /* teardown logger */
145 if (!st->finished_correctly && logbuf[0] != '\0') {
146 fprintf(stderr, "%s\n", logbuf);
147 }
148#endif
149
David Sedlák619db942019-07-03 14:47:30 +0200150 temp = st->lysp_mod->mod;
151
David Sedlákda8ffa32019-07-08 14:17:10 +0200152 lyxml_context_clear(&st->yin_ctx->xml_ctx);
David Sedlák68a1af12019-03-08 13:46:54 +0100153 lys_module_free(st->mod, NULL);
David Sedlák619db942019-07-03 14:47:30 +0200154 lysp_module_free(st->lysp_mod);
155 lys_module_free(temp, NULL);
David Sedlákda8ffa32019-07-08 14:17:10 +0200156 free(st->yin_ctx);
David Sedlák68a1af12019-03-08 13:46:54 +0100157
158 return EXIT_SUCCESS;
159}
160
David Sedlák392af4f2019-06-04 16:02:42 +0200161static struct state*
162reset_state(void **state)
163{
David Sedlák79e50cb2019-06-05 16:33:09 +0200164 ((struct state *)*state)->finished_correctly = true;
David Sedlák555c7202019-07-04 12:14:12 +0200165 logbuf[0] = '\0';
David Sedlák392af4f2019-06-04 16:02:42 +0200166 teardown_f(state);
167 setup_f(state);
168
169 return *state;
170}
171
David Sedlák79e50cb2019-06-05 16:33:09 +0200172void
173logbuf_clean(void)
174{
175 logbuf[0] = '\0';
176}
177
David Sedlák68a1af12019-03-08 13:46:54 +0100178static void
David Sedlák392af4f2019-06-04 16:02:42 +0200179test_yin_parse_module(void **state)
David Sedlák68a1af12019-03-08 13:46:54 +0100180{
181 LY_ERR ret = LY_SUCCESS;
182 struct state *st = *state;
183
184 ret = yin_parse_module(st->ctx,
David Sedlák2b214ac2019-06-06 16:11:03 +0200185 "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"\
186 name=\"example-foo\"\
David Sedlák18730132019-03-15 15:51:34 +0100187 xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"\
188 xmlns:foo=\"urn:example:foo\"\
189 xmlns:myext=\"urn:example:extensions\">\
David Sedlákcd0c9512019-03-29 13:23:06 +0100190 <namespace uri=\"urn:example:foo\" xmlns:myext=\"urn:example:extensions\"/>\
David Sedláka7406952019-04-05 10:33:07 +0200191 <prefix xmlns:myxt=\"urn:emple:extensions\" value=\"foo\" xmlns:myext=\"urn:example:extensions\"/>\
David Sedlákd9d3a312019-06-04 09:47:10 +0200192 </module>",
David Sedlák68a1af12019-03-08 13:46:54 +0100193 st->mod);
194
195 assert_int_equal(ret, LY_SUCCESS);
196 assert_string_equal(st->mod->parsed->mod->name, "example-foo");
197 assert_string_equal(st->mod->parsed->mod->prefix, "foo");
David Sedlákcd0c9512019-03-29 13:23:06 +0100198 assert_string_equal(st->mod->parsed->mod->ns, "urn:example:foo");
David Sedlák392af4f2019-06-04 16:02:42 +0200199
200 st = reset_state(state);
201 ret = yin_parse_module(st->ctx,
David Sedlák2b214ac2019-06-06 16:11:03 +0200202 "<module name=\"example-foo\">\
203 <invalid-tag uri=\"urn:example:foo\"\"/>\
204 </module>",
205 st->mod);
David Sedlák392af4f2019-06-04 16:02:42 +0200206 assert_int_equal(ret, LY_EVALID);
207
208 st = reset_state(state);
209 ret = yin_parse_module(st->ctx,
David Sedlák8f7a1172019-06-20 14:42:18 +0200210 "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">\
David Sedlák57715b12019-06-17 13:05:22 +0200211 </module>",
David Sedlák2b214ac2019-06-06 16:11:03 +0200212 st->mod);
David Sedlák392af4f2019-06-04 16:02:42 +0200213 assert_int_equal(ret, LY_EVALID);
David Sedlák882a8072019-07-08 17:51:20 +0200214 logbuf_assert("Missing mandatory attribute name of module element. Line number 1.");
David Sedlák392af4f2019-06-04 16:02:42 +0200215
216 st = reset_state(state);
217 ret = yin_parse_module(st->ctx,
218 "",
219 st->mod);
220 assert_int_equal(ret, LY_EVALID);
David Sedlák79e50cb2019-06-05 16:33:09 +0200221 logbuf_assert("Invalid keyword \"(null)\", expected \"module\" or \"submodule\". Line number 1.");
222 st->finished_correctly = true;
David Sedlák3b4db242018-10-19 16:11:01 +0200223}
224
225static void
David Sedlák1bccdfa2019-06-17 15:55:27 +0200226test_yin_match_keyword(void **state)
David Sedlák3b4db242018-10-19 16:11:01 +0200227{
David Sedlák8f7a1172019-06-20 14:42:18 +0200228 struct state *st = *state;
David Sedlák3b4db242018-10-19 16:11:01 +0200229
David Sedlák8f7a1172019-06-20 14:42:18 +0200230 const char *prefix, *name;
231 struct yin_arg_record *args = NULL;
232 size_t prefix_len, name_len;
233 /* create mock yin namespace in xml context */
234 const char *data = "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\" />";
David Sedlákda8ffa32019-07-08 14:17:10 +0200235 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix, &prefix_len, &name, &name_len);
236 yin_load_attributes(st->yin_ctx, &data, &args);
David Sedlák8f7a1172019-06-20 14:42:18 +0200237 LY_ARRAY_FREE(args);
238
David Sedlákc1771b12019-07-10 15:55:46 +0200239 assert_int_equal(yin_match_keyword(st->yin_ctx, "anydatax", strlen("anydatax"), prefix, prefix_len, YANG_NONE), YANG_NONE);
240 assert_int_equal(yin_match_keyword(st->yin_ctx, "asdasd", strlen("asdasd"), prefix, prefix_len, YANG_NONE), YANG_NONE);
241 assert_int_equal(yin_match_keyword(st->yin_ctx, "", 0, prefix, prefix_len, YANG_NONE), YANG_NONE);
242 assert_int_equal(yin_match_keyword(st->yin_ctx, "anydata", strlen("anydata"), prefix, prefix_len, YANG_NONE), YANG_ANYDATA);
243 assert_int_equal(yin_match_keyword(st->yin_ctx, "anyxml", strlen("anyxml"), prefix, prefix_len, YANG_NONE), YANG_ANYXML);
244 assert_int_equal(yin_match_keyword(st->yin_ctx, "argument", strlen("argument"), prefix, prefix_len, YANG_NONE), YANG_ARGUMENT);
245 assert_int_equal(yin_match_keyword(st->yin_ctx, "augment", strlen("augment"), prefix, prefix_len, YANG_NONE), YANG_AUGMENT);
246 assert_int_equal(yin_match_keyword(st->yin_ctx, "base", strlen("base"), prefix, prefix_len, YANG_NONE), YANG_BASE);
247 assert_int_equal(yin_match_keyword(st->yin_ctx, "belongs-to", strlen("belongs-to"), prefix, prefix_len, YANG_NONE), YANG_BELONGS_TO);
248 assert_int_equal(yin_match_keyword(st->yin_ctx, "bit", strlen("bit"), prefix, prefix_len, YANG_NONE), YANG_BIT);
249 assert_int_equal(yin_match_keyword(st->yin_ctx, "case", strlen("case"), prefix, prefix_len, YANG_NONE), YANG_CASE);
250 assert_int_equal(yin_match_keyword(st->yin_ctx, "choice", strlen("choice"), prefix, prefix_len, YANG_NONE), YANG_CHOICE);
251 assert_int_equal(yin_match_keyword(st->yin_ctx, "config", strlen("config"), prefix, prefix_len, YANG_NONE), YANG_CONFIG);
252 assert_int_equal(yin_match_keyword(st->yin_ctx, "contact", strlen("contact"), prefix, prefix_len, YANG_NONE), YANG_CONTACT);
253 assert_int_equal(yin_match_keyword(st->yin_ctx, "container", strlen("container"), prefix, prefix_len, YANG_NONE), YANG_CONTAINER);
254 assert_int_equal(yin_match_keyword(st->yin_ctx, "default", strlen("default"), prefix, prefix_len, YANG_NONE), YANG_DEFAULT);
255 assert_int_equal(yin_match_keyword(st->yin_ctx, "description", strlen("description"), prefix, prefix_len, YANG_NONE), YANG_DESCRIPTION);
256 assert_int_equal(yin_match_keyword(st->yin_ctx, "deviate", strlen("deviate"), prefix, prefix_len, YANG_NONE), YANG_DEVIATE);
257 assert_int_equal(yin_match_keyword(st->yin_ctx, "deviation", strlen("deviation"), prefix, prefix_len, YANG_NONE), YANG_DEVIATION);
258 assert_int_equal(yin_match_keyword(st->yin_ctx, "enum", strlen("enum"), prefix, prefix_len, YANG_NONE), YANG_ENUM);
259 assert_int_equal(yin_match_keyword(st->yin_ctx, "error-app-tag", strlen("error-app-tag"), prefix, prefix_len, YANG_NONE), YANG_ERROR_APP_TAG);
260 assert_int_equal(yin_match_keyword(st->yin_ctx, "error-message", strlen("error-message"), prefix, prefix_len, YANG_NONE), YANG_ERROR_MESSAGE);
261 assert_int_equal(yin_match_keyword(st->yin_ctx, "extension", strlen("extension"), prefix, prefix_len, YANG_NONE), YANG_EXTENSION);
262 assert_int_equal(yin_match_keyword(st->yin_ctx, "feature", strlen("feature"), prefix, prefix_len, YANG_NONE), YANG_FEATURE);
263 assert_int_equal(yin_match_keyword(st->yin_ctx, "fraction-digits", strlen("fraction-digits"), prefix, prefix_len, YANG_NONE), YANG_FRACTION_DIGITS);
264 assert_int_equal(yin_match_keyword(st->yin_ctx, "grouping", strlen("grouping"), prefix, prefix_len, YANG_NONE), YANG_GROUPING);
265 assert_int_equal(yin_match_keyword(st->yin_ctx, "identity", strlen("identity"), prefix, prefix_len, YANG_NONE), YANG_IDENTITY);
266 assert_int_equal(yin_match_keyword(st->yin_ctx, "if-feature", strlen("if-feature"), prefix, prefix_len, YANG_NONE), YANG_IF_FEATURE);
267 assert_int_equal(yin_match_keyword(st->yin_ctx, "import", strlen("import"), prefix, prefix_len, YANG_NONE), YANG_IMPORT);
268 assert_int_equal(yin_match_keyword(st->yin_ctx, "include", strlen("include"), prefix, prefix_len, YANG_NONE), YANG_INCLUDE);
269 assert_int_equal(yin_match_keyword(st->yin_ctx, "input", strlen("input"), prefix, prefix_len, YANG_NONE), YANG_INPUT);
270 assert_int_equal(yin_match_keyword(st->yin_ctx, "key", strlen("key"), prefix, prefix_len, YANG_NONE), YANG_KEY);
271 assert_int_equal(yin_match_keyword(st->yin_ctx, "leaf", strlen("leaf"), prefix, prefix_len, YANG_NONE), YANG_LEAF);
272 assert_int_equal(yin_match_keyword(st->yin_ctx, "leaf-list", strlen("leaf-list"), prefix, prefix_len, YANG_NONE), YANG_LEAF_LIST);
273 assert_int_equal(yin_match_keyword(st->yin_ctx, "length", strlen("length"), prefix, prefix_len, YANG_NONE), YANG_LENGTH);
274 assert_int_equal(yin_match_keyword(st->yin_ctx, "list", strlen("list"), prefix, prefix_len, YANG_NONE), YANG_LIST);
275 assert_int_equal(yin_match_keyword(st->yin_ctx, "mandatory", strlen("mandatory"), prefix, prefix_len, YANG_NONE), YANG_MANDATORY);
276 assert_int_equal(yin_match_keyword(st->yin_ctx, "max-elements", strlen("max-elements"), prefix, prefix_len, YANG_NONE), YANG_MAX_ELEMENTS);
277 assert_int_equal(yin_match_keyword(st->yin_ctx, "min-elements", strlen("min-elements"), prefix, prefix_len, YANG_NONE), YANG_MIN_ELEMENTS);
278 assert_int_equal(yin_match_keyword(st->yin_ctx, "modifier", strlen("modifier"), prefix, prefix_len, YANG_NONE), YANG_MODIFIER);
279 assert_int_equal(yin_match_keyword(st->yin_ctx, "module", strlen("module"), prefix, prefix_len, YANG_NONE), YANG_MODULE);
280 assert_int_equal(yin_match_keyword(st->yin_ctx, "must", strlen("must"), prefix, prefix_len, YANG_NONE), YANG_MUST);
281 assert_int_equal(yin_match_keyword(st->yin_ctx, "namespace", strlen("namespace"), prefix, prefix_len, YANG_NONE), YANG_NAMESPACE);
282 assert_int_equal(yin_match_keyword(st->yin_ctx, "notification", strlen("notification"), prefix, prefix_len, YANG_NONE), YANG_NOTIFICATION);
283 assert_int_equal(yin_match_keyword(st->yin_ctx, "ordered-by", strlen("ordered-by"), prefix, prefix_len, YANG_NONE), YANG_ORDERED_BY);
284 assert_int_equal(yin_match_keyword(st->yin_ctx, "organization", strlen("organization"), prefix, prefix_len, YANG_NONE), YANG_ORGANIZATION);
285 assert_int_equal(yin_match_keyword(st->yin_ctx, "output", strlen("output"), prefix, prefix_len, YANG_NONE), YANG_OUTPUT);
286 assert_int_equal(yin_match_keyword(st->yin_ctx, "path", strlen("path"), prefix, prefix_len, YANG_NONE), YANG_PATH);
287 assert_int_equal(yin_match_keyword(st->yin_ctx, "pattern", strlen("pattern"), prefix, prefix_len, YANG_NONE), YANG_PATTERN);
288 assert_int_equal(yin_match_keyword(st->yin_ctx, "position", strlen("position"), prefix, prefix_len, YANG_NONE), YANG_POSITION);
289 assert_int_equal(yin_match_keyword(st->yin_ctx, "prefix", strlen("prefix"), prefix, prefix_len, YANG_NONE), YANG_PREFIX);
290 assert_int_equal(yin_match_keyword(st->yin_ctx, "presence", strlen("presence"), prefix, prefix_len, YANG_NONE), YANG_PRESENCE);
291 assert_int_equal(yin_match_keyword(st->yin_ctx, "range", strlen("range"), prefix, prefix_len, YANG_NONE), YANG_RANGE);
292 assert_int_equal(yin_match_keyword(st->yin_ctx, "reference", strlen("reference"), prefix, prefix_len, YANG_NONE), YANG_REFERENCE);
293 assert_int_equal(yin_match_keyword(st->yin_ctx, "refine", strlen("refine"), prefix, prefix_len, YANG_NONE), YANG_REFINE);
294 assert_int_equal(yin_match_keyword(st->yin_ctx, "require-instance", strlen("require-instance"), prefix, prefix_len, YANG_NONE), YANG_REQUIRE_INSTANCE);
295 assert_int_equal(yin_match_keyword(st->yin_ctx, "revision", strlen("revision"), prefix, prefix_len, YANG_NONE), YANG_REVISION);
296 assert_int_equal(yin_match_keyword(st->yin_ctx, "revision-date", strlen("revision-date"), prefix, prefix_len, YANG_NONE), YANG_REVISION_DATE);
297 assert_int_equal(yin_match_keyword(st->yin_ctx, "rpc", strlen("rpc"), prefix, prefix_len, YANG_NONE), YANG_RPC);
298 assert_int_equal(yin_match_keyword(st->yin_ctx, "status", strlen("status"), prefix, prefix_len, YANG_NONE), YANG_STATUS);
299 assert_int_equal(yin_match_keyword(st->yin_ctx, "submodule", strlen("submodule"), prefix, prefix_len, YANG_NONE), YANG_SUBMODULE);
300 assert_int_equal(yin_match_keyword(st->yin_ctx, "type", strlen("type"), prefix, prefix_len, YANG_NONE), YANG_TYPE);
301 assert_int_equal(yin_match_keyword(st->yin_ctx, "typedef", strlen("typedef"), prefix, prefix_len, YANG_NONE), YANG_TYPEDEF);
302 assert_int_equal(yin_match_keyword(st->yin_ctx, "unique", strlen("unique"), prefix, prefix_len, YANG_NONE), YANG_UNIQUE);
303 assert_int_equal(yin_match_keyword(st->yin_ctx, "units", strlen("units"), prefix, prefix_len, YANG_NONE), YANG_UNITS);
304 assert_int_equal(yin_match_keyword(st->yin_ctx, "uses", strlen("uses"), prefix, prefix_len, YANG_NONE), YANG_USES);
305 assert_int_equal(yin_match_keyword(st->yin_ctx, "value", strlen("value"), prefix, prefix_len, YANG_NONE), YANG_VALUE);
306 assert_int_equal(yin_match_keyword(st->yin_ctx, "when", strlen("when"), prefix, prefix_len, YANG_NONE), YANG_WHEN);
307 assert_int_equal(yin_match_keyword(st->yin_ctx, "yang-version", strlen("yang-version"), prefix, prefix_len, YANG_NONE), YANG_YANG_VERSION);
308 assert_int_equal(yin_match_keyword(st->yin_ctx, "yin-element", strlen("yin-element"), prefix, prefix_len, YANG_NONE), YANG_YIN_ELEMENT);
David Sedlák8f7a1172019-06-20 14:42:18 +0200309
310 st->finished_correctly = true;
David Sedlák872c7b42018-10-26 13:15:20 +0200311}
David Sedlák3b4db242018-10-19 16:11:01 +0200312
David Sedlák872c7b42018-10-26 13:15:20 +0200313static void
David Sedlák060b00e2019-06-19 11:12:06 +0200314test_yin_match_argument_name(void **state)
David Sedlák872c7b42018-10-26 13:15:20 +0200315{
David Sedlák68a1af12019-03-08 13:46:54 +0100316 (void)state; /* unused */
David Sedlák872c7b42018-10-26 13:15:20 +0200317
David Sedlák060b00e2019-06-19 11:12:06 +0200318 assert_int_equal(yin_match_argument_name("", 5), YIN_ARG_UNKNOWN);
319 assert_int_equal(yin_match_argument_name("qwertyasd", 5), YIN_ARG_UNKNOWN);
320 assert_int_equal(yin_match_argument_name("conditionasd", 8), YIN_ARG_UNKNOWN);
321 assert_int_equal(yin_match_argument_name("condition", 9), YIN_ARG_CONDITION);
322 assert_int_equal(yin_match_argument_name("date", 4), YIN_ARG_DATE);
323 assert_int_equal(yin_match_argument_name("module", 6), YIN_ARG_MODULE);
324 assert_int_equal(yin_match_argument_name("name", 4), YIN_ARG_NAME);
325 assert_int_equal(yin_match_argument_name("tag", 3), YIN_ARG_TAG);
326 assert_int_equal(yin_match_argument_name("target-node", 11), YIN_ARG_TARGET_NODE);
327 assert_int_equal(yin_match_argument_name("text", 4), YIN_ARG_TEXT);
328 assert_int_equal(yin_match_argument_name("uri", 3), YIN_ARG_URI);
329 assert_int_equal(yin_match_argument_name("value", 5), YIN_ARG_VALUE);
David Sedlák3b4db242018-10-19 16:11:01 +0200330}
331
David Sedlák68a1af12019-03-08 13:46:54 +0100332static void
David Sedlákb1a78352019-06-28 16:16:29 +0200333test_yin_parse_element_generic(void **state)
334{
335 const char *prefix, *name;
336 struct state *st = *state;
337 struct lysp_ext_instance exts;
338 size_t prefix_len, name_len;
339 LY_ERR ret;
340
341 memset(&exts, 0, sizeof(exts));
342
343 const char *data = "<elem attr=\"value\">text_value</elem>";
David Sedlákda8ffa32019-07-08 14:17:10 +0200344 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix, &prefix_len, &name, &name_len);
345 ret = yin_parse_element_generic(st->yin_ctx, name, name_len, prefix, prefix_len, &data, &exts.child);
David Sedlákb1a78352019-06-28 16:16:29 +0200346 assert_int_equal(ret, LY_SUCCESS);
David Sedlák1fdb2522019-07-09 16:22:57 +0200347 assert_int_equal(st->yin_ctx->xml_ctx.status, LYXML_END);
David Sedlákb1a78352019-06-28 16:16:29 +0200348 assert_string_equal(exts.child->stmt, "elem");
349 assert_string_equal(exts.child->arg, "text_value");
David Sedlákb1a78352019-06-28 16:16:29 +0200350 assert_string_equal(exts.child->child->stmt, "attr");
351 assert_string_equal(exts.child->child->arg, "value");
352 assert_true(exts.child->child->flags & LYS_YIN_ATTR);
David Sedlákb1a78352019-06-28 16:16:29 +0200353 lysp_ext_instance_free(st->ctx, &exts);
David Sedlák5392a212019-07-01 09:19:10 +0200354 st = reset_state(state);
355
356 data = "<elem></elem>";
David Sedlákda8ffa32019-07-08 14:17:10 +0200357 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix, &prefix_len, &name, &name_len);
358 ret = yin_parse_element_generic(st->yin_ctx, name, name_len, prefix, prefix_len, &data, &exts.child);
David Sedlák5392a212019-07-01 09:19:10 +0200359 assert_int_equal(ret, LY_SUCCESS);
360 assert_string_equal(exts.child->stmt, "elem");
361 assert_null(exts.child->child);
362 assert_null(exts.child->arg);
David Sedlákda8ffa32019-07-08 14:17:10 +0200363 assert_int_equal(st->yin_ctx->xml_ctx.status, LYXML_END);
David Sedlák5392a212019-07-01 09:19:10 +0200364 lysp_ext_instance_free(st->ctx, &exts);
365
David Sedlákb1a78352019-06-28 16:16:29 +0200366 st->finished_correctly = true;
367}
368
369static void
370test_yin_parse_extension_instance(void **state)
371{
372 LY_ERR ret;
373 struct state *st = *state;
374 const char *prefix, *name;
375 size_t prefix_len, name_len;
376 struct yin_arg_record *args = NULL;
377 struct lysp_ext_instance *exts = NULL;
David Sedlákb1a78352019-06-28 16:16:29 +0200378 const char *data = "<ext value1=\"test\" value=\"test2\"><subelem>text</subelem></ext>";
David Sedlákda8ffa32019-07-08 14:17:10 +0200379 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix, &prefix_len, &name, &name_len);
380 yin_load_attributes(st->yin_ctx, &data, &args);
David Sedlák1f90d252019-07-10 17:09:32 +0200381 ret = yin_parse_extension_instance(st->yin_ctx, args, &data, name2fullname(name, prefix_len),
David Sedlák619db942019-07-03 14:47:30 +0200382 namelen2fulllen(name_len, prefix_len), LYEXT_SUBSTMT_CONTACT, 0, &exts);
David Sedlákb1a78352019-06-28 16:16:29 +0200383 assert_int_equal(ret, LY_SUCCESS);
384 assert_string_equal(exts->name, "ext");
385 assert_int_equal(exts->insubstmt_index, 0);
386 assert_true(exts->insubstmt == LYEXT_SUBSTMT_CONTACT);
387 assert_true(exts->yin & LYS_YIN);
388 assert_string_equal(exts->child->stmt, "value1");
389 assert_string_equal(exts->child->arg, "test");
390 assert_null(exts->child->child);
391 assert_true(exts->child->flags & LYS_YIN_ATTR);
392 assert_string_equal(exts->child->next->stmt, "value");
393 assert_string_equal(exts->child->next->arg, "test2");
394 assert_null(exts->child->next->child);
395 assert_true(exts->child->next->flags & LYS_YIN_ATTR);
396
397 assert_string_equal(exts->child->next->next->stmt, "subelem");
398 assert_string_equal(exts->child->next->next->arg, "text");
399 assert_null(exts->child->next->next->child);
400 assert_null(exts->child->next->next->next);
401 assert_false(exts->child->next->next->flags & LYS_YIN_ATTR);
David Sedlákda8ffa32019-07-08 14:17:10 +0200402 assert_int_equal(st->yin_ctx->xml_ctx.status, LYXML_END);
David Sedlákb1a78352019-06-28 16:16:29 +0200403 LY_ARRAY_FREE(args);
404 lysp_ext_instance_free(st->ctx, exts);
405 LY_ARRAY_FREE(exts);
David Sedlákf250ecf2019-07-01 11:02:05 +0200406 exts = NULL;
407 args = NULL;
408 st = reset_state(state);
409
410 data = "<extension-elem />";
David Sedlákda8ffa32019-07-08 14:17:10 +0200411 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix, &prefix_len, &name, &name_len);
412 yin_load_attributes(st->yin_ctx, &data, &args);
David Sedlák1f90d252019-07-10 17:09:32 +0200413 ret = yin_parse_extension_instance(st->yin_ctx, args, &data, name, name_len, LYEXT_SUBSTMT_CONTACT, 0, &exts);
David Sedlákf250ecf2019-07-01 11:02:05 +0200414 assert_int_equal(ret, LY_SUCCESS);
415 assert_string_equal(exts->name, "extension-elem");
416 assert_null(exts->argument);
417 assert_null(exts->child);
418 assert_int_equal(exts->insubstmt, LYEXT_SUBSTMT_CONTACT);
419 assert_int_equal(exts->insubstmt_index, 0);
420 assert_true(exts->yin & LYS_YIN);
David Sedlákda8ffa32019-07-08 14:17:10 +0200421 assert_int_equal(st->yin_ctx->xml_ctx.status, LYXML_END);
David Sedlákf250ecf2019-07-01 11:02:05 +0200422 LY_ARRAY_FREE(args);
423 lysp_ext_instance_free(st->ctx, exts);
424 LY_ARRAY_FREE(exts);
David Sedlákb1a78352019-06-28 16:16:29 +0200425 st->finished_correctly = true;
426}
427
David Sedlák555c7202019-07-04 12:14:12 +0200428static void
429test_yin_parse_content(void **state)
430{
431 struct state *st = *state;
432 LY_ERR ret = LY_SUCCESS;
433 struct sized_string name, prefix;
434 const char *data = "<prefix value=\"a_mod\" xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
435 "<custom xmlns=\"my-ext\">"
436 "totally amazing extension"
437 "</custom>"
David Sedlák986cb412019-07-04 13:10:11 +0200438 "<extension name=\"ext\">"
439 "<argument name=\"argname\"></argument>"
440 "<description><text>desc</text></description>"
441 "<reference><text>ref</text></reference>"
442 "<status value=\"deprecated\"></status>"
443 "</extension>"
David Sedlák555c7202019-07-04 12:14:12 +0200444 "<text xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">wsefsdf</text>"
David Sedlák32488102019-07-15 17:44:10 +0200445 "<if-feature name=\"foo\"></if-feature>"
David Sedlák32eee7b2019-07-09 12:38:44 +0200446 "<when condition=\"condition...\">"
447 "<reference><text>when_ref</text></reference>"
448 "<description><text>when_desc</text></description>"
449 "</when>"
David Sedláke1a30302019-07-10 13:49:38 +0200450 "<config value=\"true\"/>"
David Sedlákc1771b12019-07-10 15:55:46 +0200451 "<error-message>"
452 "<value>error-msg</value>"
453 "</error-message>"
David Sedlák2ce1be62019-07-10 16:15:09 +0200454 "<error-app-tag value=\"err-app-tag\"/>"
David Sedláka5b1d382019-07-10 16:31:09 +0200455 "<units name=\"radians\"></units>"
David Sedláke7084ce2019-07-10 16:44:15 +0200456 "<default value=\"default-value\"/>"
David Sedlák5545f5d2019-07-11 11:55:16 +0200457 "<position value=\"25\"></position>"
458 "<value value=\"-5\"/>"
David Sedlákcf5569a2019-07-11 13:31:34 +0200459 "<require-instance value=\"true\"></require-instance>"
David Sedlákb7296dd2019-07-11 14:58:38 +0200460 "<range value=\"5..10\" />"
David Sedlák438ae432019-07-11 15:36:54 +0200461 "<length value=\"baf\"/>"
David Sedlákd3983112019-07-12 11:20:56 +0200462 "<pattern value='pattern'>"
463 "<modifier value='invert-match'/>"
464 "</pattern>"
David Sedlákfd5b9c32019-07-12 15:33:13 +0200465 "<enum name=\"yay\">"
466 "</enum>"
David Sedlák555c7202019-07-04 12:14:12 +0200467 "</prefix>";
468 struct lysp_ext_instance *exts = NULL;
David Sedlák5f8191e2019-07-08 16:35:52 +0200469 const char **if_features = NULL;
David Sedlák555c7202019-07-04 12:14:12 +0200470 struct yin_arg_record *attrs = NULL;
David Sedláke7084ce2019-07-10 16:44:15 +0200471 const char *value, *err_msg, *app_tag, *units, *def;
David Sedlák986cb412019-07-04 13:10:11 +0200472 struct lysp_ext *ext_def = NULL;
David Sedlák32eee7b2019-07-09 12:38:44 +0200473 struct lysp_when *when_p = NULL;
David Sedlákcf5569a2019-07-11 13:31:34 +0200474 struct lysp_type_enum pos_enum = {}, val_enum = {};
David Sedlákfd5b9c32019-07-12 15:33:13 +0200475 struct lysp_type req_type = {}, range_type = {}, len_type = {}, patter_type = {}, enum_type = {};
David Sedláke1a30302019-07-10 13:49:38 +0200476 uint8_t config = 0;
David Sedlák555c7202019-07-04 12:14:12 +0200477
David Sedlákda8ffa32019-07-08 14:17:10 +0200478 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix.value, &prefix.len, &name.value, &name.len);
479 yin_load_attributes(st->yin_ctx, &data, &attrs);
David Sedlák555c7202019-07-04 12:14:12 +0200480
David Sedlákfd5b9c32019-07-12 15:33:13 +0200481 struct yin_subelement subelems[17] = {
David Sedlák438ae432019-07-11 15:36:54 +0200482 {YANG_CONFIG, &config, 0},
David Sedlákc3da3ef2019-07-19 12:56:08 +0200483 {YANG_DEFAULT, &def, YIN_SUBELEM_UNIQUE},
David Sedlákfd5b9c32019-07-12 15:33:13 +0200484 {YANG_ENUM, &enum_type, 0},
David Sedlák438ae432019-07-11 15:36:54 +0200485 {YANG_ERROR_APP_TAG, &app_tag, 0},
486 {YANG_ERROR_MESSAGE, &err_msg, 0},
487 {YANG_EXTENSION, &ext_def, 0},
488 {YANG_IF_FEATURE, &if_features, 0},
489 {YANG_LENGTH, &len_type, 0},
David Sedlákd3983112019-07-12 11:20:56 +0200490 {YANG_PATTERN, &patter_type, 0},
David Sedlák438ae432019-07-11 15:36:54 +0200491 {YANG_RANGE, &range_type, 0},
492 {YANG_REQUIRE_INSTANCE, &req_type, 0},
493 {YANG_UNITS, &units, 0},
David Sedlák374d2b32019-07-17 15:06:55 +0200494 {YANG_POSITION, &pos_enum, 0},
David Sedlák438ae432019-07-11 15:36:54 +0200495 {YANG_VALUE, &val_enum, 0},
496 {YANG_WHEN, &when_p, 0},
497 {YANG_CUSTOM, NULL, 0},
498 {YIN_TEXT, &value, 0}
David Sedlákd3983112019-07-12 11:20:56 +0200499 };
David Sedlákfd5b9c32019-07-12 15:33:13 +0200500 ret = yin_parse_content(st->yin_ctx, subelems, 17, &data, YANG_PREFIX, NULL, &exts);
David Sedlák555c7202019-07-04 12:14:12 +0200501 assert_int_equal(ret, LY_SUCCESS);
David Sedlák1fdb2522019-07-09 16:22:57 +0200502 assert_int_equal(st->yin_ctx->xml_ctx.status, LYXML_END);
David Sedlák2ce1be62019-07-10 16:15:09 +0200503 /* check parsed values */
David Sedláke7084ce2019-07-10 16:44:15 +0200504 assert_string_equal(def, "default-value");
David Sedlák555c7202019-07-04 12:14:12 +0200505 assert_string_equal(exts->name, "custom");
506 assert_string_equal(exts->argument, "totally amazing extension");
507 assert_string_equal(value, "wsefsdf");
David Sedláka5b1d382019-07-10 16:31:09 +0200508 assert_string_equal(units, "radians");
David Sedlák32eee7b2019-07-09 12:38:44 +0200509 assert_string_equal(when_p->cond, "condition...");
510 assert_string_equal(when_p->dsc, "when_desc");
511 assert_string_equal(when_p->ref, "when_ref");
David Sedláke1a30302019-07-10 13:49:38 +0200512 assert_int_equal(config, LYS_CONFIG_W);
David Sedlák5545f5d2019-07-11 11:55:16 +0200513 assert_int_equal(pos_enum.value, 25);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200514 assert_true(pos_enum.flags & LYS_SET_VALUE);
David Sedlák5545f5d2019-07-11 11:55:16 +0200515 assert_int_equal(val_enum.value, -5);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200516 assert_true(val_enum.flags & LYS_SET_VALUE);
David Sedlákcf5569a2019-07-11 13:31:34 +0200517 assert_int_equal(req_type.require_instance, 1);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200518 assert_true(req_type.flags &= LYS_SET_REQINST);
David Sedlákb7296dd2019-07-11 14:58:38 +0200519 assert_string_equal(range_type.range->arg, "5..10");
David Sedlákc3da3ef2019-07-19 12:56:08 +0200520 assert_true(range_type.flags & LYS_SET_RANGE);
David Sedlákc1771b12019-07-10 15:55:46 +0200521 assert_string_equal(err_msg, "error-msg");
David Sedlák2ce1be62019-07-10 16:15:09 +0200522 assert_string_equal(app_tag, "err-app-tag");
David Sedlákfd5b9c32019-07-12 15:33:13 +0200523 assert_string_equal(enum_type.enums->name, "yay");
David Sedlák438ae432019-07-11 15:36:54 +0200524 assert_string_equal(len_type.length->arg, "baf");
David Sedlákc3da3ef2019-07-19 12:56:08 +0200525 assert_true(len_type.flags & LYS_SET_LENGTH);
David Sedlákd3983112019-07-12 11:20:56 +0200526 assert_string_equal(patter_type.patterns->arg, "\x015pattern");
David Sedlákc3da3ef2019-07-19 12:56:08 +0200527 assert_true(patter_type.flags & LYS_SET_PATTERN);
David Sedlák2ce1be62019-07-10 16:15:09 +0200528 /* cleanup */
David Sedlák555c7202019-07-04 12:14:12 +0200529 lysp_ext_instance_free(st->ctx, exts);
David Sedlák32eee7b2019-07-09 12:38:44 +0200530 lysp_when_free(st->ctx, when_p);
David Sedlák986cb412019-07-04 13:10:11 +0200531 lysp_ext_free(st->ctx, ext_def);
David Sedlák5f8191e2019-07-08 16:35:52 +0200532 FREE_STRING(st->ctx, *if_features);
David Sedlákc1771b12019-07-10 15:55:46 +0200533 FREE_STRING(st->ctx, err_msg);
David Sedlák2ce1be62019-07-10 16:15:09 +0200534 FREE_STRING(st->ctx, app_tag);
David Sedláka5b1d382019-07-10 16:31:09 +0200535 FREE_STRING(st->ctx, units);
David Sedlákd3983112019-07-12 11:20:56 +0200536 FREE_STRING(st->ctx, patter_type.patterns->arg);
David Sedláke7084ce2019-07-10 16:44:15 +0200537 FREE_STRING(st->ctx, def);
David Sedlákb7296dd2019-07-11 14:58:38 +0200538 FREE_STRING(st->ctx, range_type.range->arg);
David Sedlák438ae432019-07-11 15:36:54 +0200539 FREE_STRING(st->ctx, len_type.length->arg);
David Sedlákfd5b9c32019-07-12 15:33:13 +0200540 FREE_STRING(st->ctx, enum_type.enums->name);
David Sedlákb7296dd2019-07-11 14:58:38 +0200541 FREE_STRING(st->ctx, value);
David Sedlák5f8191e2019-07-08 16:35:52 +0200542 LY_ARRAY_FREE(if_features);
David Sedlák555c7202019-07-04 12:14:12 +0200543 LY_ARRAY_FREE(exts);
David Sedlák986cb412019-07-04 13:10:11 +0200544 LY_ARRAY_FREE(ext_def);
David Sedlák555c7202019-07-04 12:14:12 +0200545 LY_ARRAY_FREE(attrs);
David Sedlákd3983112019-07-12 11:20:56 +0200546 LY_ARRAY_FREE(patter_type.patterns);
David Sedlákfd5b9c32019-07-12 15:33:13 +0200547 LY_ARRAY_FREE(enum_type.enums);
David Sedlák32eee7b2019-07-09 12:38:44 +0200548 free(when_p);
David Sedlákb7296dd2019-07-11 14:58:38 +0200549 free(range_type.range);
David Sedlák438ae432019-07-11 15:36:54 +0200550 free(len_type.length);
David Sedlák555c7202019-07-04 12:14:12 +0200551 attrs = NULL;
David Sedlák555c7202019-07-04 12:14:12 +0200552 st = reset_state(state);
553
554 /* test unique subelem */
555 const char *prefix_value;
556 struct yin_subelement subelems2[2] = {{YANG_PREFIX, &prefix_value, 0},
557 {YIN_TEXT, &value, YIN_SUBELEM_UNIQUE}};
558 data = "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
559 "<prefix value=\"inv_mod\" />"
560 "<text xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">wsefsdf</text>"
561 "<text xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">wsefsdf</text>"
562 "</module>";
David Sedlákda8ffa32019-07-08 14:17:10 +0200563 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix.value, &prefix.len, &name.value, &name.len);
564 yin_load_attributes(st->yin_ctx, &data, &attrs);
565 ret = yin_parse_content(st->yin_ctx, subelems2, 2, &data, YANG_MODULE, NULL, &exts);
David Sedlák555c7202019-07-04 12:14:12 +0200566 assert_int_equal(ret, LY_EVALID);
567 logbuf_assert("Redefinition of text element in module element. Line number 1.");
568 lydict_remove(st->ctx, prefix_value);
569 lydict_remove(st->ctx, value);
570 st = reset_state(state);
571 LY_ARRAY_FREE(attrs);
572 attrs = NULL;
573
574 /* test first subelem */
575 data = "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
576 "<prefix value=\"inv_mod\" />"
577 "<text xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">wsefsdf</text>"
578 "<text xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">wsefsdf</text>"
579 "</module>";
580 struct yin_subelement subelems3[2] = {{YANG_PREFIX, &prefix_value, 0},
581 {YIN_TEXT, &value, YIN_SUBELEM_FIRST}};
David Sedlákda8ffa32019-07-08 14:17:10 +0200582 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix.value, &prefix.len, &name.value, &name.len);
583 yin_load_attributes(st->yin_ctx, &data, &attrs);
584 ret = yin_parse_content(st->yin_ctx, subelems3, 2, &data, YANG_MODULE, NULL, &exts);
David Sedlák555c7202019-07-04 12:14:12 +0200585 assert_int_equal(ret, LY_EVALID);
586 logbuf_assert("Subelement text of module element must be defined as first subelement. Line number 1.");
587 lydict_remove(st->ctx, prefix_value);
588 st = reset_state(state);
589 LY_ARRAY_FREE(attrs);
590 attrs = NULL;
591
592 /* test mandatory subelem */
593 data = "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
594 "</module>";
595 struct yin_subelement subelems4[1] = {{YANG_PREFIX, &prefix_value, YIN_SUBELEM_MANDATORY}};
David Sedlákda8ffa32019-07-08 14:17:10 +0200596 lyxml_get_element(&st->yin_ctx->xml_ctx, &data, &prefix.value, &prefix.len, &name.value, &name.len);
597 yin_load_attributes(st->yin_ctx, &data, &attrs);
598 ret = yin_parse_content(st->yin_ctx, subelems4, 1, &data, YANG_MODULE, NULL, &exts);
David Sedlák555c7202019-07-04 12:14:12 +0200599 assert_int_equal(ret, LY_EVALID);
600 logbuf_assert("Missing mandatory subelement prefix of module element. Line number 1.");
601 LY_ARRAY_FREE(attrs);
602
603 st->finished_correctly = true;
604}
605
David Sedlák92147b02019-07-09 14:01:01 +0200606static void
David Sedlák4a650532019-07-10 11:55:18 +0200607test_validate_value(void **state)
608{
609 struct state *st = *state;
610 assert_int_equal(yin_validate_value(st->yin_ctx, Y_IDENTIF_ARG, "#invalid", 8), LY_EVALID);
611 logbuf_assert("Invalid identifier character '#'. Line number 1.");
612 assert_int_equal(yin_validate_value(st->yin_ctx, Y_STR_ARG, "", 0), LY_SUCCESS);
613 assert_int_equal(yin_validate_value(st->yin_ctx, Y_IDENTIF_ARG, "pre:b", 5), LY_EVALID);
614 assert_int_equal(yin_validate_value(st->yin_ctx, Y_PREF_IDENTIF_ARG, "pre:b", 5), LY_SUCCESS);
615 assert_int_equal(yin_validate_value(st->yin_ctx, Y_PREF_IDENTIF_ARG, "pre:pre:b", 9), LY_EVALID);
616
617 st->finished_correctly = true;
618}
619
David Sedlák32488102019-07-15 17:44:10 +0200620static int
621setup_element_test(void **state)
622{
David Sedlák8e7bda82019-07-16 17:57:50 +0200623 struct state *st = *state;
David Sedlák32488102019-07-15 17:44:10 +0200624
625#if ENABLE_LOGGER_CHECKING
626 /* setup logger */
627 ly_set_log_clb(logger, 1);
628#endif
629
630 /* reset logbuf */
631 logbuf[0] = '\0';
David Sedlák32488102019-07-15 17:44:10 +0200632
633 /* allocate parser context */
634 st->yin_ctx = calloc(1, sizeof(*st->yin_ctx));
635 st->yin_ctx->xml_ctx.ctx = st->ctx;
636 st->yin_ctx->xml_ctx.line = 1;
637
638 return EXIT_SUCCESS;
639}
640
641static int
642teardown_element_test(void **state)
643{
644 struct state *st = *(struct state **)state;
645
646#if ENABLE_LOGGER_CHECKING
647 /* teardown logger */
648 if (!st->finished_correctly && logbuf[0] != '\0') {
649 fprintf(stderr, "%s\n", logbuf);
650 }
651#endif
652
653 lyxml_context_clear(&st->yin_ctx->xml_ctx);
David Sedlák32488102019-07-15 17:44:10 +0200654 free(st->yin_ctx);
David Sedlák32488102019-07-15 17:44:10 +0200655
656 return EXIT_SUCCESS;
657}
658
659#define ELEMENT_WRAPPER_START "<module xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
660#define ELEMENT_WRAPPER_END "</module>"
661
662/* helper function to simplify unit test of each element using parse_content function */
663LY_ERR
664test_element_helper(struct state *st, const char **data, void *dest, const char **text,
665 struct lysp_ext_instance **exts, bool valid)
666{
667 struct yin_arg_record *attrs = NULL;
668 struct sized_string name, prefix;
669 LY_ERR ret = LY_SUCCESS;
670 struct yin_subelement subelems[71] = {
671 {YANG_ACTION, dest, 0},
672 {YANG_ANYDATA, dest, 0},
673 {YANG_ANYXML, dest, 0},
674 {YANG_ARGUMENT,dest, 0},
675 {YANG_AUGMENT, dest, 0},
676 {YANG_BASE, dest, 0},
677 {YANG_BELONGS_TO, dest, 0},
678 {YANG_BIT, dest, 0},
679 {YANG_CASE, dest, 0},
680 {YANG_CHOICE, dest, 0},
681 {YANG_CONFIG, dest, 0},
682 {YANG_CONTACT, dest, 0},
683 {YANG_CONTAINER, dest, 0},
David Sedlákc3da3ef2019-07-19 12:56:08 +0200684 {YANG_DEFAULT, dest, YIN_SUBELEM_UNIQUE},
David Sedlák32488102019-07-15 17:44:10 +0200685 {YANG_DESCRIPTION, dest, 0},
686 {YANG_DEVIATE, dest, 0},
687 {YANG_DEVIATION, dest, 0},
688 {YANG_ENUM, dest, 0},
689 {YANG_ERROR_APP_TAG, dest, 0},
690 {YANG_ERROR_MESSAGE, dest, 0},
691 {YANG_EXTENSION, dest, 0},
692 {YANG_FEATURE, dest, 0},
693 {YANG_FRACTION_DIGITS, dest, 0},
694 {YANG_GROUPING, dest, 0},
695 {YANG_IDENTITY, dest, 0},
696 {YANG_IF_FEATURE, dest, 0},
697 {YANG_IMPORT, dest, 0},
698 {YANG_INCLUDE, dest, 0},
699 {YANG_INPUT, dest, 0},
700 {YANG_KEY, dest, 0},
701 {YANG_LEAF, dest, 0},
702 {YANG_LEAF_LIST, dest, 0},
703 {YANG_LENGTH, dest, 0},
704 {YANG_LIST, dest, 0},
705 {YANG_MANDATORY, dest, 0},
706 {YANG_MAX_ELEMENTS, dest, 0},
707 {YANG_MIN_ELEMENTS, dest, 0},
708 {YANG_MODIFIER, dest, 0},
709 {YANG_MODULE, dest, 0},
710 {YANG_MUST, dest, 0},
711 {YANG_NAMESPACE, dest, 0},
712 {YANG_NOTIFICATION, dest, 0},
713 {YANG_ORDERED_BY, dest, 0},
714 {YANG_ORGANIZATION, dest, 0},
715 {YANG_OUTPUT, dest, 0},
716 {YANG_PATH, dest, 0},
717 {YANG_PATTERN, dest, 0},
David Sedlák32488102019-07-15 17:44:10 +0200718 {YANG_PREFIX, dest, 0},
719 {YANG_PRESENCE, dest, 0},
720 {YANG_RANGE, dest, 0},
721 {YANG_REFERENCE, dest, 0},
722 {YANG_REFINE, dest, 0},
723 {YANG_REQUIRE_INSTANCE, dest, 0},
724 {YANG_REVISION, dest, 0},
725 {YANG_REVISION_DATE, dest, 0},
726 {YANG_RPC, dest, 0},
727 {YANG_STATUS, dest, 0},
728 {YANG_SUBMODULE, dest, 0},
729 {YANG_TYPE, dest, 0},
730 {YANG_TYPEDEF, dest, 0},
731 {YANG_UNIQUE, dest, 0},
732 {YANG_UNITS, dest, 0},
733 {YANG_USES, dest, 0},
David Sedlák374d2b32019-07-17 15:06:55 +0200734 {YANG_POSITION, dest, 0},
David Sedlák32488102019-07-15 17:44:10 +0200735 {YANG_VALUE, dest, 0},
736 {YANG_WHEN, dest, 0},
737 {YANG_YANG_VERSION, dest, 0},
738 {YANG_YIN_ELEMENT, dest, 0},
739 {YANG_CUSTOM, dest, 0},
740 {YIN_TEXT, dest, 0},
741 {YIN_VALUE, dest, 0}
742 };
743 LY_CHECK_RET(lyxml_get_element(&st->yin_ctx->xml_ctx, data, &prefix.value, &prefix.len, &name.value, &name.len));\
744 LY_CHECK_RET(yin_load_attributes(st->yin_ctx, data, &attrs));\
David Sedlák8e7bda82019-07-16 17:57:50 +0200745 ret = yin_parse_content(st->yin_ctx, subelems, 71, data, yin_match_keyword(st->yin_ctx, name.value, name.len, prefix.value, prefix.len, YANG_NONE), text, exts);
David Sedlák32488102019-07-15 17:44:10 +0200746 LY_ARRAY_FREE(attrs);
747 if (valid) {
748 assert_int_equal(st->yin_ctx->xml_ctx.status, LYXML_END);
749 }
750 /* reset status */
751 st->yin_ctx->xml_ctx.status = LYXML_ELEMENT;
752 return ret;
753}
754
755static void
756test_enum_bit_elem(void **state)
757{
758 /* yin_parse_enum_bit is function that is being mainly tested by this test */
759 struct state *st = *state;
760 struct lysp_type type = {};
761 const char *data;
762 data = ELEMENT_WRAPPER_START
763 "<enum name=\"enum-name\">"
764 "<if-feature name=\"feature\" />"
765 "<value value=\"55\" />"
766 "<status value=\"deprecated\" />"
767 "<description><text>desc...</text></description>"
768 "<reference><text>ref...</text></reference>"
769 "</enum>"
770 ELEMENT_WRAPPER_END;
771 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
772 assert_string_equal(*type.enums->iffeatures, "feature");
773 assert_int_equal(type.enums->value, 55);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200774 assert_true((type.enums->flags & LYS_STATUS_DEPRC) && (type.enums->flags & LYS_SET_VALUE));
David Sedlák32488102019-07-15 17:44:10 +0200775 assert_string_equal(type.enums->dsc, "desc...");
776 assert_string_equal(type.enums->ref, "ref...");
777 lysp_type_free(st->ctx, &type);
778 memset(&type, 0, sizeof type);
779
780 /* todo bit element test */
781 st->finished_correctly = true;
782}
783
784static void
785test_meta_elem(void **state)
786{
787 struct state *st = *state;
788 char *value = NULL;
789 const char *data;
790
791 /* organization element */
792 data = ELEMENT_WRAPPER_START
793 "<organization><text>organization...</text></organization>"
794 ELEMENT_WRAPPER_END;
795 assert_int_equal(test_element_helper(st, &data, &value, NULL, NULL, true), LY_SUCCESS);
796 assert_string_equal(value, "organization...");
797 FREE_STRING(st->ctx, value);
798 value = NULL;
799 /* contact element */
800 data = ELEMENT_WRAPPER_START
801 "<contact><text>contact...</text></contact>"
802 ELEMENT_WRAPPER_END;
803 assert_int_equal(test_element_helper(st, &data, &value, NULL, NULL, true), LY_SUCCESS);
804 assert_string_equal(value, "contact...");
805 FREE_STRING(st->ctx, value);
806 value = NULL;
807 /* description element */
808 data = ELEMENT_WRAPPER_START
809 "<description><text>description...</text></description>"
810 ELEMENT_WRAPPER_END;
811 assert_int_equal(test_element_helper(st, &data, &value, NULL, NULL, true), LY_SUCCESS);
812 assert_string_equal(value, "description...");
813 FREE_STRING(st->ctx, value);
814 value = NULL;
815 /* reference element */
816 data = ELEMENT_WRAPPER_START
817 "<reference><text>reference...</text></reference>"
818 ELEMENT_WRAPPER_END;
819 assert_int_equal(test_element_helper(st, &data, &value, NULL, NULL, true), LY_SUCCESS);
820 assert_string_equal(value, "reference...");
821 FREE_STRING(st->ctx, value);
822 value = NULL;
823
824 /* missing text subelement */
825 data = ELEMENT_WRAPPER_START
826 "<reference>reference...</reference>"
827 ELEMENT_WRAPPER_END;
828 assert_int_equal(test_element_helper(st, &data, &value, NULL, NULL, false), LY_EVALID);
829 logbuf_assert("Missing mandatory subelement text of reference element. Line number 1.");
830
831 st->finished_correctly = true;
832}
833
834static void
835test_import_elem(void **state)
836{
837 struct state *st = *state;
838 const char *data;
839 struct lys_module *lys_mod = calloc(1, sizeof *lys_mod);
840 struct lysp_module *lysp_mod = calloc(1, sizeof *lysp_mod);
841 lys_mod->ctx = st->ctx;
842 lysp_mod->mod = lys_mod;
843
844 /* max subelems */
845 data = ELEMENT_WRAPPER_START
846 "<import module=\"a\">"
847 "<prefix value=\"a_mod\"/>"
848 "<revision-date date=\"2015-01-01\"></revision-date>"
849 "<description><text>import description</text></description>"
850 "<reference><text>import reference</text></reference>"
851 "</import>"
852 ELEMENT_WRAPPER_END;
853 assert_int_equal(test_element_helper(st, &data, lysp_mod, NULL, NULL, true), LY_SUCCESS);
854 assert_string_equal(lysp_mod->imports->name, "a");
855 assert_string_equal(lysp_mod->imports->prefix, "a_mod");
856 assert_string_equal(lysp_mod->imports->rev, "2015-01-01");
857 assert_string_equal(lysp_mod->imports->dsc, "import description");
858 assert_string_equal(lysp_mod->imports->ref, "import reference");
859 lysp_module_free(lysp_mod);
860 lys_module_free(lys_mod, NULL);
861
862 /* min subelems */
863 lys_mod = calloc(1, sizeof *lys_mod);
864 lysp_mod = calloc(1, sizeof *lysp_mod);
865 lys_mod->ctx = st->ctx;
866 lysp_mod->mod = lys_mod;
867 data = ELEMENT_WRAPPER_START
868 "<import module=\"a\">"
869 "<prefix value=\"a_mod\"/>"
870 "</import>"
871 ELEMENT_WRAPPER_END;
872 assert_int_equal(test_element_helper(st, &data, lysp_mod, NULL, NULL, true), LY_SUCCESS);
873 assert_string_equal(lysp_mod->imports->prefix, "a_mod");
874 lysp_module_free(lysp_mod);
875 lys_module_free(lys_mod, NULL);
876
877 /* invalid (missing prefix) */
878 lys_mod = calloc(1, sizeof *lys_mod);
879 lysp_mod = calloc(1, sizeof *lysp_mod);
880 lys_mod->ctx = st->ctx;
881 lysp_mod->mod = lys_mod;
882 data = ELEMENT_WRAPPER_START "<import module=\"a\">""</import>" ELEMENT_WRAPPER_END;
883 assert_int_equal(test_element_helper(st, &data, lysp_mod, NULL, NULL, false), LY_EVALID);
884 logbuf_assert("Missing mandatory subelement prefix of import element. Line number 1.");
885 lysp_module_free(lysp_mod);
886 lys_module_free(lys_mod, NULL);
887
888 /* invalid reused prefix */
889 lys_mod = calloc(1, sizeof *lys_mod);
890 lysp_mod = calloc(1, sizeof *lysp_mod);
891 lys_mod->ctx = st->ctx;
892 lysp_mod->mod = lys_mod;
893 data = ELEMENT_WRAPPER_START
894 "<import module=\"a\">"
895 "<prefix value=\"a_mod\"/>"
896 "</import>"
897 "<import module=\"a\">"
898 "<prefix value=\"a_mod\"/>"
899 "</import>"
900 ELEMENT_WRAPPER_END;
901 assert_int_equal(test_element_helper(st, &data, lysp_mod, NULL, NULL, false), LY_EVALID);
902 logbuf_assert("Prefix \"a_mod\" already used to import \"a\" module. Line number 1.");
903 lysp_module_free(lysp_mod);
904 lys_module_free(lys_mod, NULL);
905
906 st->finished_correctly = true;
907}
908
909static void
910test_status_elem(void **state)
911{
912 struct state *st = *state;
913 const char *data;
914 uint16_t flags = 0;
915
916 /* test valid values */
917 data = ELEMENT_WRAPPER_START "<status value=\"current\" />" ELEMENT_WRAPPER_END;
918 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200919 assert_true(flags & LYS_STATUS_CURR);
David Sedlák32488102019-07-15 17:44:10 +0200920
921 data = ELEMENT_WRAPPER_START "<status value=\"deprecated\" />" ELEMENT_WRAPPER_END;
922 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200923 assert_true(flags & LYS_STATUS_DEPRC);
David Sedlák32488102019-07-15 17:44:10 +0200924
925 data = ELEMENT_WRAPPER_START "<status value=\"obsolete\"></status>" ELEMENT_WRAPPER_END;
926 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200927 assert_true(flags & LYS_STATUS_OBSLT);
David Sedlák32488102019-07-15 17:44:10 +0200928
929 /* test invalid value */
930 data = ELEMENT_WRAPPER_START "<status value=\"invalid\"></status>" ELEMENT_WRAPPER_END;
931 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, false), LY_EVALID);
932 logbuf_assert("Invalid value \"invalid\" of \"status\". Line number 1.");
933 st->finished_correctly = true;
934}
935
936static void
937test_ext_elem(void **state)
938{
939 struct state *st = *state;
940 const char *data;
941 struct lysp_ext *ext = NULL;
942
943 /* max subelems */
944 data = ELEMENT_WRAPPER_START
945 "<extension name=\"ext_name\">"
946 "<argument name=\"arg\"></argument>"
947 "<status value=\"current\"/>"
948 "<description><text>ext_desc</text></description>"
949 "<reference><text>ext_ref</text></reference>"
950 "</extension>"
951 ELEMENT_WRAPPER_END;
952 assert_int_equal(test_element_helper(st, &data, &ext, NULL, NULL, true), LY_SUCCESS);
953 assert_string_equal(ext->name, "ext_name");
954 assert_string_equal(ext->argument, "arg");
David Sedlákc3da3ef2019-07-19 12:56:08 +0200955 assert_true(ext->flags & LYS_STATUS_CURR);
David Sedlák32488102019-07-15 17:44:10 +0200956 assert_string_equal(ext->dsc, "ext_desc");
957 assert_string_equal(ext->ref, "ext_ref");
958 lysp_ext_free(st->ctx, ext);
959 LY_ARRAY_FREE(ext);
960 ext = NULL;
961
962 /* min subelems */
963 data = ELEMENT_WRAPPER_START "<extension name=\"ext_name\"></extension>" ELEMENT_WRAPPER_END;
964 assert_int_equal(test_element_helper(st, &data, &ext, NULL, NULL, true), LY_SUCCESS);
965 assert_string_equal(ext->name, "ext_name");
966 lysp_ext_free(st->ctx, ext);
967 LY_ARRAY_FREE(ext);
968 ext = NULL;
969
970 st->finished_correctly = true;
971}
972
973static void
974test_yin_element_elem(void **state)
975{
976 struct state *st = *state;
977 const char *data;
978 uint16_t flags = 0;
979
980 data = ELEMENT_WRAPPER_START "<yin-element value=\"true\" />" ELEMENT_WRAPPER_END;
981 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200982 assert_true(flags & LYS_YINELEM_TRUE);
David Sedlák32488102019-07-15 17:44:10 +0200983
984 data = ELEMENT_WRAPPER_START "<yin-element value=\"false\" />" ELEMENT_WRAPPER_END;
985 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200986 assert_true(flags & LYS_YINELEM_TRUE);
David Sedlák32488102019-07-15 17:44:10 +0200987
988 data = ELEMENT_WRAPPER_START "<yin-element value=\"invalid\" />" ELEMENT_WRAPPER_END;
989 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, false), LY_EVALID);
David Sedlákc3da3ef2019-07-19 12:56:08 +0200990 assert_true(flags & LYS_YINELEM_TRUE);
David Sedlák32488102019-07-15 17:44:10 +0200991 logbuf_assert("Invalid value \"invalid\" of \"yin-element\". Line number 1.");
992 st->finished_correctly = true;
993}
994
995static void
996test_yangversion_elem(void **state)
997{
998 struct state *st = *state;
999 const char *data;
1000 uint8_t version = 0;
1001
1002 /* valid values */
1003 data = ELEMENT_WRAPPER_START "<yang-version value=\"1.0\" />" ELEMENT_WRAPPER_END;
1004 assert_int_equal(test_element_helper(st, &data, &version, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001005 assert_true(version & LYS_VERSION_1_0);
David Sedlák32488102019-07-15 17:44:10 +02001006 assert_int_equal(st->yin_ctx->mod_version, LYS_VERSION_1_0);
1007
1008 data = ELEMENT_WRAPPER_START "<yang-version value=\"1.1\" />" ELEMENT_WRAPPER_END;
1009 assert_int_equal(test_element_helper(st, &data, &version, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001010 assert_true(version & LYS_VERSION_1_1);
David Sedlák32488102019-07-15 17:44:10 +02001011 assert_int_equal(st->yin_ctx->mod_version, LYS_VERSION_1_1);
1012
1013 /* invalid value */
1014 data = ELEMENT_WRAPPER_START "<yang-version value=\"version\" />" ELEMENT_WRAPPER_END;
1015 assert_int_equal(test_element_helper(st, &data, &version, NULL, NULL, false), LY_EVALID);
1016 logbuf_assert("Invalid value \"version\" of \"yang-version\". Line number 1.");
1017
1018 st->finished_correctly = true;
1019}
1020
1021static void
1022test_mandatory_elem(void **state)
1023{
1024 struct state *st = *state;
1025 const char *data;
1026 uint16_t man = 0;
1027
1028 /* valid values */
1029 data = ELEMENT_WRAPPER_START "<mandatory value=\"true\" />" ELEMENT_WRAPPER_END;
1030 assert_int_equal(test_element_helper(st, &data, &man, NULL, NULL, true), LY_SUCCESS);
1031 assert_int_equal(man, LYS_MAND_TRUE);
1032 man = 0;
1033
1034 data = ELEMENT_WRAPPER_START "<mandatory value=\"false\" />" ELEMENT_WRAPPER_END;
1035 assert_int_equal(test_element_helper(st, &data, &man, NULL, NULL, true), LY_SUCCESS);
1036 assert_int_equal(man, LYS_MAND_FALSE);
1037
1038 data = ELEMENT_WRAPPER_START "<mandatory value=\"invalid\" />" ELEMENT_WRAPPER_END;
1039 assert_int_equal(test_element_helper(st, &data, &man, NULL, NULL, false), LY_EVALID);
1040 logbuf_assert("Invalid value \"invalid\" of \"mandatory\". Line number 1.");
1041
1042 st->finished_correctly = true;
1043}
1044
David Sedlák8e7bda82019-07-16 17:57:50 +02001045static void
1046test_argument_elem(void **state)
1047{
1048 struct state *st = *state;
1049 const char *data;
1050 uint16_t flags = 0;
1051 const char *arg;
1052 struct yin_argument_meta arg_meta = {&flags, &arg};
1053 /* max subelems */
1054 data = ELEMENT_WRAPPER_START
1055 "<argument name=\"arg-name\">"
1056 "<yin-element value=\"true\" />"
1057 "</argument>"
1058 ELEMENT_WRAPPER_END;
1059 assert_int_equal(test_element_helper(st, &data, &arg_meta, NULL, NULL, true), LY_SUCCESS);
1060 assert_string_equal(arg, "arg-name");
David Sedlákc3da3ef2019-07-19 12:56:08 +02001061 assert_true(flags & LYS_YINELEM_TRUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001062 flags = 0;
1063 FREE_STRING(st->ctx, arg);
1064 arg = NULL;
1065
1066 /* min subelems */
1067 data = ELEMENT_WRAPPER_START
1068 "<argument name=\"arg\">"
1069 "</argument>"
1070 ELEMENT_WRAPPER_END;
1071 assert_int_equal(test_element_helper(st, &data, &arg_meta, NULL, NULL, true), LY_SUCCESS);
1072 assert_string_equal(arg, "arg");
1073 assert_true(flags == 0);
1074 FREE_STRING(st->ctx, arg);
1075
1076 st->finished_correctly = true;
1077}
1078
1079static void
1080test_base_elem(void **state)
1081{
1082 struct state *st = *state;
1083 const char *data;
1084 const char **bases = NULL;
1085 struct lysp_type type = {};
1086
1087 /* as identity subelement */
1088 data = "<identity xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
1089 "<base name=\"base-name\"/>"
1090 "</identity>";
1091 assert_int_equal(test_element_helper(st, &data, &bases, NULL, NULL, true), LY_SUCCESS);
1092 assert_string_equal(*bases, "base-name");
1093 FREE_STRING(st->ctx, *bases);
1094 LY_ARRAY_FREE(bases);
1095
1096 /* as type subelement */
1097 data = "<type xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\">"
1098 "<base name=\"base-name\"/>"
1099 "</type>";
1100 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1101 assert_string_equal(*type.bases, "base-name");
David Sedlákc3da3ef2019-07-19 12:56:08 +02001102 assert_true(type.flags & LYS_SET_BASE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001103 FREE_STRING(st->ctx, *type.bases);
1104 LY_ARRAY_FREE(type.bases);
1105
1106 st->finished_correctly = true;
1107}
1108
1109static void
1110test_belongsto_elem(void **state)
1111{
1112 struct state *st = *state;
1113 const char *data;
1114 struct lysp_submodule submod;
1115
1116 data = ELEMENT_WRAPPER_START
1117 "<belongs-to module=\"module-name\"><prefix value=\"pref\"/></belongs-to>"
1118 ELEMENT_WRAPPER_END;
1119 assert_int_equal(test_element_helper(st, &data, &submod, NULL, NULL, true), LY_SUCCESS);
1120 assert_string_equal(submod.belongsto, "module-name");
1121 assert_string_equal(submod.prefix, "pref");
1122 FREE_STRING(st->ctx, submod.belongsto);
1123 FREE_STRING(st->ctx, submod.prefix);
1124
1125 data = ELEMENT_WRAPPER_START "<belongs-to module=\"module-name\"></belongs-to>" ELEMENT_WRAPPER_END;
1126 assert_int_equal(test_element_helper(st, &data, &submod, NULL, NULL, false), LY_EVALID);
1127 logbuf_assert("Missing mandatory subelement prefix of belongs-to element. Line number 1.");
1128 FREE_STRING(st->ctx, submod.belongsto);
1129
1130 st->finished_correctly = true;
1131}
1132
1133static void
1134test_config_elem(void **state)
1135{
1136 struct state *st = *state;
1137 const char *data;
1138 uint16_t flags = 0;
1139
1140 data = ELEMENT_WRAPPER_START "<config value=\"true\"/>" ELEMENT_WRAPPER_END;
1141 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001142 assert_true(flags & LYS_CONFIG_W);
David Sedlák8e7bda82019-07-16 17:57:50 +02001143 flags = 0;
1144
1145 data = ELEMENT_WRAPPER_START "<config value=\"false\"/>" ELEMENT_WRAPPER_END;
1146 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001147 assert_true(flags & LYS_CONFIG_R);
David Sedlák8e7bda82019-07-16 17:57:50 +02001148 flags = 0;
1149
1150 data = ELEMENT_WRAPPER_START "<config value=\"invalid\"/>" ELEMENT_WRAPPER_END;
1151 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, false), LY_EVALID);
1152 logbuf_assert("Invalid value \"invalid\" of \"config\". Line number 1.");
1153
1154 st->finished_correctly = true;
1155}
1156
1157static void
1158test_default_elem(void **state)
1159{
1160 struct state *st = *state;
1161 const char *data;
1162 const char *val = NULL;
1163
1164 data = ELEMENT_WRAPPER_START "<default value=\"defaul-value\"/>" ELEMENT_WRAPPER_END;
1165 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
1166 assert_string_equal(val, "defaul-value");
1167 FREE_STRING(st->ctx, val);
1168 val = NULL;
1169
1170 data = ELEMENT_WRAPPER_START "<default/>" ELEMENT_WRAPPER_END;
1171 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, false), LY_EVALID);
1172 logbuf_assert("Missing mandatory attribute value of default element. Line number 1.");
1173
1174 st->finished_correctly = true;
1175}
1176
1177static void
1178test_err_app_tag_elem(void **state)
1179{
1180 struct state *st = *state;
1181 const char *data;
1182 const char *val = NULL;
1183
1184 data = ELEMENT_WRAPPER_START "<error-app-tag value=\"val\"/>" ELEMENT_WRAPPER_END;
1185 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
1186 assert_string_equal(val, "val");
1187 FREE_STRING(st->ctx, val);
1188 val = NULL;
1189
1190 data = ELEMENT_WRAPPER_START "<error-app-tag/>" ELEMENT_WRAPPER_END;
1191 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, false), LY_EVALID);
1192 logbuf_assert("Missing mandatory attribute value of error-app-tag element. Line number 1.");
1193
1194 st->finished_correctly = true;
1195}
1196
1197static void
1198test_err_msg_elem(void **state)
1199{
1200 struct state *st = *state;
1201 const char *data;
1202 const char *val = NULL;
1203
1204 data = ELEMENT_WRAPPER_START "<error-message><value>val</value></error-message>" ELEMENT_WRAPPER_END;
1205 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
1206 assert_string_equal(val, "val");
1207 FREE_STRING(st->ctx, val);
1208
1209 data = ELEMENT_WRAPPER_START "<error-message></error-message>" ELEMENT_WRAPPER_END;
1210 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, false), LY_EVALID);
1211 logbuf_assert("Missing mandatory subelement value of error-message element. Line number 1.");
1212
1213 st->finished_correctly = true;
1214}
1215
1216static void
1217test_fracdigits_elem(void **state)
1218{
1219 struct state *st = *state;
1220 const char *data;
1221 struct lysp_type type = {};
1222
1223 /* valid value */
1224 data = ELEMENT_WRAPPER_START "<fraction-digits value=\"10\"></fraction-digits>" ELEMENT_WRAPPER_END;
1225 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1226 assert_int_equal(type.fraction_digits, 10);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001227 assert_true(type.flags & LYS_SET_FRDIGITS);
David Sedlák8e7bda82019-07-16 17:57:50 +02001228
1229 /* invalid values */
1230 data = ELEMENT_WRAPPER_START "<fraction-digits value=\"-1\"></fraction-digits>" ELEMENT_WRAPPER_END;
1231 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1232 logbuf_assert("Invalid value \"-1\" of \"fraction-digits\". Line number 1.");
1233
1234 data = ELEMENT_WRAPPER_START "<fraction-digits value=\"02\"></fraction-digits>" ELEMENT_WRAPPER_END;
1235 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1236 logbuf_assert("Invalid value \"02\" of \"fraction-digits\". Line number 1.");
1237
1238 data = ELEMENT_WRAPPER_START "<fraction-digits value=\"1p\"></fraction-digits>" ELEMENT_WRAPPER_END;
1239 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1240 logbuf_assert("Invalid value \"1p\" of \"fraction-digits\". Line number 1.");
1241
1242 data = ELEMENT_WRAPPER_START "<fraction-digits value=\"19\"></fraction-digits>" ELEMENT_WRAPPER_END;
1243 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1244 logbuf_assert("Invalid value \"19\" of \"fraction-digits\". Line number 1.");
1245
1246 data = ELEMENT_WRAPPER_START "<fraction-digits value=\"999999999999999999\"></fraction-digits>" ELEMENT_WRAPPER_END;
1247 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1248 logbuf_assert("Invalid value \"999999999999999999\" of \"fraction-digits\". Line number 1.");
1249
1250 st->finished_correctly = true;
1251}
1252
1253static void
1254test_iffeature_elem(void **state)
1255{
1256 struct state *st = *state;
1257 const char *data;
1258 const char **iffeatures = NULL;
1259
1260 data = ELEMENT_WRAPPER_START "<if-feature name=\"local-storage\"></if-feature>" ELEMENT_WRAPPER_END;
1261 assert_int_equal(test_element_helper(st, &data, &iffeatures, NULL, NULL, true), LY_SUCCESS);
1262 assert_string_equal(*iffeatures, "local-storage");
1263 FREE_STRING(st->ctx, *iffeatures);
1264 LY_ARRAY_FREE(iffeatures);
1265 iffeatures = NULL;
1266
1267 data = ELEMENT_WRAPPER_START "<if-feature/>" ELEMENT_WRAPPER_END;
1268 assert_int_equal(test_element_helper(st, &data, &iffeatures, NULL, NULL, false), LY_EVALID);
1269 logbuf_assert("Missing mandatory attribute name of if-feature element. Line number 1.");
1270 LY_ARRAY_FREE(iffeatures);
1271 iffeatures = NULL;
1272
1273 st->finished_correctly = true;
1274}
1275
1276static void
1277test_length_elem(void **state)
1278{
1279 struct state *st = *state;
1280 const char *data;
1281 struct lysp_type type = {};
1282
1283 /* max subelems */
1284 data = ELEMENT_WRAPPER_START
1285 "<length value=\"length-str\">"
1286 "<error-message><value>err-msg</value></error-message>"
1287 "<error-app-tag value=\"err-app-tag\"/>"
1288 "<description><text>desc</text></description>"
1289 "<reference><text>ref</text></reference>"
1290 "</length>"
1291 ELEMENT_WRAPPER_END;
1292 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1293 assert_string_equal(type.length->arg, "length-str");
1294 assert_string_equal(type.length->emsg, "err-msg");
1295 assert_string_equal(type.length->eapptag, "err-app-tag");
1296 assert_string_equal(type.length->dsc, "desc");
1297 assert_string_equal(type.length->ref, "ref");
David Sedlákc3da3ef2019-07-19 12:56:08 +02001298 assert_true(type.flags & LYS_SET_LENGTH);
David Sedlák8e7bda82019-07-16 17:57:50 +02001299 lysp_type_free(st->ctx, &type);
1300 memset(&type, 0, sizeof(type));
1301
1302 /* min subelems */
1303 data = ELEMENT_WRAPPER_START
1304 "<length value=\"length-str\">"
1305 "</length>"
1306 ELEMENT_WRAPPER_END;
1307 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1308 assert_string_equal(type.length->arg, "length-str");
1309 lysp_type_free(st->ctx, &type);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001310 assert_true(type.flags & LYS_SET_LENGTH);
David Sedlák8e7bda82019-07-16 17:57:50 +02001311 memset(&type, 0, sizeof(type));
1312
1313 data = ELEMENT_WRAPPER_START "<length></length>" ELEMENT_WRAPPER_END;
1314 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1315 logbuf_assert("Missing mandatory attribute value of length element. Line number 1.");
1316 lysp_type_free(st->ctx, &type);
1317 memset(&type, 0, sizeof(type));
1318
1319 st->finished_correctly = true;
1320}
1321
1322static void
1323test_modifier_elem(void **state)
1324{
1325 struct state *st = *state;
1326 const char *data;
1327 const char *pat = lydict_insert(st->ctx, "\006pattern", 8);
1328
1329 data = ELEMENT_WRAPPER_START "<modifier value=\"invert-match\" />" ELEMENT_WRAPPER_END;
1330 assert_int_equal(test_element_helper(st, &data, &pat, NULL, NULL, true), LY_SUCCESS);
1331 assert_string_equal(pat, "\x015pattern");
1332 FREE_STRING(st->ctx, pat);
1333
1334 pat = lydict_insert(st->ctx, "\006pattern", 8);
1335 data = ELEMENT_WRAPPER_START "<modifier value=\"invert\" />" ELEMENT_WRAPPER_END;
1336 assert_int_equal(test_element_helper(st, &data, &pat, NULL, NULL, false), LY_EVALID);
1337 logbuf_assert("Invalid value \"invert\" of \"modifier\". Line number 1.");
1338 FREE_STRING(st->ctx, pat);
1339
1340 st->finished_correctly = true;
1341}
1342
1343static void
1344test_namespace_elem(void **state)
1345{
1346 struct state *st = *state;
1347 const char *data;
1348 const char *ns;
1349
1350 data = ELEMENT_WRAPPER_START "<namespace uri=\"ns\"/>" ELEMENT_WRAPPER_END;
1351 assert_int_equal(test_element_helper(st, &data, &ns, NULL, NULL, true), LY_SUCCESS);
1352 assert_string_equal(ns, "ns");
1353 FREE_STRING(st->ctx, ns);
1354
1355 data = ELEMENT_WRAPPER_START "<namespace/>" ELEMENT_WRAPPER_END;
1356 assert_int_equal(test_element_helper(st, &data, &ns, NULL, NULL, false), LY_EVALID);
1357 logbuf_assert("Missing mandatory attribute uri of namespace element. Line number 1.");
1358
1359 st->finished_correctly = true;
1360}
1361
1362static void
1363test_path_elem(void **state)
1364{
1365 struct state *st = *state;
1366 const char *data;
1367 struct lysp_type type = {};
1368
1369 data = ELEMENT_WRAPPER_START "<path value=\"path-val\"/>" ELEMENT_WRAPPER_END;
1370 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1371 assert_string_equal("path-val", type.path);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001372 assert_true(type.flags & LYS_SET_PATH);
David Sedlák8e7bda82019-07-16 17:57:50 +02001373 lysp_type_free(st->ctx, &type);
1374
1375 st->finished_correctly = true;
1376}
1377
1378static void
1379test_pattern_elem(void **state)
1380{
1381 struct state *st = *state;
1382 const char *data;
1383 struct lysp_type type = {};
1384
1385 /* max subelems */
1386 data = ELEMENT_WRAPPER_START
1387 "<pattern value=\"super_pattern\">"
1388 "<modifier value=\"invert-match\"/>"
1389 "<error-message><value>err-msg-value</value></error-message>"
1390 "<error-app-tag value=\"err-app-tag-value\"/>"
1391 "<description><text>pattern-desc</text></description>"
1392 "<reference><text>pattern-ref</text></reference>"
1393 "</pattern>"
1394 ELEMENT_WRAPPER_END;
1395 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001396 assert_true(type.flags & LYS_SET_PATTERN);
David Sedlák8e7bda82019-07-16 17:57:50 +02001397 assert_string_equal(type.patterns->arg, "\x015super_pattern");
1398 assert_string_equal(type.patterns->dsc, "pattern-desc");
1399 assert_string_equal(type.patterns->eapptag, "err-app-tag-value");
1400 assert_string_equal(type.patterns->emsg, "err-msg-value");
1401 assert_string_equal(type.patterns->dsc, "pattern-desc");
1402 assert_string_equal(type.patterns->ref, "pattern-ref");
1403 lysp_type_free(st->ctx, &type);
1404 memset(&type, 0, sizeof(type));
1405
1406 /* min subelems */
1407 data = ELEMENT_WRAPPER_START "<pattern value=\"pattern\"> </pattern>" ELEMENT_WRAPPER_END;
1408 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1409 assert_string_equal(type.patterns->arg, "\x006pattern");
1410 lysp_type_free(st->ctx, &type);
1411 memset(&type, 0, sizeof(type));
1412
1413 st->finished_correctly = true;
1414}
1415
1416static void
1417test_value_position_elem(void **state)
1418{
1419 struct state *st = *state;
1420 const char *data;
1421 struct lysp_type_enum en = {};
1422
1423 /* valid values */
1424 data = ELEMENT_WRAPPER_START "<value value=\"55\" />" ELEMENT_WRAPPER_END;
1425 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, true), LY_SUCCESS);
1426 assert_int_equal(en.value, 55);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001427 assert_true(en.flags & LYS_SET_VALUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001428 memset(&en, 0, sizeof(en));
1429
1430 data = ELEMENT_WRAPPER_START "<value value=\"-55\"/>" ELEMENT_WRAPPER_END;
1431 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, true), LY_SUCCESS);
1432 assert_int_equal(en.value, -55);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001433 assert_true(en.flags & LYS_SET_VALUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001434 memset(&en, 0, sizeof(en));
1435
1436 data = ELEMENT_WRAPPER_START "<value value=\"0\"/>" ELEMENT_WRAPPER_END;
1437 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, true), LY_SUCCESS);
1438 assert_int_equal(en.value, 0);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001439 assert_true(en.flags & LYS_SET_VALUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001440 memset(&en, 0, sizeof(en));
1441
1442 data = ELEMENT_WRAPPER_START "<value value=\"-0\"/>" ELEMENT_WRAPPER_END;
1443 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, true), LY_SUCCESS);
1444 assert_int_equal(en.value, 0);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001445 assert_true(en.flags & LYS_SET_VALUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001446 memset(&en, 0, sizeof(en));
1447
1448 /* valid positions */
1449 data = ELEMENT_WRAPPER_START "<position value=\"55\" />" ELEMENT_WRAPPER_END;
1450 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, true), LY_SUCCESS);
1451 assert_int_equal(en.value, 55);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001452 assert_true(en.flags & LYS_SET_VALUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001453 memset(&en, 0, sizeof(en));
1454
1455 data = ELEMENT_WRAPPER_START "<position value=\"0\" />" ELEMENT_WRAPPER_END;
1456 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, true), LY_SUCCESS);
1457 assert_int_equal(en.value, 0);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001458 assert_true(en.flags & LYS_SET_VALUE);
David Sedlák8e7bda82019-07-16 17:57:50 +02001459 memset(&en, 0, sizeof(en));
1460
1461 /* invalid values */
1462 data = ELEMENT_WRAPPER_START "<value value=\"99999999999999999999999\"/>" ELEMENT_WRAPPER_END;
1463 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1464 logbuf_assert("Invalid value \"99999999999999999999999\" of \"value\". Line number 1.");
1465
1466 data = ELEMENT_WRAPPER_START "<value value=\"1k\"/>" ELEMENT_WRAPPER_END;
1467 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1468 logbuf_assert("Invalid value \"1k\" of \"value\". Line number 1.");
1469
David Sedlák69f01612019-07-17 11:41:08 +02001470 data = ELEMENT_WRAPPER_START "<value value=\"\"/>" ELEMENT_WRAPPER_END;
1471 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1472 logbuf_assert("Invalid value \"\" of \"value\". Line number 1.");
1473
David Sedlák8e7bda82019-07-16 17:57:50 +02001474 /*invalid positions */
1475 data = ELEMENT_WRAPPER_START "<position value=\"-5\"/>" ELEMENT_WRAPPER_END;
1476 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1477 logbuf_assert("Invalid value \"-5\" of \"position\". Line number 1.");
1478
1479 data = ELEMENT_WRAPPER_START "<position value=\"-0\"/>" ELEMENT_WRAPPER_END;
1480 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1481 logbuf_assert("Invalid value \"-0\" of \"position\". Line number 1.");
1482
1483 data = ELEMENT_WRAPPER_START "<position value=\"99999999999999999999\"/>" ELEMENT_WRAPPER_END;
1484 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1485 logbuf_assert("Invalid value \"99999999999999999999\" of \"position\". Line number 1.");
1486
David Sedlák69f01612019-07-17 11:41:08 +02001487 data = ELEMENT_WRAPPER_START "<position value=\"\"/>" ELEMENT_WRAPPER_END;
1488 assert_int_equal(test_element_helper(st, &data, &en, NULL, NULL, false), LY_EVALID);
1489 logbuf_assert("Invalid value \"\" of \"position\". Line number 1.");
1490
1491 st->finished_correctly = true;
1492}
1493
1494static void
1495test_prefix_elem(void **state)
1496{
1497 struct state *st = *state;
1498 const char *data;
1499 const char *value = NULL;
1500
1501 data = ELEMENT_WRAPPER_START "<prefix value=\"pref\"/>" ELEMENT_WRAPPER_END;
1502 assert_int_equal(test_element_helper(st, &data, &value, NULL, NULL, true), LY_SUCCESS);
1503 assert_string_equal(value, "pref");
1504 FREE_STRING(st->ctx, value);
1505
1506 st->finished_correctly = true;
1507}
1508
1509static void
1510test_range_elem(void **state)
1511{
1512 struct state *st = *state;
1513 const char *data;
1514 struct lysp_type type = {};
1515
1516 /* max subelems */
1517 data = ELEMENT_WRAPPER_START
1518 "<range value=\"range-str\">"
1519 "<error-message><value>err-msg</value></error-message>"
1520 "<error-app-tag value=\"err-app-tag\" />"
1521 "<description><text>desc</text></description>"
1522 "<reference><text>ref</text></reference>"
1523 "</range>"
1524 ELEMENT_WRAPPER_END;
1525 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1526 assert_string_equal(type.range->arg, "range-str");
1527 assert_string_equal(type.range->dsc, "desc");
1528 assert_string_equal(type.range->eapptag, "err-app-tag");
1529 assert_string_equal(type.range->emsg, "err-msg");
1530 assert_string_equal(type.range->ref, "ref");
David Sedlákc3da3ef2019-07-19 12:56:08 +02001531 assert_true(type.flags & LYS_SET_RANGE);
David Sedlák69f01612019-07-17 11:41:08 +02001532 lysp_type_free(st->ctx, &type);
1533 memset(&type, 0, sizeof(type));
1534
1535 /* min subelems */
1536 data = ELEMENT_WRAPPER_START "<range value=\"range-str\"/>" ELEMENT_WRAPPER_END;
1537 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1538 assert_string_equal(type.range->arg, "range-str");
1539 lysp_type_free(st->ctx, &type);
1540 memset(&type, 0, sizeof(type));
1541
1542 st->finished_correctly = true;
1543}
1544
1545static void
1546test_reqinstance_elem(void **state)
1547{
1548 struct state *st = *state;
1549 const char *data;
1550 struct lysp_type type = {};
1551
1552 data = ELEMENT_WRAPPER_START "<require-instance value=\"true\"/>" ELEMENT_WRAPPER_END;
1553 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1554 assert_int_equal(type.require_instance, 1);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001555 assert_true(type.flags & LYS_SET_REQINST);
David Sedlák69f01612019-07-17 11:41:08 +02001556 memset(&type, 0, sizeof(type));
1557
1558 data = ELEMENT_WRAPPER_START "<require-instance value=\"false\"/>" ELEMENT_WRAPPER_END;
1559 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1560 assert_int_equal(type.require_instance, 0);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001561 assert_true(type.flags & LYS_SET_REQINST);
David Sedlák69f01612019-07-17 11:41:08 +02001562 memset(&type, 0, sizeof(type));
1563
1564 data = ELEMENT_WRAPPER_START "<require-instance value=\"invalid\"/>" ELEMENT_WRAPPER_END;
1565 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, false), LY_EVALID);
1566 memset(&type, 0, sizeof(type));
1567 logbuf_assert("Invalid value \"invalid\" of \"require-instance\". Line number 1.");
1568
1569 st->finished_correctly = true;
1570}
1571
1572static void
1573test_revision_date_elem(void **state)
1574{
1575 struct state *st = *state;
1576 const char *data;
1577 char rev[LY_REV_SIZE];
1578
1579 data = ELEMENT_WRAPPER_START "<revision-date date=\"2000-01-01\"/>" ELEMENT_WRAPPER_END;
1580 assert_int_equal(test_element_helper(st, &data, rev, NULL, NULL, true), LY_SUCCESS);
1581 assert_string_equal(rev, "2000-01-01");
1582
1583 data = ELEMENT_WRAPPER_START "<revision-date date=\"2000-50-05\"/>" ELEMENT_WRAPPER_END;
1584 assert_int_equal(test_element_helper(st, &data, rev, NULL, NULL, false), LY_EVALID);
1585 logbuf_assert("Invalid value \"2000-50-05\" of \"revision-date\". Line number 1.");
1586
1587 st->finished_correctly = true;
1588}
1589
1590static void
1591test_unique_elem(void **state)
1592{
1593 struct state *st = *state;
1594 const char *data;
1595 const char **values = NULL;
1596
1597 data = ELEMENT_WRAPPER_START "<unique tag=\"tag\"/>" ELEMENT_WRAPPER_END;
1598 assert_int_equal(test_element_helper(st, &data, &values, NULL, NULL, true), LY_SUCCESS);
1599 assert_string_equal(*values, "tag");
1600 FREE_STRING(st->ctx, *values);
1601 LY_ARRAY_FREE(values);
1602
1603 st->finished_correctly = true;
1604}
1605
1606static void
1607test_units_elem(void **state)
1608{
1609 struct state *st = *state;
1610 const char *data;
1611 const char *values = NULL;
1612
1613 data = ELEMENT_WRAPPER_START "<units name=\"name\"/>" ELEMENT_WRAPPER_END;
1614 assert_int_equal(test_element_helper(st, &data, &values, NULL, NULL, true), LY_SUCCESS);
1615 assert_string_equal(values, "name");
1616 FREE_STRING(st->ctx, values);
1617
1618 st->finished_correctly = true;
1619}
1620
1621static void
1622test_when_elem(void **state)
1623{
1624 struct state *st = *state;
1625 const char *data;
1626 struct lysp_when *when = NULL;
1627
1628 data = ELEMENT_WRAPPER_START
1629 "<when condition=\"cond\">"
1630 "<description><text>desc</text></description>"
1631 "<reference><text>ref</text></reference>"
1632 "</when>"
1633 ELEMENT_WRAPPER_END;
1634 assert_int_equal(test_element_helper(st, &data, &when, NULL, NULL, true), LY_SUCCESS);
1635 assert_string_equal(when->cond, "cond");
1636 assert_string_equal(when->dsc, "desc");
1637 assert_string_equal(when->ref, "ref");
1638 lysp_when_free(st->ctx, when);
1639 free(when);
1640 when = NULL;
1641
1642 data = ELEMENT_WRAPPER_START "<when condition=\"cond\" />" ELEMENT_WRAPPER_END;
1643 assert_int_equal(test_element_helper(st, &data, &when, NULL, NULL, true), LY_SUCCESS);
1644 assert_string_equal(when->cond, "cond");
1645 lysp_when_free(st->ctx, when);
1646 free(when);
1647 when = NULL;
1648
1649 st->finished_correctly = true;
1650}
1651
1652static void
1653test_yin_text_value_elem(void **state)
1654{
1655 struct state *st = *state;
1656 const char *data;
1657 const char *val;
1658
1659 data = ELEMENT_WRAPPER_START "<text>text</text>" ELEMENT_WRAPPER_END;
1660 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
1661 assert_string_equal(val, "text");
1662 FREE_STRING(st->ctx, val);
1663
1664 data = "<error-message xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <value>text</value> </error-message>";
1665 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
1666 assert_string_equal(val, "text");
1667 FREE_STRING(st->ctx, val);
1668
1669 data = ELEMENT_WRAPPER_START "<text></text>" ELEMENT_WRAPPER_END;
1670 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
1671 assert_string_equal("", val);
1672 FREE_STRING(st->ctx, val);
1673
David Sedlák8e7bda82019-07-16 17:57:50 +02001674 st->finished_correctly = true;
1675}
David Sedlák32488102019-07-15 17:44:10 +02001676
David Sedlák374d2b32019-07-17 15:06:55 +02001677static void
1678test_type_elem(void **state)
1679{
1680 struct state *st = *state;
1681 const char *data;
1682 struct lysp_type type = {};
1683
1684 /* max subelems */
1685 data = ELEMENT_WRAPPER_START
1686 "<type name=\"type-name\">"
1687 "<base name=\"base-name\"/>"
1688 "<bit name=\"bit\"/>"
1689 "<enum name=\"enum\"/>"
1690 "<fraction-digits value=\"2\"/>"
1691 "<length value=\"length\"/>"
1692 "<path value=\"path\"/>"
1693 "<pattern value=\"pattern\"/>"
1694 "<range value=\"range\" />"
1695 "<require-instance value=\"true\"/>"
1696 "<type name=\"sub-type-name\"/>"
1697 "</type>"
1698 ELEMENT_WRAPPER_END;
1699 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1700 assert_string_equal(type.name, "type-name");
1701 assert_string_equal(*type.bases, "base-name");
1702 assert_string_equal(type.bits->name, "bit");
1703 assert_string_equal(type.enums->name, "enum");
1704 assert_int_equal(type.fraction_digits, 2);
1705 assert_string_equal(type.length->arg, "length");
1706 assert_string_equal(type.path, "path");
1707 assert_string_equal(type.patterns->arg, "\006pattern");
1708 assert_string_equal(type.range->arg, "range");
1709 assert_int_equal(type.require_instance, 1);
1710 assert_string_equal(type.types->name, "sub-type-name");
1711 lysp_type_free(st->ctx, &type);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001712 assert_true(type.flags & LYS_SET_BASE);
1713 assert_true(type.flags & LYS_SET_BIT);
1714 assert_true(type.flags & LYS_SET_ENUM);
1715 assert_true(type.flags & LYS_SET_FRDIGITS);
1716 assert_true(type.flags & LYS_SET_LENGTH);
1717 assert_true(type.flags & LYS_SET_PATH);
1718 assert_true(type.flags & LYS_SET_PATTERN);
1719 assert_true(type.flags & LYS_SET_RANGE);
1720 assert_true(type.flags & LYS_SET_REQINST);
1721 assert_true(type.flags & LYS_SET_TYPE);
David Sedlák374d2b32019-07-17 15:06:55 +02001722 memset(&type, 0, sizeof(type));
1723
1724 /* min subelems */
1725 data = ELEMENT_WRAPPER_START "<type name=\"type-name\"/>" ELEMENT_WRAPPER_END;
1726 assert_int_equal(test_element_helper(st, &data, &type, NULL, NULL, true), LY_SUCCESS);
1727 lysp_type_free(st->ctx, &type);
1728 memset(&type, 0, sizeof(type));
1729
1730 st->finished_correctly = true;
1731}
1732
David Sedlák1af868e2019-07-17 17:03:14 +02001733static void
1734test_max_elems_elem(void **state)
1735{
1736 struct state *st = *state;
1737 const char *data;
1738 struct lysp_node_list list = {};
1739 struct lysp_node_leaflist llist = {};
1740 struct lysp_refine refine = {};
1741
1742 data = "<refine xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"unbounded\"/> </refine>";
1743 assert_int_equal(test_element_helper(st, &data, &refine, NULL, NULL, true), LY_SUCCESS);
1744 assert_int_equal(refine.max, 0);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001745 assert_true(refine.flags & LYS_SET_MAX);
David Sedlák1af868e2019-07-17 17:03:14 +02001746
1747 data = "<list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"5\"/> </list>";
1748 assert_int_equal(test_element_helper(st, &data, &list, NULL, NULL, true), LY_SUCCESS);
1749 assert_int_equal(list.max, 5);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001750 assert_true(list.flags & LYS_SET_MAX);
David Sedlák1af868e2019-07-17 17:03:14 +02001751
1752 data = "<leaf-list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"85\"/> </leaf-list>";
1753 assert_int_equal(test_element_helper(st, &data, &llist, NULL, NULL, true), LY_SUCCESS);
1754 assert_int_equal(llist.max, 85);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001755 assert_true(llist.flags & LYS_SET_MAX);
David Sedlák1af868e2019-07-17 17:03:14 +02001756
1757 data = "<refine xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"10\"/> </refine>";
1758 assert_int_equal(test_element_helper(st, &data, &refine, NULL, NULL, true), LY_SUCCESS);
1759 assert_int_equal(refine.max, 10);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001760 assert_true(refine.flags & LYS_SET_MAX);
David Sedlák1af868e2019-07-17 17:03:14 +02001761
1762 data = "<list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"0\"/> </list>";
1763 assert_int_equal(test_element_helper(st, &data, &list, NULL, NULL, false), LY_EVALID);
1764 logbuf_assert("Invalid value \"0\" of \"max-elements\". Line number 1.");
1765
1766 data = "<list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"-10\"/> </list>";
1767 assert_int_equal(test_element_helper(st, &data, &list, NULL, NULL, false), LY_EVALID);
1768 logbuf_assert("Invalid value \"-10\" of \"max-elements\". Line number 1.");
1769
1770 data = "<list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"k\"/> </list>";
1771 assert_int_equal(test_element_helper(st, &data, &list, NULL, NULL, false), LY_EVALID);
1772 logbuf_assert("Invalid value \"k\" of \"max-elements\". Line number 1.");
1773
1774 data = "<list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <max-elements value=\"u12\"/> </list>";
1775 assert_int_equal(test_element_helper(st, &data, &list, NULL, NULL, false), LY_EVALID);
1776 logbuf_assert("Invalid value \"u12\" of \"max-elements\". Line number 1.");
1777
1778 st->finished_correctly = true;
1779}
1780
David Sedlák09e18c92019-07-18 11:17:11 +02001781static void
1782test_min_elems_elem(void **state)
1783{
1784 struct state *st = *state;
1785 const char *data;
1786 struct lysp_node_list list = {};
1787 struct lysp_node_leaflist llist = {};
1788 struct lysp_refine refine = {};
1789
1790 data = "<refine xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"0\"/> </refine>";
1791 assert_int_equal(test_element_helper(st, &data, &refine, NULL, NULL, true), LY_SUCCESS);
1792 assert_int_equal(refine.min, 0);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001793 assert_true(refine.flags & LYS_SET_MIN);
David Sedlák09e18c92019-07-18 11:17:11 +02001794
1795 data = "<list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"41\"/> </list>";
1796 assert_int_equal(test_element_helper(st, &data, &list, NULL, NULL, true), LY_SUCCESS);
1797 assert_int_equal(list.min, 41);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001798 assert_true(list.flags & LYS_SET_MIN);
David Sedlák09e18c92019-07-18 11:17:11 +02001799
1800 data = "<leaf-list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"50\"/> </leaf-list>";
1801 assert_int_equal(test_element_helper(st, &data, &llist, NULL, NULL, true), LY_SUCCESS);
1802 assert_int_equal(llist.min, 50);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001803 assert_true(llist.flags & LYS_SET_MIN);
David Sedlák09e18c92019-07-18 11:17:11 +02001804
1805 data = "<leaf-list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"-5\"/> </leaf-list>";
1806 assert_int_equal(test_element_helper(st, &data, &llist, NULL, NULL, false), LY_EVALID);
1807 logbuf_assert("Value \"-5\" is out of \"min-elements\" bounds. Line number 1.");
1808
1809 data = "<leaf-list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"99999999999999999\"/> </leaf-list>";
1810 assert_int_equal(test_element_helper(st, &data, &llist, NULL, NULL, false), LY_EVALID);
1811 logbuf_assert("Value \"99999999999999999\" is out of \"min-elements\" bounds. Line number 1.");
1812
1813 data = "<leaf-list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"5k\"/> </leaf-list>";
1814 assert_int_equal(test_element_helper(st, &data, &llist, NULL, NULL, false), LY_EVALID);
1815 logbuf_assert("Invalid value \"5k\" of \"min-elements\". Line number 1.");
1816
1817 data = "<leaf-list xmlns=\"urn:ietf:params:xml:ns:yang:yin:1\"> <min-elements value=\"05\"/> </leaf-list>";
1818 assert_int_equal(test_element_helper(st, &data, &llist, NULL, NULL, false), LY_EVALID);
1819 logbuf_assert("Invalid value \"05\" of \"min-elements\". Line number 1.");
1820
1821 st->finished_correctly = true;
1822}
1823
David Sedláka2dad212019-07-18 12:45:19 +02001824static void
1825test_ordby_elem(void **state)
1826{
1827 struct state *st = *state;
1828 const char *data;
1829 uint16_t flags = 0;
1830
1831 data = ELEMENT_WRAPPER_START "<ordered-by value=\"system\"/>" ELEMENT_WRAPPER_END;
1832 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001833 assert_true(flags & LYS_ORDBY_SYSTEM);
David Sedláka2dad212019-07-18 12:45:19 +02001834
1835 data = ELEMENT_WRAPPER_START "<ordered-by value=\"user\"/>" ELEMENT_WRAPPER_END;
1836 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, true), LY_SUCCESS);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001837 assert_true(flags & LYS_ORDBY_USER);
David Sedláka2dad212019-07-18 12:45:19 +02001838
1839 data = ELEMENT_WRAPPER_START "<ordered-by value=\"inv\"/>" ELEMENT_WRAPPER_END;
1840 assert_int_equal(test_element_helper(st, &data, &flags, NULL, NULL, false), LY_EVALID);
1841 logbuf_assert("Invalid value \"inv\" of \"ordered-by\". Line number 1.");
1842
1843 st->finished_correctly = true;
1844}
1845
David Sedlák8a83bbb2019-07-18 14:46:00 +02001846static void
1847test_any_elem(void **state)
1848{
1849 struct state *st = *state;
1850 const char *data;
1851 struct lysp_node *siblings = NULL;
1852 struct tree_node_meta node_meta = {.parent = NULL, .siblings = &siblings};
1853 struct lysp_node_anydata *parsed = NULL;
1854
1855 /* anyxml max subelems */
1856 data = ELEMENT_WRAPPER_START
1857 "<anyxml name=\"any-name\">"
1858 "<config value=\"true\" />"
1859 "<description><text>desc</text></description>"
1860 "<if-feature name=\"feature\" />"
1861 "<mandatory value=\"true\" />"
1862 "<must condition=\"must-cond\" />"
1863 "<reference><text>ref</text></reference>"
1864 "<status value=\"deprecated\"/>"
1865 "<when condition=\"when-cond\"/>"
1866 "</anyxml>"
1867 ELEMENT_WRAPPER_END;
1868 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
1869 parsed = (struct lysp_node_anydata *)siblings;
1870 assert_null(parsed->parent);
1871 assert_int_equal(parsed->nodetype, LYS_ANYXML);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001872 assert_true(parsed->flags & LYS_CONFIG_W);
1873 assert_true(parsed->flags & LYS_MAND_TRUE);
1874 assert_true(parsed->flags & LYS_STATUS_DEPRC);
David Sedlák8a83bbb2019-07-18 14:46:00 +02001875 assert_null(parsed->next);
1876 assert_string_equal(parsed->name, "any-name");
1877 assert_string_equal(parsed->dsc, "desc");
1878 assert_string_equal(parsed->ref, "ref");
1879 assert_string_equal(parsed->when->cond, "when-cond");
1880 assert_string_equal(*parsed->iffeatures, "feature");
1881 assert_null(parsed->exts);
1882 lysp_node_free(st->ctx, siblings);
1883 siblings = NULL;
1884
1885 /* anydata max subelems */
1886 data = ELEMENT_WRAPPER_START
1887 "<anydata name=\"any-name\">"
1888 "<config value=\"true\" />"
1889 "<description><text>desc</text></description>"
1890 "<if-feature name=\"feature\" />"
1891 "<mandatory value=\"true\" />"
1892 "<must condition=\"must-cond\" />"
1893 "<reference><text>ref</text></reference>"
1894 "<status value=\"deprecated\"/>"
1895 "<when condition=\"when-cond\"/>"
1896 "</anydata>"
1897 ELEMENT_WRAPPER_END;
1898 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
1899 parsed = (struct lysp_node_anydata *)siblings;
1900 assert_null(parsed->parent);
1901 assert_int_equal(parsed->nodetype, LYS_ANYDATA);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001902 assert_true(parsed->flags & LYS_CONFIG_W);
1903 assert_true(parsed->flags & LYS_MAND_TRUE);
1904 assert_true(parsed->flags & LYS_STATUS_DEPRC);
David Sedlák8a83bbb2019-07-18 14:46:00 +02001905 assert_null(parsed->next);
1906 assert_string_equal(parsed->name, "any-name");
1907 assert_string_equal(parsed->dsc, "desc");
1908 assert_string_equal(parsed->ref, "ref");
1909 assert_string_equal(parsed->when->cond, "when-cond");
1910 assert_string_equal(*parsed->iffeatures, "feature");
1911 assert_null(parsed->exts);
1912 lysp_node_free(st->ctx, siblings);
1913 siblings = NULL;
1914
1915 /* min subelems */
1916 node_meta.parent = (void *)0x10;
1917 data = ELEMENT_WRAPPER_START "<anydata name=\"any-name\"> </anydata>" ELEMENT_WRAPPER_END;
1918 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
1919 parsed = (struct lysp_node_anydata *)siblings;
1920 assert_ptr_equal(parsed->parent, node_meta.parent);
1921 assert_int_equal(parsed->nodetype, LYS_ANYDATA);
1922 assert_null(parsed->next);
1923 assert_null(parsed->exts);
1924 lysp_node_free(st->ctx, siblings);
1925
1926 st->finished_correctly = true;
1927}
1928
David Sedlák203ca3a2019-07-18 15:26:25 +02001929static void
1930test_leaf_elem(void **state)
1931{
1932 struct state *st = *state;
1933 const char *data;
1934 struct lysp_node *siblings = NULL;
1935 struct tree_node_meta node_meta = {.parent = NULL, .siblings = &siblings};
1936 struct lysp_node_leaf *parsed = NULL;
1937
1938 /* max elements */
1939 data = ELEMENT_WRAPPER_START
1940 "<leaf name=\"leaf\">"
1941 "<config value=\"true\" />"
1942 "<default value=\"def-val\"/>"
1943 "<description><text>desc</text></description>"
1944 "<if-feature name=\"feature\" />"
1945 "<mandatory value=\"true\" />"
1946 "<must condition=\"must-cond\" />"
1947 "<reference><text>ref</text></reference>"
1948 "<status value=\"deprecated\"/>"
1949 "<type name=\"type\"/>"
1950 "<units name=\"uni\"/>"
1951 "<when condition=\"when-cond\"/>"
1952 "</leaf>"
1953 ELEMENT_WRAPPER_END;
1954 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
1955 parsed = (struct lysp_node_leaf *)siblings;
1956 assert_null(parsed->parent);
1957 assert_int_equal(parsed->nodetype, LYS_LEAF);
David Sedlákc3da3ef2019-07-19 12:56:08 +02001958 assert_true(parsed->flags & LYS_CONFIG_W);
1959 assert_true(parsed->flags & LYS_MAND_TRUE);
1960 assert_true(parsed->flags & LYS_STATUS_DEPRC);
David Sedlák203ca3a2019-07-18 15:26:25 +02001961 assert_null(parsed->next);
1962 assert_string_equal(parsed->name, "leaf");
1963 assert_string_equal(parsed->dsc, "desc");
1964 assert_string_equal(parsed->ref, "ref");
1965 assert_string_equal(parsed->when->cond, "when-cond");
1966 assert_string_equal(*parsed->iffeatures, "feature");
1967 assert_null(parsed->exts);
1968 assert_string_equal(parsed->musts->arg, "must-cond");
1969 assert_string_equal(parsed->type.name, "type");
1970 assert_string_equal(parsed->units, "uni");
1971 assert_string_equal(parsed->dflt, "def-val");
1972 lysp_node_free(st->ctx, siblings);
1973 siblings = NULL;
1974
1975 /* min elements */
1976 data = ELEMENT_WRAPPER_START "<leaf name=\"leaf\"> <type name=\"type\"/> </leaf>" ELEMENT_WRAPPER_END;
1977 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
1978 parsed = (struct lysp_node_leaf *)siblings;
1979 assert_string_equal(parsed->name, "leaf");
1980 assert_string_equal(parsed->type.name, "type");
1981 lysp_node_free(st->ctx, siblings);
1982 siblings = NULL;
1983
1984 st->finished_correctly = true;
1985}
1986
David Sedlákc3da3ef2019-07-19 12:56:08 +02001987static void
1988test_leaf_list_elem(void **state)
1989{
1990 struct state *st = *state;
1991 const char *data;
1992 struct lysp_node *siblings = NULL;
1993 struct tree_node_meta node_meta = {.parent = NULL, .siblings = &siblings};
1994 struct lysp_node_leaflist *parsed = NULL;
1995
1996 data = ELEMENT_WRAPPER_START
1997 "<leaf-list name=\"llist\">"
1998 "<config value=\"true\" />"
1999 "<default value=\"def-val0\"/>"
2000 "<default value=\"def-val1\"/>"
2001 "<description><text>desc</text></description>"
2002 "<if-feature name=\"feature\"/>"
2003 "<max-elements value=\"5\"/>"
2004 "<must condition=\"must-cond\"/>"
2005 "<ordered-by value=\"user\" />"
2006 "<reference><text>ref</text></reference>"
2007 "<status value=\"current\"/>"
2008 "<type name=\"type\"/>"
2009 "<units name=\"uni\"/>"
2010 "<when condition=\"when-cond\"/>"
2011 "</leaf-list>"
2012 ELEMENT_WRAPPER_END;
2013 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
2014 parsed = (struct lysp_node_leaflist *)siblings;
2015 assert_string_equal(parsed->dflts[0], "def-val0");
2016 assert_string_equal(parsed->dflts[1], "def-val1");
2017 assert_string_equal(parsed->dsc, "desc");
2018 assert_string_equal(*parsed->iffeatures, "feature");
2019 assert_int_equal(parsed->max, 5);
2020 assert_string_equal(parsed->musts->arg, "must-cond");
2021 assert_string_equal(parsed->name, "llist");
2022 assert_null(parsed->next);
2023 assert_int_equal(parsed->nodetype, LYS_LEAFLIST);
2024 assert_null(parsed->parent);
2025 assert_string_equal(parsed->ref, "ref");
2026 assert_string_equal(parsed->type.name, "type");
2027 assert_string_equal(parsed->units, "uni");
2028 assert_string_equal(parsed->when->cond, "when-cond");
2029 assert_true(parsed->flags & LYS_CONFIG_W);
2030 assert_true(parsed->flags & LYS_ORDBY_USER);
2031 assert_true(parsed->flags & LYS_STATUS_CURR);
2032 lysp_node_free(st->ctx, siblings);
2033 siblings = NULL;
2034
2035 data = ELEMENT_WRAPPER_START
2036 "<leaf-list name=\"llist\">"
2037 "<config value=\"true\" />"
2038 "<description><text>desc</text></description>"
2039 "<if-feature name=\"feature\"/>"
2040 "<min-elements value=\"5\"/>"
2041 "<must condition=\"must-cond\"/>"
2042 "<ordered-by value=\"user\" />"
2043 "<reference><text>ref</text></reference>"
2044 "<status value=\"current\"/>"
2045 "<type name=\"type\"/>"
2046 "<units name=\"uni\"/>"
2047 "<when condition=\"when-cond\"/>"
2048 "</leaf-list>"
2049 ELEMENT_WRAPPER_END;
2050 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
2051 parsed = (struct lysp_node_leaflist *)siblings;
2052 assert_string_equal(parsed->dsc, "desc");
2053 assert_string_equal(*parsed->iffeatures, "feature");
2054 assert_int_equal(parsed->min, 5);
2055 assert_string_equal(parsed->musts->arg, "must-cond");
2056 assert_string_equal(parsed->name, "llist");
2057 assert_null(parsed->next);
2058 assert_int_equal(parsed->nodetype, LYS_LEAFLIST);
2059 assert_null(parsed->parent);
2060 assert_string_equal(parsed->ref, "ref");
2061 assert_string_equal(parsed->type.name, "type");
2062 assert_string_equal(parsed->units, "uni");
2063 assert_string_equal(parsed->when->cond, "when-cond");
2064 assert_true(parsed->flags & LYS_CONFIG_W);
2065 assert_true(parsed->flags & LYS_ORDBY_USER);
2066 assert_true(parsed->flags & LYS_STATUS_CURR);
2067 lysp_node_free(st->ctx, siblings);
2068 siblings = NULL;
2069
2070 data = ELEMENT_WRAPPER_START
2071 "<leaf-list name=\"llist\">"
2072 "<config value=\"true\" />"
2073 "<description><text>desc</text></description>"
2074 "<if-feature name=\"feature\"/>"
2075 "<max-elements value=\"15\"/>"
2076 "<min-elements value=\"5\"/>"
2077 "<must condition=\"must-cond\"/>"
2078 "<ordered-by value=\"user\" />"
2079 "<reference><text>ref</text></reference>"
2080 "<status value=\"current\"/>"
2081 "<type name=\"type\"/>"
2082 "<units name=\"uni\"/>"
2083 "<when condition=\"when-cond\"/>"
2084 "</leaf-list>"
2085 ELEMENT_WRAPPER_END;
2086 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
2087 parsed = (struct lysp_node_leaflist *)siblings;
2088 assert_string_equal(parsed->dsc, "desc");
2089 assert_string_equal(*parsed->iffeatures, "feature");
2090 assert_int_equal(parsed->min, 5);
2091 assert_int_equal(parsed->max, 15);
2092 assert_string_equal(parsed->musts->arg, "must-cond");
2093 assert_string_equal(parsed->name, "llist");
2094 assert_null(parsed->next);
2095 assert_int_equal(parsed->nodetype, LYS_LEAFLIST);
2096 assert_null(parsed->parent);
2097 assert_string_equal(parsed->ref, "ref");
2098 assert_string_equal(parsed->type.name, "type");
2099 assert_string_equal(parsed->units, "uni");
2100 assert_string_equal(parsed->when->cond, "when-cond");
2101 assert_true(parsed->flags & LYS_CONFIG_W);
2102 assert_true(parsed->flags & LYS_ORDBY_USER);
2103 assert_true(parsed->flags & LYS_STATUS_CURR);
2104 lysp_node_free(st->ctx, siblings);
2105 siblings = NULL;
2106
2107 data = ELEMENT_WRAPPER_START
2108 "<leaf-list name=\"llist\">"
2109 "<type name=\"type\"/>"
2110 "</leaf-list>"
2111 ELEMENT_WRAPPER_END;
2112 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, true), LY_SUCCESS);
2113 parsed = (struct lysp_node_leaflist *)siblings;
2114 assert_string_equal(parsed->name, "llist");
2115 assert_string_equal(parsed->type.name, "type");
2116 lysp_node_free(st->ctx, siblings);
2117 siblings = NULL;
2118
2119 /* invalid combinations */
2120 data = ELEMENT_WRAPPER_START
2121 "<leaf-list name=\"llist\">"
2122 "<max-elements value=\"5\"/>"
2123 "<min-elements value=\"15\"/>"
2124 "<type name=\"type\"/>"
2125 "</leaf-list>"
2126 ELEMENT_WRAPPER_END;
2127 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, false), LY_EVALID);
2128 logbuf_assert("Invalid combination of min-elements and max-elements: min value 15 is bigger than the max value 5. Line number 1.");
2129 lysp_node_free(st->ctx, siblings);
2130 siblings = NULL;
2131
2132 data = ELEMENT_WRAPPER_START
2133 "<leaf-list name=\"llist\">"
2134 "<default value=\"def-val1\"/>"
2135 "<min-elements value=\"15\"/>"
2136 "<type name=\"type\"/>"
2137 "</leaf-list>"
2138 ELEMENT_WRAPPER_END;
2139 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, false), LY_EVALID);
2140 logbuf_assert("Invalid combination of keywords \"min-elements\" and \"default\" as substatements of \"leaf-list\". Line number 1.");
2141 lysp_node_free(st->ctx, siblings);
2142 siblings = NULL;
2143
2144 data = ELEMENT_WRAPPER_START
2145 "<leaf-list name=\"llist\">"
2146 "</leaf-list>"
2147 ELEMENT_WRAPPER_END;
2148 assert_int_equal(test_element_helper(st, &data, &node_meta, NULL, NULL, false), LY_EVALID);
2149 logbuf_assert("Missing mandatory subelement type of leaf-list element. Line number 1.");
2150 lysp_node_free(st->ctx, siblings);
2151 siblings = NULL;
2152
2153 st->finished_correctly = true;
2154}
2155
David Sedlákcb39f642019-07-19 13:19:55 +02002156static void
2157test_presence_elem(void **state)
2158{
2159 struct state *st = *state;
2160 const char *data;
2161 const char *val;
2162
2163 data = ELEMENT_WRAPPER_START "<presence value=\"presence-val\"/>" ELEMENT_WRAPPER_END;
2164 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, true), LY_SUCCESS);
2165 assert_string_equal(val, "presence-val");
2166 FREE_STRING(st->ctx, val);
2167
2168 data = ELEMENT_WRAPPER_START "<presence/>" ELEMENT_WRAPPER_END;
2169 assert_int_equal(test_element_helper(st, &data, &val, NULL, NULL, false), LY_EVALID);
2170 logbuf_assert("Missing mandatory attribute value of presence element. Line number 1.");
2171
2172 st->finished_correctly = true;
2173}
2174
David Sedlák3b4db242018-10-19 16:11:01 +02002175int
2176main(void)
2177{
2178
2179 const struct CMUnitTest tests[] = {
David Sedlák392af4f2019-06-04 16:02:42 +02002180 cmocka_unit_test_setup_teardown(test_yin_parse_module, setup_f, teardown_f),
David Sedlák8f7a1172019-06-20 14:42:18 +02002181 cmocka_unit_test_setup_teardown(test_yin_match_keyword, setup_f, teardown_f),
David Sedlákb1a78352019-06-28 16:16:29 +02002182 cmocka_unit_test_setup_teardown(test_yin_parse_element_generic, setup_f, teardown_f),
2183 cmocka_unit_test_setup_teardown(test_yin_parse_extension_instance, setup_f, teardown_f),
David Sedlák555c7202019-07-04 12:14:12 +02002184 cmocka_unit_test_setup_teardown(test_yin_parse_content, setup_f, teardown_f),
David Sedlák4a650532019-07-10 11:55:18 +02002185 cmocka_unit_test_setup_teardown(test_validate_value, setup_f, teardown_f),
David Sedlák32488102019-07-15 17:44:10 +02002186
David Sedlák8e7bda82019-07-16 17:57:50 +02002187 cmocka_unit_test(test_yin_match_argument_name),
David Sedlák32488102019-07-15 17:44:10 +02002188 cmocka_unit_test_setup_teardown(test_enum_bit_elem, setup_element_test, teardown_element_test),
2189 cmocka_unit_test_setup_teardown(test_meta_elem, setup_element_test, teardown_element_test),
2190 cmocka_unit_test_setup_teardown(test_import_elem, setup_element_test, teardown_element_test),
2191 cmocka_unit_test_setup_teardown(test_status_elem, setup_element_test, teardown_element_test),
2192 cmocka_unit_test_setup_teardown(test_ext_elem, setup_element_test, teardown_element_test),
2193 cmocka_unit_test_setup_teardown(test_yin_element_elem, setup_element_test, teardown_element_test),
2194 cmocka_unit_test_setup_teardown(test_yangversion_elem, setup_element_test, teardown_element_test),
2195 cmocka_unit_test_setup_teardown(test_mandatory_elem, setup_element_test, teardown_element_test),
David Sedlák8e7bda82019-07-16 17:57:50 +02002196 cmocka_unit_test_setup_teardown(test_argument_elem, setup_element_test, teardown_element_test),
2197 cmocka_unit_test_setup_teardown(test_base_elem, setup_element_test, teardown_element_test),
2198 cmocka_unit_test_setup_teardown(test_belongsto_elem, setup_element_test, teardown_element_test),
2199 cmocka_unit_test_setup_teardown(test_config_elem, setup_element_test, teardown_element_test),
2200 cmocka_unit_test_setup_teardown(test_default_elem, setup_element_test, teardown_element_test),
2201 cmocka_unit_test_setup_teardown(test_err_app_tag_elem, setup_element_test, teardown_element_test),
2202 cmocka_unit_test_setup_teardown(test_err_msg_elem, setup_element_test, teardown_element_test),
2203 cmocka_unit_test_setup_teardown(test_fracdigits_elem, setup_element_test, teardown_element_test),
2204 cmocka_unit_test_setup_teardown(test_iffeature_elem, setup_element_test, teardown_element_test),
2205 cmocka_unit_test_setup_teardown(test_length_elem, setup_element_test, teardown_element_test),
2206 cmocka_unit_test_setup_teardown(test_modifier_elem, setup_element_test, teardown_element_test),
2207 cmocka_unit_test_setup_teardown(test_namespace_elem, setup_element_test, teardown_element_test),
2208 cmocka_unit_test_setup_teardown(test_path_elem, setup_element_test, teardown_element_test),
2209 cmocka_unit_test_setup_teardown(test_pattern_elem, setup_element_test, teardown_element_test),
2210 cmocka_unit_test_setup_teardown(test_value_position_elem, setup_element_test, teardown_element_test),
David Sedlák69f01612019-07-17 11:41:08 +02002211 cmocka_unit_test_setup_teardown(test_prefix_elem, setup_element_test, teardown_element_test),
2212 cmocka_unit_test_setup_teardown(test_range_elem, setup_element_test, teardown_element_test),
2213 cmocka_unit_test_setup_teardown(test_reqinstance_elem, setup_element_test, teardown_element_test),
2214 cmocka_unit_test_setup_teardown(test_revision_date_elem, setup_element_test, teardown_element_test),
2215 cmocka_unit_test_setup_teardown(test_unique_elem, setup_element_test, teardown_element_test),
2216 cmocka_unit_test_setup_teardown(test_units_elem, setup_element_test, teardown_element_test),
2217 cmocka_unit_test_setup_teardown(test_when_elem, setup_element_test, teardown_element_test),
2218 cmocka_unit_test_setup_teardown(test_yin_text_value_elem, setup_element_test, teardown_element_test),
David Sedlák374d2b32019-07-17 15:06:55 +02002219 cmocka_unit_test_setup_teardown(test_type_elem, setup_element_test, teardown_element_test),
David Sedlák1af868e2019-07-17 17:03:14 +02002220 cmocka_unit_test_setup_teardown(test_max_elems_elem, setup_element_test, teardown_element_test),
David Sedlák09e18c92019-07-18 11:17:11 +02002221 cmocka_unit_test_setup_teardown(test_min_elems_elem, setup_element_test, teardown_element_test),
David Sedláka2dad212019-07-18 12:45:19 +02002222 cmocka_unit_test_setup_teardown(test_ordby_elem, setup_element_test, teardown_element_test),
David Sedlák8a83bbb2019-07-18 14:46:00 +02002223 cmocka_unit_test_setup_teardown(test_any_elem, setup_element_test, teardown_element_test),
David Sedlák203ca3a2019-07-18 15:26:25 +02002224 cmocka_unit_test_setup_teardown(test_leaf_elem, setup_element_test, teardown_element_test),
David Sedlákc3da3ef2019-07-19 12:56:08 +02002225 cmocka_unit_test_setup_teardown(test_leaf_list_elem, setup_element_test, teardown_element_test),
David Sedlákcb39f642019-07-19 13:19:55 +02002226 cmocka_unit_test_setup_teardown(test_presence_elem, setup_element_test, teardown_element_test),
David Sedlák203ca3a2019-07-18 15:26:25 +02002227
David Sedlák3b4db242018-10-19 16:11:01 +02002228 };
2229
David Sedlák8e7bda82019-07-16 17:57:50 +02002230 return cmocka_run_group_tests(tests, setup_ly_ctx, destroy_ly_ctx);
David Sedlák3b4db242018-10-19 16:11:01 +02002231}