tree schema CHANGE plugin record in parsed extensions
diff --git a/src/tree_schema.c b/src/tree_schema.c
index 000c115..b0be387 100644
--- a/src/tree_schema.c
+++ b/src/tree_schema.c
@@ -37,6 +37,7 @@
#include "parser_internal.h"
#include "parser_schema.h"
#include "path.h"
+#include "plugins_internal.h"
#include "schema_compile.h"
#include "schema_compile_amend.h"
#include "schema_features.h"
@@ -1250,8 +1251,16 @@
return ret;
}
+/**
+ * @brief Resolve (find) all imported and included modules.
+ *
+ * @param[in] pctx Parser context.
+ * @param[in] pmod Parsed module to resolve.
+ * @param[out] new_mods Set with all the newly loaded modules.
+ * @return LY_ERR value.
+ */
static LY_ERR
-lys_resolve_import_include(struct lys_parser_ctx *pctx, struct lysp_module *pmod, struct ly_set *new_mods)
+lysp_resolve_import_include(struct lys_parser_ctx *pctx, struct lysp_module *pmod, struct ly_set *new_mods)
{
struct lysp_import *imp;
LY_ARRAY_COUNT_TYPE u, v;
@@ -1284,6 +1293,45 @@
return LY_SUCCESS;
}
+/**
+ * @brief Resolve (find) all extension instance records and finish their parsing.
+ *
+ * @param[in] pctx Parse context with all the parsed extension instances.
+ * @return LY_ERR value.
+ */
+static LY_ERR
+lysp_resolve_ext_instance_records(struct lys_parser_ctx *pctx)
+{
+ struct lysp_ext_instance *exts, *ext;
+ const struct lys_module *mod;
+ const char *ptr;
+ uint32_t i;
+ LY_ARRAY_COUNT_TYPE u;
+
+ for (i = 0; i < pctx->ext_inst.count; ++i) {
+ exts = pctx->ext_inst.objs[i];
+ LY_ARRAY_FOR(exts, u) {
+ ext = &exts[u];
+
+ /* find the extension (definition) module */
+ ptr = strchr(ext->name, ':');
+ assert(ptr);
+ mod = ly_resolve_prefix(PARSER_CTX(pctx), ext->name, ptr - ext->name, ext->format, ext->prefix_data);
+ if (!mod) {
+ LOGVAL(PARSER_CTX(pctx), LYVE_SYNTAX, "Unknown prefix \"%*.s\" used for an extension instance.",
+ (int)(ptr - ext->name), ext->name);
+ return LY_ENOTFOUND;
+ }
+
+ /* find the extension record, if any */
+ ++ptr;
+ ext->record = lyplg_ext_record_find(mod->name, mod->revision, ptr);
+ }
+ }
+
+ return LY_SUCCESS;
+}
+
LY_ERR
lys_parse_submodule(struct ly_ctx *ctx, struct ly_in *in, LYS_INFORMAT format, struct lys_parser_ctx *main_ctx,
LY_ERR (*custom_check)(const struct ly_ctx *, struct lysp_module *, struct lysp_submodule *, void *),
@@ -1350,7 +1398,10 @@
lys_parser_fill_filepath(ctx, in, &submod->filepath);
/* resolve imports and includes */
- LY_CHECK_GOTO(ret = lys_resolve_import_include(pctx, (struct lysp_module *)submod, new_mods), error);
+ LY_CHECK_GOTO(ret = lysp_resolve_import_include(pctx, (struct lysp_module *)submod, new_mods), error);
+
+ /* resolve extension instance plugin records */
+ LY_CHECK_GOTO(ret = lysp_resolve_ext_instance_records(pctx), error);
if (format == LYS_IN_YANG) {
yang_parser_ctx_free(yangctx);
@@ -1383,7 +1434,7 @@
* @return LY_ERR on error.
*/
static LY_ERR
-lys_parsed_add_internal_ietf_netconf(struct lysp_module *mod)
+lysp_add_internal_ietf_netconf(struct lysp_module *mod)
{
struct lysp_ext_instance *ext_p;
struct lysp_stmt *stmt;
@@ -1551,7 +1602,7 @@
* @return LY_ERR on error.
*/
static LY_ERR
-lys_parsed_add_internal_ietf_netconf_with_defaults(struct lysp_module *mod)
+lysp_add_internal_ietf_netconf_with_defaults(struct lysp_module *mod)
{
struct lysp_ext_instance *ext_p;
struct lysp_stmt *stmt;
@@ -1724,9 +1775,9 @@
/* add internal data in case specific modules were parsed */
if (!strcmp(mod->name, "ietf-netconf")) {
- LY_CHECK_GOTO(ret = lys_parsed_add_internal_ietf_netconf(mod->parsed), cleanup);
+ LY_CHECK_GOTO(ret = lysp_add_internal_ietf_netconf(mod->parsed), cleanup);
} else if (!strcmp(mod->name, "ietf-netconf-with-defaults")) {
- LY_CHECK_GOTO(ret = lys_parsed_add_internal_ietf_netconf_with_defaults(mod->parsed), cleanup);
+ LY_CHECK_GOTO(ret = lysp_add_internal_ietf_netconf_with_defaults(mod->parsed), cleanup);
}
/* add the module into newly created module set, will also be freed from there on any error */
@@ -1739,7 +1790,10 @@
ctx->change_count++;
/* resolve includes and all imports */
- LY_CHECK_GOTO(ret = lys_resolve_import_include(pctx, mod->parsed, new_mods), cleanup);
+ LY_CHECK_GOTO(ret = lysp_resolve_import_include(pctx, mod->parsed, new_mods), cleanup);
+
+ /* resolve extension instance plugin records */
+ LY_CHECK_GOTO(ret = lysp_resolve_ext_instance_records(pctx), cleanup);
/* check name collisions */
LY_CHECK_GOTO(ret = lysp_check_dup_typedefs(pctx, mod->parsed), cleanup);
@@ -1753,8 +1807,6 @@
/* compile identities */
LY_CHECK_GOTO(ret = lys_compile_identities(mod), cleanup);
- /* success */
-
cleanup:
if (ret && (ret != LY_EEXIST)) {
if (mod && mod->name) {