X-Git-Url: https://git.archive.openwrt.org/?p=project%2Fnetifd.git;a=blobdiff_plain;f=interface-ip.c;h=170b03b089d7b8214513bfe9362b24d333d468c6;hp=93e8723be216b9408144970885e7b59f981f2b93;hb=395199fcd4a1dbf8f52f13ec3e19ff568958e8e7;hpb=58d36928da0e3099e17309bd7a44ee442b5f5153 diff --git a/interface-ip.c b/interface-ip.c index 93e8723..170b03b 100644 --- a/interface-ip.c +++ b/interface-ip.c @@ -64,6 +64,7 @@ interface_ip_add_route(struct interface *iface, struct blob_attr *attr, bool v6) if (!route) return; + route->flags = v6 ? DEVADDR_INET6 : DEVADDR_INET4; route->mask = v6 ? 128 : 32; if ((cur = tb[ROUTE_MASK]) != NULL) { route->mask = parse_netmask_string(blobmsg_data(cur), v6); @@ -83,19 +84,15 @@ interface_ip_add_route(struct interface *iface, struct blob_attr *attr, bool v6) DPRINTF("Failed to parse route gateway: %s\n", (char *) blobmsg_data(cur)); goto error; } - } else { - route->flags |= DEVADDR_DEVICE; } if ((cur = tb[ROUTE_METRIC]) != NULL) route->metric = blobmsg_get_u32(cur); - else - route->metric = -1; if ((cur = tb[ROUTE_MTU]) != NULL) route->mtu = blobmsg_get_u32(cur); - vlist_add(&ip->route, &route->node); + vlist_add(&ip->route, &route->node, &route->mask); return; error: @@ -124,28 +121,51 @@ interface_update_proto_addr(struct vlist_tree *tree, struct interface_ip_settings *ip; struct interface *iface; struct device *dev; - struct device_addr *addr; + struct device_addr *a_new = NULL, *a_old = NULL; bool keep = false; ip = container_of(tree, struct interface_ip_settings, addr); iface = ip->iface; dev = iface->l3_dev->dev; - if (node_old && node_new) + if (node_new) { + a_new = container_of(node_new, struct device_addr, node); + + if ((a_new->flags & DEVADDR_FAMILY) == DEVADDR_INET4 && + !a_new->broadcast) { + + uint32_t mask = ~0; + uint32_t *a = (uint32_t *) &a_new->addr; + + mask >>= a_new->mask; + a_new->broadcast = *a | mask; + } + } + + if (node_old) + a_old = container_of(node_old, struct device_addr, node); + + if (a_new && a_old) { keep = true; + if (a_old->flags != a_new->flags) + keep = false; + + if ((a_new->flags & DEVADDR_FAMILY) == DEVADDR_INET4 && + a_new->broadcast != a_old->broadcast) + keep = false; + } + if (node_old) { - addr = container_of(node_old, struct device_addr, node); - if (!(addr->flags & DEVADDR_EXTERNAL) && addr->enabled && !keep) - system_del_address(dev, addr); - free(addr); + if (!(a_old->flags & DEVADDR_EXTERNAL) && a_old->enabled && !keep) + system_del_address(dev, a_old); + free(a_old); } if (node_new) { - addr = container_of(node_new, struct device_addr, node); - if (!(addr->flags & DEVADDR_EXTERNAL) && !keep) - system_add_address(dev, addr); - addr->enabled = true; + if (!(a_new->flags & DEVADDR_EXTERNAL) && !keep) + system_add_address(dev, a_new); + a_new->enabled = true; } } @@ -397,8 +417,6 @@ interface_ip_init(struct interface_ip_settings *ip, struct interface *iface) ip->enabled = true; vlist_simple_init(&ip->dns_search, struct dns_search_domain, node); vlist_simple_init(&ip->dns_servers, struct dns_server, node); - vlist_init(&ip->route, route_cmp, interface_update_proto_route, - struct device_route, node, mask); - vlist_init(&ip->addr, addr_cmp, interface_update_proto_addr, - struct device_addr, node, mask); + vlist_init(&ip->route, route_cmp, interface_update_proto_route); + vlist_init(&ip->addr, addr_cmp, interface_update_proto_addr); }