// SPDX-License-Identifier: GPL-2.0
/* $Id: sungem.c,v 1.44.2.22 2002/03/13 01:18:12 davem Exp $
 * sungem.c: Sun GEM ethernet driver.
 *
 * Copyright (C) 2000, 2001, 2002, 2003 David S. Miller (davem@redhat.com)
 *
 * Support for Apple GMAC and assorted PHYs, WOL, Power Management
 * (C) 2001,2002,2003 Benjamin Herrenscmidt (benh@kernel.crashing.org)
 * (C) 2004,2005 Benjamin Herrenscmidt, IBM Corp.
 *
 * NAPI and NETPOLL support
 * (C) 2004 by Eric Lemoine (eric.lemoine@gmail.com)
 *
 */

#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/fcntl.h>
#include <linux/interrupt.h>
#include <linux/ioport.h>
#include <linux/in.h>
#include <linux/sched.h>
#include <linux/string.h>
#include <linux/delay.h>
#include <linux/errno.h>
#include <linux/pci.h>
#include <linux/dma-mapping.h>
#include <linux/netdevice.h>
#include <linux/etherdevice.h>
#include <linux/skbuff.h>
#include <linux/mii.h>
#include <linux/ethtool.h>
#include <linux/crc32.h>
#include <linux/random.h>
#include <linux/workqueue.h>
#include <linux/if_vlan.h>
#include <linux/bitops.h>
#include <linux/mm.h>
#include <linux/gfp.h>

#include <asm/io.h>
#include <asm/byteorder.h>
#include <linux/uaccess.h>
#include <asm/irq.h>

#ifdef CONFIG_SPARC
#include <asm/idprom.h>
#include <asm/prom.h>
#endif

#ifdef CONFIG_PPC_PMAC
#include <asm/prom.h>
#include <asm/machdep.h>
#include <asm/pmac_feature.h>
#endif

#include <linux/sungem_phy.h>
#include "sungem.h"

#define STRIP_FCS

#define DEFAULT_MSG	(NETIF_MSG_DRV		| \
			 NETIF_MSG_PROBE	| \
			 NETIF_MSG_LINK)

#define ADVERTISE_MASK	(SUPPORTED_10baseT_Half | SUPPORTED_10baseT_Full | \
			 SUPPORTED_100baseT_Half | SUPPORTED_100baseT_Full | \
			 SUPPORTED_1000baseT_Half | SUPPORTED_1000baseT_Full | \
			 SUPPORTED_Pause | SUPPORTED_Autoneg)

#define DRV_NAME	"sungem"
#define DRV_VERSION	"1.0"
#define DRV_AUTHOR	"David S. Miller <davem@redhat.com>"

static char version[] =
        DRV_NAME ".c:v" DRV_VERSION " " DRV_AUTHOR "\n";

MODULE_AUTHOR(DRV_AUTHOR);
MODULE_DESCRIPTION("Sun GEM Gbit ethernet driver");
MODULE_LICENSE("GPL");

#define GEM_MODULE_NAME	"gem"

static const struct pci_device_id gem_pci_tbl[] = {
	{ PCI_VENDOR_ID_SUN, PCI_DEVICE_ID_SUN_GEM,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },

	/* These models only differ from the original GEM in
	 * that their tx/rx fifos are of a different size and
	 * they only support 10/100 speeds. -DaveM
	 *
	 * Apple's GMAC does support gigabit on machines with
	 * the BCM54xx PHYs. -BenH
	 */
	{ PCI_VENDOR_ID_SUN, PCI_DEVICE_ID_SUN_RIO_GEM,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{ PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_UNI_N_GMAC,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{ PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_UNI_N_GMACP,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{ PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_UNI_N_GMAC2,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{ PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_K2_GMAC,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{ PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_SH_SUNGEM,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{ PCI_VENDOR_ID_APPLE, PCI_DEVICE_ID_APPLE_IPID2_GMAC,
	  PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0UL },
	{0, }
};

MODULE_DEVICE_TABLE(pci, gem_pci_tbl);

static u16 __sungem_phy_read(struct gem *gp, int phy_addr, int reg)
{
	u32 cmd;
	int limit = 10000;

	cmd  = (1 << 30);
	cmd |= (2 << 28);
	cmd |= (phy_addr << 23) & MIF_FRAME_PHYAD;
	cmd |= (reg << 18) & MIF_FRAME_REGAD;
	cmd |= (MIF_FRAME_TAMSB);
	writel(cmd, gp->regs + MIF_FRAME);

	while (--limit) {
		cmd = readl(gp->regs + MIF_FRAME);
		if (cmd & MIF_FRAME_TALSB)
			break;

		udelay(10);
	}

	if (!limit)
		cmd = 0xffff;

	return cmd & MIF_FRAME_DATA;
}

static inline int _sungem_phy_read(struct net_device *dev, int mii_id, int reg)
{
	struct gem *gp = netdev_priv(dev);
	return __sungem_phy_read(gp, mii_id, reg);
}

static inline u16 sungem_phy_read(struct gem *gp, int reg)
{
	return __sungem_phy_read(gp, gp->mii_phy_addr, reg);
}

static void __sungem_phy_write(struct gem *gp, int phy_addr, int reg, u16 val)
{
	u32 cmd;
	int limit = 10000;

	cmd  = (1 << 30);
	cmd |= (1 << 28);
	cmd |= (phy_addr << 23) & MIF_FRAME_PHYAD;
	cmd |= (reg << 18) & MIF_FRAME_REGAD;
	cmd |= (MIF_FRAME_TAMSB);
	cmd |= (val & MIF_FRAME_DATA);
	writel(cmd, gp->regs + MIF_FRAME);

	while (limit--) {
		cmd = readl(gp->regs + MIF_FRAME);
		if (cmd & MIF_FRAME_TALSB)
			break;

		udelay(10);
	}
}

static inline void _sungem_phy_write(struct net_device *dev, int mii_id, int reg, int val)
{
	struct gem *gp = netdev_priv(dev);
	__sungem_phy_write(gp, mii_id, reg, val & 0xffff);
}

static inline void sungem_phy_write(struct gem *gp, int reg, u16 val)
{
	__sungem_phy_write(gp, gp->mii_phy_addr, reg, val);
}

static inline void gem_enable_ints(struct gem *gp)
{
	/* Enable all interrupts but TXDONE */
	writel(GREG_STAT_TXDONE, gp->regs + GREG_IMASK);
}

static inline void gem_disable_ints(struct gem *gp)
{
	/* Disable all interrupts, including TXDONE */
	writel(GREG_STAT_NAPI | GREG_STAT_TXDONE, gp->regs + GREG_IMASK);
	(void)readl(gp->regs + GREG_IMASK); /* write posting */
}

static void gem_get_cell(struct gem *gp)
{
	BUG_ON(gp->cell_enabled < 0);
	gp->cell_enabled++;
#ifdef CONFIG_PPC_PMAC
	if (gp->cell_enabled == 1) {
		mb();
		pmac_call_feature(PMAC_FTR_GMAC_ENABLE, gp->of_node, 0, 1);
		udelay(10);
	}
#endif /* CONFIG_PPC_PMAC */
}

/* Turn off the chip's clock */
static void gem_put_cell(struct gem *gp)
{
	BUG_ON(gp->cell_enabled <= 0);
	gp->cell_enabled--;
#ifdef CONFIG_PPC_PMAC
	if (gp->cell_enabled == 0) {
		mb();
		pmac_call_feature(PMAC_FTR_GMAC_ENABLE, gp->of_node, 0, 0);
		udelay(10);
	}
#endif /* CONFIG_PPC_PMAC */
}

static inline void gem_netif_stop(struct gem *gp)
{
	netif_trans_update(gp->dev);	/* prevent tx timeout */
	napi_disable(&gp->napi);
	netif_tx_disable(gp->dev);
}

static inline void gem_netif_start(struct gem *gp)
{
	/* NOTE: unconditional netif_wake_queue is only
	 * appropriate so long as all callers are assured to
	 * have free tx slots.
	 */
	netif_wake_queue(gp->dev);
	napi_enable(&gp->napi);
}

static void gem_schedule_reset(struct gem *gp)
{
	gp->reset_task_pending = 1;
	schedule_work(&gp->reset_task);
}

static void gem_handle_mif_event(struct gem *gp, u32 reg_val, u32 changed_bits)
{
	if (netif_msg_intr(gp))
		printk(KERN_DEBUG "%s: mif interrupt\n", gp->dev->name);
}

static int gem_pcs_interrupt(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	u32 pcs_istat = readl(gp->regs + PCS_ISTAT);
	u32 pcs_miistat;

	if (netif_msg_intr(gp))
		printk(KERN_DEBUG "%s: pcs interrupt, pcs_istat: 0x%x\n",
			gp->dev->name, pcs_istat);

	if (!(pcs_istat & PCS_ISTAT_LSC)) {
		netdev_err(dev, "PCS irq but no link status change???\n");
		return 0;
	}

	/* The link status bit latches on zero, so you must
	 * read it twice in such a case to see a transition
	 * to the link being up.
	 */
	pcs_miistat = readl(gp->regs + PCS_MIISTAT);
	if (!(pcs_miistat & PCS_MIISTAT_LS))
		pcs_miistat |=
			(readl(gp->regs + PCS_MIISTAT) &
			 PCS_MIISTAT_LS);

	if (pcs_miistat & PCS_MIISTAT_ANC) {
		/* The remote-fault indication is only valid
		 * when autoneg has completed.
		 */
		if (pcs_miistat & PCS_MIISTAT_RF)
			netdev_info(dev, "PCS AutoNEG complete, RemoteFault\n");
		else
			netdev_info(dev, "PCS AutoNEG complete\n");
	}

	if (pcs_miistat & PCS_MIISTAT_LS) {
		netdev_info(dev, "PCS link is now up\n");
		netif_carrier_on(gp->dev);
	} else {
		netdev_info(dev, "PCS link is now down\n");
		netif_carrier_off(gp->dev);
		/* If this happens and the link timer is not running,
		 * reset so we re-negotiate.
		 */
		if (!timer_pending(&gp->link_timer))
			return 1;
	}

	return 0;
}

static int gem_txmac_interrupt(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	u32 txmac_stat = readl(gp->regs + MAC_TXSTAT);

	if (netif_msg_intr(gp))
		printk(KERN_DEBUG "%s: txmac interrupt, txmac_stat: 0x%x\n",
			gp->dev->name, txmac_stat);

	/* Defer timer expiration is quite normal,
	 * don't even log the event.
	 */
	if ((txmac_stat & MAC_TXSTAT_DTE) &&
	    !(txmac_stat & ~MAC_TXSTAT_DTE))
		return 0;

	if (txmac_stat & MAC_TXSTAT_URUN) {
		netdev_err(dev, "TX MAC xmit underrun\n");
		dev->stats.tx_fifo_errors++;
	}

	if (txmac_stat & MAC_TXSTAT_MPE) {
		netdev_err(dev, "TX MAC max packet size error\n");
		dev->stats.tx_errors++;
	}

	/* The rest are all cases of one of the 16-bit TX
	 * counters expiring.
	 */
	if (txmac_stat & MAC_TXSTAT_NCE)
		dev->stats.collisions += 0x10000;

	if (txmac_stat & MAC_TXSTAT_ECE) {
		dev->stats.tx_aborted_errors += 0x10000;
		dev->stats.collisions += 0x10000;
	}

	if (txmac_stat & MAC_TXSTAT_LCE) {
		dev->stats.tx_aborted_errors += 0x10000;
		dev->stats.collisions += 0x10000;
	}

	/* We do not keep track of MAC_TXSTAT_FCE and
	 * MAC_TXSTAT_PCE events.
	 */
	return 0;
}

/* When we get a RX fifo overflow, the RX unit in GEM is probably hung
 * so we do the following.
 *
 * If any part of the reset goes wrong, we return 1 and that causes the
 * whole chip to be reset.
 */
static int gem_rxmac_reset(struct gem *gp)
{
	struct net_device *dev = gp->dev;
	int limit, i;
	u64 desc_dma;
	u32 val;

	/* First, reset & disable MAC RX. */
	writel(MAC_RXRST_CMD, gp->regs + MAC_RXRST);
	for (limit = 0; limit < 5000; limit++) {
		if (!(readl(gp->regs + MAC_RXRST) & MAC_RXRST_CMD))
			break;
		udelay(10);
	}
	if (limit == 5000) {
		netdev_err(dev, "RX MAC will not reset, resetting whole chip\n");
		return 1;
	}

	writel(gp->mac_rx_cfg & ~MAC_RXCFG_ENAB,
	       gp->regs + MAC_RXCFG);
	for (limit = 0; limit < 5000; limit++) {
		if (!(readl(gp->regs + MAC_RXCFG) & MAC_RXCFG_ENAB))
			break;
		udelay(10);
	}
	if (limit == 5000) {
		netdev_err(dev, "RX MAC will not disable, resetting whole chip\n");
		return 1;
	}

	/* Second, disable RX DMA. */
	writel(0, gp->regs + RXDMA_CFG);
	for (limit = 0; limit < 5000; limit++) {
		if (!(readl(gp->regs + RXDMA_CFG) & RXDMA_CFG_ENABLE))
			break;
		udelay(10);
	}
	if (limit == 5000) {
		netdev_err(dev, "RX DMA will not disable, resetting whole chip\n");
		return 1;
	}

	mdelay(5);

	/* Execute RX reset command. */
	writel(gp->swrst_base | GREG_SWRST_RXRST,
	       gp->regs + GREG_SWRST);
	for (limit = 0; limit < 5000; limit++) {
		if (!(readl(gp->regs + GREG_SWRST) & GREG_SWRST_RXRST))
			break;
		udelay(10);
	}
	if (limit == 5000) {
		netdev_err(dev, "RX reset command will not execute, resetting whole chip\n");
		return 1;
	}

	/* Refresh the RX ring. */
	for (i = 0; i < RX_RING_SIZE; i++) {
		struct gem_rxd *rxd = &gp->init_block->rxd[i];

		if (gp->rx_skbs[i] == NULL) {
			netdev_err(dev, "Parts of RX ring empty, resetting whole chip\n");
			return 1;
		}

		rxd->status_word = cpu_to_le64(RXDCTRL_FRESH(gp));
	}
	gp->rx_new = gp->rx_old = 0;

	/* Now we must reprogram the rest of RX unit. */
	desc_dma = (u64) gp->gblock_dvma;
	desc_dma += (INIT_BLOCK_TX_RING_SIZE * sizeof(struct gem_txd));
	writel(desc_dma >> 32, gp->regs + RXDMA_DBHI);
	writel(desc_dma & 0xffffffff, gp->regs + RXDMA_DBLOW);
	writel(RX_RING_SIZE - 4, gp->regs + RXDMA_KICK);
	val = (RXDMA_CFG_BASE | (RX_OFFSET << 10) |
	       (ETH_HLEN << 13) | RXDMA_CFG_FTHRESH_128);
	writel(val, gp->regs + RXDMA_CFG);
	if (readl(gp->regs + GREG_BIFCFG) & GREG_BIFCFG_M66EN)
		writel(((5 & RXDMA_BLANK_IPKTS) |
			((8 << 12) & RXDMA_BLANK_ITIME)),
		       gp->regs + RXDMA_BLANK);
	else
		writel(((5 & RXDMA_BLANK_IPKTS) |
			((4 << 12) & RXDMA_BLANK_ITIME)),
		       gp->regs + RXDMA_BLANK);
	val  = (((gp->rx_pause_off / 64) << 0) & RXDMA_PTHRESH_OFF);
	val |= (((gp->rx_pause_on / 64) << 12) & RXDMA_PTHRESH_ON);
	writel(val, gp->regs + RXDMA_PTHRESH);
	val = readl(gp->regs + RXDMA_CFG);
	writel(val | RXDMA_CFG_ENABLE, gp->regs + RXDMA_CFG);
	writel(MAC_RXSTAT_RCV, gp->regs + MAC_RXMASK);
	val = readl(gp->regs + MAC_RXCFG);
	writel(val | MAC_RXCFG_ENAB, gp->regs + MAC_RXCFG);

	return 0;
}

static int gem_rxmac_interrupt(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	u32 rxmac_stat = readl(gp->regs + MAC_RXSTAT);
	int ret = 0;

	if (netif_msg_intr(gp))
		printk(KERN_DEBUG "%s: rxmac interrupt, rxmac_stat: 0x%x\n",
			gp->dev->name, rxmac_stat);

	if (rxmac_stat & MAC_RXSTAT_OFLW) {
		u32 smac = readl(gp->regs + MAC_SMACHINE);

		netdev_err(dev, "RX MAC fifo overflow smac[%08x]\n", smac);
		dev->stats.rx_over_errors++;
		dev->stats.rx_fifo_errors++;

		ret = gem_rxmac_reset(gp);
	}

	if (rxmac_stat & MAC_RXSTAT_ACE)
		dev->stats.rx_frame_errors += 0x10000;

	if (rxmac_stat & MAC_RXSTAT_CCE)
		dev->stats.rx_crc_errors += 0x10000;

	if (rxmac_stat & MAC_RXSTAT_LCE)
		dev->stats.rx_length_errors += 0x10000;

	/* We do not track MAC_RXSTAT_FCE and MAC_RXSTAT_VCE
	 * events.
	 */
	return ret;
}

static int gem_mac_interrupt(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	u32 mac_cstat = readl(gp->regs + MAC_CSTAT);

	if (netif_msg_intr(gp))
		printk(KERN_DEBUG "%s: mac interrupt, mac_cstat: 0x%x\n",
			gp->dev->name, mac_cstat);

	/* This interrupt is just for pause frame and pause
	 * tracking.  It is useful for diagnostics and debug
	 * but probably by default we will mask these events.
	 */
	if (mac_cstat & MAC_CSTAT_PS)
		gp->pause_entered++;

	if (mac_cstat & MAC_CSTAT_PRCV)
		gp->pause_last_time_recvd = (mac_cstat >> 16);

	return 0;
}

static int gem_mif_interrupt(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	u32 mif_status = readl(gp->regs + MIF_STATUS);
	u32 reg_val, changed_bits;

	reg_val = (mif_status & MIF_STATUS_DATA) >> 16;
	changed_bits = (mif_status & MIF_STATUS_STAT);

	gem_handle_mif_event(gp, reg_val, changed_bits);

	return 0;
}

static int gem_pci_interrupt(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	u32 pci_estat = readl(gp->regs + GREG_PCIESTAT);

	if (gp->pdev->vendor == PCI_VENDOR_ID_SUN &&
	    gp->pdev->device == PCI_DEVICE_ID_SUN_GEM) {
		netdev_err(dev, "PCI error [%04x]", pci_estat);

		if (pci_estat & GREG_PCIESTAT_BADACK)
			pr_cont(" <No ACK64# during ABS64 cycle>");
		if (pci_estat & GREG_PCIESTAT_DTRTO)
			pr_cont(" <Delayed transaction timeout>");
		if (pci_estat & GREG_PCIESTAT_OTHER)
			pr_cont(" <other>");
		pr_cont("\n");
	} else {
		pci_estat |= GREG_PCIESTAT_OTHER;
		netdev_err(dev, "PCI error\n");
	}

	if (pci_estat & GREG_PCIESTAT_OTHER) {
		u16 pci_cfg_stat;

		/* Interrogate PCI config space for the
		 * true cause.
		 */
		pci_read_config_word(gp->pdev, PCI_STATUS,
				     &pci_cfg_stat);
		netdev_err(dev, "Read PCI cfg space status [%04x]\n",
			   pci_cfg_stat);
		if (pci_cfg_stat & PCI_STATUS_PARITY)
			netdev_err(dev, "PCI parity error detected\n");
		if (pci_cfg_stat & PCI_STATUS_SIG_TARGET_ABORT)
			netdev_err(dev, "PCI target abort\n");
		if (pci_cfg_stat & PCI_STATUS_REC_TARGET_ABORT)
			netdev_err(dev, "PCI master acks target abort\n");
		if (pci_cfg_stat & PCI_STATUS_REC_MASTER_ABORT)
			netdev_err(dev, "PCI master abort\n");
		if (pci_cfg_stat & PCI_STATUS_SIG_SYSTEM_ERROR)
			netdev_err(dev, "PCI system error SERR#\n");
		if (pci_cfg_stat & PCI_STATUS_DETECTED_PARITY)
			netdev_err(dev, "PCI parity error\n");

		/* Write the error bits back to clear them. */
		pci_cfg_stat &= (PCI_STATUS_PARITY |
				 PCI_STATUS_SIG_TARGET_ABORT |
				 PCI_STATUS_REC_TARGET_ABORT |
				 PCI_STATUS_REC_MASTER_ABORT |
				 PCI_STATUS_SIG_SYSTEM_ERROR |
				 PCI_STATUS_DETECTED_PARITY);
		pci_write_config_word(gp->pdev,
				      PCI_STATUS, pci_cfg_stat);
	}

	/* For all PCI errors, we should reset the chip. */
	return 1;
}

/* All non-normal interrupt conditions get serviced here.
 * Returns non-zero if we should just exit the interrupt
 * handler right now (ie. if we reset the card which invalidates
 * all of the other original irq status bits).
 */
static int gem_abnormal_irq(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	if (gem_status & GREG_STAT_RXNOBUF) {
		/* Frame arrived, no free RX buffers available. */
		if (netif_msg_rx_err(gp))
			printk(KERN_DEBUG "%s: no buffer for rx frame\n",
				gp->dev->name);
		dev->stats.rx_dropped++;
	}

	if (gem_status & GREG_STAT_RXTAGERR) {
		/* corrupt RX tag framing */
		if (netif_msg_rx_err(gp))
			printk(KERN_DEBUG "%s: corrupt rx tag framing\n",
				gp->dev->name);
		dev->stats.rx_errors++;

		return 1;
	}

	if (gem_status & GREG_STAT_PCS) {
		if (gem_pcs_interrupt(dev, gp, gem_status))
			return 1;
	}

	if (gem_status & GREG_STAT_TXMAC) {
		if (gem_txmac_interrupt(dev, gp, gem_status))
			return 1;
	}

	if (gem_status & GREG_STAT_RXMAC) {
		if (gem_rxmac_interrupt(dev, gp, gem_status))
			return 1;
	}

	if (gem_status & GREG_STAT_MAC) {
		if (gem_mac_interrupt(dev, gp, gem_status))
			return 1;
	}

	if (gem_status & GREG_STAT_MIF) {
		if (gem_mif_interrupt(dev, gp, gem_status))
			return 1;
	}

	if (gem_status & GREG_STAT_PCIERR) {
		if (gem_pci_interrupt(dev, gp, gem_status))
			return 1;
	}

	return 0;
}

static __inline__ void gem_tx(struct net_device *dev, struct gem *gp, u32 gem_status)
{
	int entry, limit;

	entry = gp->tx_old;
	limit = ((gem_status & GREG_STAT_TXNR) >> GREG_STAT_TXNR_SHIFT);
	while (entry != limit) {
		struct sk_buff *skb;
		struct gem_txd *txd;
		dma_addr_t dma_addr;
		u32 dma_len;
		int frag;

		if (netif_msg_tx_done(gp))
			printk(KERN_DEBUG "%s: tx done, slot %d\n",
				gp->dev->name, entry);
		skb = gp->tx_skbs[entry];
		if (skb_shinfo(skb)->nr_frags) {
			int last = entry + skb_shinfo(skb)->nr_frags;
			int walk = entry;
			int incomplete = 0;

			last &= (TX_RING_SIZE - 1);
			for (;;) {
				walk = NEXT_TX(walk);
				if (walk == limit)
					incomplete = 1;
				if (walk == last)
					break;
			}
			if (incomplete)
				break;
		}
		gp->tx_skbs[entry] = NULL;
		dev->stats.tx_bytes += skb->len;

		for (frag = 0; frag <= skb_shinfo(skb)->nr_frags; frag++) {
			txd = &gp->init_block->txd[entry];

			dma_addr = le64_to_cpu(txd->buffer);
			dma_len = le64_to_cpu(txd->control_word) & TXDCTRL_BUFSZ;

			pci_unmap_page(gp->pdev, dma_addr, dma_len, PCI_DMA_TODEVICE);
			entry = NEXT_TX(entry);
		}

		dev->stats.tx_packets++;
		dev_consume_skb_any(skb);
	}
	gp->tx_old = entry;

	/* Need to make the tx_old update visible to gem_start_xmit()
	 * before checking for netif_queue_stopped().  Without the
	 * memory barrier, there is a small possibility that gem_start_xmit()
	 * will miss it and cause the queue to be stopped forever.
	 */
	smp_mb();

	if (unlikely(netif_queue_stopped(dev) &&
		     TX_BUFFS_AVAIL(gp) > (MAX_SKB_FRAGS + 1))) {
		struct netdev_queue *txq = netdev_get_tx_queue(dev, 0);

		__netif_tx_lock(txq, smp_processor_id());
		if (netif_queue_stopped(dev) &&
		    TX_BUFFS_AVAIL(gp) > (MAX_SKB_FRAGS + 1))
			netif_wake_queue(dev);
		__netif_tx_unlock(txq);
	}
}

static __inline__ void gem_post_rxds(struct gem *gp, int limit)
{
	int cluster_start, curr, count, kick;

	cluster_start = curr = (gp->rx_new & ~(4 - 1));
	count = 0;
	kick = -1;
	dma_wmb();
	while (curr != limit) {
		curr = NEXT_RX(curr);
		if (++count == 4) {
			struct gem_rxd *rxd =
				&gp->init_block->rxd[cluster_start];
			for (;;) {
				rxd->status_word = cpu_to_le64(RXDCTRL_FRESH(gp));
				rxd++;
				cluster_start = NEXT_RX(cluster_start);
				if (cluster_start == curr)
					break;
			}
			kick = curr;
			count = 0;
		}
	}
	if (kick >= 0) {
		mb();
		writel(kick, gp->regs + RXDMA_KICK);
	}
}

#define ALIGNED_RX_SKB_ADDR(addr) \
        ((((unsigned long)(addr) + (64UL - 1UL)) & ~(64UL - 1UL)) - (unsigned long)(addr))
static __inline__ struct sk_buff *gem_alloc_skb(struct net_device *dev, int size,
						gfp_t gfp_flags)
{
	struct sk_buff *skb = alloc_skb(size + 64, gfp_flags);

	if (likely(skb)) {
		unsigned long offset = ALIGNED_RX_SKB_ADDR(skb->data);
		skb_reserve(skb, offset);
	}
	return skb;
}

static int gem_rx(struct gem *gp, int work_to_do)
{
	struct net_device *dev = gp->dev;
	int entry, drops, work_done = 0;
	u32 done;

	if (netif_msg_rx_status(gp))
		printk(KERN_DEBUG "%s: rx interrupt, done: %d, rx_new: %d\n",
			gp->dev->name, readl(gp->regs + RXDMA_DONE), gp->rx_new);

	entry = gp->rx_new;
	drops = 0;
	done = readl(gp->regs + RXDMA_DONE);
	for (;;) {
		struct gem_rxd *rxd = &gp->init_block->rxd[entry];
		struct sk_buff *skb;
		u64 status = le64_to_cpu(rxd->status_word);
		dma_addr_t dma_addr;
		int len;

		if ((status & RXDCTRL_OWN) != 0)
			break;

		if (work_done >= RX_RING_SIZE || work_done >= work_to_do)
			break;

		/* When writing back RX descriptor, GEM writes status
		 * then buffer address, possibly in separate transactions.
		 * If we don't wait for the chip to write both, we could
		 * post a new buffer to this descriptor then have GEM spam
		 * on the buffer address.  We sync on the RX completion
		 * register to prevent this from happening.
		 */
		if (entry == done) {
			done = readl(gp->regs + RXDMA_DONE);
			if (entry == done)
				break;
		}

		/* We can now account for the work we're about to do */
		work_done++;

		skb = gp->rx_skbs[entry];

		len = (status & RXDCTRL_BUFSZ) >> 16;
		if ((len < ETH_ZLEN) || (status & RXDCTRL_BAD)) {
			dev->stats.rx_errors++;
			if (len < ETH_ZLEN)
				dev->stats.rx_length_errors++;
			if (len & RXDCTRL_BAD)
				dev->stats.rx_crc_errors++;

			/* We'll just return it to GEM. */
		drop_it:
			dev->stats.rx_dropped++;
			goto next;
		}

		dma_addr = le64_to_cpu(rxd->buffer);
		if (len > RX_COPY_THRESHOLD) {
			struct sk_buff *new_skb;

			new_skb = gem_alloc_skb(dev, RX_BUF_ALLOC_SIZE(gp), GFP_ATOMIC);
			if (new_skb == NULL) {
				drops++;
				goto drop_it;
			}
			pci_unmap_page(gp->pdev, dma_addr,
				       RX_BUF_ALLOC_SIZE(gp),
				       PCI_DMA_FROMDEVICE);
			gp->rx_skbs[entry] = new_skb;
			skb_put(new_skb, (gp->rx_buf_sz + RX_OFFSET));
			rxd->buffer = cpu_to_le64(pci_map_page(gp->pdev,
							       virt_to_page(new_skb->data),
							       offset_in_page(new_skb->data),
							       RX_BUF_ALLOC_SIZE(gp),
							       PCI_DMA_FROMDEVICE));
			skb_reserve(new_skb, RX_OFFSET);

			/* Trim the original skb for the netif. */
			skb_trim(skb, len);
		} else {
			struct sk_buff *copy_skb = netdev_alloc_skb(dev, len + 2);

			if (copy_skb == NULL) {
				drops++;
				goto drop_it;
			}

			skb_reserve(copy_skb, 2);
			skb_put(copy_skb, len);
			pci_dma_sync_single_for_cpu(gp->pdev, dma_addr, len, PCI_DMA_FROMDEVICE);
			skb_copy_from_linear_data(skb, copy_skb->data, len);
			pci_dma_sync_single_for_device(gp->pdev, dma_addr, len, PCI_DMA_FROMDEVICE);

			/* We'll reuse the original ring buffer. */
			skb = copy_skb;
		}

		if (likely(dev->features & NETIF_F_RXCSUM)) {
			__sum16 csum;

			csum = (__force __sum16)htons((status & RXDCTRL_TCPCSUM) ^ 0xffff);
			skb->csum = csum_unfold(csum);
			skb->ip_summed = CHECKSUM_COMPLETE;
		}
		skb->protocol = eth_type_trans(skb, gp->dev);

		napi_gro_receive(&gp->napi, skb);

		dev->stats.rx_packets++;
		dev->stats.rx_bytes += len;

	next:
		entry = NEXT_RX(entry);
	}

	gem_post_rxds(gp, entry);

	gp->rx_new = entry;

	if (drops)
		netdev_info(gp->dev, "Memory squeeze, deferring packet\n");

	return work_done;
}

static int gem_poll(struct napi_struct *napi, int budget)
{
	struct gem *gp = container_of(napi, struct gem, napi);
	struct net_device *dev = gp->dev;
	int work_done;

	work_done = 0;
	do {
		/* Handle anomalies */
		if (unlikely(gp->status & GREG_STAT_ABNORMAL)) {
			struct netdev_queue *txq = netdev_get_tx_queue(dev, 0);
			int reset;

			/* We run the abnormal interrupt handling code with
			 * the Tx lock. It only resets the Rx portion of the
			 * chip, but we need to guard it against DMA being
			 * restarted by the link poll timer
			 */
			__netif_tx_lock(txq, smp_processor_id());
			reset = gem_abnormal_irq(dev, gp, gp->status);
			__netif_tx_unlock(txq);
			if (reset) {
				gem_schedule_reset(gp);
				napi_complete(napi);
				return work_done;
			}
		}

		/* Run TX completion thread */
		gem_tx(dev, gp, gp->status);

		/* Run RX thread. We don't use any locking here,
		 * code willing to do bad things - like cleaning the
		 * rx ring - must call napi_disable(), which
		 * schedule_timeout()'s if polling is already disabled.
		 */
		work_done += gem_rx(gp, budget - work_done);

		if (work_done >= budget)
			return work_done;

		gp->status = readl(gp->regs + GREG_STAT);
	} while (gp->status & GREG_STAT_NAPI);

	napi_complete_done(napi, work_done);
	gem_enable_ints(gp);

	return work_done;
}

static irqreturn_t gem_interrupt(int irq, void *dev_id)
{
	struct net_device *dev = dev_id;
	struct gem *gp = netdev_priv(dev);

	if (napi_schedule_prep(&gp->napi)) {
		u32 gem_status = readl(gp->regs + GREG_STAT);

		if (unlikely(gem_status == 0)) {
			napi_enable(&gp->napi);
			return IRQ_NONE;
		}
		if (netif_msg_intr(gp))
			printk(KERN_DEBUG "%s: gem_interrupt() gem_status: 0x%x\n",
			       gp->dev->name, gem_status);

		gp->status = gem_status;
		gem_disable_ints(gp);
		__napi_schedule(&gp->napi);
	}

	/* If polling was disabled at the time we received that
	 * interrupt, we may return IRQ_HANDLED here while we
	 * should return IRQ_NONE. No big deal...
	 */
	return IRQ_HANDLED;
}

#ifdef CONFIG_NET_POLL_CONTROLLER
static void gem_poll_controller(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);

	disable_irq(gp->pdev->irq);
	gem_interrupt(gp->pdev->irq, dev);
	enable_irq(gp->pdev->irq);
}
#endif

static void gem_tx_timeout(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);

	netdev_err(dev, "transmit timed out, resetting\n");

	netdev_err(dev, "TX_STATE[%08x:%08x:%08x]\n",
		   readl(gp->regs + TXDMA_CFG),
		   readl(gp->regs + MAC_TXSTAT),
		   readl(gp->regs + MAC_TXCFG));
	netdev_err(dev, "RX_STATE[%08x:%08x:%08x]\n",
		   readl(gp->regs + RXDMA_CFG),
		   readl(gp->regs + MAC_RXSTAT),
		   readl(gp->regs + MAC_RXCFG));

	gem_schedule_reset(gp);
}

static __inline__ int gem_intme(int entry)
{
	/* Algorithm: IRQ every 1/2 of descriptors. */
	if (!(entry & ((TX_RING_SIZE>>1)-1)))
		return 1;

	return 0;
}

static netdev_tx_t gem_start_xmit(struct sk_buff *skb,
				  struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);
	int entry;
	u64 ctrl;

	ctrl = 0;
	if (skb->ip_summed == CHECKSUM_PARTIAL) {
		const u64 csum_start_off = skb_checksum_start_offset(skb);
		const u64 csum_stuff_off = csum_start_off + skb->csum_offset;

		ctrl = (TXDCTRL_CENAB |
			(csum_start_off << 15) |
			(csum_stuff_off << 21));
	}

	if (unlikely(TX_BUFFS_AVAIL(gp) <= (skb_shinfo(skb)->nr_frags + 1))) {
		/* This is a hard error, log it. */
		if (!netif_queue_stopped(dev)) {
			netif_stop_queue(dev);
			netdev_err(dev, "BUG! Tx Ring full when queue awake!\n");
		}
		return NETDEV_TX_BUSY;
	}

	entry = gp->tx_new;
	gp->tx_skbs[entry] = skb;

	if (skb_shinfo(skb)->nr_frags == 0) {
		struct gem_txd *txd = &gp->init_block->txd[entry];
		dma_addr_t mapping;
		u32 len;

		len = skb->len;
		mapping = pci_map_page(gp->pdev,
				       virt_to_page(skb->data),
				       offset_in_page(skb->data),
				       len, PCI_DMA_TODEVICE);
		ctrl |= TXDCTRL_SOF | TXDCTRL_EOF | len;
		if (gem_intme(entry))
			ctrl |= TXDCTRL_INTME;
		txd->buffer = cpu_to_le64(mapping);
		dma_wmb();
		txd->control_word = cpu_to_le64(ctrl);
		entry = NEXT_TX(entry);
	} else {
		struct gem_txd *txd;
		u32 first_len;
		u64 intme;
		dma_addr_t first_mapping;
		int frag, first_entry = entry;

		intme = 0;
		if (gem_intme(entry))
			intme |= TXDCTRL_INTME;

		/* We must give this initial chunk to the device last.
		 * Otherwise we could race with the device.
		 */
		first_len = skb_headlen(skb);
		first_mapping = pci_map_page(gp->pdev, virt_to_page(skb->data),
					     offset_in_page(skb->data),
					     first_len, PCI_DMA_TODEVICE);
		entry = NEXT_TX(entry);

		for (frag = 0; frag < skb_shinfo(skb)->nr_frags; frag++) {
			const skb_frag_t *this_frag = &skb_shinfo(skb)->frags[frag];
			u32 len;
			dma_addr_t mapping;
			u64 this_ctrl;

			len = skb_frag_size(this_frag);
			mapping = skb_frag_dma_map(&gp->pdev->dev, this_frag,
						   0, len, DMA_TO_DEVICE);
			this_ctrl = ctrl;
			if (frag == skb_shinfo(skb)->nr_frags - 1)
				this_ctrl |= TXDCTRL_EOF;

			txd = &gp->init_block->txd[entry];
			txd->buffer = cpu_to_le64(mapping);
			dma_wmb();
			txd->control_word = cpu_to_le64(this_ctrl | len);

			if (gem_intme(entry))
				intme |= TXDCTRL_INTME;

			entry = NEXT_TX(entry);
		}
		txd = &gp->init_block->txd[first_entry];
		txd->buffer = cpu_to_le64(first_mapping);
		dma_wmb();
		txd->control_word =
			cpu_to_le64(ctrl | TXDCTRL_SOF | intme | first_len);
	}

	gp->tx_new = entry;
	if (unlikely(TX_BUFFS_AVAIL(gp) <= (MAX_SKB_FRAGS + 1))) {
		netif_stop_queue(dev);

		/* netif_stop_queue() must be done before checking
		 * checking tx index in TX_BUFFS_AVAIL() below, because
		 * in gem_tx(), we update tx_old before checking for
		 * netif_queue_stopped().
		 */
		smp_mb();
		if (TX_BUFFS_AVAIL(gp) > (MAX_SKB_FRAGS + 1))
			netif_wake_queue(dev);
	}
	if (netif_msg_tx_queued(gp))
		printk(KERN_DEBUG "%s: tx queued, slot %d, skblen %d\n",
		       dev->name, entry, skb->len);
	mb();
	writel(gp->tx_new, gp->regs + TXDMA_KICK);

	return NETDEV_TX_OK;
}

static void gem_pcs_reset(struct gem *gp)
{
	int limit;
	u32 val;

	/* Reset PCS unit. */
	val = readl(gp->regs + PCS_MIICTRL);
	val |= PCS_MIICTRL_RST;
	writel(val, gp->regs + PCS_MIICTRL);

	limit = 32;
	while (readl(gp->regs + PCS_MIICTRL) & PCS_MIICTRL_RST) {
		udelay(100);
		if (limit-- <= 0)
			break;
	}
	if (limit < 0)
		netdev_warn(gp->dev, "PCS reset bit would not clear\n");
}

static void gem_pcs_reinit_adv(struct gem *gp)
{
	u32 val;

	/* Make sure PCS is disabled while changing advertisement
	 * configuration.
	 */
	val = readl(gp->regs + PCS_CFG);
	val &= ~(PCS_CFG_ENABLE | PCS_CFG_TO);
	writel(val, gp->regs + PCS_CFG);

	/* Advertise all capabilities except asymmetric
	 * pause.
	 */
	val = readl(gp->regs + PCS_MIIADV);
	val |= (PCS_MIIADV_FD | PCS_MIIADV_HD |
		PCS_MIIADV_SP | PCS_MIIADV_AP);
	writel(val, gp->regs + PCS_MIIADV);

	/* Enable and restart auto-negotiation, disable wrapback/loopback,
	 * and re-enable PCS.
	 */
	val = readl(gp->regs + PCS_MIICTRL);
	val |= (PCS_MIICTRL_RAN | PCS_MIICTRL_ANE);
	val &= ~PCS_MIICTRL_WB;
	writel(val, gp->regs + PCS_MIICTRL);

	val = readl(gp->regs + PCS_CFG);
	val |= PCS_CFG_ENABLE;
	writel(val, gp->regs + PCS_CFG);

	/* Make sure serialink loopback is off.  The meaning
	 * of this bit is logically inverted based upon whether
	 * you are in Serialink or SERDES mode.
	 */
	val = readl(gp->regs + PCS_SCTRL);
	if (gp->phy_type == phy_serialink)
		val &= ~PCS_SCTRL_LOOP;
	else
		val |= PCS_SCTRL_LOOP;
	writel(val, gp->regs + PCS_SCTRL);
}

#define STOP_TRIES 32

static void gem_reset(struct gem *gp)
{
	int limit;
	u32 val;

	/* Make sure we won't get any more interrupts */
	writel(0xffffffff, gp->regs + GREG_IMASK);

	/* Reset the chip */
	writel(gp->swrst_base | GREG_SWRST_TXRST | GREG_SWRST_RXRST,
	       gp->regs + GREG_SWRST);

	limit = STOP_TRIES;

	do {
		udelay(20);
		val = readl(gp->regs + GREG_SWRST);
		if (limit-- <= 0)
			break;
	} while (val & (GREG_SWRST_TXRST | GREG_SWRST_RXRST));

	if (limit < 0)
		netdev_err(gp->dev, "SW reset is ghetto\n");

	if (gp->phy_type == phy_serialink || gp->phy_type == phy_serdes)
		gem_pcs_reinit_adv(gp);
}

static void gem_start_dma(struct gem *gp)
{
	u32 val;

	/* We are ready to rock, turn everything on. */
	val = readl(gp->regs + TXDMA_CFG);
	writel(val | TXDMA_CFG_ENABLE, gp->regs + TXDMA_CFG);
	val = readl(gp->regs + RXDMA_CFG);
	writel(val | RXDMA_CFG_ENABLE, gp->regs + RXDMA_CFG);
	val = readl(gp->regs + MAC_TXCFG);
	writel(val | MAC_TXCFG_ENAB, gp->regs + MAC_TXCFG);
	val = readl(gp->regs + MAC_RXCFG);
	writel(val | MAC_RXCFG_ENAB, gp->regs + MAC_RXCFG);

	(void) readl(gp->regs + MAC_RXCFG);
	udelay(100);

	gem_enable_ints(gp);

	writel(RX_RING_SIZE - 4, gp->regs + RXDMA_KICK);
}

/* DMA won't be actually stopped before about 4ms tho ...
 */
static void gem_stop_dma(struct gem *gp)
{
	u32 val;

	/* We are done rocking, turn everything off. */
	val = readl(gp->regs + TXDMA_CFG);
	writel(val & ~TXDMA_CFG_ENABLE, gp->regs + TXDMA_CFG);
	val = readl(gp->regs + RXDMA_CFG);
	writel(val & ~RXDMA_CFG_ENABLE, gp->regs + RXDMA_CFG);
	val = readl(gp->regs + MAC_TXCFG);
	writel(val & ~MAC_TXCFG_ENAB, gp->regs + MAC_TXCFG);
	val = readl(gp->regs + MAC_RXCFG);
	writel(val & ~MAC_RXCFG_ENAB, gp->regs + MAC_RXCFG);

	(void) readl(gp->regs + MAC_RXCFG);

	/* Need to wait a bit ... done by the caller */
}


// XXX dbl check what that function should do when called on PCS PHY
static void gem_begin_auto_negotiation(struct gem *gp,
				       const struct ethtool_link_ksettings *ep)
{
	u32 advertise, features;
	int autoneg;
	int speed;
	int duplex;
	u32 advertising;

	if (ep)
		ethtool_convert_link_mode_to_legacy_u32(
			&advertising, ep->link_modes.advertising);

	if (gp->phy_type != phy_mii_mdio0 &&
     	    gp->phy_type != phy_mii_mdio1)
     	    	goto non_mii;

	/* Setup advertise */
	if (found_mii_phy(gp))
		features = gp->phy_mii.def->features;
	else
		features = 0;

	advertise = features & ADVERTISE_MASK;
	if (gp->phy_mii.advertising != 0)
		advertise &= gp->phy_mii.advertising;

	autoneg = gp->want_autoneg;
	speed = gp->phy_mii.speed;
	duplex = gp->phy_mii.duplex;

	/* Setup link parameters */
	if (!ep)
		goto start_aneg;
	if (ep->base.autoneg == AUTONEG_ENABLE) {
		advertise = advertising;
		autoneg = 1;
	} else {
		autoneg = 0;
		speed = ep->base.speed;
		duplex = ep->base.duplex;
	}

start_aneg:
	/* Sanitize settings based on PHY capabilities */
	if ((features & SUPPORTED_Autoneg) == 0)
		autoneg = 0;
	if (speed == SPEED_1000 &&
	    !(features & (SUPPORTED_1000baseT_Half | SUPPORTED_1000baseT_Full)))
		speed = SPEED_100;
	if (speed == SPEED_100 &&
	    !(features & (SUPPORTED_100baseT_Half | SUPPORTED_100baseT_Full)))
		speed = SPEED_10;
	if (duplex == DUPLEX_FULL &&
	    !(features & (SUPPORTED_1000baseT_Full |
	    		  SUPPORTED_100baseT_Full |
	    		  SUPPORTED_10baseT_Full)))
	    	duplex = DUPLEX_HALF;
	if (speed == 0)
		speed = SPEED_10;

	/* If we are asleep, we don't try to actually setup the PHY, we
	 * just store the settings
	 */
	if (!netif_device_present(gp->dev)) {
		gp->phy_mii.autoneg = gp->want_autoneg = autoneg;
		gp->phy_mii.speed = speed;
		gp->phy_mii.duplex = duplex;
		return;
	}

	/* Configure PHY & start aneg */
	gp->want_autoneg = autoneg;
	if (autoneg) {
		if (found_mii_phy(gp))
			gp->phy_mii.def->ops->setup_aneg(&gp->phy_mii, advertise);
		gp->lstate = link_aneg;
	} else {
		if (found_mii_phy(gp))
			gp->phy_mii.def->ops->setup_forced(&gp->phy_mii, speed, duplex);
		gp->lstate = link_force_ok;
	}

non_mii:
	gp->timer_ticks = 0;
	mod_timer(&gp->link_timer, jiffies + ((12 * HZ) / 10));
}

/* A link-up condition has occurred, initialize and enable the
 * rest of the chip.
 */
static int gem_set_link_modes(struct gem *gp)
{
	struct netdev_queue *txq = netdev_get_tx_queue(gp->dev, 0);
	int full_duplex, speed, pause;
	u32 val;

	full_duplex = 0;
	speed = SPEED_10;
	pause = 0;

	if (found_mii_phy(gp)) {
	    	if (gp->phy_mii.def->ops->read_link(&gp->phy_mii))
	    		return 1;
		full_duplex = (gp->phy_mii.duplex == DUPLEX_FULL);
		speed = gp->phy_mii.speed;
		pause = gp->phy_mii.pause;
	} else if (gp->phy_type == phy_serialink ||
	    	   gp->phy_type == phy_serdes) {
		u32 pcs_lpa = readl(gp->regs + PCS_MIILP);

		if ((pcs_lpa & PCS_MIIADV_FD) || gp->phy_type == phy_serdes)
			full_duplex = 1;
		speed = SPEED_1000;
	}

	netif_info(gp, link, gp->dev, "Link is up at %d Mbps, %s-duplex\n",
		   speed, (full_duplex ? "full" : "half"));


	/* We take the tx queue lock to avoid collisions between
	 * this code, the tx path and the NAPI-driven error path
	 */
	__netif_tx_lock(txq, smp_processor_id());

	val = (MAC_TXCFG_EIPG0 | MAC_TXCFG_NGU);
	if (full_duplex) {
		val |= (MAC_TXCFG_ICS | MAC_TXCFG_ICOLL);
	} else {
		/* MAC_TXCFG_NBO must be zero. */
	}
	writel(val, gp->regs + MAC_TXCFG);

	val = (MAC_XIFCFG_OE | MAC_XIFCFG_LLED);
	if (!full_duplex &&
	    (gp->phy_type == phy_mii_mdio0 ||
	     gp->phy_type == phy_mii_mdio1)) {
		val |= MAC_XIFCFG_DISE;
	} else if (full_duplex) {
		val |= MAC_XIFCFG_FLED;
	}

	if (speed == SPEED_1000)
		val |= (MAC_XIFCFG_GMII);

	writel(val, gp->regs + MAC_XIFCFG);

	/* If gigabit and half-duplex, enable carrier extension
	 * mode.  Else, disable it.
	 */
	if (speed == SPEED_1000 && !full_duplex) {
		val = readl(gp->regs + MAC_TXCFG);
		writel(val | MAC_TXCFG_TCE, gp->regs + MAC_TXCFG);

		val = readl(gp->regs + MAC_RXCFG);
		writel(val | MAC_RXCFG_RCE, gp->regs + MAC_RXCFG);
	} else {
		val = readl(gp->regs + MAC_TXCFG);
		writel(val & ~MAC_TXCFG_TCE, gp->regs + MAC_TXCFG);

		val = readl(gp->regs + MAC_RXCFG);
		writel(val & ~MAC_RXCFG_RCE, gp->regs + MAC_RXCFG);
	}

	if (gp->phy_type == phy_serialink ||
	    gp->phy_type == phy_serdes) {
 		u32 pcs_lpa = readl(gp->regs + PCS_MIILP);

		if (pcs_lpa & (PCS_MIIADV_SP | PCS_MIIADV_AP))
			pause = 1;
	}

	if (!full_duplex)
		writel(512, gp->regs + MAC_STIME);
	else
		writel(64, gp->regs + MAC_STIME);
	val = readl(gp->regs + MAC_MCCFG);
	if (pause)
		val |= (MAC_MCCFG_SPE | MAC_MCCFG_RPE);
	else
		val &= ~(MAC_MCCFG_SPE | MAC_MCCFG_RPE);
	writel(val, gp->regs + MAC_MCCFG);

	gem_start_dma(gp);

	__netif_tx_unlock(txq);

	if (netif_msg_link(gp)) {
		if (pause) {
			netdev_info(gp->dev,
				    "Pause is enabled (rxfifo: %d off: %d on: %d)\n",
				    gp->rx_fifo_sz,
				    gp->rx_pause_off,
				    gp->rx_pause_on);
		} else {
			netdev_info(gp->dev, "Pause is disabled\n");
		}
	}

	return 0;
}

static int gem_mdio_link_not_up(struct gem *gp)
{
	switch (gp->lstate) {
	case link_force_ret:
		netif_info(gp, link, gp->dev,
			   "Autoneg failed again, keeping forced mode\n");
		gp->phy_mii.def->ops->setup_forced(&gp->phy_mii,
			gp->last_forced_speed, DUPLEX_HALF);
		gp->timer_ticks = 5;
		gp->lstate = link_force_ok;
		return 0;
	case link_aneg:
		/* We try forced modes after a failed aneg only on PHYs that don't
		 * have "magic_aneg" bit set, which means they internally do the
		 * while forced-mode thingy. On these, we just restart aneg
		 */
		if (gp->phy_mii.def->magic_aneg)
			return 1;
		netif_info(gp, link, gp->dev, "switching to forced 100bt\n");
		/* Try forced modes. */
		gp->phy_mii.def->ops->setup_forced(&gp->phy_mii, SPEED_100,
			DUPLEX_HALF);
		gp->timer_ticks = 5;
		gp->lstate = link_force_try;
		return 0;
	case link_force_try:
		/* Downgrade from 100 to 10 Mbps if necessary.
		 * If already at 10Mbps, warn user about the
		 * situation every 10 ticks.
		 */
		if (gp->phy_mii.speed == SPEED_100) {
			gp->phy_mii.def->ops->setup_forced(&gp->phy_mii, SPEED_10,
				DUPLEX_HALF);
			gp->timer_ticks = 5;
			netif_info(gp, link, gp->dev,
				   "switching to forced 10bt\n");
			return 0;
		} else
			return 1;
	default:
		return 0;
	}
}

static void gem_link_timer(struct timer_list *t)
{
	struct gem *gp = from_timer(gp, t, link_timer);
	struct net_device *dev = gp->dev;
	int restart_aneg = 0;

	/* There's no point doing anything if we're going to be reset */
	if (gp->reset_task_pending)
		return;

	if (gp->phy_type == phy_serialink ||
	    gp->phy_type == phy_serdes) {
		u32 val = readl(gp->regs + PCS_MIISTAT);

		if (!(val & PCS_MIISTAT_LS))
			val = readl(gp->regs + PCS_MIISTAT);

		if ((val & PCS_MIISTAT_LS) != 0) {
			if (gp->lstate == link_up)
				goto restart;

			gp->lstate = link_up;
			netif_carrier_on(dev);
			(void)gem_set_link_modes(gp);
		}
		goto restart;
	}
	if (found_mii_phy(gp) && gp->phy_mii.def->ops->poll_link(&gp->phy_mii)) {
		/* Ok, here we got a link. If we had it due to a forced
		 * fallback, and we were configured for autoneg, we do
		 * retry a short autoneg pass. If you know your hub is
		 * broken, use ethtool ;)
		 */
		if (gp->lstate == link_force_try && gp->want_autoneg) {
			gp->lstate = link_force_ret;
			gp->last_forced_speed = gp->phy_mii.speed;
			gp->timer_ticks = 5;
			if (netif_msg_link(gp))
				netdev_info(dev,
					    "Got link after fallback, retrying autoneg once...\n");
			gp->phy_mii.def->ops->setup_aneg(&gp->phy_mii, gp->phy_mii.advertising);
		} else if (gp->lstate != link_up) {
			gp->lstate = link_up;
			netif_carrier_on(dev);
			if (gem_set_link_modes(gp))
				restart_aneg = 1;
		}
	} else {
		/* If the link was previously up, we restart the
		 * whole process
		 */
		if (gp->lstate == link_up) {
			gp->lstate = link_down;
			netif_info(gp, link, dev, "Link down\n");
			netif_carrier_off(dev);
			gem_schedule_reset(gp);
			/* The reset task will restart the timer */
			return;
		} else if (++gp->timer_ticks > 10) {
			if (found_mii_phy(gp))
				restart_aneg = gem_mdio_link_not_up(gp);
			else
				restart_aneg = 1;
		}
	}
	if (restart_aneg) {
		gem_begin_auto_negotiation(gp, NULL);
		return;
	}
restart:
	mod_timer(&gp->link_timer, jiffies + ((12 * HZ) / 10));
}

static void gem_clean_rings(struct gem *gp)
{
	struct gem_init_block *gb = gp->init_block;
	struct sk_buff *skb;
	int i;
	dma_addr_t dma_addr;

	for (i = 0; i < RX_RING_SIZE; i++) {
		struct gem_rxd *rxd;

		rxd = &gb->rxd[i];
		if (gp->rx_skbs[i] != NULL) {
			skb = gp->rx_skbs[i];
			dma_addr = le64_to_cpu(rxd->buffer);
			pci_unmap_page(gp->pdev, dma_addr,
				       RX_BUF_ALLOC_SIZE(gp),
				       PCI_DMA_FROMDEVICE);
			dev_kfree_skb_any(skb);
			gp->rx_skbs[i] = NULL;
		}
		rxd->status_word = 0;
		dma_wmb();
		rxd->buffer = 0;
	}

	for (i = 0; i < TX_RING_SIZE; i++) {
		if (gp->tx_skbs[i] != NULL) {
			struct gem_txd *txd;
			int frag;

			skb = gp->tx_skbs[i];
			gp->tx_skbs[i] = NULL;

			for (frag = 0; frag <= skb_shinfo(skb)->nr_frags; frag++) {
				int ent = i & (TX_RING_SIZE - 1);

				txd = &gb->txd[ent];
				dma_addr = le64_to_cpu(txd->buffer);
				pci_unmap_page(gp->pdev, dma_addr,
					       le64_to_cpu(txd->control_word) &
					       TXDCTRL_BUFSZ, PCI_DMA_TODEVICE);

				if (frag != skb_shinfo(skb)->nr_frags)
					i++;
			}
			dev_kfree_skb_any(skb);
		}
	}
}

static void gem_init_rings(struct gem *gp)
{
	struct gem_init_block *gb = gp->init_block;
	struct net_device *dev = gp->dev;
	int i;
	dma_addr_t dma_addr;

	gp->rx_new = gp->rx_old = gp->tx_new = gp->tx_old = 0;

	gem_clean_rings(gp);

	gp->rx_buf_sz = max(dev->mtu + ETH_HLEN + VLAN_HLEN,
			    (unsigned)VLAN_ETH_FRAME_LEN);

	for (i = 0; i < RX_RING_SIZE; i++) {
		struct sk_buff *skb;
		struct gem_rxd *rxd = &gb->rxd[i];

		skb = gem_alloc_skb(dev, RX_BUF_ALLOC_SIZE(gp), GFP_KERNEL);
		if (!skb) {
			rxd->buffer = 0;
			rxd->status_word = 0;
			continue;
		}

		gp->rx_skbs[i] = skb;
		skb_put(skb, (gp->rx_buf_sz + RX_OFFSET));
		dma_addr = pci_map_page(gp->pdev,
					virt_to_page(skb->data),
					offset_in_page(skb->data),
					RX_BUF_ALLOC_SIZE(gp),
					PCI_DMA_FROMDEVICE);
		rxd->buffer = cpu_to_le64(dma_addr);
		dma_wmb();
		rxd->status_word = cpu_to_le64(RXDCTRL_FRESH(gp));
		skb_reserve(skb, RX_OFFSET);
	}

	for (i = 0; i < TX_RING_SIZE; i++) {
		struct gem_txd *txd = &gb->txd[i];

		txd->control_word = 0;
		dma_wmb();
		txd->buffer = 0;
	}
	wmb();
}

/* Init PHY interface and start link poll state machine */
static void gem_init_phy(struct gem *gp)
{
	u32 mifcfg;

	/* Revert MIF CFG setting done on stop_phy */
	mifcfg = readl(gp->regs + MIF_CFG);
	mifcfg &= ~MIF_CFG_BBMODE;
	writel(mifcfg, gp->regs + MIF_CFG);

	if (gp->pdev->vendor == PCI_VENDOR_ID_APPLE) {
		int i;

		/* Those delay sucks, the HW seem to love them though, I'll
		 * serisouly consider breaking some locks here to be able
		 * to schedule instead
		 */
		for (i = 0; i < 3; i++) {
#ifdef CONFIG_PPC_PMAC
			pmac_call_feature(PMAC_FTR_GMAC_PHY_RESET, gp->of_node, 0, 0);
			msleep(20);
#endif
			/* Some PHYs used by apple have problem getting back to us,
			 * we do an additional reset here
			 */
			sungem_phy_write(gp, MII_BMCR, BMCR_RESET);
			msleep(20);
			if (sungem_phy_read(gp, MII_BMCR) != 0xffff)
				break;
			if (i == 2)
				netdev_warn(gp->dev, "GMAC PHY not responding !\n");
		}
	}

	if (gp->pdev->vendor == PCI_VENDOR_ID_SUN &&
	    gp->pdev->device == PCI_DEVICE_ID_SUN_GEM) {
		u32 val;

		/* Init datapath mode register. */
		if (gp->phy_type == phy_mii_mdio0 ||
		    gp->phy_type == phy_mii_mdio1) {
			val = PCS_DMODE_MGM;
		} else if (gp->phy_type == phy_serialink) {
			val = PCS_DMODE_SM | PCS_DMODE_GMOE;
		} else {
			val = PCS_DMODE_ESM;
		}

		writel(val, gp->regs + PCS_DMODE);
	}

	if (gp->phy_type == phy_mii_mdio0 ||
	    gp->phy_type == phy_mii_mdio1) {
		/* Reset and detect MII PHY */
		sungem_phy_probe(&gp->phy_mii, gp->mii_phy_addr);

		/* Init PHY */
		if (gp->phy_mii.def && gp->phy_mii.def->ops->init)
			gp->phy_mii.def->ops->init(&gp->phy_mii);
	} else {
		gem_pcs_reset(gp);
		gem_pcs_reinit_adv(gp);
	}

	/* Default aneg parameters */
	gp->timer_ticks = 0;
	gp->lstate = link_down;
	netif_carrier_off(gp->dev);

	/* Print things out */
	if (gp->phy_type == phy_mii_mdio0 ||
	    gp->phy_type == phy_mii_mdio1)
		netdev_info(gp->dev, "Found %s PHY\n",
			    gp->phy_mii.def ? gp->phy_mii.def->name : "no");

	gem_begin_auto_negotiation(gp, NULL);
}

static void gem_init_dma(struct gem *gp)
{
	u64 desc_dma = (u64) gp->gblock_dvma;
	u32 val;

	val = (TXDMA_CFG_BASE | (0x7ff << 10) | TXDMA_CFG_PMODE);
	writel(val, gp->regs + TXDMA_CFG);

	writel(desc_dma >> 32, gp->regs + TXDMA_DBHI);
	writel(desc_dma & 0xffffffff, gp->regs + TXDMA_DBLOW);
	desc_dma += (INIT_BLOCK_TX_RING_SIZE * sizeof(struct gem_txd));

	writel(0, gp->regs + TXDMA_KICK);

	val = (RXDMA_CFG_BASE | (RX_OFFSET << 10) |
	       (ETH_HLEN << 13) | RXDMA_CFG_FTHRESH_128);
	writel(val, gp->regs + RXDMA_CFG);

	writel(desc_dma >> 32, gp->regs + RXDMA_DBHI);
	writel(desc_dma & 0xffffffff, gp->regs + RXDMA_DBLOW);

	writel(RX_RING_SIZE - 4, gp->regs + RXDMA_KICK);

	val  = (((gp->rx_pause_off / 64) << 0) & RXDMA_PTHRESH_OFF);
	val |= (((gp->rx_pause_on / 64) << 12) & RXDMA_PTHRESH_ON);
	writel(val, gp->regs + RXDMA_PTHRESH);

	if (readl(gp->regs + GREG_BIFCFG) & GREG_BIFCFG_M66EN)
		writel(((5 & RXDMA_BLANK_IPKTS) |
			((8 << 12) & RXDMA_BLANK_ITIME)),
		       gp->regs + RXDMA_BLANK);
	else
		writel(((5 & RXDMA_BLANK_IPKTS) |
			((4 << 12) & RXDMA_BLANK_ITIME)),
		       gp->regs + RXDMA_BLANK);
}

static u32 gem_setup_multicast(struct gem *gp)
{
	u32 rxcfg = 0;
	int i;

	if ((gp->dev->flags & IFF_ALLMULTI) ||
	    (netdev_mc_count(gp->dev) > 256)) {
	    	for (i=0; i<16; i++)
			writel(0xffff, gp->regs + MAC_HASH0 + (i << 2));
		rxcfg |= MAC_RXCFG_HFE;
	} else if (gp->dev->flags & IFF_PROMISC) {
		rxcfg |= MAC_RXCFG_PROM;
	} else {
		u16 hash_table[16];
		u32 crc;
		struct netdev_hw_addr *ha;
		int i;

		memset(hash_table, 0, sizeof(hash_table));
		netdev_for_each_mc_addr(ha, gp->dev) {
			crc = ether_crc_le(6, ha->addr);
			crc >>= 24;
			hash_table[crc >> 4] |= 1 << (15 - (crc & 0xf));
		}
	    	for (i=0; i<16; i++)
			writel(hash_table[i], gp->regs + MAC_HASH0 + (i << 2));
		rxcfg |= MAC_RXCFG_HFE;
	}

	return rxcfg;
}

static void gem_init_mac(struct gem *gp)
{
	unsigned char *e = &gp->dev->dev_addr[0];

	writel(0x1bf0, gp->regs + MAC_SNDPAUSE);

	writel(0x00, gp->regs + MAC_IPG0);
	writel(0x08, gp->regs + MAC_IPG1);
	writel(0x04, gp->regs + MAC_IPG2);
	writel(0x40, gp->regs + MAC_STIME);
	writel(0x40, gp->regs + MAC_MINFSZ);

	/* Ethernet payload + header + FCS + optional VLAN tag. */
	writel(0x20000000 | (gp->rx_buf_sz + 4), gp->regs + MAC_MAXFSZ);

	writel(0x07, gp->regs + MAC_PASIZE);
	writel(0x04, gp->regs + MAC_JAMSIZE);
	writel(0x10, gp->regs + MAC_ATTLIM);
	writel(0x8808, gp->regs + MAC_MCTYPE);

	writel((e[5] | (e[4] << 8)) & 0x3ff, gp->regs + MAC_RANDSEED);

	writel((e[4] << 8) | e[5], gp->regs + MAC_ADDR0);
	writel((e[2] << 8) | e[3], gp->regs + MAC_ADDR1);
	writel((e[0] << 8) | e[1], gp->regs + MAC_ADDR2);

	writel(0, gp->regs + MAC_ADDR3);
	writel(0, gp->regs + MAC_ADDR4);
	writel(0, gp->regs + MAC_ADDR5);

	writel(0x0001, gp->regs + MAC_ADDR6);
	writel(0xc200, gp->regs + MAC_ADDR7);
	writel(0x0180, gp->regs + MAC_ADDR8);

	writel(0, gp->regs + MAC_AFILT0);
	writel(0, gp->regs + MAC_AFILT1);
	writel(0, gp->regs + MAC_AFILT2);
	writel(0, gp->regs + MAC_AF21MSK);
	writel(0, gp->regs + MAC_AF0MSK);

	gp->mac_rx_cfg = gem_setup_multicast(gp);
#ifdef STRIP_FCS
	gp->mac_rx_cfg |= MAC_RXCFG_SFCS;
#endif
	writel(0, gp->regs + MAC_NCOLL);
	writel(0, gp->regs + MAC_FASUCC);
	writel(0, gp->regs + MAC_ECOLL);
	writel(0, gp->regs + MAC_LCOLL);
	writel(0, gp->regs + MAC_DTIMER);
	writel(0, gp->regs + MAC_PATMPS);
	writel(0, gp->regs + MAC_RFCTR);
	writel(0, gp->regs + MAC_LERR);
	writel(0, gp->regs + MAC_AERR);
	writel(0, gp->regs + MAC_FCSERR);
	writel(0, gp->regs + MAC_RXCVERR);

	/* Clear RX/TX/MAC/XIF config, we will set these up and enable
	 * them once a link is established.
	 */
	writel(0, gp->regs + MAC_TXCFG);
	writel(gp->mac_rx_cfg, gp->regs + MAC_RXCFG);
	writel(0, gp->regs + MAC_MCCFG);
	writel(0, gp->regs + MAC_XIFCFG);

	/* Setup MAC interrupts.  We want to get all of the interesting
	 * counter expiration events, but we do not want to hear about
	 * normal rx/tx as the DMA engine tells us that.
	 */
	writel(MAC_TXSTAT_XMIT, gp->regs + MAC_TXMASK);
	writel(MAC_RXSTAT_RCV, gp->regs + MAC_RXMASK);

	/* Don't enable even the PAUSE interrupts for now, we
	 * make no use of those events other than to record them.
	 */
	writel(0xffffffff, gp->regs + MAC_MCMASK);

	/* Don't enable GEM's WOL in normal operations
	 */
	if (gp->has_wol)
		writel(0, gp->regs + WOL_WAKECSR);
}

static void gem_init_pause_thresholds(struct gem *gp)
{
       	u32 cfg;

	/* Calculate pause thresholds.  Setting the OFF threshold to the
	 * full RX fifo size effectively disables PAUSE generation which
	 * is what we do for 10/100 only GEMs which have FIFOs too small
	 * to make real gains from PAUSE.
	 */
	if (gp->rx_fifo_sz <= (2 * 1024)) {
		gp->rx_pause_off = gp->rx_pause_on = gp->rx_fifo_sz;
	} else {
		int max_frame = (gp->rx_buf_sz + 4 + 64) & ~63;
		int off = (gp->rx_fifo_sz - (max_frame * 2));
		int on = off - max_frame;

		gp->rx_pause_off = off;
		gp->rx_pause_on = on;
	}


	/* Configure the chip "burst" DMA mode & enable some
	 * HW bug fixes on Apple version
	 */
       	cfg  = 0;
       	if (gp->pdev->vendor == PCI_VENDOR_ID_APPLE)
		cfg |= GREG_CFG_RONPAULBIT | GREG_CFG_ENBUG2FIX;
#if !defined(CONFIG_SPARC64) && !defined(CONFIG_ALPHA)
       	cfg |= GREG_CFG_IBURST;
#endif
       	cfg |= ((31 << 1) & GREG_CFG_TXDMALIM);
       	cfg |= ((31 << 6) & GREG_CFG_RXDMALIM);
       	writel(cfg, gp->regs + GREG_CFG);

	/* If Infinite Burst didn't stick, then use different
	 * thresholds (and Apple bug fixes don't exist)
	 */
	if (!(readl(gp->regs + GREG_CFG) & GREG_CFG_IBURST)) {
		cfg = ((2 << 1) & GREG_CFG_TXDMALIM);
		cfg |= ((8 << 6) & GREG_CFG_RXDMALIM);
		writel(cfg, gp->regs + GREG_CFG);
	}
}

static int gem_check_invariants(struct gem *gp)
{
	struct pci_dev *pdev = gp->pdev;
	u32 mif_cfg;

	/* On Apple's sungem, we can't rely on registers as the chip
	 * was been powered down by the firmware. The PHY is looked
	 * up later on.
	 */
	if (pdev->vendor == PCI_VENDOR_ID_APPLE) {
		gp->phy_type = phy_mii_mdio0;
		gp->tx_fifo_sz = readl(gp->regs + TXDMA_FSZ) * 64;
		gp->rx_fifo_sz = readl(gp->regs + RXDMA_FSZ) * 64;
		gp->swrst_base = 0;

		mif_cfg = readl(gp->regs + MIF_CFG);
		mif_cfg &= ~(MIF_CFG_PSELECT|MIF_CFG_POLL|MIF_CFG_BBMODE|MIF_CFG_MDI1);
		mif_cfg |= MIF_CFG_MDI0;
		writel(mif_cfg, gp->regs + MIF_CFG);
		writel(PCS_DMODE_MGM, gp->regs + PCS_DMODE);
		writel(MAC_XIFCFG_OE, gp->regs + MAC_XIFCFG);

		/* We hard-code the PHY address so we can properly bring it out of
		 * reset later on, we can't really probe it at this point, though
		 * that isn't an issue.
		 */
		if (gp->pdev->device == PCI_DEVICE_ID_APPLE_K2_GMAC)
			gp->mii_phy_addr = 1;
		else
			gp->mii_phy_addr = 0;

		return 0;
	}

	mif_cfg = readl(gp->regs + MIF_CFG);

	if (pdev->vendor == PCI_VENDOR_ID_SUN &&
	    pdev->device == PCI_DEVICE_ID_SUN_RIO_GEM) {
		/* One of the MII PHYs _must_ be present
		 * as this chip has no gigabit PHY.
		 */
		if ((mif_cfg & (MIF_CFG_MDI0 | MIF_CFG_MDI1)) == 0) {
			pr_err("RIO GEM lacks MII phy, mif_cfg[%08x]\n",
			       mif_cfg);
			return -1;
		}
	}

	/* Determine initial PHY interface type guess.  MDIO1 is the
	 * external PHY and thus takes precedence over MDIO0.
	 */

	if (mif_cfg & MIF_CFG_MDI1) {
		gp->phy_type = phy_mii_mdio1;
		mif_cfg |= MIF_CFG_PSELECT;
		writel(mif_cfg, gp->regs + MIF_CFG);
	} else if (mif_cfg & MIF_CFG_MDI0) {
		gp->phy_type = phy_mii_mdio0;
		mif_cfg &= ~MIF_CFG_PSELECT;
		writel(mif_cfg, gp->regs + MIF_CFG);
	} else {
#ifdef CONFIG_SPARC
		const char *p;

		p = of_get_property(gp->of_node, "shared-pins", NULL);
		if (p && !strcmp(p, "serdes"))
			gp->phy_type = phy_serdes;
		else
#endif
			gp->phy_type = phy_serialink;
	}
	if (gp->phy_type == phy_mii_mdio1 ||
	    gp->phy_type == phy_mii_mdio0) {
		int i;

		for (i = 0; i < 32; i++) {
			gp->mii_phy_addr = i;
			if (sungem_phy_read(gp, MII_BMCR) != 0xffff)
				break;
		}
		if (i == 32) {
			if (pdev->device != PCI_DEVICE_ID_SUN_GEM) {
				pr_err("RIO MII phy will not respond\n");
				return -1;
			}
			gp->phy_type = phy_serdes;
		}
	}

	/* Fetch the FIFO configurations now too. */
	gp->tx_fifo_sz = readl(gp->regs + TXDMA_FSZ) * 64;
	gp->rx_fifo_sz = readl(gp->regs + RXDMA_FSZ) * 64;

	if (pdev->vendor == PCI_VENDOR_ID_SUN) {
		if (pdev->device == PCI_DEVICE_ID_SUN_GEM) {
			if (gp->tx_fifo_sz != (9 * 1024) ||
			    gp->rx_fifo_sz != (20 * 1024)) {
				pr_err("GEM has bogus fifo sizes tx(%d) rx(%d)\n",
				       gp->tx_fifo_sz, gp->rx_fifo_sz);
				return -1;
			}
			gp->swrst_base = 0;
		} else {
			if (gp->tx_fifo_sz != (2 * 1024) ||
			    gp->rx_fifo_sz != (2 * 1024)) {
				pr_err("RIO GEM has bogus fifo sizes tx(%d) rx(%d)\n",
				       gp->tx_fifo_sz, gp->rx_fifo_sz);
				return -1;
			}
			gp->swrst_base = (64 / 4) << GREG_SWRST_CACHE_SHIFT;
		}
	}

	return 0;
}

static void gem_reinit_chip(struct gem *gp)
{
	/* Reset the chip */
	gem_reset(gp);

	/* Make sure ints are disabled */
	gem_disable_ints(gp);

	/* Allocate & setup ring buffers */
	gem_init_rings(gp);

	/* Configure pause thresholds */
	gem_init_pause_thresholds(gp);

	/* Init DMA & MAC engines */
	gem_init_dma(gp);
	gem_init_mac(gp);
}


static void gem_stop_phy(struct gem *gp, int wol)
{
	u32 mifcfg;

	/* Let the chip settle down a bit, it seems that helps
	 * for sleep mode on some models
	 */
	msleep(10);

	/* Make sure we aren't polling PHY status change. We
	 * don't currently use that feature though
	 */
	mifcfg = readl(gp->regs + MIF_CFG);
	mifcfg &= ~MIF_CFG_POLL;
	writel(mifcfg, gp->regs + MIF_CFG);

	if (wol && gp->has_wol) {
		unsigned char *e = &gp->dev->dev_addr[0];
		u32 csr;

		/* Setup wake-on-lan for MAGIC packet */
		writel(MAC_RXCFG_HFE | MAC_RXCFG_SFCS | MAC_RXCFG_ENAB,
		       gp->regs + MAC_RXCFG);
		writel((e[4] << 8) | e[5], gp->regs + WOL_MATCH0);
		writel((e[2] << 8) | e[3], gp->regs + WOL_MATCH1);
		writel((e[0] << 8) | e[1], gp->regs + WOL_MATCH2);

		writel(WOL_MCOUNT_N | WOL_MCOUNT_M, gp->regs + WOL_MCOUNT);
		csr = WOL_WAKECSR_ENABLE;
		if ((readl(gp->regs + MAC_XIFCFG) & MAC_XIFCFG_GMII) == 0)
			csr |= WOL_WAKECSR_MII;
		writel(csr, gp->regs + WOL_WAKECSR);
	} else {
		writel(0, gp->regs + MAC_RXCFG);
		(void)readl(gp->regs + MAC_RXCFG);
		/* Machine sleep will die in strange ways if we
		 * dont wait a bit here, looks like the chip takes
		 * some time to really shut down
		 */
		msleep(10);
	}

	writel(0, gp->regs + MAC_TXCFG);
	writel(0, gp->regs + MAC_XIFCFG);
	writel(0, gp->regs + TXDMA_CFG);
	writel(0, gp->regs + RXDMA_CFG);

	if (!wol) {
		gem_reset(gp);
		writel(MAC_TXRST_CMD, gp->regs + MAC_TXRST);
		writel(MAC_RXRST_CMD, gp->regs + MAC_RXRST);

		if (found_mii_phy(gp) && gp->phy_mii.def->ops->suspend)
			gp->phy_mii.def->ops->suspend(&gp->phy_mii);

		/* According to Apple, we must set the MDIO pins to this begnign
		 * state or we may 1) eat more current, 2) damage some PHYs
		 */
		writel(mifcfg | MIF_CFG_BBMODE, gp->regs + MIF_CFG);
		writel(0, gp->regs + MIF_BBCLK);
		writel(0, gp->regs + MIF_BBDATA);
		writel(0, gp->regs + MIF_BBOENAB);
		writel(MAC_XIFCFG_GMII | MAC_XIFCFG_LBCK, gp->regs + MAC_XIFCFG);
		(void) readl(gp->regs + MAC_XIFCFG);
	}
}

static int gem_do_start(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);
	int rc;

	/* Enable the cell */
	gem_get_cell(gp);

	/* Make sure PCI access and bus master are enabled */
	rc = pci_enable_device(gp->pdev);
	if (rc) {
		netdev_err(dev, "Failed to enable chip on PCI bus !\n");

		/* Put cell and forget it for now, it will be considered as
		 * still asleep, a new sleep cycle may bring it back
		 */
		gem_put_cell(gp);
		return -ENXIO;
	}
	pci_set_master(gp->pdev);

	/* Init & setup chip hardware */
	gem_reinit_chip(gp);

	/* An interrupt might come in handy */
	rc = request_irq(gp->pdev->irq, gem_interrupt,
			 IRQF_SHARED, dev->name, (void *)dev);
	if (rc) {
		netdev_err(dev, "failed to request irq !\n");

		gem_reset(gp);
		gem_clean_rings(gp);
		gem_put_cell(gp);
		return rc;
	}

	/* Mark us as attached again if we come from resume(), this has
	 * no effect if we weren't detached and needs to be done now.
	 */
	netif_device_attach(dev);

	/* Restart NAPI & queues */
	gem_netif_start(gp);

	/* Detect & init PHY, start autoneg etc... this will
	 * eventually result in starting DMA operations when
	 * the link is up
	 */
	gem_init_phy(gp);

	return 0;
}

static void gem_do_stop(struct net_device *dev, int wol)
{
	struct gem *gp = netdev_priv(dev);

	/* Stop NAPI and stop tx queue */
	gem_netif_stop(gp);

	/* Make sure ints are disabled. We don't care about
	 * synchronizing as NAPI is disabled, thus a stray
	 * interrupt will do nothing bad (our irq handler
	 * just schedules NAPI)
	 */
	gem_disable_ints(gp);

	/* Stop the link timer */
	del_timer_sync(&gp->link_timer);

	/* We cannot cancel the reset task while holding the
	 * rtnl lock, we'd get an A->B / B->A deadlock stituation
	 * if we did. This is not an issue however as the reset
	 * task is synchronized vs. us (rtnl_lock) and will do
	 * nothing if the device is down or suspended. We do
	 * still clear reset_task_pending to avoid a spurrious
	 * reset later on in case we do resume before it gets
	 * scheduled.
	 */
	gp->reset_task_pending = 0;

	/* If we are going to sleep with WOL */
	gem_stop_dma(gp);
	msleep(10);
	if (!wol)
		gem_reset(gp);
	msleep(10);

	/* Get rid of rings */
	gem_clean_rings(gp);

	/* No irq needed anymore */
	free_irq(gp->pdev->irq, (void *) dev);

	/* Shut the PHY down eventually and setup WOL */
	gem_stop_phy(gp, wol);

	/* Make sure bus master is disabled */
	pci_disable_device(gp->pdev);

	/* Cell not needed neither if no WOL */
	if (!wol)
		gem_put_cell(gp);
}

static void gem_reset_task(struct work_struct *work)
{
	struct gem *gp = container_of(work, struct gem, reset_task);

	/* Lock out the network stack (essentially shield ourselves
	 * against a racing open, close, control call, or suspend
	 */
	rtnl_lock();

	/* Skip the reset task if suspended or closed, or if it's
	 * been cancelled by gem_do_stop (see comment there)
	 */
	if (!netif_device_present(gp->dev) ||
	    !netif_running(gp->dev) ||
	    !gp->reset_task_pending) {
		rtnl_unlock();
		return;
	}

	/* Stop the link timer */
	del_timer_sync(&gp->link_timer);

	/* Stop NAPI and tx */
	gem_netif_stop(gp);

	/* Reset the chip & rings */
	gem_reinit_chip(gp);
	if (gp->lstate == link_up)
		gem_set_link_modes(gp);

	/* Restart NAPI and Tx */
	gem_netif_start(gp);

	/* We are back ! */
	gp->reset_task_pending = 0;

	/* If the link is not up, restart autoneg, else restart the
	 * polling timer
	 */
	if (gp->lstate != link_up)
		gem_begin_auto_negotiation(gp, NULL);
	else
		mod_timer(&gp->link_timer, jiffies + ((12 * HZ) / 10));

	rtnl_unlock();
}

static int gem_open(struct net_device *dev)
{
	/* We allow open while suspended, we just do nothing,
	 * the chip will be initialized in resume()
	 */
	if (netif_device_present(dev))
		return gem_do_start(dev);
	return 0;
}

static int gem_close(struct net_device *dev)
{
	if (netif_device_present(dev))
		gem_do_stop(dev, 0);

	return 0;
}

#ifdef CONFIG_PM
static int gem_suspend(struct pci_dev *pdev, pm_message_t state)
{
	struct net_device *dev = pci_get_drvdata(pdev);
	struct gem *gp = netdev_priv(dev);

	/* Lock the network stack first to avoid racing with open/close,
	 * reset task and setting calls
	 */
	rtnl_lock();

	/* Not running, mark ourselves non-present, no need for
	 * a lock here
	 */
	if (!netif_running(dev)) {
		netif_device_detach(dev);
		rtnl_unlock();
		return 0;
	}
	netdev_info(dev, "suspending, WakeOnLan %s\n",
		    (gp->wake_on_lan && netif_running(dev)) ?
		    "enabled" : "disabled");

	/* Tell the network stack we're gone. gem_do_stop() below will
	 * synchronize with TX, stop NAPI etc...
	 */
	netif_device_detach(dev);

	/* Switch off chip, remember WOL setting */
	gp->asleep_wol = !!gp->wake_on_lan;
	gem_do_stop(dev, gp->asleep_wol);

	/* Unlock the network stack */
	rtnl_unlock();

	return 0;
}

static int gem_resume(struct pci_dev *pdev)
{
	struct net_device *dev = pci_get_drvdata(pdev);
	struct gem *gp = netdev_priv(dev);

	/* See locking comment in gem_suspend */
	rtnl_lock();

	/* Not running, mark ourselves present, no need for
	 * a lock here
	 */
	if (!netif_running(dev)) {
		netif_device_attach(dev);
		rtnl_unlock();
		return 0;
	}

	/* Restart chip. If that fails there isn't much we can do, we
	 * leave things stopped.
	 */
	gem_do_start(dev);

	/* If we had WOL enabled, the cell clock was never turned off during
	 * sleep, so we end up beeing unbalanced. Fix that here
	 */
	if (gp->asleep_wol)
		gem_put_cell(gp);

	/* Unlock the network stack */
	rtnl_unlock();

	return 0;
}
#endif /* CONFIG_PM */

static struct net_device_stats *gem_get_stats(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);

	/* I have seen this being called while the PM was in progress,
	 * so we shield against this. Let's also not poke at registers
	 * while the reset task is going on.
	 *
	 * TODO: Move stats collection elsewhere (link timer ?) and
	 * make this a nop to avoid all those synchro issues
	 */
	if (!netif_device_present(dev) || !netif_running(dev))
		goto bail;

	/* Better safe than sorry... */
	if (WARN_ON(!gp->cell_enabled))
		goto bail;

	dev->stats.rx_crc_errors += readl(gp->regs + MAC_FCSERR);
	writel(0, gp->regs + MAC_FCSERR);

	dev->stats.rx_frame_errors += readl(gp->regs + MAC_AERR);
	writel(0, gp->regs + MAC_AERR);

	dev->stats.rx_length_errors += readl(gp->regs + MAC_LERR);
	writel(0, gp->regs + MAC_LERR);

	dev->stats.tx_aborted_errors += readl(gp->regs + MAC_ECOLL);
	dev->stats.collisions +=
		(readl(gp->regs + MAC_ECOLL) + readl(gp->regs + MAC_LCOLL));
	writel(0, gp->regs + MAC_ECOLL);
	writel(0, gp->regs + MAC_LCOLL);
 bail:
	return &dev->stats;
}

static int gem_set_mac_address(struct net_device *dev, void *addr)
{
	struct sockaddr *macaddr = (struct sockaddr *) addr;
	struct gem *gp = netdev_priv(dev);
	unsigned char *e = &dev->dev_addr[0];

	if (!is_valid_ether_addr(macaddr->sa_data))
		return -EADDRNOTAVAIL;

	memcpy(dev->dev_addr, macaddr->sa_data, dev->addr_len);

	/* We'll just catch it later when the device is up'd or resumed */
	if (!netif_running(dev) || !netif_device_present(dev))
		return 0;

	/* Better safe than sorry... */
	if (WARN_ON(!gp->cell_enabled))
		return 0;

	writel((e[4] << 8) | e[5], gp->regs + MAC_ADDR0);
	writel((e[2] << 8) | e[3], gp->regs + MAC_ADDR1);
	writel((e[0] << 8) | e[1], gp->regs + MAC_ADDR2);

	return 0;
}

static void gem_set_multicast(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);
	u32 rxcfg, rxcfg_new;
	int limit = 10000;

	if (!netif_running(dev) || !netif_device_present(dev))
		return;

	/* Better safe than sorry... */
	if (gp->reset_task_pending || WARN_ON(!gp->cell_enabled))
		return;

	rxcfg = readl(gp->regs + MAC_RXCFG);
	rxcfg_new = gem_setup_multicast(gp);
#ifdef STRIP_FCS
	rxcfg_new |= MAC_RXCFG_SFCS;
#endif
	gp->mac_rx_cfg = rxcfg_new;

	writel(rxcfg & ~MAC_RXCFG_ENAB, gp->regs + MAC_RXCFG);
	while (readl(gp->regs + MAC_RXCFG) & MAC_RXCFG_ENAB) {
		if (!limit--)
			break;
		udelay(10);
	}

	rxcfg &= ~(MAC_RXCFG_PROM | MAC_RXCFG_HFE);
	rxcfg |= rxcfg_new;

	writel(rxcfg, gp->regs + MAC_RXCFG);
}

/* Jumbo-grams don't seem to work :-( */
#define GEM_MIN_MTU	ETH_MIN_MTU
#if 1
#define GEM_MAX_MTU	ETH_DATA_LEN
#else
#define GEM_MAX_MTU	9000
#endif

static int gem_change_mtu(struct net_device *dev, int new_mtu)
{
	struct gem *gp = netdev_priv(dev);

	dev->mtu = new_mtu;

	/* We'll just catch it later when the device is up'd or resumed */
	if (!netif_running(dev) || !netif_device_present(dev))
		return 0;

	/* Better safe than sorry... */
	if (WARN_ON(!gp->cell_enabled))
		return 0;

	gem_netif_stop(gp);
	gem_reinit_chip(gp);
	if (gp->lstate == link_up)
		gem_set_link_modes(gp);
	gem_netif_start(gp);

	return 0;
}

static void gem_get_drvinfo(struct net_device *dev, struct ethtool_drvinfo *info)
{
	struct gem *gp = netdev_priv(dev);

	strlcpy(info->driver, DRV_NAME, sizeof(info->driver));
	strlcpy(info->version, DRV_VERSION, sizeof(info->version));
	strlcpy(info->bus_info, pci_name(gp->pdev), sizeof(info->bus_info));
}

static int gem_get_link_ksettings(struct net_device *dev,
				  struct ethtool_link_ksettings *cmd)
{
	struct gem *gp = netdev_priv(dev);
	u32 supported, advertising;

	if (gp->phy_type == phy_mii_mdio0 ||
	    gp->phy_type == phy_mii_mdio1) {
		if (gp->phy_mii.def)
			supported = gp->phy_mii.def->features;
		else
			supported = (SUPPORTED_10baseT_Half |
					  SUPPORTED_10baseT_Full);

		/* XXX hardcoded stuff for now */
		cmd->base.port = PORT_MII;
		cmd->base.phy_address = 0; /* XXX fixed PHYAD */

		/* Return current PHY settings */
		cmd->base.autoneg = gp->want_autoneg;
		cmd->base.speed = gp->phy_mii.speed;
		cmd->base.duplex = gp->phy_mii.duplex;
		advertising = gp->phy_mii.advertising;

		/* If we started with a forced mode, we don't have a default
		 * advertise set, we need to return something sensible so
		 * userland can re-enable autoneg properly.
		 */
		if (advertising == 0)
			advertising = supported;
	} else { // XXX PCS ?
		supported =
			(SUPPORTED_10baseT_Half | SUPPORTED_10baseT_Full |
			 SUPPORTED_100baseT_Half | SUPPORTED_100baseT_Full |
			 SUPPORTED_Autoneg);
		advertising = supported;
		cmd->base.speed = 0;
		cmd->base.duplex = 0;
		cmd->base.port = 0;
		cmd->base.phy_address = 0;
		cmd->base.autoneg = 0;

		/* serdes means usually a Fibre connector, with most fixed */
		if (gp->phy_type == phy_serdes) {
			cmd->base.port = PORT_FIBRE;
			supported = (SUPPORTED_1000baseT_Half |
				SUPPORTED_1000baseT_Full |
				SUPPORTED_FIBRE | SUPPORTED_Autoneg |
				SUPPORTED_Pause | SUPPORTED_Asym_Pause);
			advertising = supported;
			if (gp->lstate == link_up)
				cmd->base.speed = SPEED_1000;
			cmd->base.duplex = DUPLEX_FULL;
			cmd->base.autoneg = 1;
		}
	}

	ethtool_convert_legacy_u32_to_link_mode(cmd->link_modes.supported,
						supported);
	ethtool_convert_legacy_u32_to_link_mode(cmd->link_modes.advertising,
						advertising);

	return 0;
}

static int gem_set_link_ksettings(struct net_device *dev,
				  const struct ethtool_link_ksettings *cmd)
{
	struct gem *gp = netdev_priv(dev);
	u32 speed = cmd->base.speed;
	u32 advertising;

	ethtool_convert_link_mode_to_legacy_u32(&advertising,
						cmd->link_modes.advertising);

	/* Verify the settings we care about. */
	if (cmd->base.autoneg != AUTONEG_ENABLE &&
	    cmd->base.autoneg != AUTONEG_DISABLE)
		return -EINVAL;

	if (cmd->base.autoneg == AUTONEG_ENABLE &&
	    advertising == 0)
		return -EINVAL;

	if (cmd->base.autoneg == AUTONEG_DISABLE &&
	    ((speed != SPEED_1000 &&
	      speed != SPEED_100 &&
	      speed != SPEED_10) ||
	     (cmd->base.duplex != DUPLEX_HALF &&
	      cmd->base.duplex != DUPLEX_FULL)))
		return -EINVAL;

	/* Apply settings and restart link process. */
	if (netif_device_present(gp->dev)) {
		del_timer_sync(&gp->link_timer);
		gem_begin_auto_negotiation(gp, cmd);
	}

	return 0;
}

static int gem_nway_reset(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);

	if (!gp->want_autoneg)
		return -EINVAL;

	/* Restart link process  */
	if (netif_device_present(gp->dev)) {
		del_timer_sync(&gp->link_timer);
		gem_begin_auto_negotiation(gp, NULL);
	}

	return 0;
}

static u32 gem_get_msglevel(struct net_device *dev)
{
	struct gem *gp = netdev_priv(dev);
	return gp->msg_enable;
}

static void gem_set_msglevel(struct net_device *dev, u32 value)
{
	struct gem *gp = netdev_priv(dev);
	gp->msg_enable = value;
}


/* Add more when I understand how to program the chip */
/* like WAKE_UCAST | WAKE_MCAST | WAKE_BCAST */

#define WOL_SUPPORTED_MASK	(WAKE_MAGIC)

static void gem_get_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
{
	struct gem *gp = netdev_priv(dev);

	/* Add more when I understand how to program the chip */
	if (gp->has_wol) {
		wol->supported = WOL_SUPPORTED_MASK;
		wol->wolopts = gp->wake_on_lan;
	} else {
		wol->supported = 0;
		wol->wolopts = 0;
	}
}

static int gem_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
{
	struct gem *gp = netdev_priv(dev);

	if (!gp->has_wol)
		return -EOPNOTSUPP;
	gp->wake_on_lan = wol->wolopts & WOL_SUPPORTED_MASK;
	return 0;
}

static const struct ethtool_ops gem_ethtool_ops = {
	.get_drvinfo		= gem_get_drvinfo,
	.get_link		= ethtool_op_get_link,
	.nway_reset		= gem_nway_reset,
	.get_msglevel		= gem_get_msglevel,
	.set_msglevel		= gem_set_msglevel,
	.get_wol		= gem_get_wol,
	.set_wol		= gem_set_wol,
	.get_link_ksettings	= gem_get_link_ksettings,
	.set_link_ksettings	= gem_set_link_ksettings,
};

static int gem_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
{
	struct gem *gp = netdev_priv(dev);
	struct mii_ioctl_data *data = if_mii(ifr);
	int rc = -EOPNOTSUPP;

	/* For SIOCGMIIREG and SIOCSMIIREG the core checks for us that
	 * netif_device_present() is true and holds rtnl_lock for us
	 * so we have nothing to worry about
	 */

	switch (cmd) {
	case SIOCGMIIPHY:		/* Get address of MII PHY in use. */
		data->phy_id = gp->mii_phy_addr;
		/* Fallthrough... */

	case SIOCGMIIREG:		/* Read MII PHY register. */
		data->val_out = __sungem_phy_read(gp, data->phy_id & 0x1f,
					   data->reg_num & 0x1f);
		rc = 0;
		break;

	case SIOCSMIIREG:		/* Write MII PHY register. */
		__sungem_phy_write(gp, data->phy_id & 0x1f, data->reg_num & 0x1f,
			    data->val_in);
		rc = 0;
		break;
	}
	return rc;
}

#if (!defined(CONFIG_SPARC) && !defined(CONFIG_PPC_PMAC))
/* Fetch MAC address from vital product data of PCI ROM. */
static int find_eth_addr_in_vpd(void __iomem *rom_base, int len, unsigned char *dev_addr)
{
	int this_offset;

	for (this_offset = 0x20; this_offset < len; this_offset++) {
		void __iomem *p = rom_base + this_offset;
		int i;

		if (readb(p + 0) != 0x90 ||
		    readb(p + 1) != 0x00 ||
		    readb(p + 2) != 0x09 ||
		    readb(p + 3) != 0x4e ||
		    readb(p + 4) != 0x41 ||
		    readb(p + 5) != 0x06)
			continue;

		this_offset += 6;
		p += 6;

		for (i = 0; i < 6; i++)
			dev_addr[i] = readb(p + i);
		return 1;
	}
	return 0;
}

static void get_gem_mac_nonobp(struct pci_dev *pdev, unsigned char *dev_addr)
{
	size_t size;
	void __iomem *p = pci_map_rom(pdev, &size);

	if (p) {
		int found;

		found = readb(p) == 0x55 &&
			readb(p + 1) == 0xaa &&
			find_eth_addr_in_vpd(p, (64 * 1024), dev_addr);
		pci_unmap_rom(pdev, p);
		if (found)
			return;
	}

	/* Sun MAC prefix then 3 random bytes. */
	dev_addr[0] = 0x08;
	dev_addr[1] = 0x00;
	dev_addr[2] = 0x20;
	get_random_bytes(dev_addr + 3, 3);
}
#endif /* not Sparc and not PPC */

static int gem_get_device_address(struct gem *gp)
{
#if defined(CONFIG_SPARC) || defined(CONFIG_PPC_PMAC)
	struct net_device *dev = gp->dev;
	const unsigned char *addr;

	addr = of_get_property(gp->of_node, "local-mac-address", NULL);
	if (addr == NULL) {
#ifdef CONFIG_SPARC
		addr = idprom->id_ethaddr;
#else
		printk("\n");
		pr_err("%s: can't get mac-address\n", dev->name);
		return -1;
#endif
	}
	memcpy(dev->dev_addr, addr, ETH_ALEN);
#else
	get_gem_mac_nonobp(gp->pdev, gp->dev->dev_addr);
#endif
	return 0;
}

static void gem_remove_one(struct pci_dev *pdev)
{
	struct net_device *dev = pci_get_drvdata(pdev);

	if (dev) {
		struct gem *gp = netdev_priv(dev);

		unregister_netdev(dev);

		/* Ensure reset task is truly gone */
		cancel_work_sync(&gp->reset_task);

		/* Free resources */
		pci_free_consistent(pdev,
				    sizeof(struct gem_init_block),
				    gp->init_block,
				    gp->gblock_dvma);
		iounmap(gp->regs);
		pci_release_regions(pdev);
		free_netdev(dev);
	}
}

static const struct net_device_ops gem_netdev_ops = {
	.ndo_open		= gem_open,
	.ndo_stop		= gem_close,
	.ndo_start_xmit		= gem_start_xmit,
	.ndo_get_stats		= gem_get_stats,
	.ndo_set_rx_mode	= gem_set_multicast,
	.ndo_do_ioctl		= gem_ioctl,
	.ndo_tx_timeout		= gem_tx_timeout,
	.ndo_change_mtu		= gem_change_mtu,
	.ndo_validate_addr	= eth_validate_addr,
	.ndo_set_mac_address    = gem_set_mac_address,
#ifdef CONFIG_NET_POLL_CONTROLLER
	.ndo_poll_controller    = gem_poll_controller,
#endif
};

static int gem_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
{
	unsigned long gemreg_base, gemreg_len;
	struct net_device *dev;
	struct gem *gp;
	int err, pci_using_dac;

	printk_once(KERN_INFO "%s", version);

	/* Apple gmac note: during probe, the chip is powered up by
	 * the arch code to allow the code below to work (and to let
	 * the chip be probed on the config space. It won't stay powered
	 * up until the interface is brought up however, so we can't rely
	 * on register configuration done at this point.
	 */
	err = pci_enable_device(pdev);
	if (err) {
		pr_err("Cannot enable MMIO operation, aborting\n");
		return err;
	}
	pci_set_master(pdev);

	/* Configure DMA attributes. */

	/* All of the GEM documentation states that 64-bit DMA addressing
	 * is fully supported and should work just fine.  However the
	 * front end for RIO based GEMs is different and only supports
	 * 32-bit addressing.
	 *
	 * For now we assume the various PPC GEMs are 32-bit only as well.
	 */
	if (pdev->vendor == PCI_VENDOR_ID_SUN &&
	    pdev->device == PCI_DEVICE_ID_SUN_GEM &&
	    !pci_set_dma_mask(pdev, DMA_BIT_MASK(64))) {
		pci_using_dac = 1;
	} else {
		err = pci_set_dma_mask(pdev, DMA_BIT_MASK(32));
		if (err) {
			pr_err("No usable DMA configuration, aborting\n");
			goto err_disable_device;
		}
		pci_using_dac = 0;
	}

	gemreg_base = pci_resource_start(pdev, 0);
	gemreg_len = pci_resource_len(pdev, 0);

	if ((pci_resource_flags(pdev, 0) & IORESOURCE_IO) != 0) {
		pr_err("Cannot find proper PCI device base address, aborting\n");
		err = -ENODEV;
		goto err_disable_device;
	}

	dev = alloc_etherdev(sizeof(*gp));
	if (!dev) {
		err = -ENOMEM;
		goto err_disable_device;
	}
	SET_NETDEV_DEV(dev, &pdev->dev);

	gp = netdev_priv(dev);

	err = pci_request_regions(pdev, DRV_NAME);
	if (err) {
		pr_err("Cannot obtain PCI resources, aborting\n");
		goto err_out_free_netdev;
	}

	gp->pdev = pdev;
	gp->dev = dev;

	gp->msg_enable = DEFAULT_MSG;

	timer_setup(&gp->link_timer, gem_link_timer, 0);

	INIT_WORK(&gp->reset_task, gem_reset_task);

	gp->lstate = link_down;
	gp->timer_ticks = 0;
	netif_carrier_off(dev);

	gp->regs = ioremap(gemreg_base, gemreg_len);
	if (!gp->regs) {
		pr_err("Cannot map device registers, aborting\n");
		err = -EIO;
		goto err_out_free_res;
	}

	/* On Apple, we want a reference to the Open Firmware device-tree
	 * node. We use it for clock control.
	 */
#if defined(CONFIG_PPC_PMAC) || defined(CONFIG_SPARC)
	gp->of_node = pci_device_to_OF_node(pdev);
#endif

	/* Only Apple version supports WOL afaik */
	if (pdev->vendor == PCI_VENDOR_ID_APPLE)
		gp->has_wol = 1;

	/* Make sure cell is enabled */
	gem_get_cell(gp);

	/* Make sure everything is stopped and in init state */
	gem_reset(gp);

	/* Fill up the mii_phy structure (even if we won't use it) */
	gp->phy_mii.dev = dev;
	gp->phy_mii.mdio_read = _sungem_phy_read;
	gp->phy_mii.mdio_write = _sungem_phy_write;
#ifdef CONFIG_PPC_PMAC
	gp->phy_mii.platform_data = gp->of_node;
#endif
	/* By default, we start with autoneg */
	gp->want_autoneg = 1;

	/* Check fifo sizes, PHY type, etc... */
	if (gem_check_invariants(gp)) {
		err = -ENODEV;
		goto err_out_iounmap;
	}

	/* It is guaranteed that the returned buffer will be at least
	 * PAGE_SIZE aligned.
	 */
	gp->init_block = (struct gem_init_block *)
		pci_alloc_consistent(pdev, sizeof(struct gem_init_block),
				     &gp->gblock_dvma);
	if (!gp->init_block) {
		pr_err("Cannot allocate init block, aborting\n");
		err = -ENOMEM;
		goto err_out_iounmap;
	}

	err = gem_get_device_address(gp);
	if (err)
		goto err_out_free_consistent;

	dev->netdev_ops = &gem_netdev_ops;
	netif_napi_add(dev, &gp->napi, gem_poll, 64);
	dev->ethtool_ops = &gem_ethtool_ops;
	dev->watchdog_timeo = 5 * HZ;
	dev->dma = 0;

	/* Set that now, in case PM kicks in now */
	pci_set_drvdata(pdev, dev);

	/* We can do scatter/gather and HW checksum */
	dev->hw_features = NETIF_F_SG | NETIF_F_HW_CSUM | NETIF_F_RXCSUM;
	dev->features = dev->hw_features;
	if (pci_using_dac)
		dev->features |= NETIF_F_HIGHDMA;

	/* MTU range: 68 - 1500 (Jumbo mode is broken) */
	dev->min_mtu = GEM_MIN_MTU;
	dev->max_mtu = GEM_MAX_MTU;

	/* Register with kernel */
	if (register_netdev(dev)) {
		pr_err("Cannot register net device, aborting\n");
		err = -ENOMEM;
		goto err_out_free_consistent;
	}

	/* Undo the get_cell with appropriate locking (we could use
	 * ndo_init/uninit but that would be even more clumsy imho)
	 */
	rtnl_lock();
	gem_put_cell(gp);
	rtnl_unlock();

	netdev_info(dev, "Sun GEM (PCI) 10/100/1000BaseT Ethernet %pM\n",
		    dev->dev_addr);
	return 0;

err_out_free_consistent:
	gem_remove_one(pdev);
err_out_iounmap:
	gem_put_cell(gp);
	iounmap(gp->regs);

err_out_free_res:
	pci_release_regions(pdev);

err_out_free_netdev:
	free_netdev(dev);
err_disable_device:
	pci_disable_device(pdev);
	return err;

}


static struct pci_driver gem_driver = {
	.name		= GEM_MODULE_NAME,
	.id_table	= gem_pci_tbl,
	.probe		= gem_init_one,
	.remove		= gem_remove_one,
#ifdef CONFIG_PM
	.suspend	= gem_suspend,
	.resume		= gem_resume,
#endif /* CONFIG_PM */
};

module_pci_driver(gem_driver);
