X-Git-Url: http://git.archive.openwrt.org/?p=project%2Fnetifd.git;a=blobdiff_plain;f=wireless.c;h=387f4baf709b6242fe8f0100daf49e3c7c75b94f;hp=fbd6191617ab59937ed306f05cf64408c18eb024;hb=HEAD;hpb=212288ba1518c0fd4d44f22e7c2af09022944a9f diff --git a/wireless.c b/wireless.c index fbd6191..387f4ba 100644 --- a/wireless.c +++ b/wireless.c @@ -35,12 +35,16 @@ static const struct uci_blob_param_list wdev_param = { enum { VIF_ATTR_DISABLED, VIF_ATTR_NETWORK, + VIF_ATTR_ISOLATE, + VIF_ATTR_MODE, __VIF_ATTR_MAX, }; static const struct blobmsg_policy vif_policy[__VIF_ATTR_MAX] = { [VIF_ATTR_DISABLED] = { .name = "disabled", .type = BLOBMSG_TYPE_BOOL }, [VIF_ATTR_NETWORK] = { .name = "network", .type = BLOBMSG_TYPE_ARRAY }, + [VIF_ATTR_ISOLATE] = { .name = "isolate", .type = BLOBMSG_TYPE_BOOL }, + [VIF_ATTR_MODE] = { .name = "mode", .type = BLOBMSG_TYPE_STRING }, }; static const struct uci_blob_param_list vif_param = { @@ -79,7 +83,7 @@ vif_config_add_bridge(struct blob_buf *buf, struct blob_attr *networks, bool pre if (!dev) return; - if (dev->type != &bridge_device_type) + if (!dev->type->bridge_capability) return; } @@ -90,6 +94,10 @@ vif_config_add_bridge(struct blob_buf *buf, struct blob_attr *networks, bool pre dev->hotplug_ops->prepare(dev); blobmsg_add_string(buf, "bridge", dev->ifname); + + if (dev->settings.flags & DEV_OPT_MULTICAST_TO_UNICAST) + blobmsg_add_u8(buf, "multicast_to_unicast", + dev->settings.multicast_to_unicast); } static void @@ -204,8 +212,11 @@ static void wireless_interface_handle_link(struct wireless_interface *vif, bool if (up) { struct device *dev = device_get(vif->ifname, 2); - if (dev) + if (dev) { + dev->wireless_isolate = vif->isolate; dev->wireless = true; + dev->wireless_ap = vif->ap_mode; + } } blobmsg_for_each_attr(cur, vif->network, rem) { @@ -276,6 +287,12 @@ __wireless_device_set_up(struct wireless_device *wdev) if (wdev->disabled) return; + if (wdev->retry_setup_failed) + return; + + if (!wdev->autostart) + return; + if (wdev->state != IFS_DOWN || config_init) return; @@ -303,9 +320,9 @@ wdev_handle_config_change(struct wireless_device *wdev) switch(state) { case IFC_NORMAL: case IFC_RELOAD: + __wireless_device_set_up(wdev); + wdev->config_state = IFC_NORMAL; - if (wdev->autostart) - __wireless_device_set_up(wdev); break; case IFC_REMOVE: wireless_device_free(wdev); @@ -388,7 +405,7 @@ wireless_device_retry_setup(struct wireless_device *wdev) return; if (--wdev->retry < 0) - wdev->autostart = false; + wdev->retry_setup_failed = true; __wireless_device_set_down(wdev); } @@ -413,6 +430,7 @@ wireless_device_script_task_cb(struct netifd_process *proc, int ret) void wireless_device_set_down(struct wireless_device *wdev) { + wdev->retry_setup_failed = false; wdev->autostart = false; __wireless_device_set_down(wdev); } @@ -456,6 +474,7 @@ wdev_change_config(struct wireless_device *wdev, struct wireless_device *wd_new) free(wdev->config); wdev->config = blob_memdup(new_config); wdev->disabled = disabled; + wdev->retry_setup_failed = false; wdev_set_config_state(wdev, IFC_RELOAD); } @@ -548,6 +567,14 @@ wireless_interface_init_config(struct wireless_interface *vif) if ((cur = tb[VIF_ATTR_NETWORK])) vif->network = cur; + + cur = tb[VIF_ATTR_ISOLATE]; + if (cur) + vif->isolate = blobmsg_get_bool(cur); + + cur = tb[VIF_ATTR_MODE]; + if (cur) + vif->ap_mode = !strcmp(blobmsg_get_string(cur), "ap"); } static void @@ -572,8 +599,11 @@ vif_update(struct vlist_tree *tree, struct vlist_node *node_new, } D(WIRELESS, "Update wireless interface %s on device %s\n", vif_new->name, wdev->name); + wireless_interface_handle_link(vif_old, false); free(vif_old->config); vif_old->config = blob_memdup(vif_new->config); + vif_old->isolate = vif_new->isolate; + vif_old->ap_mode = vif_new->ap_mode; wireless_interface_init_config(vif_old); free(vif_new); } else if (vif_new) { @@ -583,6 +613,7 @@ vif_update(struct vlist_tree *tree, struct vlist_node *node_new, wireless_interface_init_config(vif_new); } else if (vif_old) { D(WIRELESS, "Delete wireless interface %s on device %s\n", vif_old->name, wdev->name); + wireless_interface_handle_link(vif_old, false); free((void *) vif_old->section); free(vif_old->config); free(vif_old); @@ -659,8 +690,8 @@ wireless_device_create(struct wireless_driver *drv, const char *name, struct blo wdev->config_state = IFC_NORMAL; wdev->name = strcpy(name_buf, name); wdev->config = data; - wdev->config_autostart = true; - wdev->autostart = wdev->config_autostart; + wdev->retry_setup_failed = false; + wdev->autostart = true; INIT_LIST_HEAD(&wdev->script_proc); vlist_init(&wdev->interfaces, avl_strcmp, vif_update); wdev->interfaces.keep_old = true; @@ -700,6 +731,8 @@ void wireless_interface_create(struct wireless_device *wdev, struct blob_attr *d vif->wdev = wdev; vif->config = data; vif->section = section; + vif->isolate = false; + vlist_add(&wdev->interfaces, &vif->node, vif->name); } @@ -728,6 +761,7 @@ wireless_device_status(struct wireless_device *wdev, struct blob_buf *b) blobmsg_add_u8(b, "pending", wdev->state == IFS_SETUP || wdev->state == IFS_TEARDOWN); blobmsg_add_u8(b, "autostart", wdev->autostart); blobmsg_add_u8(b, "disabled", wdev->disabled); + blobmsg_add_u8(b, "retry_setup_failed", wdev->retry_setup_failed); put_container(b, wdev->config, "config"); i = blobmsg_open_array(b, "interfaces"); @@ -967,6 +1001,5 @@ wireless_start_pending(void) struct wireless_device *wdev; vlist_for_each_element(&wireless_devices, wdev, node) - if (wdev->autostart) - __wireless_device_set_up(wdev); + __wireless_device_set_up(wdev); }