Fixed memory error in RESTCONF PATCH/PUT when accessing top-level data node.

This commit is contained in:
Olof hagsand 2020-12-09 13:38:57 +01:00
parent b8641f30bd
commit d6db28c47a
3 changed files with 28 additions and 7 deletions

View file

@ -79,6 +79,7 @@ Developers may need to change their code
### Corrected Bugs ### Corrected Bugs
* Fixed error memory in RESTCONF PATCH/PUT when accessing top-level data node.
* Fixed: [ Calling copy-config RPC from restconf #158](https://github.com/clicon/clixon/issues/158) * Fixed: [ Calling copy-config RPC from restconf #158](https://github.com/clicon/clixon/issues/158)
* Fixed: [namespace prefix nc is not supported in full #154](https://github.com/clicon/clixon/issues/154) * Fixed: [namespace prefix nc is not supported in full #154](https://github.com/clicon/clixon/issues/154)
* edit-config "config" parameter did not work with prefix other than null * edit-config "config" parameter did not work with prefix other than null

View file

@ -479,10 +479,22 @@ api_data_write(clicon_handle h,
* Replace xparent with x, ie bottom of api-path with data * Replace xparent with x, ie bottom of api-path with data
*/ */
dname = xml_name(xdata); dname = xml_name(xdata);
if (api_path==NULL && strcmp(dname,"data")==0){ if (api_path==NULL) {
if (strcmp(dname, "data")!=0){
if (netconf_bad_element_xml(&xerr, "application", dname,
"Data element does not match top-level data") < 0)
goto done;
if ((xe = xpath_first(xerr, NULL, "rpc-error")) == NULL){
clicon_err(OE_XML, EINVAL, "rpc-error not found (internal error)");
goto done;
}
if (api_return_err(h, req, xe, pretty, media_out, 0) < 0)
goto done;
goto ok;
}
if (xml_addsub(NULL, xdata) < 0) if (xml_addsub(NULL, xdata) < 0)
goto done; goto done;
if (xtop) if (xtop) /* also xbot */
xml_free(xtop); xml_free(xtop);
xtop = xdata; xtop = xdata;
xml_name_set(xtop, "config"); xml_name_set(xtop, "config");
@ -494,7 +506,7 @@ api_data_write(clicon_handle h,
goto done; goto done;
} }
} }
else { else { /* api-path != NULL */
/* There is an api-path that defines an element in the datastore tree. /* There is an api-path that defines an element in the datastore tree.
* Not top-of-tree. * Not top-of-tree.
*/ */
@ -502,7 +514,8 @@ api_data_write(clicon_handle h,
/* Check same symbol in api-path as data */ /* Check same symbol in api-path as data */
if (strcmp(dname, xml_name(xbot))){ if (strcmp(dname, xml_name(xbot))){
if (netconf_operation_failed_xml(&xerr, "protocol", "Not same symbol in api-path as data") < 0) if (netconf_bad_element_xml(&xerr, "application", dname,
"Data element does not match api-path") < 0)
goto done; goto done;
if ((xe = xpath_first(xerr, NULL, "rpc-error")) == NULL){ if ((xe = xpath_first(xerr, NULL, "rpc-error")) == NULL){
clicon_err(OE_XML, EINVAL, "rpc-error not found (internal error)"); clicon_err(OE_XML, EINVAL, "rpc-error not found (internal error)");
@ -564,8 +577,9 @@ api_data_write(clicon_handle h,
} }
} }
} }
xml_purge(xbot); if (xtop != xbot) /* Should always be true */
if (xml_addsub(xparent, xdata) < 0) xml_purge(xbot);
if (xml_addsub(xparent, xdata) < 0)
goto done; goto done;
/* If restconf insert/point attributes are present, translate to netconf */ /* If restconf insert/point attributes are present, translate to netconf */
if (restconf_insert_attributes(xdata, qvec) < 0) if (restconf_insert_attributes(xdata, qvec) < 0)
@ -584,7 +598,7 @@ api_data_write(clicon_handle h,
if (namespace && strcmp(namespace, xml_value(xa))==0) if (namespace && strcmp(namespace, xml_value(xa))==0)
xml_purge(xa); xml_purge(xa);
} }
} } /* api-path != NULL */
/* For internal XML protocol: add username attribute for access control /* For internal XML protocol: add username attribute for access control
*/ */
username = clicon_username_get(h); username = clicon_username_get(h);

View file

@ -236,6 +236,12 @@ expectpart "$(curl -u andy:bar $CURLOPTS -X PATCH -H 'Content-Type: application/
new "The key leaf values MUST be the same as the key leaf values in the request" new "The key leaf values MUST be the same as the key leaf values in the request"
expectpart "$(curl -u andy:bar $CURLOPTS -X PATCH -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/data/example-jukebox:jukebox/library/artist=Clash/album=London%20Calling -d '{"example-jukebox:album":{"name":"The Clash"}}')" 0 'HTTP/1.1 412 Precondition Failed' expectpart "$(curl -u andy:bar $CURLOPTS -X PATCH -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/data/example-jukebox:jukebox/library/artist=Clash/album=London%20Calling -d '{"example-jukebox:album":{"name":"The Clash"}}')" 0 'HTTP/1.1 412 Precondition Failed'
new "PATCH on root resource extra c" # merge extra/c
expectpart "$(curl -u andy:bar $CURLOPTS -X PATCH -H "Content-Type: application/yang-data+json" $RCPROTO://localhost/restconf/data -d '{"ietf-restconf:data":{"example-jukebox:extra":"c"}}')" 0 "HTTP/1.1 204 No Content"
new "GET check" # XXX: "data" should probably be namespaced?
expectpart "$(curl -u andy:bar $CURLOPTS -X GET $RCPROTO://localhost/restconf/data?content=config -H 'Accept: application/yang-data+xml')" 0 'HTTP/1.1 200 OK' '<extra xmlns="http://example.com/ns/example-jukebox">c</extra>' '<data>'
if [ $RC -ne 0 ]; then if [ $RC -ne 0 ]; then
new "Kill restconf daemon" new "Kill restconf daemon"
stop_restconf stop_restconf