Netdev List
 help / color / mirror / Atom feed
* [PATCH net-2.6 1/5] bnx2x: Don't prevent RSS configuration in INT#x and MSI interrupt modes.
From: Vladislav Zolotarov @ 2011-01-09 12:19 UTC (permalink / raw)
  To: Dave Miller; +Cc: netdev list, Eilon Greenstein

Don't prevent RSS configuration in INT#x and MSI interrupt modes. Otherwise
Rx hash key won't be available.

Signed-off-by: Vladislav Zolotarov <vladz@broadcom.com>
Signed-off-by: Eilon Greenstein <eilong@broadcom.com>
---
 drivers/net/bnx2x/bnx2x_main.c |    7 -------
 1 files changed, 0 insertions(+), 7 deletions(-)

diff --git a/drivers/net/bnx2x/bnx2x_main.c b/drivers/net/bnx2x/bnx2x_main.c
index 9709b85..972b957 100644
--- a/drivers/net/bnx2x/bnx2x_main.c
+++ b/drivers/net/bnx2x/bnx2x_main.c
@@ -8382,13 +8382,6 @@ static int __devinit bnx2x_init_bp(struct bnx2x *bp)
 		dev_err(&bp->pdev->dev, "MCP disabled, "
 					"must load devices in order!\n");
 
-	/* Set multi queue mode */
-	if ((multi_mode != ETH_RSS_MODE_DISABLED) &&
-	    ((int_mode == INT_MODE_INTx) || (int_mode == INT_MODE_MSI))) {
-		dev_err(&bp->pdev->dev, "Multi disabled since int_mode "
-					"requested is not MSI-X\n");
-		multi_mode = ETH_RSS_MODE_DISABLED;
-	}
 	bp->multi_mode = multi_mode;
 	bp->int_mode = int_mode;
 
-- 
1.7.0.4





^ permalink raw reply related

* Re: 2.6.37 vlans on bnx2 not functional, panic with tcpdump
From: Iain Paton @ 2011-01-09 11:22 UTC (permalink / raw)
  To: Jarek Poplawski
  Cc: Michael Chan, netdev@vger.kernel.org,
	linux-kernel@vger.kernel.org
In-Reply-To: <4D28AFD1.3020808@gmail.com>

Jarek Poplawski wrote:
> Iain Paton wrote:
> ...
>> So you can consider any bnx2 cause for this closed. I'll get back to the
>> list if I can come up with any more useful info.
> 
> Hi Iain,
> If it's not a problem, please try if the attached debugging patch
> (not tested) can change anything.

No problem testing with the patch installed, however I'm now unable to duplicate the problem with a rebuilt kernel, with or without 
the patch.

The original kernel build I did still fails repeatably, but something as simple as erasing the directory, unpacking the same source 
tarball and re-compiling using the same config file gets me a working kernel.

This is somewhat troubling as there must have been some initial cause, but I'm unable to pin it down. Have spent the last day or so 
checking toolchain versions, running hardware tests on the physical build server and have come up completely empty.

I think we can safely ignore this now as it appears to be a one-off bad compile, for reasons unknown, but totally unrepeatable.

Thanks to all for your help, and apologies for the noise.

Iain

^ permalink raw reply

* Re: [PATCH net-next-2.6 v3 1/1] can: c_can: Added support for Bosch C_CAN controller
From: Oliver Hartkopp @ 2011-01-09 11:01 UTC (permalink / raw)
  To: Wolfgang Grandegger, Tomoya MORINAGA, Bhupesh Sharma
  Cc: Socketcan-core-0fE9KPoRgkgATYTw5x5z8w,
	netdev-u79uwXL29TY76Z2rM5mHXA, Marc Kleine-Budde, David Miller
In-Reply-To: <4D262158.4030301-5Yr1BZd7O62+XT7JhA+gdA@public.gmane.org>

On 06.01.2011 21:08, Wolfgang Grandegger wrote:
> Hi Marc,
> 
> On 01/06/2011 08:44 PM, Marc Kleine-Budde wrote:

>> If this driver will be merged, we'll have two drivers for the same can
>> core in the tree. The other one is the pch_can. What do you think should
>> be the mid term perspective for ccan based hardware?
> 
> Yes, I know. Unfortunately, we did realize rather late the the PCH
> controller is a C_CAN clone and the OKI/Intel ppls did not tell us
> either. Therefore I asked Bhupesh to provide a SJA1000-a-like interface
> for the C_CAN, which would allow us to provide an alternative PCI driver
> "pch_pci.c" for the PCH. If that driver works well on the PCH hardware
> as well, we should merge the best of both, if necessary, and then
> finally remove the pch_can driver. Would that be a reasonable proposal.

At least for me this looks great. The idea to have a similar approach as we
successfully implemented for the sja1000 will solve future hardware
implementations based on the ccan controller core.

BTW. for the next submission of Bhupeshs patchset, i would propose to name the
driver 'ccan' instead of 'c_can', so that we have a

    linux/drivers/net/can/ccan/...

path.

Checking directory names in linux/drivers with

    find . -type d | grep '_'

driver names with underscores are pretty unusual and mostly selected without
fortune:

./staging/olpc_dcon
./staging/wlags49_h2
./staging/wlags49_h2/man
./staging/serqt_usb2
./staging/intel_sst
./staging/quatech_usb2
./staging/asus_oled
./staging/wlags49_h25
./staging/ath6kl/hif/sdio/linux_sdio             <- Ugh!
./staging/ath6kl/hif/sdio/linux_sdio/src
./staging/ath6kl/hif/sdio/linux_sdio/include
./net/pch_gbe
./net/fs_enet
./net/wireless/libertas_tf
./net/ibm_newemacds

For that reason i would prefer 'ccan' to name this driver core.

Best regards,
Oliver

^ permalink raw reply

* Re: [PATCH]netdev: add driver for enc424j600 ethernet chip on SPI bus
From: Balaji Venkatachalam @ 2011-01-09  9:00 UTC (permalink / raw)
  To: Michał Mirosław
  Cc: netdev, mohan, blue.cube, lanconelli.claudio, Sriram Subramanian
In-Reply-To: <AANLkTinosxXKgfkqGKqCLGi8tWeP4xnT1P3kMRu51CvS@mail.gmail.com>

Thanks for the comments. I am working on them. Will post the updated patch soon.

^ permalink raw reply

* [PATCH 6/6] net: fix kernel-doc warning in core/filter.c
From: Randy Dunlap @ 2011-01-09  3:41 UTC (permalink / raw)
  To: netdev; +Cc: Linus, davem

From: Randy Dunlap <randy.dunlap@oracle.com>

Fix new kernel-doc notation warning in net/core/filter.c:

Warning(net/core/filter.c:172): No description found for parameter 'fentry'
Warning(net/core/filter.c:172): Excess function parameter 'filter' description in 'sk_run_filter'

Signed-off-by: Randy Dunlap <randy.dunlap@oracle.com>
---
 net/core/filter.c |    2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

--- lnx0107.orig/net/core/filter.c
+++ lnx0107/net/core/filter.c
@@ -158,7 +158,7 @@ EXPORT_SYMBOL(sk_filter);
 /**
  *	sk_run_filter - run a filter on a socket
  *	@skb: buffer to run the filter on
- *	@filter: filter to apply
+ *	@fentry: filter to apply
  *
  * Decode and apply filter instructions to the skb->data.
  * Return length to keep, 0 for none. @skb is the data we are

^ permalink raw reply

* [PATCH 4/6] net/sock.h: make some fields private to fix kernel-doc warning(s)
From: Randy Dunlap @ 2011-01-09  3:39 UTC (permalink / raw)
  To: lkml, Linus; +Cc: netdev, davem

From: Randy Dunlap <randy.dunlap@oracle.com>

Fix new kernel-doc notation warning in sock.h by annotating skc_dontcopy_*
as private fields.

Warning(include/net/sock.h:163): No description found for parameter 'skc_dontcopy_end[0]'

Signed-off-by: Randy Dunlap <randy.dunlap@oracle.com>
---
 include/net/sock.h |    4 ++++
 1 file changed, 4 insertions(+)

--- lnx0107.orig/include/net/sock.h
+++ lnx0107/include/net/sock.h
@@ -152,14 +152,18 @@ struct sock_common {
 	 * fields between dontcopy_begin/dontcopy_end
 	 * are not copied in sock_copy()
 	 */
+	/* private: */
 	int			skc_dontcopy_begin[0];
+	/* public: */
 	union {
 		struct hlist_node	skc_node;
 		struct hlist_nulls_node skc_nulls_node;
 	};
 	int			skc_tx_queue_mapping;
 	atomic_t		skc_refcnt;
+	/* private: */
 	int                     skc_dontcopy_end[0];
+	/* public: */
 };
 
 /**

^ permalink raw reply

* Re: [PATCH 3/5] NET: IPV4: ARP: allow to invalidate specific ARP entries
From: Maxim Levitsky @ 2011-01-08 23:57 UTC (permalink / raw)
  To: Eric Dumazet
  Cc: linux1394-devel, Stefan Richter, netdev, David S. Miller,
	Alexey Kuznetsov, James Morris, Patrick McHardy
In-Reply-To: <1294405062.3306.11.camel@edumazet-laptop>

On Fri, 2011-01-07 at 13:57 +0100, Eric Dumazet wrote:
> Le vendredi 07 janvier 2011 à 14:47 +0200, Maxim Levitsky a écrit :
> > On Mon, 2010-11-29 at 04:09 +0200, Maxim Levitsky wrote:
> > > IPv4 over firewire needs to be able to remove ARP entries
> > > from the ARP cache that belong to nodes that are removed, because
> > > IPv4 over firewire uses ARP packets for private information
> > > about nodes.
> > > 
> > > This information becomes invalid as soon as node drops
> > > off the bus and when it reconnects, its only possible
> > > to start takling to is after it responded to an ARP packet.
> > > But ARP cache prevents such packets from being sent.
> > > 
> > > CC: netdev@vger.kernel.org
> > > CC: "David S. Miller" <davem@davemloft.net>
> > > CC: Alexey Kuznetsov <kuznet@ms2.inr.ac.ru>
> > > CC: James Morris <jmorris@namei.org>
> > > CC: Patrick McHardy <kaber@trash.net>
> > 
> > Anybody?
> > 
> > Best regards,
> > 	Maxim Levitsky
> > 
> > > 
> > > 
> > > Signed-off-by: Maxim Levitsky <maximlevitsky@gmail.com>
> > > ---
> > >  include/net/arp.h |    1 +
> > >  net/ipv4/arp.c    |   29 ++++++++++++++++++-----------
> > >  2 files changed, 19 insertions(+), 11 deletions(-)
> > > 
> > > diff --git a/include/net/arp.h b/include/net/arp.h
> > > index f4cf6ce..91f0568 100644
> > > --- a/include/net/arp.h
> > > +++ b/include/net/arp.h
> > > @@ -25,5 +25,6 @@ extern struct sk_buff *arp_create(int type, int ptype, __be32 dest_ip,
> > >  				  const unsigned char *src_hw,
> > >  				  const unsigned char *target_hw);
> > >  extern void arp_xmit(struct sk_buff *skb);
> > > +int arp_invalidate(struct net_device *dev, __be32 ip);
> > >  
> > >  #endif	/* _ARP_H */
> > > diff --git a/net/ipv4/arp.c b/net/ipv4/arp.c
> > > index d8e540c..35b1272 100644
> > > --- a/net/ipv4/arp.c
> > > +++ b/net/ipv4/arp.c
> > > @@ -1142,6 +1142,23 @@ static int arp_req_get(struct arpreq *r, struct net_device *dev)
> > >  	return err;
> > >  }
> > >  
> > > +int arp_invalidate(struct net_device *dev, __be32 ip)
> > > +{
> > > +	int err = -ENXIO;
> > > +	struct neighbour *neigh = neigh_lookup(&arp_tbl, &ip, dev);
> > > +
> > > +	if (neigh) {
> > > +		if (neigh->nud_state & ~NUD_NOARP)
> > > +			err = neigh_update(neigh, NULL, NUD_FAILED,
> > > +					   NEIGH_UPDATE_F_OVERRIDE|
> > > +					   NEIGH_UPDATE_F_ADMIN);
> > > +		neigh_release(neigh);
> > > +	}
> > > +
> > > +	return err;
> > > +}
> > > +EXPORT_SYMBOL(arp_invalidate);
> > > +
> > >  static int arp_req_delete_public(struct net *net, struct arpreq *r,
> > >  		struct net_device *dev)
> > >  {
> > > @@ -1162,7 +1179,6 @@ static int arp_req_delete(struct net *net, struct arpreq *r,
> > >  {
> > >  	int err;
> > >  	__be32 ip;
> > > -	struct neighbour *neigh;
> > >  
> > >  	if (r->arp_flags & ATF_PUBL)
> > >  		return arp_req_delete_public(net, r, dev);
> > > @@ -1180,16 +1196,7 @@ static int arp_req_delete(struct net *net, struct arpreq *r,
> > >  		if (!dev)
> > >  			return -EINVAL;
> > >  	}
> > > -	err = -ENXIO;
> > > -	neigh = neigh_lookup(&arp_tbl, &ip, dev);
> > > -	if (neigh) {
> > > -		if (neigh->nud_state & ~NUD_NOARP)
> > > -			err = neigh_update(neigh, NULL, NUD_FAILED,
> > > -					   NEIGH_UPDATE_F_OVERRIDE|
> > > -					   NEIGH_UPDATE_F_ADMIN);
> > > -		neigh_release(neigh);
> > > -	}
> > > -	return err;
> > > +	return arp_invalidate(dev, ip);
> > >  }
> > >  
> > >  /*
> > 
> 
> Hi Maxim
> 
> You were supposed to respin your patch after my commit :
> 
> (941666c2e3e0f9f6a1 net: RCU conversion of dev_getbyhwaddr() and
> arp_ioctl())
> 
> Thanks

Hi,

After looking at the code (and honestly its hard to work with it as it
has no documentation at all), I think I don't need any changes in my
patch.

Here is the latest version for I use with the above commit applied (it
is in mainline now).

---

commit 7da91d68d78b6a44ba6337be3b29b22ba2909b9e
Author: Maxim Levitsky <maximlevitsky@gmail.com>
Date:   Sat Nov 27 00:50:45 2010 +0200

    NET: IPV4: ARP: allow to invalidate specific ARP entries
    
    IPv4 over firewire needs to be able to remove ARP entries
    from the ARP cache that belong to nodes that are removed, because
    IPv4 over firewire uses ARP packets for private information
    about nodes.
    
    This information becomes invalid as soon as node drops
    off the bus and when it reconnects, its only possible
    to start takling to is after it responded to an ARP packet.
    But ARP cache prevents such packets from being sent.
    
    CC: netdev@vger.kernel.org
    CC: "David S. Miller" <davem@davemloft.net>
    CC: Alexey Kuznetsov <kuznet@ms2.inr.ac.ru>
    CC: James Morris <jmorris@namei.org>
    CC: Patrick McHardy <kaber@trash.net>
    
    
    Signed-off-by: Maxim Levitsky <maximlevitsky@gmail.com>

diff --git a/include/net/arp.h b/include/net/arp.h
index f4cf6ce..91f0568 100644
--- a/include/net/arp.h
+++ b/include/net/arp.h
@@ -25,5 +25,6 @@ extern struct sk_buff *arp_create(int type, int ptype, __be32 dest_ip,
 				  const unsigned char *src_hw,
 				  const unsigned char *target_hw);
 extern void arp_xmit(struct sk_buff *skb);
+int arp_invalidate(struct net_device *dev, __be32 ip);
 
 #endif	/* _ARP_H */
diff --git a/net/ipv4/arp.c b/net/ipv4/arp.c
index a2fc7b9..e941c75 100644
--- a/net/ipv4/arp.c
+++ b/net/ipv4/arp.c
@@ -1143,6 +1143,23 @@ static int arp_req_get(struct arpreq *r, struct net_device *dev)
 	return err;
 }
 
+int arp_invalidate(struct net_device *dev, __be32 ip)
+{
+	int err = -ENXIO;
+	struct neighbour *neigh = neigh_lookup(&arp_tbl, &ip, dev);
+
+	if (neigh) {
+		if (neigh->nud_state & ~NUD_NOARP)
+			err = neigh_update(neigh, NULL, NUD_FAILED,
+					   NEIGH_UPDATE_F_OVERRIDE|
+					   NEIGH_UPDATE_F_ADMIN);
+		neigh_release(neigh);
+	}
+
+	return err;
+}
+EXPORT_SYMBOL(arp_invalidate);
+
 static int arp_req_delete_public(struct net *net, struct arpreq *r,
 		struct net_device *dev)
 {
@@ -1163,7 +1180,6 @@ static int arp_req_delete(struct net *net, struct arpreq *r,
 {
 	int err;
 	__be32 ip;
-	struct neighbour *neigh;
 
 	if (r->arp_flags & ATF_PUBL)
 		return arp_req_delete_public(net, r, dev);
@@ -1181,16 +1197,7 @@ static int arp_req_delete(struct net *net, struct arpreq *r,
 		if (!dev)
 			return -EINVAL;
 	}
-	err = -ENXIO;
-	neigh = neigh_lookup(&arp_tbl, &ip, dev);
-	if (neigh) {
-		if (neigh->nud_state & ~NUD_NOARP)
-			err = neigh_update(neigh, NULL, NUD_FAILED,
-					   NEIGH_UPDATE_F_OVERRIDE|
-					   NEIGH_UPDATE_F_ADMIN);
-		neigh_release(neigh);
-	}
-	return err;
+	return arp_invalidate(dev, ip);
 }
 
 /*





^ permalink raw reply related

* [PATCH v1] TCPCT socket API update to draft -02
From: William Allen Simpson @ 2011-01-08 22:07 UTC (permalink / raw)
  To: Linux Kernel Network Developers
In-Reply-To: <4D28D8EF.5010008@gmail.com>

[-- Attachment #1: Type: text/plain, Size: 581 bytes --]

Use most recently specified symbols of RFC-to-be-6013.

Permit setting either cookie or s_data or both (sequentially).

Allows different s_data limits for SYN and SYN_ACK.

Split the data value from socket option header, saving more than
1K of stack space in the handler by copying long data values
directly from user space into the kref block.

Signed-off-by: William.Allen.Simpson@gmail.com
---
  include/linux/tcp.h |   35 ++++++++++++++++-----
  net/ipv4/tcp.c      |   86 ++++++++++++++++++++++++++++++++++++--------------
  2 files changed, 89 insertions(+), 32 deletions(-)

[-- Attachment #2: TCPCT+API-02v1+2.6.37.patch --]
[-- Type: text/plain, Size: 7093 bytes --]

diff --git a/include/linux/tcp.h b/include/linux/tcp.h
index e64f4c6..ddfdd26 100644
--- a/include/linux/tcp.h
+++ b/include/linux/tcp.h
@@ -184,23 +184,42 @@ struct tcp_md5sig {
 #define TCP_COOKIE_MAX		16		/* 128-bits */
 #define TCP_COOKIE_PAIR_SIZE	(2*TCP_COOKIE_MAX)
 
+/* Implementation-specific data limits */
+#define TCP_SYN_DATA_LIMIT      (TCP_MSS_DEFAULT - sizeof(struct tcphdr))
+#define TCP_SYN_ACK_DATA_LIMIT  (TCP_MSS_DESIRED)
+
 /* Flags for both getsockopt and setsockopt */
-#define TCP_COOKIE_IN_ALWAYS	(1 << 0)	/* Discard SYN without cookie */
-#define TCP_COOKIE_OUT_NEVER	(1 << 1)	/* Prohibit outgoing cookies,
+#define TCPCT_IN_ALWAYS		(1 << 0)	/* Discard SYN without cookie */
+#define TCPCT_OUT_NEVER		(1 << 1)	/* Prohibit outgoing cookies,
 						 * supercedes everything. */
-
-/* Flags for getsockopt */
-#define TCP_S_DATA_IN		(1 << 2)	/* Was data received? */
-#define TCP_S_DATA_OUT		(1 << 3)	/* Was data sent? */
-
-/* TCP_COOKIE_TRANSACTIONS data */
+#define TCPCT_IN_DATA		(1 << 2)	/* Was data received? */
+#define TCPCT_OUT_DATA		(1 << 3)	/* Was data sent? */
+/* reserved for future use: bits 4 .. 6 */
+#define TCPCT_EXTEND		(1 << 7)
+
+/* Extended Option flags for both getsockopt and setsockopt */
+#define TCPCT_EXTEND_SIZE	(0x7)		/* mask */
+#define TCPCT_EXTEND_TS32	(0x1)		/* default */
+#define TCPCT_EXTEND_TS64	(0x2)
+#define TCPCT_EXTEND_TS128	(0x4)
+
+/* TCP_COOKIE_TRANSACTIONS socket option header */
 struct tcp_cookie_transactions {
 	__u16	tcpct_flags;			/* see above */
-	__u8	__tcpct_pad1;			/* zero */
+	__u8	tcpct_extended;
 	__u8	tcpct_cookie_desired;		/* bytes */
 	__u16	tcpct_s_data_desired;		/* bytes of variable data */
 	__u16	tcpct_used;			/* bytes in value */
-	__u8	tcpct_value[TCP_MSS_DEFAULT];
+};
+
+struct tcpct_full {
+	struct tcp_cookie_transactions soh;
+	__u8	tcpct_value[TCP_COOKIE_PAIR_SIZE];
+};
+
+struct tcpct_half {
+	struct tcp_cookie_transactions soh;
+	__u8	tcpct_value[TCP_COOKIE_MAX];
 };
 
 #ifdef __KERNEL__
diff --git a/net/ipv4/tcp.c b/net/ipv4/tcp.c
index 6c11eec..28dd6a1 100644
--- a/net/ipv4/tcp.c
+++ b/net/ipv4/tcp.c
@@ -2143,16 +2143,13 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
 	case TCP_COOKIE_TRANSACTIONS: {
 		struct tcp_cookie_transactions ctd;
 		struct tcp_cookie_values *cvp = NULL;
+		int s_data_used = 0;
 
 		if (sizeof(ctd) > optlen)
 			return -EINVAL;
 		if (copy_from_user(&ctd, optval, sizeof(ctd)))
 			return -EFAULT;
 
-		if (ctd.tcpct_used > sizeof(ctd.tcpct_value) ||
-		    ctd.tcpct_s_data_desired > TCP_MSS_DESIRED)
-			return -EINVAL;
-
 		if (ctd.tcpct_cookie_desired == 0) {
 			/* default to global value */
 		} else if ((0x1 & ctd.tcpct_cookie_desired) ||
@@ -2161,7 +2158,33 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
 			return -EINVAL;
 		}
 
-		if (TCP_COOKIE_OUT_NEVER & ctd.tcpct_flags) {
+		if (ctd.tcpct_used > 0) {
+			if (ctd.tcpct_used + sizeof(ctd) > optlen)
+				return -EINVAL;
+			if (TCPCT_OUT_DATA & ctd.tcpct_flags) {
+				if (ctd.tcpct_used > TCP_SYN_ACK_DATA_LIMIT)
+					return -EINVAL;
+				if (ctd.tcpct_s_data_desired > 0)
+					return -EINVAL;
+				s_data_used = ctd.tcpct_used;
+			} else {
+				if (ctd.tcpct_used > TCP_COOKIE_PAIR_SIZE)
+					return -EINVAL;
+				if (ctd.tcpct_used !=
+						ctd.tcpct_cookie_desired &&
+				    ctd.tcpct_used !=
+						ctd.tcpct_cookie_desired * 2)
+					return -EINVAL;
+				if (ctd.tcpct_s_data_desired >
+						TCP_SYN_DATA_LIMIT)
+					return -EINVAL;
+			}
+		} else if (TCPCT_OUT_DATA & ctd.tcpct_flags) {
+			/* unexpected flag without s_data */
+			return -EINVAL;
+		}
+
+		if (TCPCT_OUT_NEVER & ctd.tcpct_flags) {
 			/* Supercedes all other values */
 			lock_sock(sk);
 			if (tp->cookie_values != NULL) {
@@ -2177,12 +2200,12 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
 
 		/* Allocate ancillary memory before locking.
 		 */
-		if (ctd.tcpct_used > 0 ||
+		if (s_data_used > 0 ||
 		    (tp->cookie_values == NULL &&
 		     (sysctl_tcp_cookie_size > 0 ||
 		      ctd.tcpct_cookie_desired > 0 ||
 		      ctd.tcpct_s_data_desired > 0))) {
-			cvp = kzalloc(sizeof(*cvp) + ctd.tcpct_used,
+			cvp = kzalloc(sizeof(*cvp) + s_data_used,
 				      GFP_KERNEL);
 			if (cvp == NULL)
 				return -ENOMEM;
@@ -2191,7 +2214,7 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
 		}
 		lock_sock(sk);
 		tp->rx_opt.cookie_in_always =
-			(TCP_COOKIE_IN_ALWAYS & ctd.tcpct_flags);
+			(TCPCT_IN_ALWAYS & ctd.tcpct_flags);
 		tp->rx_opt.cookie_out_never = 0; /* false */
 
 		if (tp->cookie_values != NULL) {
@@ -2210,11 +2233,26 @@ static int do_tcp_setsockopt(struct sock *sk, int level,
 		if (cvp != NULL) {
 			cvp->cookie_desired = ctd.tcpct_cookie_desired;
 
-			if (ctd.tcpct_used > 0) {
-				memcpy(cvp->s_data_payload, ctd.tcpct_value,
-				       ctd.tcpct_used);
-				cvp->s_data_desired = ctd.tcpct_used;
+			if (s_data_used > 0) {
+				if (copy_from_user(cvp->s_data_payload,
+						   optval + sizeof(ctd),
+						   s_data_used)) {
+					kref_put(&cvp->kref,
+						 tcp_cookie_values_release);
+					return -EFAULT;
+				}
+				cvp->s_data_desired = s_data_used;
 				cvp->s_data_constant = 1; /* true */
+			} else if (ctd.tcpct_used > 0) {
+				if (copy_from_user(cvp->cookie_pair,
+						   optval + sizeof(ctd),
+						   ctd.tcpct_used)) {
+					kref_put(&cvp->kref,
+						 tcp_cookie_values_release);
+					return -EFAULT;
+				}
+				cvp->s_data_desired = ctd.tcpct_s_data_desired;
+				cvp->s_data_constant = 0; /* false */
 			} else {
 				/* No constant payload data. */
 				cvp->s_data_desired = ctd.tcpct_s_data_desired;
@@ -2574,7 +2612,7 @@ static int do_tcp_getsockopt(struct sock *sk, int level,
 		return 0;
 
 	case TCP_COOKIE_TRANSACTIONS: {
-		struct tcp_cookie_transactions ctd;
+		struct tcpct_full ctd;
 		struct tcp_cookie_values *cvp = tp->cookie_values;
 
 		if (get_user(len, optlen))
@@ -2583,23 +2621,23 @@ static int do_tcp_getsockopt(struct sock *sk, int level,
 			return -EINVAL;
 
 		memset(&ctd, 0, sizeof(ctd));
-		ctd.tcpct_flags = (tp->rx_opt.cookie_in_always ?
-				   TCP_COOKIE_IN_ALWAYS : 0)
-				| (tp->rx_opt.cookie_out_never ?
-				   TCP_COOKIE_OUT_NEVER : 0);
+		ctd.soh.tcpct_flags = (tp->rx_opt.cookie_in_always ?
+				       TCPCT_IN_ALWAYS : 0)
+				    | (tp->rx_opt.cookie_out_never ?
+				       TCPCT_OUT_NEVER : 0);
 
 		if (cvp != NULL) {
-			ctd.tcpct_flags |= (cvp->s_data_in ?
-					    TCP_S_DATA_IN : 0)
-					 | (cvp->s_data_out ?
-					    TCP_S_DATA_OUT : 0);
+			ctd.soh.tcpct_flags |= (cvp->s_data_in ?
+						TCPCT_IN_DATA : 0)
+					     | (cvp->s_data_out ?
+						TCPCT_OUT_DATA : 0);
 
-			ctd.tcpct_cookie_desired = cvp->cookie_desired;
-			ctd.tcpct_s_data_desired = cvp->s_data_desired;
+			ctd.soh.tcpct_cookie_desired = cvp->cookie_desired;
+			ctd.soh.tcpct_s_data_desired = cvp->s_data_desired;
 
 			memcpy(&ctd.tcpct_value[0], &cvp->cookie_pair[0],
 			       cvp->cookie_pair_size);
-			ctd.tcpct_used = cvp->cookie_pair_size;
+			ctd.soh.tcpct_used = cvp->cookie_pair_size;
 		}
 
 		if (put_user(sizeof(ctd), optlen))
-- 
1.7.1

^ permalink raw reply related

* TCPCT API update for 2.6.37
From: William Allen Simpson @ 2011-01-08 21:36 UTC (permalink / raw)
  To: Linux Kernel Network Developers

With the recent flurry of messages related to TCPCT, I devoted a nice
snowy Saturday afternoon to updating the socket option code.  Linux is
rather fair behind on TCPCT implementation, so this will help with
future software compatibility.

I'm not on this list, so anybody with comments should CC me.  Thanks.

^ permalink raw reply

* Re: [PATCH] iproute2: ip: add wilcard support for device matching
From: Philip Prindeville @ 2011-01-08 21:10 UTC (permalink / raw)
  To: hadi
  Cc: Vlad Dogaru, Octavian Purdila, Eric Dumazet, Stephen Hemminger,
	netdev, Lucian Adrian Grijincu
In-Reply-To: <1292937262.6535.15.camel@mojatatu>

On 12/21/10 5:14 AM, jamal wrote:
> On Mon, 2010-12-20 at 11:23 -0800, Vlad Dogaru wrote:
>
>> I'll try to implement this approach in the next few days.
> Excellent ;->  Remember, this is general purpose tag, sort
> like socket/route/skb->mark. It is upto the administrator to
> define its use via policy.
>
> cheers,
> jamal


Did that end up going anywhere?

There are a lot of cases where matching on "ppp*" would be handy.



^ permalink raw reply

* Re: Seeing transmit timeouts on 8139cp
From: Philip Prindeville @ 2011-01-08 21:09 UTC (permalink / raw)
  To: Francois Romieu; +Cc: Linux Netdev List
In-Reply-To: <4C99A289.2030109@redfish-solutions.com>

On 9/21/10 11:30 PM, Philip Prindeville wrote:
>  On 9/17/10 1:00 PM, Francois Romieu wrote:
>> Philip Prindeville<philipp_subx@redfish-solutions.com>  :
>> [...]
>>> Does this look familiar to anyone?
>> 349124a00754129a5f1e43efa84733e364bf3749 ?
>>
>> It would be a bit too easy.
>>
> Thanks.  I'll give it a try now.

No, that's not the problem.  Still seeing traces, even after applying that patch.

This is in 2.6.27.57:

Jan  8 00:11:25 pdx user.warn kernel: ------------[ cut here ]------------
Jan  8 00:11:25 pdx user.warn kernel: WARNING: at net/sched/sch_generic.c:219 dev_watchdog+0xf1/0x176()
Jan  8 00:11:25 pdx user.info kernel: NETDEV WATCHDOG: eth1 (8139cp): transmit timed out
Jan  8 00:11:25 pdx user.warn kernel: Modules linked in: pppoatm pppox ppp_generic slhc bridge stp llc solos_pci atm dummy ath5k mac80211 ath cfg80211 rfkill_backport compat dahdi sha512_generic sha256_generic deflate zlib_deflate arc4 ecb sha1_generic blowfish des
Jan  8 00:11:25 pdx user.warn kernel: Pid: 0, comm: swapper Tainted: P          2.6.27.57-astlinux #1
Jan  8 00:11:25 pdx user.warn kernel:  [<c0115462>] warn_slowpath+0x61/0x84
Jan  8 00:11:25 pdx user.warn kernel:  [<c026649b>] nf_hook_slow+0x44/0xb1
Jan  8 00:11:25 pdx user.warn kernel:  [<e018d968>] br_nf_pre_routing_finish+0x0/0x257 [bridge]
Jan  8 00:11:25 pdx user.warn kernel:  [<e018e5a3>] br_nf_pre_routing+0x532/0x54b [bridge]
Jan  8 00:11:25 pdx user.warn kernel:  [<c01065e8>] read_tsc+0x6/0x22
Jan  8 00:11:25 pdx user.warn kernel:  [<c01289a6>] getnstimeofday+0x4a/0xc7
Jan  8 00:11:25 pdx user.warn kernel:  [<c01267ca>] ktime_get_ts+0x1d/0x3f
Jan  8 00:11:25 pdx user.warn kernel:  [<c0126056>] hrtimer_forward+0xe2/0xfe
Jan  8 00:11:25 pdx user.warn kernel:  [<c025e0b3>] dev_watchdog+0x0/0x176
Jan  8 00:11:25 pdx user.warn kernel:  [<c01cfb57>] strlcpy+0x15/0x62
Jan  8 00:11:25 pdx user.warn kernel:  [<c025e1a4>] dev_watchdog+0xf1/0x176
Jan  8 00:11:25 pdx user.warn kernel:  [<e00e7f3c>] coretimer_func+0xb1/0x133 [dahdi]
Jan  8 00:11:25 pdx user.warn kernel:  [<c011c05a>] run_timer_softirq+0x116/0x17a
Jan  8 00:11:25 pdx user.warn kernel:  [<c0118ce4>] __do_softirq+0x35/0x75
Jan  8 00:11:25 pdx user.warn kernel:  [<c0118d46>] do_softirq+0x22/0x26
Jan  8 00:11:25 pdx user.warn kernel:  [<c0118f20>] irq_exit+0x25/0x30
Jan  8 00:11:25 pdx user.warn kernel:  [<c010477c>] do_IRQ+0x4d/0x5d
Jan  8 00:11:25 pdx user.warn kernel:  [<c010394b>] common_interrupt+0x23/0x28
Jan  8 00:11:25 pdx user.warn kernel:  [<c0106f3d>] default_idle+0x25/0x38
Jan  8 00:11:25 pdx user.warn kernel:  [<c010254b>] cpu_idle+0x37/0x5f
Jan  8 00:11:25 pdx user.warn kernel:  =======================
Jan  8 00:11:25 pdx user.warn kernel: ---[ end trace 4eb2e0ef5bc6569d ]---
Jan  8 00:11:25 pdx user.warn kernel: eth1: Transmit timeout, status  c   2b    0 80ff



Any other ideas?

Thanks.



^ permalink raw reply

* Re: iproute2 caching and batch mode
From: denys @ 2011-01-08 20:36 UTC (permalink / raw)
  To: denys; +Cc: Stephen Hemminger, netdev
In-Reply-To: <0befc7c09f04936c1244eaa5a1d2620c@localhost>

On Sat, 08 Jan 2011 22:09:39 +0200, <denys@visp.net.lb> wrote:
> Hi,
> 
> noticed some issue a while ago, and because of recent patches decided to
> post my thoughts:
> 
> This issue can happen if ip or tc running in some kind of "daemon" batch
> mode, or processing large batch file on computer where interfaces can
> reappear with same name but different index (pppoe NAS for example).
> 
> It is easy to reproduce the problem:
> 
> centaur iproute2-2.6.37 # ip/ip -force -batch -
> tunnel add test0 mode ipip remote 1.1.1.2 local 1.1.1.1
> link show dev test0
> 201: test0: <POINTOPOINT,NOARP> mtu 1480 qdisc noop state DOWN 
>     link/ipip 1.1.1.1 peer 1.1.1.2
> tunnel del test0
> Unsupported family:17
> 
> Or:
> 
> centaur iproute2-2.6.37 # ip/ip -force -batch -
> tunnel del test0
> tunnel add test0 mode ipip remote 1.1.1.2 local 1.1.1.1
> link show dev test0
> 202: test0: <POINTOPOINT,NOARP> mtu 1480 qdisc noop state DOWN 
>     link/ipip 1.1.1.1 peer 1.1.1.2
> (another console, delete and create again test0)
> link show dev test0
> (nothing will appear)
Sorry, just got mail sent before i finish it.

Is it appropriate to implement some kind of "flush" command, to flush
internal cache?
I can try to do that, if this way is ok.
Sure maybe best way to monitor interface updates over netlink, in batch
mode, and update cache accordingly.


^ permalink raw reply

* iproute2 caching and batch mode
From: denys @ 2011-01-08 20:09 UTC (permalink / raw)
  To: Stephen Hemminger, netdev

Hi,

noticed some issue a while ago, and because of recent patches decided to
post my thoughts:

This issue can happen if ip or tc running in some kind of "daemon" batch
mode, or processing large batch file on computer where interfaces can
reappear with same name but different index (pppoe NAS for example).

It is easy to reproduce the problem:

centaur iproute2-2.6.37 # ip/ip -force -batch -
tunnel add test0 mode ipip remote 1.1.1.2 local 1.1.1.1
link show dev test0
201: test0: <POINTOPOINT,NOARP> mtu 1480 qdisc noop state DOWN 
    link/ipip 1.1.1.1 peer 1.1.1.2
tunnel del test0
Unsupported family:17

Or:

centaur iproute2-2.6.37 # ip/ip -force -batch -
tunnel del test0
tunnel add test0 mode ipip remote 1.1.1.2 local 1.1.1.1
link show dev test0
202: test0: <POINTOPOINT,NOARP> mtu 1480 qdisc noop state DOWN 
    link/ipip 1.1.1.1 peer 1.1.1.2
(another console, delete and create again test0)
link show dev test0
(nothing will appear)


^ permalink raw reply

* Re: 2.6.37 vlans on bnx2 not functional, panic with tcpdump
From: Jarek Poplawski @ 2011-01-08 18:41 UTC (permalink / raw)
  To: Iain Paton
  Cc: Michael Chan, netdev@vger.kernel.org,
	linux-kernel@vger.kernel.org
In-Reply-To: <4D2754F9.8050707@gmail.com>

[-- Attachment #1: Type: text/plain, Size: 276 bytes --]

Iain Paton wrote:
...
> So you can consider any bnx2 cause for this closed. I'll get back to the
> list if I can come up with any more useful info.

Hi Iain,
If it's not a problem, please try if the attached debugging patch
(not tested) can change anything.

Thanks,
Jarek P.

[-- Attachment #2: dev.c.deliver_skb.1.diff --]
[-- Type: text/plain, Size: 1286 bytes --]

diff --git a/net/core/dev.c b/net/core/dev.c
index 0dd54a6..9244373 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2720,6 +2720,17 @@ static inline int deliver_skb(struct sk_buff *skb,
 	return pt_prev->func(skb, skb->dev, pt_prev, orig_dev);
 }
 
+static inline int deliver_skb_clone(struct sk_buff *skb,
+			      struct packet_type *pt_prev,
+			      struct net_device *orig_dev)
+{
+	struct sk_buff *nskb = skb_clone(skb, GFP_ATOMIC);
+
+	if (!nskb)
+		return 0;
+	return pt_prev->func(nskb, nskb->dev, pt_prev, orig_dev);
+}
+
 #if (defined(CONFIG_BRIDGE) || defined(CONFIG_BRIDGE_MODULE)) && \
     (defined(CONFIG_ATM_LANE) || defined(CONFIG_ATM_LANE_MODULE))
 /* This hook is defined here for ATM LANE */
@@ -2950,7 +2961,7 @@ static int __netif_receive_skb(struct sk_buff *skb)
 		if (ptype->dev == null_or_orig || ptype->dev == skb->dev ||
 		    ptype->dev == orig_dev) {
 			if (pt_prev)
-				ret = deliver_skb(skb, pt_prev, orig_dev);
+				ret = deliver_skb_clone(skb, pt_prev, orig_dev);
 			pt_prev = ptype;
 		}
 	}
@@ -2976,7 +2987,7 @@ ncls:
 
 	if (vlan_tx_tag_present(skb)) {
 		if (pt_prev) {
-			ret = deliver_skb(skb, pt_prev, orig_dev);
+			ret = deliver_skb_clone(skb, pt_prev, orig_dev);
 			pt_prev = NULL;
 		}
 		if (vlan_hwaccel_do_receive(&skb)) {

^ permalink raw reply related

* Re: [PATCH V8 02/13] ntp: add ADJ_SETOFFSET mode bit
From: Richard Cochran @ 2011-01-08 17:50 UTC (permalink / raw)
  To: Kuwahara,T.
  Cc: linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-api-u79uwXL29TY76Z2rM5mHXA, netdev-u79uwXL29TY76Z2rM5mHXA,
	Alan Cox, Arnd Bergmann, Christoph Lameter, David Miller,
	John Stultz, Krzysztof Halasa, Peter Zijlstra, Rodolfo Giometti,
	Thomas Gleixner
In-Reply-To: <AANLkTini2WdT-1v4k9V3JOZYDkA59P+SyscTe8-fK2Wk-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>

On Sun, Jan 02, 2011 at 05:38:19AM +0900, Kuwahara,T. wrote:
> As you know, it conflicts with MOD_PPSMAX.  And also, it is logically
> the same as ADJ_OFFSET, unless the kernel PLL is enabled explicitly.

I choose another bit, for the next version of the patch series.

> 
> So here's my simple solution:
> 

I have read the API documentation in the nanokernel source archive. It
explains the (very complex looking) timex structure quite clearly and
nicely. Now I am more convinced than ever that adding a new mode bit
is the best way to go, as opposed to ADJ_OFFSET/!STA_PLL, because:

1. The mode bits update kernel variables. That is what we want.
2. Clearing STA_PLL means disable adjustments.
3. The range of the timex.offset is way too small.

I expand on each point, below. BTW, the API document is also available
for online reading here:

   http://www.slac.stanford.edu/comp/unix/package/rtems/src/ssrlApps/ntpNanoclock/api.htm

1. Looking at the API, the documentation for the bits of the 'modes'
   field states:

        These bits control which field of the timex structure are used
        to update the corresponding kernel variable. The bits may be
        set in any combination. See the description below for which
        bits control which variable.

   With the ADJ_SETOFFSET mode, we are telling the kernel to update
   the instantaneous value of the 'current time' variable. That usage
   agrees with the sematics of the other mode bits.

2. The documentation for STA_PLL states:

        Master enable switch for the PLL/FLL loop. The algorithm is
        responsive to time and/or frequency updates if set; otherwise,
        no change in the current time or frequency will be made other
        than to complete a pending phase adjustment. This bit does not
        affect the PPS loop.

   So when we clear this bit, the kernel promises that it will make
   "no change in the current time." The proposed ADJ_OFFSET/!STA_PLL
   solution would break this pattern.

3. The timex.offset field is of type "long" and represents either
   nanoseconds or microseconds. On 32 bit architectures, the maximum
   possible adjustment would be

   2^31 * 10^-6 = 2147.5 seconds

   which is less than one hour. For the first adjustment of a clock,
   we want to be able to jump the clock arbitrarily. Not every
   computer has an RTC, and so some boot up believing that it is still
   the year 1970.

Richard

^ permalink raw reply

* Re: [PATCH v4 net-next-2.6] netfilter: x_tables: dont block BH while reading counters
From: Eric Dumazet @ 2011-01-08 16:45 UTC (permalink / raw)
  To: Patrick McHardy, David Miller
  Cc: Jesper Dangaard Brouer, netfilter-devel, netdev,
	Stephen Hemminger
In-Reply-To: <1292646579.7894.42.camel@edumazet-laptop>

David,

I am resending this patch, sent 3 weeks ago, Patrick gave no answer.

I believe it should be included in linux-2.6.38 and stable kernels.

Some people found they had to change NIC RX ring sizes in order not
missing frames (from 1024 to 2048), while root cause of the problem was
this.

Quoting Jesper : "I can now hit the system with a pktgen at 128 bytes,
and see no drops/overruns while running iptables.  (This packet load at
128bytes is 822 kpps and 840Mbit/s) (iptables ruleset is the big chains:
20929 rules: 81239)."

Thanks

[PATCH v4] netfilter: x_tables: dont block BH while reading counters

Using "iptables -L" with a lot of rules have a too big BH latency.
Jesper mentioned ~6 ms and worried of frame drops.

Switch to a per_cpu seqlock scheme, so that taking a snapshot of
counters doesnt need to block BH (for this cpu, but also other cpus).

This adds two increments on seqlock sequence per ipt_do_table() call,
its a reasonable cost for allowing "iptables -L" not block BH
processing.

Reported-by: Jesper Dangaard Brouer <hawk@comx.dk>
Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
CC: Patrick McHardy <kaber@trash.net>
Acked-by: Stephen Hemminger <shemminger@vyatta.com>
Acked-by: Jesper Dangaard Brouer <hawk@comx.dk>
---
 include/linux/netfilter/x_tables.h |   10 +++---
 net/ipv4/netfilter/arp_tables.c    |   45 ++++++++-------------------
 net/ipv4/netfilter/ip_tables.c     |   45 ++++++++-------------------
 net/ipv6/netfilter/ip6_tables.c    |   45 ++++++++-------------------
 net/netfilter/x_tables.c           |    3 +
 5 files changed, 49 insertions(+), 99 deletions(-)

diff --git a/include/linux/netfilter/x_tables.h b/include/linux/netfilter/x_tables.h
index 742bec0..6712e71 100644
--- a/include/linux/netfilter/x_tables.h
+++ b/include/linux/netfilter/x_tables.h
@@ -472,7 +472,7 @@ extern void xt_free_table_info(struct xt_table_info *info);
  *  necessary for reading the counters.
  */
 struct xt_info_lock {
-	spinlock_t lock;
+	seqlock_t lock;
 	unsigned char readers;
 };
 DECLARE_PER_CPU(struct xt_info_lock, xt_info_locks);
@@ -497,7 +497,7 @@ static inline void xt_info_rdlock_bh(void)
 	local_bh_disable();
 	lock = &__get_cpu_var(xt_info_locks);
 	if (likely(!lock->readers++))
-		spin_lock(&lock->lock);
+		write_seqlock(&lock->lock);
 }
 
 static inline void xt_info_rdunlock_bh(void)
@@ -505,7 +505,7 @@ static inline void xt_info_rdunlock_bh(void)
 	struct xt_info_lock *lock = &__get_cpu_var(xt_info_locks);
 
 	if (likely(!--lock->readers))
-		spin_unlock(&lock->lock);
+		write_sequnlock(&lock->lock);
 	local_bh_enable();
 }
 
@@ -516,12 +516,12 @@ static inline void xt_info_rdunlock_bh(void)
  */
 static inline void xt_info_wrlock(unsigned int cpu)
 {
-	spin_lock(&per_cpu(xt_info_locks, cpu).lock);
+	write_seqlock(&per_cpu(xt_info_locks, cpu).lock);
 }
 
 static inline void xt_info_wrunlock(unsigned int cpu)
 {
-	spin_unlock(&per_cpu(xt_info_locks, cpu).lock);
+	write_sequnlock(&per_cpu(xt_info_locks, cpu).lock);
 }
 
 /*
diff --git a/net/ipv4/netfilter/arp_tables.c b/net/ipv4/netfilter/arp_tables.c
index 3fac340..e855fff 100644
--- a/net/ipv4/netfilter/arp_tables.c
+++ b/net/ipv4/netfilter/arp_tables.c
@@ -710,42 +710,25 @@ static void get_counters(const struct xt_table_info *t,
 	struct arpt_entry *iter;
 	unsigned int cpu;
 	unsigned int i;
-	unsigned int curcpu = get_cpu();
-
-	/* Instead of clearing (by a previous call to memset())
-	 * the counters and using adds, we set the counters
-	 * with data used by 'current' CPU
-	 *
-	 * Bottom half has to be disabled to prevent deadlock
-	 * if new softirq were to run and call ipt_do_table
-	 */
-	local_bh_disable();
-	i = 0;
-	xt_entry_foreach(iter, t->entries[curcpu], t->size) {
-		SET_COUNTER(counters[i], iter->counters.bcnt,
-			    iter->counters.pcnt);
-		++i;
-	}
-	local_bh_enable();
-	/* Processing counters from other cpus, we can let bottom half enabled,
-	 * (preemption is disabled)
-	 */
 
 	for_each_possible_cpu(cpu) {
-		if (cpu == curcpu)
-			continue;
+		seqlock_t *lock = &per_cpu(xt_info_locks, cpu).lock;
+
 		i = 0;
-		local_bh_disable();
-		xt_info_wrlock(cpu);
 		xt_entry_foreach(iter, t->entries[cpu], t->size) {
-			ADD_COUNTER(counters[i], iter->counters.bcnt,
-				    iter->counters.pcnt);
+			u64 bcnt, pcnt;
+			unsigned int start;
+
+			do {
+				start = read_seqbegin(lock);
+				bcnt = iter->counters.bcnt;
+				pcnt = iter->counters.pcnt;
+			} while (read_seqretry(lock, start));
+
+			ADD_COUNTER(counters[i], bcnt, pcnt);
 			++i;
 		}
-		xt_info_wrunlock(cpu);
-		local_bh_enable();
 	}
-	put_cpu();
 }
 
 static struct xt_counters *alloc_counters(const struct xt_table *table)
@@ -759,7 +742,7 @@ static struct xt_counters *alloc_counters(const struct xt_table *table)
 	 * about).
 	 */
 	countersize = sizeof(struct xt_counters) * private->number;
-	counters = vmalloc(countersize);
+	counters = vzalloc(countersize);
 
 	if (counters == NULL)
 		return ERR_PTR(-ENOMEM);
@@ -1007,7 +990,7 @@ static int __do_replace(struct net *net, const char *name,
 	struct arpt_entry *iter;
 
 	ret = 0;
-	counters = vmalloc(num_counters * sizeof(struct xt_counters));
+	counters = vzalloc(num_counters * sizeof(struct xt_counters));
 	if (!counters) {
 		ret = -ENOMEM;
 		goto out;
diff --git a/net/ipv4/netfilter/ip_tables.c b/net/ipv4/netfilter/ip_tables.c
index a846d63..652efea 100644
--- a/net/ipv4/netfilter/ip_tables.c
+++ b/net/ipv4/netfilter/ip_tables.c
@@ -884,42 +884,25 @@ get_counters(const struct xt_table_info *t,
 	struct ipt_entry *iter;
 	unsigned int cpu;
 	unsigned int i;
-	unsigned int curcpu = get_cpu();
-
-	/* Instead of clearing (by a previous call to memset())
-	 * the counters and using adds, we set the counters
-	 * with data used by 'current' CPU.
-	 *
-	 * Bottom half has to be disabled to prevent deadlock
-	 * if new softirq were to run and call ipt_do_table
-	 */
-	local_bh_disable();
-	i = 0;
-	xt_entry_foreach(iter, t->entries[curcpu], t->size) {
-		SET_COUNTER(counters[i], iter->counters.bcnt,
-			    iter->counters.pcnt);
-		++i;
-	}
-	local_bh_enable();
-	/* Processing counters from other cpus, we can let bottom half enabled,
-	 * (preemption is disabled)
-	 */
 
 	for_each_possible_cpu(cpu) {
-		if (cpu == curcpu)
-			continue;
+		seqlock_t *lock = &per_cpu(xt_info_locks, cpu).lock;
+
 		i = 0;
-		local_bh_disable();
-		xt_info_wrlock(cpu);
 		xt_entry_foreach(iter, t->entries[cpu], t->size) {
-			ADD_COUNTER(counters[i], iter->counters.bcnt,
-				    iter->counters.pcnt);
+			u64 bcnt, pcnt;
+			unsigned int start;
+
+			do {
+				start = read_seqbegin(lock);
+				bcnt = iter->counters.bcnt;
+				pcnt = iter->counters.pcnt;
+			} while (read_seqretry(lock, start));
+
+			ADD_COUNTER(counters[i], bcnt, pcnt);
 			++i; /* macro does multi eval of i */
 		}
-		xt_info_wrunlock(cpu);
-		local_bh_enable();
 	}
-	put_cpu();
 }
 
 static struct xt_counters *alloc_counters(const struct xt_table *table)
@@ -932,7 +915,7 @@ static struct xt_counters *alloc_counters(const struct xt_table *table)
 	   (other than comefrom, which userspace doesn't care
 	   about). */
 	countersize = sizeof(struct xt_counters) * private->number;
-	counters = vmalloc(countersize);
+	counters = vzalloc(countersize);
 
 	if (counters == NULL)
 		return ERR_PTR(-ENOMEM);
@@ -1203,7 +1186,7 @@ __do_replace(struct net *net, const char *name, unsigned int valid_hooks,
 	struct ipt_entry *iter;
 
 	ret = 0;
-	counters = vmalloc(num_counters * sizeof(struct xt_counters));
+	counters = vzalloc(num_counters * sizeof(struct xt_counters));
 	if (!counters) {
 		ret = -ENOMEM;
 		goto out;
diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
index 4555823..7d227c6 100644
--- a/net/ipv6/netfilter/ip6_tables.c
+++ b/net/ipv6/netfilter/ip6_tables.c
@@ -897,42 +897,25 @@ get_counters(const struct xt_table_info *t,
 	struct ip6t_entry *iter;
 	unsigned int cpu;
 	unsigned int i;
-	unsigned int curcpu = get_cpu();
-
-	/* Instead of clearing (by a previous call to memset())
-	 * the counters and using adds, we set the counters
-	 * with data used by 'current' CPU
-	 *
-	 * Bottom half has to be disabled to prevent deadlock
-	 * if new softirq were to run and call ipt_do_table
-	 */
-	local_bh_disable();
-	i = 0;
-	xt_entry_foreach(iter, t->entries[curcpu], t->size) {
-		SET_COUNTER(counters[i], iter->counters.bcnt,
-			    iter->counters.pcnt);
-		++i;
-	}
-	local_bh_enable();
-	/* Processing counters from other cpus, we can let bottom half enabled,
-	 * (preemption is disabled)
-	 */
 
 	for_each_possible_cpu(cpu) {
-		if (cpu == curcpu)
-			continue;
+		seqlock_t *lock = &per_cpu(xt_info_locks, cpu).lock;
+
 		i = 0;
-		local_bh_disable();
-		xt_info_wrlock(cpu);
 		xt_entry_foreach(iter, t->entries[cpu], t->size) {
-			ADD_COUNTER(counters[i], iter->counters.bcnt,
-				    iter->counters.pcnt);
+			u64 bcnt, pcnt;
+			unsigned int start;
+
+			do {
+				start = read_seqbegin(lock);
+				bcnt = iter->counters.bcnt;
+				pcnt = iter->counters.pcnt;
+			} while (read_seqretry(lock, start));
+
+			ADD_COUNTER(counters[i], bcnt, pcnt);
 			++i;
 		}
-		xt_info_wrunlock(cpu);
-		local_bh_enable();
 	}
-	put_cpu();
 }
 
 static struct xt_counters *alloc_counters(const struct xt_table *table)
@@ -945,7 +928,7 @@ static struct xt_counters *alloc_counters(const struct xt_table *table)
 	   (other than comefrom, which userspace doesn't care
 	   about). */
 	countersize = sizeof(struct xt_counters) * private->number;
-	counters = vmalloc(countersize);
+	counters = vzalloc(countersize);
 
 	if (counters == NULL)
 		return ERR_PTR(-ENOMEM);
@@ -1216,7 +1199,7 @@ __do_replace(struct net *net, const char *name, unsigned int valid_hooks,
 	struct ip6t_entry *iter;
 
 	ret = 0;
-	counters = vmalloc(num_counters * sizeof(struct xt_counters));
+	counters = vzalloc(num_counters * sizeof(struct xt_counters));
 	if (!counters) {
 		ret = -ENOMEM;
 		goto out;
diff --git a/net/netfilter/x_tables.c b/net/netfilter/x_tables.c
index 8046350..c942376 100644
--- a/net/netfilter/x_tables.c
+++ b/net/netfilter/x_tables.c
@@ -1325,7 +1325,8 @@ static int __init xt_init(void)
 
 	for_each_possible_cpu(i) {
 		struct xt_info_lock *lock = &per_cpu(xt_info_locks, i);
-		spin_lock_init(&lock->lock);
+
+		seqlock_init(&lock->lock);
 		lock->readers = 0;
 	}
 



^ permalink raw reply related

* Re: [PATCH V8 12/13] ptp: Added a clock driver for the IXP46x.
From: Krzysztof Halasa @ 2011-01-08 16:25 UTC (permalink / raw)
  To: Richard Cochran
  Cc: linux-kernel-u79uwXL29TY76Z2rM5mHXA,
	linux-api-u79uwXL29TY76Z2rM5mHXA, netdev-u79uwXL29TY76Z2rM5mHXA,
	Alan Cox, Arnd Bergmann, Christoph Lameter, David Miller,
	John Stultz, Peter Zijlstra, Rodolfo Giometti, Thomas Gleixner
In-Reply-To: <20110107170752.GB8666-7KxsofuKt4IfAd9E5cN8NEzG7cXyKsk/@public.gmane.org>

Richard Cochran <richardcochran-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org> writes:

> The time stamp code clones the skb, but the LE version frees the skb
> too early. Perhaps we can move that dev_kfree_skb(skb) in the LE case
> to be the last statement in eth_xmit(). What do you think?

I think so. Or something similar.

> Do you mean, you don't like the constant on the left hand side?

Yes.

> Is that prohibited by CodingStyle or similar?

I don't think so. It's just a personal taste. I think it's based on
things learned in primary school, they teach to write (comparisons)
X = 4 instead of the other way around, and my brain seems to shock
a bit on the opposite.

> I got into the habit of writing it that way to prevent a typo like:
>
> 	if (irq = NO_IRQ)

I see. Unfortunately it doesn't prevent typos like this when the right
side isn't a constant. Anyway gcc warns about them, even when both sides
are variable.

>> Also I don't like the ixp_read/ixp_write() trivial macros. Why not
>> simply call __raw_readl() and __raw_writel()?
>
> Well, I have had the experience back in 2.4 days of having my drivers
> ruined by the changing IO macros in the kernel. The wrappers are
> supposed to help if that ever happens again. Seeing *two* leading
> underscores in the macro names certainly makes me nervous.

Well, these two underscores mainly mean it's arch-dependent, but so are
the ixp4xx drivers. Using the __raw_read* directly is the preferred
method (or, perhaps, in such case, it's the only way).

Actually, I was thinking about changing the macros some time ago, and it
may eventually happen. But we'll fix all the code using them then.
-- 
Krzysztof Halasa

^ permalink raw reply

* Re: [PATCH] net_sched: factorize qdisc stats handling
From: Eric Dumazet @ 2011-01-08 15:40 UTC (permalink / raw)
  To: Jarek Poplawski
  Cc: Stephen Hemminger, Changli Gao, David Miller, Fabio Checconi,
	netdev, Luigi Rizzo
In-Reply-To: <4D286823.8050707@gmail.com>

Le samedi 08 janvier 2011 à 14:35 +0100, Jarek Poplawski a écrit :

> I guess you can't use qdisc_pkt_len() without qdisc_enqueue_root().
> 

Indeed !

This TCQ_F_CAN_BYPASS thing is truly evil ;)

Hmm, this makes me thing we could add TCQ_F_CAN_BYPASS on SFQ.

Thanks !



^ permalink raw reply

* Re: [PATCH] net_sched: factorize qdisc stats handling
From: Jarek Poplawski @ 2011-01-08 13:35 UTC (permalink / raw)
  To: Eric Dumazet
  Cc: Stephen Hemminger, Changli Gao, David Miller, Fabio Checconi,
	netdev, Luigi Rizzo
In-Reply-To: <1294478789.2709.79.camel@edumazet-laptop>

Eric Dumazet wrote:
...
> -static inline void __qdisc_update_bstats(struct Qdisc *sch, unsigned int len)
> +
> +static inline void bstats_update(struct gnet_stats_basic_packed *bstats,
> +				 struct sk_buff *skb)
> +{
> +	bstats->bytes += qdisc_pkt_len(skb);
> +	bstats->packets += skb_is_gso(skb) ? skb_shinfo(skb)->gso_segs : 1;
> +}
> +
> +static inline void qdisc_bstats_update(struct Qdisc *sch, struct sk_buff *skb)
>  {
> -	sch->bstats.bytes += len;
> -	sch->bstats.packets++;
> +	bstats_update(&sch->bstats, skb);
>  }
>  
>  static inline int __qdisc_enqueue_tail(struct sk_buff *skb, struct Qdisc *sch,
> @@ -437,7 +444,7 @@ static inline int __qdisc_enqueue_tail(struct sk_buff *skb, struct Qdisc *sch,
>  {
>  	__skb_queue_tail(list, skb);
>  	sch->qstats.backlog += qdisc_pkt_len(skb);
> -	__qdisc_update_bstats(sch, qdisc_pkt_len(skb));
> +	qdisc_bstats_update(sch, skb);
>  
>  	return NET_XMIT_SUCCESS;
>  }
> diff --git a/net/core/dev.c b/net/core/dev.c
> index a215269..ab60f58 100644
> --- a/net/core/dev.c
> +++ b/net/core/dev.c
> @@ -2301,7 +2301,7 @@ static inline int __dev_xmit_skb(struct sk_buff *skb, struct Qdisc *q,
>  		 */
>  		if (!(dev->priv_flags & IFF_XMIT_DST_RELEASE))
>  			skb_dst_force(skb);
> -		__qdisc_update_bstats(q, skb->len);
> +		qdisc_bstats_update(q, skb);
>  		if (sch_direct_xmit(skb, q, dev, txq, root_lock)) {
>  			if (unlikely(contended)) {
>  				spin_unlock(&q->busylock);

I guess you can't use qdisc_pkt_len() without qdisc_enqueue_root().

Jarek P.

^ permalink raw reply

* [e100] Page allocation failure warning(?) in 2.6.36.3
From: Chris Rankin @ 2011-01-08 12:53 UTC (permalink / raw)
  To: e1000-devel; +Cc: netdev

Hi,

I've just booted 2.6.36.3 on my old router box (which contains one single e100 card, and one dual-port e100 card), and have discovered this rather scary message in the dmesg log:

e100: Intel(R) PRO/100 Network Driver, 3.5.24-k2-NAPI
e100: Copyright(c) 1999-2006 Intel Corporation
e100 0000:00:0f.0: PME# disabled
e100 0000:00:0f.0: eth0: addr 0xffbeb000, irq 10, MAC addr 00:90:27:76:d0:ec
e100 0000:01:04.0: PME# disabled
e100 0000:01:04.0: eth1: addr 0xff0fe000, irq 11, MAC addr 00:03:47:3b:29:5c
e100 0000:01:05.0: PME# disabled
e100 0000:01:05.0: eth2: addr 0xff0ff000, irq 10, MAC addr 00:03:47:3b:29:5d
...
device eth1 entered promiscuous mode
ADDRCONF(NETDEV_UP): eth1: link is not ready
e100 0000:01:04.0: eth1: NIC Link is Up 100 Mbps Full Duplex
ADDRCONF(NETDEV_CHANGE): eth1: link becomes ready
device eth2 entered promiscuous mode
ADDRCONF(NETDEV_UP): eth2: link is not ready
br0: port 1(eth1) entering learning state
br0: port 1(eth1) entering learning state
ifconfig: page allocation failure. order:6, mode:0x8020
Pid: 3716, comm: ifconfig Not tainted 2.6.36.3 #1
Call Trace:
 [<c104b2a9>] ? __alloc_pages_nodemask+0x477/0x4a6
 [<c106177d>] ? __slab_alloc+0x1eb/0x396
 [<c1004ca6>] ? dma_generic_alloc_coherent+0x4e/0xac
 [<c105fb5c>] ? dma_pool_alloc+0xe5/0x1d9
 [<c1004c58>] ? dma_generic_alloc_coherent+0x0/0xac
 [<c58f97f3>] ? e100_rx_alloc_skb+0x87/0x122 [e100]
 [<c58f9883>] ? e100_rx_alloc_skb+0x117/0x122 [e100]
 [<c58f98dc>] ? e100_alloc_cbs+0x4e/0xfa [e100]
 [<c58fb370>] ? e100_up+0x1b/0xf1 [e100]
 [<c58fb45d>] ? e100_open+0x17/0x3b [e100]
 [<c1121630>] ? __dev_open+0x7c/0xa0
 [<c11217ed>] ? __dev_change_flags+0x8b/0x100
 [<c11218c3>] ? dev_change_flags+0x10/0x3b
 [<c1159880>] ? devinet_ioctl+0x25a/0x532
 [<c11146d2>] ? sock_ioctl+0x1a8/0x1ca
 [<c111452a>] ? sock_ioctl+0x0/0x1ca
 [<c106e061>] ? do_vfs_ioctl+0x464/0x4a2
 [<c1014ce0>] ? do_page_fault+0x2d2/0x2ea
 [<c1014cc8>] ? do_page_fault+0x2ba/0x2ea
 [<c10636f6>] ? sys_faccessat+0x144/0x151
 [<c106e0cc>] ? sys_ioctl+0x2d/0x49
 [<c1177dd5>] ? syscall_call+0x7/0xb
Mem-Info:
DMA per-cpu:
CPU    0: hi:    0, btch:   1 usd:   0
Normal per-cpu:
CPU    0: hi:    6, btch:   1 usd:   0
active_anon:280 inactive_anon:808 isolated_anon:0
 active_file:1384 inactive_file:9672 isolated_file:0
 unevictable:0 dirty:77 writeback:0 unstable:0
 free:753 slab_reclaimable:499 slab_unreclaimable:1393
 mapped:375 shmem:643 pagetables:59 bounce:0
DMA free:1492kB min:248kB low:308kB high:372kB active_anon:0kB inactive_anon:12kB active_file:288kB inactive_file:12548kB unevictable:0kB isolated(anon):0kB isolated(file):0kB present:15864kB mlocked:0kB dirty:48kB writeback:0kB mapped:28kB shmem:0kB slab_reclaimable:312kB slab_unreclaimable:884kB kernel_stack:0kB pagetables:0kB unstable:0kB bounce:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? no
lowmem_reserve[]: 0 47 47
Normal free:1520kB min:764kB low:952kB high:1144kB active_anon:1120kB inactive_anon:3220kB active_file:5248kB inactive_file:26140kB unevictable:0kB isolated(anon):0kB isolated(file):0kB present:48768kB mlocked:0kB dirty:260kB writeback:0kB mapped:1472kB shmem:2572kB slab_reclaimable:1684kB slab_unreclaimable:4688kB kernel_stack:176kB pagetables:236kB unstable:0kB bounce:0kB writeback_tmp:0kB pages_scanned:0 all_unreclaimable? no
lowmem_reserve[]: 0 0 0
DMA: 51*4kB 23*8kB 3*16kB 3*32kB 7*64kB 4*128kB 0*256kB 0*512kB 0*1024kB 0*2048kB 0*4096kB = 1492kB
Normal: 260*4kB 26*8kB 1*16kB 0*32kB 0*64kB 0*128kB 1*256kB 0*512kB 0*1024kB 0*2048kB 0*4096kB = 1520kB
11715 total pagecache pages
16 pages in swap cache
Swap cache stats: add 44, delete 28, find 72/72
Free swap  = 2179532kB
Total swap = 2179596kB
16383 pages RAM
826 pages reserved
10736 pages shared
5361 pages non-shared
ADDRCONF(NETDEV_UP): eth0: link is not ready
e100 0000:00:0f.0: eth0: NIC Link is Up 100 Mbps Full Duplex
ADDRCONF(NETDEV_CHANGE): eth0: link becomes ready
br0: port 1(eth1) entering forwarding state

Should I be concerned, please? All three e100 devices still appear to be working, but something nasty seems to have happened anyway.

The lspci output for these devices is:
00:0f.0 0200: 8086:1229 (rev 08)
	Subsystem: 8086:000c
	Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV+ VGASnoop- ParErr- Stepping- SERR+ FastB2B- DisINTx-
	Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- <TAbort- <MAbort- >SERR- <PERR- INTx-
	Latency: 72 (2000ns min, 14000ns max), Cache Line Size: 32 bytes
	Interrupt: pin A routed to IRQ 10
	Region 0: Memory at ffbeb000 (32-bit, non-prefetchable) [size=4K]
	Region 1: I/O ports at ef00 [size=64]
	Region 2: Memory at fef00000 (32-bit, non-prefetchable) [size=1M]
	[virtual] Expansion ROM at 04000000 [disabled] [size=1M]
	Capabilities: [dc] Power Management version 2
		Flags: PMEClk- DSI+ D1+ D2+ AuxCurrent=0mA PME(D0+,D1+,D2+,D3hot+,D3cold-)
		Status: D0 PME-Enable- DSel=0 DScale=2 PME-
	Kernel driver in use: e100
	Kernel modules: e100

01:04.0 0200: 8086:1229 (rev 05)
	Subsystem: 8086:10f0
	Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV+ VGASnoop- ParErr- Stepping- SERR+ FastB2B- DisINTx-
	Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- <TAbort- <MAbort- >SERR- <PERR- INTx-
	Latency: 72 (2000ns min, 14000ns max), Cache Line Size: 32 bytes
	Interrupt: pin A routed to IRQ 11
	Region 0: Memory at ff0fe000 (32-bit, prefetchable) [size=4K]
	Region 1: I/O ports at fcc0 [size=32]
	Region 2: Memory at ff700000 (32-bit, non-prefetchable) [size=1M]
	[virtual] Expansion ROM at ff100000 [disabled] [size=1M]
	Capabilities: [dc] Power Management version 1
		Flags: PMEClk- DSI+ D1+ D2+ AuxCurrent=0mA PME(D0+,D1+,D2+,D3hot+,D3cold-)
		Status: D0 PME-Enable- DSel=0 DScale=0 PME-
	Kernel driver in use: e100
	Kernel modules: e100

01:05.0 0200: 8086:1229 (rev 05)
	Subsystem: 8086:10f0
	Control: I/O+ Mem+ BusMaster+ SpecCycle- MemWINV+ VGASnoop- ParErr- Stepping- SERR+ FastB2B- DisINTx-
	Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- <TAbort- <MAbort- >SERR- <PERR- INTx-
	Latency: 72 (2000ns min, 14000ns max), Cache Line Size: 32 bytes
	Interrupt: pin A routed to IRQ 10
	Region 0: Memory at ff0ff000 (32-bit, prefetchable) [size=4K]
	Region 1: I/O ports at fce0 [size=32]
	Region 2: Memory at ff900000 (32-bit, non-prefetchable) [size=1M]
	[virtual] Expansion ROM at ff200000 [disabled] [size=1M]
	Capabilities: [dc] Power Management version 1
		Flags: PMEClk- DSI+ D1+ D2+ AuxCurrent=0mA PME(D0+,D1+,D2+,D3hot+,D3cold-)
		Status: D0 PME-Enable- DSel=0 DScale=0 PME-
	Kernel driver in use: e100
	Kernel modules: e100

Thanks,
Chris


      

------------------------------------------------------------------------------
Gaining the trust of online customers is vital for the success of any company
that requires sensitive data to be transmitted over the Web.   Learn how to 
best implement a security strategy that keeps consumers' information secure 
and instills the confidence they need to proceed with transactions.
http://p.sf.net/sfu/oracle-sfdevnl 
_______________________________________________
E1000-devel mailing list
E1000-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/e1000-devel
To learn more about Intel&#174; Ethernet, visit http://communities.intel.com/community/wired

^ permalink raw reply

* Re: [GIT] Networking
From: Francois Romieu @ 2011-01-08 12:17 UTC (permalink / raw)
  To: Linus Torvalds
  Cc: Ben Hutchings, David Miller, Hayes Wang, David Woodhouse, akpm,
	netdev, linux-kernel
In-Reply-To: <20110108000901.GA2133@electric-eye.fr.zoreil.com>

r8169: delay phy init until device opens.

It workarounds the 60s firmware load failure timeout for the
non-modular case.

Signed-off-by: Francois Romieu <romieu@fr.zoreil.com>

diff --git a/drivers/net/r8169.c b/drivers/net/r8169.c
index 27a7c20..dd758cd 100644
--- a/drivers/net/r8169.c
+++ b/drivers/net/r8169.c
@@ -3069,15 +3069,6 @@ rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
 		rtl8168_driver_start(tp);
 	}
 
-	rtl8169_init_phy(dev, tp);
-
-	/*
-	 * Pretend we are using VLANs; This bypasses a nasty bug where
-	 * Interrupts stop flowing on high load on 8110SCd controllers.
-	 */
-	if (tp->mac_version == RTL_GIGA_MAC_VER_05)
-		RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) | RxVlan);
-
 	device_set_wakeup_enable(&pdev->dev, tp->features & RTL_FEATURE_WOL);
 
 	if (pci_dev_run_wake(pdev))
@@ -3127,6 +3118,7 @@ static void __devexit rtl8169_remove_one(struct pci_dev *pdev)
 static int rtl8169_open(struct net_device *dev)
 {
 	struct rtl8169_private *tp = netdev_priv(dev);
+	void __iomem *ioaddr = tp->mmio_addr;
 	struct pci_dev *pdev = tp->pci_dev;
 	int retval = -ENOMEM;
 
@@ -3162,6 +3154,15 @@ static int rtl8169_open(struct net_device *dev)
 
 	napi_enable(&tp->napi);
 
+	rtl8169_init_phy(dev, tp);
+
+	/*
+	 * Pretend we are using VLANs; This bypasses a nasty bug where
+	 * Interrupts stop flowing on high load on 8110SCd controllers.
+	 */
+	if (tp->mac_version == RTL_GIGA_MAC_VER_05)
+		RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) | RxVlan);
+
 	rtl_pll_power_up(tp);
 
 	rtl_hw_start(dev);
@@ -3171,7 +3172,7 @@ static int rtl8169_open(struct net_device *dev)
 	tp->saved_wolopts = 0;
 	pm_runtime_put_noidle(&pdev->dev);
 
-	rtl8169_check_link_status(dev, tp, tp->mmio_addr);
+	rtl8169_check_link_status(dev, tp, ioaddr);
 out:
 	return retval;
 

^ permalink raw reply related

* Re: [PATCH v2] net: ppp: use {get,put}_unaligned_be{16,32}
From: Jarek Poplawski @ 2011-01-08 10:33 UTC (permalink / raw)
  To: Eric Dumazet
  Cc: David Miller, xiaosuo, paulus, harvey.harrison, linux-ppp, netdev
In-Reply-To: <1294482005.2709.90.camel@edumazet-laptop>

Eric Dumazet wrote:
> Le samedi 08 janvier 2011 à 11:04 +0100, Jarek Poplawski a écrit :
> 
>> Just for the record: I agree with Paul that current code is more readable.
>> This code still requires thinking about specific bytes and the patch mixes
>> it only with word access.
>>
>> Jarek P.
>>
>>> @@ -395,16 +396,14 @@ mppe_compress(void *arg, unsigned char *ibuf, unsigned char *obuf,
>>>  	 */
>>>  	obuf[0] = PPP_ADDRESS(ibuf);
>>>  	obuf[1] = PPP_CONTROL(ibuf);
>>> -	obuf[2] = PPP_COMP >> 8;	/* isize + MPPE_OVHD + 1 */
>>> -	obuf[3] = PPP_COMP;	/* isize + MPPE_OVHD + 2 */
>>> +	put_unaligned_be16(PPP_COMP, obuf + 2);
>>>  	obuf += PPP_HDRLEN;
> 
> Compilers are stupid not generating optimal code, so we should help them
> a bit.
> 
> Yes, I agree this is ugly Jarek and makes reading of this code a bit
> more complex, but this is a move we cannot stop. Number of functions,
> macros, etc... is exploding and we must follow the trend ;)
> 
> 41 c6 44 24 02 00       movb   $0x0,0x2(%r12)
> 41 c6 44 24 03 fd       movb   $0xfd,0x3(%r12)
> 
> After patch :
> 
> 66 41 c7 44 24 02 00 fd   movw   $0xfd00,0x2(%r12)

And that's why Paul wanted more justification, because readability
gain is questionable.

Jarek P.

^ permalink raw reply

* Re: [PATCH v2] net: ppp: use {get,put}_unaligned_be{16,32}
From: Eric Dumazet @ 2011-01-08 10:20 UTC (permalink / raw)
  To: Jarek Poplawski
  Cc: David Miller, xiaosuo, paulus, harvey.harrison, linux-ppp, netdev
In-Reply-To: <4D2836BB.6000600@gmail.com>

Le samedi 08 janvier 2011 à 11:04 +0100, Jarek Poplawski a écrit :

> Just for the record: I agree with Paul that current code is more readable.
> This code still requires thinking about specific bytes and the patch mixes
> it only with word access.
> 
> Jarek P.
> 
> > @@ -395,16 +396,14 @@ mppe_compress(void *arg, unsigned char *ibuf, unsigned char *obuf,
> >  	 */
> >  	obuf[0] = PPP_ADDRESS(ibuf);
> >  	obuf[1] = PPP_CONTROL(ibuf);
> > -	obuf[2] = PPP_COMP >> 8;	/* isize + MPPE_OVHD + 1 */
> > -	obuf[3] = PPP_COMP;	/* isize + MPPE_OVHD + 2 */
> > +	put_unaligned_be16(PPP_COMP, obuf + 2);
> >  	obuf += PPP_HDRLEN;

Compilers are stupid not generating optimal code, so we should help them
a bit.

Yes, I agree this is ugly Jarek and makes reading of this code a bit
more complex, but this is a move we cannot stop. Number of functions,
macros, etc... is exploding and we must follow the trend ;)

41 c6 44 24 02 00       movb   $0x0,0x2(%r12)
41 c6 44 24 03 fd       movb   $0xfd,0x3(%r12)

After patch :

66 41 c7 44 24 02 00 fd   movw   $0xfd00,0x2(%r12)




^ permalink raw reply

* Re: [PATCH v2] net: ppp: use {get,put}_unaligned_be{16,32}
From: Jarek Poplawski @ 2011-01-08 10:04 UTC (permalink / raw)
  To: David Miller; +Cc: xiaosuo, paulus, harvey.harrison, linux-ppp, netdev
In-Reply-To: <20110107.171534.193718114.davem@davemloft.net>

David Miller wrote:
> From: Changli Gao <xiaosuo@gmail.com>
> Date: Sat, 8 Jan 2011 08:43:01 +0800
> 
>> On Fri, Jan 7, 2011 at 11:01 AM, Paul Mackerras <paulus@samba.org> wrote:
>>> On Fri, Jan 07, 2011 at 07:37:36AM +0800, Changli Gao wrote:
>>>
>>>> Signed-off-by: Changli Gao <xiaosuo@gmail.com>
>>>
>>> This patch description is inadequate.  It should tell us why you are
>>> making this change.  Does it result in smaller and/or faster code, and
>>> if so by how much on what sort of machine?  Do you think it makes the
>>> code clearer?  (I don't.)  Or is there some other motivation for this?
>>>
>>
>> Good designed APIs always make code clearer, smaller and faster. It is
>> obvious enough I think.
> 
> I have to say that every time I go read the header parsing code in the
> PPP driver, I absolutely regret it.
> 
> And Changli's patch fixes some of the readability problems.

Just for the record: I agree with Paul that current code is more readable.
This code still requires thinking about specific bytes and the patch mixes
it only with word access.

Jarek P.

> @@ -395,16 +396,14 @@ mppe_compress(void *arg, unsigned char *ibuf, unsigned char *obuf,
>  	 */
>  	obuf[0] = PPP_ADDRESS(ibuf);
>  	obuf[1] = PPP_CONTROL(ibuf);
> -	obuf[2] = PPP_COMP >> 8;	/* isize + MPPE_OVHD + 1 */
> -	obuf[3] = PPP_COMP;	/* isize + MPPE_OVHD + 2 */
> +	put_unaligned_be16(PPP_COMP, obuf + 2);
>  	obuf += PPP_HDRLEN;


^ permalink raw reply

* [PATCH] net_sched: factorize qdisc stats handling
From: Eric Dumazet @ 2011-01-08  9:26 UTC (permalink / raw)
  To: Stephen Hemminger
  Cc: Changli Gao, David Miller, Fabio Checconi, netdev, Luigi Rizzo
In-Reply-To: <20110107200234.3f5e7ff8@nehalam>

Le vendredi 07 janvier 2011 à 20:02 -0800, Stephen Hemminger a écrit :
> On Sat, 8 Jan 2011 10:56:33 +0800
> Changli Gao <xiaosuo@gmail.com> wrote:
> 
> > > +       cl->bstats.packets += skb_is_gso(skb)?skb_shinfo(skb)->gso_segs:1;  
> > 
> > Hmm, there is no other packets schedulers which account packets in
> > this way. Which one is better? I am not sure. And in this patch,
> > qstats.drops isn't maintained in the same way. Would these two be
> > consistent.
> 
> HTB uses this accounting.

Yes, but we should use generic helpers and avoid duplicating this kind
of magic here and here ;)


[PATCH] net_sched: factorize qdisc stats handling

HTB takes into account skb is segmented in stats updates.
Generalize this to all schedulers.

They should use qdisc_bstats_update() helper instead of manipulating
bstats.bytes and bstats.packets

Add bstats_update() helper too for classes that use
gnet_stats_basic_packed fields.

Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
---
 include/net/sch_generic.h |   15 +++++++++++----
 net/core/dev.c            |    2 +-
 net/sched/act_csum.c      |    3 +--
 net/sched/act_ipt.c       |    3 +--
 net/sched/act_mirred.c    |    3 +--
 net/sched/act_nat.c       |    3 +--
 net/sched/act_pedit.c     |    3 +--
 net/sched/act_police.c    |    3 +--
 net/sched/act_simple.c    |    3 +--
 net/sched/act_skbedit.c   |    3 +--
 net/sched/sch_atm.c       |    6 ++----
 net/sched/sch_cbq.c       |    6 ++----
 net/sched/sch_drr.c       |    8 ++------
 net/sched/sch_dsmark.c    |    3 +--
 net/sched/sch_hfsc.c      |    6 ++----
 net/sched/sch_htb.c       |   17 ++++++-----------
 net/sched/sch_ingress.c   |    3 +--
 net/sched/sch_multiq.c    |    3 +--
 net/sched/sch_netem.c     |    6 ++----
 net/sched/sch_prio.c      |    3 +--
 net/sched/sch_red.c       |    3 +--
 net/sched/sch_sfq.c       |    3 +--
 net/sched/sch_tbf.c       |    3 +--
 net/sched/sch_teql.c      |    3 +--
 24 files changed, 44 insertions(+), 70 deletions(-)

diff --git a/include/net/sch_generic.h b/include/net/sch_generic.h
index 0af57eb..389bbcb 100644
--- a/include/net/sch_generic.h
+++ b/include/net/sch_generic.h
@@ -426,10 +426,17 @@ static inline int qdisc_enqueue_root(struct sk_buff *skb, struct Qdisc *sch)
 	return qdisc_enqueue(skb, sch) & NET_XMIT_MASK;
 }
 
-static inline void __qdisc_update_bstats(struct Qdisc *sch, unsigned int len)
+
+static inline void bstats_update(struct gnet_stats_basic_packed *bstats,
+				 struct sk_buff *skb)
+{
+	bstats->bytes += qdisc_pkt_len(skb);
+	bstats->packets += skb_is_gso(skb) ? skb_shinfo(skb)->gso_segs : 1;
+}
+
+static inline void qdisc_bstats_update(struct Qdisc *sch, struct sk_buff *skb)
 {
-	sch->bstats.bytes += len;
-	sch->bstats.packets++;
+	bstats_update(&sch->bstats, skb);
 }
 
 static inline int __qdisc_enqueue_tail(struct sk_buff *skb, struct Qdisc *sch,
@@ -437,7 +444,7 @@ static inline int __qdisc_enqueue_tail(struct sk_buff *skb, struct Qdisc *sch,
 {
 	__skb_queue_tail(list, skb);
 	sch->qstats.backlog += qdisc_pkt_len(skb);
-	__qdisc_update_bstats(sch, qdisc_pkt_len(skb));
+	qdisc_bstats_update(sch, skb);
 
 	return NET_XMIT_SUCCESS;
 }
diff --git a/net/core/dev.c b/net/core/dev.c
index a215269..ab60f58 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2301,7 +2301,7 @@ static inline int __dev_xmit_skb(struct sk_buff *skb, struct Qdisc *q,
 		 */
 		if (!(dev->priv_flags & IFF_XMIT_DST_RELEASE))
 			skb_dst_force(skb);
-		__qdisc_update_bstats(q, skb->len);
+		qdisc_bstats_update(q, skb);
 		if (sch_direct_xmit(skb, q, dev, txq, root_lock)) {
 			if (unlikely(contended)) {
 				spin_unlock(&q->busylock);
diff --git a/net/sched/act_csum.c b/net/sched/act_csum.c
index 67dc7ce..83ddfc0 100644
--- a/net/sched/act_csum.c
+++ b/net/sched/act_csum.c
@@ -508,8 +508,7 @@ static int tcf_csum(struct sk_buff *skb,
 
 	spin_lock(&p->tcf_lock);
 	p->tcf_tm.lastuse = jiffies;
-	p->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	p->tcf_bstats.packets++;
+	bstats_update(&p->tcf_bstats, skb);
 	action = p->tcf_action;
 	update_flags = p->update_flags;
 	spin_unlock(&p->tcf_lock);
diff --git a/net/sched/act_ipt.c b/net/sched/act_ipt.c
index 8daef96..c2a7c20 100644
--- a/net/sched/act_ipt.c
+++ b/net/sched/act_ipt.c
@@ -209,8 +209,7 @@ static int tcf_ipt(struct sk_buff *skb, struct tc_action *a,
 	spin_lock(&ipt->tcf_lock);
 
 	ipt->tcf_tm.lastuse = jiffies;
-	ipt->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	ipt->tcf_bstats.packets++;
+	bstats_update(&ipt->tcf_bstats, skb);
 
 	/* yes, we have to worry about both in and out dev
 	 worry later - danger - this API seems to have changed
diff --git a/net/sched/act_mirred.c b/net/sched/act_mirred.c
index 0c311be..d765067 100644
--- a/net/sched/act_mirred.c
+++ b/net/sched/act_mirred.c
@@ -165,8 +165,7 @@ static int tcf_mirred(struct sk_buff *skb, struct tc_action *a,
 
 	spin_lock(&m->tcf_lock);
 	m->tcf_tm.lastuse = jiffies;
-	m->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	m->tcf_bstats.packets++;
+	bstats_update(&m->tcf_bstats, skb);
 
 	dev = m->tcfm_dev;
 	if (!dev) {
diff --git a/net/sched/act_nat.c b/net/sched/act_nat.c
index 186eb83..178a4bd 100644
--- a/net/sched/act_nat.c
+++ b/net/sched/act_nat.c
@@ -125,8 +125,7 @@ static int tcf_nat(struct sk_buff *skb, struct tc_action *a,
 	egress = p->flags & TCA_NAT_FLAG_EGRESS;
 	action = p->tcf_action;
 
-	p->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	p->tcf_bstats.packets++;
+	bstats_update(&p->tcf_bstats, skb);
 
 	spin_unlock(&p->tcf_lock);
 
diff --git a/net/sched/act_pedit.c b/net/sched/act_pedit.c
index a0593c9..445bef7 100644
--- a/net/sched/act_pedit.c
+++ b/net/sched/act_pedit.c
@@ -187,8 +187,7 @@ static int tcf_pedit(struct sk_buff *skb, struct tc_action *a,
 bad:
 	p->tcf_qstats.overlimits++;
 done:
-	p->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	p->tcf_bstats.packets++;
+	bstats_update(&p->tcf_bstats, skb);
 	spin_unlock(&p->tcf_lock);
 	return p->tcf_action;
 }
diff --git a/net/sched/act_police.c b/net/sched/act_police.c
index 7ebf743..e2f08b1 100644
--- a/net/sched/act_police.c
+++ b/net/sched/act_police.c
@@ -298,8 +298,7 @@ static int tcf_act_police(struct sk_buff *skb, struct tc_action *a,
 
 	spin_lock(&police->tcf_lock);
 
-	police->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	police->tcf_bstats.packets++;
+	bstats_update(&police->tcf_bstats, skb);
 
 	if (police->tcfp_ewma_rate &&
 	    police->tcf_rate_est.bps >= police->tcfp_ewma_rate) {
diff --git a/net/sched/act_simple.c b/net/sched/act_simple.c
index 97e84f3..7287cff 100644
--- a/net/sched/act_simple.c
+++ b/net/sched/act_simple.c
@@ -42,8 +42,7 @@ static int tcf_simp(struct sk_buff *skb, struct tc_action *a, struct tcf_result
 
 	spin_lock(&d->tcf_lock);
 	d->tcf_tm.lastuse = jiffies;
-	d->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	d->tcf_bstats.packets++;
+	bstats_update(&d->tcf_bstats, skb);
 
 	/* print policy string followed by _ then packet count
 	 * Example if this was the 3rd packet and the string was "hello"
diff --git a/net/sched/act_skbedit.c b/net/sched/act_skbedit.c
index 66cbf4e..836f5fe 100644
--- a/net/sched/act_skbedit.c
+++ b/net/sched/act_skbedit.c
@@ -46,8 +46,7 @@ static int tcf_skbedit(struct sk_buff *skb, struct tc_action *a,
 
 	spin_lock(&d->tcf_lock);
 	d->tcf_tm.lastuse = jiffies;
-	d->tcf_bstats.bytes += qdisc_pkt_len(skb);
-	d->tcf_bstats.packets++;
+	bstats_update(&d->tcf_bstats, skb);
 
 	if (d->flags & SKBEDIT_F_PRIORITY)
 		skb->priority = d->priority;
diff --git a/net/sched/sch_atm.c b/net/sched/sch_atm.c
index 2825407..943d733 100644
--- a/net/sched/sch_atm.c
+++ b/net/sched/sch_atm.c
@@ -422,10 +422,8 @@ drop: __maybe_unused
 		}
 		return ret;
 	}
-	sch->bstats.bytes += qdisc_pkt_len(skb);
-	sch->bstats.packets++;
-	flow->bstats.bytes += qdisc_pkt_len(skb);
-	flow->bstats.packets++;
+	qdisc_bstats_update(sch, skb);
+	bstats_update(&flow->bstats, skb);
 	/*
 	 * Okay, this may seem weird. We pretend we've dropped the packet if
 	 * it goes via ATM. The reason for this is that the outer qdisc
diff --git a/net/sched/sch_cbq.c b/net/sched/sch_cbq.c
index eb76315..c80d1c2 100644
--- a/net/sched/sch_cbq.c
+++ b/net/sched/sch_cbq.c
@@ -390,8 +390,7 @@ cbq_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 	ret = qdisc_enqueue(skb, cl->q);
 	if (ret == NET_XMIT_SUCCESS) {
 		sch->q.qlen++;
-		sch->bstats.packets++;
-		sch->bstats.bytes += qdisc_pkt_len(skb);
+		qdisc_bstats_update(sch, skb);
 		cbq_mark_toplevel(q, cl);
 		if (!cl->next_alive)
 			cbq_activate_class(cl);
@@ -650,8 +649,7 @@ static int cbq_reshape_fail(struct sk_buff *skb, struct Qdisc *child)
 		ret = qdisc_enqueue(skb, cl->q);
 		if (ret == NET_XMIT_SUCCESS) {
 			sch->q.qlen++;
-			sch->bstats.packets++;
-			sch->bstats.bytes += qdisc_pkt_len(skb);
+			qdisc_bstats_update(sch, skb);
 			if (!cl->next_alive)
 				cbq_activate_class(cl);
 			return 0;
diff --git a/net/sched/sch_drr.c b/net/sched/sch_drr.c
index aa8b531..de55e64 100644
--- a/net/sched/sch_drr.c
+++ b/net/sched/sch_drr.c
@@ -351,7 +351,6 @@ static int drr_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 {
 	struct drr_sched *q = qdisc_priv(sch);
 	struct drr_class *cl;
-	unsigned int len;
 	int err;
 
 	cl = drr_classify(skb, sch, &err);
@@ -362,7 +361,6 @@ static int drr_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 		return err;
 	}
 
-	len = qdisc_pkt_len(skb);
 	err = qdisc_enqueue(skb, cl->qdisc);
 	if (unlikely(err != NET_XMIT_SUCCESS)) {
 		if (net_xmit_drop_count(err)) {
@@ -377,10 +375,8 @@ static int drr_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 		cl->deficit = cl->quantum;
 	}
 
-	cl->bstats.packets++;
-	cl->bstats.bytes += len;
-	sch->bstats.packets++;
-	sch->bstats.bytes += len;
+	bstats_update(&cl->bstats, skb);
+	qdisc_bstats_update(sch, skb);
 
 	sch->q.qlen++;
 	return err;
diff --git a/net/sched/sch_dsmark.c b/net/sched/sch_dsmark.c
index 1d295d6..60f4bdd 100644
--- a/net/sched/sch_dsmark.c
+++ b/net/sched/sch_dsmark.c
@@ -260,8 +260,7 @@ static int dsmark_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 		return err;
 	}
 
-	sch->bstats.bytes += qdisc_pkt_len(skb);
-	sch->bstats.packets++;
+	qdisc_bstats_update(sch, skb);
 	sch->q.qlen++;
 
 	return NET_XMIT_SUCCESS;
diff --git a/net/sched/sch_hfsc.c b/net/sched/sch_hfsc.c
index 069c62b..2e45791 100644
--- a/net/sched/sch_hfsc.c
+++ b/net/sched/sch_hfsc.c
@@ -1599,10 +1599,8 @@ hfsc_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 	if (cl->qdisc->q.qlen == 1)
 		set_active(cl, qdisc_pkt_len(skb));
 
-	cl->bstats.packets++;
-	cl->bstats.bytes += qdisc_pkt_len(skb);
-	sch->bstats.packets++;
-	sch->bstats.bytes += qdisc_pkt_len(skb);
+	bstats_update(&cl->bstats, skb);
+	qdisc_bstats_update(sch, skb);
 	sch->q.qlen++;
 
 	return NET_XMIT_SUCCESS;
diff --git a/net/sched/sch_htb.c b/net/sched/sch_htb.c
index 01b519d..984c1b0 100644
--- a/net/sched/sch_htb.c
+++ b/net/sched/sch_htb.c
@@ -569,15 +569,12 @@ static int htb_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 		}
 		return ret;
 	} else {
-		cl->bstats.packets +=
-			skb_is_gso(skb)?skb_shinfo(skb)->gso_segs:1;
-		cl->bstats.bytes += qdisc_pkt_len(skb);
+		bstats_update(&cl->bstats, skb);
 		htb_activate(q, cl);
 	}
 
 	sch->q.qlen++;
-	sch->bstats.packets += skb_is_gso(skb)?skb_shinfo(skb)->gso_segs:1;
-	sch->bstats.bytes += qdisc_pkt_len(skb);
+	qdisc_bstats_update(sch, skb);
 	return NET_XMIT_SUCCESS;
 }
 
@@ -648,12 +645,10 @@ static void htb_charge_class(struct htb_sched *q, struct htb_class *cl,
 				htb_add_to_wait_tree(q, cl, diff);
 		}
 
-		/* update byte stats except for leaves which are already updated */
-		if (cl->level) {
-			cl->bstats.bytes += bytes;
-			cl->bstats.packets += skb_is_gso(skb)?
-					skb_shinfo(skb)->gso_segs:1;
-		}
+		/* update basic stats except for leaves which are already updated */
+		if (cl->level)
+			bstats_update(&cl->bstats, skb);
+
 		cl = cl->parent;
 	}
 }
diff --git a/net/sched/sch_ingress.c b/net/sched/sch_ingress.c
index f10e34a..bce1665 100644
--- a/net/sched/sch_ingress.c
+++ b/net/sched/sch_ingress.c
@@ -63,8 +63,7 @@ static int ingress_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 
 	result = tc_classify(skb, p->filter_list, &res);
 
-	sch->bstats.packets++;
-	sch->bstats.bytes += qdisc_pkt_len(skb);
+	qdisc_bstats_update(sch, skb);
 	switch (result) {
 	case TC_ACT_SHOT:
 		result = TC_ACT_SHOT;
diff --git a/net/sched/sch_multiq.c b/net/sched/sch_multiq.c
index 32690de..21f13da 100644
--- a/net/sched/sch_multiq.c
+++ b/net/sched/sch_multiq.c
@@ -83,8 +83,7 @@ multiq_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 
 	ret = qdisc_enqueue(skb, qdisc);
 	if (ret == NET_XMIT_SUCCESS) {
-		sch->bstats.bytes += qdisc_pkt_len(skb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, skb);
 		sch->q.qlen++;
 		return NET_XMIT_SUCCESS;
 	}
diff --git a/net/sched/sch_netem.c b/net/sched/sch_netem.c
index e5593c0..1c4bce8 100644
--- a/net/sched/sch_netem.c
+++ b/net/sched/sch_netem.c
@@ -240,8 +240,7 @@ static int netem_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 
 	if (likely(ret == NET_XMIT_SUCCESS)) {
 		sch->q.qlen++;
-		sch->bstats.bytes += qdisc_pkt_len(skb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, skb);
 	} else if (net_xmit_drop_count(ret)) {
 		sch->qstats.drops++;
 	}
@@ -477,8 +476,7 @@ static int tfifo_enqueue(struct sk_buff *nskb, struct Qdisc *sch)
 		__skb_queue_after(list, skb, nskb);
 
 		sch->qstats.backlog += qdisc_pkt_len(nskb);
-		sch->bstats.bytes += qdisc_pkt_len(nskb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, nskb);
 
 		return NET_XMIT_SUCCESS;
 	}
diff --git a/net/sched/sch_prio.c b/net/sched/sch_prio.c
index b1c95bc..966158d 100644
--- a/net/sched/sch_prio.c
+++ b/net/sched/sch_prio.c
@@ -84,8 +84,7 @@ prio_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 
 	ret = qdisc_enqueue(skb, qdisc);
 	if (ret == NET_XMIT_SUCCESS) {
-		sch->bstats.bytes += qdisc_pkt_len(skb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, skb);
 		sch->q.qlen++;
 		return NET_XMIT_SUCCESS;
 	}
diff --git a/net/sched/sch_red.c b/net/sched/sch_red.c
index a67ba3c..a6009c5 100644
--- a/net/sched/sch_red.c
+++ b/net/sched/sch_red.c
@@ -94,8 +94,7 @@ static int red_enqueue(struct sk_buff *skb, struct Qdisc* sch)
 
 	ret = qdisc_enqueue(skb, child);
 	if (likely(ret == NET_XMIT_SUCCESS)) {
-		sch->bstats.bytes += qdisc_pkt_len(skb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, skb);
 		sch->q.qlen++;
 	} else if (net_xmit_drop_count(ret)) {
 		q->stats.pdrop++;
diff --git a/net/sched/sch_sfq.c b/net/sched/sch_sfq.c
index d54ac94..239ec53 100644
--- a/net/sched/sch_sfq.c
+++ b/net/sched/sch_sfq.c
@@ -403,8 +403,7 @@ sfq_enqueue(struct sk_buff *skb, struct Qdisc *sch)
 		slot->allot = q->scaled_quantum;
 	}
 	if (++sch->q.qlen <= q->limit) {
-		sch->bstats.bytes += qdisc_pkt_len(skb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, skb);
 		return NET_XMIT_SUCCESS;
 	}
 
diff --git a/net/sched/sch_tbf.c b/net/sched/sch_tbf.c
index 641a30d..77565e7 100644
--- a/net/sched/sch_tbf.c
+++ b/net/sched/sch_tbf.c
@@ -134,8 +134,7 @@ static int tbf_enqueue(struct sk_buff *skb, struct Qdisc* sch)
 	}
 
 	sch->q.qlen++;
-	sch->bstats.bytes += qdisc_pkt_len(skb);
-	sch->bstats.packets++;
+	qdisc_bstats_update(sch, skb);
 	return NET_XMIT_SUCCESS;
 }
 
diff --git a/net/sched/sch_teql.c b/net/sched/sch_teql.c
index 106479a..af9360d 100644
--- a/net/sched/sch_teql.c
+++ b/net/sched/sch_teql.c
@@ -83,8 +83,7 @@ teql_enqueue(struct sk_buff *skb, struct Qdisc* sch)
 
 	if (q->q.qlen < dev->tx_queue_len) {
 		__skb_queue_tail(&q->q, skb);
-		sch->bstats.bytes += qdisc_pkt_len(skb);
-		sch->bstats.packets++;
+		qdisc_bstats_update(sch, skb);
 		return NET_XMIT_SUCCESS;
 	}
 



^ permalink raw reply related


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