static int
md_nkn_events_commit_apply(md_commit *commit,
                     const mdb_db *old_db, const mdb_db *new_db,
                     mdb_db_change_array *change_list, void *arg)
{
    int err = 0;
    int i = 0, num_changes = 0;
    const mdb_db_change *change = NULL;
    tstring *val = NULL;
    tstring *source  = NULL;

    num_changes = mdb_db_change_array_length_quick (change_list);
    for (i = 0; i < num_changes; i++)
    {
	change = mdb_db_change_array_get_quick (change_list, i);
	bail_null (change);

	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "net", "interface", "config", "*", "offloading", "gro", "enable"))
		&& (mdct_modify == change->mdc_change_type || mdct_add == change->mdc_change_type))
	{
	    const char *intf_name = NULL;
	    const bn_attrib *new_val = NULL;
	    uint32_t gro_toggle = 0;
	    ts_free(&source);
	    node_name_t intf_nd = {0};
	    tbool intf_valid = false;

	    ts_free(&val);
	    intf_name = tstr_array_get_str_quick(change->mdc_name_parts, 3);
	    bail_null(intf_name);

	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs,
		    ba_value);
	    bail_null(new_val);

	    err = bn_attrib_get_tstr(new_val, NULL, bt_bool,
		    NULL, &val);
	    bail_error_null(err, val);

	    if (ts_equal_str(val , "true", false)) {
		gro_toggle = 1;
	    } else {
		gro_toggle = 0;

	    }
	    snprintf(intf_nd, sizeof(intf_nd),
		    "/net/interface/state/%s/devsource", intf_name);
	    err = mdb_get_node_value_tstr(commit, new_db, intf_nd, 0,
		    &intf_valid, &source);
	    bail_error(err);
	    if(source  && ts_equal_str(source, "physical", false)) {
		err = md_nkn_ethtool(intf_name, NKN_ETHTOOL_GRO_SET,
			&gro_toggle);
		bail_error(err);
	    }
	    ts_free(&val);
	}

	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "net", "interface", "config", "*", "offloading", "gso", "enable"))
		&& (mdct_modify == change->mdc_change_type || mdct_add == change->mdc_change_type))
	{
	    const char *intf_name = NULL;
	    const bn_attrib *new_val = NULL;
	    uint32_t gso_toggle = 0;
	    ts_free(&source);
	    node_name_t intf_nd = {0};
	    tbool intf_valid = false;

	    ts_free(&val);
	    intf_name = tstr_array_get_str_quick(change->mdc_name_parts, 3);
	    bail_null(intf_name);

	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs,
		    ba_value);
	    bail_null(new_val);

	    err = bn_attrib_get_tstr(new_val, NULL, bt_bool,
		    NULL, &val);
	    bail_error_null(err, val);

	    if (ts_equal_str(val , "true", false)) {
		gso_toggle = 1;
	    } else {
		gso_toggle = 0;

	    }
	    snprintf(intf_nd, sizeof(intf_nd),
		    "/net/interface/state/%s/devsource", intf_name);
	    err = mdb_get_node_value_tstr(commit, new_db, intf_nd, 0,
		    &intf_valid, &source);
	    bail_error(err);
	    if(source  && ts_equal_str(source, "physical", false)) {
		err = md_nkn_ethtool(intf_name, NKN_ETHTOOL_GSO_SET,
			&gso_toggle);
		bail_error(err);
	    }
	    ts_free(&val);
	}

	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "net", "interface", "config", "*", "offloading", "tso", "enable"))
		&& (mdct_modify == change->mdc_change_type || mdct_add == change->mdc_change_type))
	{
	    const char *intf_name = NULL;
	    const bn_attrib *new_val = NULL;
	    uint32_t tso_toggle = 0;
	    ts_free(&source);
	    node_name_t intf_nd = {0};
	    tbool intf_valid = false;

	    ts_free(&val);
	    intf_name = tstr_array_get_str_quick(change->mdc_name_parts, 3);
	    bail_null(intf_name);

	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs,
		    ba_value);
	    bail_null(new_val);

	    err = bn_attrib_get_tstr(new_val, NULL, bt_bool,
		    NULL, &val);
	    bail_error_null(err, val);

	    if (ts_equal_str(val , "true", false)) {
		tso_toggle = 1;
	    } else {
		tso_toggle = 0;

	    }
	    snprintf(intf_nd, sizeof(intf_nd),
		    "/net/interface/state/%s/devsource", intf_name);
	    err = mdb_get_node_value_tstr(commit, new_db, intf_nd, 0,
		    &intf_valid, &source);
	    bail_error(err);
	    if(source  && ts_equal_str(source, "physical", false)) {
		err = md_nkn_ethtool(intf_name, NKN_ETHTOOL_TSO_SET,
			&tso_toggle);
		bail_error(err);
	    }
	    ts_free(&val);
	}
	if (bn_binding_name_pattern_match(ts_str(change->mdc_name), arp_announce_node)) {
	    const char *intf_name = NULL;
	    const bn_attrib *new_val = NULL;
	    uint32_t arp_announce = 0;
	    node_name_t intf_nd = {0};
	    node_name_t proc_file = {0};
	    tbool intf_valid = false;

	    ts_free(&source);
	    intf_name = tstr_array_get_str_quick(change->mdc_name_parts, 3);
	    bail_null(intf_name);

	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    bail_null(new_val);

	    err = bn_attrib_get_uint32(new_val, NULL, NULL, &arp_announce);
	    bail_error(err);

	    snprintf(intf_nd, sizeof(intf_nd), "/net/interface/state/%s/devsource", intf_name);
	    err = mdb_get_node_value_tstr(commit, new_db, intf_nd, 0, &intf_valid, &source);
	    bail_error(err);
	    if (source && (ts_equal_str(source, "physical", false) || ts_equal_str(source, "bond", false))) {
		snprintf(proc_file, sizeof(proc_file), "/proc/sys/net/ipv4/conf/%s/arp_announce", intf_name);
		md_nkn_proc_ctl_int(proc_file, arp_announce);
	    }
	}

	if (bn_binding_name_pattern_match(ts_str(change->mdc_name), arp_ignore_node)) {
	    const char *intf_name = NULL;
	    const bn_attrib *new_val = NULL;
	    uint32_t arp_ignore = 0;
	    node_name_t intf_nd = {0};
	    node_name_t proc_file = {0};
	    tbool intf_valid = false;

	    ts_free(&source);
	    intf_name = tstr_array_get_str_quick(change->mdc_name_parts, 3);
	    bail_null(intf_name);

	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    bail_null(new_val);

	    err = bn_attrib_get_uint32(new_val, NULL, NULL, &arp_ignore);
	    bail_error(err);

	    snprintf(intf_nd, sizeof(intf_nd), "/net/interface/state/%s/devsource", intf_name);
	    err = mdb_get_node_value_tstr(commit, new_db, intf_nd, 0, &intf_valid, &source);
	    bail_error(err);
	    if (source && (ts_equal_str(source, "physical", false) || ts_equal_str(source, "bond", false))) {
		snprintf(proc_file, sizeof(proc_file), "/proc/sys/net/ipv4/conf/%s/arp_ignore", intf_name);
		md_nkn_proc_ctl_int(proc_file, arp_ignore);
	    }
	}
    }

bail:
    ts_free(&val);
    ts_free(&source);
    return(err);
}
static int
md_nkn_get_proc_intf_conf
		(
		md_commit *commit,
		const mdb_db *db,
		const char *node_name,
		const bn_attrib_array *node_attribs,
		bn_binding **ret_binding,
		uint32 *ret_node_flags,
		void *arg)
{
    int err = 0;
    uint32_t arp_value = 0;
    tstring *t_str = NULL;
    node_name_t intf_nd = {0};
    node_name_t proc_file = {0};
    tbool intf_valid = false;
    tstring *source = NULL;
    const char *arp_string = "NA";

    err = bn_binding_name_to_parts_va(node_name, false, 1, 4, &t_str);
    bail_error_null(err, t_str);

    snprintf(intf_nd, sizeof(intf_nd), "/net/interface/state/%s/devsource", ts_str(t_str));
    err = mdb_get_node_value_tstr(commit, db, intf_nd, 0, &intf_valid, &source);
    bail_error(err);

    if(source  && (ts_equal_str(source, "physical", false) || ts_equal_str(source, "bond", false))) {
        snprintf(proc_file, sizeof(proc_file), "/proc/sys/net/ipv4/conf/%s/%s", ts_str(t_str), (char *) arg);
        md_nkn_get_proc_ctl_int(proc_file, &arp_value);
    }

    if (0 == strcmp(arg, "arp_announce")) {
        switch(arp_value) {
            case 2:
                arp_string = "best";
                break;
            case 0:
            default:
                arp_string = "any";
        }
    }
    if (0 == strcmp(arg, "arp_ignore")) {
        switch(arp_value) {
            case 1:
                arp_string = "no-ip-match";
                break;
            case 2:
                arp_string = "no-match";
                break;
            case 8:
                arp_string = "all";
                break;
            case 0:
            default:
                arp_string = "none";
        }
    }

    err = bn_binding_new_str(ret_binding, node_name, ba_value, bt_string, 0, arp_string);
    bail_error(err);

bail:
    ts_free(&t_str);
    ts_free(&source);
    return err;
}
/*-----------------------------------------------------------------------------
 * IMPLEMENTATION
 */
static int
wcf_handle_mfpadd(void)
{
    const bn_response *resp = NULL;
    bn_request *req = NULL;
    bn_binding *binding = NULL;
    const tstring *mfp_value = NULL;
    const tstring *action_value = NULL;
    const tstring *media_value = NULL;
    const tstring *live_encap_value = NULL;
    const tstring *file_encap_value = NULL;
    char *bn_mfp_name = NULL;
    char *bn_mfp_media = NULL;
    char *bn_mfp_encap = NULL;
    char *bn_mfp_status = NULL;
    char *ret_msg = NULL;
    uint32 ret_err=0;
    tstring *msg = NULL;
    tstring *profile_rec = NULL;
    uint32 code = 0;
    int err = 0;
    const tstring *old_stream_profile = NULL;

    err = web_get_request_param_str(g_web_data, wcf_field_streamname, ps_post_data,
	    &mfp_value);
    bail_error(err);

    if (mfp_value == NULL || ts_num_chars(mfp_value) <= 0) {
	err = ts_new_str(&msg, _("No session name entered."));
	bail_error(err);
        ret_err = 1;
        goto check_error;
    }

    err = web_get_request_param_str(g_web_data, wcf_field_media, ps_post_data,
	    &media_value);
    bail_error(err);

    err = web_get_request_param_str(g_web_data, wcf_field_file_encap, ps_post_data,
	    &file_encap_value);
    bail_error(err);

    err = web_get_request_param_str(g_web_data, wcf_field_live_encap, ps_post_data,
	    &live_encap_value);
    bail_error(err);

    err = web_get_request_param_str(g_web_data, wcf_field_old_stream, ps_post_data,
	    &old_stream_profile);
    bail_error(err);

    /*session name*/
    err = mdc_get_binding_tstr_fmt
	(web_mcc, NULL, NULL, NULL, &profile_rec, NULL,
	 "/nkn/nvsd/mfp/config/%s", ts_str(mfp_value));
    bail_error(err);
    if (profile_rec && ts_num_chars(profile_rec) > 0) {
	ret_msg = smprintf(_("Profile \"%s\" already exists."),
		ts_str(mfp_value));
	bail_null(ret_msg);
	err = web_set_msg_result_str(g_web_data, 1, ret_msg);
	bail_error(err);
	goto bail;
    }

    if(!ts_equal_str(old_stream_profile, "(none)", false)){
	bn_mfp_name = smprintf("/nkn/nvsd/mfp/config/%s", ts_str(old_stream_profile));
	bail_null(bn_mfp_name);
	err = mdc_reparent_binding_ex(web_mcc, &code, &msg,
		bn_mfp_name, NULL, ts_str(mfp_value), 0,
		bsnf_reparent_by_copy);
	bail_error(err);
	if (code) {
	    err = web_set_msg_result_str(g_web_data, code, ts_str(msg));
	    bail_error(err);
	    goto bail;
	}
    } else {
	/*Get the values from the  different fields*/
	if(ts_equal_str(media_value,"File",true) &&
		(ts_equal_str(file_encap_value,"not_selected",true))) {
	    err = ts_new_str(&msg, _("No encapsulation type selected for File media."));
	    bail_error(err);
	    ret_err = 1;
	    goto check_error;
	}
	if(ts_equal_str(media_value,"Live",true) &&
		(ts_equal_str(live_encap_value,"not_selected",true))) {
	    err = ts_new_str(&msg, _("No encapsulation type selected for Live media."));
	    bail_error(err);
	    ret_err = 1;
	    goto check_error;
	}

	/*session name*/
	bn_mfp_name= smprintf("/nkn/nvsd/mfp/config/%s",ts_str(mfp_value));
	bail_null(bn_mfp_name);
	err = mdc_set_binding(web_mcc, &ret_err, &msg,
		bsso_modify,bt_string,ts_str(mfp_value),
		bn_mfp_name);
	bail_error(err);
	if(ret_err) {
	    goto check_error;
	}

	/* media */
	bn_mfp_media=smprintf("/nkn/nvsd/mfp/config/%s/media-type",ts_str(mfp_value));
	bail_null(bn_mfp_name);
	err = mdc_set_binding(web_mcc, &ret_err, &msg,
		bsso_modify,bt_string,ts_str(media_value),
		bn_mfp_media);
	bail_error(err);
	if(ret_err) {
	    goto check_error;
	}

	/* encap */
	bn_mfp_encap=smprintf("/nkn/nvsd/mfp/config/%s/media-encap",ts_str(mfp_value));
	bail_null(bn_mfp_encap);
	if(ts_equal_str(media_value,"File",true)){
	    err = mdc_set_binding(web_mcc, &ret_err, &msg,
		    bsso_modify,bt_string,ts_str(file_encap_value),
		    bn_mfp_encap);
	    bail_error(err);
	    if(ret_err) {
		goto check_error;
	    }
	}else{
	    err = mdc_set_binding(web_mcc, &ret_err, &msg,
		    bsso_modify,bt_string,ts_str(live_encap_value),
		    bn_mfp_encap);
	    bail_error(err);
	    if(ret_err) {
		goto check_error;
	    }
	}
    }
    /* status */
    bn_mfp_status=smprintf("/nkn/nvsd/mfp/config/%s/status",ts_str(mfp_value));
    bail_null(bn_mfp_status);
    err = mdc_set_binding(web_mcc, &ret_err, &msg,
	    bsso_modify,bt_string,"NEW",
	    bn_mfp_status);
    bail_error(err);
    if(ret_err) {
	goto check_error;
    }
    /*session value name*/
    bn_mfp_name= smprintf("/nkn/nvsd/mfp/config/%s/name",ts_str(mfp_value));
    bail_null(bn_mfp_name);
    err = mdc_set_binding(web_mcc, &ret_err, &msg,
	    bsso_modify,bt_string,ts_str(mfp_value),
	    bn_mfp_name);
    bail_error(err);
    if(ret_err) {
	goto check_error;
    }
check_error:
    err = web_set_msg_result(g_web_data, ret_err,msg);
    bail_error(err);
    if (!ret_err) {
	err = web_set_msg_result(g_web_data,ret_err,msg);
	bail_error(err);
	err = web_clear_post_data(g_web_data);
	bail_error(err);
    }
bail:
    bn_binding_free(&binding);
    bn_request_msg_free(&req);
    ts_free(&msg);
    safe_free(bn_mfp_name);
    safe_free(bn_mfp_media);
    safe_free(bn_mfp_encap);
    safe_free(bn_mfp_status);
    return(err);
}
static int
wcf_handle_mfpsave(void)
{
    int err = 0;
    bn_request *req = NULL;
    uint32 code = 0;
    uint32 i = 0, num_others = 0;
    tstring *msg = NULL;
    tstring *clear_str = NULL;
    tstring *list_others = NULL;
    tstr_array *others = NULL;
    const char *suffix = NULL;
    const bn_response *resp = NULL;
    tstring *action = NULL;
    tstr_array *fields = NULL;
    const tstring *field = NULL;
    bn_type type = bt_none;
    tstring *field_value = NULL;
    tstring *fields_str = NULL;
    uint32 num_fields = 0;
    char *ret_msg = NULL;
 
    /*dump params*/
    //web_dump_params(g_web_data);
    /* create the message */
    err = bn_set_request_msg_create(&req, 0);
    bail_error(err);

    err = wcf_do_list_root(req, "", &msg, &code);
    bail_error(err);

    if (code) {
        goto check_error;
    }

    if (!code) {
	lc_log_basic(LOG_NOTICE, _("Sending data to mgmt\n"));
        err = mdc_send_mgmt_msg(web_mcc, 
                                req, false, NULL, &code, &msg);
        bail_error(err);
    }

check_error:    
    err = web_set_msg_result(g_web_data, code, msg);
    bail_error(err);
    /*
     * Dont clear the data here , since this function is used for action handler for publish
     * to save any unsaved  data
     */
#if 0
    if (!code) {
        if (clear_str == NULL || !ts_equal_str(clear_str, "false", false)) {
            err = web_clear_post_data(g_web_data);
            bail_error(err);
        }
    }
#endif
bail:
    ts_free(&msg);
    if(code) {
	return code;
    }
    return err;
}
static int agentd_op_show_crawler_name (agentd_context_t * context, void *data, const char * crawl_name){
    int err = 0;
    node_name_t cfg_node_pat = {0};
    node_name_t mon_node_pat = {0};
    bn_binding_array * cfg_bindings = NULL;
    bn_binding_array * mon_bindings = NULL;
    uint8 status = 0, op_status = 0, auto_gen = 0;
    uint32 file_ext_count = 0, preload_files_count = 0, nonpreload_files_count = 0;
    char crawler_cfg_status [MAX_TMP_BUF_LEN] = {0};
    char crawler_op_status [MAX_TMP_BUF_LEN] = {0};
    agentd_crawler_file_context files_context = {0,0};
    tstring * url = NULL;
    tstring * depth = NULL;
    tstring * auto_gen_new = NULL;
    tstring * auto_gen_source = NULL;
    tstring * last_start = NULL;
    tstring * last_end = NULL;

    const char * agentd_crawler_op_status_str [] = {"CRAWL_NOT_SCHEDULED", 
	                                            "CRAWL_IN_PROGRESS",
						    "CRAWL_IN_PROGRESS",
						    "CRAWL_STOPPED",
						    "CRAWL_STOPPED"
                                                 };
    #define MAX_CRAWLER_OP_STATUS (sizeof(agentd_crawler_op_status_str)/sizeof (const char *))

    bail_null (crawl_name);

    /* Get the configuration nodes */
    snprintf(cfg_node_pat, sizeof(cfg_node_pat), "/nkn/crawler/config/profile/%s", crawl_name);
    err = mdc_get_binding_children(agentd_mcc, NULL, NULL, true, &cfg_bindings,
                                  true, true, cfg_node_pat);
    bail_error_null(err, cfg_bindings);
    bn_binding_array_dump("CRAWLER-CFG-BINDINGS", cfg_bindings, jnpr_log_level);

    err = agentd_binding_array_get_value_tstr_fmt (cfg_bindings, &url,  "/nkn/crawler/config/profile/%s/url", crawl_name);
    bail_error (err);

    if (!url) {
        /* URL is mandatory for crawler. If it is null, probably crawler is not configured. Throw error */
        lc_log_debug (jnpr_log_level, "Crawler %s is not configured", crawl_name);
        err = 1;
        goto bail;
    }
    err = agentd_binding_array_get_value_tstr_fmt (cfg_bindings, &depth, "/nkn/crawler/config/profile/%s/link_depth", crawl_name);
    bail_error (err);
    err = agentd_binding_array_get_value_uint8_fmt (cfg_bindings, &status, "/nkn/crawler/config/profile/%s/status", crawl_name);
    bail_error (err);
    snprintf(crawler_cfg_status, sizeof(crawler_cfg_status), "%s", (status ? "Active" : "Inactive"));
    err = agentd_binding_array_get_value_uint8_fmt (cfg_bindings, &auto_gen, "/nkn/crawler/config/profile/%s/auto_generate", crawl_name);
    bail_error (err);
    if (auto_gen){
        /* TODO : Get the file types from TM nodes */
        /* Hardcoding now as currently we are supporting only one action */
        ts_new_str(&auto_gen_new, "ASX");
        ts_new_str(&auto_gen_source, "WMV");
    }

    /* Get the list of preloaded and non-preloaded file extensions */
    tstr_array_new (&files_context.preloaded_files, NULL);
    tstr_array_new (&files_context.nonpreloaded_files, NULL);

    err = mdc_foreach_binding_prequeried (cfg_bindings, "/nkn/crawler/config/profile/*/file_extension/*",
                                          NULL, agentd_crawler_foreach_file_extn, &files_context, &file_ext_count);
    bail_error (err);

    lc_log_debug (jnpr_log_level, "Number of file extensions: %d", file_ext_count);

    /* Get the monitoring nodes */
    snprintf(mon_node_pat, sizeof(mon_node_pat), "/nkn/crawler/monitor/profile/external/%s", crawl_name);
    err = mdc_get_binding_children(agentd_mcc, NULL, NULL, true, &mon_bindings,
                                  true, true, mon_node_pat);
    bail_error (err);

    bn_binding_array_dump("CRAWLER-MON-BINDINGS", mon_bindings, jnpr_log_level);

    err = agentd_binding_array_get_value_tstr_fmt (mon_bindings, &last_start, "/nkn/crawler/monitor/profile/external/%s/start_ts", crawl_name);
    bail_error (err);
    err = agentd_binding_array_get_value_tstr_fmt (mon_bindings, &last_end, "/nkn/crawler/monitor/profile/external/%s/end_ts", crawl_name);
    bail_error (err);
    err = agentd_binding_array_get_value_uint8_fmt (mon_bindings, &op_status, "/nkn/crawler/monitor/profile/external/%s/status", crawl_name);
    bail_error (err);
    snprintf(crawler_op_status, sizeof(crawler_op_status), "%s", (op_status >= MAX_CRAWLER_OP_STATUS)? "UNKNOWN":agentd_crawler_op_status_str[op_status]);

    /* Construct XML response */
    OP_EMIT_TAG_START(context, ODCI_MFC_CRAWLER_DETAIL);
        OP_EMIT_TAG_VALUE(context, ODCI_CRAWLER_NAME, crawl_name);
        OP_EMIT_TAG_VALUE(context, ODCI_URL, ts_str(url));
        OP_EMIT_TAG_VALUE(context, ODCI_DEPTH, ts_str(depth));
        OP_EMIT_TAG_VALUE(context, ODCI_CRAWLER_CFG_STATUS, crawler_cfg_status);
    preload_files_count = tstr_array_length_quick(files_context.preloaded_files);
    nonpreload_files_count = tstr_array_length_quick(files_context.nonpreloaded_files);
    if (preload_files_count){
        OP_EMIT_TAG_START(context, ODCI_PRELOADED_FILES);
        for (uint32 i = 0; i < preload_files_count; i++) {
            OP_EMIT_TAG_VALUE(context, ODCI_CRAWL_FILE_TYPE,tstr_array_get_str_quick(files_context.preloaded_files, i));
        }
        OP_EMIT_TAG_END (context, ODCI_PRELOADED_FILES);
    }
    if (nonpreload_files_count){
        OP_EMIT_TAG_START(context, ODCI_NON_PRELOADED_FILES);
        for (uint32 i = 0; i < nonpreload_files_count; i++) {
            OP_EMIT_TAG_VALUE(context, ODCI_CRAWL_FILE_TYPE,tstr_array_get_str_quick(files_context.nonpreloaded_files, i));
        }
        OP_EMIT_TAG_END (context, ODCI_NON_PRELOADED_FILES);
    }
    if (auto_gen) {
        OP_EMIT_TAG_START (context, ODCI_AUTO_GENERATE);
            OP_EMIT_TAG_START (context, ODCI_AUTO_GENERATE_CFG);
                OP_EMIT_TAG_VALUE(context, ODCI_NEW_FILE_TYPE, ts_str(auto_gen_new));
                OP_EMIT_TAG_VALUE(context, ODCI_SOURCE_FILE_TYPE, ts_str(auto_gen_source));
            OP_EMIT_TAG_END (context, ODCI_AUTO_GENERATE_CFG);
        OP_EMIT_TAG_END (context, ODCI_AUTO_GENERATE);
    }
        OP_EMIT_TAG_VALUE(context, ODCI_LAST_START, ts_str(last_start));
        OP_EMIT_TAG_VALUE(context, ODCI_LAST_END, ts_str(last_end));
        OP_EMIT_TAG_VALUE(context, ODCI_CRAWL_STATUS, crawler_op_status);
    OP_EMIT_TAG_END(context, ODCI_MFC_CRAWLER_DETAIL);

bail:
    bn_binding_array_free(&cfg_bindings);
    bn_binding_array_free(&mon_bindings);
    ts_free(&url);
    ts_free(&depth);
    ts_free(&auto_gen_new);
    ts_free(&auto_gen_source);
    ts_free(&last_start);
    ts_free(&last_end);
    tstr_array_free(&files_context.preloaded_files);
    tstr_array_free(&files_context.nonpreloaded_files);
    return err;
}
static int
wcf_do_list_root(bn_request *req, const char *list_sfx, tstring **inout_msg,
                 uint32 *ret_code)
{
    bn_binding *binding = NULL;
    tstr_array *fields = NULL;
    tstr_array *list_fields = NULL;
    const tstring *display_name = NULL;
    const tstring *field = NULL;
    const tstring *list_field = NULL;
    char *node_name = NULL;
    char *list_name = NULL;
    char *list_root_fn = NULL, *list_index_fn = NULL;
    char *list_fields_fn = NULL;
    tstring *root = NULL;
    tstring *windex = NULL;
    tstring *windex_value = NULL;
    char *windex_value_esc = NULL;
    tstring *value = NULL;
    tstring *fields_str = NULL;
    tstring *list_value_fields_str = NULL;
    tstring *list_field_value = NULL;
    char *list_field_value_esc = NULL;
    bn_type type = bt_none;
    tbool required = false;
    uint32 code = 0;
    uint32 num_fields = 0;
    uint32 num_list_fields = 0;
    uint32 i = 0;
    uint32 j = 0;
    int err = 0;
    tstring *msg = NULL;
    tstring *profile_rec = NULL;

    bail_null(req);
    bail_null(inout_msg);
    bail_null(ret_code);
    const tstring *mfp_value = NULL;

    err = web_get_request_param_str(g_web_data, wcf_field_name, ps_post_data,&mfp_value);
    bail_error(err);
    /* get the root */
    list_root_fn = smprintf("%s%s", "/nkn/nvsd/mfp/config", list_sfx);
    bail_null(list_root_fn);
    /* get the fields to process */
    list_fields_fn = smprintf("%s%s", wcf_id_list_fields, list_sfx);
    bail_null(list_fields_fn);

    err = web_get_trimmed_form_field_str(g_web_data, list_fields_fn,
                                         &fields_str);
    bail_error_null(err, fields_str);
    lc_log_basic(LOG_DEBUG, _("field_str:%s\n"), ts_str(fields_str));

    err = ts_tokenize(fields_str, ',', 0, 0,
                      ttf_ignore_leading_separator |
                      ttf_ignore_trailing_separator |
                      ttf_single_empty_token_null, &fields);
    bail_error(err);

    /*BUG:6580: Check if the node exists first.Else throw error saying the node wasn't even created
     * or was deleted recently before the config changes could be saved.
     */

    err = mdc_get_binding_tstr_fmt
	(web_mcc, &code, NULL, NULL, &profile_rec, NULL,
	 "/nkn/nvsd/mfp/config/%s/media-type", ts_str(mfp_value));
    bail_error(err);
    if (code || (!profile_rec) || (ts_length(profile_rec)== 0)) {
	err = ts_new_sprintf(inout_msg,
		_("The session \"%s\"doesn't exists or was deleted recently.\n"),
                                         ts_str(mfp_value));
	code = 1; //Set the error code
	goto bail;
    }




    node_name = smprintf("/nkn/nvsd/mfp/config/%s", ts_str(mfp_value));
    bail_null(node_name);

    err = bn_binding_new_str_autoinval(
        &binding, node_name, ba_value, bt_string, 0, ts_str(mfp_value));
    bail_error(err);
    safe_free(node_name);

    err = bn_set_request_msg_append(req, bsso_modify, 0, binding, NULL);
    bail_error(err);
    bn_binding_free(&binding);

    /* go through all the fields */
    if (fields != NULL) {
        err = tstr_array_length(fields, &num_fields);
        bail_error(err);
    }
    for (i = 0; i < num_fields; ++i) {
	field = tstr_array_get_quick(fields, i);
	bail_null(field);
	/*
         * if list values exist for this field, then this field is a
         * wildcard so we need to populate with other fields.
         */
	list_name = smprintf("%s%s%s", wcf_child_prefix, ts_str(field),
		wcf_child_list_suffix);
	bail_null(list_name);
	lc_log_basic(LOG_DEBUG, _("field:%s,list_name:%s\n"), ts_str(field),list_name);
	err = web_get_trimmed_value_str(g_web_data, list_name,
		&list_value_fields_str);
	bail_error(err);

	if (list_value_fields_str) {
	    err = ts_tokenize(list_value_fields_str, ',', 0, 0,
		    ttf_ignore_leading_separator |
		    ttf_ignore_trailing_separator |
		    ttf_single_empty_token_null, &list_fields);
	    bail_error(err);

	    if (list_fields) {
		err = tstr_array_length(list_fields, &num_list_fields);
		bail_error(err);
	    }

            for (j = 0; j < num_list_fields; ++j) {
                list_field = tstr_array_get_quick(list_fields, j);
                bail_null(list_field);

                err = web_get_type_for_form_field(g_web_data, list_field,
                                                  &type);
                bail_error(err);

                err = web_get_trimmed_form_field(g_web_data, list_field,
                                                 &list_field_value);
                bail_error_null(err, list_field_value);

                err = bn_binding_name_escape_str(ts_str(list_field_value),
                                                 &list_field_value_esc);
                bail_error_null(err, list_field_value_esc);

                err = web_is_required_form_field(g_web_data, list_field,
                                                 &required);
                bail_error(err);

                /*
                 * check if the field is required. if the field is required
                 * and there is no value, inform the user. if the field is not
                 * required and there is no value, don't insert a node for it
                 * so that the mgmt module fills in the default value.
                 */
                if (required && ts_length(list_field_value) == 0) {
                    err = web_get_field_display_name(g_web_data, list_field,
                                                     &display_name);
                    bail_error(err);
                    code = 1;
                    err = ts_new_sprintf(inout_msg,
                                         _("No value specified for %s."),
                                         ts_str(display_name));
                    bail_error(err);
                    goto bail;
                } else if (!required && ts_length(list_field_value) == 0) {
                    goto list_loop_clean;
                }

                node_name = smprintf("/nkn/nvsd/mfp/config/%s/%s/%s",
                                     ts_str(mfp_value),
                                     ts_str(field), list_field_value_esc);
		lc_log_basic(LOG_DEBUG, "Nodename:%s\n", node_name);
                bail_null(node_name);
                err = bn_binding_new_str_autoinval(
                    &binding, node_name, ba_value, type, 0,
                    ts_str(list_field_value));
                bail_error(err);

                err = bn_set_request_msg_append(
                    req, bsso_modify, 0, binding, NULL);
                bail_error(err);

 list_loop_clean:
                ts_free(&list_field_value);
                safe_free(list_field_value_esc);
                safe_free(node_name);
                bn_binding_free(&binding);
            }

            goto loop_clean;
        }

        err = web_get_type_for_form_field(g_web_data, field, &type);
        bail_error(err);

        err = web_get_trimmed_form_field(g_web_data, field, &value);
        bail_error(err);

	lc_log_basic(LOG_DEBUG, ("Field:%s\n"), ts_str(field));
        if ((value == NULL) && (type == bt_bool)) {
            /* XXX should we really default to false if no value? */
            err = ts_new_str(&value, "false");
            bail_error(err);
        } else if (value == NULL && 
		   !ts_cmp_str(field,"smooth/dvrlength", 0)) {
	    err = ts_new_str(&value, "30");
	    bail_error(err);
        } else {
            bail_null(value);
        }

        err = web_is_required_form_field(g_web_data, field, &required);
        bail_error(err);

        /*
         * check if the field is required. if the field is required
         * and there is no value, inform the user. if the field is not
         * required and there is no value, don't insert a node for it
         * so that the mgmt module fills in the default value.
         */
        if (required && ts_length(value) == 0) {
            err = web_get_field_display_name(g_web_data, field, &display_name);
            bail_error(err);

            code = 1;
            err = ts_new_sprintf(inout_msg, _("No value specified for %s."),
                                 ts_str(display_name));
            bail_error(err);
            goto bail;
        } else if (!required && ts_length(value) == 0) {

	    node_name = smprintf("/nkn/nvsd/mfp/config/%s/%s", ts_str(mfp_value),
				 ts_str(field));
	    bail_null(node_name);
	    
	    err = bn_binding_new_str_autoinval(
	        &binding, node_name, ba_value, type, 0, ts_str(value));
	    bail_error(err);

	    err = bn_set_request_msg_append(req, bsso_reset, 0,
					    binding, NULL);
	    bail_error(err);

            goto loop_clean;
        }

        node_name = smprintf("/nkn/nvsd/mfp/config/%s/%s", ts_str(mfp_value),
                             ts_str(field));
        bail_null(node_name);
	lc_log_basic(LOG_DEBUG, "Nodename:%s\n", node_name);

        err = bn_binding_new_str_autoinval(
            &binding, node_name, ba_value, type, 0, ts_str(value));
        bail_error(err);

        err = bn_set_request_msg_append(req, bsso_modify, 0, binding, NULL);
        bail_error(err);

 loop_clean:
        tstr_array_free(&list_fields);
        ts_free(&value);
        ts_free(&list_value_fields_str);
        ts_free(&list_field_value);
        safe_free(list_field_value_esc);
        safe_free(node_name);
        safe_free(list_name);
        bn_binding_free(&binding);
    }

 bail:
    *ret_code = code;
    bn_binding_free(&binding);
    tstr_array_free(&fields);
    tstr_array_free(&list_fields);
    ts_free(&list_value_fields_str);
    ts_free(&root);
    ts_free(&windex);
    ts_free(&windex_value);
    safe_free(windex_value_esc);
    ts_free(&value);
    ts_free(&fields_str);
    ts_free(&list_field_value);
    safe_free(list_field_value_esc);
    safe_free(node_name);
    safe_free(list_name);
    safe_free(list_root_fn);
    safe_free(list_index_fn);
    safe_free(list_fields_fn);
    ts_free(&profile_rec);
    return(err);
}
static int agentd_show_interfaces_show_one_config(
                        const bn_binding_array *bindings, uint32 idx,
                        const bn_binding *binding, const tstring *name,
                        const tstr_array *name_components,
                        const tstring *name_last_part,
                        const tstring *value,
                        void *callback_data)
{
    int err = 0;
    uint8 masklen = 0;
    agentd_interface_show_context *ctxt = NULL;
    const bn_binding_array *config_bindings = NULL;

    node_name_t bn_name = {0};

    tstring *alias_ifdevname = NULL;
    tbool is_alias = false;
    void *alias_list_v = NULL;
    const tstring *alias_list = NULL;
    char* o_netmask = NULL;
    tbool found = false;
    tbool display = true, has_display = false;

    tstring *masklen_tstr = NULL;

    tstring* os_comment=NULL;
    tstring* os_enabled=NULL;
#ifdef PROD_FEATURE_DHCP_CLIENT
    tstring* os_dhcp=NULL;
#endif /*PROD_FEATURE_DHCP_CLIENT*/

#ifdef PROD_FEATURE_ZEROCONF
    tstring* os_zeroconf=NULL;
#endif /*PROD_FEATURE_ZEROCONF*/
    tstring* os_ip_addr=NULL;

    tstring* os_alias_of=NULL;

    tstring* os_speed=NULL;
    tstring* os_duplex=NULL;
    tstring* os_mtu=NULL;
    tstring* os_arp=NULL;
    tstring* s_devsource=NULL;

    tstring * os_ipv6_enabled = NULL;

    const char* r = ts_str(name);
    bail_null(r);
    bail_null(callback_data);

    ctxt = callback_data;

    config_bindings = bindings;

    if (ctxt->cisc_show_all)
    {
       snprintf(bn_name,sizeof(bn_name),"/net/interface/config/%s/display",ts_str(name_last_part));

       err = bn_binding_array_get_value_tbool_by_name(config_bindings, bn_name, &has_display, &display);
       bail_error_msg(err, "Failed to get IF display configuration");

       if (!display)
           goto bail;
       /*
        * If has_display is false,
        * If we're showing interface configuration, something's
        * wrong, since we were iterating only over interfaces that
        * had configuration...
        */
       if (!has_display)
       {
           lc_log_basic(LOG_WARNING, I_("Could not find node %s"),bn_name);
           goto bail;
       }
    }

    err = bn_binding_array_get_value_tstr_by_name_fmt( config_bindings, NULL,&alias_ifdevname,
            "/net/interface/config/%s/alias/ifdevname",ts_str(name_last_part)
           );

    bail_error(err);

    if (alias_ifdevname && (ts_length(alias_ifdevname) > 0))
    {
       is_alias = true;
    }


    err=agentd_binding_array_get_value_tstr_fmt(bindings,&masklen_tstr,"%s/addr/ipv4/static/1/mask_len",r);
    bail_error(err);

    if (masklen_tstr)
    {
        err = lia_masklen_str_to_ipv4addr_str(ts_str(masklen_tstr), &o_netmask);
        bail_error(err);
    }
    else
    {
        o_netmask = strdup("");
        bail_null(o_netmask);
    }

    lc_log_debug(jnpr_log_level,"netmask of %s = %s",name?ts_str(name):"*", o_netmask );


    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_comment,"%s/comment",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_enabled,"%s/enable",r);
    bail_error(err);

#ifdef PROD_FEATURE_DHCP_CLIENT
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_dhcp,"%s/addr/ipv4/dhcp",r);
#endif /*PROD_FEATURE_DHCP_CLIENT*/

#ifdef PROD_FEATURE_ZEROCONF
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_zeroconf,"%s/addr/ipv4/zeroconf",r);
#endif /* PROD_FEATURE_ZEROCONF */

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_arp,"%s/arp",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_ip_addr,"%s/addr/ipv4/static/1/ip",r);
    lc_log_debug(jnpr_log_level,"IP Addr = %s",ts_str(os_ip_addr) );

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_ipv6_enabled,"%s/addr/ipv6/enable",r);
    bail_error(err);

    err = ht_lookup(ctxt->cisc_aliases, name_last_part,
                    ts_length(name_last_part), &found, NULL, NULL,
                    &alias_list_v);
    bail_error(err);
    alias_list = alias_list_v;

    if (alias_list && ts_num_chars(alias_list) > 0)
    {
        lc_log_debug(jnpr_log_level,"Aliases : %s",ts_str(alias_list));
    }
    if (is_alias)
    {
        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_alias_of,"%s/alias/ifdevname",r);
        bail_error(err);

        lc_log_debug(jnpr_log_level,"Alias of = %s",ts_str(os_alias_of) );
    }
    else
    {
        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_speed,"%s/type/ethernet/speed",r);
        bail_error(err);

        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_duplex,"%s/type/ethernet/duplex",r);
        bail_error(err);

        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_mtu,"%s/mtu",r);
        bail_error(err);

        lc_log_debug(jnpr_log_level,"speed = %s",ts_str(os_speed) );
        lc_log_debug(jnpr_log_level,"duplex = %s",ts_str(os_duplex) );
        lc_log_debug(jnpr_log_level,"mtu = %s",ts_str(os_mtu) );
    }

    { //This block retrieves the devsource needed to check if the if is bond
        agentd_mdc_get_value_tstr_fmt(&s_devsource,"/net/interface/state/%s/devsource",ts_str_maybe(name_last_part) );
    }
        OP_EMIT_TAG_START(ctxt->agentd_context, ODCI_INTERFACE_CONFIGURED);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_NAME,ts_str_maybe_empty(name_last_part) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_COMMENT,ts_str_maybe_empty(os_comment) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ENABLED,agentd_ts_map_true_false(os_enabled) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_DHCP,agentd_ts_map_true_false(os_dhcp) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ZEROCONF,agentd_ts_map_true_false(os_zeroconf) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_IP_ADDRESS,ts_str_maybe_empty(os_ip_addr) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_NETMASK,o_netmask );
            OP_EMIT_TAG_START(ctxt->agentd_context, ODCI_IPV6);
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ENABLED, agentd_ts_map_true_false(os_ipv6_enabled));
                agentd_show_ipv6_addresses (ctxt, bindings, r);
            OP_EMIT_TAG_END(ctxt->agentd_context, ODCI_IPV6);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ARP,agentd_ts_map_true_false(os_arp) );

            agentd_show_bond_maybe(ctxt,name_last_part,s_devsource);

            if(is_alias)
            {
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ALIAS_OF,ts_str_maybe_empty(alias_ifdevname) );
            }
            else
            {
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_SPEED,ts_str_maybe_empty(os_speed) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_DUPLEX,ts_str_maybe_empty(os_duplex) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_MTU,ts_str_maybe_empty(os_mtu) );
                agentd_show_if_alias_names_for_config(ctxt,alias_list);
            }
        OP_EMIT_TAG_END(ctxt->agentd_context, ODCI_INTERFACE_CONFIGURED);

bail:
     lc_log_debug(jnpr_log_level,"crossed bail...");
     ts_free(&alias_ifdevname);
     ts_free(&masklen_tstr);
     safe_free(o_netmask);

     { //This block is to free objects created to emit XML content

         ts_free(&os_comment);
         ts_free(&os_enabled);
     #ifdef PROD_FEATURE_DHCP_CLIENT
         ts_free(&os_dhcp);
     #endif /*PROD_FEATURE_DHCP_CLIENT*/

     #ifdef PROD_FEATURE_ZEROCONF
         ts_free(&os_zeroconf);
     #endif /*PROD_FEATURE_ZEROCONF*/
         ts_free(&os_ip_addr);

         ts_free(&os_alias_of);

         ts_free(&os_speed);
         ts_free(&os_duplex);
         ts_free(&os_mtu);
         ts_free(&s_devsource);
         ts_free(&os_ipv6_enabled);
     }
    return err;
}
static int
md_pub_point_commit_check(md_commit *commit,
			const mdb_db *old_db,
			const mdb_db *new_db,
			mdb_db_change_array *change_list,
			void *arg)
{
    int err = 0;
    tstring *ret_msg = NULL;
    int i = 0;
    int num_changes = 0;
    const mdb_db_change *change = NULL;
    const char *t_pp_name = NULL;
    const bn_attrib *new_val = NULL;
    tstring *t_duration = NULL;
    tstring *t_sdp = NULL;
    tstring *t_pub_server = NULL;
    tstring *t_mode = NULL;
    lt_time_sec ret_ts = 0;

    num_changes = mdb_db_change_array_length_quick (change_list);
    for (i = 0; i < num_changes; ++i)
    {
	change = mdb_db_change_array_get_quick (change_list, i);
	bail_null(change);

	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 5, "nkn", "nvsd", "pub-point", "config", "*"))
		&& ((mdct_add == change->mdc_change_type)))
	{
	    t_pp_name = tstr_array_get_str_quick(change->mdc_name_parts, 4);

	    err = md_nvsd_pp_validate_name(t_pp_name, &ret_msg);
	    if (err) {
		err = md_commit_set_return_status_msg_fmt(commit, 1,
			"error: %s", ts_str(ret_msg));
		bail_error(err);
		goto bail;
	    }
	}

	/* Check if EVENT-DURATION is correct format */
	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "nkn", "nvsd", "pub-point", "config", "*", "event", "duration"))
		&& ((mdct_modify == change->mdc_change_type)))
	{
	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    if (new_val) {
		err = bn_attrib_get_tstr(new_val, NULL, bt_string, NULL, &t_duration);
		bail_error(err);

		if (ts_length(t_duration) != 0) {
		    err = lt_str_to_daytime_sec(ts_str(t_duration), &ret_ts);

		    if ( err || (ret_ts < 0)) {
			err = md_commit_set_return_status_msg_fmt(commit, 1, "error: Bad duration");
			bail_error(err);
			goto bail;
		    }
		}
	    }
	}

	/* Check if START-TIME is correct format */
	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "nkn", "nvsd", "pub-point", "config", "*", "pub-server", "start-time"))
		&& ((mdct_modify == change->mdc_change_type)))
	{
	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    if (new_val) {
		err = bn_attrib_get_tstr(new_val, NULL, bt_string, NULL, &t_duration);
		bail_error(err);

		if (ts_length(t_duration) != 0) {
		    err = lt_str_to_daytime_sec(ts_str(t_duration), &ret_ts);
		    lc_log_basic(LOG_NOTICE, "ret = %d, %s", ret_ts, ts_str(t_duration));

		    if ( err || (ret_ts < 0)) {
			err = md_commit_set_return_status_msg_fmt(commit, 1, "error: Bad Start-time");
			bail_error(err);
			goto bail;
		    }
		}
	    }
	}

	/* Check if END-TIME is correct format */
	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "nkn", "nvsd", "pub-point", "config", "*", "pub-server", "end-time"))
		&& ((mdct_modify == change->mdc_change_type)))
	{
	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    if (new_val) {
		err = bn_attrib_get_tstr(new_val, NULL, bt_string, NULL, &t_duration);
		bail_error(err);

		if (ts_length(t_duration) != 0) {
		    err = lt_str_to_daytime_sec(ts_str(t_duration), &ret_ts);
		    lc_log_basic(LOG_NOTICE, "ret = %d, %s", ret_ts, ts_str(t_duration));

		    if ( err || (ret_ts < 0)) {
			err = md_commit_set_return_status_msg_fmt(commit, 1, "error: Bad Start-time");
			bail_error(err);
			goto bail;
		    }
		}
	    }
	}

	/* Check if SDP-STATIC is correct format */
	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "nkn", "nvsd", "pub-point", "config", "*", "sdp", "static"))
		&& ((mdct_modify == change->mdc_change_type)))
	{
	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    if (new_val) {
		err = bn_attrib_get_tstr(new_val, NULL, bt_uri, NULL, &t_sdp);
		bail_error(err);

	    }
	}
	/* Check if pub-server is correct format */
	if ((bn_binding_name_parts_pattern_match_va(change->mdc_name_parts, 0, 7, "nkn", "nvsd", "pub-point", "config", "*", "pub-server", "uri"))
		&& ((mdct_modify == change->mdc_change_type)))
	{
	    new_val = bn_attrib_array_get_quick(change->mdc_new_attribs, ba_value);
	    if (new_val) {
		err = bn_attrib_get_tstr(new_val, NULL, bt_uri, NULL, &t_pub_server);
		bail_error(err);

		if (ts_length(t_pub_server) != 0) {
		    /* validate URI */
		    err = md_nvsd_pp_validate_pub_server_uri(t_pub_server, &ret_msg);
		    if (err) {
			err = md_commit_set_return_status_msg_fmt(commit, 1,
				"error: %s", ts_str(ret_msg));
			bail_error(err);
			goto bail;
		    }
		}
	    }
	}
    }


    err = md_commit_set_return_status(commit, 0);
    bail_error(err);

bail:
    ts_free(&ret_msg);
    ts_free(&t_duration);
    ts_free(&t_sdp);
    ts_free(&t_pub_server);
    ts_free(&t_mode);
    return err;
}
static int agentd_show_if_aliases(agentd_interface_show_context *ctxt, const tstring* name_last_part)
{
    int err =0;
    char *addr_subtree = NULL;
    uint32 num_addr_bindings = 0, i = 0;
    const bn_binding *addr_binding = NULL;

    node_name_t  amask_bn = {0};
    node_name_t  aifname_bn = {0};
    tstring *amask = NULL, *aifname = NULL, *os_arp=NULL;

    const tstring *addrroot_bn = NULL;
    tstr_array *name_parts_var = NULL;
    const tstr_array *name_parts = NULL;
    const tstring *ifdevname = NULL;
    const char *addr_str = NULL;
    char *mask_len = NULL;

    /* /net/interface/address/state/ifdevname/vlan1249/ipv4addr */
    err = bn_binding_name_append_parts_va
        (&addr_subtree, "/net/interface/address/state/ifdevname",
         2, ts_str(name_last_part), "ipv4addr");
    bail_error_null(err, addr_subtree);

    num_addr_bindings = bn_binding_array_length_quick(ctxt->cisc_addr_bindings);

    lc_log_debug(jnpr_log_level,"into show aliases for %s",ts_str(name_last_part) );

    for (i = 0; i < num_addr_bindings; ++i)
    {
        ts_free(&amask);
        safe_free(mask_len);
        ts_free(&aifname);
        ts_free(&os_arp);

        addr_binding = bn_binding_array_get_quick(ctxt->cisc_addr_bindings, i);
        bail_null(addr_binding);

        err = bn_binding_get_name(addr_binding, &addrroot_bn);
        bail_error(err);

        /*
         * We want to find the parent of the addr nodes, which are like:
         * /net/interface/address/state/ifdevname/vlan1249/ipv4addr/10.99.3.241
         */
        if (!lc_is_prefix(addr_subtree, ts_str(addrroot_bn), false))
        {
            continue;
        }

        tstr_array_free(&name_parts_var);
        name_parts = NULL;

        name_parts = bn_binding_get_name_parts_const_quick(addr_binding);
        if (!name_parts)
        {
            err = bn_binding_get_name_parts(addr_binding, &name_parts_var);
            bail_error(err);
            name_parts = name_parts_var;
        }

        if (tstr_array_length_quick(name_parts) != 8)
        {
            continue;
        }

        err = tstr_array_get(name_parts, 5, (tstring **)&ifdevname);
        bail_error(err);

        err = tstr_array_get_str(name_parts, 7, &addr_str);
        bail_error(err);

        if ( (ts_num_chars(ifdevname) <= 0) || !ts_equal(name_last_part, ifdevname))
            continue;


        snprintf(aifname_bn,sizeof(aifname_bn),"%s/ifname", ts_str(addrroot_bn));

        err = bn_binding_array_get_value_tstr_by_name
            (ctxt->cisc_addr_bindings, aifname_bn, NULL,
             &aifname);
        bail_error(err);
        bail_null(aifname);

        /* Any address on the interface itself is not a secondary */
        if (!ts_str_maybe(aifname) ||
            !safe_strcmp(ts_str(aifname), ts_str(ifdevname)))
        {
            continue;
        }
        snprintf(amask_bn,sizeof(amask_bn),"%s/mask", ts_str(addrroot_bn));
        err = bn_binding_array_get_value_tstr_by_name
            (ctxt->cisc_addr_bindings, amask_bn, NULL, &amask);
        bail_error(err);

        err = lia_ipv4addr_maskspec_to_masklen_str(ts_str(amask),&mask_len);
        bail_error(err);


        err = agentd_binding_array_get_value_tstr_fmt(ctxt->cisc_config_bindings,
                &os_arp,"/net/interface/config/%s/arp",ts_str_maybe_empty(aifname) );
        bail_error(err);

        lc_log_debug(jnpr_log_level,"Secondary address:  %s/%s (alias: '%s')\n", addr_str, mask_len, ts_str(aifname) );

        const char* aindex = NULL;
        aindex = ts_str_nth(aifname,ts_length(name_last_part)+1); //Move past the "<name>:"

        OP_EMIT_TAG_START(ctxt->agentd_context, ODCI_ALIAS_DETAILS);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_NAME,aindex);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_IP_ADDRESS,addr_str);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_NETMASK,mask_len);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ARP,agentd_ts_map_true_false(os_arp) );
        OP_EMIT_TAG_END(ctxt->agentd_context, ODCI_ALIAS_DETAILS);
    }

bail:
    ts_free(&os_arp);
    ts_free(&amask);
    ts_free(&aifname);
    safe_free(addr_subtree);

    return 0;
}
static int agentd_show_interfaces_show_stats (
        const bn_binding_array *bindings,
        const tstring* name,
        agentd_interface_show_context *ctxt
        )
{
    int err = 0;

    const char* r = ts_str(name);

    tstring* rx_by=NULL;
    tstring* tx_by=NULL;

    tstring* rx_pa=NULL;
    tstring* tx_pa=NULL;

    tstring* rx_mcast=NULL;

    tstring* rx_disc=NULL;
    tstring* tx_disc=NULL;

    tstring* rx_err=NULL;
    tstring* tx_err=NULL;

    tstring* rx_oruns=NULL;
    tstring* tx_oruns=NULL;

    tstring* tx_carrier=NULL;

    tstring* rx_frame=NULL;

    tstring* tx_colli=NULL;

    tstring* tx_queuelen=NULL;

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_by,"%s/stats/rx/bytes",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_by,"%s/stats/tx/bytes",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_pa,"%s/stats/rx/packets",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_pa,"%s/stats/tx/packets",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_mcast,"%s/stats/rx/multicast_packets",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_disc,"%s/stats/rx/discards",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_disc,"%s/stats/tx/discards",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_err,"%s/stats/rx/errors",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_err,"%s/stats/tx/errors",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_oruns,"%s/stats/rx/overruns",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_oruns,"%s/stats/tx/overruns",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_carrier,"%s/stats/tx/carrier",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&rx_frame,"%s/stats/rx/frame",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_colli,"%s/stats/tx/collisions",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&tx_queuelen,"%s/txqueuelen",r);
    bail_error(err);


        OP_EMIT_TAG_START(ctxt->agentd_context, ODCI_INTERFACE_STATS);
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_BY,ts_str(rx_by) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_BY,ts_str(tx_by) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_PA,ts_str(rx_pa) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_PA,ts_str(tx_pa) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_MCAST,ts_str(rx_mcast) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_DISC,ts_str(rx_disc) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_DISC,ts_str(tx_disc) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_ERR,ts_str(rx_err) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_ERR,ts_str(tx_err) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_ORUNS,ts_str(rx_oruns) );
            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_ORUNS,ts_str(tx_oruns) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_CARRIER,ts_str(tx_carrier) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_RX_FRAME,ts_str(rx_frame) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_COLLI,ts_str(tx_colli) );

            OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_TX_QUEUELEN,ts_str(tx_queuelen) );
        OP_EMIT_TAG_END(ctxt->agentd_context, ODCI_INTERFACE_STATS);
bail:
    {
        ts_free(&rx_by);
        ts_free(&tx_by);

        ts_free(&rx_pa);
        ts_free(&tx_pa);

        ts_free(&rx_mcast);

        ts_free(&rx_disc);
        ts_free(&tx_disc);

        ts_free(&rx_err);
        ts_free(&tx_err);

        ts_free(&rx_oruns);
        ts_free(&tx_oruns);

        ts_free(&tx_carrier);

        ts_free(&rx_frame);

        ts_free(&tx_colli);

        ts_free(&tx_queuelen);
    }
    return err;
}
static int agentd_show_ipv6_addresses (agentd_interface_show_context *ctxt, const bn_binding_array * bindings,
                                             const char * node_parent) {
    int err = 0;
    node_name_t ipv6_addr_wc_name = {0}, ipv6_addr_name = {0};
    int ipv6_wc_pos = 0;
    tstr_array * static_ids = NULL;
    uint32 num_addrs = 0, i = 0;
    const char * static_id = NULL;
    tstring * os_ipv6_addr = NULL;
    tstring * os_ipv6_mask_len = NULL;
    str_value_t ipv6_addr_mask = {0};

    lc_log_debug (jnpr_log_level, "IPv6 addresses from node :%s", node_parent);
    if (strstr (node_parent, "/net/interface/config") ) { 
        snprintf(ipv6_addr_name, sizeof(ipv6_addr_name), 
                  "%s/addr/ipv6/static", node_parent);
        snprintf(ipv6_addr_wc_name, sizeof(ipv6_addr_wc_name), 
                  "%s/addr/ipv6/static/*", node_parent);
        ipv6_wc_pos = 7;
    } else if (strstr (node_parent, "/net/interface/state") ) {
        snprintf(ipv6_addr_name, sizeof(ipv6_addr_name), 
                  "%s/addr/ipv6", node_parent);
        snprintf (ipv6_addr_wc_name, sizeof(ipv6_addr_wc_name),
                  "%s/addr/ipv6/*", node_parent);
        ipv6_wc_pos = 6;
    } else {
        lc_log_basic (LOG_ERR, "Incorrect parent node for gettng ipv6 addresses");
        err = 1;
        bail_error (err);
    }
    err = bn_binding_array_get_name_part_tstr_array(bindings,
                                                    ipv6_addr_wc_name,
                                                    ipv6_wc_pos,
                                                    &static_ids);
    bail_error (err);
    num_addrs = tstr_array_length_quick (static_ids);
    lc_log_debug (jnpr_log_level, "Number of IPv6 addresses :%d", num_addrs);
    
    for (i = 0; i < num_addrs; i++) {
        static_id = tstr_array_get_str_quick (static_ids, i);
        bail_null (static_id);
        
        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_ipv6_addr,
                       "%s/%s/ip",ipv6_addr_name, static_id);
        bail_error(err);
        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_ipv6_mask_len,
                     "%s/%s/mask_len",ipv6_addr_name, static_id);
        bail_error(err);
      
        snprintf (ipv6_addr_mask , sizeof (ipv6_addr_mask), 
                   "%s/%s", ts_str(os_ipv6_addr), ts_str(os_ipv6_mask_len));
        OP_EMIT_TAG_VALUE (ctxt->agentd_context, ODCI_ADDRESS, ipv6_addr_mask);
        ts_free (&os_ipv6_addr); 
        ts_free (&os_ipv6_mask_len); 
    }

bail:
    tstr_array_free (&static_ids);
    ts_free (&os_ipv6_addr);
    ts_free (&os_ipv6_mask_len);
    return err;
}
static int agentd_bonding_show_one(
                    const bn_binding_array *bindings, uint32 idx,
                    const bn_binding *binding, const tstring *name,
                    const tstr_array *name_components,
                    const tstring *name_last_part,
                    const tstring *value, void *callback_data)
{
    int err = 0;
    const char *node_name = NULL; /* node name */
    const char *bonding = NULL;

    uint32 num_intfs = 0;

    node_name_t node_name_tmp = {0};

    agentd_context_t* ctxt = callback_data;

    tstring* os_link_mon_time=NULL;
    tstring* os_up_delay_time=NULL;
    tstring* os_down_delay_time=NULL;

    tstring* os_name=NULL;
    tstring* os_enabled=NULL;
    tstring* os_mode=NULL;

    bail_null(ctxt);

    node_name = ts_str(name);
    bail_null(node_name);

    bonding = ts_str(name_last_part);
    bail_null(bonding);

    lc_log_debug(jnpr_log_level,"Showing bond %s and last part = %s",node_name,bonding);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_link_mon_time,"/net/bonding/config/%s/link-mon-time", bonding);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_up_delay_time,"/net/bonding/config/%s/up-delay-time", bonding);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_down_delay_time,"/net/bonding/config/%s/down-delay-time", bonding);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_name,    "%s/name",  node_name);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_enabled, "%s/enable",node_name);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_mode,    "%s/mode",  node_name);
    bail_error(err);

    { //This block outputs xml content
            OP_EMIT_TAG_START(ctxt, ODCI_BOND_DETAIL);
                OP_EMIT_TAG_VALUE(ctxt, ODCI_NAME,ts_str(os_name) );
                OP_EMIT_TAG_VALUE(ctxt, ODCI_ENABLED,agentd_ts_map_true_false(os_enabled) );
                OP_EMIT_TAG_VALUE(ctxt, ODCI_MODE,ts_str(os_mode) );
                OP_EMIT_TAG_VALUE(ctxt, ODCI_LINK_MON_TIME,ts_str(os_link_mon_time) );
                OP_EMIT_TAG_VALUE(ctxt, ODCI_DOWN_DEL_TIME,ts_str(os_down_delay_time) );
                OP_EMIT_TAG_VALUE(ctxt, ODCI_UP_DEL_TIME,ts_str(os_up_delay_time) );
                snprintf(node_name_tmp,sizeof(node_name_tmp),"/net/bonding/config/%s/interface/*", bonding);
                err = mdc_foreach_binding_prequeried(bindings,node_name_tmp, NULL, agentd_bonding_show_one_bond_if,ctxt,&num_intfs);
            OP_EMIT_TAG_END(ctxt, ODCI_BOND_DETAIL);
    }

    bail_error(err);

    if (num_intfs == 0)
        lc_log_debug(jnpr_log_level,"No interfaces for %s",ts_str(os_name));

bail:

    ts_free(&os_link_mon_time);
    ts_free(&os_up_delay_time);
    ts_free(&os_down_delay_time);

    ts_free(&os_name);
    ts_free(&os_enabled);
    ts_free(&os_mode);

    return(err);
}
static int
md_nvsd_pp_validate_pub_server_uri(const tstring *name,
			tstring **ret_msg)
{
    int err = 0, length = 0;
    unsigned int  i = 0;
    int32 colon_offset =0, slash_offset = 0, uri_offset = 0;
    tstring *absuri = NULL;
    tstring *port = NULL;
    const char *c_port = NULL;

    if (  !(ts_has_prefix_str(name, "rtsp://", true) ||
		ts_has_prefix_str(name, "http://", true))) {

	err = ts_new_sprintf(ret_msg, "only rtsp:// and http:// URLs are supported");
	err = lc_err_not_found;
	goto bail;
    }

    err = ts_find_str(name, 0, "://", &uri_offset);
    length = ts_length(name) - uri_offset + strlen("://");
    err = ts_substr (name, 7, length, &absuri);
    bail_null(absuri);

    err = ts_find_str(absuri, 0, ":", &colon_offset);
    err = ts_find_str(absuri, 0, "/", &slash_offset);
    if (colon_offset != -1) {
	if(slash_offset != -1) {
	    if(slash_offset < colon_offset){
		err = ts_new_sprintf(ret_msg,
			"Invalid Pub Server URL \n");
		err = lc_err_not_found;
		goto bail;

	    }
	    err = ts_substr (absuri,
		    colon_offset,
		    slash_offset - colon_offset, &port);
	    bail_null(port);
	}
	else {
	    err = ts_substr (absuri,
		    colon_offset,
		    length - colon_offset, &port);
	    bail_null( port);
	}

	err = ts_trim (port, ':', '/');
	bail_null(port);

	c_port = ts_str(port);

	for ( i = 0 ; i < strlen ( c_port) ; i++) {
	    if ( !(isdigit(c_port [i]) ) ) {
		err = ts_new_sprintf(ret_msg,
			"Invalid Pub Server Port Number \n");
		err = lc_err_not_found;
		goto bail;
	    }
	}	
    }
bail:
    ts_free(&absuri);
    ts_free(&port);
    return err;
}
int
md_nkn_ethtool(const char *intf_name,
	nkn_ethtool_cmd_t cmd, uint32_t *data)
{

    int err = 0;
    tstring *output = NULL;
    tstr_array *ret_params = NULL;
    const char *cmd_str = NULL;
    const char* oper = NULL;
    int32_t status = 0;
    struct ethtool_value edata;
    int need_change = 0;

    bail_null(intf_name);
    bail_null(data);

    if (cmd == NKN_ETHTOOL_GRO_SET) {
	oper = *data? "on":"off";
	cmd_str = "gro";

	err = lc_launch_quick_status(&status, &output, true, 5
		,"/usr/sbin/ethtool", "-K"
		,intf_name, cmd_str, oper);
	bail_error(err);

	memset(&edata, 0, sizeof(struct ethtool_value));
	edata.cmd = ETHTOOL_GFLAGS;
	if (!md_nkn_ethtool_ioctl(intf_name, &edata)) {
	    if(*data && !(ETH_FLAG_LRO & edata.data)) {
		edata.data |= ETH_FLAG_LRO;
		need_change = 1;
		lc_log_basic(LOG_NOTICE, "Enabling RSC/LRO for intf '%s'\n", intf_name);
	    }
	    else if (!*data && (ETH_FLAG_LRO & edata.data)) {
		edata.data &= ~ETH_FLAG_LRO;
		need_change = 1;
		lc_log_basic(LOG_NOTICE, "Disabling RSC/LRO for intf '%s'\n", intf_name);
	    }
	    else {
		need_change = 0;
	    }

	    if (need_change) {
		edata.cmd = ETHTOOL_SFLAGS;
		md_nkn_ethtool_ioctl(intf_name, &edata);
	    }
	}

	complain_error(status);

    } else if (cmd == NKN_ETHTOOL_GRO_GET) {
	uint32_t gro_idx = 0;
	const char *gro_status = NULL;
	str_value_t gro = {0};

	err = lc_launch_quick_status(&status, &output, true,3,
		"/usr/sbin/ethtool", "-k",
		intf_name);
	bail_error(err);

	complain_error(status);

	err = ts_tokenize(output, '\n', '\\', '"', 0, &ret_params);
	bail_error(err);

	err = tstr_array_linear_search_prefix_str(ret_params, "generic-receive-offload:",
		false, true, 0, &gro_idx);
	bail_error(err);

	gro_status = tstr_array_get_str_quick(ret_params, gro_idx);
	bail_null(gro_status);

	sscanf(gro_status, "generic-receive-offload: %s", gro);

	*data = (!strcmp(gro, "on")) ? 1 : 0;
    }

    if (cmd == NKN_ETHTOOL_GSO_SET) {
	oper = *data? "on":"off";
	cmd_str = "gso";

	err = lc_launch_quick_status(&status, &output, true, 5
		,"/usr/sbin/ethtool", "-K"
		,intf_name, cmd_str, oper);
	bail_error(err);

	memset(&edata, 0, sizeof(struct ethtool_value));
	edata.cmd = ETHTOOL_GGSO;
	if (!md_nkn_ethtool_ioctl(intf_name, &edata)) {
	    if(*data && !(NETIF_F_GSO & edata.data)) {
		edata.data |= NETIF_F_GSO;
		need_change = 1;
		lc_log_basic(LOG_NOTICE, "Enabling GSO for intf '%s'\n", intf_name);
	    }
	    else if (!*data && (NETIF_F_GSO & edata.data)) {
		edata.data &= ~NETIF_F_GSO;
		need_change = 1;
		lc_log_basic(LOG_NOTICE, "Disabling GSO for intf '%s'\n", intf_name);
	    }
	    else {
		need_change = 0;
	    }

	    if (need_change) {
		edata.cmd = ETHTOOL_SGSO;
		md_nkn_ethtool_ioctl(intf_name, &edata);
	    }
	}

	complain_error(status);

    } else if (cmd == NKN_ETHTOOL_GSO_GET) {
	uint32_t gso_idx = 0;
	const char *gso_status = NULL;
	str_value_t gso = {0};

	err = lc_launch_quick_status(&status, &output, true,3,
		"/usr/sbin/ethtool", "-k",
		intf_name);
	bail_error(err);

	complain_error(status);

	err = ts_tokenize(output, '\n', '\\', '"', 0, &ret_params);
	bail_error(err);

	err = tstr_array_linear_search_prefix_str(ret_params, "generic-segmentation-offload:",
		false, true, 0, &gso_idx);
	bail_error(err);

	gso_status = tstr_array_get_str_quick(ret_params, gso_idx);
	bail_null(gso_status);

	sscanf(gso_status, "generic-segmentation-offload: %s", gso);

	*data = (!strcmp(gso, "on")) ? 1 : 0;
    }

    if (cmd == NKN_ETHTOOL_TSO_SET) {
	oper = *data? "on":"off";
	cmd_str = "tso";

	err = lc_launch_quick_status(&status, &output, true, 5
		,"/usr/sbin/ethtool", "-K"
		,intf_name, cmd_str, oper);
	bail_error(err);

	memset(&edata, 0, sizeof(struct ethtool_value));
	edata.cmd = ETHTOOL_GTSO;
	if (!md_nkn_ethtool_ioctl(intf_name, &edata)) {
	    if(*data && !(NETIF_F_TSO & edata.data)) {
		edata.data |= NETIF_F_TSO;
		need_change = 1;
		lc_log_basic(LOG_NOTICE, "Enabling TSO for intf '%s'\n", intf_name);
	    }
	    else if (!*data && (NETIF_F_TSO & edata.data)) {
		edata.data &= ~NETIF_F_TSO;
		need_change = 1;
		lc_log_basic(LOG_NOTICE, "Disabling TSO for intf '%s'\n", intf_name);
	    }
	    else {
		need_change = 0;
	    }

	    if (need_change) {
		edata.cmd = ETHTOOL_STSO;
		md_nkn_ethtool_ioctl(intf_name, &edata);
	    }
	}

	complain_error(status);

    } else if (cmd == NKN_ETHTOOL_TSO_GET) {
	uint32_t tso_idx = 0;
	const char *tso_status = NULL;
	str_value_t tso = {0};

	err = lc_launch_quick_status(&status, &output, true,3,
		"/usr/sbin/ethtool", "-k",
		intf_name);
	bail_error(err);

	complain_error(status);

	err = ts_tokenize(output, '\n', '\\', '"', 0, &ret_params);
	bail_error(err);

	err = tstr_array_linear_search_prefix_str(ret_params, "tcp-segmentation-offload:",
		false, true, 0, &tso_idx);
	bail_error(err);

	tso_status = tstr_array_get_str_quick(ret_params, tso_idx);
	bail_null(tso_status);

	sscanf(tso_status, "tcp-segmentation-offload: %s", tso);

	*data = (!strcmp(tso, "on")) ? 1 : 0;
    }

bail:
    tstr_array_free(&ret_params);
    ts_free(&output);
    return err;
}
static int agentd_show_interfaces_show_one_state(
                        const bn_binding_array *bindings, uint32 idx,
                        const bn_binding *binding, const tstring *name,
                        const tstr_array *name_components,
                        const tstring *name_last_part,
                        const tstring *value,
                        void *callback_data)
{
    int err = 0;
    lc_log_debug(jnpr_log_level, "showing interface %s = %s", ts_str(name), ts_str(name_last_part) );

    uint8 masklen = 0;
    const char *r = NULL;
    tstring *masklen_tstr = NULL;
    char *o_netmask = NULL;
    uint32 show_type = 0;

    agentd_interface_show_context *ctxt = NULL;

    tbool display = true;
    node_name_t bn_name = {0};
    str_value_t o_speed =  {0};

    tstring *alias_ifdevname = NULL;
    tbool is_alias = false;

    const bn_binding_array *config_bindings = NULL;

    node_name_t  node_name = {0};

    tstring* os_comment=NULL;
    tstring* os_ip_addr=NULL;

    tstring* os_speed=NULL;
    tstring* os_duplex=NULL;
    tstring* os_mtu=NULL;

    tstring* os_admin_up=NULL;
    tstring* os_link_up=NULL;

    tstring* os_devsource=NULL;
    tstring* os_hwaddr=NULL;

    tstring* os_iftype=NULL;
    tstring* os_arp=NULL;

    tstring* os_dhcp=NULL;
    tstring *os_ipv6_enabled=NULL;

    bail_null(callback_data);

    ctxt = callback_data;
    show_type = ctxt->cisc_magic;

    config_bindings = ctxt->cisc_config_bindings;

    if (ctxt->cisc_show_all)
    {
        snprintf(bn_name,sizeof(bn_name),"/net/interface/config/%s/display",
                           ts_str(name_last_part));

        err = bn_binding_array_get_value_tbool_by_name(config_bindings, bn_name, NULL, &display);
        bail_error_msg(err, "Failed to get IF display configuration");

        if (!display)
        {
            goto bail;
        }
    }

    err = bn_binding_array_get_value_tstr_by_name_fmt( config_bindings, NULL,
            &alias_ifdevname,"/net/interface/config/%s/alias/ifdevname",
            ts_str(name_last_part)
            );

    bail_error(err);

    if (alias_ifdevname && (ts_length(alias_ifdevname) > 0))
    {
        is_alias = true;
    }

    r = ts_str(name);

    bail_null(r);


    err=agentd_binding_array_get_value_tstr_fmt(bindings,&masklen_tstr,"%s/addr/ipv4/1/mask_len",r);
    bail_error(err);

    if (masklen_tstr)
    {
        err =lia_masklen_str_to_ipv4addr_str(ts_str(masklen_tstr), &o_netmask);
        bail_error(err);
    }
    else
    {
        o_netmask = strdup("");
        bail_null(o_netmask);
    }

    lc_log_debug(jnpr_log_level,"netmask of %s = %s",name?ts_str(name):"*", o_netmask );



    /* Run-time interface state */

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_admin_up,"%s/flags/oper_up",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_link_up,"%s/flags/link_up",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_ip_addr,"%s/addr/ipv4/1/ip",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_devsource,"%s/devsource",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_speed,"%s/type/ethernet/speed",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_duplex,"%s/type/ethernet/duplex",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_iftype,"%s/iftype",r);
    bail_error(err);
    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_mtu,"%s/mtu",r);
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(config_bindings,&os_comment,"/net/interface/config/%s/comment",ts_str(name_last_part));
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(config_bindings,&os_arp,"/net/interface/config/%s/arp",ts_str(name_last_part));
    bail_error(err);

    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_ipv6_enabled,"%s/addr/settings/ipv6/enable",r);
    bail_error(err);
    
#ifdef PROD_FEATURE_DHCP_CLIENT
    err=agentd_binding_array_get_value_tstr_fmt(config_bindings,&os_dhcp,"/net/interface/config/%s/addr/ipv4/dhcp",ts_str(name_last_part) );
    bail_error(err);
#endif /*PROD_FEATURE_DHCP_CLIENT*/


    err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_hwaddr,"%s/type/ethernet/mac",r);
    bail_error(err);

    if (
            !os_hwaddr ||
       ts_length(os_hwaddr) == 0 ||
       ts_cmp_str(os_hwaddr, "N/A", false) == 0
      )
    {
        /*
         * The ethernet mac was empty, see if the top level "hwaddr"
         * has something.
         */
        ts_free(&os_hwaddr);
        err=agentd_binding_array_get_value_tstr_fmt(bindings,&os_hwaddr,"%s/hwaddr",r);
        bail_error(err);
    }

    {//This block does the necessary manipulations on the collected data

        /*
         * the retrieved speed value is like : "1000Mb/s (auto)" or "100Mb/s"
         * we need to only pass the numeric part of the value to MFA
         * */
        unsigned int speed = strtoul(ts_str_maybe_empty(os_speed),NULL,10);
        if(speed>0) snprintf(o_speed,sizeof(o_speed),"%u",speed);

        /*
         * The retrieved duplex has value like : "full (auto)", "half (auto)"
         * but we need to prove only : full or half to MFA
         */
        err = agentd_cook_duplex_state_value(os_duplex);
        bail_error(err);
    }
    { //This block of code is used to do XML output

        int showStats = (show_type != cid_interface_show_brief) && !is_alias;

            OP_EMIT_TAG_START(ctxt->agentd_context, ODCI_INTERFACE_BRIEF);
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_NAME,ts_str_maybe_empty(name_last_part) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ADMIN_STATE,agentd_ts_map_true_false(os_admin_up) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_LINK_STATE,agentd_ts_map_true_false(os_link_up) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_IP_ADDRESS,ts_str_maybe_empty(os_ip_addr) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_NETMASK,o_netmask );
                OP_EMIT_TAG_START(ctxt->agentd_context, ODCI_IPV6);
                    OP_EMIT_TAG_VALUE (ctxt->agentd_context, ODCI_ENABLED, agentd_ts_map_true_false(os_ipv6_enabled) );
                    agentd_show_ipv6_addresses (ctxt, bindings, r);
                OP_EMIT_TAG_END(ctxt->agentd_context, ODCI_IPV6);
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_SPEED,o_speed );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_DUPLEX,ts_str_maybe_empty(os_duplex) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_INTERFACE_TYPE,ts_str_maybe_empty(os_iftype) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_INTERFACE_SOURCE,ts_str_maybe_empty(os_devsource) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_MTU,ts_str_maybe_empty(os_mtu) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_HW_ADDRESS,ts_str_maybe_empty(os_hwaddr) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_COMMENT,ts_str_maybe_empty(os_comment) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_ARP,agentd_ts_map_true_false(os_arp) );
                OP_EMIT_TAG_VALUE(ctxt->agentd_context, ODCI_DHCP,agentd_ts_map_true_false(os_dhcp) );

                agentd_show_if_aliases(ctxt,name_last_part);

                agentd_show_bond_maybe(ctxt,name_last_part,os_devsource);

            OP_EMIT_TAG_END(ctxt->agentd_context, ODCI_INTERFACE_BRIEF);

            if (showStats)
            {
                agentd_show_interfaces_show_stats(bindings,name,ctxt);
            }
    }

 bail:
    lc_log_debug(jnpr_log_level,"crossed bail...");
    ts_free(&alias_ifdevname);

    ts_free(&masklen_tstr);
    safe_free(o_netmask);

    { //This block is to free objects created to emit XML content

        ts_free(&os_comment);

        ts_free(&os_ip_addr);

        ts_free(&os_speed);
        ts_free(&os_duplex);
        ts_free(&os_mtu);

        ts_free(&os_admin_up);
        ts_free(&os_link_up);

        ts_free(&os_devsource);
        ts_free(&os_hwaddr);

        ts_free(&os_iftype);
        ts_free(&os_ipv6_enabled);
    };
    return(err);
}
Exemplo n.º 16
0
void ts_crypto_free(struct ts_crypto_ctx *ctx) {
    ts_free(ctx);
}
int
geodbd_mgmt_handle_action_request(gcl_session *sess,
	bn_request **inout_action_request, void *arg)
{
    int err = 0;
    bn_msg_type req_type = bbmt_none;
    bn_binding_array *bindings = NULL;
    tstring *action_name = NULL;
    tstring *t_filename = NULL;
    tstring *t_app_name = NULL;
    tstring *ret_output = NULL;
    bn_request *req = NULL;

    /* Standard Samara logic first */
    bail_null(inout_action_request);
    bail_null(*inout_action_request);
    
    err = bn_request_get
	(*inout_action_request, &req_type, NULL, true, &bindings, NULL, NULL);
    bail_error(err);
    bail_require(req_type == bbmt_action_request);
    err = bn_action_request_msg_get_action_name(*inout_action_request,
	    &action_name);
    bail_error(err);
    lc_log_basic(LOG_INFO, "Received action %s", ts_str(action_name));
    if (ts_equal_str (action_name, "/nkn/geodb/actions/install", false)){
	err = bn_binding_array_get_value_tstr_by_name
	    (bindings, "filename", NULL, &t_filename);
	if (!t_filename) {
	    lc_log_basic(LOG_NOTICE, "No filename entered\n");
	    goto bail;
	}
	lc_log_basic(LOG_NOTICE, I_("Got the install action for %s \n"),
		ts_str(t_filename));
	/* Call the  Geodbd function*/
	err = geodbd_install(ts_str(t_filename), &ret_output);
	/* Send response message*/
	err = bn_response_msg_create_send
	    (sess, bbmt_action_response,
	     bn_request_get_msg_id(*inout_action_request),
	     err, ts_str(ret_output), 0);

    /*Raise an event to notify the installation*/
    err = bn_event_request_msg_create(&req, "/nkn/geodb/events/installation");
    bail_error(err);

    err = mdc_send_mgmt_msg(geodbd_mcc, req, false, NULL, NULL, NULL);
    bail_error(err);
    }
    else if (ts_equal_str (action_name, "/nkn/geodb/actions/info_display", false)){

	err = bn_binding_array_get_value_tstr_by_name
	    (bindings, "app_name", NULL, &t_app_name);
	if (!t_app_name) {
	    lc_log_basic(LOG_NOTICE, "No application entered\n");
	    goto bail;
	}
	lc_log_basic(LOG_NOTICE, I_("Got the info_display action for %s \n"),
		ts_str(t_app_name));
	/* Call the  Geodbd function*/
	err = geodbd_info_display(ts_str(t_app_name), &ret_output);
	/* Send response message*/
	err = bn_response_msg_create_send
	    (sess, bbmt_action_response,
	     bn_request_get_msg_id(*inout_action_request),
	     err, ts_str(ret_output), 0);
    }

bail:
    ts_free(&action_name);
    ts_free(&ret_output);
    ts_free(&t_filename);
    bn_binding_array_free(&bindings);
	bn_request_msg_free(&req);

    return err;
}