Netdev List
 help / color / mirror / Atom feed
* Re: [PATCH net-next] tg3: use netdev_alloc_frag() API
From: Eric Dumazet @ 2012-05-19  8:17 UTC (permalink / raw)
  To: David Miller; +Cc: netdev, mcarlson, mchan
In-Reply-To: <20120519.040101.508727755785767140.davem@davemloft.net>

On Sat, 2012-05-19 at 04:01 -0400, David Miller wrote:
> From: Eric Dumazet <eric.dumazet@gmail.com>
> Date: Sat, 19 May 2012 09:31:41 +0200
> 
> > Indeed, there is an extra space at the end of one line in my tree... ???
> > 
> > atomic_add((PAGE_SIZE / TG3_FRAGSIZE) - 1, &page->_count); <HERE>
> 
> I silently fix trailing whitespace errors in your patches.

OK, good to know ;)

^ permalink raw reply

* Re: [PATCH net-next] ipv6: disable GSO on sockets hitting dst_allfrag
From: David Miller @ 2012-05-19  8:03 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev, tore
In-Reply-To: <1337413904.7029.93.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 09:51:44 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> If the allfrag feature has been set on a host route (due to an ICMPv6
> Packet Too Big received indicating a MTU of less than 1280), we hit a
> very slow behavior in TCP stack, because all big packets are dropped and
> only a retransmit timer is able to push one MSS frame every 200 ms.
> 
> One way to handle this is to disable GSO on the socket the first time a
> super packet is dropped. Adding a specific dst_allfrag() in the fast
> path is probably overkill since the dst_allfrag() case almost never
> happen.
> 
> Result on netperf TCP_STREAM, one flow :
> 
> Before : 60 kbit/sec
> After : 1.6 Gbit/sec
> 
> Reported-by: Tore Anderson <tore@fud.no>
> Signed-off-by: Eric Dumazet <edumazet@google.com>
> Tested-by: Tore Anderson <tore@fud.no>

Applied.

^ permalink raw reply

* Re: [PATCH v2 net-next] tg3: use netdev_alloc_frag() API
From: David Miller @ 2012-05-19  8:03 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev, mcarlson, mchan
In-Reply-To: <1337412819.7029.81.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 09:33:39 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> Update our reference driver to use netdev_alloc_frag() API instead of
> the temporary custom allocator I introduced in commit 8d4057a938
> (tg3: provide frags as skb head)
> 
> This removes the memory leak we had, since we could leak one page at
> device dismantle.
> 
> Signed-off-by: Eric Dumazet <edumazet@google.com>

Applied.

^ permalink raw reply

* Re: [PATCH net-next] tg3: use netdev_alloc_frag() API
From: David Miller @ 2012-05-19  8:01 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev, mcarlson, mchan
In-Reply-To: <1337412701.7029.79.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 09:31:41 +0200

> Indeed, there is an extra space at the end of one line in my tree... ???
> 
> atomic_add((PAGE_SIZE / TG3_FRAGSIZE) - 1, &page->_count); <HERE>

I silently fix trailing whitespace errors in your patches.

^ permalink raw reply

* [PATCH net-next] ipv6: disable GSO on sockets hitting dst_allfrag
From: Eric Dumazet @ 2012-05-19  7:51 UTC (permalink / raw)
  To: David Miller; +Cc: netdev, Tore Anderson

From: Eric Dumazet <edumazet@google.com>

If the allfrag feature has been set on a host route (due to an ICMPv6
Packet Too Big received indicating a MTU of less than 1280), we hit a
very slow behavior in TCP stack, because all big packets are dropped and
only a retransmit timer is able to push one MSS frame every 200 ms.

One way to handle this is to disable GSO on the socket the first time a
super packet is dropped. Adding a specific dst_allfrag() in the fast
path is probably overkill since the dst_allfrag() case almost never
happen.

Result on netperf TCP_STREAM, one flow :

Before : 60 kbit/sec
After : 1.6 Gbit/sec

Reported-by: Tore Anderson <tore@fud.no>
Signed-off-by: Eric Dumazet <edumazet@google.com>
Tested-by: Tore Anderson <tore@fud.no>
---
Sorry for the delay, thanks Tore for the gentle reminders ;)

( http://thread.gmane.org/gmane.linux.network/217998/focus=218080 )

 net/ipv6/ip6_output.c |    5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/net/ipv6/ip6_output.c b/net/ipv6/ip6_output.c
index 3dc633f..d99fdc6 100644
--- a/net/ipv6/ip6_output.c
+++ b/net/ipv6/ip6_output.c
@@ -643,7 +643,10 @@ int ip6_fragment(struct sk_buff *skb, int (*output)(struct sk_buff *))
 	/* We must not fragment if the socket is set to force MTU discovery
 	 * or if the skb it not generated by a local socket.
 	 */
-	if (!skb->local_df && skb->len > mtu) {
+	if (unlikely(!skb->local_df && skb->len > mtu)) {
+		if (skb->sk && dst_allfrag(skb_dst(skb)))
+			sk_nocaps_add(skb->sk, NETIF_F_GSO_MASK);
+
 		skb->dev = skb_dst(skb)->dev;
 		icmpv6_send(skb, ICMPV6_PKT_TOOBIG, 0, mtu);
 		IP6_INC_STATS(net, ip6_dst_idev(skb_dst(skb)),

^ permalink raw reply related

* [PATCH v2 net-next] tg3: use netdev_alloc_frag() API
From: Eric Dumazet @ 2012-05-19  7:33 UTC (permalink / raw)
  To: David Miller; +Cc: netdev, Matt Carlson, Michael Chan
In-Reply-To: <1337411749.7029.77.camel@edumazet-glaptop>

From: Eric Dumazet <edumazet@google.com>

Update our reference driver to use netdev_alloc_frag() API instead of
the temporary custom allocator I introduced in commit 8d4057a938
(tg3: provide frags as skb head)

This removes the memory leak we had, since we could leak one page at
device dismantle.

Signed-off-by: Eric Dumazet <edumazet@google.com>
Cc: Matt Carlson <mcarlson@broadcom.com>
Cc: Michael Chan <mchan@broadcom.com>
---
 drivers/net/ethernet/broadcom/tg3.c |   38 +++-----------------------
 drivers/net/ethernet/broadcom/tg3.h |    2 -
 2 files changed, 5 insertions(+), 35 deletions(-)

diff --git a/drivers/net/ethernet/broadcom/tg3.c b/drivers/net/ethernet/broadcom/tg3.c
index 39b92f5..d55df32 100644
--- a/drivers/net/ethernet/broadcom/tg3.c
+++ b/drivers/net/ethernet/broadcom/tg3.c
@@ -195,15 +195,6 @@ static inline void _tg3_flag_clear(enum TG3_FLAGS flag, unsigned long *bits)
 #define TG3_RX_OFFSET(tp)	(NET_SKB_PAD)
 #endif
 
-/* This driver uses the new build_skb() API providing a frag as skb->head
- * This strategy permits better GRO aggregation, better TCP coalescing, and
- * better splice() implementation (avoids a copy from head to a page), at
- * minimal memory cost.
- * In this 2048 bytes block, we have enough room to store the MTU=1500 frame
- * and the struct skb_shared_info.
- */
-#define TG3_FRAGSIZE 2048
-
 /* minimum number of free TX descriptors required to wake up TX process */
 #define TG3_TX_WAKEUP_THRESH(tnapi)		((tnapi)->tx_pending / 4)
 #define TG3_TX_BD_DMA_MAX_2K		2048
@@ -5631,25 +5622,6 @@ static void tg3_tx(struct tg3_napi *tnapi)
 	}
 }
 
-static void *tg3_frag_alloc(struct tg3_rx_prodring_set *tpr)
-{
-	void *data;
-
-	if (tpr->rx_page_size < TG3_FRAGSIZE) {
-		struct page *page = alloc_page(GFP_ATOMIC);
-
-		if (!page)
-			return NULL;
-		atomic_add((PAGE_SIZE / TG3_FRAGSIZE) - 1, &page->_count);
-		tpr->rx_page_addr = page_address(page);
-		tpr->rx_page_size = PAGE_SIZE;
-	}
-	data = tpr->rx_page_addr;
-	tpr->rx_page_addr += TG3_FRAGSIZE;
-	tpr->rx_page_size -= TG3_FRAGSIZE;
-	return data;
-}
-
 static void tg3_frag_free(bool is_frag, void *data)
 {
 	if (is_frag)
@@ -5668,7 +5640,7 @@ static void tg3_rx_data_free(struct tg3 *tp, struct ring_info *ri, u32 map_sz)
 
 	pci_unmap_single(tp->pdev, dma_unmap_addr(ri, mapping),
 			 map_sz, PCI_DMA_FROMDEVICE);
-	tg3_frag_free(skb_size <= TG3_FRAGSIZE, ri->data);
+	tg3_frag_free(skb_size <= PAGE_SIZE, ri->data);
 	ri->data = NULL;
 }
 
@@ -5721,9 +5693,9 @@ static int tg3_alloc_rx_data(struct tg3 *tp, struct tg3_rx_prodring_set *tpr,
 	 */
 	skb_size = SKB_DATA_ALIGN(data_size + TG3_RX_OFFSET(tp)) +
 		   SKB_DATA_ALIGN(sizeof(struct skb_shared_info));
-	if (skb_size <= TG3_FRAGSIZE) {
-		data = tg3_frag_alloc(tpr);
-		*frag_size = TG3_FRAGSIZE;
+	if (skb_size <= PAGE_SIZE) {
+		data = netdev_alloc_frag(skb_size);
+		*frag_size = skb_size;
 	} else {
 		data = kmalloc(skb_size, GFP_ATOMIC);
 		*frag_size = 0;
@@ -5736,7 +5708,7 @@ static int tg3_alloc_rx_data(struct tg3 *tp, struct tg3_rx_prodring_set *tpr,
 				 data_size,
 				 PCI_DMA_FROMDEVICE);
 	if (unlikely(pci_dma_mapping_error(tp->pdev, mapping))) {
-		tg3_frag_free(skb_size <= TG3_FRAGSIZE, data);
+		tg3_frag_free(skb_size <= PAGE_SIZE, data);
 		return -EIO;
 	}
 
diff --git a/drivers/net/ethernet/broadcom/tg3.h b/drivers/net/ethernet/broadcom/tg3.h
index 7c85545..93865f8 100644
--- a/drivers/net/ethernet/broadcom/tg3.h
+++ b/drivers/net/ethernet/broadcom/tg3.h
@@ -2815,8 +2815,6 @@ struct tg3_rx_prodring_set {
 	struct ring_info		*rx_jmb_buffers;
 	dma_addr_t			rx_std_mapping;
 	dma_addr_t			rx_jmb_mapping;
-	void				*rx_page_addr;
-	unsigned int			rx_page_size;
 };
 
 #define TG3_IRQ_MAX_VECS_RSS		5

^ permalink raw reply related

* Re: [PATCH net-next] tg3: use netdev_alloc_frag() API
From: Eric Dumazet @ 2012-05-19  7:31 UTC (permalink / raw)
  To: David Miller; +Cc: netdev, mcarlson, mchan
In-Reply-To: <20120519.031914.1744866102736414778.davem@davemloft.net>

On Sat, 2012-05-19 at 03:19 -0400, David Miller wrote:
> From: Eric Dumazet <eric.dumazet@gmail.com>
> Date: Sat, 19 May 2012 09:15:49 +0200
> 
> > From: Eric Dumazet <edumazet@google.com>
> > 
> > Update our reference driver to use netdev_alloc_frag() API instead of
> > the temporary custom allocator I introduced in commit 8d4057a938
> > (tg3: provide frags as skb head)
> > 
> > This removes the memory leak we had, since we could leak one page at
> > device dismantle.
> > 
> > Signed-off-by: Eric Dumazet <edumazet@google.com>
> 
> Hmmm, doesn't apply cleanly to net-next for some reason:
> 
> [davem@drr net-next]$ git am --signoff net-next-tg3-use-netdev_alloc_frag-API.patch 
> Applying: tg3: use netdev_alloc_frag() API
> error: patch failed: drivers/net/ethernet/broadcom/tg3.c:5631
> error: drivers/net/ethernet/broadcom/tg3.c: patch does not apply
> Patch failed at 0001 tg3: use netdev_alloc_frag() API
> When you have resolved this problem run "git am --resolved".
> If you would prefer to skip this patch, instead run "git am --skip".
> To restore the original branch and stop patching run "git am --abort".

Indeed, there is an extra space at the end of one line in my tree... ???

atomic_add((PAGE_SIZE / TG3_FRAGSIZE) - 1, &page->_count); <HERE>

I submit a v2 immediately.

Sorry

^ permalink raw reply

* Re: [PATCH net-next] tg3: use netdev_alloc_frag() API
From: David Miller @ 2012-05-19  7:19 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev, mcarlson, mchan
In-Reply-To: <1337411749.7029.77.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 09:15:49 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> Update our reference driver to use netdev_alloc_frag() API instead of
> the temporary custom allocator I introduced in commit 8d4057a938
> (tg3: provide frags as skb head)
> 
> This removes the memory leak we had, since we could leak one page at
> device dismantle.
> 
> Signed-off-by: Eric Dumazet <edumazet@google.com>

Hmmm, doesn't apply cleanly to net-next for some reason:

[davem@drr net-next]$ git am --signoff net-next-tg3-use-netdev_alloc_frag-API.patch 
Applying: tg3: use netdev_alloc_frag() API
error: patch failed: drivers/net/ethernet/broadcom/tg3.c:5631
error: drivers/net/ethernet/broadcom/tg3.c: patch does not apply
Patch failed at 0001 tg3: use netdev_alloc_frag() API
When you have resolved this problem run "git am --resolved".
If you would prefer to skip this patch, instead run "git am --skip".
To restore the original branch and stop patching run "git am --abort".

^ permalink raw reply

* [PATCH net-next] tg3: use netdev_alloc_frag() API
From: Eric Dumazet @ 2012-05-19  7:15 UTC (permalink / raw)
  To: David Miller; +Cc: netdev, Matt Carlson, Michael Chan

From: Eric Dumazet <edumazet@google.com>

Update our reference driver to use netdev_alloc_frag() API instead of
the temporary custom allocator I introduced in commit 8d4057a938
(tg3: provide frags as skb head)

This removes the memory leak we had, since we could leak one page at
device dismantle.

Signed-off-by: Eric Dumazet <edumazet@google.com>
Cc: Matt Carlson <mcarlson@broadcom.com>
Cc: Michael Chan <mchan@broadcom.com>
---
 drivers/net/ethernet/broadcom/tg3.c |   38 +++-----------------------
 drivers/net/ethernet/broadcom/tg3.h |    2 -
 2 files changed, 5 insertions(+), 35 deletions(-)

diff --git a/drivers/net/ethernet/broadcom/tg3.c b/drivers/net/ethernet/broadcom/tg3.c
index 4230e70..d55df32 100644
--- a/drivers/net/ethernet/broadcom/tg3.c
+++ b/drivers/net/ethernet/broadcom/tg3.c
@@ -195,15 +195,6 @@ static inline void _tg3_flag_clear(enum TG3_FLAGS flag, unsigned long *bits)
 #define TG3_RX_OFFSET(tp)	(NET_SKB_PAD)
 #endif
 
-/* This driver uses the new build_skb() API providing a frag as skb->head
- * This strategy permits better GRO aggregation, better TCP coalescing, and
- * better splice() implementation (avoids a copy from head to a page), at
- * minimal memory cost.
- * In this 2048 bytes block, we have enough room to store the MTU=1500 frame
- * and the struct skb_shared_info.
- */
-#define TG3_FRAGSIZE 2048
-
 /* minimum number of free TX descriptors required to wake up TX process */
 #define TG3_TX_WAKEUP_THRESH(tnapi)		((tnapi)->tx_pending / 4)
 #define TG3_TX_BD_DMA_MAX_2K		2048
@@ -5631,25 +5622,6 @@ static void tg3_tx(struct tg3_napi *tnapi)
 	}
 }
 
-static void *tg3_frag_alloc(struct tg3_rx_prodring_set *tpr)
-{
-	void *data;
-
-	if (tpr->rx_page_size < TG3_FRAGSIZE) {
-		struct page *page = alloc_page(GFP_ATOMIC);
-
-		if (!page)
-			return NULL;
-		atomic_add((PAGE_SIZE / TG3_FRAGSIZE) - 1, &page->_count); 
-		tpr->rx_page_addr = page_address(page);
-		tpr->rx_page_size = PAGE_SIZE;
-	}
-	data = tpr->rx_page_addr;
-	tpr->rx_page_addr += TG3_FRAGSIZE;
-	tpr->rx_page_size -= TG3_FRAGSIZE;
-	return data;
-}
-
 static void tg3_frag_free(bool is_frag, void *data)
 {
 	if (is_frag)
@@ -5668,7 +5640,7 @@ static void tg3_rx_data_free(struct tg3 *tp, struct ring_info *ri, u32 map_sz)
 
 	pci_unmap_single(tp->pdev, dma_unmap_addr(ri, mapping),
 			 map_sz, PCI_DMA_FROMDEVICE);
-	tg3_frag_free(skb_size <= TG3_FRAGSIZE, ri->data);
+	tg3_frag_free(skb_size <= PAGE_SIZE, ri->data);
 	ri->data = NULL;
 }
 
@@ -5721,9 +5693,9 @@ static int tg3_alloc_rx_data(struct tg3 *tp, struct tg3_rx_prodring_set *tpr,
 	 */
 	skb_size = SKB_DATA_ALIGN(data_size + TG3_RX_OFFSET(tp)) +
 		   SKB_DATA_ALIGN(sizeof(struct skb_shared_info));
-	if (skb_size <= TG3_FRAGSIZE) {
-		data = tg3_frag_alloc(tpr);
-		*frag_size = TG3_FRAGSIZE;
+	if (skb_size <= PAGE_SIZE) {
+		data = netdev_alloc_frag(skb_size);
+		*frag_size = skb_size;
 	} else {
 		data = kmalloc(skb_size, GFP_ATOMIC);
 		*frag_size = 0;
@@ -5736,7 +5708,7 @@ static int tg3_alloc_rx_data(struct tg3 *tp, struct tg3_rx_prodring_set *tpr,
 				 data_size,
 				 PCI_DMA_FROMDEVICE);
 	if (unlikely(pci_dma_mapping_error(tp->pdev, mapping))) {
-		tg3_frag_free(skb_size <= TG3_FRAGSIZE, data);
+		tg3_frag_free(skb_size <= PAGE_SIZE, data);
 		return -EIO;
 	}
 
diff --git a/drivers/net/ethernet/broadcom/tg3.h b/drivers/net/ethernet/broadcom/tg3.h
index 7c85545..93865f8 100644
--- a/drivers/net/ethernet/broadcom/tg3.h
+++ b/drivers/net/ethernet/broadcom/tg3.h
@@ -2815,8 +2815,6 @@ struct tg3_rx_prodring_set {
 	struct ring_info		*rx_jmb_buffers;
 	dma_addr_t			rx_std_mapping;
 	dma_addr_t			rx_jmb_mapping;
-	void				*rx_page_addr;
-	unsigned int			rx_page_size;
 };
 
 #define TG3_IRQ_MAX_VECS_RSS		5

^ permalink raw reply related

* Re: [PATCH net-next] net: napi_frags_skb() is static
From: David Miller @ 2012-05-19  6:51 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev
In-Reply-To: <1337410146.7029.71.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 08:49:06 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> No need to export napi_frags_skb()
> 
> Signed-off-by: Eric Dumazet <edumazet@google.com>

Applied.

^ permalink raw reply

* [PATCH net-next] net: napi_frags_skb() is static
From: Eric Dumazet @ 2012-05-19  6:49 UTC (permalink / raw)
  To: David Miller; +Cc: netdev

From: Eric Dumazet <edumazet@google.com>

No need to export napi_frags_skb()

Signed-off-by: Eric Dumazet <edumazet@google.com>
---
 include/linux/netdevice.h |    1 -
 net/core/dev.c            |    3 +--
 2 files changed, 1 insertion(+), 3 deletions(-)

diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index 9c710bd..e7fd468 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -2142,7 +2142,6 @@ extern struct sk_buff *	napi_get_frags(struct napi_struct *napi);
 extern gro_result_t	napi_frags_finish(struct napi_struct *napi,
 					  struct sk_buff *skb,
 					  gro_result_t ret);
-extern struct sk_buff *	napi_frags_skb(struct napi_struct *napi);
 extern gro_result_t	napi_gro_frags(struct napi_struct *napi);
 
 static inline void napi_free_frags(struct napi_struct *napi)
diff --git a/net/core/dev.c b/net/core/dev.c
index 33684b6..cd09819 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -3602,7 +3602,7 @@ gro_result_t napi_frags_finish(struct napi_struct *napi, struct sk_buff *skb,
 }
 EXPORT_SYMBOL(napi_frags_finish);
 
-struct sk_buff *napi_frags_skb(struct napi_struct *napi)
+static struct sk_buff *napi_frags_skb(struct napi_struct *napi)
 {
 	struct sk_buff *skb = napi->skb;
 	struct ethhdr *eth;
@@ -3637,7 +3637,6 @@ struct sk_buff *napi_frags_skb(struct napi_struct *napi)
 out:
 	return skb;
 }
-EXPORT_SYMBOL(napi_frags_skb);
 
 gro_result_t napi_gro_frags(struct napi_struct *napi)
 {

^ permalink raw reply related

* Re: ppp/l2tp doing oversized allocations ?
From: David Miller @ 2012-05-19  6:34 UTC (permalink / raw)
  To: eric.dumazet; +Cc: davej, netdev, kernel-team, edumazet
In-Reply-To: <1337408730.7029.69.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 08:25:30 +0200

> On Sat, 2012-05-19 at 07:01 +0200, Eric Dumazet wrote:
>> On Sat, 2012-05-19 at 00:46 -0400, David Miller wrote:
>> 
>> > So it's ESP encapsulated IPSEC over L2tp.
>> > 
>> > Eric, I wonder if session->hdr_len can take on undesirable values and
>> > thus trip up the skb COW'ing calculations you added?
>> 
>> I take a look, thanks
>> 
> 
> hdr_len is u16, I have no idea how we can reach MAX_ORDER page
> allocations... (more than 2 Mbytes...)
> 
> Maybe a memory corruption, or a signed/unsigned mismatch.

Yes, the trace looks really weird to me too.

It's also possible that the big length comes accidently from IPSEC
too.

If this can be readily reproduced, we can construct some debugging
patches for the user to try.

^ permalink raw reply

* Re: [PATCH net-next] ppp: avoid false drop_monitor false positives
From: David Miller @ 2012-05-19  6:33 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev
In-Reply-To: <1337408580.7029.66.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 08:23:00 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> Call consume_skb() in place of kfree_skb() were appropriate.
> 
> Signed-off-by: Eric Dumazet <edumazet@google.com>

Applied, thanks Eric.

^ permalink raw reply

* Re: ppp/l2tp doing oversized allocations ?
From: Eric Dumazet @ 2012-05-19  6:25 UTC (permalink / raw)
  To: David Miller; +Cc: davej, netdev, kernel-team, edumazet
In-Reply-To: <1337403685.7029.63.camel@edumazet-glaptop>

On Sat, 2012-05-19 at 07:01 +0200, Eric Dumazet wrote:
> On Sat, 2012-05-19 at 00:46 -0400, David Miller wrote:
> 
> > So it's ESP encapsulated IPSEC over L2tp.
> > 
> > Eric, I wonder if session->hdr_len can take on undesirable values and
> > thus trip up the skb COW'ing calculations you added?
> 
> I take a look, thanks
> 

hdr_len is u16, I have no idea how we can reach MAX_ORDER page
allocations... (more than 2 Mbytes...)

Maybe a memory corruption, or a signed/unsigned mismatch.

^ permalink raw reply

* [PATCH net-next] ppp: avoid false drop_monitor false positives
From: Eric Dumazet @ 2012-05-19  6:23 UTC (permalink / raw)
  To: David Miller; +Cc: netdev

From: Eric Dumazet <edumazet@google.com>

Call consume_skb() in place of kfree_skb() were appropriate.

Signed-off-by: Eric Dumazet <edumazet@google.com>
---
 drivers/net/ppp/ppp_async.c   |    2 +-
 drivers/net/ppp/ppp_generic.c |   14 +++++++-------
 drivers/net/ppp/ppp_synctty.c |    4 ++--
 drivers/net/ppp/pppoe.c       |    6 ++++--
 drivers/net/ppp/pptp.c        |    2 +-
 5 files changed, 15 insertions(+), 13 deletions(-)

diff --git a/drivers/net/ppp/ppp_async.c b/drivers/net/ppp/ppp_async.c
index af95a98..a031f6b 100644
--- a/drivers/net/ppp/ppp_async.c
+++ b/drivers/net/ppp/ppp_async.c
@@ -613,7 +613,7 @@ ppp_async_encode(struct asyncppp *ap)
 	*buf++ = PPP_FLAG;
 	ap->olim = buf;
 
-	kfree_skb(ap->tpkt);
+	consume_skb(ap->tpkt);
 	ap->tpkt = NULL;
 	return 1;
 }
diff --git a/drivers/net/ppp/ppp_generic.c b/drivers/net/ppp/ppp_generic.c
index 21d7151..5c05572 100644
--- a/drivers/net/ppp/ppp_generic.c
+++ b/drivers/net/ppp/ppp_generic.c
@@ -1092,13 +1092,13 @@ pad_compress_skb(struct ppp *ppp, struct sk_buff *skb)
 				   new_skb->data, skb->len + 2,
 				   compressor_skb_size);
 	if (len > 0 && (ppp->flags & SC_CCP_UP)) {
-		kfree_skb(skb);
+		consume_skb(skb);
 		skb = new_skb;
 		skb_put(skb, len);
 		skb_pull(skb, 2);	/* pull off A/C bytes */
 	} else if (len == 0) {
 		/* didn't compress, or CCP not up yet */
-		kfree_skb(new_skb);
+		consume_skb(new_skb);
 		new_skb = skb;
 	} else {
 		/*
@@ -1112,7 +1112,7 @@ pad_compress_skb(struct ppp *ppp, struct sk_buff *skb)
 		if (net_ratelimit())
 			netdev_err(ppp->dev, "ppp: compressor dropped pkt\n");
 		kfree_skb(skb);
-		kfree_skb(new_skb);
+		consume_skb(new_skb);
 		new_skb = NULL;
 	}
 	return new_skb;
@@ -1178,7 +1178,7 @@ ppp_send_frame(struct ppp *ppp, struct sk_buff *skb)
 				    !(ppp->flags & SC_NO_TCP_CCID));
 		if (cp == skb->data + 2) {
 			/* didn't compress */
-			kfree_skb(new_skb);
+			consume_skb(new_skb);
 		} else {
 			if (cp[0] & SL_TYPE_COMPRESSED_TCP) {
 				proto = PPP_VJC_COMP;
@@ -1187,7 +1187,7 @@ ppp_send_frame(struct ppp *ppp, struct sk_buff *skb)
 				proto = PPP_VJC_UNCOMP;
 				cp[0] = skb->data[2];
 			}
-			kfree_skb(skb);
+			consume_skb(skb);
 			skb = new_skb;
 			cp = skb_put(skb, len + 2);
 			cp[0] = 0;
@@ -1703,7 +1703,7 @@ ppp_receive_nonmp_frame(struct ppp *ppp, struct sk_buff *skb)
 			}
 			skb_reserve(ns, 2);
 			skb_copy_bits(skb, 0, skb_put(ns, skb->len), skb->len);
-			kfree_skb(skb);
+			consume_skb(skb);
 			skb = ns;
 		}
 		else
@@ -1851,7 +1851,7 @@ ppp_decompress_frame(struct ppp *ppp, struct sk_buff *skb)
 			goto err;
 		}
 
-		kfree_skb(skb);
+		consume_skb(skb);
 		skb = ns;
 		skb_put(skb, len);
 		skb_pull(skb, 2);	/* pull off the A/C bytes */
diff --git a/drivers/net/ppp/ppp_synctty.c b/drivers/net/ppp/ppp_synctty.c
index 55e466c..1a12033 100644
--- a/drivers/net/ppp/ppp_synctty.c
+++ b/drivers/net/ppp/ppp_synctty.c
@@ -588,7 +588,7 @@ ppp_sync_txmunge(struct syncppp *ap, struct sk_buff *skb)
 			skb_reserve(npkt,2);
 			skb_copy_from_linear_data(skb,
 				      skb_put(npkt, skb->len), skb->len);
-			kfree_skb(skb);
+			consume_skb(skb);
 			skb = npkt;
 		}
 		skb_push(skb,2);
@@ -656,7 +656,7 @@ ppp_sync_push(struct syncppp *ap)
 			if (sent < ap->tpkt->len) {
 				tty_stuffed = 1;
 			} else {
-				kfree_skb(ap->tpkt);
+				consume_skb(ap->tpkt);
 				ap->tpkt = NULL;
 				clear_bit(XMIT_FULL, &ap->xmit_flags);
 				done = 1;
diff --git a/drivers/net/ppp/pppoe.c b/drivers/net/ppp/pppoe.c
index dd15b8f..cbf7047 100644
--- a/drivers/net/ppp/pppoe.c
+++ b/drivers/net/ppp/pppoe.c
@@ -984,8 +984,10 @@ static int pppoe_recvmsg(struct kiocb *iocb, struct socket *sock,
 	if (skb) {
 		total_len = min_t(size_t, total_len, skb->len);
 		error = skb_copy_datagram_iovec(skb, 0, m->msg_iov, total_len);
-		if (error == 0)
-			error = total_len;
+		if (error == 0) {
+			consume_skb(skb);
+			return total_len;
+		}
 	}
 
 	kfree_skb(skb);
diff --git a/drivers/net/ppp/pptp.c b/drivers/net/ppp/pptp.c
index 72b50f5..1c98321 100644
--- a/drivers/net/ppp/pptp.c
+++ b/drivers/net/ppp/pptp.c
@@ -209,7 +209,7 @@ static int pptp_xmit(struct ppp_channel *chan, struct sk_buff *skb)
 		}
 		if (skb->sk)
 			skb_set_owner_w(new_skb, skb->sk);
-		kfree_skb(skb);
+		consume_skb(skb);
 		skb = new_skb;
 	}
 

^ permalink raw reply related

* Re: [PATCH v2 4/5] staging: octeon_ethernet: Convert to use device tree.
From: Grant Likely @ 2012-05-19  6:07 UTC (permalink / raw)
  To: David Daney, linux-mips, ralf, devicetree-discuss, Rob Herring
  Cc: linux-kernel, David Daney, netdev, Greg Kroah-Hartman,
	David S. Miller
In-Reply-To: <1335489630-27017-5-git-send-email-ddaney.cavm@gmail.com>

On Thu, 26 Apr 2012 18:20:29 -0700, David Daney <ddaney.cavm@gmail.com> wrote:
> From: David Daney <david.daney@cavium.com>
> 
> Get MAC address and PHY connection from the device tree.  The driver
> is converted to a platform driver.
> 
> Acked-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
> Signed-off-by: David Daney <david.daney@cavium.com>
> Cc: netdev@vger.kernel.org
> Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
> Cc: David S. Miller <davem@davemloft.net>

Acked-by: Grant Likely <grant.likely@secretlab.ca>

^ permalink raw reply

* Re: [PATCH v2 2/5] netdev: mdio-octeon.c: Convert to use device tree.
From: Grant Likely @ 2012-05-19  6:06 UTC (permalink / raw)
  To: David Daney, linux-mips-6z/3iImG2C8G8FEW9MqTrA,
	ralf-6z/3iImG2C8G8FEW9MqTrA,
	devicetree-discuss-uLR06cmDAlY/bJ5BZ2RsiQ, Rob Herring
  Cc: netdev-u79uwXL29TY76Z2rM5mHXA, David S. Miller,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA, David Daney
In-Reply-To: <1335489630-27017-3-git-send-email-ddaney.cavm-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>

On Thu, 26 Apr 2012 18:20:27 -0700, David Daney <ddaney.cavm-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org> wrote:
> From: David Daney <david.daney-YGCgFSpz5w/QT0dZR+AlfA@public.gmane.org>
> 
> Get the MDIO bus controller addresses from the device tree, small
> clean up in use of devm_*
> 
> Remove, now unused, platform device setup code.

Ditto on this one (and the others); make sure the new compatible value
is documented.  Otherwise looks good.

g.

^ permalink raw reply

* Re: [PATCH net-next] ipv6: bool/const conversions phase2
From: David Miller @ 2012-05-19  5:08 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev
In-Reply-To: <1337403454.7029.62.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Sat, 19 May 2012 06:57:34 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> Mostly bool conversions, some inline removals and const additions.
> 
> Signed-off-by: Eric Dumazet <edumazet@google.com>

Applied, thanks Eric.

^ permalink raw reply

* Re: ppp/l2tp doing oversized allocations ?
From: Eric Dumazet @ 2012-05-19  5:01 UTC (permalink / raw)
  To: David Miller; +Cc: davej, netdev, kernel-team, edumazet
In-Reply-To: <20120519.004652.2261671316587735315.davem@davemloft.net>

On Sat, 2012-05-19 at 00:46 -0400, David Miller wrote:

> So it's ESP encapsulated IPSEC over L2tp.
> 
> Eric, I wonder if session->hdr_len can take on undesirable values and
> thus trip up the skb COW'ing calculations you added?

I take a look, thanks

^ permalink raw reply

* [PATCH net-next] ipv6: bool/const conversions phase2
From: Eric Dumazet @ 2012-05-19  4:57 UTC (permalink / raw)
  To: David Miller; +Cc: netdev

From: Eric Dumazet <edumazet@google.com>

Mostly bool conversions, some inline removals and const additions.

Signed-off-by: Eric Dumazet <edumazet@google.com>
---
 include/net/addrconf.h   |   18 +++++-----
 include/net/ip6_route.h  |    2 -
 include/net/ipv6.h       |    2 -
 include/net/rawv6.h      |    2 -
 net/ipv6/addrlabel.c     |   24 ++++++-------
 net/ipv6/ah6.c           |    6 +--
 net/ipv6/anycast.c       |   12 +++---
 net/ipv6/datagram.c      |    4 +-
 net/ipv6/exthdrs.c       |   54 +++++++++++++++---------------
 net/ipv6/exthdrs_core.c  |    2 -
 net/ipv6/icmp.c          |   14 +++----
 net/ipv6/ip6_flowlabel.c |   24 ++++++-------
 net/ipv6/ip6_input.c     |    9 ++---
 net/ipv6/mcast.c         |   66 ++++++++++++++++++-------------------
 net/ipv6/ndisc.c         |    4 +-
 net/ipv6/raw.c           |   10 ++---
 net/ipv6/route.c         |    8 ++--
 17 files changed, 131 insertions(+), 130 deletions(-)

diff --git a/include/net/addrconf.h b/include/net/addrconf.h
index 27f450b..f2b801c 100644
--- a/include/net/addrconf.h
+++ b/include/net/addrconf.h
@@ -131,9 +131,9 @@ extern int ipv6_sock_mc_join(struct sock *sk, int ifindex,
 extern int ipv6_sock_mc_drop(struct sock *sk, int ifindex,
 			     const struct in6_addr *addr);
 extern void ipv6_sock_mc_close(struct sock *sk);
-extern int inet6_mc_check(struct sock *sk,
-			  const struct in6_addr *mc_addr,
-			  const struct in6_addr *src_addr);
+extern bool inet6_mc_check(struct sock *sk,
+			   const struct in6_addr *mc_addr,
+			   const struct in6_addr *src_addr);
 
 extern int ipv6_dev_mc_inc(struct net_device *dev, const struct in6_addr *addr);
 extern int __ipv6_dev_mc_dec(struct inet6_dev *idev, const struct in6_addr *addr);
@@ -146,10 +146,10 @@ extern void ipv6_mc_init_dev(struct inet6_dev *idev);
 extern void ipv6_mc_destroy_dev(struct inet6_dev *idev);
 extern void addrconf_dad_failure(struct inet6_ifaddr *ifp);
 
-extern int ipv6_chk_mcast_addr(struct net_device *dev,
-			       const struct in6_addr *group,
-			       const struct in6_addr *src_addr);
-extern int ipv6_is_mld(struct sk_buff *skb, int nexthdr);
+extern bool ipv6_chk_mcast_addr(struct net_device *dev,
+				const struct in6_addr *group,
+				const struct in6_addr *src_addr);
+extern bool ipv6_is_mld(struct sk_buff *skb, int nexthdr);
 
 extern void addrconf_prefix_rcv(struct net_device *dev,
 				u8 *opt, int len, bool sllao);
@@ -163,8 +163,8 @@ extern void ipv6_sock_ac_close(struct sock *sk);
 
 extern int ipv6_dev_ac_inc(struct net_device *dev, const struct in6_addr *addr);
 extern int __ipv6_dev_ac_dec(struct inet6_dev *idev, const struct in6_addr *addr);
-extern int ipv6_chk_acast_addr(struct net *net, struct net_device *dev,
-			       const struct in6_addr *addr);
+extern bool ipv6_chk_acast_addr(struct net *net, struct net_device *dev,
+				const struct in6_addr *addr);
 
 
 /* Device notifier */
diff --git a/include/net/ip6_route.h b/include/net/ip6_route.h
index c062b67..37c1a1e 100644
--- a/include/net/ip6_route.h
+++ b/include/net/ip6_route.h
@@ -175,7 +175,7 @@ static inline void ip6_dst_store(struct sock *sk, struct dst_entry *dst,
 	spin_unlock(&sk->sk_dst_lock);
 }
 
-static inline int ipv6_unicast_destination(struct sk_buff *skb)
+static inline bool ipv6_unicast_destination(const struct sk_buff *skb)
 {
 	struct rt6_info *rt = (struct rt6_info *) skb_dst(skb);
 
diff --git a/include/net/ipv6.h b/include/net/ipv6.h
index 1402139..aecf884 100644
--- a/include/net/ipv6.h
+++ b/include/net/ipv6.h
@@ -559,7 +559,7 @@ extern void			ipv6_push_frag_opts(struct sk_buff *skb,
 extern int			ipv6_skip_exthdr(const struct sk_buff *, int start,
 					         u8 *nexthdrp, __be16 *frag_offp);
 
-extern int 			ipv6_ext_hdr(u8 nexthdr);
+extern bool			ipv6_ext_hdr(u8 nexthdr);
 
 extern int ipv6_find_tlv(struct sk_buff *skb, int offset, int type);
 
diff --git a/include/net/rawv6.h b/include/net/rawv6.h
index cf75772..e7ea660 100644
--- a/include/net/rawv6.h
+++ b/include/net/rawv6.h
@@ -5,7 +5,7 @@
 
 void raw6_icmp_error(struct sk_buff *, int nexthdr,
 		u8 type, u8 code, int inner_offset, __be32);
-int raw6_local_deliver(struct sk_buff *, int);
+bool raw6_local_deliver(struct sk_buff *, int);
 
 extern int			rawv6_rcv(struct sock *sk,
 					  struct sk_buff *skb);
diff --git a/net/ipv6/addrlabel.c b/net/ipv6/addrlabel.c
index 95aea16..eb6a636 100644
--- a/net/ipv6/addrlabel.c
+++ b/net/ipv6/addrlabel.c
@@ -129,7 +129,7 @@ static void ip6addrlbl_free_rcu(struct rcu_head *h)
 	ip6addrlbl_free(container_of(h, struct ip6addrlbl_entry, rcu));
 }
 
-static inline int ip6addrlbl_hold(struct ip6addrlbl_entry *p)
+static bool ip6addrlbl_hold(struct ip6addrlbl_entry *p)
 {
 	return atomic_inc_not_zero(&p->refcnt);
 }
@@ -141,20 +141,20 @@ static inline void ip6addrlbl_put(struct ip6addrlbl_entry *p)
 }
 
 /* Find label */
-static int __ip6addrlbl_match(struct net *net,
-			      struct ip6addrlbl_entry *p,
-			      const struct in6_addr *addr,
-			      int addrtype, int ifindex)
+static bool __ip6addrlbl_match(struct net *net,
+			       const struct ip6addrlbl_entry *p,
+			       const struct in6_addr *addr,
+			       int addrtype, int ifindex)
 {
 	if (!net_eq(ip6addrlbl_net(p), net))
-		return 0;
+		return false;
 	if (p->ifindex && p->ifindex != ifindex)
-		return 0;
+		return false;
 	if (p->addrtype && p->addrtype != addrtype)
-		return 0;
+		return false;
 	if (!ipv6_prefix_equal(addr, &p->prefix, p->prefixlen))
-		return 0;
-	return 1;
+		return false;
+	return true;
 }
 
 static struct ip6addrlbl_entry *__ipv6_addr_label(struct net *net,
@@ -456,8 +456,8 @@ static int ip6addrlbl_newdel(struct sk_buff *skb, struct nlmsghdr *nlh,
 	return err;
 }
 
-static inline void ip6addrlbl_putmsg(struct nlmsghdr *nlh,
-				     int prefixlen, int ifindex, u32 lseq)
+static void ip6addrlbl_putmsg(struct nlmsghdr *nlh,
+			      int prefixlen, int ifindex, u32 lseq)
 {
 	struct ifaddrlblmsg *ifal = nlmsg_data(nlh);
 	ifal->ifal_family = AF_INET6;
diff --git a/net/ipv6/ah6.c b/net/ipv6/ah6.c
index 5d32e7a..f1a4a2c 100644
--- a/net/ipv6/ah6.c
+++ b/net/ipv6/ah6.c
@@ -113,7 +113,7 @@ static inline struct scatterlist *ah_req_sg(struct crypto_ahash *ahash,
 			     __alignof__(struct scatterlist));
 }
 
-static int zero_out_mutable_opts(struct ipv6_opt_hdr *opthdr)
+static bool zero_out_mutable_opts(struct ipv6_opt_hdr *opthdr)
 {
 	u8 *opt = (u8 *)opthdr;
 	int len = ipv6_optlen(opthdr);
@@ -145,10 +145,10 @@ static int zero_out_mutable_opts(struct ipv6_opt_hdr *opthdr)
 		len -= optlen;
 	}
 	if (len == 0)
-		return 1;
+		return true;
 
 bad:
-	return 0;
+	return false;
 }
 
 #if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
diff --git a/net/ipv6/anycast.c b/net/ipv6/anycast.c
index db00d27..cdf02be 100644
--- a/net/ipv6/anycast.c
+++ b/net/ipv6/anycast.c
@@ -342,7 +342,7 @@ static int ipv6_dev_ac_dec(struct net_device *dev, const struct in6_addr *addr)
  *	check if the interface has this anycast address
  *	called with rcu_read_lock()
  */
-static int ipv6_chk_acast_dev(struct net_device *dev, const struct in6_addr *addr)
+static bool ipv6_chk_acast_dev(struct net_device *dev, const struct in6_addr *addr)
 {
 	struct inet6_dev *idev;
 	struct ifacaddr6 *aca;
@@ -356,16 +356,16 @@ static int ipv6_chk_acast_dev(struct net_device *dev, const struct in6_addr *add
 		read_unlock_bh(&idev->lock);
 		return aca != NULL;
 	}
-	return 0;
+	return false;
 }
 
 /*
  *	check if given interface (or any, if dev==0) has this anycast address
  */
-int ipv6_chk_acast_addr(struct net *net, struct net_device *dev,
-			const struct in6_addr *addr)
+bool ipv6_chk_acast_addr(struct net *net, struct net_device *dev,
+			 const struct in6_addr *addr)
 {
-	int found = 0;
+	bool found = false;
 
 	rcu_read_lock();
 	if (dev)
@@ -373,7 +373,7 @@ int ipv6_chk_acast_addr(struct net *net, struct net_device *dev,
 	else
 		for_each_netdev_rcu(net, dev)
 			if (ipv6_chk_acast_dev(dev, addr)) {
-				found = 1;
+				found = true;
 				break;
 			}
 	rcu_read_unlock();
diff --git a/net/ipv6/datagram.c b/net/ipv6/datagram.c
index b8b61ac..be2b67d6 100644
--- a/net/ipv6/datagram.c
+++ b/net/ipv6/datagram.c
@@ -34,9 +34,9 @@
 #include <linux/errqueue.h>
 #include <asm/uaccess.h>
 
-static inline int ipv6_mapped_addr_any(const struct in6_addr *a)
+static bool ipv6_mapped_addr_any(const struct in6_addr *a)
 {
-	return (ipv6_addr_v4mapped(a) && (a->s6_addr32[3] == 0));
+	return ipv6_addr_v4mapped(a) && (a->s6_addr32[3] == 0);
 }
 
 int ip6_datagram_connect(struct sock *sk, struct sockaddr *uaddr, int addr_len)
diff --git a/net/ipv6/exthdrs.c b/net/ipv6/exthdrs.c
index a3cded6..50ec95f 100644
--- a/net/ipv6/exthdrs.c
+++ b/net/ipv6/exthdrs.c
@@ -96,14 +96,14 @@ EXPORT_SYMBOL_GPL(ipv6_find_tlv);
 /*
  *	Parsing tlv encoded headers.
  *
- *	Parsing function "func" returns 1, if parsing succeed
- *	and 0, if it failed.
+ *	Parsing function "func" returns true, if parsing succeed
+ *	and false, if it failed.
  *	It MUST NOT touch skb->h.
  */
 
 struct tlvtype_proc {
 	int	type;
-	int	(*func)(struct sk_buff *skb, int offset);
+	bool	(*func)(struct sk_buff *skb, int offset);
 };
 
 /*********************
@@ -112,11 +112,11 @@ struct tlvtype_proc {
 
 /* An unknown option is detected, decide what to do */
 
-static int ip6_tlvopt_unknown(struct sk_buff *skb, int optoff)
+static bool ip6_tlvopt_unknown(struct sk_buff *skb, int optoff)
 {
 	switch ((skb_network_header(skb)[optoff] & 0xC0) >> 6) {
 	case 0: /* ignore */
-		return 1;
+		return true;
 
 	case 1: /* drop packet */
 		break;
@@ -129,18 +129,18 @@ static int ip6_tlvopt_unknown(struct sk_buff *skb, int optoff)
 			break;
 	case 2: /* send ICMP PARM PROB regardless and drop packet */
 		icmpv6_param_prob(skb, ICMPV6_UNK_OPTION, optoff);
-		return 0;
+		return false;
 	}
 
 	kfree_skb(skb);
-	return 0;
+	return false;
 }
 
 /* Parse tlv encoded option header (hop-by-hop or destination) */
 
-static int ip6_parse_tlv(struct tlvtype_proc *procs, struct sk_buff *skb)
+static bool ip6_parse_tlv(const struct tlvtype_proc *procs, struct sk_buff *skb)
 {
-	struct tlvtype_proc *curr;
+	const struct tlvtype_proc *curr;
 	const unsigned char *nh = skb_network_header(skb);
 	int off = skb_network_header_len(skb);
 	int len = (skb_transport_header(skb)[1] + 1) << 3;
@@ -186,14 +186,14 @@ static int ip6_parse_tlv(struct tlvtype_proc *procs, struct sk_buff *skb)
 					/* type specific length/alignment
 					   checks will be performed in the
 					   func(). */
-					if (curr->func(skb, off) == 0)
-						return 0;
+					if (curr->func(skb, off) == false)
+						return false;
 					break;
 				}
 			}
 			if (curr->type < 0) {
 				if (ip6_tlvopt_unknown(skb, off) == 0)
-					return 0;
+					return false;
 			}
 			break;
 		}
@@ -201,10 +201,10 @@ static int ip6_parse_tlv(struct tlvtype_proc *procs, struct sk_buff *skb)
 		len -= optlen;
 	}
 	if (len == 0)
-		return 1;
+		return true;
 bad:
 	kfree_skb(skb);
-	return 0;
+	return false;
 }
 
 /*****************************
@@ -212,7 +212,7 @@ bad:
  *****************************/
 
 #if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
-static int ipv6_dest_hao(struct sk_buff *skb, int optoff)
+static bool ipv6_dest_hao(struct sk_buff *skb, int optoff)
 {
 	struct ipv6_destopt_hao *hao;
 	struct inet6_skb_parm *opt = IP6CB(skb);
@@ -266,15 +266,15 @@ static int ipv6_dest_hao(struct sk_buff *skb, int optoff)
 	if (skb->tstamp.tv64 == 0)
 		__net_timestamp(skb);
 
-	return 1;
+	return true;
 
  discard:
 	kfree_skb(skb);
-	return 0;
+	return false;
 }
 #endif
 
-static struct tlvtype_proc tlvprocdestopt_lst[] = {
+static const struct tlvtype_proc tlvprocdestopt_lst[] = {
 #if defined(CONFIG_IPV6_MIP6) || defined(CONFIG_IPV6_MIP6_MODULE)
 	{
 		.type	= IPV6_TLV_HAO,
@@ -579,23 +579,23 @@ static inline struct net *ipv6_skb_net(struct sk_buff *skb)
 
 /* Router Alert as of RFC 2711 */
 
-static int ipv6_hop_ra(struct sk_buff *skb, int optoff)
+static bool ipv6_hop_ra(struct sk_buff *skb, int optoff)
 {
 	const unsigned char *nh = skb_network_header(skb);
 
 	if (nh[optoff + 1] == 2) {
 		IP6CB(skb)->ra = optoff;
-		return 1;
+		return true;
 	}
 	LIMIT_NETDEBUG(KERN_DEBUG "ipv6_hop_ra: wrong RA length %d\n",
 		       nh[optoff + 1]);
 	kfree_skb(skb);
-	return 0;
+	return false;
 }
 
 /* Jumbo payload */
 
-static int ipv6_hop_jumbo(struct sk_buff *skb, int optoff)
+static bool ipv6_hop_jumbo(struct sk_buff *skb, int optoff)
 {
 	const unsigned char *nh = skb_network_header(skb);
 	struct net *net = ipv6_skb_net(skb);
@@ -614,13 +614,13 @@ static int ipv6_hop_jumbo(struct sk_buff *skb, int optoff)
 		IP6_INC_STATS_BH(net, ipv6_skb_idev(skb),
 				 IPSTATS_MIB_INHDRERRORS);
 		icmpv6_param_prob(skb, ICMPV6_HDR_FIELD, optoff+2);
-		return 0;
+		return false;
 	}
 	if (ipv6_hdr(skb)->payload_len) {
 		IP6_INC_STATS_BH(net, ipv6_skb_idev(skb),
 				 IPSTATS_MIB_INHDRERRORS);
 		icmpv6_param_prob(skb, ICMPV6_HDR_FIELD, optoff);
-		return 0;
+		return false;
 	}
 
 	if (pkt_len > skb->len - sizeof(struct ipv6hdr)) {
@@ -632,14 +632,14 @@ static int ipv6_hop_jumbo(struct sk_buff *skb, int optoff)
 	if (pskb_trim_rcsum(skb, pkt_len + sizeof(struct ipv6hdr)))
 		goto drop;
 
-	return 1;
+	return true;
 
 drop:
 	kfree_skb(skb);
-	return 0;
+	return false;
 }
 
-static struct tlvtype_proc tlvprochopopt_lst[] = {
+static const struct tlvtype_proc tlvprochopopt_lst[] = {
 	{
 		.type	= IPV6_TLV_ROUTERALERT,
 		.func	= ipv6_hop_ra,
diff --git a/net/ipv6/exthdrs_core.c b/net/ipv6/exthdrs_core.c
index 7b1a884..f73d59a 100644
--- a/net/ipv6/exthdrs_core.c
+++ b/net/ipv6/exthdrs_core.c
@@ -9,7 +9,7 @@
  * find out if nexthdr is a well-known extension header or a protocol
  */
 
-int ipv6_ext_hdr(u8 nexthdr)
+bool ipv6_ext_hdr(u8 nexthdr)
 {
 	/*
 	 * find out if nexthdr is an extension header or a protocol
diff --git a/net/ipv6/icmp.c b/net/ipv6/icmp.c
index 23c56ce..091a297 100644
--- a/net/ipv6/icmp.c
+++ b/net/ipv6/icmp.c
@@ -131,7 +131,7 @@ void icmpv6_param_prob(struct sk_buff *skb, u8 code, int pos)
  *	--ANK (980726)
  */
 
-static int is_ineligible(struct sk_buff *skb)
+static bool is_ineligible(const struct sk_buff *skb)
 {
 	int ptr = (u8 *)(ipv6_hdr(skb) + 1) - skb->data;
 	int len = skb->len - ptr;
@@ -139,11 +139,11 @@ static int is_ineligible(struct sk_buff *skb)
 	__be16 frag_off;
 
 	if (len < 0)
-		return 1;
+		return true;
 
 	ptr = ipv6_skip_exthdr(skb, ptr, &nexthdr, &frag_off);
 	if (ptr < 0)
-		return 0;
+		return false;
 	if (nexthdr == IPPROTO_ICMPV6) {
 		u8 _type, *tp;
 		tp = skb_header_pointer(skb,
@@ -151,9 +151,9 @@ static int is_ineligible(struct sk_buff *skb)
 			sizeof(_type), &_type);
 		if (tp == NULL ||
 		    !(*tp & ICMPV6_INFOMSG_MASK))
-			return 1;
+			return true;
 	}
-	return 0;
+	return false;
 }
 
 /*
@@ -208,14 +208,14 @@ static inline bool icmpv6_xrlim_allow(struct sock *sk, u8 type,
  *	highest-order two bits set to 10
  */
 
-static __inline__ int opt_unrec(struct sk_buff *skb, __u32 offset)
+static bool opt_unrec(struct sk_buff *skb, __u32 offset)
 {
 	u8 _optval, *op;
 
 	offset += skb_network_offset(skb);
 	op = skb_header_pointer(skb, offset, sizeof(_optval), &_optval);
 	if (op == NULL)
-		return 1;
+		return true;
 	return (*op & 0xC0) == 0x80;
 }
 
diff --git a/net/ipv6/ip6_flowlabel.c b/net/ipv6/ip6_flowlabel.c
index cb43df6..9772fbd 100644
--- a/net/ipv6/ip6_flowlabel.c
+++ b/net/ipv6/ip6_flowlabel.c
@@ -433,32 +433,32 @@ static int mem_check(struct sock *sk)
 	return 0;
 }
 
-static int ipv6_hdr_cmp(struct ipv6_opt_hdr *h1, struct ipv6_opt_hdr *h2)
+static bool ipv6_hdr_cmp(struct ipv6_opt_hdr *h1, struct ipv6_opt_hdr *h2)
 {
 	if (h1 == h2)
-		return 0;
+		return false;
 	if (h1 == NULL || h2 == NULL)
-		return 1;
+		return true;
 	if (h1->hdrlen != h2->hdrlen)
-		return 1;
+		return true;
 	return memcmp(h1+1, h2+1, ((h1->hdrlen+1)<<3) - sizeof(*h1));
 }
 
-static int ipv6_opt_cmp(struct ipv6_txoptions *o1, struct ipv6_txoptions *o2)
+static bool ipv6_opt_cmp(struct ipv6_txoptions *o1, struct ipv6_txoptions *o2)
 {
 	if (o1 == o2)
-		return 0;
+		return false;
 	if (o1 == NULL || o2 == NULL)
-		return 1;
+		return true;
 	if (o1->opt_nflen != o2->opt_nflen)
-		return 1;
+		return true;
 	if (ipv6_hdr_cmp(o1->hopopt, o2->hopopt))
-		return 1;
+		return true;
 	if (ipv6_hdr_cmp(o1->dst0opt, o2->dst0opt))
-		return 1;
+		return true;
 	if (ipv6_hdr_cmp((struct ipv6_opt_hdr *)o1->srcrt, (struct ipv6_opt_hdr *)o2->srcrt))
-		return 1;
-	return 0;
+		return true;
+	return false;
 }
 
 static inline void fl_link(struct ipv6_pinfo *np, struct ipv6_fl_socklist *sfl,
diff --git a/net/ipv6/ip6_input.c b/net/ipv6/ip6_input.c
index 1ca5d45..21a15df 100644
--- a/net/ipv6/ip6_input.c
+++ b/net/ipv6/ip6_input.c
@@ -170,7 +170,8 @@ static int ip6_input_finish(struct sk_buff *skb)
 {
 	const struct inet6_protocol *ipprot;
 	unsigned int nhoff;
-	int nexthdr, raw;
+	int nexthdr;
+	bool raw;
 	u8 hash;
 	struct inet6_dev *idev;
 	struct net *net = dev_net(skb_dst(skb)->dev);
@@ -251,7 +252,7 @@ int ip6_input(struct sk_buff *skb)
 int ip6_mc_input(struct sk_buff *skb)
 {
 	const struct ipv6hdr *hdr;
-	int deliver;
+	bool deliver;
 
 	IP6_UPD_PO_STATS_BH(dev_net(skb_dst(skb)->dev),
 			 ip6_dst_idev(skb_dst(skb)), IPSTATS_MIB_INMCAST,
@@ -287,7 +288,7 @@ int ip6_mc_input(struct sk_buff *skb)
 			 * is for MLD (0x0000).
 			 */
 			if ((ptr[2] | ptr[3]) == 0) {
-				deliver = 0;
+				deliver = false;
 
 				if (!ipv6_ext_hdr(nexthdr)) {
 					/* BUG */
@@ -312,7 +313,7 @@ int ip6_mc_input(struct sk_buff *skb)
 				case ICMPV6_MGM_REPORT:
 				case ICMPV6_MGM_REDUCTION:
 				case ICMPV6_MLD2_REPORT:
-					deliver = 1;
+					deliver = true;
 					break;
 				}
 				goto out;
diff --git a/net/ipv6/mcast.c b/net/ipv6/mcast.c
index 2a3a22c..6d0f5dc 100644
--- a/net/ipv6/mcast.c
+++ b/net/ipv6/mcast.c
@@ -606,13 +606,13 @@ done:
 	return err;
 }
 
-int inet6_mc_check(struct sock *sk, const struct in6_addr *mc_addr,
-		   const struct in6_addr *src_addr)
+bool inet6_mc_check(struct sock *sk, const struct in6_addr *mc_addr,
+		    const struct in6_addr *src_addr)
 {
 	struct ipv6_pinfo *np = inet6_sk(sk);
 	struct ipv6_mc_socklist *mc;
 	struct ip6_sf_socklist *psl;
-	int rv = 1;
+	bool rv = true;
 
 	rcu_read_lock();
 	for_each_pmc_rcu(np, mc) {
@@ -621,7 +621,7 @@ int inet6_mc_check(struct sock *sk, const struct in6_addr *mc_addr,
 	}
 	if (!mc) {
 		rcu_read_unlock();
-		return 1;
+		return true;
 	}
 	read_lock(&mc->sflock);
 	psl = mc->sflist;
@@ -635,9 +635,9 @@ int inet6_mc_check(struct sock *sk, const struct in6_addr *mc_addr,
 				break;
 		}
 		if (mc->sfmode == MCAST_INCLUDE && i >= psl->sl_count)
-			rv = 0;
+			rv = false;
 		if (mc->sfmode == MCAST_EXCLUDE && i < psl->sl_count)
-			rv = 0;
+			rv = false;
 	}
 	read_unlock(&mc->sflock);
 	rcu_read_unlock();
@@ -931,15 +931,15 @@ int ipv6_dev_mc_dec(struct net_device *dev, const struct in6_addr *addr)
 /*
  * identify MLD packets for MLD filter exceptions
  */
-int ipv6_is_mld(struct sk_buff *skb, int nexthdr)
+bool ipv6_is_mld(struct sk_buff *skb, int nexthdr)
 {
 	struct icmp6hdr *pic;
 
 	if (nexthdr != IPPROTO_ICMPV6)
-		return 0;
+		return false;
 
 	if (!pskb_may_pull(skb, sizeof(struct icmp6hdr)))
-		return 0;
+		return false;
 
 	pic = icmp6_hdr(skb);
 
@@ -948,22 +948,22 @@ int ipv6_is_mld(struct sk_buff *skb, int nexthdr)
 	case ICMPV6_MGM_REPORT:
 	case ICMPV6_MGM_REDUCTION:
 	case ICMPV6_MLD2_REPORT:
-		return 1;
+		return true;
 	default:
 		break;
 	}
-	return 0;
+	return false;
 }
 
 /*
  *	check if the interface/address pair is valid
  */
-int ipv6_chk_mcast_addr(struct net_device *dev, const struct in6_addr *group,
-			const struct in6_addr *src_addr)
+bool ipv6_chk_mcast_addr(struct net_device *dev, const struct in6_addr *group,
+			 const struct in6_addr *src_addr)
 {
 	struct inet6_dev *idev;
 	struct ifmcaddr6 *mc;
-	int rv = 0;
+	bool rv = false;
 
 	rcu_read_lock();
 	idev = __in6_dev_get(dev);
@@ -990,7 +990,7 @@ int ipv6_chk_mcast_addr(struct net_device *dev, const struct in6_addr *group,
 					rv = mc->mca_sfcount[MCAST_EXCLUDE] !=0;
 				spin_unlock_bh(&mc->mca_lock);
 			} else
-				rv = 1; /* don't filter unspecified source */
+				rv = true; /* don't filter unspecified source */
 		}
 		read_unlock_bh(&idev->lock);
 	}
@@ -1046,8 +1046,8 @@ static void igmp6_group_queried(struct ifmcaddr6 *ma, unsigned long resptime)
 }
 
 /* mark EXCLUDE-mode sources */
-static int mld_xmarksources(struct ifmcaddr6 *pmc, int nsrcs,
-	const struct in6_addr *srcs)
+static bool mld_xmarksources(struct ifmcaddr6 *pmc, int nsrcs,
+			     const struct in6_addr *srcs)
 {
 	struct ip6_sf_list *psf;
 	int i, scount;
@@ -1070,12 +1070,12 @@ static int mld_xmarksources(struct ifmcaddr6 *pmc, int nsrcs,
 	}
 	pmc->mca_flags &= ~MAF_GSQUERY;
 	if (scount == nsrcs)	/* all sources excluded */
-		return 0;
-	return 1;
+		return false;
+	return true;
 }
 
-static int mld_marksources(struct ifmcaddr6 *pmc, int nsrcs,
-	const struct in6_addr *srcs)
+static bool mld_marksources(struct ifmcaddr6 *pmc, int nsrcs,
+			    const struct in6_addr *srcs)
 {
 	struct ip6_sf_list *psf;
 	int i, scount;
@@ -1099,10 +1099,10 @@ static int mld_marksources(struct ifmcaddr6 *pmc, int nsrcs,
 	}
 	if (!scount) {
 		pmc->mca_flags &= ~MAF_GSQUERY;
-		return 0;
+		return false;
 	}
 	pmc->mca_flags |= MAF_GSQUERY;
-	return 1;
+	return true;
 }
 
 /* called with rcu_read_lock() */
@@ -1276,17 +1276,17 @@ int igmp6_event_report(struct sk_buff *skb)
 	return 0;
 }
 
-static int is_in(struct ifmcaddr6 *pmc, struct ip6_sf_list *psf, int type,
-	int gdeleted, int sdeleted)
+static bool is_in(struct ifmcaddr6 *pmc, struct ip6_sf_list *psf, int type,
+		  int gdeleted, int sdeleted)
 {
 	switch (type) {
 	case MLD2_MODE_IS_INCLUDE:
 	case MLD2_MODE_IS_EXCLUDE:
 		if (gdeleted || sdeleted)
-			return 0;
+			return false;
 		if (!((pmc->mca_flags & MAF_GSQUERY) && !psf->sf_gsresp)) {
 			if (pmc->mca_sfmode == MCAST_INCLUDE)
-				return 1;
+				return true;
 			/* don't include if this source is excluded
 			 * in all filters
 			 */
@@ -1295,29 +1295,29 @@ static int is_in(struct ifmcaddr6 *pmc, struct ip6_sf_list *psf, int type,
 			return pmc->mca_sfcount[MCAST_EXCLUDE] ==
 				psf->sf_count[MCAST_EXCLUDE];
 		}
-		return 0;
+		return false;
 	case MLD2_CHANGE_TO_INCLUDE:
 		if (gdeleted || sdeleted)
-			return 0;
+			return false;
 		return psf->sf_count[MCAST_INCLUDE] != 0;
 	case MLD2_CHANGE_TO_EXCLUDE:
 		if (gdeleted || sdeleted)
-			return 0;
+			return false;
 		if (pmc->mca_sfcount[MCAST_EXCLUDE] == 0 ||
 		    psf->sf_count[MCAST_INCLUDE])
-			return 0;
+			return false;
 		return pmc->mca_sfcount[MCAST_EXCLUDE] ==
 			psf->sf_count[MCAST_EXCLUDE];
 	case MLD2_ALLOW_NEW_SOURCES:
 		if (gdeleted || !psf->sf_crcount)
-			return 0;
+			return false;
 		return (pmc->mca_sfmode == MCAST_INCLUDE) ^ sdeleted;
 	case MLD2_BLOCK_OLD_SOURCES:
 		if (pmc->mca_sfmode == MCAST_INCLUDE)
 			return gdeleted || (psf->sf_crcount && sdeleted);
 		return psf->sf_crcount && !gdeleted && !sdeleted;
 	}
-	return 0;
+	return false;
 }
 
 static int
diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c
index c7a27ac..54f62d3 100644
--- a/net/ipv6/ndisc.c
+++ b/net/ipv6/ndisc.c
@@ -348,7 +348,7 @@ static int ndisc_constructor(struct neighbour *neigh)
 	struct net_device *dev = neigh->dev;
 	struct inet6_dev *in6_dev;
 	struct neigh_parms *parms;
-	int is_multicast = ipv6_addr_is_multicast(addr);
+	bool is_multicast = ipv6_addr_is_multicast(addr);
 
 	in6_dev = in6_dev_get(dev);
 	if (in6_dev == NULL) {
@@ -725,7 +725,7 @@ static void ndisc_recv_ns(struct sk_buff *skb)
 	struct inet6_dev *idev = NULL;
 	struct neighbour *neigh;
 	int dad = ipv6_addr_any(saddr);
-	int inc;
+	bool inc;
 	int is_router = -1;
 
 	if (ipv6_addr_is_multicast(&msg->target)) {
diff --git a/net/ipv6/raw.c b/net/ipv6/raw.c
index 5bddea7..93d6983 100644
--- a/net/ipv6/raw.c
+++ b/net/ipv6/raw.c
@@ -72,7 +72,7 @@ static struct sock *__raw_v6_lookup(struct net *net, struct sock *sk,
 		const struct in6_addr *rmt_addr, int dif)
 {
 	struct hlist_node *node;
-	int is_multicast = ipv6_addr_is_multicast(loc_addr);
+	bool is_multicast = ipv6_addr_is_multicast(loc_addr);
 
 	sk_for_each_from(sk, node)
 		if (inet_sk(sk)->inet_num == num) {
@@ -153,12 +153,12 @@ EXPORT_SYMBOL(rawv6_mh_filter_unregister);
  *
  *	Caller owns SKB so we must make clones.
  */
-static int ipv6_raw_deliver(struct sk_buff *skb, int nexthdr)
+static bool ipv6_raw_deliver(struct sk_buff *skb, int nexthdr)
 {
 	const struct in6_addr *saddr;
 	const struct in6_addr *daddr;
 	struct sock *sk;
-	int delivered = 0;
+	bool delivered = false;
 	__u8 hash;
 	struct net *net;
 
@@ -179,7 +179,7 @@ static int ipv6_raw_deliver(struct sk_buff *skb, int nexthdr)
 	while (sk) {
 		int filtered;
 
-		delivered = 1;
+		delivered = true;
 		switch (nexthdr) {
 		case IPPROTO_ICMPV6:
 			filtered = icmpv6_filter(sk, skb);
@@ -225,7 +225,7 @@ out:
 	return delivered;
 }
 
-int raw6_local_deliver(struct sk_buff *skb, int nexthdr)
+bool raw6_local_deliver(struct sk_buff *skb, int nexthdr)
 {
 	struct sock *raw_sk;
 
diff --git a/net/ipv6/route.c b/net/ipv6/route.c
index 90119a3..999a982 100644
--- a/net/ipv6/route.c
+++ b/net/ipv6/route.c
@@ -333,22 +333,22 @@ static void ip6_dst_ifdown(struct dst_entry *dst, struct net_device *dev,
 	}
 }
 
-static __inline__ int rt6_check_expired(const struct rt6_info *rt)
+static bool rt6_check_expired(const struct rt6_info *rt)
 {
 	struct rt6_info *ort = NULL;
 
 	if (rt->rt6i_flags & RTF_EXPIRES) {
 		if (time_after(jiffies, rt->dst.expires))
-			return 1;
+			return true;
 	} else if (rt->dst.from) {
 		ort = (struct rt6_info *) rt->dst.from;
 		return (ort->rt6i_flags & RTF_EXPIRES) &&
 			time_after(jiffies, ort->dst.expires);
 	}
-	return 0;
+	return false;
 }
 
-static inline int rt6_need_strict(const struct in6_addr *daddr)
+static bool rt6_need_strict(const struct in6_addr *daddr)
 {
 	return ipv6_addr_type(daddr) &
 		(IPV6_ADDR_MULTICAST | IPV6_ADDR_LINKLOCAL | IPV6_ADDR_LOOPBACK);

^ permalink raw reply related

* Re: inconsistent null checking in ipx_ioctl()
From: David Miller @ 2012-05-19  4:51 UTC (permalink / raw)
  To: dan.carpenter; +Cc: netdev
In-Reply-To: <20120514205618.GB20836@elgon.mountain>

From: Dan Carpenter <dan.carpenter@oracle.com>
Date: Mon, 14 May 2012 23:56:18 +0300

> Hi, I'm working on some new Smatch stuff and going through some warnings
> in old code.
> 
> ----
> This is a semi-automatic email about new static checker warnings.
> 
> The patch b0d0d915d1d1: "ipx: remove the BKL" from Jan 25, 2011, 
> leads to the following Smatch complaint:
> 
> net/ipx/af_ipx.c:1928 ipx_ioctl()
> 	 error: we previously assumed 'sk' could be null (see line 1913)

Thanks Dan, I've commited the following:

--------------------
ipx: Remove spurious NULL checking in ipx_ioctl().

We already unconditionally dereference 'sk' via lock_sock(sk) earlier
in this function, and our caller (sock_do_ioctl()) makes takes similar
liberties.

Reported-by: Dan Carpenter <dan.carpenter@oracle.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
---
 net/ipx/af_ipx.c |    4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/net/ipx/af_ipx.c b/net/ipx/af_ipx.c
index 824d4a3..dfd6faa 100644
--- a/net/ipx/af_ipx.c
+++ b/net/ipx/af_ipx.c
@@ -1901,9 +1901,7 @@ static int ipx_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
 			      (const unsigned short __user *)argp);
 		break;
 	case SIOCGSTAMP:
-		rc = -EINVAL;
-		if (sk)
-			rc = sock_get_timestamp(sk, argp);
+		rc = sock_get_timestamp(sk, argp);
 		break;
 	case SIOCGIFDSTADDR:
 	case SIOCSIFDSTADDR:
-- 
1.7.10.1

^ permalink raw reply related

* Re: ppp/l2tp doing oversized allocations ?
From: David Miller @ 2012-05-19  4:46 UTC (permalink / raw)
  To: davej; +Cc: netdev, kernel-team, edumazet
In-Reply-To: <20120514162923.GA4439@redhat.com>

From: Dave Jones <davej@redhat.com>
Date: Mon, 14 May 2012 12:29:23 -0400

> We just got this trace from reported by a Fedora user running 3.3.4
> 
> :WARNING: at mm/page_alloc.c:2204 __alloc_pages_nodemask+0x231/0x8f0()
> :Call Trace:
> : [<ffffffff81057abf>] warn_slowpath_common+0x7f/0xc0
> : [<ffffffff81057b1a>] warn_slowpath_null+0x1a/0x20
> : [<ffffffff81129671>] __alloc_pages_nodemask+0x231/0x8f0
> : [<ffffffff814e84db>] ? dev_queue_xmit+0x1db/0x640
> : [<ffffffff8151f210>] ? ip_forward_options+0x1f0/0x1f0
> : [<ffffffff814ef7a1>] ? neigh_direct_output+0x11/0x20
> : [<ffffffff81520dee>] ? ip_finish_output+0x17e/0x2f0
> : [<ffffffff8151f210>] ? ip_forward_options+0x1f0/0x1f0
> : [<ffffffff811608d3>] alloc_pages_current+0xa3/0x110
> : [<ffffffff811254b4>] __get_free_pages+0x14/0x50
> : [<ffffffff8116b99f>] kmalloc_order_trace+0x3f/0xd0
> : [<ffffffff8156d137>] ? xfrm4_output_finish+0x27/0x40
> : [<ffffffff8116c8c7>] __kmalloc+0x177/0x1a0
> : [<ffffffff81521196>] ? ip_queue_xmit+0x156/0x400
> : [<ffffffff814dab07>] pskb_expand_head+0x87/0x310
> : [<ffffffff8113dbf9>] ? __mod_zone_page_state+0x49/0x50
> : [<ffffffffa05e84dd>] pppol2tp_xmit+0x1ed/0x220 [l2tp_ppp]

So it's ESP encapsulated IPSEC over L2tp.

Eric, I wonder if session->hdr_len can take on undesirable values and
thus trip up the skb COW'ing calculations you added?

^ permalink raw reply

* Re: [PATCH net-next] ipv6: ip6_fragment() should check CHECKSUM_PARTIAL
From: David Miller @ 2012-05-19  3:54 UTC (permalink / raw)
  To: eric.dumazet; +Cc: netdev, tore
In-Reply-To: <1337374935.7029.60.camel@edumazet-glaptop>

From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Fri, 18 May 2012 23:02:15 +0200

> From: Eric Dumazet <edumazet@google.com>
> 
> Quoting Tore Anderson from :
> 
> If the allfrag feature has been set on a host route (due to an ICMPv6
> Packet Too Big received indicating a MTU of less than 1280),
> TCP SYN/ACK packets to that destination appears to get an incorrect
> TCP checksum. This in turn means they are thrown away as invalid.
> 
> In the case of an IPv4 client behind a link with a MTU of less than
> 1260, accessing an IPv6 server through a stateless translator,
> this means that the client can only download a single large file
> from the server, because once it is in the server's routing cache
> with the allfrag feature set, new TCP connections can no longer
> be established.
> 
> </endquote>
> 
> It appears ip6_fragment() doesn't handle CHECKSUM_PARTIAL properly.
> 
> As network drivers are not prepared to fetch correct transport header, a
> safe fix is to call skb_checksum_help() before fragmenting packet.
> 
> Reported-by: Tore Anderson <tore@fud.no>
> Signed-off-by: Eric Dumazet <edumazet@google.com>
> Tested-by: Tore Anderson <tore@fud.no>

Applied, thanks.

^ permalink raw reply

* Re: [PATCH net-next] drivers/net: delete old 8bit ISA 3c501 driver.
From: David Miller @ 2012-05-19  3:54 UTC (permalink / raw)
  To: paul.gortmaker; +Cc: netdev, alan
In-Reply-To: <1337362769-4676-1-git-send-email-paul.gortmaker@windriver.com>

From: Paul Gortmaker <paul.gortmaker@windriver.com>
Date: Fri, 18 May 2012 13:39:29 -0400

> It was amusing that linux was able to make use of this 1980's
> technology on machines long past its intended lifespan, but
> it probably should go now -- it is causing issues in some
> distros[1], and while that might be fixable, it is just not
> worth it.
> 
> To set the context, the 3c501 was designed in the 1980's to be
> used on 8088 PC-XT 8bit ISA machines.  It was built using
> discrete TTL components and truly looks like a relic of the past.
> 
> But from a functional point of view, the real issue, as stated
> in the (also obsolete) Ethernet-HowTo, is that "...the 3c501 can
> only do one thing at a time -- while you are removing one packet
> from the single-packet buffer it cannot receive another packet,
> nor can it receive a packet while loading a transmit packet."
> 
> You know things are not good when the Kconfig help text suggests
> you make a cron job doing a ping every minute.
> 
> Hardware that old and crippled is simply not going to be used by
> anyone in a time where 10 year old 100Mbit PCI cards (that are
> still functional) are largely give-away items.
> 
> [1] http://www.linuxquestions.org/questions/linux-networking-3/3com-3c501-card-not-detecting-934344/
> 
> Cc: Alan Cox <alan@linux.intel.com>
> Signed-off-by: Paul Gortmaker <paul.gortmaker@windriver.com>

Alan, any objections?

^ permalink raw reply

* Re: [PATCH net-next 0/5] cirrus: cs89x0: Neatening
From: David Miller @ 2012-05-19  3:53 UTC (permalink / raw)
  To: joe; +Cc: netdev, jaccon.bastiaansen, linux-kernel
In-Reply-To: <cover.1337381533.git.joe@perches.com>

From: Joe Perches <joe@perches.com>
Date: Fri, 18 May 2012 15:56:26 -0700

> Yeah, some might consider it gratuitous.
> I think it's cleaner now though.
> 
> Joe Perches (5):
>   cirrus: cs89x0: Code style neatening
>   cirrus: cs89x0: Convert printks to pr_<level>
>   cirrus: cs89x0: Code neatening
>   cirrus: cs89x0: Neaten debugging and logging
>   cirrus: cs89x0: Remove function prototypes and reorder declarations

Series applied, thanks joe.

^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox