Netdev List
 help / color / mirror / Atom feed
* Re: [IOC3] IP27: Really set PCI64_ATTR_VIRTUAL, not PCI64_ATTR_PREC.
From: Ingo Oeser @ 2006-06-20  8:15 UTC (permalink / raw)
  To: Ralf Baechle; +Cc: netdev, Jeff Garzik
In-Reply-To: <20060617175738.GA4346@linux-mips.org>

Hi Ralf,

Ralf Baechle :
> IOC3's homegrown DMA mapping functions that are used to optimize things
> a little on IP27 set the wrong bit.

What about using a symbol instead of magic numbers?
That way one at least sees the intention of the coder.
 
> Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
> 
> diff --git a/drivers/net/ioc3-eth.c b/drivers/net/ioc3-eth.c
> index ae71ed5..e76e6e7 100644
> --- a/drivers/net/ioc3-eth.c
> +++ b/drivers/net/ioc3-eth.c
> @@ -145,7 +145,7 @@ static inline struct sk_buff * ioc3_allo
>  static inline unsigned long ioc3_map(void *ptr, unsigned long vdev)
>  {
>  #ifdef CONFIG_SGI_IP27
> -	vdev <<= 58;   /* Shift to PCI64_ATTR_VIRTUAL */
> +	vdev <<= 57;   /* Shift to PCI64_ATTR_VIRTUAL */

So please use a symbolic value here.
  

Regards

Ingo Oeser

^ permalink raw reply

* Re: [DOC]: generic netlink
From: Thomas Graf @ 2006-06-20  8:02 UTC (permalink / raw)
  To: jamal; +Cc: netdev, David S. Miller, Jay Lan, Shailabh Nagar, Per Liden
In-Reply-To: <1150724482.5815.48.camel@jzny2>

* jamal <hadi@cyberus.ca> 2006-06-19 09:41
> // the attributes you want to own
> 
> enum {
>         FOOBAR_ATTR_UNSPEC,
>         FOOBAR_ATTR_TYPE,
>         FOOBAR_ATTR_TYPEID,
>         FOOBAR_ATTR_TYPENAME,
>         FOOBAR_ATTR_OPER,
> 	/* add future attributes here */
>         __FOOBAR_ATTR_MAX,
> };
> 
> #define FOOBAR_ATTR_MAX (__FOOBAR_ATTR_MAX - 1)

One important point about attributes in generic netlink is that
their scope is per command instead of per family as in netlink.
It's not forbidden to use the same set of attribute identifiers
for two separete commands but it should be avoided to have a
single large list of attributes and have every command pick out
the attributes it needs.


> TODO:
> a) Add a more complete compiling kernel module with events.
> Have Thomas put his Mashimaro example and point to it.

I guess we have a legal issue here ;)

> b) Describe some details on how user space -> kernel works
> probably using libnl??

I'll take care of that.

^ permalink raw reply

* Re: [PATCH 0/2] NET: Accurate packet scheduling for ATM/ADSL
From: Jesper Dangaard Brouer @ 2006-06-20  7:33 UTC (permalink / raw)
  To: Chris Wedgwood; +Cc: netdev, russell-tcatm
In-Reply-To: <20060620053536.GA10311@tuatara.stupidest.org>

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


On Mon, 2006-06-19 at 22:35 -0700, Chris Wedgwood wrote:
> On Wed, Jun 14, 2006 at 11:40:04AM +0200, Jesper Dangaard Brouer wrote:
> 
> > The Linux traffic's control engine inaccurately calculates
> > transmission times for packets sent over ADSL links.  For some
> > packet sizes the error rises to over 50%.  This occurs because ADSL
> > uses ATM as its link layer transport, and ATM transmits packets in
> > fixed sized 53 byte cells.
> 
> What if AAL5 is used?  The cell-alignment math is going to be wrong
> there surely?

Actually it _is_ AAL5 which is accounted for.

See Chapter 5 "ADSL link layer overhead" (page 48-54).
http://www.adsl-optimizer.dk/thesis/main_final_hyper.pdf

-- 
Med venlig hilsen / Best regards
  Jesper Brouer
  ComX Networks A/S
  Linux Network developer
  Cand. Scient Datalog / MSc.
  Author of http://adsl-optimizer.dk


[-- Attachment #2: This is a digitally signed message part --]
[-- Type: application/pgp-signature, Size: 189 bytes --]

^ permalink raw reply

* Re: [Bug 6688] Memory allocation problem
From: Andrew Morton @ 2006-06-20  7:24 UTC (permalink / raw)
  To: netdev
In-Reply-To: <200606200646.k5K6k8Z3009667@fire-2.osdl.org>

On Mon, 19 Jun 2006 23:46:08 -0700
bugme-daemon@bugzilla.kernel.org wrote:

> http://bugzilla.kernel.org/show_bug.cgi?id=6688

This is looking like a net memory leak in 2.6.16.  1/3rd is in ip_fib_alias
and 2/3rds is in size-64.  I've asked the reporter to apply the leak
detector patch so we can find out who is using the size-64 part.

^ permalink raw reply

* Re: [FORCEDETH]: Fix xmit_lock/netif_tx_lock after merge
From: Jeff Garzik @ 2006-06-20  7:21 UTC (permalink / raw)
  To: Herbert Xu; +Cc: David S. Miller, Linus Torvalds, netdev, Ayaz Abdulla
In-Reply-To: <20060620070450.GA12609@gondor.apana.org.au>

Herbert Xu wrote:
> Hi:
> 
> [FORCEDETH]: Fix xmit_lock/netif_tx_lock after merge
> 
> There has been an update to the forcedeth driver that added a few new
> uses of xmit_lock which is no longer meant to be used directly.  This
> patch replaces them with netif_tx_lock_bh.
> 
> Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

ACK.  I'll apply, if Linus doesn't pick this up...

	Jeff




^ permalink raw reply

* Re: [FORCEDETH]: Fix xmit_lock/netif_tx_lock after merge
From: David Miller @ 2006-06-20  7:10 UTC (permalink / raw)
  To: herbert; +Cc: jgarzik, torvalds, netdev, aabdulla
In-Reply-To: <20060620070450.GA12609@gondor.apana.org.au>

From: Herbert Xu <herbert@gondor.apana.org.au>
Date: Tue, 20 Jun 2006 17:04:50 +1000

> [FORCEDETH]: Fix xmit_lock/netif_tx_lock after merge

Thanks for checking out that merge conflict.

Linus, please apply.

^ permalink raw reply

* [FORCEDETH]: Fix xmit_lock/netif_tx_lock after merge
From: Herbert Xu @ 2006-06-20  7:04 UTC (permalink / raw)
  To: Jeff Garzik, David S. Miller, Linus Torvalds, netdev; +Cc: Ayaz Abdulla

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

Hi:

[FORCEDETH]: Fix xmit_lock/netif_tx_lock after merge

There has been an update to the forcedeth driver that added a few new
uses of xmit_lock which is no longer meant to be used directly.  This
patch replaces them with netif_tx_lock_bh.

Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

[-- Attachment #2: forcedeth-xmit-lock.patch --]
[-- Type: text/plain, Size: 2561 bytes --]

diff --git a/drivers/net/forcedeth.c b/drivers/net/forcedeth.c
index 04a53f1..62b38a4 100644
--- a/drivers/net/forcedeth.c
+++ b/drivers/net/forcedeth.c
@@ -2991,13 +2991,13 @@ static int nv_set_settings(struct net_de
 	netif_carrier_off(dev);
 	if (netif_running(dev)) {
 		nv_disable_irq(dev);
-		spin_lock_bh(&dev->xmit_lock);
+		netif_tx_lock_bh(dev);
 		spin_lock(&np->lock);
 		/* stop engines */
 		nv_stop_rx(dev);
 		nv_stop_tx(dev);
 		spin_unlock(&np->lock);
-		spin_unlock_bh(&dev->xmit_lock);
+		netif_tx_unlock_bh(dev);
 	}
 
 	if (ecmd->autoneg == AUTONEG_ENABLE) {
@@ -3131,13 +3131,13 @@ static int nv_nway_reset(struct net_devi
 		netif_carrier_off(dev);
 		if (netif_running(dev)) {
 			nv_disable_irq(dev);
-			spin_lock_bh(&dev->xmit_lock);
+			netif_tx_lock_bh(dev);
 			spin_lock(&np->lock);
 			/* stop engines */
 			nv_stop_rx(dev);
 			nv_stop_tx(dev);
 			spin_unlock(&np->lock);
-			spin_unlock_bh(&dev->xmit_lock);
+			netif_tx_unlock_bh(dev);
 			printk(KERN_INFO "%s: link down.\n", dev->name);
 		}
 
@@ -3244,7 +3244,7 @@ static int nv_set_ringparam(struct net_d
 
 	if (netif_running(dev)) {
 		nv_disable_irq(dev);
-		spin_lock_bh(&dev->xmit_lock);
+		netif_tx_lock_bh(dev);
 		spin_lock(&np->lock);
 		/* stop engines */
 		nv_stop_rx(dev);
@@ -3303,7 +3303,7 @@ static int nv_set_ringparam(struct net_d
 		nv_start_rx(dev);
 		nv_start_tx(dev);
 		spin_unlock(&np->lock);
-		spin_unlock_bh(&dev->xmit_lock);
+		netif_tx_unlock_bh(dev);
 		nv_enable_irq(dev);
 	}
 	return 0;
@@ -3339,13 +3339,13 @@ static int nv_set_pauseparam(struct net_
 	netif_carrier_off(dev);
 	if (netif_running(dev)) {
 		nv_disable_irq(dev);
-		spin_lock_bh(&dev->xmit_lock);
+		netif_tx_lock_bh(dev);
 		spin_lock(&np->lock);
 		/* stop engines */
 		nv_stop_rx(dev);
 		nv_stop_tx(dev);
 		spin_unlock(&np->lock);
-		spin_unlock_bh(&dev->xmit_lock);
+		netif_tx_unlock_bh(dev);
 	}
 
 	np->pause_flags &= ~(NV_PAUSEFRAME_RX_REQ|NV_PAUSEFRAME_TX_REQ);
@@ -3729,7 +3729,7 @@ static void nv_self_test(struct net_devi
 	if (test->flags & ETH_TEST_FL_OFFLINE) {
 		if (netif_running(dev)) {
 			netif_stop_queue(dev);
-			spin_lock_bh(&dev->xmit_lock);
+			netif_tx_lock_bh(dev);
 			spin_lock_irq(&np->lock);
 			nv_disable_hw_interrupts(dev, np->irqmask);
 			if (!(np->msi_flags & NV_MSI_X_ENABLED)) {
@@ -3745,7 +3745,7 @@ static void nv_self_test(struct net_devi
 			nv_drain_rx(dev);
 			nv_drain_tx(dev);
 			spin_unlock_irq(&np->lock);
-			spin_unlock_bh(&dev->xmit_lock);
+			netif_tx_unlock_bh(dev);
 		}
 
 		if (!nv_register_test(dev)) {

^ permalink raw reply related

* Re: [NET]: Prevent multiple qdisc runs
From: Herbert Xu @ 2006-06-20  7:00 UTC (permalink / raw)
  To: David Miller; +Cc: netdev
In-Reply-To: <20060619.235719.58454931.davem@davemloft.net>

On Mon, Jun 19, 2006 at 11:57:19PM -0700, David Miller wrote:
> 
> But this is yet another atomic operation on the transmit
> path :-(  This problem, however, is inevitable because of
> how we do things and thus isn't the fault of your change.
> 
> I'm going to apply this patch to 2.6.18, however...  we should split
> up the dev->state handling into seperate cacheline synchronizers.
> Sharing RX and TX locking bits in the same word is not all that
> efficient.

Good point.  This particular bit doesn't even need to be atomic since
it's sitting inside a spinlock.

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply

* Re: [NET]: Prevent multiple qdisc runs
From: David Miller @ 2006-06-20  6:57 UTC (permalink / raw)
  To: herbert; +Cc: netdev
In-Reply-To: <20060619121519.GA16031@gondor.apana.org.au>

From: Herbert Xu <herbert@gondor.apana.org.au>
Date: Mon, 19 Jun 2006 22:15:19 +1000

> [NET]: Prevent multiple qdisc runs

I have no real objection to this semantically.

But this is yet another atomic operation on the transmit
path :-(  This problem, however, is inevitable because of
how we do things and thus isn't the fault of your change.

I'm going to apply this patch to 2.6.18, however...  we should split
up the dev->state handling into seperate cacheline synchronizers.
Sharing RX and TX locking bits in the same word is not all that
efficient.

Thanks.

^ permalink raw reply

* Re: [PKT_SCHED]: PSCHED_TADD() and PSCHED_TADD2() can result,tv_usec >= 1000000
From: David Miller @ 2006-06-20  6:51 UTC (permalink / raw)
  To: maeda-sxb; +Cc: netdev
In-Reply-To: <449637EE.4020608@necst.nec.co.jp>

From: Shuya MAEDA <maeda-sxb@necst.nec.co.jp>
Date: Mon, 19 Jun 2006 14:36:46 +0900

>  #define PSCHED_TADD2(tv, delta, tv_res) \
>  ({ \
> -          int __delta = (tv).tv_usec + (delta); \
> -          (tv_res).tv_sec = (tv).tv_sec; \
> -          if (__delta > USEC_PER_SEC) { (tv_res).tv_sec++; __delta -= USEC_PER_SEC; } \
> -          (tv_res).tv_usec = __delta; \
> +          int __delta = (delta); \
> +          (tv_res) = (tv); \
> +          if((delta) > USEC_PER_SEC) { \
> +                (tv_res).tv_sec += (delta) / USEC_PER_SEC; \
> +                __delta -= (delta) % USEC_PER_SEC; \
> +          } \
> +          (tv_res).tv_usec += __delta; \
> +          if((tv_res).tv_usec >= USEC_PER_SEC) { \
> +                (tv_res).tv_sec++; \
> +                (tv_res).tv_usec -= USEC_PER_SEC; \
> +          } \
>  })

Divide and modulus can be extremely expensive on some systems, so
let's try to avoid using them.

It is probably sufficient to adjust the passed in delta only once if
it is >= USEC_PER_SEC, but if you feel that is an unsafe assumption
then please use a simply loop like this:

	while (__delta >= USEC_PER_SEC) {
		(tv_res).tv_sec++;
		__delta -= USEC_PER_SEC;
	}

And please provide a proper "Signed-off-by: " line in your next
patch submission.

Thank you very much.

^ permalink raw reply

* rtl8150 usb driver, needs more vendor ids?
From: Ben Greear @ 2006-06-20  6:46 UTC (permalink / raw)
  To: NetDev, petkan

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

Someone put a wired usb-to-ethernet adapter into a system running
the 2.6.13.5 kernel.  The driver is evidently the rtl8150, and this
person sent me what appeared to be a modified version of the rtl8150
that is in the kernel.  The kernel driver does not appear to even attempt
to use this device.

Here is the output from /proc/bus/usb/devices:

T:  Bus=01 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#=  4 Spd=12  MxCh= 0
D:  Ver= 1.10 Cls=00(>ifc ) Sub=00 Prot=00 MxPS= 8 #Cfgs=  1
P:  Vendor=07a6 ProdID=8511 Rev= 1.01
S:  Manufacturer=ADMtek
S:  Product=USB To LAN Converter
S:  SerialNumber=0001
C:* #Ifs= 1 Cfg#= 1 Atr=a0 MxPwr=160mA
I:  If#= 0 Alt= 0 #EPs= 3 Cls=00(>ifc ) Sub=00 Prot=00 Driver=(none)
E:  Ad=81(I) Atr=02(Bulk) MxPS=  64 Ivl=0ms
E:  Ad=02(O) Atr=02(Bulk) MxPS=  64 Ivl=0ms
E:  Ad=83(I) Atr=03(Int.) MxPS=   8 Ivl=1ms

The vendor driver (GPL) I received is available here:
http://www.candelatech.com/oss/RTL8150.C

When I get a chance later this week, I plan to add this vendor id
and see if it works.  Since the physical equipment is half a world
away, I'd welcome any conjecture as to whether simply adding the
device ID will work or not...

Thanks,
Ben

-- 
Ben Greear <greearb@candelatech.com>
Candela Technologies Inc  http://www.candelatech.com


[-- Attachment #2: RTL8150.C --]
[-- Type: text/x-c++src, Size: 35649 bytes --]

/*
**	Pegasus: USB 10/100Mbps/HomePNA (1Mbps) Controller
**
**	Copyright (c) 1999,2000 Petko Manolov - Petkan (petkan@dce.bg)
**	
**
**	ChangeLog:
**		....	Most of the time spend reading sources & docs.
**		v0.2.x	First official release for the Linux kernel.
**		v0.3.0	Beutified and structured, some bugs fixed.
**		v0.3.x	URBifying bulk requests and bugfixing. First relatively
**			stable release. Still can touch device's registers only
**			from top-halves.
**		v0.4.0	Control messages remained unurbified are now URBs.
**			Now we can touch the HW at any time.
**		v0.4.9	Control urbs again use process context to wait. Argh...
**			Some long standing bugs (enable_net_traffic) fixed.
**			Also nasty trick about resubmiting control urb from
**			interrupt context used. Please let me know how it
**			behaves. Pegasus II support added since this version.
**			TODO: suppressing HCD warnings spewage on disconnect.
**		v0.4.13	Ethernet address is now set at probe(), not at open()
**			time as this seems to break dhcpd. 
*/

/*
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
 */

 /*
 **
 **	ChangeLog of Realtek:
 **		1.0.0	First release for RTL8150 USB Fast Ethernet NIC
 **
 */


#include <linux/module.h>
#include <linux/sched.h>
#include <linux/malloc.h>
#include <linux/init.h>
#include <linux/delay.h>
#include <linux/netdevice.h>
#include <linux/etherdevice.h>
#include <linux/usb.h>


static const char *version = __FILE__ ": v1.0.0 2001/01/31 (C) 2001 Realtek Semiconductor Corp.(shwei@realtek.com.tw)";


/// define this to use interrupt endpoint 3
#define	RTL8150_USE_INTR	


#define	RTL8150_MTU			1500
#define	RTL8150_MAX_MTU			1536
#define RTL8150_MIN_PACKET_LENGTH	60


/// phy registers index
#define MII_PHY_ID1	0x02
#define MII_PHY_ID2	0x03


/// manufacture ID of HPNA PHY 
#define AMD_PHY_ID	0x6b90
#define NS_PHY_ID	0x5c20


/// rtl8150->features
#define	FEATURE_DEFAULT		0x00
#define	FEATURE_HAS_HOME_PNA	0x01


/// rtl8150 states
#define	RTL8150_PRESENT		0x00000001
#define	RTL8150_RUNNING		0x00000002
#define	RTL8150_TX_BUSY		0x00000004
#define	RTL8150_RX_BUSY		0x00000008
#define	RTL8150_UNPLUG		0x00000040


/// ctrl urb
#define	CTRL_URB_RUNNING	0x00000010
#define	CTRL_URB_SLEEP		0x00000020

//#define	ETH_REGS_CHANGE		0x40000000
#define	ETH_REGS_CHANGED	0x80000000

#define	REG_TIMEOUT		(HZ)
#define	RTL8150_TX_TIMEOUT	(HZ*10)


/// vendor memory read & write
#define	RTL8150_REQT_READ	0xc0
#define	RTL8150_REQT_WRITE	0x40
#define	RTL8150_REQ_GET_REG	0x05
#define	RTL8150_REQ_SET_REG	0x05


#define	NUM_CTRL_URBS		0x10
#define	ALIGN(x)		x __attribute__((aligned(L1_CACHE_BYTES)))


#define SIZE32_BIT0		0x00000001
#define SIZE32_BIT1		0x00000002
#define SIZE32_BIT2		0x00000004
#define SIZE32_BIT3		0x00000008
#define SIZE32_BIT4		0x00000010
#define SIZE32_BIT5		0x00000020
#define SIZE32_BIT6		0x00000040
#define SIZE32_BIT7		0x00000080
#define SIZE32_BIT8		0x00000100
#define SIZE32_BIT9		0x00000200
#define SIZE32_BIT10		0x00000400
#define SIZE32_BIT11		0x00000800
#define SIZE32_BIT12		0x00001000
#define SIZE32_BIT13		0x00002000
#define SIZE32_BIT14		0x00004000
#define SIZE32_BIT15		0x00008000
#define SIZE32_BIT16		0x00010000
#define SIZE32_BIT17		0x00020000
#define SIZE32_BIT18		0x00040000
#define SIZE32_BIT19		0x00080000
#define SIZE32_BIT20		0x00100000
#define SIZE32_BIT21		0x00200000
#define SIZE32_BIT22		0x00400000
#define SIZE32_BIT23		0x00800000
#define SIZE32_BIT24		0x01000000
#define SIZE32_BIT25		0x02000000
#define SIZE32_BIT26		0x04000000
#define SIZE32_BIT27		0x08000000
#define SIZE32_BIT28		0x10000000
#define SIZE32_BIT29		0x20000000
#define SIZE32_BIT30		0x40000000
#define SIZE32_BIT31		0x80000000


#define SIZE16_BIT0		0x0001
#define SIZE16_BIT1		0x0002
#define SIZE16_BIT2		0x0004
#define SIZE16_BIT3		0x0008
#define SIZE16_BIT4		0x0010
#define SIZE16_BIT5		0x0020
#define SIZE16_BIT6		0x0040
#define SIZE16_BIT7		0x0080
#define SIZE16_BIT8		0x0100
#define SIZE16_BIT9		0x0200
#define SIZE16_BIT10		0x0400
#define SIZE16_BIT11		0x0800
#define SIZE16_BIT12		0x1000
#define SIZE16_BIT13		0x2000
#define SIZE16_BIT14		0x4000
#define SIZE16_BIT15		0x8000


#define SIZE8_BIT0		0x01
#define SIZE8_BIT1		0x02
#define SIZE8_BIT2		0x04
#define SIZE8_BIT3		0x08
#define SIZE8_BIT4		0x10
#define SIZE8_BIT5		0x20
#define SIZE8_BIT6		0x40
#define SIZE8_BIT7		0x80


/// registers index
#define IDR0			0x0120
#define Command			0x012e
#define TxConfig		0x012f
#define RxConfig		0x0130
#define TxStst			0x0132
#define RxStst			0x0133
#define Config			0x0135
#define Config1			0x0136
#define MediaStst		0x0137
#define MiiPhyAddr		0x0138
#define MiiPhyData		0x0139
#define MiiPhyAccess		0x013b
#define GPPCtrl			0x013d
#define WakeUpEventCtrl		0x013e
#define BasicModeCtrl		0x0140
#define BasicModeStst		0x0142
#define AutoNegoAdver		0x0144
#define AutoNegoLinkPartner	0x0146
#define AutoNegoExpan		0x0148
#define NwayTst			0x014a
#define CSConfig		0x014c


/// which HPNA PHY
enum hpna_phy {
	UNKNOWN_PHY = 0,
	AMD_PHY = 1,
	NS_PHY = 2,
};


/// loopback mode
enum loopback_mode{
	NORMAL_OPERATION = 0,
	DIGITAL_LOOPBACK = 1,
	ANALOG_LOOPBACK = 2,
};


/// EEPROM index
#define		EPROM_IDR0	 	0x1202
#define 	EPROM_Config0   	0x1208
#define	  	EPROM_MSR		0x1209
#define 	EPROM_GPCP		0x120a
#define		EPROM_UDP		0x120b
#define		EPROM_ATTR		0x120c
#define		EPROM_PHY2_PARM		0x120d
#define		EPROM_PHY1_PARM		0x120e
#define		EPROM_TW1_PARM		0x1212
#define		EPROM_MAXPOR		0x1216
#define		EPROM_Interv		0x1217
#define		EPROM_LanguageID	0x1218
#define		EPROM_ManufactureID	0x121a
#define 	EPROM_ProductID		0x121c
#define		EPROM_SerialNumber	0x121e
#define		EPROM_ManufactureString	0x1228
#define		EPROM_ProductString	0x1250


/// Command Register
#define 	WEPROM			SIZE8_BIT5
#define 	SOFT_RST		SIZE8_BIT4
#define		RE			SIZE8_BIT3
#define		TE			SIZE8_BIT2
#define 	EP3CLEAR		SIZE8_BIT1
#define 	AUTOLOAD      		SIZE8_BIT0


/// Transmit Configuration Register
#define		TXRR1			SIZE8_BIT7
#define		TXRR0			SIZE8_BIT6
#define 	IFG1			SIZE8_BIT4
#define		IFG0			SIZE8_BIT3
#define 	LBK1			SIZE8_BIT2
#define 	LBK0			SIZE8_BIT1
#define		NOCRC			SIZE8_BIT0


/// Receive Configuration Register
#define 	EARRX			SIZE16_BIT10
#define		TAIL			SIZE16_BIT7
#define		AER		   	SIZE16_BIT6
#define		AR		    	SIZE16_BIT5
#define		AM		   	SIZE16_BIT4
#define		AB		    	SIZE16_BIT3
#define		AD		    	SIZE16_BIT2
#define		AAM		 	SIZE16_BIT1
#define		AAP		   	SIZE16_BIT0

/// Transmit Status Register
#define 	ECOL			SIZE8_BIT5
#define		LCOL			SIZE8_BIT4
#define 	LOSS_CRS		SIZE8_BIT3
#define		JBR			SIZE8_BIT2
#define 	TX_BUF_EMPTY		SIZE8_BIT1
#define		TX_BUF_FULL		SIZE8_BIT0

/// Receive Status Register
#define		WEVENT			SIZE8_BIT7
#define		RX_BUF_FULL		SIZE8_BIT6
#define		LKCHG			SIZE8_BIT5
#define 	RUNT			SIZE8_BIT4
#define		LONG			SIZE8_BIT3
#define 	CRC			SIZE8_BIT2
#define		FAE			SIZE8_BIT1
#define		ROK			SIZE8_BIT0

/// Configuration Register0
#define		SUSLED			SIZE8_BIT7
#define		PARM_EN			SIZE8_BIT6
#define		LDPS			SIZE8_BIT3
#define		MSEL			SIZE8_BIT2
#define		LEDS1			SIZE8_BIT1
#define 	LEDS0			SIZE8_BIT0

/// Configuration Register1
#define 	BWF			SIZE8_BIT6
#define		MWF			SIZE8_BIT5
#define		UWF			SIZE8_BIT4
#define		LONGWF1			SIZE8_BIT1
#define		LONGWF0			SIZE8_BIT0

/// Media Status Register
#define		TXFCE			SIZE8_BIT7
#define		RXFCE			SIZE8_BIT6
#define		DUPLEX			SIZE8_BIT4
#define		SPEED_100		SIZE8_BIT3
#define 	LINK			SIZE8_BIT2
#define		TXPF			SIZE8_BIT1
#define		RXPF			SIZE8_BIT0


typedef struct rtl8150 {
	struct usb_device	*usb; // store "dev" passed in rtl8150_probe( struct usb_device *dev...)
	struct net_device	*net; // store "net" returned by init_etherdev()
	struct net_device_stats	stats;
	unsigned		flags;
	unsigned		features;
	int			intr_interval;
	struct urb		ctrl_urb, rx_urb, tx_urb, intr_urb;
	devrequest		dr;
	wait_queue_head_t	ctrl_wait;
	struct semaphore	ctrl_sem;
	unsigned char		ALIGN(rx_buff[RTL8150_MAX_MTU]);
	unsigned char		ALIGN(tx_buff[RTL8150_MAX_MTU]);
	unsigned char		ALIGN(intr_buff[8]);
	__u8			eth_regs[4];
	__u8			phy;
	__u8			hpna_phy;
	__u8			gpio_res;
	
	/// added by Owen on 01/11/2000
	__u8			get_registers_flag;
	__u8			set_registers_flag;
} rtl8150_t;


struct usb_eth_dev {
	char	*name;
	__u16	vendor;
	__u16	device;
	__u32	private; /* LSB is gpio reset value */
};


static int loopback = 0;
static int mii_mode = 0;
static int multicast_filter_limit = 32;


MODULE_AUTHOR("shwei@realtek.com.tw");
MODULE_DESCRIPTION("Realtek RTL8150 USB 10/100 Fast Ethernet Driver");
MODULE_PARM(loopback, "i");
MODULE_PARM(mii_mode, "i");
MODULE_PARM_DESC(loopback, "Enable MAC loopback mode (bit 0)");
MODULE_PARM_DESC(mii_mode, "Enable HomePNA mode (bit 0) - default = MII mode = 0");


static struct usb_eth_dev usb_dev_id[] = {
	{"Realtek RTL8150 USB 10/100 Fast Ethernet Adatper", 0x0bda, 0x8150, FEATURE_DEFAULT},
	{"Realtek RTL8150 USB 1Mbps HomePNA", 0x0bda, 0x8151, FEATURE_HAS_HOME_PNA | FEATURE_DEFAULT},
	{NULL, 0, 0, 0}
};

static void set_registers_callback( urb_t *urb )
{
	rtl8150_t	*rtl8150 = urb->context;

	//info( "+set_registers_callback()");

	if ( !rtl8150 )
		return;

	switch ( urb->status ) {
		case USB_ST_NOERROR:
			break;
		case USB_ST_URB_PENDING:
			//info( " set_registers_callback: case USB_ST_URB_PENDING" );
			return;
		case USB_ST_URB_KILLED:
			break;
		default:
			//info( " set_registers_callback: default: status = 0x%x", urb->status );
			warn( __FUNCTION__ " status %d", urb->status);
	}
	rtl8150->flags &= ~ETH_REGS_CHANGED;
	if ( rtl8150->flags & CTRL_URB_SLEEP )
	{
		rtl8150->flags &= ~CTRL_URB_SLEEP;
		/// marked and added by Owen on 01/11/2001
		///wake_up_interruptible( &rtl8150->ctrl_wait );
		rtl8150->set_registers_flag = 0;
	}
	
	//info("-set_registers_callback()");
}


static void get_registers_callback( urb_t *urb )
{
	rtl8150_t	*rtl8150 = urb->context;

	///info( "+get_registers_callback()");

	if ( !rtl8150 )
		return;

	switch ( urb->status ) {
		case USB_ST_NOERROR:
			break;
		case USB_ST_URB_PENDING:
			//info( " get_registers_callback: case USB_ST_URB_PENDING" );
			return;
		case USB_ST_URB_KILLED:
			break;
		default:
			//info( " get_registers_callback: default: status = 0x%x", urb->status );
			warn( __FUNCTION__ " status %d", urb->status);
	}
	rtl8150->flags &= ~ETH_REGS_CHANGED;
	if ( rtl8150->flags & CTRL_URB_SLEEP ) 
	{
		rtl8150->flags &= ~CTRL_URB_SLEEP;
		/// marked and added by Owen on 01/11/2001
		///wake_up_interruptible( &rtl8150->ctrl_wait );
		rtl8150->get_registers_flag = 0;
	}
	
	///info("-get_registers_callback()");
}


static int get_registers(rtl8150_t *rtl8150, __u16 indx, __u16 size, void *data)
{
	int	ret;

	///info( "+get_registers()=====>" );

	rtl8150->dr.requesttype = RTL8150_REQT_READ;
	rtl8150->dr.request = RTL8150_REQ_GET_REG;
	rtl8150->dr.value = cpu_to_le16p(&indx);
	rtl8150->dr.index = 0;
	rtl8150->dr.length = 
	rtl8150->ctrl_urb.transfer_buffer_length = cpu_to_le16p(&size);

	FILL_CONTROL_URB( &rtl8150->ctrl_urb, rtl8150->usb,
			  usb_rcvctrlpipe(rtl8150->usb,0),
			  (char *)&rtl8150->dr,
			  data, size, get_registers_callback, rtl8150 );

	if ( (ret = usb_submit_urb( &rtl8150->ctrl_urb )) ) {
		info( " get_registers: usb_submit_urb failed" );	
		err( __FUNCTION__ " BAD CTRLs %d", ret);
		goto out;
	}
	rtl8150->flags |= CTRL_URB_SLEEP;
	/// marked by Owen on 01/11/2001
	//interruptible_sleep_on( &rtl8150->ctrl_wait );
out:
	///info( "-get_registers()<=====" );
	return	ret;
}


static int set_registers(rtl8150_t *rtl8150, __u16 indx, __u16 size, void *data)
{
	int	ret;

	///info( "+set_registers() =====>" );

	/// marked by Owen on 01/11/2001
	//if ( rtl8150->flags & ETH_REGS_CHANGED ) {
	//	rtl8150->flags |= CTRL_URB_SLEEP ;
	//	interruptible_sleep_on( &rtl8150->ctrl_wait );
	//}
	rtl8150->dr.requesttype = RTL8150_REQT_WRITE;
	rtl8150->dr.request = RTL8150_REQ_SET_REG;
	rtl8150->dr.value = cpu_to_le16p( &indx );
	rtl8150->dr.index = 0;
	rtl8150->dr.length = rtl8150->ctrl_urb.transfer_buffer_length = cpu_to_le16p( &size );

	FILL_CONTROL_URB( &rtl8150->ctrl_urb, rtl8150->usb,
			  usb_sndctrlpipe(rtl8150->usb,0),
			  (char *)&rtl8150->dr,
			  data, size, set_registers_callback, rtl8150 );

	if ( (ret = usb_submit_urb( &rtl8150->ctrl_urb )) ) {
		info( " set_registers: usb_submit_urb failed" );
		err( __FUNCTION__ " BAD CTRL %d", ret);
		return	ret;
	}
	rtl8150->flags |= CTRL_URB_SLEEP;
	/// marked by Owen on 01/11/2001
	//interruptible_sleep_on( &rtl8150->ctrl_wait );
	
	///info( "-set_registers()<=====" );

	return	ret;
}



static int read_phy_word( rtl8150_t *rtl8150, __u8 phy, __u8 indx, __u16 *regd )
{
	int	i;
	__u8	MiiPhyAccessContent;

	/*
	set_register( rtl8150, MiiPhyAccess, 0 );
	set_register( rtl8150, MiiPhyAddr, phy );
	set_register( rtl8150, MiiPhyAccess, (0x40 | indx) );
	for (i = 0; i < REG_TIMEOUT; i++) 
	{
		get_registers( rtl8150, MiiPhyAccess, 1, &MiiPhyAccessContent );
		if ( (MiiPhyAccessContent & 0x40) == 0)
			break;
	}
	if ( i < REG_TIMEOUT ) 
	{
		get_registers( rtl8150, MiiPhyData, 2, regd );
		return	0;
	}
	warn( __FUNCTION__ " failed" );
	*/
	
	return 1;
}



static int write_phy_word( rtl8150_t *rtl8150, __u8 phy, __u8 indx, __u16 regd )
{
	int	i;
	__u8	data[2] = { 0, 0 };
	__u8	MiiPhyAccessContent;
	
	//info( "write_phy_word() =====>" );

	/*
	*data = cpu_to_le16p( &regd );
	set_register( rtl8150, MiiPhyAccess, 0 );
	set_register( rtl8150, MiiPhyAddr, phy );
	set_registers( rtl8150, MiiPhyData, 2, data );
	set_register( rtl8150, MiiPhyAccess, (0x60 | indx) );
	for (i = 0; i < REG_TIMEOUT; i++) 
	{
		get_registers( rtl8150, MiiPhyAccess, 1, &MiiPhyAccessContent );
		if ( (MiiPhyAccessContent & 0x40) == 0)
			break;
	}

	if ( i < REG_TIMEOUT )
		return	0;
	
	warn( __FUNCTION__ " failed" );
	*/

	return 1;
}



static int read_eprom_word( rtl8150_t *rtl8150, __u8 index, __u16 *retdata )
{
	int	i, tmp;

	//info( "+read_eprom_word() =====>" );

	while( rtl8150->get_registers_flag == 1 )
		;
	rtl8150->get_registers_flag = 1;
	get_registers( rtl8150, index, 2, retdata );
	while( rtl8150->get_registers_flag == 1 )
		;
	
	//info( "-read_eprom_word() <=====" );
	return	0;
}



static int read_eprom_byte( rtl8150_t *rtl8150, __u16 index, __u8 *retdata )
{
	int	i, tmp;

	//info( "+read_eprom_byte() =====>" );

	while( rtl8150->get_registers_flag == 1 )
		;
	rtl8150->get_registers_flag = 1;
	get_registers( rtl8150,  index, 1, retdata );
	while( rtl8150->get_registers_flag == 1 )
		;
	
	//info( "-read_eprom_byte() <=====");

	return 0;
}

#ifdef	RTL8150_WRITE_EEPROM
static inline void enable_eprom_write( rtl8150_t *rtl8150 )
{
	__u8	tmp;

	//info( "+enable_eprom_write() =====>" );

	//info( "-enable_eprom_write() <=====" );
}


static inline void disable_eprom_write( rtl8150_t *rtl8150 )
{
	__u8 	tmp;

	//info( "+disable_eprom_write() =====>" );
	
	//info( "-disable_eprom_write() <=====" );
}


static int write_eprom_word( rtl8150_t *rtl8150, __u8 index, __u16 data )
{
	int	i, tmp;
	__u8	d[4] = {0x3f, 0, 0, EPROM_WRITE};

	//info( "+write_eprom_word() =====>" );

	/*
	set_registers( rtl8150, EpromOffset, 4, d );
	enable_eprom_write( rtl8150 );
	set_register( rtl8150, EpromOffset, index );
	set_registers( rtl8150, EpromData, 2, &data );
	set_register( rtl8150, EpromCtrl, EPROM_WRITE );

	for ( i=0; i < REG_TIMEOUT; i++ ) {
		get_registers( rtl8150, EpromCtrl, 1, &tmp );
		if ( tmp & EPROM_DONE )
			break;
	}
	disable_eprom_write( rtl8150 );
	if ( i < REG_TIMEOUT )
		return	0;
	warn( __FUNCTION__ " failed" );
	*/
	//info( "-write_eprom_word <=====");
	return	-1;
}
#endif	/* RTL8150_WRITE_EEPROM */


static inline void get_node_id( rtl8150_t *rtl8150, __u8 *id )
{
	int	i;

	info( "+get_node_id() =====>" );
	for (i=0; i < 6; i++)
	{
		while( rtl8150->get_registers_flag == 1 )
			;
		rtl8150->get_registers_flag = 1;
		get_registers( rtl8150, IDR0+i, 1, &id[i] );
		while( rtl8150->get_registers_flag == 1 )
			;
	}
	info( "-get_node_id() <=====" );
}


static void set_ethernet_addr( rtl8150_t *rtl8150 )
{
	__u8	node_id[6];

	info( "+set_ethernet_addr() =====>" );
	get_node_id(rtl8150, node_id);
	memcpy( rtl8150->net->dev_addr, node_id, sizeof(node_id) );
	info( " set_ethernet_addr: node id = %x %x %x %x %x %x",
		node_id[0], node_id[1], node_id[2], node_id[3], node_id[4], node_id[5] );
	info( "-set_ethernet_addr() <======" );
}


static inline int reset_mac( rtl8150_t *rtl8150 )
{
	__u8	data = 0;
	int	i;

	info( "+reset_mac() =====>" );
	/// software reset
	data = SOFT_RST;

	///info( " reset_mac: before set_register(rtl8150, Command, data)" );
	while( rtl8150->set_registers_flag == 1 )
		;
	rtl8150->set_registers_flag = 1;
	set_registers(rtl8150, Command, 1, &data);
	while( rtl8150->set_registers_flag == 1 )
		;
	
	///info( " reset_mac: after set_register( rtl8150, Command, data)" );
	for (i = 0; i < REG_TIMEOUT; i++)
	{
		while( rtl8150->get_registers_flag == 1 )
			;
		rtl8150->get_registers_flag = 1;
		get_registers(rtl8150, Command, 1, &data);
		while( rtl8150->get_registers_flag == 1 )
			;
		if ( ~(data & SOFT_RST) )
		{
			break;
		}
	}
	if ( i == REG_TIMEOUT )
	{
		info( " reset_mac: software reset failed" );
		return 1;
	}
	
	info( "-reset_mac() <=====" );
	return	0;
}


static int enable_net_traffic( struct net_device *dev, struct usb_device *usb )
{
	__u16	linkpart, bmsr;
	__u8	data[4];
	__u8	byte_tmp = 0;
	rtl8150_t *rtl8150 = dev->priv;
	__u16  	rx_config_content;

	info("+enable_net_traffic() =====>");
	
	/// check if link okay!
	while( rtl8150->get_registers_flag == 1 )
		;
	rtl8150->get_registers_flag = 1;
	get_registers( rtl8150, MediaStst, 1, &byte_tmp );
	while( rtl8150->get_registers_flag == 1 )
		;
	info(" enable_net_traffic: MediaStst = 0x%x", byte_tmp);
	if ( byte_tmp & LINK )
		info(" enable_net_traffic: LINK ON");
	else
		info(" enable_net_traffic: LINK OFF");

	
	/// software reset
	/// byte_tmp = SOFT_RST;
	///set_register( rtl8150, Command, 1, &byte_tmp );
	
	/// set Transmit Configuration Register
	///info(" enable_net_traffic: before setting Tx Config");
	while( rtl8150->set_registers_flag == 1 )
		;
	rtl8150->set_registers_flag = 1;
	byte_tmp = TXRR1 | TXRR0 | IFG1 | IFG0;
	set_registers( rtl8150, TxConfig, 1, &byte_tmp);
	while( rtl8150->set_registers_flag == 1)
		;
	///while( rtl8150->get_registers_flag == 1 )
	///	;
	///rtl8150->get_registers_flag = 1;
	///get_registers( rtl8150, TxConfig, 1, &byte_tmp );
	///while( rtl8150->get_registers_flag == 1 )
	///	;
	///info( "enable_net_traffic: TxConfig = 0x%x", byte_tmp );
	///info(" enable_net_traffic: after setting Tx Config");

	/// set Receive Configuration Register
	///info(" enable_net_traffic: before setting Rx Config");
	while( rtl8150->set_registers_flag == 1 )
		;
	rtl8150->set_registers_flag = 1;
	rx_config_content = AM | AB | AD | AAM;
	set_registers( rtl8150, RxConfig, 2, &rx_config_content );
	while( rtl8150->set_registers_flag == 1 )
		;
	///info(" enable_net_traffic: after setting Rx Config");

	/// enable Tx and Rx
	///info(" enable_net_traffic: before enabling Tx and Rx" );
	while( rtl8150->set_registers_flag == 1 )
		;
	rtl8150->set_registers_flag = 1;
	byte_tmp = RE | TE;
	set_registers( rtl8150, Command, 1, &byte_tmp );
	while( rtl8150->set_registers_flag == 1 )
		;
	///info(" enable_net_traffic: after enabling Tx and Rx" );
	
	///while( rtl8150->get_registers_flag == 1 )
	///	;
	///rtl8150->get_registers_flag = 1;
	///get_register( rtl8150, Command, &byte_tmp);
	///while( rtl8150->get_registers_flag == 1 )
	///	;
	///info(" enable_net_traffic: Command = 0x%x", byte_tmp );

	info( "-enable_net_traffic() <=====");
	return 0;
}


static void read_bulk_callback( struct urb *urb )
{
	rtl8150_t *rtl8150 = urb->context;
	struct net_device *net;
	int count = urb->actual_length, res;
	int rx_status;
	struct sk_buff	*skb;
	__u16 pkt_len;

	//info( "+read_bulk_callback() =====>" );

	if ( !rtl8150 || !(rtl8150->flags & RTL8150_RUNNING) )
		return;

	net = rtl8150->net;
	if ( !netif_device_present(net) )
		return;

	if ( rtl8150->flags & RTL8150_RX_BUSY ) 
	{
		rtl8150->stats.rx_errors++;
		return;
	}
	rtl8150->flags |= RTL8150_RX_BUSY;

	switch ( urb->status ) {
		case USB_ST_NOERROR:
			break;
		case USB_ST_NORESPONSE:
			info( " read_bulk_callback: NO RESPONSE" );
			dbg( "reset MAC" );
			rtl8150->flags &= ~RTL8150_RX_BUSY;
			break;
		default:
			info( " read_bulk_callback: Rx status = 0x%x", urb->status);
			dbg( "%s: RX status %d", net->name, urb->status );
			goto goon;
	}
	
	pkt_len = count - 4;
	//info(" read_bulk_callback: packet length = 0x%x", pkt_len );
	//info(" read_bulk_callback: packet = %x %x %x %x %x %x %x %x %x %x %x %x", rtl8150->rx_buff[0], rtl8150->rx_buff[1],
	//	rtl8150->rx_buff[2], rtl8150->rx_buff[3], rtl8150->rx_buff[4], rtl8150->rx_buff[5],
	//	rtl8150->rx_buff[6], rtl8150->rx_buff[7], rtl8150->rx_buff[8], rtl8150->rx_buff[9],
	//	rtl8150->rx_buff[10], rtl8150->rx_buff[11] );

	if ( !(skb = dev_alloc_skb(pkt_len+2)) )   /// why "pkt_len + 2" 
		goto goon;

	skb->dev = net;
	skb_reserve(skb, 2);
	
	eth_copy_and_sum(skb, rtl8150->rx_buff, pkt_len, 0);
	skb_put(skb, pkt_len);
	/// in "Linux Device Drivers", the two statements above should be 
	///	"memcpy( skb_put( skb, pkt_len), rtl8150->rx_buff, pkt_len );"


	skb->protocol = eth_type_trans(skb, net);
	netif_rx(skb);	/// call this system call to transfer the "skb" to the upper layer
	rtl8150->stats.rx_packets++;
	rtl8150->stats.rx_bytes += pkt_len;

goon:
	FILL_BULK_URB( &rtl8150->rx_urb, rtl8150->usb,
			usb_rcvbulkpipe(rtl8150->usb, 1),
			rtl8150->rx_buff, RTL8150_MAX_MTU, 
			read_bulk_callback, rtl8150 );
	if ( (res = usb_submit_urb(&rtl8150->rx_urb)) )
	{
		info( " read_bulk_callback: usb_submit_urb failed" );
		warn( __FUNCTION__ " failed submint rx_urb %d", res);
	}
	rtl8150->flags &= ~RTL8150_RX_BUSY;
	
	//info( "-read_bulk_callback() <=====");
}


static void write_bulk_callback( struct urb *urb )
{
	rtl8150_t *rtl8150 = urb->context;

	///info( "+write_bulk_callback() =====>" );

	if ( !rtl8150 || !(rtl8150->flags & RTL8150_RUNNING) )
		return;

	if ( !netif_device_present(rtl8150->net) )
		return;
		
	if ( urb->status )
		info("%s: TX status %d", rtl8150->net->name, urb->status);

	netif_wake_queue( rtl8150->net );
	///info( "-write_bulk_callback() <=====" );
}



#ifdef	RTL8150_USE_INTR
static void intr_callback( struct urb *urb )
{
	rtl8150_t *rtl8150 = urb->context;
	struct net_device *net;
	__u8	*d;

	///info( "intr_callback() =====>" );

	if ( !rtl8150 )
		return;
	d = urb->transfer_buffer;
	net = rtl8150->net;
///	if ( d[0] & 0xfc ) {
///		rtl8150->stats.tx_errors++;
///		if ( d[0] & TX_UNDERRUN )
///			rtl8150->stats.tx_fifo_errors++;
///		if ( d[0] & (EXCESSIVE_COL | JABBER_TIMEOUT) )
///			rtl8150->stats.tx_aborted_errors++;
///		if ( d[0] & LATE_COL )
///			rtl8150->stats.tx_window_errors++;
///		if ( d[0] & (NO_CARRIER | LOSS_CARRIER) )
///			rtl8150->stats.tx_carrier_errors++;
///	}
	switch ( urb->status ) 
	{
		case USB_ST_NOERROR:
			break;
		case USB_ST_URB_KILLED:
			break;
		default:
			info("intr status %d", urb->status);
	}
}
#endif



static void rtl8150_tx_timeout( struct net_device *net )
{
	rtl8150_t *rtl8150 = net->priv;

	info( "+rtl8150_tx_timeout() =====>" );

	if ( !rtl8150 )
		return;
	
	usb_unlink_urb( &rtl8150->tx_urb );
	warn("%s: Tx timed out.", net->name);
	rtl8150->stats.tx_errors++;
	net->trans_start = jiffies;

	netif_wake_queue( net );
	info( "-rtl8150_tx_timeout() <=====" );
}



static int rtl8150_start_xmit( struct sk_buff *skb, struct net_device *net )
{
	rtl8150_t	*rtl8150 = net->priv;
	int 	count = ((skb->len) & 0x3f) ? skb->len : skb->len+1;
		/// increase 64n-length packet by one, because the host controller sometimes doesn't send
		/// 0-length usb packet to end the 64n-length packet.
	int 	res;

	//info( "+rtl8150_start_xmit() =====>" );

	netif_stop_queue( net );
		
	memcpy( rtl8150->tx_buff, skb->data, skb->len );
	
	if(count < RTL8150_MIN_PACKET_LENGTH)
		count = RTL8150_MIN_PACKET_LENGTH;
	FILL_BULK_URB( &rtl8150->tx_urb, rtl8150->usb,
			usb_sndbulkpipe(rtl8150->usb, 2),
			rtl8150->tx_buff, RTL8150_MAX_MTU, 
			write_bulk_callback, rtl8150 );
	rtl8150->tx_urb.transfer_buffer_length = count;

	//info( " rtl8150_start_xmit: packet length = 0x%x", count);	
	//info( " rtl8150_start_xmit: packet = %x %x %x %x %x %x %x %x %x %x %x %x", rtl8150->tx_buff[0], rtl8150->tx_buff[1],
	//	rtl8150->tx_buff[2], rtl8150->tx_buff[3], rtl8150->tx_buff[4], rtl8150->tx_buff[5],
	//	rtl8150->tx_buff[6], rtl8150->tx_buff[7], rtl8150->tx_buff[8], rtl8150->tx_buff[9],
	//	rtl8150->tx_buff[10], rtl8150->tx_buff[11]);
	rtl8150->tx_urb.transfer_flags |= USB_ASYNC_UNLINK;
	if ((res = usb_submit_urb(&rtl8150->tx_urb))) 
	{
		warn("failed tx_urb %d", res);
		rtl8150->stats.tx_errors++;
		netif_start_queue( net );
	}
	else 
	{
		rtl8150->stats.tx_packets++;
		rtl8150->stats.tx_bytes += skb->len;
		net->trans_start = jiffies;	/// record the time stamp
	}

	dev_kfree_skb(skb);
	
	//info( "-rtl8150_start_xmit() <=====" );	
	return 0;
}


/// this function is called when "ifconfig ethx" or "netstat"
static struct net_device_stats *rtl8150_netdev_stats( struct net_device *dev )
{
	//info( "+rtl8150_netdev_stats() =====>" );
	return &((rtl8150_t *)dev->priv)->stats;
	//info( "-rtl8150_netdev_stats() <=====" );
}



static inline void disable_net_traffic( rtl8150_t *rtl8150 )
{
	__u8	tmp = 0;

	info( "+disable_net_traffic() =====>" );
	set_registers( rtl8150, Command, 1, &tmp );
	info( "-disable_net_traffic() <=====" );
}



static inline void get_interrupt_interval( rtl8150_t *rtl8150 )
{
	__u8	data;

	info( "+get_interrupt_interval() =====>" );

	read_eprom_byte( rtl8150, EPROM_Interv, &data );
	rtl8150->intr_interval = data;
	info( "-get_interrupt_interval() <=====" );
}


/// this function is called when "ifconfig ethx xxx ....."
static int rtl8150_open(struct net_device *net)
{
	rtl8150_t *rtl8150 = (rtl8150_t *)net->priv;
	int	res;

	info( "+rtl8150_open() =====>" );

	MOD_INC_USE_COUNT;
	
	///info( " rtl8150_open: before enable_net_traffic()" );
	if ( (res = enable_net_traffic(net, rtl8150->usb)) ) 
	{
		info(" rtl8150_open: enable_net_traffic failed");
		err("can't enable_net_traffic() - %d", res);
		MOD_DEC_USE_COUNT;
		return -EIO;
	}

	/// initiate the rx operation
	info( " rtl8150_open: initiate the rx operation" );
	FILL_BULK_URB( &rtl8150->rx_urb, rtl8150->usb,
			usb_rcvbulkpipe(rtl8150->usb, 1),
			rtl8150->rx_buff, RTL8150_MAX_MTU, 
			read_bulk_callback, rtl8150 );
	if ( (res = usb_submit_urb(&rtl8150->rx_urb)) )
	{
		info(" rtl8150_open: usb_submit_urb failed" );
		warn( __FUNCTION__ " failed rx_urb %d", res );
	}

	/*
	/// initiate the interrupt operation
#ifdef	RTL8150_USE_INTR
	get_interrupt_interval( rtl8150 );
	FILL_INT_URB( &rtl8150->intr_urb, rtl8150->usb,
			usb_rcvintpipe(rtl8150->usb, 3),
			rtl8150->intr_buff, sizeof(rtl8150->intr_buff),
			intr_callback, rtl8150, rtl8150->intr_interval );
	if ( (res = usb_submit_urb(&rtl8150->intr_urb)) )
		warn( __FUNCTION__ " failed intr_urb %d", res);
#endif
	*/
	netif_start_queue( net );
	rtl8150->flags |= RTL8150_RUNNING;

	info( "-rt8150_open() <=====" );
	
	return 0;
}



/// this funciton is called when "ifconfig ethx down"
static int rtl8150_close( struct net_device *net )
{
	rtl8150_t	*rtl8150 = net->priv;

	info( "+rtl8150_close() =====>" );

	rtl8150->flags &= ~RTL8150_RUNNING;
	netif_stop_queue( net );
	if ( !(rtl8150->flags & RTL8150_UNPLUG) )
		disable_net_traffic( rtl8150 );

	usb_unlink_urb( &rtl8150->rx_urb );
	usb_unlink_urb( &rtl8150->tx_urb );
	usb_unlink_urb( &rtl8150->ctrl_urb );
	usb_unlink_urb( &rtl8150->intr_urb );

	MOD_DEC_USE_COUNT;

	info( "-rtl8150_close() <=====" );
	return 0;
}



static int rtl8150_ioctl( struct net_device *net, struct ifreq *rq, int cmd )
{
	__u16 *data = (__u16 *)&rq->ifr_data;
	rtl8150_t	*rtl8150 = net->priv;

	info( "+rtl8150_ioctl() =====> return -EOPNOTSUPP directly" );

	return -EOPNOTSUPP;

	switch(cmd) {
		case SIOCDEVPRIVATE:
			data[0] = rtl8150->phy;
		case SIOCDEVPRIVATE+1:
			read_phy_word(rtl8150, data[0], data[1]&0x1f, &data[3]);
			return 0;
		case SIOCDEVPRIVATE+2:
			if ( !capable(CAP_NET_ADMIN) )
				return -EPERM;
			write_phy_word(rtl8150, rtl8150->phy, data[1] & 0x1f, data[2]);
			return 0;
		default:
			return -EOPNOTSUPP;
	}
}


static void rtl8150_set_multicast( struct net_device *net )
{
	__u16	rcr_content;
	rtl8150_t *rtl8150 = net->priv;

	info( "+rtl8150_set_multicast() =====>" );

	netif_stop_queue(net);

	while( rtl8150->get_registers_flag == 1 )
		;
	rtl8150->get_registers_flag = 1;
	get_registers( rtl8150, RxConfig, 2, &rcr_content );
	while( rtl8150->get_registers_flag == 1 )
		;

	if (net->flags & IFF_PROMISC) 
	{
		rcr_content |= AAP;
		info(" %s: Promiscuous mode enabled", net->name);
	} 
	else if( (net->mc_count > multicast_filter_limit) || (net->flags & IFF_ALLMULTI) ) 
	{
		rcr_content |= AAM;
		rcr_content &= ~AAP;
		info(" %s set allmulti", net->name);
	} 
	else 
	{
		rcr_content &= ~AAM;
		rcr_content &= ~AAP;
		info(" %s: No Promiscuous and All Multicast", net->name);
		/// added by Owen, please refer to 14.14.2 of Linux Device Drivers
		/// if( net->mc_count==0 )
		/// 	ff_get_only_own_packets();
		/// else
		/// {
		///	struct dev_mc_list	*mcptr;
		/// 	ff_clear_mc_list();
		///	for( mc_ptr = net->mc_list; mc_ptr; mc_ptr = mc_ptr->next )
		///		ff_store_mc_address( mc_ptr->dmi_addr );
		//	ff_get_packets_in_multicast_list();
		/// }
	}

	while( rtl8150->set_registers_flag == 1 )
		;
	rtl8150->set_registers_flag = 1;
	set_registers( rtl8150, RxConfig, 2, &rcr_content );
	while( rtl8150->set_registers_flag == 1 )
		;
	
	netif_wake_queue(net);	
	info( "-rtl8150_set_multicast() <=====" );	
}


static int check_device_ids( __u16 vendor, __u16 product )
{
	int i=0;

	info( "+check_device_ids() =====>" );
	info( " check_device_ids: vendor id = 0x%x", vendor );
	info( " check_device_ids: device id = 0x%x", product );
	
	while ( usb_dev_id[i].name ) {
		if ( (usb_dev_id[i].vendor == vendor) && (usb_dev_id[i].device == product) )
		{
		 	info( " check_device_ids: BINGO!" );
		 	info( "-check_device_ids() <=====" );
			return i;
		}
		i++;
	}
	
	info( " check_device_ids: not our device");
	info( "-check_device_ids() <=====" );
	return	-1;
}


static void mii_HPNA_phy_probe( rtl8150_t *rtl8150 )
{
	int	i;
	__u16	tmp;

        /*
	for ( i=0; i < 32; i++ ) 
	{
		read_phy_word( rtl8150, i, MII_PHY_ID2, &tmp );
		tmp = tmp & 0xfff0;
		if( tmp == AMD_PHY_ID ) 
		{
			rtl8150->hpna_phy = AMD_PHY;
			rtl8150->phy = i;
			return;
		}
		else if( tmp == NS_PHY_ID )
		{
			rtl8150->hpna_phy = NS_PHY;
			rtl8150->phy = i;
			return;
		}
		else
			continue;	
	}

	rtl8150->phy = 0;
	rtl8150->hpna_phy = UNKNOWN_PHY;
	*/
}



static void * rtl8150_probe( struct usb_device *dev, unsigned int ifnum, const struct usb_device_id *id)
{
	struct net_device *net;
	rtl8150_t *rtl8150;
	int	dev_indx;

	info( "+rtl8150_probe() =====>" );

	///info( " rtl8150_probe: before check_deice_ids()" );
	if ( (dev_indx = check_device_ids(dev->descriptor.idVendor, dev->descriptor.idProduct)) == -1 ) 
	{
		info( " rtl8150_pbobe: this is not my device!" );
		return NULL;
	}
	///info( " rtl8150_probe: after check_device_ids()" );
	

	///info( " rtl8150_probe: before usb_set_configuration()" );
	/// the following is for fixing the bug of 1st-cut, and must be removed in 2nd-cut
	dev->config[0].bConfigurationValue = 1;
	////////////////////////////////////////////////
	if (usb_set_configuration(dev, dev->config[0].bConfigurationValue)) 
	{
		err("usb_set_configuration() failed");
		info( " rtl8150_probe: usb_set_configuration() failed" );
		return NULL;
	}
	///info( " rtl8150_probe: after usb_set_configuration()" );

	if(!(rtl8150 = kmalloc(sizeof(struct rtl8150), GFP_KERNEL))) 
	{
		err("out of memory allocating device structure");
		info( " rtl8150_probe: out of memory allocating device structure" );
		return NULL;
	}
	
	/// added by Owen on 01/11/2000
	rtl8150->get_registers_flag = 0;
	rtl8150->set_registers_flag = 0;

	///info( " rtl8150_probe: before usb_inc_dev_use()" );
	usb_inc_dev_use( dev );
	memset(rtl8150, 0, sizeof(struct rtl8150));
	///info( " rtl8150_probe: after usb_inc_dev_use()" );
	
	///info( " rtl8150_probe: before init_MUTEX()" );
	init_MUTEX( &rtl8150-> ctrl_sem );
	///info( " rtl8150_probe: after init_MUTEX()" );
	
	///info( " rtl8150_probe: before init_waitqueue_head()" );
	init_waitqueue_head( &rtl8150->ctrl_wait );
	///info( " rtl8150_probe: after init_waitqueue_head()" );

	///info( " rtl8150_probe: before init_etherdev()" );
	net = init_etherdev( NULL, 0 );
	if ( !net ) 
	{
		kfree( rtl8150 );
		info( " rtl8150_probe: init_etherdev() failed" );
		return	NULL;
	}
	///info( " rtl8150_probe: after init_etherdev()" );
	
	rtl8150->usb = dev;
	rtl8150->net = net;
	net->priv = rtl8150;
	net->open = rtl8150_open;
	net->stop = rtl8150_close;
#if LINUX_VERSION_CODE > KERNEL_VERSION(2,3,48)
	net->watchdog_timeo = RTL8150_TX_TIMEOUT;
	net->tx_timeout = rtl8150_tx_timeout;
#endif
	net->do_ioctl = rtl8150_ioctl;
	net->hard_start_xmit = rtl8150_start_xmit;
	net->set_multicast_list = rtl8150_set_multicast;
	net->get_stats = rtl8150_netdev_stats;
	net->mtu = RTL8150_MTU;     //  1500

	rtl8150->features = usb_dev_id[dev_indx].private;
	
	///info( " rtl8150_probe: before reset_mac()" );
	if ( reset_mac(rtl8150) ) 
	{
		err("can't reset MAC");
		info( " rtl8150_probe: reset_mac() failed" );
		unregister_netdev( rtl8150->net );
		kfree(rtl8150);
		rtl8150 = NULL;
		return NULL;
	}
	///info( " rtl8150_probe: after reset_mac()" );

	///info( " rtl8150_probe: before set_ethernet_addr()" );
	set_ethernet_addr( rtl8150 );
	///info( " rtl8150_probe: after set_ethernet_addr()" );
	
	if( rtl8150->features & FEATURE_HAS_HOME_PNA )
		mii_HPNA_phy_probe( rtl8150 );
	
	info( "%s: %s", net->name, usb_dev_id[dev_indx].name );

	info( "-rtl8150_probe() <=====" );
	return rtl8150;
}


static void rtl8150_disconnect( struct usb_device *dev, void *ptr )
{
	struct rtl8150 *rtl8150 = ptr;

	info( "+rtl8150_disconnect() =====>" );

	if ( !rtl8150 ) {
		info( " rtl8150_disconnect: unregister non-existant device" );
		warn("unregistering non-existant device");
		return;
	}

	rtl8150->flags |= RTL8150_UNPLUG;
	unregister_netdev( rtl8150->net );
	usb_dec_dev_use( dev );
	kfree( rtl8150 );
	rtl8150 = NULL;
	info( "-rtl8150_disconnect() <=====" );
}


static struct usb_driver rtl8150_driver = {
	name:		"RTL8150",
	probe:		rtl8150_probe,
	disconnect:	rtl8150_disconnect,
};


/// this function is called when "insmod rtl8150.o"
int __init rtl8150_init(void)
{
	int	registerResult;
	
	info( "+rtl8150_init() =====>" );
	info( "%s", version );
        registerResult = usb_register( &rtl8150_driver );
	info( "-rtl8150_init() <=====" );

	return registerResult;
}


/// this funciton is called when "rmmod rtl8150"
void __exit rtl8150_exit(void)
{
	info( "+rtl8150_exit() =====>" );
	usb_deregister( &rtl8150_driver );
	info( "-rtl8150_exit() <=====" );
}

module_init( rtl8150_init );

module_exit( rtl8150_exit );

^ permalink raw reply

* Re: [1/1] connector: export cn_already_initialized.
From: David Miller @ 2006-06-20  6:43 UTC (permalink / raw)
  To: johnpol; +Cc: netdev
In-Reply-To: <20060619053031.GA17406@2ka.mipt.ru>

From: Evgeniy Polyakov <johnpol@2ka.mipt.ru>
Date: Mon, 19 Jun 2006 09:30:35 +0400

> Attached patch declares connector init function as subsys_init()
> and returns -EAGAIN in case connector is not initialized yet.
> 
> Signed-off-by: Evgeniy Polyakov <johnpol@2ka.mipt.ru>

Applied, but I had to fixup something by hand:

> @@ -433,7 +436,7 @@ static void cn_callback(void *data)
>  	up(&notify_lock);
>  }
>  
> -static int __init cn_init(void)
> +static int __devinit cn_init(void)

notify_lock is now a mutex.

^ permalink raw reply

* (no subject)
From: Abimanyu G @ 2006-06-20 11:31 UTC (permalink / raw)
  To: netdev



^ permalink raw reply

* Re: [PATCH 0/2] NET: Accurate packet scheduling for ATM/ADSL
From: Chris Wedgwood @ 2006-06-20  5:35 UTC (permalink / raw)
  To: Jesper Dangaard Brouer; +Cc: netdev
In-Reply-To: <1150278004.26181.35.camel@localhost.localdomain>

On Wed, Jun 14, 2006 at 11:40:04AM +0200, Jesper Dangaard Brouer wrote:

> The Linux traffic's control engine inaccurately calculates
> transmission times for packets sent over ADSL links.  For some
> packet sizes the error rises to over 50%.  This occurs because ADSL
> uses ATM as its link layer transport, and ATM transmits packets in
> fixed sized 53 byte cells.

What if AAL5 is used?  The cell-alignment math is going to be wrong
there surely?


^ permalink raw reply

* [patch] ieee80211: fix not allocating IV+ICV space when using encryption in ieee80211_tx_frame
From: Hong Liu @ 2006-06-20  2:26 UTC (permalink / raw)
  To: linville; +Cc: netdev

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

We should preallocate IV+ICV space when encrypting the frame.
Currently no problem shows up just because dev_alloc_skb aligns the
data len to SMP_CACHE_BYTES which can be used for ICV.

Thanks,
Hong

[-- Attachment #2: ieee80211-1.1.14-newtxfix.patch --]
[-- Type: text/x-patch, Size: 1620 bytes --]

diff -urp a/net/ieee80211/ieee80211_tx.c b/net/ieee80211/ieee80211_tx.c
--- a/net/ieee80211/ieee80211_tx.c	2006-06-20 09:36:13.000000000 +0800
+++ b/net/ieee80211/ieee80211_tx.c	2006-06-20 09:32:39.000000000 +0800
@@ -562,10 +562,12 @@ int ieee80211_tx_frame(struct ieee80211_
 	struct net_device_stats *stats = &ieee->stats;
 	struct sk_buff *skb_frag;
 	int priority = -1;
+	int fraglen = total_len;
+	struct ieee80211_crypt_data *crypt = ieee->crypt[ieee->tx_keyidx];
 
 	spin_lock_irqsave(&ieee->lock, flags);
 
-	if (encrypt_mpdu && !ieee->sec.encrypt)
+	if (encrypt_mpdu && (!ieee->sec.encrypt || !crypt))
 		encrypt_mpdu = 0;
 
 	/* If there is no driver handler to take the TXB, dont' bother
@@ -581,20 +583,25 @@ int ieee80211_tx_frame(struct ieee80211_
 		goto success;
 	}
 
-	if (encrypt_mpdu)
+	if (encrypt_mpdu) {
 		frame->frame_ctl |= cpu_to_le16(IEEE80211_FCTL_PROTECTED);
+		/* mpdu_prefix_len will be add to the headroom */
+		fraglen += crypt->ops->extra_mpdu_postfix_len;
+	}
 
 	/* When we allocate the TXB we allocate enough space for the reserve
 	 * and full fragment bytes (bytes_per_frag doesn't include prefix,
 	 * postfix, header, FCS, etc.) */
-	txb = ieee80211_alloc_txb(1, total_len, ieee->tx_headroom, GFP_ATOMIC);
+	txb = ieee80211_alloc_txb(1, fraglen, ieee->tx_headroom +
+				  crypt->ops->extra_mpdu_prefix_len,
+				  GFP_ATOMIC);
 	if (unlikely(!txb)) {
 		printk(KERN_WARNING "%s: Could not allocate TXB\n",
 		       ieee->dev->name);
 		goto failed;
 	}
 	txb->encrypted = 0;
-	txb->payload_size = total_len;
+	txb->payload_size = fraglen;
 
 	skb_frag = txb->fragments[0];
 

^ permalink raw reply

* Re: Network performance degradation from 2.6.11.12 to 2.6.16.20
From: Herbert Xu @ 2006-06-20  2:11 UTC (permalink / raw)
  To: Harry Edmon; +Cc: shemminger, akpm, linux-kernel, netdev
In-Reply-To: <4496ACA6.7090305@atmos.washington.edu>

Harry Edmon <harry@atmos.washington.edu> wrote:
> 
> That did not help.  I have 1 minute outputs from tcpdump under both 2.6.11.12 
> and 2.6.16.20.  You will see a large size difference between the files.  Since 
> the 2.6.11.12 one is 2 MBytes, I thought I would post them via the web instead 
> of via attachments.   Look at:
> 
> http://www.atmos.washington.edu/~harry/linux/2.6.11.12.out.1min
> http://www.atmos.washington.edu/~harry/linux/2.6.16.20.out.1min

The latter shows that it took 40ms to generate an ACK.  What does
'vmstat 1' show while this is happneing?
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply

* Re: [PATCH 0/2] NET: Accurate packet scheduling for ATM/ADSL
From: Patrick McHardy @ 2006-06-20  1:04 UTC (permalink / raw)
  To: hadi
  Cc: Jesper Dangaard Brouer, Stephen Hemminger, netdev, lartc,
	russell-tcatm, hawk
In-Reply-To: <1150377383.5116.38.camel@jzny2>

jamal wrote:
> You are still speaking ATM (and the above may still be valid), but: 
> Could you for example look at the netdevice->type and from that figure
> out the link layer overhead and compensate for it.
> Obviously a lot more useful if such activity is doable in user space
> without any knowledge of the kernel? and therefore zero change to the
> kernel and everything then becomes forward and backward compatible.

It would be nice to have support for HFSC as well, which unfortunately
needs to be done in the kernel since it doesn't use rate tables.
What about qdiscs like SFQ (which uses the packet size in quantum
calculations)? I guess it would make sense to use the wire-length
there as well.


^ permalink raw reply

* Re: [PATCH 0/2] NET: Accurate packet scheduling for ATM/ADSL
From: Patrick McHardy @ 2006-06-20  0:54 UTC (permalink / raw)
  To: hadi
  Cc: Jesper Dangaard Brouer, hawk, russell-tcatm, lartc, netdev,
	Stephen Hemminger
In-Reply-To: <1150286766.5233.15.camel@jzny2>

jamal wrote:
> - For further reflection: Have you considered the case where the rate
> table has already been considered on some link speed in user space and
> then somewhere post-config the physical link speed changes? This would
> happen in the case where ethernet AN is involved and the partner makes
> some changes (use ethtool). 
> 
> I would say the last bullet is a more interesting problem than a corner
> case of some link layer technology that has high overhead.
> Your work would be more interesting if it was generic for many link
> layers instead of just ATM.

I've thought about this a couple of times, scaling the virtual clock
rate should be enough for "simple" qdiscs like TBF or HTB, which have
a linear relation between time and bandwidth. I haven't really thought
about the effects on HFSC yet, on a small scale the relation is
non-linear. But this is a different problem from trying to accomodate
for link-layer overhead.

^ permalink raw reply

* Re: [Bugme-new] [Bug 6682] New: BUG: soft lockup detected on CPU#0! / ksoftirqd takse 100% CPU
From: Paul E. McKenney @ 2006-06-20  0:26 UTC (permalink / raw)
  To: Andrew Morton
  Cc: netdev, Dipankar Sarma, bugme-daemon@kernel-bugs.osdl.org,
	alchemyx
In-Reply-To: <20060619152010.5c648b97.akpm@osdl.org>

On Mon, Jun 19, 2006 at 03:20:10PM -0700, Andrew Morton wrote:
> bugme-daemon@bugzilla.kernel.org wrote:
> >
> > http://bugzilla.kernel.org/show_bug.cgi?id=6682
> > 
> >            Summary: BUG: soft lockup detected on CPU#0! / ksoftirqd takse
> >                     100% CPU
> >     Kernel Version: 2.6.15.6
> >             Status: NEW
> >           Severity: normal
> >              Owner: acme@conectiva.com.br
> >          Submitter: alchemyx@uznam.net.pl
> > 
> > 
> > Most recent kernel where this bug did not occur: (unknown)
> > Distribution: Gentoo
> > Hardware Environment: 2x Xeon 2.66, 1 GB RAM, NICS: 2 x e1000, and one double
> > port e100. Based on Intel E7501 architecture (2U rack Intel chassis).
> > Software Environment: quagga 0.98.6
> > Problem Description: ksoftirqd/0 takes 100% of CPU. further investigation shows
> > no sing of network flood or something (and also 2 of 3 NICs are e1000 with
> > NAPI). Ocassionaly there are "BUG: soft lockup detected on CPU#0!".
> > 
> > Steps to reproduce:
> > 
> > There is no simple way to reproduce. I think that everythint started when we
> > attached second provider with BGP support. We are using quagga which injects
> > about 186 000 routes into kernel. When running for a while (at least few hours,
> > sometimes a day) we get 100% usage on ksoftirqd/0 and following messages in logs:

Is it possible that there is a routing loop, either in the overall
configuration or in some intermediate point in the route injection?
Both CPUs seem to be receiving ethernet packets at the time of the oops.

						Thanx, Paul

> > BUG: soft lockup detected on CPU#0!
> > 
> > Pid: 6506, comm:                zebra
> > EIP: 0060:[<c027f6fd>] CPU: 0
> > EIP is at _spin_lock+0x7/0xf
> >  EFLAGS: 00000286    Not tainted  (2.6.15.6)
> > EAX: f6203180 EBX: e6fbf000 ECX: 00000000 EDX: f6bec000
> > ESI: f6203000 EDI: eddb4b80 EBP: fffffff4 DS: 007b ES: 007b
> > CR0: 8005003b CR2: aca6dff0 CR3: 361ad000 CR4: 000006d0
> >  [<c02396f9>] dev_queue_xmit+0xe0/0x203
> >  [<c0250de8>] ip_output+0x1e1/0x237
> >  [<c024f3f5>] ip_forward+0x181/0x1df
> >  [<c024e21a>] ip_rcv+0x40c/0x485
> >  [<c0239bd0>] netif_receive_skb+0x12f/0x165
> >  [<f885aa4c>] e1000_clean_rx_irq+0x389/0x410 [e1000]
> >  [<f885a1ca>] e1000_clean+0x94/0x12f [e1000]
> >  [<c0239d5a>] net_rx_action+0x69/0xf0
> >  [<c011a305>] __do_softirq+0x55/0xbd
> >  [<c011a39a>] do_softirq+0x2d/0x31
> >  [<c011a3f8>] local_bh_enable+0x5a/0x65
> >  [<c024a0a1>] rt_run_flush+0x5f/0x80
> >  [<c027623f>] fn_hash_insert+0x352/0x39f
> >  [<c027364c>] inet_rtm_newroute+0x57/0x62
> >  [<c02413ed>] rtnetlink_rcv_msg+0x1a8/0x1cb
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c0247c1e>] netlink_rcv_skb+0x3a/0x8b
> >  [<c0247cb1>] netlink_run_queue+0x42/0xc3
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c0241227>] rtnetlink_rcv+0x22/0x40
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c024764c>] netlink_data_ready+0x17/0x54
> >  [<c0246a99>] netlink_sendskb+0x1f/0x39
> >  [<c0247449>] netlink_sendmsg+0x27b/0x28c
> >  [<c0231467>] sock_sendmsg+0xce/0xe9
> >  [<c0112b36>] __wake_up+0x27/0x3b
> >  [<c01a6216>] copy_to_user+0x38/0x42
> >  [<c01a625a>] copy_from_user+0x3a/0x60
> >  [<c01a625a>] copy_from_user+0x3a/0x60
> >  [<c0126be2>] autoremove_wake_function+0x0/0x3a
> >  [<c0236bcd>] verify_iovec+0x49/0x7f
> >  [<c02327f2>] sys_sendmsg+0x152/0x1a8
> >  [<c0147a62>] do_sync_read+0xb8/0xeb
> >  [<c01a6216>] copy_to_user+0x38/0x42
> >  [<c0126be2>] autoremove_wake_function+0x0/0x3a
> >  [<c0122b7a>] getrusage+0x34/0x43
> >  [<c0168504>] inotify_dentry_parent_queue_event+0x29/0x7c
> >  [<c01a625a>] copy_from_user+0x3a/0x60
> >  [<c0232b6b>] sys_socketcall+0x167/0x180
> >  [<c0102433>] sysenter_past_esp+0x54/0x75
> > 
> > BUG: soft lockup detected on CPU#0!
> > 
> > Pid: 6506, comm:                zebra
> > EIP: 0060:[<f8952052>] CPU: 0
> > EIP is at u32_classify+0x52/0x170 [cls_u32]
> >  EFLAGS: 00000206    Not tainted  (2.6.15.6)
> > EAX: e2fbd020 EBX: f48649c0 ECX: 00000010 EDX: 29b09d5a
> > ESI: f48649ec EDI: 00000001 EBP: e2fbd020 DS: 007b ES: 007b
> > CR0: 8005003b CR2: 08154004 CR3: 361ad000 CR4: 000006d0
> >  [<f88462fa>] ipt_do_table+0x2de/0x2fd [ip_tables]
> >  [<f883b523>] ip_nat_fn+0x177/0x185 [iptable_nat]
> >  [<f88e159f>] ip_refrag+0x23/0x5f [ip_conntrack]
> >  [<c0244d82>] tc_classify+0x2c/0x3f
> >  [<f895514b>] htb_classify+0x14b/0x1dd [sch_htb]
> >  [<f8955638>] htb_enqueue+0x1d/0x13a [sch_htb]
> >  [<c02396fd>] dev_queue_xmit+0xe4/0x203
> >  [<c0250de8>] ip_output+0x1e1/0x237
> >  [<c024f3f5>] ip_forward+0x181/0x1df
> >  [<c024e21a>] ip_rcv+0x40c/0x485
> >  [<c0239bd0>] netif_receive_skb+0x12f/0x165
> >  [<f885aa4c>] e1000_clean_rx_irq+0x389/0x410 [e1000]
> >  [<f885a1ca>] e1000_clean+0x94/0x12f [e1000]
> >  [<c0239d5a>] net_rx_action+0x69/0xf0
> >  [<c011a305>] __do_softirq+0x55/0xbd
> >  [<c011a39a>] do_softirq+0x2d/0x31
> >  [<c011a3f8>] local_bh_enable+0x5a/0x65
> >  [<c024a0a1>] rt_run_flush+0x5f/0x80
> >  [<c027623f>] fn_hash_insert+0x352/0x39f
> >  [<c027364c>] inet_rtm_newroute+0x57/0x62
> >  [<c02413ed>] rtnetlink_rcv_msg+0x1a8/0x1cb
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c0247c1e>] netlink_rcv_skb+0x3a/0x8b
> >  [<c0247cb1>] netlink_run_queue+0x42/0xc3
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c0241227>] rtnetlink_rcv+0x22/0x40
> >  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
> >  [<c024764c>] netlink_data_ready+0x17/0x54
> >  [<c0246a99>] netlink_sendskb+0x1f/0x39
> >  [<c0247449>] netlink_sendmsg+0x27b/0x28c
> >  [<c0231467>] sock_sendmsg+0xce/0xe9
> >  [<c0112b36>] __wake_up+0x27/0x3b
> >  [<c01a625a>] copy_from_user+0x3a/0x60
> >  [<c01a625a>] copy_from_user+0x3a/0x60
> >  [<c0126be2>] autoremove_wake_function+0x0/0x3a
> >  [<c0236bcd>] verify_iovec+0x49/0x7f
> >  [<c02327f2>] sys_sendmsg+0x152/0x1a8
> >  [<c0147a62>] do_sync_read+0xb8/0xeb
> >  [<c0122b7a>] getrusage+0x34/0x43
> >  [<c011d72f>] update_wall_time+0xa/0x32
> >  [<c011d9e5>] do_timer+0x33/0xa9
> >  [<c01a625a>] copy_from_user+0x3a/0x60
> >  [<c0232b6b>] sys_socketcall+0x167/0x180
> >  [<c0102433>] sysenter_past_esp+0x54/0x75
> > 
> > It happens on 2.6.15.6. Tonight I will try 2.6.16.16 with FIB_TRIE instead of
> > FIB_HASH. I am submitting that bug under network but I am not completly sure if
> > it belongs here.
> 
> This also happens on 2.6.16.6.

^ permalink raw reply

* Re: [PATCH, RFT] bcm43xx: Busting the 1G limit
From: Daniel Gryniewicz @ 2006-06-19 23:06 UTC (permalink / raw)
  To: Michael Buesch; +Cc: bcm43xx-dev, netdev
In-Reply-To: <200606192243.09039.mb@bu3sch.de>

On Mon, 2006-06-19 at 22:43 +0200, Michael Buesch wrote:
> On Monday 19 June 2006 17:23, Daniel Gryniewicz wrote:
> > On Sat, 2006-06-17 at 19:28 +0200, Michael Buesch wrote:
> > > Hi,
> > > 
> > > This patch adds full 32-bit and 64-bit DMA support
> > > to the bcm43xx driver. Well, it _should_ do this. I can
> > > not test it, as I don't have a machine to trigger the 1G
> > > limit.
> > > The 1G limit should be exploitable on an AMD64 machine
> > > with more than 1G RAM.
> > > 
> > > Please test and report, if it works or not. In the
> > > case of "works not", please provide full dmesg log.
> > > 
> > > Note that I am not sure which cards actually support
> > > full 32-bit or even 64-bit mode. Older cards might still
> > > only support 30-bit DMA.
> > 
> > Hi.
> > 
> > I tried this on both 2.6.17-rc6 and on wireless-dev, and got pretty much
> > the same panic on both (modulo locking).  My box is a turion with 2 GB
> > of ram and a BCM4318.  Here's the panic from wireless-dev:
> > 
> > Unable to handle kernel NULL pointer dereference at 0000000000000020
> > RIP:
> > <ffffffff88104f24>{:bcm43xx:bcm43xx_dma_handle_xmitstatus+436}
> 
> I am still not absolutely sure where this oops comes from.
> Could you remove at least 1G of your RAM and retry?
> 

I took out 1G of RAM (2 1G sticks), and there was no more panic.  It
still didn't work (no output from iwlist scan), but also no panic.

dmesg output was:
Jun 19 18:00:54 athena bcm43xx: Radio turned on
Jun 19 18:00:54 athena bcm43xx: ASSERTION FAILED (radio_attenuation <
10) at:
drivers/net/wireless/bcm43xx/bcm43xx_phy.c:1485:bcm43xx_find_lopair()
Jun 19 18:00:54 athena bcm43xx: ASSERTION FAILED (radio_attenuation <
10) at:
drivers/net/wireless/bcm43xx/bcm43xx_phy.c:1485:bcm43xx_find_lopair()
Jun 19 18:00:54 athena bcm43xx: Chip initialized
Jun 19 18:00:54 athena bcm43xx: 32-bit DMA initialized
Jun 19 18:00:54 athena bcm43xx: 80211 cores initialized
Jun 19 18:00:54 athena bcm43xx: Keys cleared
Jun 19 18:00:54 athena SoftMAC: Associate: Scanning for networks first.
Jun 19 18:00:54 athena SoftMAC: Associate: failed to initiate scan. Is
device up?

followed by a bunch of:
Jun 19 18:01:15 athena SoftMAC: Start scanning with channel: 1
Jun 19 18:01:15 athena SoftMAC: Scanning 14 channels
Jun 19 18:01:15 athena SoftMAC: Scanning finished

followed by:
Jun 19 18:02:03 athena SoftMAC: Associate: Scanning for networks first.
Jun 19 18:02:03 athena SoftMAC: Start scanning with channel: 1
Jun 19 18:02:03 athena SoftMAC: Scanning 14 channels
Jun 19 18:02:03 athena bcm43xx: set security called
Jun 19 18:02:03 athena bcm43xx:    .level = 0
Jun 19 18:02:03 athena bcm43xx:    .enabled = 0
Jun 19 18:02:03 athena bcm43xx:    .encrypt = 0
Jun 19 18:02:03 athena SoftMAC: Scanning finished
Jun 19 18:02:03 athena SoftMAC: Associate: Scanning for networks first.
Jun 19 18:02:03 athena SoftMAC: Start scanning with channel: 1
Jun 19 18:02:03 athena SoftMAC: Scanning 14 channels
Jun 19 18:02:03 athena SoftMAC: Scanning finished
Jun 19 18:02:03 athena SoftMAC: Associate: Scanning for networks first.
Jun 19 18:02:03 athena SoftMAC: Start scanning with channel: 1
Jun 19 18:02:03 athena SoftMAC: Scanning 14 channels
Jun 19 18:02:04 athena SoftMAC: Scanning finished
Jun 19 18:02:04 athena SoftMAC: Unable to find matching network after
scan!

and finally:

Jun 19 18:02:44 athena bcm43xx: Radio turned off
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x0200 (RX) max used slots: 0/64
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x02A0 (TX) max used slots: 0/512
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x0280 (TX) max used slots: 0/512
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x0260 (TX) max used slots: 0/512
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x0240 (TX) max used slots: 0/512
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x0220 (TX) max used slots: 2/512
Jun 19 18:02:44 athena bcm43xx: DMA-32 0x0200 (TX) max used slots: 0/512

At that point, I remove the bcm43xx module, and switched over to my
prism54 card in order to get net access.

This was all on wireless-dev as of yesterday with the 1G limit patch
from this thread.

Let me know if there's anything I can try, I'd love to get this working
properly.

Daniel


^ permalink raw reply

* Re: [Bugme-new] [Bug 6698] New: unregister_netdevice hangs indefinitely from /proc/sys/net/ipv6/conf/all/forwarding
From: Andrew Morton @ 2006-06-19 23:06 UTC (permalink / raw)
  To: netdev; +Cc: bugme-daemon@kernel-bugs.osdl.org, kernelbmw
In-Reply-To: <200606161620.k5GGKagU011416@fire-2.osdl.org>

bugme-daemon@bugzilla.kernel.org wrote:
>
> http://bugzilla.kernel.org/show_bug.cgi?id=6698
> 
>            Summary: unregister_netdevice hangs indefinitely from
>                     /proc/sys/net/ipv6/conf/all/forwarding
>     Kernel Version: 2.6.17-rc6
>             Status: NEW
>           Severity: normal
>              Owner: yoshfuji@linux-ipv6.org
>          Submitter: kernelbmw@lsmod.de
> 
> 
> Most recent kernel where this bug did not occur: none known (yet)
> Distribution: reproduced on Debian/stable, SuSE/10.0, SuSE/10.1
> Hardware Environment: reproduced on UML, i386, x86/64
> Software Environment: reproduced with openvpn and UML tap devices
> Problem Description: after adding IPv6 to my previously working openvpn
> tunneling setup, a (really old) IPv6-related bug started to occurr:
> http://lkml.org/lkml/2003/8/21/1
> I also reproduced this bug with kernel 2.6.15.1(vanilla,uml) and
> 2.6.16.13(SuSE-version,x86/64) and linux-2.6.13 (SuSE-version,i386)
> 
> Steps to reproduce:
> echo 0 > /proc/sys/net/ipv6/conf/all/forwarding # this is important initialization
> 
> Have (any version of) openvpn open a tunnel using a tap (virtual ethernet)
> device. In the "up" script do:
> echo 1 > /proc/sys/net/ipv6/conf/all/forwarding
> this can be easily tested with these lines:
> apt-get install openvpn
> modprobe tun
> mknod /dev/net/tun c 10 200
> echo 0 > /proc/sys/net/ipv6/conf/all/forwarding
> echo "echo 1 > /proc/sys/net/ipv6/conf/all/forwarding" > /tmp/up ; chmod a+x /tmp/up
> openvpn --dev-type tap --remote tunnel.lsmod.de 5003 --ifconfig 10.9.0.2
> 255.255.255.0 --dev-node /dev/net/tun --up /tmp/up
> # at this point you can verify your tunnel setup by ping 10.9.0.1
> # on the server I have this: openvpn --dev-type tap --ifconfig 10.9.0.1
> 255.255.255.0 --port 5003 --dev-node /dev/net/tun --float
> # you need UDP port 5003 to pass through your firewall for this
> 
> 
> Alternatively get an user-mode-linux(UML) binary and do something along the
> lines of:
> apt-get install uml-utilities
> TAP=`tunctl -b`
> ifconfig $TAP 192.168.121.1 netmask 255.255.255.252
> echo 1 > /proc/sys/net/ipv6/conf/all/forwarding
> /path/to/linux eth0=tuntap,$TAP ... # booting up to the point where the tap dev
> is really bound (at "ifconfig eth0 192.168.121.2" within the UML)
> tunctl -d $TAP
> 
> 
> After 20 seconds kill the openvpn or linux process.
> This hangs indefinitely, leaving the openvpn process in "D" state.
> syslog states every 10 secs:
> unregister_netdevice: waiting for tap0 to become free.  Usage count = 1
> 
> The kernel will then hang "ifconfig" and "ip" commands, probably because the
> waiting-for-tap0 still holds a mutex.
> 
> After a dozen reboots of trying I found a work-around: replacing the critical
> line with
> (sleep 2 ; echo 1 > /proc/sys/net/ipv6/conf/all/forwarding )&
> 
> A sleep 1 does not suffice.
> Doing the echo before calling openvpn also works fine, so there seems to be a
> timing problem or race condition during initialization of the IPv6 on the newly
> created tap0 device.
> 

Thought to be an ipv6 refcount leak.

^ permalink raw reply

* Re: [DOC]: generic netlink
From: Shailabh Nagar @ 2006-06-19 22:37 UTC (permalink / raw)
  To: hadi; +Cc: netdev, David S. Miller, Thomas Graf, Jay Lan, Per Liden
In-Reply-To: <1150724482.5815.48.camel@jzny2>

jamal wrote:
> Folks,
> 
> Attached is a document that should help people wishing to use generic
> netlink interface. It is a WIP so a lot more to go if i see interest.
> The doc has been around for a while, i spent part of yesterday and this
> morning cleaning it up. If you have sent me comments before, please
> forgive me for having misplaced them - just send again. 

Jamal,

Completing the documentation on generic netlink usage will definitely be
useful. I'd be happy to help out with this since I've recently gone through
trying to understand and use genetlink for the taskstats interface. Hopefully
this will help other users like me who aren't netlink experts to begin with !

I've sent you a patch to the document that attempts to cover the following
TODOS (didn't see any point sending it to the whole list since its harder to
read patches to documentation). Pls use as you see fit.

> TODO:
> a) Add a more complete compiling kernel module with events.
> Have Thomas put his Mashimaro example and point to it.
(not the Mashimaro example, nor a completly compiled module but snippets
of pseudo code taken from the user space program used in taskstats development,
modified to the foobar example you've used)
> b) Describe some details on how user space -> kernel works
> probably using libnl??
> c) Describe discovery using the controller..

I'll provide another patch that will cover d) and e) in the set below, again
in the context of the foobar example, which might need to be modified a bit.

> d) talk about policies etc
> e) talk about how something coming from user space eventually
> gets to you.
> f) Talk about the TLV manipulation stuff from Thomas.
> g) submit controller patch to iproute2

One point...does d), f) etc. belong in a separate doc describing usage
of netlink attributes ? Its useful here too but not directly related to
genetlink perhaps.

> PS:- I dont have a good place to put this doc and point to, hence the
> 17K attachment
>

http://www.kernel.org/pub/linux/kernel/people/hadi/ ?

(unless your permissions have been revoked for lack of use ! :-)

Having the current document will be useful to see what edits have been accepted
and work on that instead of the original.

--Shailabh

^ permalink raw reply

* Re: [NET]: Prevent multiple qdisc runs
From: Herbert Xu @ 2006-06-19 22:33 UTC (permalink / raw)
  To: jamal; +Cc: netdev, David S. Miller
In-Reply-To: <1150727810.5815.78.camel@jzny2>

On Mon, Jun 19, 2006 at 10:36:50AM -0400, jamal wrote:
> 
> Ok, but:
> The queue lock will ensure only one of the qdisc runs (assuming
> different CPUs) will be able to dequeue at any one iota in time, no?
> And if you assume that the cpu that manages to get the tx lock as well
> is going to be contending for the qlock in ordewr to requeue, then the
> only scenario i can see the race happening is when you have one CPU
> faster than the other.
> Did i miss something?

First of all you could receive an IRQ in between dropping xmit_lock
and regaining the queue lock.  Secondly we now have lockless drivers
where this assumption also does not hold.

Cheers,
-- 
Visit Openswan at http://www.openswan.org/
Email: Herbert Xu ~{PmV>HI~} <herbert@gondor.apana.org.au>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt

^ permalink raw reply

* Re: [Bugme-new] [Bug 6681] New: TC crash and rule freeze
From: Andrew Morton @ 2006-06-19 22:21 UTC (permalink / raw)
  To: netdev; +Cc: slavon, bugme-daemon@kernel-bugs.osdl.org
In-Reply-To: <200606121733.k5CHX9rn022476@fire-2.osdl.org>

bugme-daemon@bugzilla.kernel.org wrote:
>
> http://bugzilla.kernel.org/show_bug.cgi?id=6681
> 
>            Summary: TC crash and rule freeze
>     Kernel Version: 2.6.16-gentoo-r6
>             Status: NEW
>           Severity: normal
>              Owner: shemminger@osdl.org
>          Submitter: slavon@bigtelecom.ru
> 
> 
> Most recent kernel where this bug did not occur:
> 2.6.16-gentoo-r6
> Distribution:
> Gentoo
> Hardware Environment:
> 00:00.0 Host bridge: Intel Corporation 82865G/PE/P DRAM Controller/Host-Hub
> Interface (rev 02)
> 00:02.0 VGA compatible controller: Intel Corporation 82865G Integrated Graphics
> Controller (rev 02)
> 00:1d.0 USB Controller: Intel Corporation 82801EB/ER (ICH5/ICH5R) USB UHCI
> Controller #1 (rev 02)
> 00:1d.1 USB Controller: Intel Corporation 82801EB/ER (ICH5/ICH5R) USB UHCI
> Controller #2 (rev 02)
> 00:1d.2 USB Controller: Intel Corporation 82801EB/ER (ICH5/ICH5R) USB UHCI
> Controller #3 (rev 02)
> 00:1d.3 USB Controller: Intel Corporation 82801EB/ER (ICH5/ICH5R) USB UHCI
> Controller #4 (rev 02)
> 00:1d.7 USB Controller: Intel Corporation 82801EB/ER (ICH5/ICH5R) USB2 EHCI
> Controller (rev 02)
> 00:1e.0 PCI bridge: Intel Corporation 82801 PCI Bridge (rev c2)
> 00:1f.0 ISA bridge: Intel Corporation 82801EB/ER (ICH5/ICH5R) LPC Interface
> Bridge (rev 02)
> 00:1f.1 IDE interface: Intel Corporation 82801EB/ER (ICH5/ICH5R) IDE Controller
> (rev 02)
> 01:09.0 Ethernet controller: Intel Corporation 82557/8/9 [Ethernet Pro 100] (rev 05)
> 01:0a.0 Ethernet controller: Intel Corporation 82557/8/9 [Ethernet Pro 100] (rev 05)
> 01:0b.0 SCSI storage controller: Adaptec ASC-39320 U320 (rev 03)
> 01:0b.1 SCSI storage controller: Adaptec ASC-39320 U320 (rev 03)
> Software Environment:
> sys-apps/iproute2-2.6.16.20060323
> Problem Description:
> #cat dmeseg
> Unable to handle kernel NULL pointer dereference at virtual address 0000000c
> printing eip:
> c0217c26
> *pde = 00000000
> Oops: 0000 [#1]
> SMP
> Modules linked in: sch_sfq cls_u32 sch_red sch_htb iptable_filter ip_tables
> x_tables uhci_hcd ehci_hcd usbcore
> CPU:    0
> EIP:    0060:[<c0217c26>]    Not tainted VLI
> EFLAGS: 00010287   (2.6.16-gentoo-r6 #2)
> EIP is at __rb_erase_color+0x94/0x1ad
> eax: f55f4954   ebx: f724bb54   ecx: f724bb54   edx: 00000000
> esi: 00000000   edi: f7679468   ebp: f7679468   esp: f676bbbc
> ds: 007b   es: 007b   ss: 0068
> Process tc (pid: 24294, threadinfo=f676a000 task=f7d7da90)
> Stack: <0>f724bb54 f7679468 00000000 e6bbf154 00000000 c0217e36 00000000 f724bb54
> f7679468 e6bbf000 e6bbf06c f7679000 f7679080 f8903366 e6bbf154 f7679468
> 00000004 000000d0 00000000 00010006 000103c9 f7679000 c0311ffa f7679000
> Call Trace:
> [<c0217e36>] rb_erase+0xf7/0x12d
> [<f8903366>] htb_destroy_class+0xec/0x15d [sch_htb]
> [<c0311ffa>] tc_ctl_tclass+0x1b1/0x288
> [<c030d69e>] rtnetlink_dump_ifinfo+0x6c/0x89
> [<c030dcef>] rtnetlink_rcv_msg+0x171/0x233
> [<c031759f>] netlink_dump+0x94/0x1e2
> [<c030db7e>] rtnetlink_rcv_msg+0x0/0x233
> [<c0317a45>] netlink_rcv_skb+0x46/0xad
> [<c030db7e>] rtnetlink_rcv_msg+0x0/0x233
> [<c0317aec>] netlink_run_queue+0x40/0xd0
> [<c030db7e>] rtnetlink_rcv_msg+0x0/0x233
> [<c030db5e>] rtnetlink_rcv+0x2e/0x4e
> [<c030db7e>] rtnetlink_rcv_msg+0x0/0x233
> [<c031735c>] netlink_data_ready+0x60/0x62
> [<c03164ed>] netlink_sendskb+0x32/0x61
> [<c031704d>] netlink_sendmsg+0x291/0x304
> [<c02f9b0d>] sock_sendmsg+0xeb/0x10d
> [<c02f9b0d>] sock_sendmsg+0xeb/0x10d
> [<c0131fa6>] autoremove_wake_function+0x0/0x57
> [<c021a084>] copy_from_user+0x46/0x7e
> [<c0300ae4>] verify_iovec+0x44/0x9e
> [<c02fb525>] sys_sendmsg+0x15a/0x272
> [<c0140ca6>] filemap_nopage+0x30d/0x38a
> [<c0152e83>] page_add_file_rmap+0x2a/0x2e
> [<c014e014>] do_no_page+0x219/0x278
> [<c021a084>] copy_from_user+0x46/0x7e
> [<c02fbaf7>] sys_socketcall+0x28d/0x294
> [<c0102ca7>] sysenter_past_esp+0x54/0x75
> Code: 04 01 00 00 00 c7 43 04 00 00 00 00 89 7c 24 04 89 1c 24 e8 6b fe ff ff 8b
> 53 0c eb 8e 8b 53 08 8b 72 04 85 f6 0f 84 82 00 00 00  <8b> 4a 0c 85 c9 74 0a 83
> 79 04 01 0f 85 00 01 00 00 8b 72 08 85
> 

It crashed in net/sched/somewhere.

^ permalink raw reply

* Re: [Bugme-new] [Bug 6682] New: BUG: soft lockup detected on CPU#0! / ksoftirqd takse 100% CPU
From: Andrew Morton @ 2006-06-19 22:20 UTC (permalink / raw)
  To: netdev
  Cc: Dipankar Sarma, Paul E. McKenney,
	bugme-daemon@kernel-bugs.osdl.org, alchemyx
In-Reply-To: <200606122311.k5CNBMEx007518@fire-2.osdl.org>

bugme-daemon@bugzilla.kernel.org wrote:
>
> http://bugzilla.kernel.org/show_bug.cgi?id=6682
> 
>            Summary: BUG: soft lockup detected on CPU#0! / ksoftirqd takse
>                     100% CPU
>     Kernel Version: 2.6.15.6
>             Status: NEW
>           Severity: normal
>              Owner: acme@conectiva.com.br
>          Submitter: alchemyx@uznam.net.pl
> 
> 
> Most recent kernel where this bug did not occur: (unknown)
> Distribution: Gentoo
> Hardware Environment: 2x Xeon 2.66, 1 GB RAM, NICS: 2 x e1000, and one double
> port e100. Based on Intel E7501 architecture (2U rack Intel chassis).
> Software Environment: quagga 0.98.6
> Problem Description: ksoftirqd/0 takes 100% of CPU. further investigation shows
> no sing of network flood or something (and also 2 of 3 NICs are e1000 with
> NAPI). Ocassionaly there are "BUG: soft lockup detected on CPU#0!".
> 
> 
> Steps to reproduce:
> 
> There is no simple way to reproduce. I think that everythint started when we
> attached second provider with BGP support. We are using quagga which injects
> about 186 000 routes into kernel. When running for a while (at least few hours,
> sometimes a day) we get 100% usage on ksoftirqd/0 and following messages in logs:
> 
> BUG: soft lockup detected on CPU#0!
> 
> Pid: 6506, comm:                zebra
> EIP: 0060:[<c027f6fd>] CPU: 0
> EIP is at _spin_lock+0x7/0xf
>  EFLAGS: 00000286    Not tainted  (2.6.15.6)
> EAX: f6203180 EBX: e6fbf000 ECX: 00000000 EDX: f6bec000
> ESI: f6203000 EDI: eddb4b80 EBP: fffffff4 DS: 007b ES: 007b
> CR0: 8005003b CR2: aca6dff0 CR3: 361ad000 CR4: 000006d0
>  [<c02396f9>] dev_queue_xmit+0xe0/0x203
>  [<c0250de8>] ip_output+0x1e1/0x237
>  [<c024f3f5>] ip_forward+0x181/0x1df
>  [<c024e21a>] ip_rcv+0x40c/0x485
>  [<c0239bd0>] netif_receive_skb+0x12f/0x165
>  [<f885aa4c>] e1000_clean_rx_irq+0x389/0x410 [e1000]
>  [<f885a1ca>] e1000_clean+0x94/0x12f [e1000]
>  [<c0239d5a>] net_rx_action+0x69/0xf0
>  [<c011a305>] __do_softirq+0x55/0xbd
>  [<c011a39a>] do_softirq+0x2d/0x31
>  [<c011a3f8>] local_bh_enable+0x5a/0x65
>  [<c024a0a1>] rt_run_flush+0x5f/0x80
>  [<c027623f>] fn_hash_insert+0x352/0x39f
>  [<c027364c>] inet_rtm_newroute+0x57/0x62
>  [<c02413ed>] rtnetlink_rcv_msg+0x1a8/0x1cb
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c0247c1e>] netlink_rcv_skb+0x3a/0x8b
>  [<c0247cb1>] netlink_run_queue+0x42/0xc3
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c0241227>] rtnetlink_rcv+0x22/0x40
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c024764c>] netlink_data_ready+0x17/0x54
>  [<c0246a99>] netlink_sendskb+0x1f/0x39
>  [<c0247449>] netlink_sendmsg+0x27b/0x28c
>  [<c0231467>] sock_sendmsg+0xce/0xe9
>  [<c0112b36>] __wake_up+0x27/0x3b
>  [<c01a6216>] copy_to_user+0x38/0x42
>  [<c01a625a>] copy_from_user+0x3a/0x60
>  [<c01a625a>] copy_from_user+0x3a/0x60
>  [<c0126be2>] autoremove_wake_function+0x0/0x3a
>  [<c0236bcd>] verify_iovec+0x49/0x7f
>  [<c02327f2>] sys_sendmsg+0x152/0x1a8
>  [<c0147a62>] do_sync_read+0xb8/0xeb
>  [<c01a6216>] copy_to_user+0x38/0x42
>  [<c0126be2>] autoremove_wake_function+0x0/0x3a
>  [<c0122b7a>] getrusage+0x34/0x43
>  [<c0168504>] inotify_dentry_parent_queue_event+0x29/0x7c
>  [<c01a625a>] copy_from_user+0x3a/0x60
>  [<c0232b6b>] sys_socketcall+0x167/0x180
>  [<c0102433>] sysenter_past_esp+0x54/0x75
> 
> BUG: soft lockup detected on CPU#0!
> 
> Pid: 6506, comm:                zebra
> EIP: 0060:[<f8952052>] CPU: 0
> EIP is at u32_classify+0x52/0x170 [cls_u32]
>  EFLAGS: 00000206    Not tainted  (2.6.15.6)
> EAX: e2fbd020 EBX: f48649c0 ECX: 00000010 EDX: 29b09d5a
> ESI: f48649ec EDI: 00000001 EBP: e2fbd020 DS: 007b ES: 007b
> CR0: 8005003b CR2: 08154004 CR3: 361ad000 CR4: 000006d0
>  [<f88462fa>] ipt_do_table+0x2de/0x2fd [ip_tables]
>  [<f883b523>] ip_nat_fn+0x177/0x185 [iptable_nat]
>  [<f88e159f>] ip_refrag+0x23/0x5f [ip_conntrack]
>  [<c0244d82>] tc_classify+0x2c/0x3f
>  [<f895514b>] htb_classify+0x14b/0x1dd [sch_htb]
>  [<f8955638>] htb_enqueue+0x1d/0x13a [sch_htb]
>  [<c02396fd>] dev_queue_xmit+0xe4/0x203
>  [<c0250de8>] ip_output+0x1e1/0x237
>  [<c024f3f5>] ip_forward+0x181/0x1df
>  [<c024e21a>] ip_rcv+0x40c/0x485
>  [<c0239bd0>] netif_receive_skb+0x12f/0x165
>  [<f885aa4c>] e1000_clean_rx_irq+0x389/0x410 [e1000]
>  [<f885a1ca>] e1000_clean+0x94/0x12f [e1000]
>  [<c0239d5a>] net_rx_action+0x69/0xf0
>  [<c011a305>] __do_softirq+0x55/0xbd
>  [<c011a39a>] do_softirq+0x2d/0x31
>  [<c011a3f8>] local_bh_enable+0x5a/0x65
>  [<c024a0a1>] rt_run_flush+0x5f/0x80
>  [<c027623f>] fn_hash_insert+0x352/0x39f
>  [<c027364c>] inet_rtm_newroute+0x57/0x62
>  [<c02413ed>] rtnetlink_rcv_msg+0x1a8/0x1cb
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c0247c1e>] netlink_rcv_skb+0x3a/0x8b
>  [<c0247cb1>] netlink_run_queue+0x42/0xc3
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c0241227>] rtnetlink_rcv+0x22/0x40
>  [<c0241245>] rtnetlink_rcv_msg+0x0/0x1cb
>  [<c024764c>] netlink_data_ready+0x17/0x54
>  [<c0246a99>] netlink_sendskb+0x1f/0x39
>  [<c0247449>] netlink_sendmsg+0x27b/0x28c
>  [<c0231467>] sock_sendmsg+0xce/0xe9
>  [<c0112b36>] __wake_up+0x27/0x3b
>  [<c01a625a>] copy_from_user+0x3a/0x60
>  [<c01a625a>] copy_from_user+0x3a/0x60
>  [<c0126be2>] autoremove_wake_function+0x0/0x3a
>  [<c0236bcd>] verify_iovec+0x49/0x7f
>  [<c02327f2>] sys_sendmsg+0x152/0x1a8
>  [<c0147a62>] do_sync_read+0xb8/0xeb
>  [<c0122b7a>] getrusage+0x34/0x43
>  [<c011d72f>] update_wall_time+0xa/0x32
>  [<c011d9e5>] do_timer+0x33/0xa9
>  [<c01a625a>] copy_from_user+0x3a/0x60
>  [<c0232b6b>] sys_socketcall+0x167/0x180
>  [<c0102433>] sysenter_past_esp+0x54/0x75
> 
> It happens on 2.6.15.6. Tonight I will try 2.6.16.16 with FIB_TRIE instead of
> FIB_HASH. I am submitting that bug under network but I am not completly sure if
> it belongs here.

This also happens on 2.6.16.6.

^ 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