Fix VLANTermination LowerLayers bug and other bugs

This commit is contained in:
Omar Kallel 2019-02-20 17:56:08 +01:00
parent d71f1e51f0
commit fe51651e57
5 changed files with 107 additions and 26 deletions

View file

@ -40,7 +40,7 @@ config cwmp 'cpe'
# datamodel possible configs: tr098, tr181
option datamodel 'tr181'
option notification '1'
#vlan_method: 1: iopsys method 2: genexis method
#vlan_method: 1: only tagged vlantermination 2: all vlanterminations (tagged and untagged)
option vlan_method '1'
config cwmp 'lwn'

View file

@ -1451,4 +1451,55 @@ char *get_macaddr(char *interface_name)
}
return mac;
}
}
/*
* Manage string lists
*/
int is_ifname_exit_in_list(char *iface_list, char *ifname){
char *pch, *spch, *list;
list= strdup(iface_list);
for (pch = strtok_r(list, " ", &spch); pch != NULL; pch = strtok_r(NULL, " ", &spch)) {
if(strcmp(pch, ifname) == 0)
return 1;
}
return 0;
}
void add_iface_to_iface_list(char **iface_list, char *ifname){
char *list= NULL;
list= dmstrdup(*iface_list);
dmfree(*iface_list);
*iface_list= NULL;
dmasprintf(iface_list, "%s %s", list, ifname);
}
void remove_iface_from_iface_list(char **iface_list, char *ifname){
char *list= NULL, *tmp=NULL;
char *pch, *spch;
list= dmstrdup(*iface_list);
dmfree(*iface_list);
*iface_list= NULL;
for (pch = strtok_r(list, " ", &spch); pch != NULL; pch = strtok_r(NULL, " ", &spch)) {
if(strcmp(pch, ifname) == 0)
continue;
if(tmp == NULL)
dmasprintf(iface_list, "%s", pch);
else
dmasprintf(iface_list, "%s %s", tmp, pch);
if(tmp){
dmfree(tmp);
tmp= NULL;
}
if(*iface_list){
tmp= dmstrdup(*iface_list);
dmfree(*iface_list);
*iface_list= NULL;
}
}
dmasprintf(iface_list, "%s", tmp);
}

View file

@ -125,6 +125,7 @@ struct dmmap_sect {
struct dm_args
{
struct uci_section *section;
struct uci_section *dmmap_section;
char *name;
};
@ -184,5 +185,8 @@ unsigned char isdigit_str(char *str);
char *dm_strword(char *src, char *str);
char **strsplit(const char* str, const char* delim, size_t* numtokens);
char *get_macaddr(char *ifname);
int is_ifname_exit_in_list(char *iface_list, char *ifname);
void add_iface_to_iface_list(char **iface_list, char *ifname);
void remove_iface_from_iface_list(char **iface_list, char *ifname);
#endif

View file

@ -539,6 +539,26 @@ char *update_instance_without_section(int action, char **last_inst, void *argv[]
return instance;
}
char *get_vlan_last_instance_icwmpd(char *package, char *section, char *opt_inst, char *vlan_method)
{
struct uci_section *s;
char *inst = NULL;
char *last_inst = NULL, *type, *confsect, *sect_name;
uci_path_foreach_sections(icwmpd, package, section, s) {
dmuci_get_value_by_section_string(s, "section_name", &sect_name);
get_config_section_of_dmmap_section("network", "device", sect_name, &confsect);
dmuci_get_value_by_section_string(confsect, "type", &type);
if ((strcmp(vlan_method, "2") != 0 && strcmp(vlan_method, "1") != 0) || (strcmp(vlan_method, "1") == 0 && strcmp(type, "untagged") == 0) )
continue;
inst = update_instance_icwmpd(s, last_inst, opt_inst);
if(last_inst)
dmfree(last_inst);
last_inst = dmstrdup(inst);
}
return inst;
}
char *get_last_instance_icwmpd(char *package, char *section, char *opt_inst)
{
struct uci_section *s;

View file

@ -594,6 +594,7 @@ int get_vlan_term_name(char *refparam, struct dmctx *ctx, void *data, char *inst
/**************************************************************************
* SET & GET Lowerlayers
***************************************************************************/
int get_vlan_term_lowerlayers(char *refparam, struct dmctx *ctx, void *data, char *instance, char **value)
{
char *devifname, *ifname, *dupifname;
@ -607,10 +608,7 @@ int get_vlan_term_lowerlayers(char *refparam, struct dmctx *ctx, void *data, cha
dupifname = dmstrdup(ifname);
for (pch = strtok_r(dupifname, " ", &spch); pch != NULL; pch = strtok_r(NULL, " ", &spch)) {
if(strcmp(pch, devifname) == 0){
macaddr = get_macaddr(section_name(section));
if (macaddr != NULL && *macaddr != '\0'){
adm_entry_get_linker_param(ctx, dm_print_path("%s%cEthernet%cLink%c", dmroot, dm_delim, dm_delim, dm_delim), macaddr, value);
}
adm_entry_get_linker_param(ctx, dm_print_path("%s%cEthernet%cLink%c", dmroot, dm_delim, dm_delim, dm_delim), section_name(section), value);
break;
}
}
@ -623,8 +621,8 @@ int set_vlan_term_lowerlayers(char *refparam, struct dmctx *ctx, void *data, cha
{
char *linker= NULL;
char *newvalue= NULL;
char *ifname;
struct uci_section *section;
char *ifname, *v, *vlan_name= NULL, *iface_list;
struct uci_section *s, *vlan_s;
switch (action) {
case VALUECHECK:
@ -638,13 +636,20 @@ int set_vlan_term_lowerlayers(char *refparam, struct dmctx *ctx, void *data, cha
} else
adm_entry_get_linker_value(ctx, value, &linker);
if (linker == NULL || *linker == '\0') {
CWMP_LOG(ERROR, "failed to get linker of %s", value)
if (linker == NULL || *linker == '\0')
return -1;
}
/* linker value of Ethernet.Link is the mac address */
dmuci_set_value_by_section(((struct dm_args *)data)->section, "macaddr", linker);
dmuci_get_value_by_section_string(((struct dm_args *)data)->section, "name", &vlan_name);
uci_foreach_sections("network", "interface", s) {
dmuci_get_value_by_section_string(s, "ifname", &iface_list);
if(strcmp(section_name(s), linker) != 0 && is_ifname_exit_in_list(iface_list, vlan_name)){
remove_iface_from_iface_list(&iface_list, vlan_name);
dmuci_set_value_by_section(s, "ifname", iface_list);
} else if (strcmp(section_name(s), linker) == 0 && !is_ifname_exit_in_list(iface_list, vlan_name)){
add_iface_to_iface_list(&iface_list, vlan_name);
dmuci_set_value_by_section(s, "ifname", iface_list);
}
}
}
return 0;
}
@ -660,12 +665,12 @@ int add_vlan_term(char *refparam, struct dmctx *ctx, void *data, char **instance
check_create_dmmap_package("dmmap_network");
dmuci_get_option_value_string("cwmp", "cpe", "vlan_method", &vlan_method);
if(strcmp(vlan_method, "2") == 0)
instance = get_last_instance_icwmpd("dmmap_network", "device", "genexis_vlan_term_instance");
instance = get_vlan_last_instance_icwmpd("dmmap_network", "device", "all_vlan_term_instance", vlan_method);
else
instance = get_last_instance_icwmpd("dmmap_network", "device", "vlan_term_instance");
instance = get_vlan_last_instance_icwmpd("dmmap_network", "device", "only_tagged_vlan_term_instance", vlan_method);
dmuci_get_option_value_string("ports", "WAN", "ifname", &eth_wan);
dmasprintf(&vid, "%d", atoi(instance)+1);
dmasprintf(&vid, "%d", instance?atoi(instance)+4:4);
dmasprintf(&vlan_name, "vlan_%s", vid);
dmuci_set_value("network", vlan_name, "", "device");
dmuci_set_value("network", vlan_name, "ifname", eth_wan);
@ -677,9 +682,9 @@ int add_vlan_term(char *refparam, struct dmctx *ctx, void *data, char **instance
dmuci_add_section_icwmpd("dmmap_network", "device", &dmmap_network, &v);
dmuci_set_value_by_section(dmmap_network, "section_name", vlan_name);
if(strcmp(vlan_method, "2") == 0)
*instance_para = update_instance_icwmpd(dmmap_network, instance, "genexis_vlan_term_instance");
*instance_para = update_instance_icwmpd(dmmap_network, instance, "all_vlan_term_instance");
else
*instance_para = update_instance_icwmpd(dmmap_network, instance, "vlan_term_instance");
*instance_para = update_instance_icwmpd(dmmap_network, instance, "only_tagged_vlan_term_instance");
return 0;
}
@ -698,12 +703,12 @@ int delete_vlan_term(char *refparam, struct dmctx *ctx, void *data, char *instan
if(is_section_unnamed(section_name(((struct dm_args *)data)->section))){
LIST_HEAD(dup_list);
if(strcmp(vlan_method, "2") == 0){
delete_sections_save_next_sections("dmmap_network", "device", "genexis_vlan_term_instance", section_name((struct uci_section *)data), atoi(instance), &dup_list);
update_dmmap_sections(&dup_list, "genexis_vlan_term_instance", "dmmap_network", "device");
delete_sections_save_next_sections("dmmap_network", "device", "all_vlan_term_instance", section_name((struct uci_section *)data), atoi(instance), &dup_list);
update_dmmap_sections(&dup_list, "all_vlan_term_instance", "dmmap_network", "device");
}
else{
delete_sections_save_next_sections("dmmap_network", "device", "vlan_term_instance", section_name((struct uci_section *)data), atoi(instance), &dup_list);
update_dmmap_sections(&dup_list, "vlan_term_instance", "dmmap_network", "device");
delete_sections_save_next_sections("dmmap_network", "device", "only_tagged_vlan_term_instance", section_name((struct uci_section *)data), atoi(instance), &dup_list);
update_dmmap_sections(&dup_list, "only_tagged_vlan_term_instance", "dmmap_network", "device");
}
dmuci_delete_by_section_unnamed(((struct dm_args *)data)->section, NULL, NULL);
} else {
@ -749,13 +754,13 @@ int browseVLANTermInst(struct dmctx *dmctx, DMNODE *parent_node, void *prev_data
list_for_each_entry(p, &dup_list, list) {
dmuci_get_value_by_section_string(p->config_section, "type", &type);
dmuci_get_option_value_string("cwmp", "cpe", "vlan_method", &vlan_method);
if ((strcmp(vlan_method, "2") != 0 && strcmp(vlan_method, "1") != 0) || (strcmp(vlan_method, "1") == 0 && strcmp(type, "untagged") == 0) ) //&& (strcmp(vlan_method, "1") != 0 || strcmp(type, "untagged") != 0)
if ((strcmp(vlan_method, "2") != 0 && strcmp(vlan_method, "1") != 0) || (strcmp(vlan_method, "1") == 0 && strcmp(type, "untagged") == 0) )
continue;
curr_vlan_term_args.section = p->config_section;
if(strcmp(vlan_method, "2") == 0)
vlan_term = handle_update_instance(1, dmctx, &vlan_term_last, update_instance_alias, 3, p->dmmap_section, "genexis_vlan_term_instance", "genexis_vlan_term_alias");
vlan_term = handle_update_instance(1, dmctx, &vlan_term_last, update_instance_alias, 3, p->dmmap_section, "all_vlan_term_instance", "genexis_vlan_term_alias");
else
vlan_term = handle_update_instance(1, dmctx, &vlan_term_last, update_instance_alias, 3, p->dmmap_section, "vlan_term_instance", "vlan_term_alias");
vlan_term = handle_update_instance(1, dmctx, &vlan_term_last, update_instance_alias, 3, p->dmmap_section, "only_tagged_vlan_term_instance", "vlan_term_alias");
if (DM_LINK_INST_OBJ(dmctx, parent_node, (void *)&curr_vlan_term_args, vlan_term) == DM_STOP)
break;
}
@ -766,7 +771,7 @@ int browseVLANTermInst(struct dmctx *dmctx, DMNODE *parent_node, void *prev_data
int get_linker_link(char *refparam, struct dmctx *dmctx, void *data, char *instance, char **linker)
{
dmuci_get_value_by_section_string(((struct dm_args *)data)->section, "mac", linker);
dmuci_get_value_by_section_string(((struct dm_args *)data)->section, "section_name", linker);
return 0;
}
int get_link_enable(char *refparam, struct dmctx *ctx, void *data, char *instance, char **value)
@ -936,6 +941,7 @@ static void create_link(char *ifname)
dmuci_add_section_icwmpd(DMMAP, "link", &dmmap, &v);
dmuci_set_value_by_section(dmmap, "mac", macaddr);
dmuci_set_value_by_section(dmmap, "section_name", ifname);
}
int browseLinkInst(struct dmctx *dmctx, DMNODE *parent_node, void *prev_data, char *prev_instance)