]> Pileus Git - ~andy/linux/blob - net/bridge/br_vlan.c
9ea358fbbf789870a2b85d0fee991b5b502887a6
[~andy/linux] / net / bridge / br_vlan.c
1 #include <linux/kernel.h>
2 #include <linux/netdevice.h>
3 #include <linux/rtnetlink.h>
4 #include <linux/slab.h>
5
6 #include "br_private.h"
7
8 static void __vlan_add_pvid(struct net_port_vlans *v, u16 vid)
9 {
10         if (v->pvid == vid)
11                 return;
12
13         smp_wmb();
14         v->pvid = vid;
15 }
16
17 static void __vlan_delete_pvid(struct net_port_vlans *v, u16 vid)
18 {
19         if (v->pvid != vid)
20                 return;
21
22         smp_wmb();
23         v->pvid = 0;
24 }
25
26 static int __vlan_add(struct net_port_vlans *v, u16 vid, u16 flags)
27 {
28         struct net_bridge_port *p = NULL;
29         struct net_bridge *br;
30         struct net_device *dev;
31         int err;
32
33         if (test_bit(vid, v->vlan_bitmap)) {
34                 if (flags & BRIDGE_VLAN_INFO_PVID)
35                         __vlan_add_pvid(v, vid);
36                 return 0;
37         }
38
39         if (vid) {
40                 if (v->port_idx) {
41                         p = v->parent.port;
42                         br = p->br;
43                         dev = p->dev;
44                 } else {
45                         br = v->parent.br;
46                         dev = br->dev;
47                 }
48
49                 if (p && (dev->features & NETIF_F_HW_VLAN_FILTER)) {
50                         /* Add VLAN to the device filter if it is supported.
51                          * Stricly speaking, this is not necessary now, since
52                          * devices are made promiscuous by the bridge, but if
53                          * that ever changes this code will allow tagged
54                          * traffic to enter the bridge.
55                          */
56                         err = dev->netdev_ops->ndo_vlan_rx_add_vid(dev, vid);
57                         if (err)
58                                 return err;
59                 }
60
61                 err = br_fdb_insert(br, p, dev->dev_addr, vid);
62                 if (err) {
63                         br_err(br, "failed insert local address into bridge "
64                                "forwarding table\n");
65                         goto out_filt;
66                 }
67
68         }
69
70         set_bit(vid, v->vlan_bitmap);
71         v->num_vlans++;
72         if (flags & BRIDGE_VLAN_INFO_PVID)
73                 __vlan_add_pvid(v, vid);
74
75         return 0;
76
77 out_filt:
78         if (p && (dev->features & NETIF_F_HW_VLAN_FILTER))
79                 dev->netdev_ops->ndo_vlan_rx_kill_vid(dev, vid);
80         return err;
81 }
82
83 static int __vlan_del(struct net_port_vlans *v, u16 vid)
84 {
85         if (!test_bit(vid, v->vlan_bitmap))
86                 return -EINVAL;
87
88         __vlan_delete_pvid(v, vid);
89
90         if (v->port_idx && vid) {
91                 struct net_device *dev = v->parent.port->dev;
92
93                 if (dev->features & NETIF_F_HW_VLAN_FILTER)
94                         dev->netdev_ops->ndo_vlan_rx_kill_vid(dev, vid);
95         }
96
97         clear_bit(vid, v->vlan_bitmap);
98         v->num_vlans--;
99         if (bitmap_empty(v->vlan_bitmap, BR_VLAN_BITMAP_LEN)) {
100                 if (v->port_idx)
101                         rcu_assign_pointer(v->parent.port->vlan_info, NULL);
102                 else
103                         rcu_assign_pointer(v->parent.br->vlan_info, NULL);
104                 kfree_rcu(v, rcu);
105         }
106         return 0;
107 }
108
109 static void __vlan_flush(struct net_port_vlans *v)
110 {
111         smp_wmb();
112         v->pvid = 0;
113         bitmap_zero(v->vlan_bitmap, BR_VLAN_BITMAP_LEN);
114         if (v->port_idx)
115                 rcu_assign_pointer(v->parent.port->vlan_info, NULL);
116         else
117                 rcu_assign_pointer(v->parent.br->vlan_info, NULL);
118         kfree_rcu(v, rcu);
119 }
120
121 /* Strip the tag from the packet.  Will return skb with tci set 0.  */
122 static struct sk_buff *br_vlan_untag(struct sk_buff *skb)
123 {
124         if (skb->protocol != htons(ETH_P_8021Q)) {
125                 skb->vlan_tci = 0;
126                 return skb;
127         }
128
129         skb->vlan_tci = 0;
130         skb = vlan_untag(skb);
131         if (skb)
132                 skb->vlan_tci = 0;
133
134         return skb;
135 }
136
137 struct sk_buff *br_handle_vlan(struct net_bridge *br,
138                                const struct net_port_vlans *pv,
139                                struct sk_buff *skb)
140 {
141         u16 vid;
142
143         if (!br->vlan_enabled)
144                 goto out;
145
146         /* At this point, we know that the frame was filtered and contains
147          * a valid vlan id.  If the vlan id matches the pvid of current port
148          * send untagged; otherwise, send taged.
149          */
150         br_vlan_get_tag(skb, &vid);
151         if (vid == br_get_pvid(pv))
152                 skb = br_vlan_untag(skb);
153         else {
154                 /* Egress policy says "send tagged".  If output device
155                  * is the  bridge, we need to add the VLAN header
156                  * ourselves since we'll be going through the RX path.
157                  * Sending to ports puts the frame on the TX path and
158                  * we let dev_hard_start_xmit() add the header.
159                  */
160                 if (skb->protocol != htons(ETH_P_8021Q) &&
161                     pv->port_idx == 0) {
162                         /* vlan_put_tag expects skb->data to point to
163                          * mac header.
164                          */
165                         skb_push(skb, ETH_HLEN);
166                         skb = __vlan_put_tag(skb, skb->vlan_tci);
167                         if (!skb)
168                                 goto out;
169                         /* put skb->data back to where it was */
170                         skb_pull(skb, ETH_HLEN);
171                         skb->vlan_tci = 0;
172                 }
173         }
174
175 out:
176         return skb;
177 }
178
179 /* Called under RCU */
180 bool br_allowed_ingress(struct net_bridge *br, struct net_port_vlans *v,
181                         struct sk_buff *skb, u16 *vid)
182 {
183         /* If VLAN filtering is disabled on the bridge, all packets are
184          * permitted.
185          */
186         if (!br->vlan_enabled)
187                 return true;
188
189         /* If there are no vlan in the permitted list, all packets are
190          * rejected.
191          */
192         if (!v)
193                 return false;
194
195         if (br_vlan_get_tag(skb, vid)) {
196                 u16 pvid = br_get_pvid(v);
197
198                 /* Frame did not have a tag.  See if pvid is set
199                  * on this port.  That tells us which vlan untagged
200                  * traffic belongs to.
201                  */
202                 if (pvid == VLAN_N_VID)
203                         return false;
204
205                 /* PVID is set on this port.  Any untagged ingress
206                  * frame is considered to belong to this vlan.
207                  */
208                 __vlan_hwaccel_put_tag(skb, pvid);
209                 return true;
210         }
211
212         /* Frame had a valid vlan tag.  See if vlan is allowed */
213         if (test_bit(*vid, v->vlan_bitmap))
214                 return true;
215
216         return false;
217 }
218
219 /* Called under RCU. */
220 bool br_allowed_egress(struct net_bridge *br,
221                        const struct net_port_vlans *v,
222                        const struct sk_buff *skb)
223 {
224         u16 vid;
225
226         if (!br->vlan_enabled)
227                 return true;
228
229         if (!v)
230                 return false;
231
232         br_vlan_get_tag(skb, &vid);
233         if (test_bit(vid, v->vlan_bitmap))
234                 return true;
235
236         return false;
237 }
238
239 /* Must be protected by RTNL */
240 int br_vlan_add(struct net_bridge *br, u16 vid, u16 flags)
241 {
242         struct net_port_vlans *pv = NULL;
243         int err;
244
245         ASSERT_RTNL();
246
247         pv = rtnl_dereference(br->vlan_info);
248         if (pv)
249                 return __vlan_add(pv, vid, flags);
250
251         /* Create port vlan infomration
252          */
253         pv = kzalloc(sizeof(*pv), GFP_KERNEL);
254         if (!pv)
255                 return -ENOMEM;
256
257         pv->parent.br = br;
258         err = __vlan_add(pv, vid, flags);
259         if (err)
260                 goto out;
261
262         rcu_assign_pointer(br->vlan_info, pv);
263         return 0;
264 out:
265         kfree(pv);
266         return err;
267 }
268
269 /* Must be protected by RTNL */
270 int br_vlan_delete(struct net_bridge *br, u16 vid)
271 {
272         struct net_port_vlans *pv;
273
274         ASSERT_RTNL();
275
276         pv = rtnl_dereference(br->vlan_info);
277         if (!pv)
278                 return -EINVAL;
279
280         if (vid) {
281                 /* If the VID !=0 remove fdb for this vid. VID 0 is special
282                  * in that it's the default and is always there in the fdb.
283                  */
284                 spin_lock_bh(&br->hash_lock);
285                 fdb_delete_by_addr(br, br->dev->dev_addr, vid);
286                 spin_unlock_bh(&br->hash_lock);
287         }
288
289         __vlan_del(pv, vid);
290         return 0;
291 }
292
293 void br_vlan_flush(struct net_bridge *br)
294 {
295         struct net_port_vlans *pv;
296
297         ASSERT_RTNL();
298         pv = rtnl_dereference(br->vlan_info);
299         if (!pv)
300                 return;
301
302         __vlan_flush(pv);
303 }
304
305 int br_vlan_filter_toggle(struct net_bridge *br, unsigned long val)
306 {
307         if (!rtnl_trylock())
308                 return restart_syscall();
309
310         if (br->vlan_enabled == val)
311                 goto unlock;
312
313         br->vlan_enabled = val;
314
315 unlock:
316         rtnl_unlock();
317         return 0;
318 }
319
320 /* Must be protected by RTNL */
321 int nbp_vlan_add(struct net_bridge_port *port, u16 vid, u16 flags)
322 {
323         struct net_port_vlans *pv = NULL;
324         int err;
325
326         ASSERT_RTNL();
327
328         pv = rtnl_dereference(port->vlan_info);
329         if (pv)
330                 return __vlan_add(pv, vid, flags);
331
332         /* Create port vlan infomration
333          */
334         pv = kzalloc(sizeof(*pv), GFP_KERNEL);
335         if (!pv) {
336                 err = -ENOMEM;
337                 goto clean_up;
338         }
339
340         pv->port_idx = port->port_no;
341         pv->parent.port = port;
342         err = __vlan_add(pv, vid, flags);
343         if (err)
344                 goto clean_up;
345
346         rcu_assign_pointer(port->vlan_info, pv);
347         return 0;
348
349 clean_up:
350         kfree(pv);
351         return err;
352 }
353
354 /* Must be protected by RTNL */
355 int nbp_vlan_delete(struct net_bridge_port *port, u16 vid)
356 {
357         struct net_port_vlans *pv;
358
359         ASSERT_RTNL();
360
361         pv = rtnl_dereference(port->vlan_info);
362         if (!pv)
363                 return -EINVAL;
364
365         if (vid) {
366                 /* If the VID !=0 remove fdb for this vid. VID 0 is special
367                  * in that it's the default and is always there in the fdb.
368                  */
369                 spin_lock_bh(&port->br->hash_lock);
370                 fdb_delete_by_addr(port->br, port->dev->dev_addr, vid);
371                 spin_unlock_bh(&port->br->hash_lock);
372         }
373
374         return __vlan_del(pv, vid);
375 }
376
377 void nbp_vlan_flush(struct net_bridge_port *port)
378 {
379         struct net_port_vlans *pv;
380
381         ASSERT_RTNL();
382
383         pv = rtnl_dereference(port->vlan_info);
384         if (!pv)
385                 return;
386
387         __vlan_flush(pv);
388 }
389
390 bool nbp_vlan_find(struct net_bridge_port *port, u16 vid)
391 {
392         struct net_port_vlans *pv;
393         bool found = false;
394
395         rcu_read_lock();
396         pv = rcu_dereference(port->vlan_info);
397
398         if (!pv)
399                 goto out;
400
401         if (test_bit(vid, pv->vlan_bitmap))
402                 found = true;
403
404 out:
405         rcu_read_unlock();
406         return found;
407 }