Refactored yang schema code
YANG Deprecated: `CLICON_YANG_SCHEMA_MOUNT_SHARE` due to yang domain support
This commit is contained in:
parent
b1d969e42b
commit
6c73c36fb7
8 changed files with 87 additions and 41 deletions
|
|
@ -30,6 +30,7 @@ Expected: January 2025
|
|||
* Changed: `CLICON_NETCONF_DUPLICATE_ALLOW` to not only check but remove duplicates
|
||||
* Added: `CLICON_CLI_PIPE_DIR`
|
||||
* Added: `CLICON_XMLDB_SYSTEM_ONLY_CONFIG`
|
||||
* Deprecated: `CLICON_YANG_SCHEMA_MOUNT_SHARE`
|
||||
|
||||
### C/CLI-API changes on existing features
|
||||
|
||||
|
|
|
|||
|
|
@ -45,10 +45,10 @@
|
|||
*/
|
||||
int xml_bind_yang_unknown_anydata(int val);
|
||||
int xml_bind_netconf_message_id_optional(int val);
|
||||
int xml_bind_yang(clixon_handle h, cxobj *xt, yang_bind yb, yang_stmt *yspec, cxobj **xerr);
|
||||
int xml_bind_yang0(clixon_handle h, cxobj *xt, yang_bind yb, yang_stmt *yspec, cxobj **xerr);
|
||||
int xml_bind_yang_rpc(clixon_handle h, cxobj *xrpc, yang_stmt *yspec, cxobj **xerr);
|
||||
int xml_bind_yang_rpc_reply(clixon_handle h, cxobj *xrpc, char *name, yang_stmt *yspec, cxobj **xerr);
|
||||
int xml_bind_yang0(clixon_handle h, cxobj *xt, yang_bind yb, yang_stmt *yspec, cxobj **xerr);
|
||||
int xml_bind_yang(clixon_handle h, cxobj *xt, yang_bind yb, yang_stmt *yspec, cxobj **xerr);
|
||||
int xml_bind_special(cxobj *xd, yang_stmt *yspec, char *schema_nodeid);
|
||||
|
||||
#endif /* _CLIXON_XML_BIND_H_ */
|
||||
|
|
|
|||
|
|
@ -63,7 +63,8 @@ int xml_yang_mount_get(clixon_handle h, cxobj *x, validate_level *vl, char **xpa
|
|||
int xml_yang_mount_set(clixon_handle h, cxobj *x, yang_stmt *yspec);
|
||||
int yang_mount_xtop2xmnt(cxobj *xtop, cvec **cvvp);
|
||||
int yang_schema_mount_statedata(clixon_handle h, yang_stmt *yspec, char *xpath, cvec *nsc, cxobj **xret, cxobj **xerr);
|
||||
int yang_schema_yanglib_parse_mount(clixon_handle h, cxobj *xt);
|
||||
int yang_schema_yanglib_mount_parse(clixon_handle h, cxobj *xt, cxobj *xyanglib, yang_stmt **yspecp);
|
||||
int yang_schema_yanglib_get_mount_parse(clixon_handle h, cxobj *xt);
|
||||
int yang_schema_get_child(clixon_handle h, cxobj *x1, cxobj *x1c, yang_stmt **yc);
|
||||
int yang_schema_yspec_rm(clixon_handle h, cxobj *xmnt);
|
||||
|
||||
|
|
|
|||
|
|
@ -142,7 +142,6 @@ strip_body_objects(cxobj *xt)
|
|||
* @param[in] h Clixon handle
|
||||
* @param[in] xt XML tree node
|
||||
* @param[in] xsibling
|
||||
* @param[in] yspec Top-level YANG spec / mount-point
|
||||
* @param[out] xerr Reason for failure, or NULL
|
||||
* @retval 2 OK Yang assignment not made because yang parent is anyxml or anydata
|
||||
* @retval 1 OK Yang assignment made
|
||||
|
|
@ -155,7 +154,6 @@ static int
|
|||
populate_self_parent(clixon_handle h,
|
||||
cxobj *xt,
|
||||
cxobj *xsibling,
|
||||
yang_stmt *yspec,
|
||||
cxobj **xerr)
|
||||
{
|
||||
int retval = -1;
|
||||
|
|
@ -448,7 +446,7 @@ xml_bind_yang0_opt(clixon_handle h,
|
|||
goto done;
|
||||
break;
|
||||
case YB_PARENT:
|
||||
if ((ret = populate_self_parent(h, xt, xsibling, yspec, xerr)) < 0)
|
||||
if ((ret = populate_self_parent(h, xt, xsibling, xerr)) < 0)
|
||||
goto done;
|
||||
break;
|
||||
default:
|
||||
|
|
@ -474,7 +472,7 @@ xml_bind_yang0_opt(clixon_handle h,
|
|||
else if (h == NULL)
|
||||
goto ok; /* treat as anydata */
|
||||
else{
|
||||
if ((ret = yang_schema_yanglib_parse_mount(h, xt)) < 0) // XXX malloc + freed här
|
||||
if ((ret = yang_schema_yanglib_get_mount_parse(h, xt)) < 0)
|
||||
goto done;
|
||||
if (ret == 0){ /* Special flag if mount-point but no yanglib */
|
||||
xml_flag_set(xt, XML_FLAG_ANYDATA);
|
||||
|
|
@ -557,7 +555,7 @@ xml_bind_yang0(clixon_handle h,
|
|||
goto done;
|
||||
break;
|
||||
case YB_PARENT:
|
||||
if ((ret = populate_self_parent(h, xt, NULL, yspec, xerr)) < 0)
|
||||
if ((ret = populate_self_parent(h, xt, NULL, xerr)) < 0)
|
||||
goto done;
|
||||
break;
|
||||
case YB_NONE:
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@
|
|||
* such as <n:a><n:b>. An xml with <m:a><m:b> (or <a><b>) will NOT match EVEN IF they have the
|
||||
* same namespace given by xmlns settings.
|
||||
* 2) RFC6241 8.9.1
|
||||
* In the scope of get-.config, the set of namespace declarations are those in scope on the
|
||||
* In the scope of get-config, the set of namespace declarations are those in scope on the
|
||||
* <filter> element.
|
||||
* <rpc message-id="101" xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
|
||||
* <get-config>
|
||||
|
|
|
|||
|
|
@ -851,10 +851,10 @@ yang_metadata_init(clixon_handle h)
|
|||
* This function is used where a yang-lib module-set is available to populate
|
||||
* an XML mount-point.
|
||||
* @param[in] h Clixon handle
|
||||
* @param[in] xyanglib XML tree on the form <yang-lib>...
|
||||
* @param[in] mntpnt Name of mount-point for logs
|
||||
* @param[in] xyanglib XML tree on the form <any><module-set><module>*
|
||||
* @param[in] mntpnt Name of mount-point for logs (debug)
|
||||
* @param[in] domain YANG domain (NULL is default)
|
||||
* @param[in] yspec Will be populated with YANGs, is consumed
|
||||
* @param[in] yspec Will be populated with YANGs
|
||||
* @retval 1 OK
|
||||
* @retval 0 Parse error
|
||||
* @retval -1 Error
|
||||
|
|
|
|||
|
|
@ -53,6 +53,10 @@
|
|||
* The API handles the relation between yext -->* ymnt -->* xmnt
|
||||
* Structure:
|
||||
*
|
||||
* ymounts(top)
|
||||
* |
|
||||
* ydomain*
|
||||
* |
|
||||
* yspec0(1) xtop(1)
|
||||
* | | (xpath)
|
||||
* ymnt(*) <-- xmnt(*)
|
||||
|
|
@ -64,11 +68,11 @@
|
|||
* The calls in this code are:
|
||||
* - yang_schema_mount_point(): Is ymnt a yang mount-point? (ymnt)
|
||||
* - yang_mount_get(): ymnt + xpath -> yspec
|
||||
* XXXX - yang_mount_get(): ymnt + xpath -> yspec
|
||||
* - yang_mount_set(): ymnt
|
||||
* - xml_yang_mount_get(): xmnt-> yspec
|
||||
* - xml_yang_mount_set(): xmnt -> yspec
|
||||
* - yang_mount_get_yspec_any(): ymnt -> yspec
|
||||
* - yang_mounto_freeall(): ymnt-> free cvec
|
||||
* - yang_mount_xmnt2ymnt_xpath(): xmnt -> ymnt + xpath
|
||||
* - yang_mount_xtop2xmnt(): top-level xml -> xmnt vector
|
||||
* - yang_mount_yspec2ymnt(): top-level yspec -> ymnt vector NOTUSED
|
||||
|
|
@ -183,11 +187,13 @@ yang_schema_mount_point(yang_stmt *y)
|
|||
|
||||
/*! Get yangspec mount-point
|
||||
*
|
||||
* @param[in] y Yang container/list containing unknown node
|
||||
* @param[in] ys Yang container/list containing unknown node
|
||||
* @param[in] xpath Key for yspec on y
|
||||
* @param[out] yspec YANG stmt spec
|
||||
* @retval 0 OK
|
||||
* @retval -1 Error
|
||||
* With domains it is assumed an xpath is unique across domains, which is true if the xpath
|
||||
* has eg a list name which is unique. But there could be cases where this is not true.
|
||||
*/
|
||||
int
|
||||
yang_mount_get(yang_stmt *ys,
|
||||
|
|
@ -721,7 +727,7 @@ yang_schema_find_share(clixon_handle h,
|
|||
cg_var *cv;
|
||||
cxobj *xroot;
|
||||
cxobj *xmnt;
|
||||
cxobj *xylib;
|
||||
cxobj *xylib = NULL;
|
||||
int config = 1;
|
||||
int ret;
|
||||
|
||||
|
|
@ -735,7 +741,10 @@ yang_schema_find_share(clixon_handle h,
|
|||
xmnt = cv_void_get(cv);
|
||||
if (xmnt == xt)
|
||||
continue;
|
||||
xylib = NULL;
|
||||
if (xylib){
|
||||
xml_free(xylib);
|
||||
xylib = NULL;
|
||||
}
|
||||
/* Get xyanglib */
|
||||
if (clixon_plugin_yang_mount_all(h, xmnt, &config, NULL, &xylib) < 0)
|
||||
goto done;
|
||||
|
|
@ -753,44 +762,41 @@ yang_schema_find_share(clixon_handle h,
|
|||
}
|
||||
retval = 0;
|
||||
done:
|
||||
if (xylib)
|
||||
xml_free(xylib);
|
||||
if (cvv)
|
||||
cvec_free(cvv);
|
||||
return retval;
|
||||
}
|
||||
|
||||
/*! Get yanglib from user plugin callback, parse it and mount it
|
||||
/*! Given yanglib, mount it, potentially create a new yspec, and parse all its yangs
|
||||
*
|
||||
* Optionally check for shared yspec
|
||||
* @param[in] h Clixon handle
|
||||
* @param[in] xt XML tree node
|
||||
* @retval 1 OK
|
||||
* @retval 0 No yanglib or problem when parsing yanglib
|
||||
* @retval -1 Error
|
||||
* @param[in] h Clixon handle
|
||||
* @param[in] xt XML tree node
|
||||
* @param[in] xyanglib XML yang-lib
|
||||
* @retval 1 OK
|
||||
* @retval 0 No yanglib or problem when parsing yanglib
|
||||
* @retval -1 Error
|
||||
*/
|
||||
int
|
||||
yang_schema_yanglib_parse_mount(clixon_handle h,
|
||||
cxobj *xt)
|
||||
yang_schema_yanglib_mount_parse(clixon_handle h,
|
||||
cxobj *xt,
|
||||
cxobj *xyanglib,
|
||||
yang_stmt **yspecp)
|
||||
{
|
||||
int retval = -1;
|
||||
cxobj *xyanglib = NULL;
|
||||
cxobj *xb;
|
||||
char *domain = NULL;
|
||||
yang_stmt *ymounts;
|
||||
yang_stmt *ydomain;
|
||||
yang_stmt *yspec0 = NULL;
|
||||
yang_stmt *yspec1 = NULL;
|
||||
char *xpath = NULL;
|
||||
char *domain = NULL;
|
||||
cbuf *cb = NULL;
|
||||
int ret;
|
||||
static unsigned int nr = 0;
|
||||
|
||||
/* 1. Get modstate (xyanglib) of node: xyanglib, by querying backend state (via callback)
|
||||
* XXX this xyanglib is not proper RFC8525, submodules appear as modules WHY?
|
||||
*/
|
||||
if (clixon_plugin_yang_mount_all(h, xt, NULL, NULL, &xyanglib) < 0)
|
||||
goto done;
|
||||
if (xyanglib == NULL)
|
||||
goto anydata;
|
||||
if ((xb = xpath_first(xyanglib, NULL, "module-set/name")) != NULL)
|
||||
domain = xml_body(xb);
|
||||
if (domain == NULL){
|
||||
|
|
@ -813,10 +819,8 @@ yang_schema_yanglib_parse_mount(clixon_handle h,
|
|||
goto done;
|
||||
}
|
||||
/* Optimization: find equal yspec from other mount-point */
|
||||
if (clicon_option_bool(h, "CLICON_YANG_SCHEMA_MOUNT_SHARE")) {
|
||||
if (yang_schema_find_share(h, xt, xyanglib, &yspec0) < 0)
|
||||
goto done;
|
||||
}
|
||||
if (yang_schema_find_share(h, xt, xyanglib, &yspec0) < 0)
|
||||
goto done;
|
||||
if ((cb = cbuf_new()) == NULL){
|
||||
clixon_err(OE_YANG, errno, "cbuf_new");
|
||||
goto done;
|
||||
|
|
@ -835,15 +839,54 @@ yang_schema_yanglib_parse_mount(clixon_handle h,
|
|||
}
|
||||
if (xml_yang_mount_set(h, xt, yspec1) < 0)
|
||||
goto done;
|
||||
if (yspecp)
|
||||
*yspecp = yspec1;
|
||||
yspec1 = NULL;
|
||||
retval = 1;
|
||||
done:
|
||||
if (yspec1)
|
||||
ys_free(yspec1);
|
||||
if (cb)
|
||||
cbuf_free(cb);
|
||||
if (xpath)
|
||||
free(xpath);
|
||||
if (yspec1)
|
||||
ys_free(yspec1);
|
||||
return retval;
|
||||
anydata:
|
||||
retval = 0;
|
||||
goto done;
|
||||
}
|
||||
|
||||
/*! Get yanglib from user plugin callback, create yspec, mount it and parse all yangs
|
||||
*
|
||||
* Optionally check for shared yspec
|
||||
* @param[in] h Clixon handle
|
||||
* @param[in] xt XML tree node
|
||||
* @retval 1 OK
|
||||
* @retval 0 No yanglib or problem when parsing yanglib
|
||||
* @retval -1 Error
|
||||
*/
|
||||
int
|
||||
yang_schema_yanglib_get_mount_parse(clixon_handle h,
|
||||
cxobj *xt)
|
||||
{
|
||||
int retval = -1;
|
||||
cxobj *xyanglib = NULL;
|
||||
int ret;
|
||||
|
||||
clixon_debug(CLIXON_DBG_APP, "");
|
||||
/* 1. Get modstate (xyanglib) of node: xyanglib, by querying backend state (via callback)
|
||||
* XXX this xyanglib is not proper RFC8525, submodules appear as modules WHY?
|
||||
*/
|
||||
if (clixon_plugin_yang_mount_all(h, xt, NULL, NULL, &xyanglib) < 0)
|
||||
goto done;
|
||||
if (xyanglib == NULL)
|
||||
goto anydata;
|
||||
if ((ret = yang_schema_yanglib_mount_parse(h, xt, xyanglib, NULL)) < 0)
|
||||
goto done;
|
||||
if (ret == 0)
|
||||
goto anydata;
|
||||
retval = 1;
|
||||
done:
|
||||
if (xyanglib)
|
||||
xml_free(xyanglib);
|
||||
return retval;
|
||||
|
|
|
|||
|
|
@ -55,6 +55,7 @@ module clixon-config {
|
|||
CLICON_XMLDB_SYSTEM_ONLY_CONFIG
|
||||
CLICON_CLI_PIPE_DIR
|
||||
Changed: CLICON_NETCONF_DUPLICATE_ALLOW to not only check but remove duplicates
|
||||
Deprecated: CLICON_YANG_SCHEMA_MOUNT_SHARE
|
||||
Released in Clixon 7.3";
|
||||
}
|
||||
revision 2024-08-01 {
|
||||
|
|
@ -618,8 +619,10 @@ module clixon-config {
|
|||
(yangmnt:mount-point is on same node).
|
||||
A comparison is made between yang modules and revision and must match exactly.
|
||||
If so, a new yang-spec is not created, instead the other is used.
|
||||
Only if CLICON_YANG_SCHEMA_MOUNT is enabled";
|
||||
default false;
|
||||
Only if CLICON_YANG_SCHEMA_MOUNT is enabled
|
||||
Enabled permanently and deprecated when yang domains introduced";
|
||||
status deprecated;
|
||||
default true;
|
||||
}
|
||||
leaf CLICON_YANG_AUGMENT_ACCEPT_BROKEN {
|
||||
type boolean;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue