CLI edit modes and mountpoints
This commit is contained in:
parent
4b49953461
commit
bd5b51d860
6 changed files with 138 additions and 69 deletions
|
|
@ -1,5 +1,6 @@
|
||||||
# Clixon Changelog
|
# Clixon Changelog
|
||||||
|
|
||||||
|
* [6.3.0](#630) Expected: July 2023
|
||||||
* [6.2.0](#620) 30 April 2023
|
* [6.2.0](#620) 30 April 2023
|
||||||
* [6.1.0](#610) 19 Feb 2023
|
* [6.1.0](#610) 19 Feb 2023
|
||||||
* [6.0.0](#600) 29 Nov 2022
|
* [6.0.0](#600) 29 Nov 2022
|
||||||
|
|
@ -39,6 +40,13 @@
|
||||||
* [3.3.2](#332) Aug 27 2017
|
* [3.3.2](#332) Aug 27 2017
|
||||||
* [3.3.1](#331) June 7 2017
|
* [3.3.1](#331) June 7 2017
|
||||||
|
|
||||||
|
## 6.3.0
|
||||||
|
Expected: July 2023
|
||||||
|
|
||||||
|
### Corrected Bugs
|
||||||
|
|
||||||
|
* Fixed autocli edit modes for schema mounts
|
||||||
|
|
||||||
## 6.2.0
|
## 6.2.0
|
||||||
30 April 2023
|
30 April 2023
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -97,40 +97,16 @@ co2apipath(cg_obj *co)
|
||||||
return cv_string_get(cv);
|
return cv_string_get(cv);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Append to cvv1 to cvv0
|
|
||||||
* @note if cvv0 is non-null, the first element of cvv1 is skipped
|
|
||||||
*/
|
|
||||||
static cvec*
|
|
||||||
cvec_append(cvec *cvv0,
|
|
||||||
cvec *cvv1)
|
|
||||||
{
|
|
||||||
cvec *cvv2 = NULL;
|
|
||||||
cg_var *cv;
|
|
||||||
|
|
||||||
if (cvv0 == NULL){
|
|
||||||
if ((cvv2 = cvec_dup(cvv1)) == NULL){
|
|
||||||
clicon_err(OE_UNIX, errno, "cvec_dup");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else{
|
|
||||||
if ((cvv2 = cvec_dup(cvv0)) == NULL){
|
|
||||||
clicon_err(OE_UNIX, errno, "cvec_dup");
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
cv = NULL; /* Append cvv1 to cvv2 */
|
|
||||||
while ((cv = cvec_each1(cvv1, cv)) != NULL)
|
|
||||||
cvec_append_var(cvv2, cv);
|
|
||||||
}
|
|
||||||
return cvv2;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*! Enter a CLI edit mode
|
/*! Enter a CLI edit mode
|
||||||
|
*
|
||||||
* @param[in] h CLICON handle
|
* @param[in] h CLICON handle
|
||||||
* @param[in] cvv Vector of variables from CLIgen command-line
|
* @param[in] cvv Vector of variables from CLIgen command-line
|
||||||
* @param[in] argv Vector of user-supplied keywords
|
* @param[in] argv Vector of user-supplied keywords
|
||||||
|
* @retval 0 OK
|
||||||
|
* @retval -1 Error
|
||||||
* Format of argv:
|
* Format of argv:
|
||||||
* <api_path_fmt> Generated API PATH (This is where we are in the tree)
|
* <api_path_fmt> Generated API PATH (This is where we are in the tree)
|
||||||
|
* [<api-path-fmt>] Extra api-path from mount-point
|
||||||
* <treename> Name of generated cligen parse-tree, eg "datamodel"
|
* <treename> Name of generated cligen parse-tree, eg "datamodel"
|
||||||
* Note api_path_fmt is not used in code but must be there in order to pick coorig from matching
|
* Note api_path_fmt is not used in code but must be there in order to pick coorig from matching
|
||||||
* code
|
* code
|
||||||
|
|
@ -143,19 +119,28 @@ cli_auto_edit(clicon_handle h,
|
||||||
int retval = -1;
|
int retval = -1;
|
||||||
char *api_path_fmt; /* xml key format */
|
char *api_path_fmt; /* xml key format */
|
||||||
char *api_path = NULL;
|
char *api_path = NULL;
|
||||||
cg_var *cv;
|
|
||||||
char *treename;
|
char *treename;
|
||||||
pt_head *ph;
|
pt_head *ph;
|
||||||
cg_obj *co;
|
cg_obj *co;
|
||||||
cg_obj *coorig;
|
cg_obj *coorig;
|
||||||
cvec *cvv2 = NULL; /* cvv2 = cvv0 + cvv1 */
|
cvec *cvv2 = NULL; /* cvv2 = cvv0 + cvv1 */
|
||||||
|
int argc = 0;
|
||||||
|
char *str;
|
||||||
|
char *mtpoint = NULL;
|
||||||
|
|
||||||
if (cvec_len(argv) != 2){
|
if (cvec_len(argv) != 2 && cvec_len(argv) != 3){
|
||||||
clicon_err(OE_PLUGIN, EINVAL, "Usage: %s(api_path_fmt>, <treename>)", __FUNCTION__);
|
clicon_err(OE_PLUGIN, EINVAL, "Usage: %s(api_path_fmt>*, <treename>)", __FUNCTION__);
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
cv = cvec_i(argv, 1);
|
api_path_fmt = cv_string_get(cvec_i(argv, argc++));
|
||||||
treename = cv_string_get(cv);
|
str = cv_string_get(cvec_i(argv, argc++));
|
||||||
|
if (str && str[0] == '/'){ /* ad-hoc to see if 2nd arg is mountpoint */
|
||||||
|
mtpoint = str;
|
||||||
|
clicon_debug(1, "%s mtpoint:%s", __FUNCTION__, mtpoint);
|
||||||
|
treename = cv_string_get(cvec_i(argv, argc++));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
treename = str;
|
||||||
/* Find current cligen tree */
|
/* Find current cligen tree */
|
||||||
if ((ph = cligen_ph_find(cli_cligen(h), treename)) == NULL){
|
if ((ph = cligen_ph_find(cli_cligen(h), treename)) == NULL){
|
||||||
clicon_err(OE_PLUGIN, 0, "No such parsetree header: %s", treename);
|
clicon_err(OE_PLUGIN, 0, "No such parsetree header: %s", treename);
|
||||||
|
|
@ -191,6 +176,15 @@ cli_auto_edit(clicon_handle h,
|
||||||
/* Store this as edit-mode */
|
/* Store this as edit-mode */
|
||||||
if (clicon_data_set(h, "cli-edit-mode", api_path) < 0)
|
if (clicon_data_set(h, "cli-edit-mode", api_path) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
|
if (mtpoint){
|
||||||
|
char *mtpoint2;
|
||||||
|
if ((mtpoint2 = strdup(mtpoint)) == NULL){
|
||||||
|
clicon_err(OE_UNIX, errno, "strdup");
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
|
if (clicon_data_set(h, "cli-edit-mtpoint", mtpoint2) < 0)
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
if (clicon_data_cvec_set(h, "cli-edit-cvv", cvv2) < 0)
|
if (clicon_data_cvec_set(h, "cli-edit-cvv", cvv2) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
if (co->co_filter){
|
if (co->co_filter){
|
||||||
|
|
@ -437,12 +431,13 @@ struct findpt_arg{
|
||||||
};
|
};
|
||||||
|
|
||||||
/*! Iterate through parse-tree to find first argument set by cli_generate code
|
/*! Iterate through parse-tree to find first argument set by cli_generate code
|
||||||
|
*
|
||||||
* @see cg_applyfn_t
|
* @see cg_applyfn_t
|
||||||
* @param[in] co CLIgen parse-tree object
|
* @param[in] co CLIgen parse-tree object
|
||||||
* @param[in] arg Argument, cast to application-specific info
|
* @param[in] arg Argument, cast to application-specific info
|
||||||
* @retval -1 Error: break and return
|
|
||||||
* @retval 0 OK and continue
|
|
||||||
* @retval 1 OK and return (abort iteration)
|
* @retval 1 OK and return (abort iteration)
|
||||||
|
* @retval 0 OK and continue
|
||||||
|
* @retval -1 Error: break and return
|
||||||
*/
|
*/
|
||||||
static int
|
static int
|
||||||
cli_auto_findpt(cg_obj *co,
|
cli_auto_findpt(cg_obj *co,
|
||||||
|
|
|
||||||
|
|
@ -1593,3 +1593,31 @@ cli_restart_plugin(clicon_handle h,
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Append cvv1 to cvv0 and return a new cvec
|
||||||
|
*
|
||||||
|
* @note if cvv0 is non-null, the first element of cvv1 is skipped
|
||||||
|
*/
|
||||||
|
cvec*
|
||||||
|
cvec_append(cvec *cvv0,
|
||||||
|
cvec *cvv1)
|
||||||
|
{
|
||||||
|
cvec *cvv2 = NULL;
|
||||||
|
cg_var *cv;
|
||||||
|
|
||||||
|
if (cvv0 == NULL){
|
||||||
|
if ((cvv2 = cvec_dup(cvv1)) == NULL){
|
||||||
|
clicon_err(OE_UNIX, errno, "cvec_dup");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else{
|
||||||
|
if ((cvv2 = cvec_dup(cvv0)) == NULL){
|
||||||
|
clicon_err(OE_UNIX, errno, "cvec_dup");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
cv = NULL; /* Append cvv1 to cvv2 */
|
||||||
|
while ((cv = cvec_each1(cvv1, cv)) != NULL)
|
||||||
|
cvec_append_var(cvv2, cv);
|
||||||
|
}
|
||||||
|
return cvv2;
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -39,9 +39,10 @@
|
||||||
#ifndef _CLI_COMMON_H_
|
#ifndef _CLI_COMMON_H_
|
||||||
#define _CLI_COMMON_H_
|
#define _CLI_COMMON_H_
|
||||||
|
|
||||||
void cli_signal_block(clicon_handle h);
|
void cli_signal_block(clicon_handle h);
|
||||||
void cli_signal_unblock(clicon_handle h);
|
void cli_signal_unblock(clicon_handle h);
|
||||||
int mtpoint_paths(yang_stmt *yspec0, char *mtpoint, char *api_path_fmt1, char **api_path_fmt01);
|
int mtpoint_paths(yang_stmt *yspec0, char *mtpoint, char *api_path_fmt1, char **api_path_fmt01);
|
||||||
|
cvec *cvec_append(cvec *cvv0, cvec *cvv1);
|
||||||
|
|
||||||
/* If you do not find a function here it may be in clixon_cli_api.h which is
|
/* If you do not find a function here it may be in clixon_cli_api.h which is
|
||||||
the external API */
|
the external API */
|
||||||
|
|
|
||||||
|
|
@ -52,6 +52,7 @@
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <dirent.h>
|
#include <dirent.h>
|
||||||
#include <syslog.h>
|
#include <syslog.h>
|
||||||
|
#include <pwd.h>
|
||||||
#include <arpa/inet.h>
|
#include <arpa/inet.h>
|
||||||
#include <netinet/in.h>
|
#include <netinet/in.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
|
|
@ -60,7 +61,6 @@
|
||||||
#include <sys/wait.h>
|
#include <sys/wait.h>
|
||||||
#include <sys/param.h>
|
#include <sys/param.h>
|
||||||
#include <sys/mount.h>
|
#include <sys/mount.h>
|
||||||
#include <pwd.h>
|
|
||||||
|
|
||||||
/* cligen */
|
/* cligen */
|
||||||
#include <cligen/cligen.h>
|
#include <cligen/cligen.h>
|
||||||
|
|
@ -216,6 +216,9 @@ expand_dbvar(void *h,
|
||||||
yang_stmt *ytype;
|
yang_stmt *ytype;
|
||||||
char *mtpoint = NULL;
|
char *mtpoint = NULL;
|
||||||
yang_stmt *yspec0 = NULL;
|
yang_stmt *yspec0 = NULL;
|
||||||
|
yang_stmt *yspec;
|
||||||
|
yang_stmt *yu = NULL;
|
||||||
|
cvec *nsc0 = NULL;
|
||||||
|
|
||||||
if (argv == NULL || (cvec_len(argv) != 2 && cvec_len(argv) != 3)){
|
if (argv == NULL || (cvec_len(argv) != 2 && cvec_len(argv) != 3)){
|
||||||
clicon_err(OE_PLUGIN, EINVAL, "requires arguments: <db> <apipathfmt> [<mountpt>]");
|
clicon_err(OE_PLUGIN, EINVAL, "requires arguments: <db> <apipathfmt> [<mountpt>]");
|
||||||
|
|
@ -245,24 +248,12 @@ expand_dbvar(void *h,
|
||||||
cv = cvec_i(argv, 2);
|
cv = cvec_i(argv, 2);
|
||||||
mtpoint = cv_string_get(cv);
|
mtpoint = cv_string_get(cv);
|
||||||
}
|
}
|
||||||
if (mtpoint){
|
/* api_path_fmt = /interface/%s/address/%s
|
||||||
/* Get combined api-path01 */
|
* api_path: --> /interface/eth0/address/.*
|
||||||
if (mtpoint_paths(yspec0, mtpoint, api_path_fmt, &api_path_fmt01) < 0)
|
* xpath: --> /interface/[name="eth0"]/address
|
||||||
goto done;
|
*/
|
||||||
/* Transform template format string + cvv to actual api-path
|
if (api_path_fmt2api_path(api_path_fmt, cvv, &api_path, &cvvi) < 0)
|
||||||
* cvv_i indicates if all cvv entries were used
|
goto done;
|
||||||
*/
|
|
||||||
if (api_path_fmt2api_path(api_path_fmt01, cvv, &api_path, &cvvi) < 0)
|
|
||||||
goto done;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
/* api_path_fmt = /interface/%s/address/%s
|
|
||||||
* api_path: --> /interface/eth0/address/.*
|
|
||||||
* xpath: --> /interface/[name="eth0"]/address
|
|
||||||
*/
|
|
||||||
if (api_path_fmt2api_path(api_path_fmt, cvv, &api_path, &cvvi) < 0)
|
|
||||||
goto done;
|
|
||||||
}
|
|
||||||
/* Create config top-of-tree */
|
/* Create config top-of-tree */
|
||||||
if ((xtop = xml_new(DATASTORE_TOP_SYMBOL, NULL, CX_ELMNT)) == NULL)
|
if ((xtop = xml_new(DATASTORE_TOP_SYMBOL, NULL, CX_ELMNT)) == NULL)
|
||||||
goto done;
|
goto done;
|
||||||
|
|
@ -271,8 +262,15 @@ expand_dbvar(void *h,
|
||||||
* xpath2xml would have worked!!
|
* xpath2xml would have worked!!
|
||||||
* XXX: but y is just the first in this list, there could be other y:s?
|
* XXX: but y is just the first in this list, there could be other y:s?
|
||||||
*/
|
*/
|
||||||
|
yspec = yspec0; /* may be reset to mount yspec below */
|
||||||
if (api_path){
|
if (api_path){
|
||||||
if ((ret = api_path2xml(api_path, yspec0, xtop, YC_DATANODE, 0, &xbot, &y, &xerr)) < 0)
|
if (mtpoint){
|
||||||
|
if (yang_path_arg(yspec0, mtpoint, &yu) < 0)
|
||||||
|
goto done;
|
||||||
|
if (yang_mount_get(yu, mtpoint, &yspec) < 0)
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
|
if ((ret = api_path2xml(api_path, yspec, xtop, YC_DATANODE, 0, &xbot, &y, &xerr)) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
if (ret == 0){
|
if (ret == 0){
|
||||||
// XXX cf cli_dbxml
|
// XXX cf cli_dbxml
|
||||||
|
|
@ -283,13 +281,20 @@ expand_dbvar(void *h,
|
||||||
if (y==NULL)
|
if (y==NULL)
|
||||||
goto ok;
|
goto ok;
|
||||||
/* Transform api-path to xpath for netconf */
|
/* Transform api-path to xpath for netconf */
|
||||||
if (api_path2xpath(api_path, yspec0, &xpath, &nsc, NULL) < 0)
|
if (api_path2xpath(api_path, yspec, &xpath, &nsc, NULL) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
|
|
||||||
if ((cbxpath = cbuf_new()) == NULL){
|
if ((cbxpath = cbuf_new()) == NULL){
|
||||||
clicon_err(OE_UNIX, errno, "cbuf_new");
|
clicon_err(OE_UNIX, errno, "cbuf_new");
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
if (mtpoint){
|
||||||
|
cprintf(cbxpath, "%s", mtpoint);
|
||||||
|
if (xml_nsctx_yangspec(yspec0, &nsc0) < 0)
|
||||||
|
goto done;
|
||||||
|
cv = NULL; /* Append cvv1 to cvv2 */
|
||||||
|
while ((cv = cvec_each(nsc0, cv)) != NULL)
|
||||||
|
cvec_append_var(nsc, cv);
|
||||||
|
}
|
||||||
cprintf(cbxpath, "%s", xpath);
|
cprintf(cbxpath, "%s", xpath);
|
||||||
if (clicon_option_bool(h, "CLICON_CLI_EXPAND_LEAFREF") &&
|
if (clicon_option_bool(h, "CLICON_CLI_EXPAND_LEAFREF") &&
|
||||||
(ytype = yang_find(y, Y_TYPE, NULL)) != NULL &&
|
(ytype = yang_find(y, Y_TYPE, NULL)) != NULL &&
|
||||||
|
|
@ -376,6 +381,8 @@ expand_dbvar(void *h,
|
||||||
ok:
|
ok:
|
||||||
retval = 0;
|
retval = 0;
|
||||||
done:
|
done:
|
||||||
|
if (nsc0)
|
||||||
|
cvec_free(nsc0);
|
||||||
if (api_path_fmt01)
|
if (api_path_fmt01)
|
||||||
free(api_path_fmt01);
|
free(api_path_fmt01);
|
||||||
if (cbxpath)
|
if (cbxpath)
|
||||||
|
|
@ -558,7 +565,7 @@ done:
|
||||||
* @param[in] argc Index into argv
|
* @param[in] argc Index into argv
|
||||||
* @param[out] format Output format
|
* @param[out] format Output format
|
||||||
* @retval 0 OK
|
* @retval 0 OK
|
||||||
* @retval -1 Error
|
* @retval -1 Error
|
||||||
*/
|
*/
|
||||||
static int
|
static int
|
||||||
cli_show_option_format(cvec *argv,
|
cli_show_option_format(cvec *argv,
|
||||||
|
|
@ -584,7 +591,7 @@ cli_show_option_format(cvec *argv,
|
||||||
* @param[in] argc Index into argv
|
* @param[in] argc Index into argv
|
||||||
* @param[out] bool result boolean: 0 or 1
|
* @param[out] bool result boolean: 0 or 1
|
||||||
* @retval 0 OK
|
* @retval 0 OK
|
||||||
* @retval -1 Error
|
* @retval -1 Error
|
||||||
*/
|
*/
|
||||||
static int
|
static int
|
||||||
cli_show_option_bool(cvec *argv,
|
cli_show_option_bool(cvec *argv,
|
||||||
|
|
@ -624,7 +631,7 @@ cli_show_option_bool(cvec *argv,
|
||||||
* @param[in] withdefault RFC 6243 with-default modes
|
* @param[in] withdefault RFC 6243 with-default modes
|
||||||
* @param[in] extdefault with-defaults with propriatary extensions
|
* @param[in] extdefault with-defaults with propriatary extensions
|
||||||
* @retval 0 OK
|
* @retval 0 OK
|
||||||
* @retval -1 Error
|
* @retval -1 Error
|
||||||
*/
|
*/
|
||||||
static int
|
static int
|
||||||
cli_show_option_withdefault(cvec *argv,
|
cli_show_option_withdefault(cvec *argv,
|
||||||
|
|
@ -988,8 +995,6 @@ cli_show_auto(clicon_handle h,
|
||||||
* @endcode
|
* @endcode
|
||||||
* @see cli_show_auto autocli with expansion
|
* @see cli_show_auto autocli with expansion
|
||||||
* @see cli_show_config with no autocli coupling
|
* @see cli_show_config with no autocli coupling
|
||||||
*
|
|
||||||
* XXX merge cli_show_auto and cli_show_auto_mode
|
|
||||||
*/
|
*/
|
||||||
int
|
int
|
||||||
cli_show_auto_mode(clicon_handle h,
|
cli_show_auto_mode(clicon_handle h,
|
||||||
|
|
@ -1008,13 +1013,23 @@ cli_show_auto_mode(clicon_handle h,
|
||||||
int argc = 0;
|
int argc = 0;
|
||||||
int skiptop = 0;
|
int skiptop = 0;
|
||||||
char *xpath = NULL;
|
char *xpath = NULL;
|
||||||
|
yang_stmt *yspec0;
|
||||||
yang_stmt *yspec;
|
yang_stmt *yspec;
|
||||||
char *api_path = NULL;
|
char *api_path = NULL;
|
||||||
|
char *mtpoint = NULL;
|
||||||
|
yang_stmt *yu;
|
||||||
|
cbuf *cbxpath = NULL;
|
||||||
|
cvec *nsc0 = NULL;
|
||||||
|
cg_var *cv;
|
||||||
|
|
||||||
if (cvec_len(argv) < 2 || cvec_len(argv) > 7){
|
if (cvec_len(argv) < 2 || cvec_len(argv) > 7){
|
||||||
clicon_err(OE_PLUGIN, EINVAL, "Received %d arguments. Expected: <database> [ <format> <pretty> <state> <default> <cli-prefix>]", cvec_len(argv));
|
clicon_err(OE_PLUGIN, EINVAL, "Received %d arguments. Expected: <database> [ <format> <pretty> <state> <default> <cli-prefix>]", cvec_len(argv));
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
if ((yspec0 = clicon_dbspec_yang(h)) == NULL){
|
||||||
|
clicon_err(OE_FATAL, 0, "No DB_SPEC");
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
dbname = cv_string_get(cvec_i(argv, argc++));
|
dbname = cv_string_get(cvec_i(argv, argc++));
|
||||||
if (cvec_len(argv) > argc)
|
if (cvec_len(argv) > argc)
|
||||||
if (cli_show_option_format(argv, argc++, &format) < 0)
|
if (cli_show_option_format(argv, argc++, &format) < 0)
|
||||||
|
|
@ -1041,23 +1056,44 @@ cli_show_auto_mode(clicon_handle h,
|
||||||
;
|
;
|
||||||
else
|
else
|
||||||
api_path = "/";
|
api_path = "/";
|
||||||
if ((yspec = clicon_dbspec_yang(h)) == NULL){
|
if (clicon_data_get(h, "cli-edit-mtpoint", &mtpoint) == 0 && strlen(mtpoint)){
|
||||||
clicon_err(OE_FATAL, 0, "No DB_SPEC");
|
if (yang_path_arg(yspec0, mtpoint, &yu) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
|
if (yang_mount_get(yu, mtpoint, &yspec) < 0)
|
||||||
|
goto done;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
yspec = yspec0;
|
||||||
if (api_path2xpath(api_path, yspec, &xpath, &nsc, NULL) < 0)
|
if (api_path2xpath(api_path, yspec, &xpath, &nsc, NULL) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
if (xpath == NULL){
|
if (xpath == NULL){
|
||||||
clicon_err(OE_FATAL, 0, "Invalid api-path: %s", api_path);
|
clicon_err(OE_FATAL, 0, "Invalid api-path: %s", api_path);
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
if ((cbxpath = cbuf_new()) == NULL){
|
||||||
|
clicon_err(OE_UNIX, errno, "cbuf_new");
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
|
if (mtpoint){
|
||||||
|
cprintf(cbxpath, "%s", mtpoint);
|
||||||
|
if (xml_nsctx_yangspec(yspec0, &nsc0) < 0)
|
||||||
|
goto done;
|
||||||
|
cv = NULL; /* Append cvv1 to cvv2 */
|
||||||
|
while ((cv = cvec_each(nsc0, cv)) != NULL)
|
||||||
|
cvec_append_var(nsc, cv);
|
||||||
|
}
|
||||||
|
cprintf(cbxpath, "%s", xpath);
|
||||||
skiptop = (strcmp(xpath,"/") != 0);
|
skiptop = (strcmp(xpath,"/") != 0);
|
||||||
if (cli_show_common(h, dbname, format, pretty, state,
|
if (cli_show_common(h, dbname, format, pretty, state,
|
||||||
withdefault, extdefault,
|
withdefault, extdefault,
|
||||||
prepend, xpath, nsc, skiptop) < 0)
|
prepend, cbuf_get(cbxpath), nsc, skiptop) < 0)
|
||||||
goto done;
|
goto done;
|
||||||
retval = 0;
|
retval = 0;
|
||||||
done:
|
done:
|
||||||
|
if (nsc0)
|
||||||
|
cvec_free(nsc0);
|
||||||
|
if (cbxpath)
|
||||||
|
cbuf_free(cbxpath);
|
||||||
if (nsc)
|
if (nsc)
|
||||||
xml_nsctx_free(nsc);
|
xml_nsctx_free(nsc);
|
||||||
if (xpath)
|
if (xpath)
|
||||||
|
|
|
||||||
|
|
@ -319,6 +319,7 @@ xml_nsctx_node(cxobj *xn,
|
||||||
* xml_nsctx_free(nsc)
|
* xml_nsctx_free(nsc)
|
||||||
* @endcode
|
* @endcode
|
||||||
* @see RFC7950 Sections 6.4.1 (and 9.9.2?)
|
* @see RFC7950 Sections 6.4.1 (and 9.9.2?)
|
||||||
|
* @see xml_nsctx_yangspec
|
||||||
* @note Assume yn is in a yang structure (eg has parents and belongs to a (sub)module)
|
* @note Assume yn is in a yang structure (eg has parents and belongs to a (sub)module)
|
||||||
*/
|
*/
|
||||||
int
|
int
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue