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