* Restructure and more generic plugin API (cli,backend,restconf,netconf)

* For preparation for authorization RFC8341
  * Plugins add clixon_plugin_init() and api struct for function pointers, eg:
```
static const struct clixon_plugin_api api = {
    "example",
    clixon_plugin_init,
    ...
}
clixon_plugin_api *clixon_plugin_init(clicon_handle h)
{
    return (void*)&api;
}
```
  * Moved specific plugin functions from apps/ to generic functions in lib/
    * New generic plugin load function: clixon_plugins_load()
  * Removed client-local netconf plugins netconf_plugin_callbacks()
    * This was code used before generic YANG rpc calls
  * Added username to clixon handle:
    * clicon_username_get() / clicon_username_set()
  * Added authentication plugin callback
  * Removed some obscure plugin code that seem not to be used (please report if needed!)
    * CLI parse hook
    * CLICON_FIND_PLUGIN
    * clicon_valcb()
* Removed username to rpc calls (added below)
This commit is contained in:
Olof hagsand 2018-04-02 10:38:53 +02:00
parent b8e35742b9
commit 79e3fbdaa9
41 changed files with 470 additions and 772 deletions

View file

@ -654,13 +654,13 @@ compare_dbs(clicon_handle h,
astext = cv_int32_get(cvec_i(argv, 0));
else
astext = 0;
if (clicon_rpc_get_config(h, "running", "/", NULL, &xc1) < 0)
if (clicon_rpc_get_config(h, "running", "/", &xc1) < 0)
goto done;
if ((xerr = xpath_first(xc1, "/rpc-error")) != NULL){
clicon_rpc_generate_error("Get configuration", xerr);
goto done;
}
if (clicon_rpc_get_config(h, "candidate", "/", NULL, &xc2) < 0)
if (clicon_rpc_get_config(h, "candidate", "/", &xc2) < 0)
goto done;
if ((xerr = xpath_first(xc2, "/rpc-error")) != NULL){
clicon_rpc_generate_error("Get configuration", xerr);
@ -827,7 +827,7 @@ save_config_file(clicon_handle h,
goto done;
}
filename = cv_string_get(cv);
if (clicon_rpc_get_config(h, dbstr,"/", NULL, &xt) < 0)
if (clicon_rpc_get_config(h, dbstr,"/", &xt) < 0)
goto done;
if (xt == NULL){
clicon_err(OE_CFG, 0, "get config: empty tree"); /* Shouldnt happen */
@ -1180,7 +1180,7 @@ cli_copy_config(clicon_handle h,
cprintf(cb, xpath, keyname, fromname);
/* Get from object configuration and store in x1 */
if (clicon_rpc_get_config(h, db, cbuf_get(cb), NULL, &x1) < 0)
if (clicon_rpc_get_config(h, db, cbuf_get(cb), &x1) < 0)
goto done;
if ((xerr = xpath_first(x1, "/rpc-error")) != NULL){
clicon_rpc_generate_error("Get configuration", xerr);

View file

@ -66,13 +66,11 @@
#include "cli_plugin.h"
#include "cli_handle.h"
/*! Name of master plugin functions
* More in clicon_plugin.h
* @note not really used consider documenting or remove
*/
#define PLUGIN_PROMPT_HOOK "plugin_prompt_hook"
#define PLUGIN_PARSE_HOOK "plugin_parse_hook"
#define PLUGIN_SUSP_HOOK "plugin_susp_hook"
/*
@ -380,7 +378,6 @@ cli_plugin_load_dir(clicon_handle h,
struct stat st;
int retval = -1;
/* Format master plugin path */
if ((master_plugin = clicon_master_plugin(h)) == NULL){
clicon_err(OE_PLUGIN, 0, "clicon_master_plugin option not set");
@ -403,8 +400,6 @@ cli_plugin_load_dir(clicon_handle h,
/* Look up certain call-backs in master plugin */
stx->stx_prompt_hook =
dlsym(cp->cp_handle, PLUGIN_PROMPT_HOOK);
stx->stx_parse_hook =
dlsym(cp->cp_handle, PLUGIN_PARSE_HOOK);
stx->stx_susp_hook =
dlsym(cp->cp_handle, PLUGIN_SUSP_HOOK);
INSQ(cp, stx->stx_plugins);
@ -679,15 +674,6 @@ clicon_parse(clicon_handle h,
goto done;
case CG_NOMATCH: /* no match */
smode = NULL;
if (stx->stx_parse_hook) {
/* Try to find a match in upper modes, a'la IOS. */
if ((modename = stx->stx_parse_hook(h, cmd, modename)) != NULL) {
if ((smode = syntax_mode_find(stx, modename, 0)) != NULL)
continue;
else
cli_output(f, "Can't find syntax mode '%s'\n", modename);
}
}
/* clicon_err(OE_CFG, 0, "CLI syntax error: \"%s\": %s",
cmd, cli_nomatch(h));*/
cli_output(f, "CLI syntax error: \"%s\": %s\n",
@ -745,42 +731,14 @@ clicon_cliread(clicon_handle h)
return ret;
}
/*
* cli_find_plugin
* Find a plugin by name and return the dlsym handl
* Used by libclicon code to find callback funcctions in plugins.
*/
static void *
cli_find_plugin(clicon_handle h, char *plugin)
{
struct cli_plugin *p;
p = plugin_find_cli(cli_syntax(h), plugin);
if (p)
return p->cp_handle;
return NULL;
}
/*! Initialize plugin code (not the plugins themselves)
*/
int
cli_plugin_init(clicon_handle h)
{
find_plugin_t *fp = cli_find_plugin;
clicon_hash_t *data = clicon_data(h);
/* Register CLICON_FIND_PLUGIN in data hash */
if (hash_add(data, "CLICON_FIND_PLUGIN", &fp, sizeof(fp)) == NULL) {
clicon_err(OE_UNIX, errno, "failed to register CLICON_FIND_PLUGIN");
return -1;
}
return 0;
}
/*
*
* CLI PLUGIN INTERFACE, PUBLIC SECTION
@ -816,7 +774,6 @@ cli_syntax_mode(clicon_handle h)
return csm->csm_name;
}
/*
* Callback from cli_set_prompt(). Set prompt format for syntax mode
* Arguments:
@ -880,7 +837,6 @@ prompt_fmt (char *prompt, size_t plen, char *fmt, ...)
cprintf(cb, "%c", *s);
s++;
}
done:
if (cb)
fmt = cbuf_get(cb);
@ -905,55 +861,3 @@ cli_prompt(char *fmt)
return prompt;
}
/*! Find a cli plugin based on name and resolve a function pointer in it.
* Callback from clicon_dbvars_parse()
* Find a cli plugin based on name if given and use dlsym to resolve a
* function pointer in it.
* Call the resolved function to get the cgv populated
*/
int
clicon_valcb(void *arg, cvec *vars, cg_var *cgv, char *fname, cg_var *funcarg)
{
char *func;
char *plgnam = NULL;
void *handle;
struct cli_plugin *p;
cli_valcb_t *cb;
clicon_handle h = (clicon_handle)arg;
/* Make copy */
if ((fname = strdup(fname)) == NULL) {
clicon_err(OE_UNIX, errno, "strdup");
return -1;
}
/* Extract plugin name if any */
if ((func = strstr(fname, "::")) != NULL) {
*func = '\0';
func += 2;
plgnam = fname;
}
else
func = fname;
/* If we have specified a plugin name, find the handle to be used
* with dlsym()
*/
handle = NULL;
if (plgnam && (p = plugin_find_cli(cli_syntax(h), plgnam)))
handle = p->cp_handle;
/* Look up function pointer */
if ((cb = dlsym(handle, func)) == NULL) {
clicon_err(OE_UNIX, errno, "unable to find %s()", func);
free(fname);
return -1;
}
free(fname);
if (cb(vars, cgv, funcarg) < 0)
return -1;
return 0;
}

View file

@ -77,10 +77,9 @@ typedef struct {
int stx_nplugins; /* Number of plugins */
struct cli_plugin *stx_plugins; /* List of plugins */
int stx_nmodes; /* Number of syntax modes */
cli_syntaxmode_t *stx_active_mode; /* Current active syntax mode */
cli_syntaxmode_t *stx_modes; /* List of syntax modes */
cli_syntaxmode_t *stx_active_mode; /* Current active syntax mode */
cli_syntaxmode_t *stx_modes; /* List of syntax modes */
cli_prompthook_t *stx_prompt_hook; /* Prompt hook */
cli_parsehook_t *stx_parse_hook; /* Parse mode hook */
cli_susphook_t *stx_susp_hook; /* Ctrl-Z hook from getline() */
} cli_syntax_t;

View file

@ -156,7 +156,7 @@ expand_dbvar(void *h,
goto done;
/* XXX read whole configuration, why not send xpath? */
if (clicon_rpc_get_config(h, dbstr, "/", NULL, &xt) < 0)
if (clicon_rpc_get_config(h, dbstr, "/", &xt) < 0)
goto done;
if ((xerr = xpath_first(xt, "/rpc-error")) != NULL){
clicon_rpc_generate_error("Get configuration", xerr);
@ -487,7 +487,7 @@ cli_show_config(clicon_handle h,
else
cprintf(cbxpath, "%s", xpath);
/* Get configuration from database */
if (clicon_rpc_get_config(h, db, cbuf_get(cbxpath), NULL, &xt) < 0)
if (clicon_rpc_get_config(h, db, cbuf_get(cbxpath), &xt) < 0)
goto done;
if ((xerr = xpath_first(xt, "/rpc-error")) != NULL){
clicon_rpc_generate_error("Get configuration", xerr);
@ -571,7 +571,7 @@ show_conf_xpath(clicon_handle h,
}
cv = cvec_find_var(cvv, "xpath");
xpath = cv_string_get(cv);
if (clicon_rpc_get_config(h, str, xpath, NULL, &xt) < 0)
if (clicon_rpc_get_config(h, str, xpath, &xt) < 0)
goto done;
if ((xerr = xpath_first(xt, "/rpc-error")) != NULL){
clicon_rpc_generate_error("Get configuration", xerr);