Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 25 additions & 0 deletions lib/northbound.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@
* Renato Westphal
*/

#include <stdlib.h>
#include <unistd.h>
#include <sys/mman.h>
#include <zebra.h>

#include "darr.h"
Expand Down Expand Up @@ -683,6 +686,10 @@ void nb_config_diff(const struct nb_config *config1,
lyd_free_all(diff);
}

#define __dbg(fmt, ...) \
zlog_err("%s: ERROR: " fmt, __func__, ##__VA_ARGS__)

struct lyd_node *rm_set_src_node;
static int dnode_create(struct nb_config *candidate, const char *xpath,
const char *value, uint32_t options,
struct lyd_node **new_dnode)
Expand All @@ -692,6 +699,17 @@ static int dnode_create(struct nb_config *candidate, const char *xpath,

err = lyd_new_path(candidate->dnode, ly_native_ctx, xpath, value,
options, &dnode);
if (dnode) {
__dbg("frr_debug_sonic_create: dnode %p, xpath %s, value %s", dnode, xpath, value);
char *xpath = lyd_path(dnode, LYD_PATH_STD, NULL, 0);
if (xpath &&
!strcmp("/frr-route-map:lib/route-map[name='RM_SET_SRC']/entry[sequence='10']/set-action[action='frr-zebra-route-map:src-address']/rmap-set-action/frr-zebra-route-map:ipv4-src-address", xpath)) {
mprotect(dnode->schema, sizeof(dnode->schema), PROT_READ);
rm_set_src_node = dnode;
free(xpath);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

free should be outside the if block, else there is leak.

}
}

if (err) {
flog_warn(EC_LIB_LIBYANG, "%s: lyd_new_path(%s) failed: %d",
__func__, xpath, err);
Expand Down Expand Up @@ -858,6 +876,7 @@ void nb_candidate_edit_config_changes(struct nb_config *candidate_config,
if (xpath_base == NULL)
xpath_base = "";

__dbg("frr_debug_sonic: num_cfg_changes: '%u'", num_cfg_changes);
/* Edit candidate configuration. */
for (size_t i = 0; i < num_cfg_changes; i++) {
struct nb_cfg_change *change = &cfg_changes[i];
Expand All @@ -875,6 +894,7 @@ void nb_candidate_edit_config_changes(struct nb_config *candidate_config,
change_xpath++; /* skip '.' */
}
strlcat(xpath, change_xpath, sizeof(xpath));
__dbg("frr_debug_sonic: XPath: '%s'", xpath);

/* Find the northbound node associated to the data path. */
nb_node = nb_node_find(xpath);
Expand All @@ -890,13 +910,15 @@ void nb_candidate_edit_config_changes(struct nb_config *candidate_config,
if (error)
*error = true;
}
__dbg("frr_debug_sonic: XPath: '%s', nb_node NULL", xpath);
continue;
}
/* Find if the node to be edited is not a key node */
if (!nb_is_operation_allowed(nb_node, change->operation)) {
zlog_err(" Xpath %s points to key node", xpath);
if (error)
*error = true;
__dbg("frr_debug_sonic: XPath: '%s', nb_is_operation_allowed NULL", xpath);
break;
}

Expand All @@ -910,6 +932,8 @@ void nb_candidate_edit_config_changes(struct nb_config *candidate_config,
* Ignore "not found" errors when editing the candidate
* configuration.
*/
__dbg("frr_debug_sonic: XPath: '%s', value '%s', operation %u", xpath,
value, change->operation);
ret = nb_candidate_edit(candidate_config, nb_node,
change->operation, xpath, NULL, data);
yang_data_free(data);
Expand All @@ -921,6 +945,7 @@ void nb_candidate_edit_config_changes(struct nb_config *candidate_config,
xpath);
if (error)
*error = true;
__dbg("frr_debug_sonic: XPath: '%s', nb_candidate_edit NULL", xpath);
continue;
}
}
Expand Down
2 changes: 2 additions & 0 deletions lib/vty.c
Original file line number Diff line number Diff line change
Expand Up @@ -2845,6 +2845,8 @@ bool vty_read_config(struct nb_config *config, const char *config_file,
{
FILE *confp;

zlog_err("vty_read_config: frr_debug_sonic: config file: %s, config_default_dir %s ",
config_file, config_default_dir);
confp = vty_open_config(config_file, config_default_dir);
if (!confp)
return false;
Expand Down
22 changes: 22 additions & 0 deletions lib/yang.c
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
#include "northbound.h"

#include "lib/config_paths.h"
#include "zlog.h"

DEFINE_MTYPE_STATIC(LIB, YANG_MODULE, "YANG module");
DEFINE_MTYPE_STATIC(LIB, YANG_DATA, "YANG data structure");
Expand Down Expand Up @@ -1343,3 +1344,24 @@ const char *yang_ly_strvecode(LY_VECODE vecode)
}
#endif
}

void debug_lyd_free_tree(struct lyd_node *dnode)
{

zlog_err("%s: ERROR: frr_debug_sonic_free: dnode %p", __func__, dnode);
#undef lyd_free_tree
lyd_free_tree(dnode);
}

static pthread_mutex_t candidate_edit_lock = PTHREAD_MUTEX_INITIALIZER;
LY_ERR debug_lyd_new_path(struct lyd_node *parent, const struct ly_ctx
*ctx, const char *path, const char *value,
uint32_t options, struct lyd_node **node)
{
LY_ERR err;
pthread_mutex_lock(&candidate_edit_lock);
#undef lyd_new_path
err = lyd_new_path(parent, ctx, path, value, options, node);
pthread_mutex_unlock(&candidate_edit_lock);
return err;
}
10 changes: 10 additions & 0 deletions lib/yang.h
Original file line number Diff line number Diff line change
Expand Up @@ -801,6 +801,16 @@ extern LY_ERR yang_lyd_new_list(struct lyd_node_inner *parent,
struct lyd_node **nodes);
extern LY_ERR yang_lyd_trim_xpath(struct lyd_node **rootp, const char *xpath);

#define lyd_free_tree debug_lyd_free_tree

extern void debug_lyd_free_tree(struct lyd_node *dnode);

#define lyd_new_path debug_lyd_new_path

extern LY_ERR debug_lyd_new_path(struct lyd_node *parent, const struct ly_ctx
*ctx, const char *path, const char *value,
uint32_t options, struct lyd_node **node);

#ifdef __cplusplus
}
#endif
Expand Down
120 changes: 119 additions & 1 deletion mgmtd/mgmt_txn.c
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
#include "mgmtd/mgmt.h"
#include "mgmtd/mgmt_memory.h"
#include "mgmtd/mgmt_txn.h"
#include "libyang/libyang.h"

#define __dbg(fmt, ...) \
DEBUGD(&mgmt_debug_txn, "TXN: %s: " fmt, __func__, ##__VA_ARGS__)
Expand Down Expand Up @@ -945,10 +946,112 @@ static int mgmt_txn_create_config_batches(struct mgmt_txn_req *txn_req,
return 0;
}


static void mgmt_print_nb_config_cbs(const char *prefix, struct nb_config_cbs *cfg_chgs)
{
struct nb_config_cb *cb, *nxt;
struct nb_config_change *chg;
char *xpath;

if (!cfg_chgs) {
__dbg("%s: nb_config_cbs is NULL", prefix);
return;
}

__dbg("%s: nb_config_cbs structure: %p", prefix, cfg_chgs);

if (RB_EMPTY(nb_config_cbs, cfg_chgs)) {
__dbg("%s: nb_config_cbs is empty", prefix);
return;
}

RB_FOREACH_SAFE (cb, nb_config_cbs, cfg_chgs, nxt) {
chg = (struct nb_config_change *)cb;

__dbg("%s: Change operation: %d", prefix, chg->cb.operation);
__dbg("%s: Change nb_node: %p", prefix, chg->cb.nb_node);
if (chg->cb.nb_node) {
__dbg("%s: Change nb_node schema: %s", prefix, chg->cb.nb_node->snode->name);
__dbg("%s: Change nb_node module: %s", prefix, chg->cb.nb_node->snode->module->name);
}

__dbg("%s: Change dnode: %p", prefix, chg->cb.dnode);
if (chg->cb.dnode) {
__dbg("%s: Change dnode schema: %s", prefix, chg->cb.dnode->schema->name);
__dbg("%s: Change dnode module: %s", prefix, chg->cb.dnode->schema->module->name);
__dbg("%s: Change dnode type: %d", prefix, chg->cb.dnode->schema->nodetype);

xpath = lyd_path(chg->cb.dnode, LYD_PATH_STD, NULL, 0);
if (xpath) {
__dbg("%s: Change dnode xpath: %s", prefix, xpath);
if (chg->cb.dnode->schema->nodetype & LYD_NODE_TERM) {
const char *value = lyd_get_value(chg->cb.dnode);
__dbg("%s: Change dnode value: %s", prefix, value ? value : "NULL");
}
free(xpath);
}
}
}
}

static void mgmt_print_nb_config(const char *prefix, struct nb_config *nb_config)
{
struct lyd_node *dnode;
struct lyd_node *root, *child;
const char *value;
char *xpath;

if (!nb_config) {
__dbg("%s: nb_config is NULL", prefix);
return;
}

__dbg("%s: nb_config structure: %p", prefix, nb_config);
__dbg("%s: nb_config dnode: %p", prefix, nb_config->dnode);

if (!nb_config->dnode) {
__dbg("%s: nb_config dnode is NULL", prefix);
return;
}

__dbg("%s: nb_config dnode schema: %s", prefix, nb_config->dnode->schema->name);
__dbg("%s: nb_config dnode module: %s", prefix, nb_config->dnode->schema->module->name);
__dbg("%s: nb_config dnode type: %d", prefix, nb_config->dnode->schema->nodetype);

/* Print the root node */
xpath = lyd_path(nb_config->dnode, LYD_PATH_STD, NULL, 0);
if (xpath) {
__dbg("%s: Root node xpath: %s", prefix, xpath);
free(xpath);
}

/* Print all child nodes */
LY_LIST_FOR (nb_config->dnode, root) {
LYD_TREE_DFS_BEGIN (root, child) {
xpath = lyd_path(child, LYD_PATH_STD, NULL, 0);
if (xpath) {
__dbg("%s: Child node %p xpath: %s", prefix, child, xpath);
//__dbg("%s: Child node schema: %s", prefix, child->schema->name);
//__dbg("%s: Child node module: %s", prefix, child->schema->module->name);
//__dbg("%s: Child node type: %d", prefix, child->schema->nodetype);

if (child->schema->nodetype & LYD_NODE_TERM) {
value = lyd_get_value(child);
__dbg("%s: Child node value: %s", prefix, value ? value : "NULL");
}

free(xpath);
}
LYD_TREE_DFS_END(root, child);
}
}
}

extern struct lyd_node *rm_set_src_node;
static int mgmt_txn_prepare_config(struct mgmt_txn_ctx *txn)
{
struct nb_context nb_ctx;
struct nb_config *nb_config;
struct nb_config *nb_config, *dst_nb_config;
struct nb_config_cbs changes;
struct nb_config_cbs *cfg_chgs = NULL;
int ret;
Expand Down Expand Up @@ -1013,6 +1116,17 @@ static int mgmt_txn_prepare_config(struct mgmt_txn_ctx *txn)
goto mgmt_txn_prepare_config_done;
}

if (rm_set_src_node) {
char *xpath = lyd_path(rm_set_src_node, LYD_PATH_STD, NULL, 0);
__dbg("frr_debug_sonic: dnode %p, xpath %s", rm_set_src_node, xpath);
__dbg("frr_debug_sonic: node schema: %s", rm_set_src_node->schema->name);
__dbg("frr_debug_sonic: node module: %s", rm_set_src_node->schema->module->name);
free(xpath);
}
else {
__dbg("frr_debug_sonic: rm_set_src_node is NULL");
}
mgmt_print_nb_config("frr_debug_sonic: SET_CFG src", nb_config);
/*
* Validate YANG contents of the source DS and get the diff
* between source and destination DS contents.
Expand All @@ -1029,13 +1143,17 @@ static int mgmt_txn_prepare_config(struct mgmt_txn_ctx *txn)
ret = -1;
goto mgmt_txn_prepare_config_done;
}
dst_nb_config = mgmt_ds_get_nb_config(
txn->commit_cfg_req->req.commit_cfg.dst_ds_ctx);
mgmt_print_nb_config("frr_debug_sonic: SET_CFG dst", dst_nb_config);

nb_config_diff(mgmt_ds_get_nb_config(txn->commit_cfg_req->req.commit_cfg
.dst_ds_ctx),
nb_config, &changes);
cfg_chgs = &changes;
del_cfg_chgs = true;

mgmt_print_nb_config_cbs("frr_debug_sonic: CONFIG_CHANGES", cfg_chgs);
if (RB_EMPTY(nb_config_cbs, cfg_chgs)) {
/*
* This means there's no changes to commit whatsoever
Expand Down