[<prev] [next>] [<thread-prev] [day] [month] [year] [list]
Message-ID: <1326842262.2606.31.camel@edumazet-laptop>
Date: Wed, 18 Jan 2012 00:17:42 +0100
From: Eric Dumazet <eric.dumazet@...il.com>
To: Stefan Gula <steweg@...t.sk>
Cc: Alexey Kuznetsov <kuznet@....inr.ac.ru>,
"David S. Miller" <davem@...emloft.net>,
James Morris <jmorris@...ei.org>,
Hideaki YOSHIFUJI <yoshfuji@...ux-ipv6.org>,
Patrick McHardy <kaber@...sh.net>, netdev@...r.kernel.org,
linux-kernel@...r.kernel.org
Subject: Re: [patch v3, kernel version 3.2.1] net/ipv4/ip_gre: Ethernet
multipoint GRE over IP
Le mardi 17 janvier 2012 à 23:20 +0100, Stefan Gula a écrit :
> From: Stefan Gula <steweg@...il.com>
>
> This patch is an extension for current Ethernet over GRE
> implementation, which allows user to create virtual bridge (multipoint
> VPN) and forward traffic based on Ethernet MAC address information in
> it. It simulates the Bridge behavior learning mechanism, but instead
> of learning port ID from which given MAC address comes, it learns IP
> address of peer which encapsulated given packet. Multicast, Broadcast
> and unknown-multicast traffic is send over network as multicast
> encapsulated GRE packet, so one Ethernet multipoint GRE tunnel can be
> represented as one single virtual switch on logical level and be also
> represented as one multicast IPv4 address on network level.
>
> Signed-off-by: Stefan Gula <steweg@...il.com>
>
> ---
>
> code was merged with Eric Dumazet proposal (all except the reordering
> of orig_source as that needed to be previous value), tested and fixed
> with additional lines in ipgre_tap_netdev_ops struct
>
Sorry, this is buggy (again...)
Its even clearly commented in the code :
/* Warning: All skb pointers will be invalidated! */
>
> if (!pskb_may_pull(skb, 16))
> goto drop_nolock;
> @@ -659,10 +836,38 @@ static int ipgre_rcv(struct sk_buff *skb
> tunnel->dev->stats.rx_errors++;
> goto drop;
> }
At this point, iph can point to freed memory and its dereference can
crash, since pskb_may_pull() can reallocate skb head.
> -
> +#ifdef CONFIG_NET_IPGRE_BRIDGE
> + orig_source = iph->saddr;
> +#endif
Without any doubt, you know here there is a bug.
> iph = ip_hdr(skb);
> skb->protocol = eth_type_trans(skb, tunnel->dev);
> skb_postpull_rcsum(skb, eth_hdr(skb), ETH_HLEN);
So if you need orig_source as the previous iph->saddr value, you must
fetch it _before_ the pskb_may_pull()
/* Warning: All skb pointers will be invalidated! */
if (tunnel->dev->type == ARPHRD_ETHER) {
#ifdef CONFIG_NET_IPGRE_BRIDGE
orig_source = iph->saddr; /* must be done before pskb_may_pull() */
#endif
if (!pskb_may_pull(skb, ETH_HLEN)) {
tunnel->dev->stats.rx_length_errors++;
tunnel->dev->stats.rx_errors++;
goto drop;
}
iph = ip_hdr(skb);
...
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@...r.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Powered by blists - more mailing lists