aboutsummaryrefslogtreecommitdiff
path: root/net/bridge/br_private.h
diff options
context:
space:
mode:
authorVlad Yasevich <vyasevic@redhat.com>2013-02-13 12:00:14 +0000
committerDavid S. Miller <davem@davemloft.net>2013-02-13 19:42:15 -0500
commit7885198861fc9a3dfdc6bb90dc0ba12689d6cd57 (patch)
treea75ed0f9b3fe72be08dcb13216c87f4f8e37bb75 /net/bridge/br_private.h
parent6cbdceeb1cb12c7d620161925a8c3e81daadb2e4 (diff)
bridge: Implement vlan ingress/egress policy with PVID.
At ingress, any untagged traffic is assigned to the PVID. Any tagged traffic is filtered according to membership bitmap. At egress, if the vlan matches the PVID, the frame is sent untagged. Otherwise the frame is sent tagged. Signed-off-by: Vlad Yasevich <vyasevic@redhat.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/bridge/br_private.h')
-rw-r--r--net/bridge/br_private.h34
1 files changed, 31 insertions, 3 deletions
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index ce2235255c2..ea8e7efd913 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -67,6 +67,7 @@ struct br_ip
struct net_port_vlans {
u16 port_idx;
+ u16 pvid;
union {
struct net_bridge_port *port;
struct net_bridge *br;
@@ -554,10 +555,13 @@ static inline void br_mdb_uninit(void)
/* br_vlan.c */
#ifdef CONFIG_BRIDGE_VLAN_FILTERING
extern bool br_allowed_ingress(struct net_bridge *br, struct net_port_vlans *v,
- struct sk_buff *skb);
+ struct sk_buff *skb, u16 *vid);
extern bool br_allowed_egress(struct net_bridge *br,
const struct net_port_vlans *v,
const struct sk_buff *skb);
+extern struct sk_buff *br_handle_vlan(struct net_bridge *br,
+ const struct net_port_vlans *v,
+ struct sk_buff *skb);
extern int br_vlan_add(struct net_bridge *br, u16 vid);
extern int br_vlan_delete(struct net_bridge *br, u16 vid);
extern void br_vlan_flush(struct net_bridge *br);
@@ -594,10 +598,23 @@ static inline int br_vlan_get_tag(const struct sk_buff *skb, u16 *vid)
return err;
}
+
+static inline u16 br_get_pvid(const struct net_port_vlans *v)
+{
+ /* Return just the VID if it is set, or VLAN_N_VID (invalid vid) if
+ * vid wasn't set
+ */
+ smp_rmb();
+ return (v->pvid & VLAN_TAG_PRESENT) ?
+ (v->pvid & ~VLAN_TAG_PRESENT) :
+ VLAN_N_VID;
+}
+
#else
static inline bool br_allowed_ingress(struct net_bridge *br,
struct net_port_vlans *v,
- struct sk_buff *skb)
+ struct sk_buff *skb,
+ u16 *vid)
{
return true;
}
@@ -609,6 +626,13 @@ static inline bool br_allowed_egress(struct net_bridge *br,
return true;
}
+static inline struct sk_buff *br_handle_vlan(struct net_bridge *br,
+ const struct net_port_vlans *v,
+ struct sk_buff *skb)
+{
+ return skb;
+}
+
static inline int br_vlan_add(struct net_bridge *br, u16 vid)
{
return -EOPNOTSUPP;
@@ -648,10 +672,14 @@ static inline struct net_port_vlans *nbp_get_vlan_info(
return NULL;
}
-static inline u16 br_vlan_get_tag(const struct sk_buff *skb)
+static inline u16 br_vlan_get_tag(const struct sk_buff *skb, u16 *tag)
{
return 0;
}
+static inline u16 br_get_pvid(const struct net_port_vlans *v)
+{
+ return VLAN_N_VID; /* Returns invalid vid */
+}
#endif
/* br_netfilter.c */