summaryrefslogtreecommitdiffstats
path: root/net/bridge/br_input.c
diff options
context:
space:
mode:
authorHerbert Xu <herbert@gondor.apana.org.au>2007-10-14 09:39:01 +0200
committerDavid S. Miller <davem@sunset.davemloft.net>2007-10-15 21:26:27 +0200
commit7b995651e373d6424f81db23f2ec503306dfd7f0 (patch)
tree6d41d29bce9e46d33f2a21d4fd2fa279e6e9730d /net/bridge/br_input.c
parent[NET]: Avoid unnecessary cloning for ingress filtering (diff)
downloadlinux-7b995651e373d6424f81db23f2ec503306dfd7f0.tar.xz
linux-7b995651e373d6424f81db23f2ec503306dfd7f0.zip
[BRIDGE]: Unshare skb upon entry
Due to the special location of the bridging hook, it should never see a shared packet anyway (certainly not with any in-kernel code). So it makes sense to unshare the skb there if necessary as that will greatly simplify the code below it (in particular, netfilter). Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/bridge/br_input.c')
-rw-r--r--net/bridge/br_input.c4
1 files changed, 4 insertions, 0 deletions
diff --git a/net/bridge/br_input.c b/net/bridge/br_input.c
index 3a8a015c92e0..f8e0a2fa796e 100644
--- a/net/bridge/br_input.c
+++ b/net/bridge/br_input.c
@@ -126,6 +126,10 @@ struct sk_buff *br_handle_frame(struct net_bridge_port *p, struct sk_buff *skb)
if (!is_valid_ether_addr(eth_hdr(skb)->h_source))
goto drop;
+ skb = skb_share_check(skb, GFP_ATOMIC);
+ if (!skb)
+ return NULL;
+
if (unlikely(is_link_local(dest))) {
/* Pause frames shouldn't be passed up by driver anyway */
if (skb->protocol == htons(ETH_P_PAUSE))