Re: [PATCH] macb: Fix speed setting

2008-02-21 Thread Haavard Skinnemoen
On Thu, 21 Feb 2008 22:50:54 +0900 (JST)
Atsushi Nemoto [EMAIL PROTECTED] wrote:

 Fix NCFGR.SPD setting on 10Mbps.  This bug was introduced by
 conversion to generic PHY layer in kernel 2.6.23.
 
 Signed-off-by: Atsushi Nemoto [EMAIL PROTECTED]
 ---
 diff --git a/drivers/net/macb.c b/drivers/net/macb.c
 index 81bf005..1d210ed 100644
 --- a/drivers/net/macb.c
 +++ b/drivers/net/macb.c
 @@ -148,7 +148,7 @@ static void macb_handle_link_change(struct net_device 
 *dev)
  
   if (phydev-duplex)
   reg |= MACB_BIT(FD);
 - if (phydev-speed)
 + if (phydev-speed == SPEED_100)

I have to admit that even after looking through include/linux/phy.h and
include/linux/mii.h, I don't have the faintest idea what values we can
expect to find in the speed field of phydev. The comment above struct
phy_device says that it is used like in mii_if_info, but struct
mii_if_info doesn't have a speed field...

I'm willing to take your word for it, but some documentation would be
really nice...

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] macb: Fix speed setting

2008-02-21 Thread Haavard Skinnemoen
On Fri, 22 Feb 2008 00:07:31 +0900 (JST)
Atsushi Nemoto [EMAIL PROTECTED] wrote:

  I'm willing to take your word for it, but some documentation would be
  really nice...  
 
 Well, simple grepping drivers/net/phy enlighten us ;)

Yeah, the patch certainly looks correct as far as I can tell.

 Anyway, this patch fixes problem with 10Mbps on AT91SAM9260 board.

Thanks. I'll pass it on.

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: BUG: 2.6.25-rc1: iptables postrouting setup causes oops

2008-02-13 Thread Haavard Skinnemoen
On Wed, 13 Feb 2008 00:48:29 -0800
Andrew Morton [EMAIL PROTECTED] wrote:

 On Tue, 12 Feb 2008 22:46:01 +1100 Ben Nizette [EMAIL PROTECTED] wrote:
 
  
  On an AVR32, root over NFS, config attached, running (from a startup
  script):
  
  iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
  
  Results in (dmesg extract including a bit of context for good measure):
  -8
  VFS: Mounted root (nfs filesystem).
  Freeing init memory: 72K (9000 - 90012000)
  eth0: no IPv6 routers present
  warning: `dnsmasq' uses 32-bit capabilities (legacy support in use)

Hmm. What does that mean? What size do capabilities normally have?

  ip_tables: (C) 2000-2006 Netfilter Core Team
  nf_conntrack version 0.5.0 (1024 buckets, 4096 max)
  Unable to handle kernel paging request at virtual address d76a7138
  ptbr = 91d3b000 pgd = e5f3 pte = 00014370

Hmm. It actually found something in the pte? Looks like a swap
entry...but that doesn't make sense at that virtual address. Userspace
is below 0x8000.

  Oops: Kernel access of bad area, sig: 11 [#1]
  FRAME_POINTER chip: 0x01f:0x1e82 rev 2
  Modules linked in: nf_conntrack_ipv4(+) nf_conntrack ip_tables
  PC is at kmem_cache_alloc+0x2c/0x54
  LR is at nf_conntrack_l4proto_register+0x34/0x9c [nf_conntrack]
 
 I take it that the above means that the crash is in kmem_cache_alloc()?

That's correct.

 If so, the bug could be almost anywhere - in slab, or in some random piece
 of code which scribbles on slab's data structures.

Yes, it looks like memory corruption, especially since the page table
appears to be corrupted as well. But I'll have a look and see if the
code that dumps the pte is doing something bogus...

  Perfectly repeatable.
 
 If my theory is correct, changing pretty much anything in the kernel config
 might just make it go away.  But still, it would be most valuable if you
 could try running a bisection search, as described in
 http://www.kernel.org/doc/local/git-quick.html, thanks.

Yes, that would be very valuable.

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: BUG: 2.6.25-rc1: iptables postrouting setup causes oops

2008-02-13 Thread Haavard Skinnemoen
On Wed, 13 Feb 2008 10:10:24 +0100
Haavard Skinnemoen [EMAIL PROTECTED] wrote:

   ip_tables: (C) 2000-2006 Netfilter Core Team
   nf_conntrack version 0.5.0 (1024 buckets, 4096 max)
   Unable to handle kernel paging request at virtual address d76a7138
   ptbr = 91d3b000 pgd = e5f3 pte = 00014370  
 
 Hmm. It actually found something in the pte? Looks like a swap
 entry...but that doesn't make sense at that virtual address. Userspace
 is below 0x8000.

(...)

  If so, the bug could be almost anywhere - in slab, or in some random piece
  of code which scribbles on slab's data structures.  
 
 Yes, it looks like memory corruption, especially since the page table
 appears to be corrupted as well. But I'll have a look and see if the
 code that dumps the pte is doing something bogus...

Yes, that code is indeed buggy. The below patch should fix it, although
the page tables probably won't contain anything interesting, and it
could still be a memory corruption issue. And it definitely won't fix
the real issue.

I have a couple of patches that will eliminate the need for this fixup
(and probably improve performance as well), but they are probably 2.6.26
material.

Haavard

diff --git a/arch/avr32/mm/fault.c b/arch/avr32/mm/fault.c
index 6560cb1..ce4e429 100644
--- a/arch/avr32/mm/fault.c
+++ b/arch/avr32/mm/fault.c
@@ -189,6 +189,8 @@ no_context:
 
page = sysreg_read(PTBR);
printk(KERN_ALERT ptbr = %08lx, page);
+   if (address = TASK_SIZE)
+   page = (unsigned long)swapper_pg_dir;
if (page) {
page = ((unsigned long *)page)[address  22];
printk( pgd = %08lx, page);
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: BUG: 2.6.25-rc1: iptables postrouting setup causes oops

2008-02-13 Thread Haavard Skinnemoen
On Wed, 13 Feb 2008 08:42:15 -0800
Andrew G. Morgan [EMAIL PROTECTED] wrote:

 However, it is a warning and, for any existing app that doesn't care
 about newly added capabilities, the warning is benign.

Ok, I see. Thanks for explaining.

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] macb: Fix section mismatch and shrink runtime footprint

2008-01-31 Thread Haavard Skinnemoen
macb devices are only found integrated on SoCs, so they can't be
hotplugged. Thus, the probe() and exit() functions can be __init and
__exit, respectively. By using platform_driver_probe() instead of
platform_driver_register(), there won't be any references to the
discarded probe() function after the driver has loaded.

This also fixes a section mismatch due to macb_probe(), defined as
__devinit, calling macb_get_hwaddr, defined as __init.

Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |9 -
 1 files changed, 4 insertions(+), 5 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index e10528e..81bf005 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -1084,7 +1084,7 @@ static int macb_ioctl(struct net_device *dev, struct 
ifreq *rq, int cmd)
return phy_mii_ioctl(phydev, if_mii(rq), cmd);
 }
 
-static int __devinit macb_probe(struct platform_device *pdev)
+static int __init macb_probe(struct platform_device *pdev)
 {
struct eth_platform_data *pdata;
struct resource *regs;
@@ -1248,7 +1248,7 @@ err_out:
return err;
 }
 
-static int __devexit macb_remove(struct platform_device *pdev)
+static int __exit macb_remove(struct platform_device *pdev)
 {
struct net_device *dev;
struct macb *bp;
@@ -1276,8 +1276,7 @@ static int __devexit macb_remove(struct platform_device 
*pdev)
 }
 
 static struct platform_driver macb_driver = {
-   .probe  = macb_probe,
-   .remove = __devexit_p(macb_remove),
+   .remove = __exit_p(macb_remove),
.driver = {
.name   = macb,
},
@@ -1285,7 +1284,7 @@ static struct platform_driver macb_driver = {
 
 static int __init macb_init(void)
 {
-   return platform_driver_register(macb_driver);
+   return platform_driver_probe(macb_driver, macb_probe);
 }
 
 static void __exit macb_exit(void)
-- 
1.5.3.8

--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] PHYLIB: Locking fixes for PHY I/O potentially sleeping

2008-01-29 Thread Haavard Skinnemoen
On Tue, 29 Jan 2008 10:05:09 -0600
Nate Case [EMAIL PROTECTED] wrote:

 +/* PHY timer which schedules the state machine work */
 +static void phy_timer(unsigned long data)
 +{
 + struct phy_device *phydev = (struct phy_device *)data;
 +
 + /*
 +  * PHY I/O operations can potentially sleep so we ensure that
 +  * it's done from a process context
 +  */
 + schedule_work(phydev-state_queue);
 +}

If you use schedule_delayed_work() instead, you can get rid of the
timer.

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] MACB: clear transmit buffers properly on transmit underrun

2007-12-19 Thread Haavard Skinnemoen
From: Gregory CLEMENT [EMAIL PROTECTED]

Initially transmit buffer pointers were only reset. But buffer
descriptors were possibly still set as ready, and buffer in upper
layer was not freed. This caused driver hang under big load.  Now
reset clean properly the buffer descriptor and freed upper layer.

Signed-off-by: Gregory CLEMENT [EMAIL PROTECTED]
Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |   25 -
 1 files changed, 24 insertions(+), 1 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index 047ea7b..e10528e 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -307,8 +307,31 @@ static void macb_tx(struct macb *bp)
(unsigned long)status);
 
if (status  MACB_BIT(UND)) {
+   int i;
printk(KERN_ERR %s: TX underrun, resetting buffers\n,
-  bp-dev-name);
+   bp-dev-name);
+
+   head = bp-tx_head;
+
+   /*Mark all the buffer as used to avoid sending a lost buffer*/
+   for (i = 0; i  TX_RING_SIZE; i++)
+   bp-tx_ring[i].ctrl = MACB_BIT(TX_USED);
+
+   /* free transmit buffer in upper layer*/
+   for (tail = bp-tx_tail; tail != head; tail = NEXT_TX(tail)) {
+   struct ring_info *rp = bp-tx_skb[tail];
+   struct sk_buff *skb = rp-skb;
+
+   BUG_ON(skb == NULL);
+
+   rmb();
+
+   dma_unmap_single(bp-pdev-dev, rp-mapping, skb-len,
+DMA_TO_DEVICE);
+   rp-skb = NULL;
+   dev_kfree_skb_irq(skb);
+   }
+
bp-tx_head = bp-tx_tail = 0;
}
 
-- 
1.5.3.4

--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] MACB: clear transmit buffers properly on TX Underrun

2007-12-18 Thread Haavard Skinnemoen
On Sun, 16 Dec 2007 12:37:25 +0100
Gregory CLEMENT [EMAIL PROTECTED] wrote:

 Haavard Skinnemoen a écrit :
  But the patch is a bit mangled, so I don't think it will apply. Please
  have a look in Documentation/email-clients.txt for information on how
  to set up Thunderbird to avoid this.
 
 I read it and apply it. Hope it will be OK as I didn't see any problem in m 
 first mail...

Looks good, thanks.

  
  I also think this should be done as part of the previous loop, before
  they are freed. Having free buffers in the ring sounds dangerous, even
  if it's only for a short time.
 
 OK, I moved this loop before the previous loop, as I wanted to be sure that
 all buffers are marked.
 I did it, but I think we don't really need to do it, as when underrun happen, 
 controller stop transmitting, so it won't transmit a free buffer.

Yes, you're probably right. But it looks better now, I think.

  
  +
   bp-tx_head = bp-tx_tail = 0;
  
  Now, I wonder if it would be better to just scan the ring descriptors,
  find the one that failed and just move the DMA pointer to the next
  entry. The hardware resets the DMA pointer when an underrun happens, so
  I think your code will work, but we're losing more packets than
  strictly necessary. In any case, it's better than the existing code.
 
 As hardware reset the DMA pointer, we have to rewrite all the buffer 
 descriptor.
 
 For example if descriptor n°78 failed, and there is descriptor 79 and 80 which
 are pending. When underrun happen on 78 the hardware reset DMA pointer which
 will point on descriptor 0. So we have to copy descriptor 79 on 0 and 80 on 1.
 The other option is to change Transmit Buffer Queue Pointer Register (TBQP), 
 to
 make it point on descriptor 79, but on the next descriptor having wrapped bit 
 set,
 the DMA pointer will wrapped on descriptor 79 and not on 0. So I don't think 
 it
 is a good solution.

The second option sounds feasible to me. We know how large the ring is,
so taking care of the wrapping isn't very expensive.

  Perhaps we need a check in macb_start_xmit() as well to avoid starting
  a transmission when the ring has just been reset.
  
 
 I joined the patch change along your recommendation, if there is no more 
 error, you
 can maybe submit it for 2.6.24 release, and other improvement can be done 
 later.

Ok, if it works for you, I'll send it upstream; your patch certainly
improves things. I think there's still an unresolved race with
macb_start_xmit()...but closing it involves more complex modifications
to the main tx patch, so it's probably safest to leave it for 2.6.25.

 From: Gregory CLEMENT [EMAIL PROTECTED]
 Date: Sun, 16 Dec 2007 11:45:03 +0100
 Subject: [PATCH]  MACB: clear transmit buffers properly on transmit underrun
 
 Initially transmit buffer pointers were only reset. But buffer descriptors
 were possibly still set as ready, and buffer in upper layer was not
 freed. This caused driver hang under big load.
 Now reset clean properly the buffer descriptor and freed upper layer.
 
 Signed-off-by: Gregory CLEMENT [EMAIL PROTECTED]
 ---
  drivers/net/macb.c |   27 ++-
  1 files changed, 26 insertions(+), 1 deletions(-)
 
 diff --git a/drivers/net/macb.c b/drivers/net/macb.c
 index 047ea7b..e898713 100644
 --- a/drivers/net/macb.c
 +++ b/drivers/net/macb.c
 @@ -307,9 +307,34 @@ static void macb_tx(struct macb *bp)
   (unsigned long)status);
  
   if (status  MACB_BIT(UND)) {
 + int i;
   printk(KERN_ERR %s: TX underrun, resetting buffers\n,
 -bp-dev-name);
 +bp-dev-name);

I'll just kill these extra spaces...


   bp-tx_head = bp-tx_tail = 0;
 +

...and this extra line.

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] MACB: clear transmit buffers properly on TX Underrun

2007-12-13 Thread Haavard Skinnemoen
On Thu, 13 Dec 2007 08:51:57 +0100
Gregory CLEMENT [EMAIL PROTECTED] wrote:

 Hi,
 I generated this patch for linux 2.6.24-rc5 and test it on AT91SAM9263 
 with iperf.
 
 From: Gregory CLEMENT [EMAIL PROTECTED]
 Date: Wed, 12 Dec 2007 18:10:14 +0100
 Subject: [PATCH] MACB: clear transmit buffers properly on TX Underrun
 
 Initially transmit buffer pointers were only reset. But buffer descriptors
 were possibly still set as ready, and buffer in upper layer was not
 freed. This caused driver hang under big load.
 Now reset clean properly the buffer descriptor and freed upper layer.

Nice. I think we want this for 2.6.24.

But the patch is a bit mangled, so I don't think it will apply. Please
have a look in Documentation/email-clients.txt for information on how
to set up Thunderbird to avoid this.

 Signed-off-by: Gregory CLEMENT [EMAIL PROTECTED]
 ---
  drivers/net/macb.c |   26 +-
  1 files changed, 25 insertions(+), 1 deletions(-)
 
 diff --git a/drivers/net/macb.c b/drivers/net/macb.c
 index 047ea7b..2ee1dab 100644
 --- a/drivers/net/macb.c
 +++ b/drivers/net/macb.c
 @@ -307,9 +307,33 @@ static void macb_tx(struct macb *bp)
  (unsigned long)status);
  
  if (status  MACB_BIT(UND)) {
 +int i;
  printk(KERN_ERR %s: TX underrun, resetting buffers\n,
 -   bp-dev-name);
 +   bp-dev-name);
 +
 +head = bp-tx_head;
 +
 +/* free transmit buffer in upper layer*/
 +for (tail = bp-tx_tail; tail != head; tail = NEXT_TX(tail)) {
 +struct ring_info *rp = bp-tx_skb[tail];
 +struct sk_buff *skb = rp-skb;
 +
 +BUG_ON(skb == NULL);
 +
 +rmb();
 +
 +dma_unmap_single(bp-pdev-dev, rp-mapping, skb-len,
 + DMA_TO_DEVICE);
 +rp-skb = NULL;
 +dev_kfree_skb_irq(skb);
 +}
 +
 +/*Mark all the buffer as used to avoid sending a lost buffer*/
 +for (i = 0; i  RX_RING_SIZE; i++)
 +bp-tx_ring[i].ctrl = MACB_BIT(TX_USED);

That should be TX_RING_SIZE, shouldn't it?

I also think this should be done as part of the previous loop, before
they are freed. Having free buffers in the ring sounds dangerous, even
if it's only for a short time.

 +
  bp-tx_head = bp-tx_tail = 0;

Now, I wonder if it would be better to just scan the ring descriptors,
find the one that failed and just move the DMA pointer to the next
entry. The hardware resets the DMA pointer when an underrun happens, so
I think your code will work, but we're losing more packets than
strictly necessary. In any case, it's better than the existing code.

Perhaps we need a check in macb_start_xmit() as well to avoid starting
a transmission when the ring has just been reset.

Haavard
--
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH 2.6.23-rc8-mm2] Fix a compile problem in macb.c

2007-10-02 Thread Haavard Skinnemoen
From: Hans-Jürgen Koch [EMAIL PROTECTED]

Compiling macb.c fails because the type of parameter 2 of macb_poll()
was changed from int* to int. Furthermore, a local variable was removed
but was still used inside the function. This patch fixes it.

Signed-off-by: Hans J. Koch [EMAIL PROTECTED]
Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |4 ++--
 1 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index c28a0a4..047ea7b 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -492,7 +492,7 @@ static int macb_poll(struct napi_struct *napi, int budget)
}
 
dev_dbg(bp-pdev-dev, poll: status = %08lx, budget = %d\n,
-   (unsigned long)status, *budget);
+   (unsigned long)status, budget);
 
if (!(status  MACB_BIT(REC))) {
dev_warn(bp-pdev-dev,
@@ -503,7 +503,7 @@ static int macb_poll(struct napi_struct *napi, int budget)
}
 
work_done = macb_rx(bp, budget);
-   if (work_done  orig_budget)
+   if (work_done  budget)
netif_rx_complete(dev, napi);
 
/*
-- 
1.5.3.1

-
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] macb: Add multicast capability

2007-07-12 Thread Haavard Skinnemoen
From: Patrice Vilchez [EMAIL PROTECTED]

Add multicast capability to Atmel ethernet macb driver.

Signed-off-by: Patrice Vilchez [EMAIL PROTECTED]
Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |  120 
 1 files changed, 120 insertions(+), 0 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index 83c35fd..a4bb026 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -796,6 +796,125 @@ static void macb_init_hw(struct macb *bp)
 
 }
 
+/*
+ * The hash address register is 64 bits long and takes up two
+ * locations in the memory map.  The least significant bits are stored
+ * in EMAC_HSL and the most significant bits in EMAC_HSH.
+ *
+ * The unicast hash enable and the multicast hash enable bits in the
+ * network configuration register enable the reception of hash matched
+ * frames. The destination address is reduced to a 6 bit index into
+ * the 64 bit hash register using the following hash function.  The
+ * hash function is an exclusive or of every sixth bit of the
+ * destination address.
+ *
+ * hi[5] = da[5] ^ da[11] ^ da[17] ^ da[23] ^ da[29] ^ da[35] ^ da[41] ^ da[47]
+ * hi[4] = da[4] ^ da[10] ^ da[16] ^ da[22] ^ da[28] ^ da[34] ^ da[40] ^ da[46]
+ * hi[3] = da[3] ^ da[09] ^ da[15] ^ da[21] ^ da[27] ^ da[33] ^ da[39] ^ da[45]
+ * hi[2] = da[2] ^ da[08] ^ da[14] ^ da[20] ^ da[26] ^ da[32] ^ da[38] ^ da[44]
+ * hi[1] = da[1] ^ da[07] ^ da[13] ^ da[19] ^ da[25] ^ da[31] ^ da[37] ^ da[43]
+ * hi[0] = da[0] ^ da[06] ^ da[12] ^ da[18] ^ da[24] ^ da[30] ^ da[36] ^ da[42]
+ *
+ * da[0] represents the least significant bit of the first byte
+ * received, that is, the multicast/unicast indicator, and da[47]
+ * represents the most significant bit of the last byte received.  If
+ * the hash index, hi[n], points to a bit that is set in the hash
+ * register then the frame will be matched according to whether the
+ * frame is multicast or unicast.  A multicast match will be signalled
+ * if the multicast hash enable bit is set, da[0] is 1 and the hash
+ * index points to a bit set in the hash register.  A unicast match
+ * will be signalled if the unicast hash enable bit is set, da[0] is 0
+ * and the hash index points to a bit set in the hash register.  To
+ * receive all multicast frames, the hash register should be set with
+ * all ones and the multicast hash enable bit should be set in the
+ * network configuration register.
+ */
+
+static inline int hash_bit_value(int bitnr, __u8 *addr)
+{
+   if (addr[bitnr / 8]  (1  (bitnr % 8)))
+   return 1;
+   return 0;
+}
+
+/*
+ * Return the hash index value for the specified address.
+ */
+static int hash_get_index(__u8 *addr)
+{
+   int i, j, bitval;
+   int hash_index = 0;
+
+   for (j = 0; j  6; j++) {
+   for (i = 0, bitval = 0; i  8; i++)
+   bitval ^= hash_bit_value(i*6 + j, addr);
+
+   hash_index |= (bitval  j);
+   }
+
+   return hash_index;
+}
+
+/*
+ * Add multicast addresses to the internal multicast-hash table.
+ */
+static void macb_sethashtable(struct net_device *dev)
+{
+   struct dev_mc_list *curr;
+   unsigned long mc_filter[2];
+   unsigned int i, bitnr;
+   struct macb *bp = netdev_priv(dev);
+
+   mc_filter[0] = mc_filter[1] = 0;
+
+   curr = dev-mc_list;
+   for (i = 0; i  dev-mc_count; i++, curr = curr-next) {
+   if (!curr) break;   /* unexpected end of list */
+
+   bitnr = hash_get_index(curr-dmi_addr);
+   mc_filter[bitnr  5] |= 1  (bitnr  31);
+   }
+
+   macb_writel(bp, HRB, mc_filter[0]);
+   macb_writel(bp, HRT, mc_filter[1]);
+}
+
+/*
+ * Enable/Disable promiscuous and multicast modes.
+ */
+static void macb_set_rx_mode(struct net_device *dev)
+{
+   unsigned long cfg;
+   struct macb *bp = netdev_priv(dev);
+
+   cfg = macb_readl(bp, NCFGR);
+
+   if (dev-flags  IFF_PROMISC)
+   /* Enable promiscuous mode */
+   cfg |= MACB_BIT(CAF);
+   else if (dev-flags  (~IFF_PROMISC))
+/* Disable promiscuous mode */
+   cfg = ~MACB_BIT(CAF);
+
+   if (dev-flags  IFF_ALLMULTI) {
+   /* Enable all multicast mode */
+   macb_writel(bp, HRB, -1);
+   macb_writel(bp, HRT, -1);
+   cfg |= MACB_BIT(NCFGR_MTI);
+   } else if (dev-mc_count  0) {
+   /* Enable specific multicasts */
+   macb_sethashtable(dev);
+   cfg |= MACB_BIT(NCFGR_MTI);
+   } else if (dev-flags  (~IFF_ALLMULTI)) {
+   /* Disable all multicast mode */
+   macb_writel(bp, HRB, 0);
+   macb_writel(bp, HRT, 0);
+   cfg = ~MACB_BIT(NCFGR_MTI);
+   }
+
+   macb_writel(bp, NCFGR, cfg);
+}
+
 static int macb_open(struct net_device *dev)
 {
struct macb *bp = netdev_priv(dev);
@@ -1025,6 +1144,7

[PATCH] macb: Use generic PHY layer

2007-07-12 Thread Haavard Skinnemoen
From: frederic RODO [EMAIL PROTECTED]

Convert the macb driver to use the generic PHY layer in
drivers/net/phy.

Signed-off-by: Frederic RODO [EMAIL PROTECTED]
Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/Kconfig   |2 +-
 drivers/net/macb.c|  451 +++--
 drivers/net/macb.h|   10 +-
 include/asm-arm/arch-at91/board.h |1 +
 include/asm-avr32/arch-at32ap/board.h |1 +
 5 files changed, 208 insertions(+), 257 deletions(-)

diff --git a/drivers/net/Kconfig b/drivers/net/Kconfig
index b941c74..4b9b7fe 100644
--- a/drivers/net/Kconfig
+++ b/drivers/net/Kconfig
@@ -187,7 +187,7 @@ config MII
 config MACB
tristate Atmel MACB support
depends on AVR32 || ARCH_AT91SAM9260 || ARCH_AT91SAM9263
-   select MII
+   select PHYLIB
help
  The Atmel MACB ethernet interface is found on many AT32 and AT91
  parts. Say Y to include support for the MACB chip.
diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index 0e04f7a..83c35fd 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -17,13 +17,12 @@
 #include linux/init.h
 #include linux/netdevice.h
 #include linux/etherdevice.h
-#include linux/mii.h
-#include linux/mutex.h
 #include linux/dma-mapping.h
-#include linux/ethtool.h
 #include linux/platform_device.h
+#include linux/phy.h
 
 #include asm/arch/board.h
+#include asm/arch/cpu.h
 
 #include macb.h
 
@@ -85,172 +84,202 @@ static void __init macb_get_hwaddr(struct macb *bp)
memcpy(bp-dev-dev_addr, addr, sizeof(addr));
 }
 
-static void macb_enable_mdio(struct macb *bp)
+static int macb_mdio_read(struct mii_bus *bus, int mii_id, int regnum)
 {
-   unsigned long flags;
-   u32 reg;
-
-   spin_lock_irqsave(bp-lock, flags);
-   reg = macb_readl(bp, NCR);
-   reg |= MACB_BIT(MPE);
-   macb_writel(bp, NCR, reg);
-   macb_writel(bp, IER, MACB_BIT(MFD));
-   spin_unlock_irqrestore(bp-lock, flags);
-}
-
-static void macb_disable_mdio(struct macb *bp)
-{
-   unsigned long flags;
-   u32 reg;
-
-   spin_lock_irqsave(bp-lock, flags);
-   reg = macb_readl(bp, NCR);
-   reg = ~MACB_BIT(MPE);
-   macb_writel(bp, NCR, reg);
-   macb_writel(bp, IDR, MACB_BIT(MFD));
-   spin_unlock_irqrestore(bp-lock, flags);
-}
-
-static int macb_mdio_read(struct net_device *dev, int phy_id, int location)
-{
-   struct macb *bp = netdev_priv(dev);
+   struct macb *bp = bus-priv;
int value;
 
-   mutex_lock(bp-mdio_mutex);
-
-   macb_enable_mdio(bp);
macb_writel(bp, MAN, (MACB_BF(SOF, MACB_MAN_SOF)
  | MACB_BF(RW, MACB_MAN_READ)
- | MACB_BF(PHYA, phy_id)
- | MACB_BF(REGA, location)
+ | MACB_BF(PHYA, mii_id)
+ | MACB_BF(REGA, regnum)
  | MACB_BF(CODE, MACB_MAN_CODE)));
 
-   wait_for_completion(bp-mdio_complete);
+   /* wait for end of transfer */
+   while (!MACB_BFEXT(IDLE, macb_readl(bp, NSR)))
+   cpu_relax();
 
value = MACB_BFEXT(DATA, macb_readl(bp, MAN));
-   macb_disable_mdio(bp);
-   mutex_unlock(bp-mdio_mutex);
 
return value;
 }
 
-static void macb_mdio_write(struct net_device *dev, int phy_id,
-   int location, int val)
+static int macb_mdio_write(struct mii_bus *bus, int mii_id, int regnum,
+  u16 value)
 {
-   struct macb *bp = netdev_priv(dev);
-
-   dev_dbg(bp-pdev-dev, mdio_write %02x:%02x - %04x\n,
-   phy_id, location, val);
-
-   mutex_lock(bp-mdio_mutex);
-   macb_enable_mdio(bp);
+   struct macb *bp = bus-priv;
 
macb_writel(bp, MAN, (MACB_BF(SOF, MACB_MAN_SOF)
  | MACB_BF(RW, MACB_MAN_WRITE)
- | MACB_BF(PHYA, phy_id)
- | MACB_BF(REGA, location)
+ | MACB_BF(PHYA, mii_id)
+ | MACB_BF(REGA, regnum)
  | MACB_BF(CODE, MACB_MAN_CODE)
- | MACB_BF(DATA, val)));
+ | MACB_BF(DATA, value)));
 
-   wait_for_completion(bp-mdio_complete);
+   /* wait for end of transfer */
+   while (!MACB_BFEXT(IDLE, macb_readl(bp, NSR)))
+   cpu_relax();
+
+   return 0;
+}
 
-   macb_disable_mdio(bp);
-   mutex_unlock(bp-mdio_mutex);
+static int macb_mdio_reset(struct mii_bus *bus)
+{
+   return 0;
 }
 
-static int macb_phy_probe(struct macb *bp)
+static void macb_handle_link_change(struct net_device *dev)
 {
-   int phy_address;
-   u16 phyid1, phyid2;
+   struct macb *bp = netdev_priv(dev);
+   struct phy_device *phydev = bp-phy_dev;
+   unsigned long flags;
 
-   for (phy_address = 0

[PATCH] macb: Remove inappropriate spinlocks around mii calls

2007-02-16 Thread Haavard Skinnemoen
Remove spin_lock_irqsave() around mii_ethtool_gset, mii_ethtool_sset
and generic_mii_ioctl. These are unnecessary and harmful because
the mii calls may call back into the mdio functions, which may sleep.

Pointed out by David Brownell.

Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |   24 +++-
 1 files changed, 3 insertions(+), 21 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index a41418b..2e9571b 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -881,27 +881,15 @@ static struct net_device_stats *macb_get_stats(struct 
net_device *dev)
 static int macb_get_settings(struct net_device *dev, struct ethtool_cmd *cmd)
 {
struct macb *bp = netdev_priv(dev);
-   int ret;
-   unsigned long flags;
-
-   spin_lock_irqsave(bp-lock, flags);
-   ret = mii_ethtool_gset(bp-mii, cmd);
-   spin_unlock_irqrestore(bp-lock, flags);
 
-   return ret;
+   return mii_ethtool_gset(bp-mii, cmd);
 }
 
 static int macb_set_settings(struct net_device *dev, struct ethtool_cmd *cmd)
 {
struct macb *bp = netdev_priv(dev);
-   int ret;
-   unsigned long flags;
-
-   spin_lock_irqsave(bp-lock, flags);
-   ret = mii_ethtool_sset(bp-mii, cmd);
-   spin_unlock_irqrestore(bp-lock, flags);
 
-   return ret;
+   return mii_ethtool_sset(bp-mii, cmd);
 }
 
 static void macb_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo 
*info)
@@ -930,17 +918,11 @@ static struct ethtool_ops macb_ethtool_ops = {
 static int macb_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
 {
struct macb *bp = netdev_priv(dev);
-   int ret;
-   unsigned long flags;
 
if (!netif_running(dev))
return -EINVAL;
 
-   spin_lock_irqsave(bp-lock, flags);
-   ret = generic_mii_ioctl(bp-mii, if_mii(rq), cmd, NULL);
-   spin_unlock_irqrestore(bp-lock, flags);
-
-   return ret;
+   return generic_mii_ioctl(bp-mii, if_mii(rq), cmd, NULL);
 }
 
 static ssize_t macb_mii_show(const struct device *_dev, char *buf,
-- 
1.4.4.4

-
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] AT91: MACB support

2007-02-07 Thread Haavard Skinnemoen
From: Andrew Victor [EMAIL PROTECTED]

The Atmel MACB Ethernet peripheral is also integrated in the AT91SAM9260
and AT91SAM9263 processors.  The differences from the AVR32 version are:
  * Single peripheral clock.
  * MII/RMII selection bit is inverted.
  * Clock enable bit.

Original patch from Patrice Vilchez.

Signed-off-by: Andrew Victor [EMAIL PROTECTED]
Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/Kconfig |2 +-
 drivers/net/macb.c  |   25 +++--
 drivers/net/macb.h  |8 +++-
 3 files changed, 31 insertions(+), 4 deletions(-)

diff --git a/drivers/net/Kconfig b/drivers/net/Kconfig
index 8aa8dd0..3318f30 100644
--- a/drivers/net/Kconfig
+++ b/drivers/net/Kconfig
@@ -190,7 +190,7 @@ config MII
 
 config MACB
tristate Atmel MACB support
-   depends on NET_ETHERNET  AVR32
+   depends on NET_ETHERNET  (AVR32 || ARCH_AT91SAM9260 || 
ARCH_AT91SAM9263)
select MII
help
  The Atmel MACB ethernet interface is found on many AT32 and AT91
diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index 25b559b..5eb7a35 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -1046,6 +1046,14 @@ static int __devinit macb_probe(struct platform_device 
*pdev)
 
spin_lock_init(bp-lock);
 
+#if defined(CONFIG_ARCH_AT91)
+   bp-pclk = clk_get(pdev-dev, macb_clk);
+   if (IS_ERR(bp-pclk)) {
+   dev_err(pdev-dev, failed to get macb_clk\n);
+   goto err_out_free_dev;
+   }
+   clk_enable(bp-pclk);
+#else
bp-pclk = clk_get(pdev-dev, pclk);
if (IS_ERR(bp-pclk)) {
dev_err(pdev-dev, failed to get pclk\n);
@@ -1059,6 +1067,7 @@ static int __devinit macb_probe(struct platform_device 
*pdev)
 
clk_enable(bp-pclk);
clk_enable(bp-hclk);
+#endif
 
bp-regs = ioremap(regs-start, regs-end - regs-start + 1);
if (!bp-regs) {
@@ -1119,9 +1128,17 @@ static int __devinit macb_probe(struct platform_device 
*pdev)
 
pdata = pdev-dev.platform_data;
if (pdata  pdata-is_rmii)
+#if defined(CONFIG_ARCH_AT91)
+   macb_writel(bp, USRIO, (MACB_BIT(RMII) | MACB_BIT(CLKEN)) );
+#else
macb_writel(bp, USRIO, 0);
+#endif
else
+#if defined(CONFIG_ARCH_AT91)
+   macb_writel(bp, USRIO, MACB_BIT(CLKEN));
+#else
macb_writel(bp, USRIO, MACB_BIT(MII));
+#endif
 
bp-tx_pending = DEF_TX_RING_PENDING;
 
@@ -1148,9 +1165,11 @@ err_out_free_irq:
 err_out_iounmap:
iounmap(bp-regs);
 err_out_disable_clocks:
+#ifndef CONFIG_ARCH_AT91
clk_disable(bp-hclk);
-   clk_disable(bp-pclk);
clk_put(bp-hclk);
+#endif
+   clk_disable(bp-pclk);
 err_out_put_pclk:
clk_put(bp-pclk);
 err_out_free_dev:
@@ -1173,9 +1192,11 @@ static int __devexit macb_remove(struct platform_device 
*pdev)
unregister_netdev(dev);
free_irq(dev-irq, dev);
iounmap(bp-regs);
+#ifndef CONFIG_ARCH_AT91
clk_disable(bp-hclk);
-   clk_disable(bp-pclk);
clk_put(bp-hclk);
+#endif
+   clk_disable(bp-pclk);
clk_put(bp-pclk);
free_netdev(dev);
platform_set_drvdata(pdev, NULL);
diff --git a/drivers/net/macb.h b/drivers/net/macb.h
index 27bf0ae..b3bb218 100644
--- a/drivers/net/macb.h
+++ b/drivers/net/macb.h
@@ -200,7 +200,7 @@
 #define MACB_SOF_OFFSET30
 #define MACB_SOF_SIZE  2
 
-/* Bitfields in USRIO */
+/* Bitfields in USRIO (AVR32) */
 #define MACB_MII_OFFSET0
 #define MACB_MII_SIZE  1
 #define MACB_EAM_OFFSET1
@@ -210,6 +210,12 @@
 #define MACB_TX_PAUSE_ZERO_OFFSET  3
 #define MACB_TX_PAUSE_ZERO_SIZE1
 
+/* Bitfields in USRIO (AT91) */
+#define MACB_RMII_OFFSET   0
+#define MACB_RMII_SIZE 1
+#define MACB_CLKEN_OFFSET  1
+#define MACB_CLKEN_SIZE1
+
 /* Bitfields in WOL */
 #define MACB_IP_OFFSET 0
 #define MACB_IP_SIZE   16
-- 
1.4.4.3

-
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] MACB: Use struct delayed_work instead of struct work_struct

2006-12-08 Thread Haavard Skinnemoen
The macb driver calls schedule_delayed_work() and friends, so we need
to use a struct delayed_work along with it. The conversion was
explained by David Howells on lkml Dec 5 2006:

http://lkml.org/lkml/2006/12/5/269

Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |6 +++---
 drivers/net/macb.h |2 +-
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index bd0ce98..3496d19 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -267,9 +267,9 @@ static void macb_update_stats(struct mac
*p += readl(reg);
 }
 
-static void macb_periodic_task(void *arg)
+static void macb_periodic_task(struct work_struct *work)
 {
-   struct macb *bp = arg;
+   struct macb *bp = container_of(work, struct macb, periodic_task.work);
 
macb_update_stats(bp);
macb_check_media(bp, 1, 0);
@@ -1088,7 +1088,7 @@ static int __devinit macb_probe(struct p
 
dev-base_addr = regs-start;
 
-   INIT_WORK(bp-periodic_task, macb_periodic_task, bp);
+   INIT_DELAYED_WORK(bp-periodic_task, macb_periodic_task);
mutex_init(bp-mdio_mutex);
init_completion(bp-mdio_complete);
 
diff --git a/drivers/net/macb.h b/drivers/net/macb.h
index 8c253db..e3fcb2e 100644
--- a/drivers/net/macb.h
+++ b/drivers/net/macb.h
@@ -377,7 +377,7 @@ struct macb {
 
unsigned intrx_pending, tx_pending;
 
-   struct work_struct  periodic_task;
+   struct delayed_work periodic_task;
 
struct mutexmdio_mutex;
struct completion   mdio_complete;
-- 
1.4.3.3

-
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] MACB: Use __raw register access

2006-12-08 Thread Haavard Skinnemoen
Since macb is a chip-internal device, use __raw_readl and
__raw_writel instead of readl/writel. This will perform native-endian
accesses, which is the right thing to do on both AVR32 and ARM devices.

Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 drivers/net/macb.c |2 +-
 drivers/net/macb.h |4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/net/macb.c b/drivers/net/macb.c
index 3496d19..25b559b 100644
--- a/drivers/net/macb.c
+++ b/drivers/net/macb.c
@@ -264,7 +264,7 @@ static void macb_update_stats(struct mac
WARN_ON((unsigned long)(end - p - 1) != (MACB_TPF - MACB_PFR) / 4);
 
for(; p  end; p++, reg++)
-   *p += readl(reg);
+   *p += __raw_readl(reg);
 }
 
 static void macb_periodic_task(struct work_struct *work)
diff --git a/drivers/net/macb.h b/drivers/net/macb.h
index e3fcb2e..27bf0ae 100644
--- a/drivers/net/macb.h
+++ b/drivers/net/macb.h
@@ -250,9 +250,9 @@
 
 /* Register access macros */
 #define macb_readl(port,reg)   \
-   readl((port)-regs + MACB_##reg)
+   __raw_readl((port)-regs + MACB_##reg)
 #define macb_writel(port,reg,value)\
-   writel((value), (port)-regs + MACB_##reg)
+   __raw_writel((value), (port)-regs + MACB_##reg)
 
 struct dma_desc {
u32 addr;
-- 
1.4.3.3

-
To unsubscribe from this list: send the line unsubscribe netdev in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH take 2] Atmel MACB ethernet driver

2006-11-09 Thread Haavard Skinnemoen
Driver for the Atmel MACB on-chip ethernet module.

Tested on AVR32/AT32AP7000/ATSTK1000. I've heard rumours that it works
with AT91SAM9260 as well, and it may be possible to share some code with
the at91_ether driver for AT91RM9200.

Hardware documentation can be found in the AT32AP7000 data sheet,
which can be downloaded from

http://www.atmel.com/dyn/products/datasheets.asp?family_id=682

Changes since previous version:
  * Probe for PHY ID instead of depending on it being provided through
platform_data.
  * Grab initial ethernet address from the MACB registers instead
of depending on platform_data.
  * Set MII/RMII mode correctly.

These changes are mostly about making the driver more compatible with
the at91 infrastructure.

Signed-off-by: Haavard Skinnemoen [EMAIL PROTECTED]
---
 MAINTAINERS  |7 +
 drivers/net/Kconfig  |   11 +
 drivers/net/Makefile |2 +
 drivers/net/macb.c   | 1210 ++
 drivers/net/macb.h   |  387 
 5 files changed, 1617 insertions(+), 0 deletions(-)

diff --git a/MAINTAINERS b/MAINTAINERS
index d708702..b8c28b5 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -426,6 +426,13 @@ L: [EMAIL PROTECTED]
 W: http://linux-atm.sourceforge.net
 S: Maintained
 
+ATMEL MACB ETHERNET DRIVER
+P: Atmel AVR32 Support Team
+M: [EMAIL PROTECTED]
+P: Haavard Skinnemoen
+M: [EMAIL PROTECTED]
+S: Supported
+
 ATMEL WIRELESS DRIVER
 P: Simon Kelley
 M: [EMAIL PROTECTED]
diff --git a/drivers/net/Kconfig b/drivers/net/Kconfig
index 9cb3ca5..4e033b1 100644
--- a/drivers/net/Kconfig
+++ b/drivers/net/Kconfig
@@ -188,6 +188,17 @@ config MII
  or internal device.  It is safe to say Y or M here even if your
  ethernet card lack MII.
 
+config MACB
+   tristate Atmel MACB support
+   depends on NET_ETHERNET  AVR32
+   select MII
+   help
+ The Atmel MACB ethernet interface is found on many AT32 and AT91
+ parts. Say Y to include support for the MACB chip.
+
+ To compile this driver as a module, choose M here: the module
+ will be called macb.
+
 source drivers/net/arm/Kconfig
 
 config MACE
diff --git a/drivers/net/Makefile b/drivers/net/Makefile
index f270bc4..8e67697 100644
--- a/drivers/net/Makefile
+++ b/drivers/net/Makefile
@@ -197,6 +197,8 @@ obj-$(CONFIG_SMC911X) += smc911x.o
 obj-$(CONFIG_DM9000) += dm9000.o
 obj-$(CONFIG_FEC_8XX) += fec_8xx/
 
+obj-$(CONFIG_MACB) += macb.o
+
 obj-$(CONFIG_ARM) += arm/
 obj-$(CONFIG_DEV_APPLETALK) += appletalk/
 obj-$(CONFIG_TR) += tokenring/
diff --git a/drivers/net/macb.c b/drivers/net/macb.c
new file mode 100644
index 000..bd0ce98
--- /dev/null
+++ b/drivers/net/macb.c
@@ -0,0 +1,1210 @@
+/*
+ * Atmel MACB Ethernet Controller driver
+ *
+ * Copyright (C) 2004-2006 Atmel Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#include linux/clk.h
+#include linux/module.h
+#include linux/moduleparam.h
+#include linux/kernel.h
+#include linux/types.h
+#include linux/slab.h
+#include linux/init.h
+#include linux/netdevice.h
+#include linux/etherdevice.h
+#include linux/mii.h
+#include linux/mutex.h
+#include linux/dma-mapping.h
+#include linux/ethtool.h
+#include linux/platform_device.h
+
+#include asm/arch/board.h
+
+#include macb.h
+
+#define to_net_dev(class) container_of(class, struct net_device, class_dev)
+
+#define RX_BUFFER_SIZE 128
+#define RX_RING_SIZE   512
+#define RX_RING_BYTES  (sizeof(struct dma_desc) * RX_RING_SIZE)
+
+/* Make the IP header word-aligned (the ethernet header is 14 bytes) */
+#define RX_OFFSET  2
+
+#define TX_RING_SIZE   128
+#define DEF_TX_RING_PENDING(TX_RING_SIZE - 1)
+#define TX_RING_BYTES  (sizeof(struct dma_desc) * TX_RING_SIZE)
+
+#define TX_RING_GAP(bp)\
+   (TX_RING_SIZE - (bp)-tx_pending)
+#define TX_BUFFS_AVAIL(bp) \
+   (((bp)-tx_tail = (bp)-tx_head) ? \
+(bp)-tx_tail + (bp)-tx_pending - (bp)-tx_head : \
+(bp)-tx_tail - (bp)-tx_head - TX_RING_GAP(bp))
+#define NEXT_TX(n) (((n) + 1)  (TX_RING_SIZE - 1))
+
+#define NEXT_RX(n) (((n) + 1)  (RX_RING_SIZE - 1))
+
+/* minimum number of free TX descriptors before waking up TX process */
+#define MACB_TX_WAKEUP_THRESH  (TX_RING_SIZE / 4)
+
+#define MACB_RX_INT_FLAGS  (MACB_BIT(RCOMP) | MACB_BIT(RXUBR)  \
+| MACB_BIT(ISR_ROVR))
+
+static void __macb_set_hwaddr(struct macb *bp)
+{
+   u32 bottom;
+   u16 top;
+
+   bottom = cpu_to_le32(*((u32 *)bp-dev-dev_addr));
+   macb_writel(bp, SA1B, bottom);
+   top = cpu_to_le16(*((u16 *)(bp-dev-dev_addr + 4)));
+   macb_writel(bp, SA1T