summaryrefslogtreecommitdiffstats
path: root/net/ieee802154/6lowpan.c
diff options
context:
space:
mode:
authorAlan Ott <alan@signal11.us>2012-09-01 05:57:06 +0000
committerDavid S. Miller <davem@tempietto.lan>2012-09-01 22:48:01 -0400
commita437d2744b0a4e5f405f6b9be284eb9e0a2d7741 (patch)
tree9d83ef2dcca22e73cb0638ccf6512a884f3878b5 /net/ieee802154/6lowpan.c
parent1bed966cc3bd4042110129f0fc51aeeb59c5b200 (diff)
6lowpan: Make a copy of skb's delivered to 6lowpan
Since lowpan_process_data() modifies the skb (by calling skb_pull()), we need our own copy so that it doesn't affect the data received by other protcols (in this case, af_ieee802154). Signed-off-by: Alan Ott <alan@signal11.us> Signed-off-by: David S. Miller <davem@tempietto.lan>
Diffstat (limited to 'net/ieee802154/6lowpan.c')
-rw-r--r--net/ieee802154/6lowpan.c9
1 files changed, 8 insertions, 1 deletions
diff --git a/net/ieee802154/6lowpan.c b/net/ieee802154/6lowpan.c
index 6a095225148..b28ec790c7c 100644
--- a/net/ieee802154/6lowpan.c
+++ b/net/ieee802154/6lowpan.c
@@ -1133,6 +1133,8 @@ static int lowpan_validate(struct nlattr *tb[], struct nlattr *data[])
static int lowpan_rcv(struct sk_buff *skb, struct net_device *dev,
struct packet_type *pt, struct net_device *orig_dev)
{
+ struct sk_buff *local_skb;
+
if (!netif_running(dev))
goto drop;
@@ -1144,7 +1146,12 @@ static int lowpan_rcv(struct sk_buff *skb, struct net_device *dev,
case LOWPAN_DISPATCH_IPHC: /* ipv6 datagram */
case LOWPAN_DISPATCH_FRAG1: /* first fragment header */
case LOWPAN_DISPATCH_FRAGN: /* next fragments headers */
- lowpan_process_data(skb);
+ local_skb = skb_clone(skb, GFP_ATOMIC);
+ if (!local_skb)
+ goto drop;
+ lowpan_process_data(local_skb);
+
+ kfree_skb(skb);
break;
default:
break;