- struct ifreq ifr;
- strncpy(ifr.ifr_name, dev->ifname, sizeof(ifr.ifr_name));
- if (!ioctl(sock_ioctl, SIOCGIFINDEX, &ifr))
- return ifr.ifr_ifindex;
- else
- return 0;
+ char buf[256];
+ char *bridge;
+
+ dev->ifindex = system_if_resolve(dev);
+ if (!dev->ifindex)
+ return;
+
+ system_if_flags(dev->ifname, 0, IFF_UP);
+
+ if (system_is_bridge(dev->ifname, buf, sizeof(buf))) {
+ D(SYSTEM, "Delete existing bridge named '%s'\n", dev->ifname);
+ system_bridge_delbr(dev);
+ return;
+ }
+
+ bridge = system_get_bridge(dev->ifname, buf, sizeof(buf));
+ if (bridge) {
+ D(SYSTEM, "Remove device '%s' from bridge '%s'\n", dev->ifname, bridge);
+ system_bridge_if(bridge, dev, SIOCBRDELIF);
+ }
+}
+
+int system_bridge_addbr(struct device *bridge)
+{
+ system_if_clear_state(bridge);
+ return ioctl(sock_ioctl, SIOCBRADDBR, bridge->ifname);
+}
+
+static int system_vlan(struct device *dev, int id)
+{
+ struct vlan_ioctl_args ifr = {
+ .cmd = (id == 0) ? DEL_VLAN_CMD : ADD_VLAN_CMD,
+ .u = {.VID = id},
+ };
+ strncpy(ifr.device1, dev->ifname, sizeof(ifr.device1));
+ return ioctl(sock_ioctl, SIOCSIFVLAN, &ifr);
+}
+
+int system_vlan_add(struct device *dev, int id)
+{
+ system_if_clear_state(dev);
+ return system_vlan(dev, id);
+}
+
+int system_vlan_del(struct device *dev)
+{
+ return system_vlan(dev, 0);