}
int nb_callback_rpc(const struct nb_node *nb_node, const char *xpath,
- const struct list *input, struct list *output)
+ const struct list *input, struct list *output, char *errmsg,
+ size_t errmsg_len)
{
struct nb_cb_rpc_args args = {};
args.xpath = xpath;
args.input = input;
args.output = output;
+ args.errmsg = errmsg;
+ args.errmsg_len = errmsg_len;
return nb_node->cbs.rpc(&args);
}
/* List of output parameters to be populated by the callback. */
struct list *output;
+
+ /* Buffer to store human-readable error message in case of error. */
+ char *errmsg;
+
+ /* Size of errmsg. */
+ size_t errmsg_len;
};
/*
const void *parent_list_entry,
const struct yang_list_keys *keys);
extern int nb_callback_rpc(const struct nb_node *nb_node, const char *xpath,
- const struct list *input, struct list *output);
+ const struct list *input, struct list *output,
+ char *errmsg, size_t errmsg_len);
/*
* Create a northbound node for all YANG schema nodes.
return CMD_SUCCESS;
}
-int nb_cli_rpc(const char *xpath, struct list *input, struct list *output)
+int nb_cli_rpc(struct vty *vty, const char *xpath, struct list *input,
+ struct list *output)
{
struct nb_node *nb_node;
int ret;
+ char errmsg[BUFSIZ] = {0};
nb_node = nb_node_find(xpath);
if (!nb_node) {
return CMD_WARNING;
}
- ret = nb_callback_rpc(nb_node, xpath, input, output);
+ ret = nb_callback_rpc(nb_node, xpath, input, output, errmsg,
+ sizeof(errmsg));
switch (ret) {
case NB_OK:
return CMD_SUCCESS;
default:
+ if (strlen(errmsg))
+ vty_show_nb_errors(vty, ret, errmsg);
return CMD_WARNING;
}
}
/*
* Execute a YANG RPC or Action.
*
+ * vty
+ * The vty terminal to dump any error.
+ *
* xpath
* XPath of the YANG RPC or Action node.
*
* Returns:
* CMD_SUCCESS on success, CMD_WARNING otherwise.
*/
-extern int nb_cli_rpc(const char *xpath, struct list *input,
+extern int nb_cli_rpc(struct vty *vty, const char *xpath, struct list *input,
struct list *output);
/*
struct yang_data *data;
confd_tag_value_t *reply;
int ret = CONFD_OK;
+ char errmsg[BUFSIZ] = {0};
/* Getting the XPath is tricky. */
if (kp) {
}
/* Execute callback registered for this XPath. */
- if (nb_callback_rpc(nb_node, xpath, input, output) != NB_OK) {
+ if (nb_callback_rpc(nb_node, xpath, input, output, errmsg,
+ sizeof(errmsg))
+ != NB_OK) {
flog_warn(EC_LIB_NB_CB_RPC, "%s: rpc callback failed: %s",
__func__, xpath);
ret = CONFD_ERR;
struct listnode *node;
struct yang_data *data;
const char *xpath;
+ char errmsg[BUFSIZ] = {0};
switch (tag->state) {
case CREATE:
// Execute callback registered for this XPath.
if (nb_callback_rpc(nb_node, xpath, input_list,
- output_list)
+ output_list, errmsg, sizeof(errmsg))
!= NB_OK) {
flog_warn(EC_LIB_NB_CB_RPC,
"%s: rpc callback failed: %s",
struct yang_data *data;
size_t cb_output_cnt;
int ret = SR_ERR_OK;
+ char errmsg[BUFSIZ] = {0};
nb_node = nb_node_find(xpath);
if (!nb_node) {
}
/* Execute callback registered for this XPath. */
- if (nb_callback_rpc(nb_node, xpath, input, output) != NB_OK) {
+ if (nb_callback_rpc(nb_node, xpath, input, output, errmsg,
+ sizeof(errmsg))
+ != NB_OK) {
flog_warn(EC_LIB_NB_CB_RPC, "%s: rpc callback failed: %s",
__func__, xpath);
ret = SR_ERR_OPERATION_FAILED;
listnode_add(input, yang_vrf);
}
- ret = nb_cli_rpc("/frr-ripd:clear-rip-route", input, NULL);
+ ret = nb_cli_rpc(vty, "/frr-ripd:clear-rip-route", input, NULL);
list_delete(&input);
listnode_add(input, yang_vrf);
}
- ret = nb_cli_rpc("/frr-ripngd:clear-ripng-route", input, NULL);
+ ret = nb_cli_rpc(vty, "/frr-ripngd:clear-ripng-route", input, NULL);
list_delete(&input);
if (yang_dup) {
listnode_add(input, yang_dup);
- ret = nb_cli_rpc("/frr-zebra:clear-evpn-dup-addr", input, NULL);
+ ret = nb_cli_rpc(vty, "/frr-zebra:clear-evpn-dup-addr", input,
+ NULL);
}
list_delete(&input);