aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNikolay Aleksandrov <nikolay@cumulusnetworks.com>2015-09-30 14:16:52 -0400
committerDavid S. Miller <davem@davemloft.net>2015-10-01 21:24:04 -0400
commit468e7944589c7f096bb4ea14db17980aa6c2766c (patch)
tree473b882e2365c413e85cef4adfef8ee41a4a819f
parent8af78b6487856d8a896ba15e9255b8e5fa91eb5f (diff)
bridge: vlan: fix possible null vlgrp deref while registering new port
While a new port is being initialized the rx_handler gets set, but the vlans get initialized later in br_add_if() and in that window if we receive a frame with a link-local address we can try to dereference p->vlgrp in: br_handle_frame() -> br_handle_local_finish() -> br_should_learn() Fix this by checking vlgrp before using it. Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--net/bridge/br_vlan.c4
1 files changed, 3 insertions, 1 deletions
diff --git a/net/bridge/br_vlan.c b/net/bridge/br_vlan.c
index 283d012c3d89..678d5c41b551 100644
--- a/net/bridge/br_vlan.c
+++ b/net/bridge/br_vlan.c
@@ -476,13 +476,15 @@ bool br_allowed_egress(struct net_bridge_vlan_group *vg,
476/* Called under RCU */ 476/* Called under RCU */
477bool br_should_learn(struct net_bridge_port *p, struct sk_buff *skb, u16 *vid) 477bool br_should_learn(struct net_bridge_port *p, struct sk_buff *skb, u16 *vid)
478{ 478{
479 struct net_bridge_vlan_group *vg;
479 struct net_bridge *br = p->br; 480 struct net_bridge *br = p->br;
480 481
481 /* If filtering was disabled at input, let it pass. */ 482 /* If filtering was disabled at input, let it pass. */
482 if (!br->vlan_enabled) 483 if (!br->vlan_enabled)
483 return true; 484 return true;
484 485
485 if (!p->vlgrp->num_vlans) 486 vg = p->vlgrp;
487 if (!vg || !vg->num_vlans)
486 return false; 488 return false;
487 489
488 if (!br_vlan_get_tag(skb, vid) && skb->vlan_proto != br->vlan_proto) 490 if (!br_vlan_get_tag(skb, vid) && skb->vlan_proto != br->vlan_proto)