From 8f7ae3326276c4c645710b09a4b5851d30dc319f Mon Sep 17 00:00:00 2001 From: Olof hagsand Date: Tue, 7 Feb 2023 17:12:52 +0100 Subject: [PATCH] Yang schema mount: repaired yanglib statedata mountpoint Example: patch to fix "dual xpath" issue --- example/main/example_backend.c | 19 ++++++++++++++++--- lib/src/clixon_yang_schema_mount.c | 2 +- test/test_perf_state.sh | 2 +- test/test_restconf_err.sh | 12 +++++++++++- test/test_yang_schema_mount.sh | 6 ++---- 5 files changed, 31 insertions(+), 10 deletions(-) diff --git a/example/main/example_backend.c b/example/main/example_backend.c index 7aa4bef7..fb29688d 100644 --- a/example/main/example_backend.c +++ b/example/main/example_backend.c @@ -70,6 +70,12 @@ /* Command line options to be passed to getopt(3) */ #define BACKEND_EXAMPLE_OPTS "a:nrsS:x:iuUtV:" +/* Enabling this improves performance in tests, but there may trigger the "double XPath" + * problem. + * Disabling it makes perf go down but makes it safe for "double XPath" + */ +#define _STATEFILTER + /*! Yang action * Start backend with -- -a * where instance-id points to an action node in some YANG @@ -523,13 +529,15 @@ example_statefile(clicon_handle h, { int retval = -1; cxobj **xvec = NULL; - size_t xlen = 0; - int i; cxobj *xt = NULL; yang_stmt *yspec = NULL; FILE *fp = NULL; - cxobj *x1; int ret; +#ifdef _STATEFILTER + size_t xlen = 0; + int i; + cxobj *x1; +#endif /* If -S is set, then read state data from file */ if (!_state || !_state_file) @@ -551,6 +559,7 @@ example_statefile(clicon_handle h, } if (_state_file_cached) xt = _state_xml_cache; +#ifdef _STATEFILTER if (xpath_vec(xt, nsc, "%s", &xvec, &xlen, xpath) < 0) goto done; /* Mark elements to copy: @@ -573,6 +582,10 @@ example_statefile(clicon_handle h, /* Unmark returned state tree */ if (xml_apply(xstate, CX_ELMNT, (xml_applyfn_t*)xml_flag_reset, (void*)(XML_FLAG_MARK|XML_FLAG_CHANGE)) < 0) goto done; +#else + if (xml_copy(xt, xstate) < 0) + goto done; +#endif if (_state_file_cached) xt = NULL; /* ensure cache is not cleared */ ok: diff --git a/lib/src/clixon_yang_schema_mount.c b/lib/src/clixon_yang_schema_mount.c index 3ee11648..adb1b09e 100644 --- a/lib/src/clixon_yang_schema_mount.c +++ b/lib/src/clixon_yang_schema_mount.c @@ -202,7 +202,7 @@ xml_yang_mount_set(cxobj *x, (yu = yang_find(y, Y_UNKNOWN, "yangmnt:mount-point")) == NULL){ goto done; } - if (xml2xpath(x, NULL, 0, &xpath) < 0) + if (xml2xpath(x, NULL, 1, &xpath) < 0) goto done; if ((cvv = yang_cvec_get(yu)) != NULL && (cv = cvec_find(cvv, xpath)) != NULL && diff --git a/test/test_perf_state.sh b/test/test_perf_state.sh index 97b391b3..ca8120d1 100755 --- a/test/test_perf_state.sh +++ b/test/test_perf_state.sh @@ -122,7 +122,7 @@ if [ $RC -ne 0 ]; then fi new "wait restconf" -swait_restconf +wait_restconf rpc="" rpc+="foo" diff --git a/test/test_restconf_err.sh b/test/test_restconf_err.sh index 3241f765..53b7a08d 100755 --- a/test/test_restconf_err.sh +++ b/test/test_restconf_err.sh @@ -163,7 +163,7 @@ EOF # State file with error: wrong namespace cat < $fstate - + x x @@ -305,6 +305,16 @@ new "restconf GET augment multi-namespace, no 2nd module in api-path, fail" expectpart "$(curl $CURLOPTS -X GET $RCPROTO://localhost/restconf/data/augment:route-config/dynamic/ospf)" 0 "HTTP/$HVER 404" '{"ietf-restconf:errors":{"error":{"error-type":"application","error-tag":"invalid-value","error-severity":"error","error-message":"Instance does not exist"}}}' #---------------------------------------------- +# State file with error: wrong namespace +cat < $fstate + + + x + x + + +EOF + # Also generate an invalid state XML. This should generate an "Internal" error and the name of the new "restconf GET failed state" expectpart "$(curl $CURLOPTS -X GET -H 'Accept: application/yang-data+xml' $RCPROTO://localhost/restconf/data?content=nonconfig)" 0 "HTTP/$HVER 412" 'applicationoperation-failedmystateerrorFailed to find YANG spec of XML node: mystate with parent: config in namespace: urn:example:foobar. Internal error, state callback returned invalid XML from plugin: example_backend' diff --git a/test/test_yang_schema_mount.sh b/test/test_yang_schema_mount.sh index 1e8bbf0d..b2036c18 100755 --- a/test/test_yang_schema_mount.sh +++ b/test/test_yang_schema_mount.sh @@ -76,9 +76,9 @@ fi new "wait backend" wait_backend - new "Add two mountpoints: x and y" expecteof_netconf "$clixon_netconf -qf $cfg" 0 "$DEFAULTHELLO" "xy" "" "" + new "netconf commit" expecteof_netconf "$clixon_netconf -qf $cfg" 0 "$DEFAULTHELLO" "" "" "" @@ -86,9 +86,7 @@ new "Retrieve schema-mounts with Operation" expecteof_netconf "$clixon_netconf -qf $cfg" 0 "$DEFAULTHELLO" "" "clixon-exampletrue" new "get yang-lib at mountpoint" -# XXX maybe too many yangs here, difficult to maintain -expecteof_netconf "$clixon_netconf -qf $cfg" 0 "$DEFAULTHELLO" ">" "x -defaultclixon-autocli2022-02-11http://clicon.org/autocliclixon-example2022-11-01urn:example:clixonietf-datastores2018-02-14urn:ietf:params:xml:ns:yang:ietf-datastoresietf-inet-types2021-02-22urn:ietf:params:xml:ns:yang:ietf-inet-typesietf-yang-library2019-01-04urn:ietf:params:xml:ns:yang:ietf-yang-libraryietf-yang-types2013-07-15urn:ietf:params:xml:ns:yang:ietf-yang-typesmount-pointydefaultclixon-autocli2022-02-11http://clicon.org/autocliclixon-example2022-11-01urn:example:clixonietf-datastores2018-02-14urn:ietf:params:xml:ns:yang:ietf-datastoresietf-inet-types2021-02-22urn:ietf:params:xml:ns:yang:ietf-inet-typesietf-yang-library2019-01-04urn:ietf:params:xml:ns:yang:ietf-yang-libraryietf-yang-types2013-07-15urn:ietf:params:xml:ns:yang:ietf-yang-typesmount-point" +expecteof_netconf "$clixon_netconf -qf $cfg" 0 "$DEFAULTHELLO" ">" "xmountclixon-example2022-11-01urn:example:urnymountclixon-example2022-11-01urn:example:urn" if [ $BE -ne 0 ]; then new "Kill backend"