Back to home page

Quest Cross Reference

 
 

    


Warning, cross-references for /kernel/drivers/net/r8169.c need to be fixed.

0001 /*                    The Quest Operating System
0002  *  Copyright (C) 2005-2010  Richard West, Boston University
0003  *
0004  *  This program is free software: you can redistribute it and/or modify
0005  *  it under the terms of the GNU General Public License as published by
0006  *  the Free Software Foundation, either version 3 of the License, or
0007  *  (at your option) any later version.
0008  *
0009  *  This program is distributed in the hope that it will be useful,
0010  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
0011  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
0012  *  GNU General Public License for more details.
0013  *
0014  *  You should have received a copy of the GNU General Public License
0015  *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
0016  */
0017 
0018 /* Realtek 8169 NIC driver */
0019 
0020 /* Based on Linux driver by ShuChen, Francois Romieu, et al. */
0021 
0022 #include "drivers/pci/pci.h"
0023 #include "drivers/net/ethernet.h"
0024 #include "drivers/net/skbuff.h"
0025 #include "arch/i386.h"
0026 #include "util/printf.h"
0027 #include "util/bitrev.h"
0028 #include "util/crc32.h"
0029 #include "smp/smp.h"
0030 #include "smp/apic.h"
0031 #include "mem/physical.h"
0032 #include "mem/virtual.h"
0033 #include "mem/pow2.h"
0034 #include "kernel.h"
0035 #include "sched/vcpu.h"
0036 #include "sched/sched.h"
0037 #include "module/header.h"
0038 
0039 //#define DEBUG_R8169
0040 #define TX_TIMING
0041 
0042 #ifdef TX_TIMING
0043 #include "lwip/udp.h"
0044 #endif
0045 
0046 #ifdef DEBUG_R8169
0047 #define DLOG(fmt,...) DLOG_PREFIX("r8169",fmt,##__VA_ARGS__)
0048 #else
0049 #define DLOG(fmt,...) ;
0050 #endif
0051 
0052 #define udelay tsc_delay_usec
0053 #define net_device _ethernet_device
0054 #define netdev_priv(x) (x)->drvdata
0055 #define pci_get_drvdata(x) (x)->drvdata
0056 
0057 #define PCI_SUBSYSTEM_VENDOR_ID 0x2c
0058 #define PCI_SUBSYSTEM_ID        0x2e
0059 #define PCI_CACHE_LINE_SIZE     0x0c    /* 8 bits */
0060 #define PCI_LATENCY_TIMER       0x0d    /* 8 bits */
0061 
0062 static void
0063 pci_write_config_word (pci_device *p, u32 offset, u16 val)
0064 {
0065   pci_write_word (pci_addr (p->bus, p->slot, p->func, offset), val);
0066 }
0067 
0068 static void
0069 pci_write_config_byte (pci_device *p, u32 offset, u8 val)
0070 {
0071   pci_write_byte (pci_addr (p->bus, p->slot, p->func, offset), val);
0072 }
0073 
0074 static void
0075 pci_read_config_word (pci_device *p, u32 offset, u16 *val)
0076 {
0077   *val = pci_read_word (pci_addr (p->bus, p->slot, p->func, offset));
0078 }
0079 
0080 /* The forced speed, 10Mb, 100Mb, gigabit, 2.5Gb, 10GbE. */
0081 #define SPEED_10                10
0082 #define SPEED_100               100
0083 #define SPEED_1000              1000
0084 #define SPEED_2500              2500
0085 #define SPEED_10000             10000
0086 
0087 /* Duplex, half or full. */
0088 #define DUPLEX_HALF             0x00
0089 #define DUPLEX_FULL             0x01
0090 
0091 #define AUTONEG_DISABLE         0x00
0092 #define AUTONEG_ENABLE          0x01
0093 
0094 /* 1000BASE-T Control register */
0095 #define ADVERTISE_1000FULL      0x0200  /* Advertise 1000BASE-T full duplex */
0096 #define ADVERTISE_1000HALF      0x0100  /* Advertise 1000BASE-T half duplex */
0097 
0098 /* Advertisement control register. */
0099 #define ADVERTISE_SLCT          0x001f  /* Selector bits               */
0100 #define ADVERTISE_CSMA          0x0001  /* Only selector supported     */
0101 #define ADVERTISE_10HALF        0x0020  /* Try for 10mbps half-duplex  */
0102 #define ADVERTISE_1000XFULL     0x0020  /* Try for 1000BASE-X full-duplex */
0103 #define ADVERTISE_10FULL        0x0040  /* Try for 10mbps full-duplex  */
0104 #define ADVERTISE_1000XHALF     0x0040  /* Try for 1000BASE-X half-duplex */
0105 #define ADVERTISE_100HALF       0x0080  /* Try for 100mbps half-duplex */
0106 #define ADVERTISE_1000XPAUSE    0x0080  /* Try for 1000BASE-X pause    */
0107 #define ADVERTISE_100FULL       0x0100  /* Try for 100mbps full-duplex */
0108 #define ADVERTISE_1000XPSE_ASYM 0x0100  /* Try for 1000BASE-X asym pause */
0109 #define ADVERTISE_100BASE4      0x0200  /* Try for 100mbps 4k packets  */
0110 #define ADVERTISE_PAUSE_CAP     0x0400  /* Try for pause               */
0111 #define ADVERTISE_PAUSE_ASYM    0x0800  /* Try for asymetric pause     */
0112 #define ADVERTISE_RESV          0x1000  /* Unused...                   */
0113 #define ADVERTISE_RFAULT        0x2000  /* Say we can detect faults    */
0114 #define ADVERTISE_LPACK         0x4000  /* Ack link partners response  */
0115 #define ADVERTISE_NPAGE         0x8000  /* Next page bit               */
0116 
0117 #define MII_BMCR            0x00        /* Basic mode control register */
0118 #define MII_BMSR            0x01        /* Basic mode status register  */
0119 #define MII_PHYSID1         0x02        /* PHYS ID 1                   */
0120 #define MII_PHYSID2         0x03        /* PHYS ID 2                   */
0121 #define MII_ADVERTISE       0x04        /* Advertisement control reg   */
0122 #define MII_LPA             0x05        /* Link partner ability reg    */
0123 #define MII_EXPANSION       0x06        /* Expansion register          */
0124 #define MII_CTRL1000        0x09        /* 1000BASE-T control          */
0125 #define MII_STAT1000        0x0a        /* 1000BASE-T status           */
0126 #define MII_ESTATUS         0x0f        /* Extended Status */
0127 #define MII_DCOUNTER        0x12        /* Disconnect counter          */
0128 #define MII_FCSCOUNTER      0x13        /* False carrier counter       */
0129 #define MII_NWAYTEST        0x14        /* N-way auto-neg test reg     */
0130 #define MII_RERRCOUNTER     0x15        /* Receive error counter       */
0131 #define MII_SREVISION       0x16        /* Silicon revision            */
0132 #define MII_RESV1           0x17        /* Reserved...                 */
0133 #define MII_LBRERROR        0x18        /* Lpback, rx, bypass error    */
0134 #define MII_PHYADDR         0x19        /* PHY address                 */
0135 #define MII_RESV2           0x1a        /* Reserved...                 */
0136 #define MII_TPISTATUS       0x1b        /* TPI status for 10mbps       */
0137 #define MII_NCONFIG         0x1c        /* Network interface config    */
0138 
0139 /* Basic mode control register. */
0140 #define BMCR_RESV               0x003f  /* Unused...                   */
0141 #define BMCR_SPEED1000          0x0040  /* MSB of Speed (1000)         */
0142 #define BMCR_CTST               0x0080  /* Collision test              */
0143 #define BMCR_FULLDPLX           0x0100  /* Full duplex                 */
0144 #define BMCR_ANRESTART          0x0200  /* Auto negotiation restart    */
0145 #define BMCR_ISOLATE            0x0400  /* Disconnect DP83840 from MII */
0146 #define BMCR_PDOWN              0x0800  /* Powerdown the DP83840       */
0147 #define BMCR_ANENABLE           0x1000  /* Enable auto negotiation     */
0148 #define BMCR_SPEED100           0x2000  /* Select 100Mbps              */
0149 #define BMCR_LOOPBACK           0x4000  /* TXD loopback bits           */
0150 #define BMCR_RESET              0x8000  /* Reset the DP83840           */
0151 
0152 
0153 /* MAC address length */
0154 #define MAC_ADDR_LEN    6
0155 
0156 #define MAX_READ_REQUEST_SHIFT  12
0157 #define RX_FIFO_THRESH  7       /* 7 means NO threshold, Rx buffer level before first PCI xfer. */
0158 #define RX_DMA_BURST    6       /* Maximum PCI burst, '6' is 1024 */
0159 #define TX_DMA_BURST    6       /* Maximum PCI burst, '6' is 1024 */
0160 #define EarlyTxThld     0x3F    /* 0x3F means NO early transmit */
0161 #define SafeMtu         0x1c20  /* ... actually life sucks beyond ~7k */
0162 #define InterFrameGap   0x03    /* 3 means InterFrameGap = the shortest one */
0163 
0164 #define R8169_REGS_SIZE         256
0165 #define R8169_NAPI_WEIGHT       64
0166 #define NUM_TX_DESC     64      /* Number of Tx descriptor registers */
0167 #define NUM_RX_DESC     256     /* Number of Rx descriptor registers */
0168 #define RX_BUF_SIZE     1536    /* Rx Buffer size */
0169 #define R8169_TX_RING_BYTES     (NUM_TX_DESC * sizeof(struct TxDesc))
0170 #define R8169_RX_RING_BYTES     (NUM_RX_DESC * sizeof(struct RxDesc))
0171 
0172 #define RTL8169_TX_TIMEOUT      (6*HZ)
0173 #define RTL8169_PHY_TIMEOUT     (10*HZ)
0174 
0175 #define RTL_EEPROM_SIG          cpu_to_le32(0x8129)
0176 #define RTL_EEPROM_SIG_MASK     cpu_to_le32(0xffff)
0177 #define RTL_EEPROM_SIG_ADDR     0x0000
0178 
0179 static inline u8
0180 __raw_readb(const volatile void *addr)
0181 {
0182   return *(const volatile u8 *) addr;
0183 }
0184 
0185 static inline u16
0186 __raw_readw(const volatile void *addr)
0187 {
0188   return *(const volatile u16 *) addr;
0189 }
0190 
0191 static inline u32
0192 __raw_readl(const volatile void *addr)
0193 {
0194   return *(const volatile u32 *) addr;
0195 }
0196 
0197 static inline void
0198 __raw_writeb(u8 b, volatile void *addr)
0199 {
0200   *(volatile u8 *) addr = b;
0201 }
0202 
0203 static inline void
0204 __raw_writew(u16 b, volatile void *addr)
0205 {
0206   *(volatile u16 *) addr = b;
0207 }
0208 
0209 static inline void
0210 __raw_writel(u32 b, volatile void *addr)
0211 {
0212   *(volatile u32 *) addr = b;
0213 }
0214 
0215 /* write/read MMIO register */
0216 #define RTL_W8(reg, val8)       __raw_writeb ((val8), ioaddr + (reg))
0217 #define RTL_W16(reg, val16)     __raw_writew ((val16), ioaddr + (reg))
0218 #define RTL_W32(reg, val32)     __raw_writel ((val32), ioaddr + (reg))
0219 #define RTL_R8(reg)             __raw_readb (ioaddr + (reg))
0220 #define RTL_R16(reg)            __raw_readw (ioaddr + (reg))
0221 #define RTL_R32(reg)            __raw_readl (ioaddr + (reg))
0222 
0223 enum mac_version {
0224   RTL_GIGA_MAC_NONE   = 0x00,
0225   RTL_GIGA_MAC_VER_01 = 0x01, // 8169
0226   RTL_GIGA_MAC_VER_02 = 0x02, // 8169S
0227   RTL_GIGA_MAC_VER_03 = 0x03, // 8110S
0228   RTL_GIGA_MAC_VER_04 = 0x04, // 8169SB
0229   RTL_GIGA_MAC_VER_05 = 0x05, // 8110SCd
0230   RTL_GIGA_MAC_VER_06 = 0x06, // 8110SCe
0231   RTL_GIGA_MAC_VER_07 = 0x07, // 8102e
0232   RTL_GIGA_MAC_VER_08 = 0x08, // 8102e
0233   RTL_GIGA_MAC_VER_09 = 0x09, // 8102e
0234   RTL_GIGA_MAC_VER_10 = 0x0a, // 8101e
0235   RTL_GIGA_MAC_VER_11 = 0x0b, // 8168Bb
0236   RTL_GIGA_MAC_VER_12 = 0x0c, // 8168Be
0237   RTL_GIGA_MAC_VER_13 = 0x0d, // 8101Eb
0238   RTL_GIGA_MAC_VER_14 = 0x0e, // 8101 ?
0239   RTL_GIGA_MAC_VER_15 = 0x0f, // 8101 ?
0240   RTL_GIGA_MAC_VER_16 = 0x11, // 8101Ec
0241   RTL_GIGA_MAC_VER_17 = 0x10, // 8168Bf
0242   RTL_GIGA_MAC_VER_18 = 0x12, // 8168CP
0243   RTL_GIGA_MAC_VER_19 = 0x13, // 8168C
0244   RTL_GIGA_MAC_VER_20 = 0x14, // 8168C
0245   RTL_GIGA_MAC_VER_21 = 0x15, // 8168C
0246   RTL_GIGA_MAC_VER_22 = 0x16, // 8168C
0247   RTL_GIGA_MAC_VER_23 = 0x17, // 8168CP
0248   RTL_GIGA_MAC_VER_24 = 0x18, // 8168CP
0249   RTL_GIGA_MAC_VER_25 = 0x19, // 8168D
0250   RTL_GIGA_MAC_VER_26 = 0x1a, // 8168D
0251   RTL_GIGA_MAC_VER_27 = 0x1b  // 8168DP
0252 };
0253 
0254 #define _R(NAME,MAC,MASK)                                       \
0255   { .name = NAME, .mac_version = MAC, .RxConfigMask = MASK }
0256 
0257 static const struct {
0258   const char *name;
0259   u8 mac_version;
0260   u32 RxConfigMask;     /* Clears the bits supported by this chip */
0261 } rtl_chip_info[] = {
0262   _R("RTL8169",         RTL_GIGA_MAC_VER_01, 0xff7e1880), // 8169
0263   _R("RTL8169s",                RTL_GIGA_MAC_VER_02, 0xff7e1880), // 8169S
0264   _R("RTL8110s",                RTL_GIGA_MAC_VER_03, 0xff7e1880), // 8110S
0265   _R("RTL8169sb/8110sb",        RTL_GIGA_MAC_VER_04, 0xff7e1880), // 8169SB
0266   _R("RTL8169sc/8110sc",        RTL_GIGA_MAC_VER_05, 0xff7e1880), // 8110SCd
0267   _R("RTL8169sc/8110sc",        RTL_GIGA_MAC_VER_06, 0xff7e1880), // 8110SCe
0268   _R("RTL8102e",                RTL_GIGA_MAC_VER_07, 0xff7e1880), // PCI-E
0269   _R("RTL8102e",                RTL_GIGA_MAC_VER_08, 0xff7e1880), // PCI-E
0270   _R("RTL8102e",                RTL_GIGA_MAC_VER_09, 0xff7e1880), // PCI-E
0271   _R("RTL8101e",                RTL_GIGA_MAC_VER_10, 0xff7e1880), // PCI-E
0272   _R("RTL8168b/8111b",  RTL_GIGA_MAC_VER_11, 0xff7e1880), // PCI-E
0273   _R("RTL8168b/8111b",  RTL_GIGA_MAC_VER_12, 0xff7e1880), // PCI-E
0274   _R("RTL8101e",                RTL_GIGA_MAC_VER_13, 0xff7e1880), // PCI-E 8139
0275   _R("RTL8100e",                RTL_GIGA_MAC_VER_14, 0xff7e1880), // PCI-E 8139
0276   _R("RTL8100e",                RTL_GIGA_MAC_VER_15, 0xff7e1880), // PCI-E 8139
0277   _R("RTL8168b/8111b",  RTL_GIGA_MAC_VER_17, 0xff7e1880), // PCI-E
0278   _R("RTL8101e",                RTL_GIGA_MAC_VER_16, 0xff7e1880), // PCI-E
0279   _R("RTL8168cp/8111cp",        RTL_GIGA_MAC_VER_18, 0xff7e1880), // PCI-E
0280   _R("RTL8168c/8111c",  RTL_GIGA_MAC_VER_19, 0xff7e1880), // PCI-E
0281   _R("RTL8168c/8111c",  RTL_GIGA_MAC_VER_20, 0xff7e1880), // PCI-E
0282   _R("RTL8168c/8111c",  RTL_GIGA_MAC_VER_21, 0xff7e1880), // PCI-E
0283   _R("RTL8168c/8111c",  RTL_GIGA_MAC_VER_22, 0xff7e1880), // PCI-E
0284   _R("RTL8168cp/8111cp",        RTL_GIGA_MAC_VER_23, 0xff7e1880), // PCI-E
0285   _R("RTL8168cp/8111cp",        RTL_GIGA_MAC_VER_24, 0xff7e1880), // PCI-E
0286   _R("RTL8168d/8111d",  RTL_GIGA_MAC_VER_25, 0xff7e1880), // PCI-E
0287   _R("RTL8168d/8111d",  RTL_GIGA_MAC_VER_26, 0xff7e1880), // PCI-E
0288   _R("RTL8168dp/8111dp",        RTL_GIGA_MAC_VER_27, 0xff7e1880)  // PCI-E
0289 };
0290 #undef _R
0291 
0292 enum cfg_version {
0293   RTL_CFG_0 = 0x00,
0294   RTL_CFG_1,
0295   RTL_CFG_2
0296 };
0297 
0298 #define PCI_VENDOR_ID_REALTEK           0x10ec
0299 #define PCI_VENDOR_ID_DLINK             0x1186
0300 #define PCI_VENDOR_ID_AT                0x1259
0301 #define PCI_VENDOR_ID_GIGABYTE          0x1458
0302 
0303 /* List of compatible cards (ended by { 0xFFFF, 0xFFFF }) */
0304 static struct {
0305   uint16 vendor, device, cfg;
0306 } compatible_ids[] = {
0307   { PCI_VENDOR_ID_REALTEK,   0x8129, RTL_CFG_0 },
0308   { PCI_VENDOR_ID_REALTEK,   0x8136, RTL_CFG_2 },
0309   { PCI_VENDOR_ID_REALTEK,   0x8167, RTL_CFG_0 },
0310   { PCI_VENDOR_ID_REALTEK,   0x8168, RTL_CFG_1 },
0311   { PCI_VENDOR_ID_REALTEK,   0x8169, RTL_CFG_0 },
0312   { PCI_VENDOR_ID_DLINK,     0x4300, RTL_CFG_0 },
0313   { PCI_VENDOR_ID_AT,        0xc107, RTL_CFG_0 },
0314   { 0x16ec,                  0x0116, RTL_CFG_0 },
0315   { 0xFFFF, 0xFFFF }
0316 };
0317 
0318 #define __iomem
0319 
0320 enum rtl_registers {
0321   MAC0          = 0,    /* Ethernet hardware address. */
0322   MAC4          = 4,
0323   MAR0          = 8,    /* Multicast filter. */
0324   CounterAddrLow                = 0x10,
0325   CounterAddrHigh               = 0x14,
0326   TxDescStartAddrLow    = 0x20,
0327   TxDescStartAddrHigh   = 0x24,
0328   TxHDescStartAddrLow   = 0x28,
0329   TxHDescStartAddrHigh  = 0x2c,
0330   FLASH         = 0x30,
0331   ERSR          = 0x36,
0332   ChipCmd               = 0x37,
0333   TxPoll                = 0x38,
0334   IntrMask      = 0x3c,
0335   IntrStatus    = 0x3e,
0336   TxConfig      = 0x40,
0337   RxConfig      = 0x44,
0338   RxMissed      = 0x4c,
0339   Cfg9346               = 0x50,
0340   Config0               = 0x51,
0341   Config1               = 0x52,
0342   Config2               = 0x53,
0343   Config3               = 0x54,
0344   Config4               = 0x55,
0345   Config5               = 0x56,
0346   MultiIntr     = 0x5c,
0347   PHYAR         = 0x60,
0348   PHYstatus     = 0x6c,
0349   RxMaxSize     = 0xda,
0350   CPlusCmd      = 0xe0,
0351   IntrMitigate  = 0xe2,
0352   RxDescAddrLow = 0xe4,
0353   RxDescAddrHigh        = 0xe8,
0354   EarlyTxThres  = 0xec,
0355   FuncEvent     = 0xf0,
0356   FuncEventMask = 0xf4,
0357   FuncPresetState       = 0xf8,
0358   FuncForceEvent        = 0xfc,
0359 };
0360 
0361 enum rtl8110_registers {
0362   TBICSR                        = 0x64,
0363   TBI_ANAR              = 0x68,
0364   TBI_LPAR              = 0x6a,
0365 };
0366 
0367 enum rtl8168_8101_registers {
0368   CSIDR                 = 0x64,
0369   CSIAR                 = 0x68,
0370 #define CSIAR_FLAG                      0x80000000
0371 #define CSIAR_WRITE_CMD                 0x80000000
0372 #define CSIAR_BYTE_ENABLE               0x0f
0373 #define CSIAR_BYTE_ENABLE_SHIFT         12
0374 #define CSIAR_ADDR_MASK                 0x0fff
0375 
0376   EPHYAR                        = 0x80,
0377 #define EPHYAR_FLAG                     0x80000000
0378 #define EPHYAR_WRITE_CMD                0x80000000
0379 #define EPHYAR_REG_MASK                 0x1f
0380 #define EPHYAR_REG_SHIFT                16
0381 #define EPHYAR_DATA_MASK                0xffff
0382   DBG_REG                       = 0xd1,
0383 #define FIX_NAK_1                       (1 << 4)
0384 #define FIX_NAK_2                       (1 << 3)
0385   EFUSEAR                       = 0xdc,
0386 #define EFUSEAR_FLAG                    0x80000000
0387 #define EFUSEAR_WRITE_CMD               0x80000000
0388 #define EFUSEAR_READ_CMD                0x00000000
0389 #define EFUSEAR_REG_MASK                0x03ff
0390 #define EFUSEAR_REG_SHIFT               8
0391 #define EFUSEAR_DATA_MASK               0xff
0392 };
0393 
0394 enum rtl_register_content {
0395   /* InterruptStatusBits */
0396   SYSErr        = 0x8000,
0397   PCSTimeout    = 0x4000,
0398   SWInt         = 0x0100,
0399   TxDescUnavail = 0x0080,
0400   RxFIFOOver    = 0x0040,
0401   LinkChg       = 0x0020,
0402   RxOverflow    = 0x0010,
0403   TxErr         = 0x0008,
0404   TxOK          = 0x0004,
0405   RxErr         = 0x0002,
0406   RxOK          = 0x0001,
0407 
0408   /* RxStatusDesc */
0409   RxFOVF        = (1 << 23),
0410   RxRWT = (1 << 22),
0411   RxRES = (1 << 21),
0412   RxRUNT        = (1 << 20),
0413   RxCRC = (1 << 19),
0414 
0415   /* ChipCmdBits */
0416   CmdReset      = 0x10,
0417   CmdRxEnb      = 0x08,
0418   CmdTxEnb      = 0x04,
0419   RxBufEmpty    = 0x01,
0420 
0421   /* TXPoll register p.5 */
0422   HPQ           = 0x80,         /* Poll cmd on the high prio queue */
0423   NPQ           = 0x40,         /* Poll cmd on the low prio queue */
0424   FSWInt                = 0x01,         /* Forced software interrupt */
0425 
0426   /* Cfg9346Bits */
0427   Cfg9346_Lock  = 0x00,
0428   Cfg9346_Unlock        = 0xc0,
0429 
0430   /* rx_mode_bits */
0431   AcceptErr     = 0x20,
0432   AcceptRunt    = 0x10,
0433   AcceptBroadcast       = 0x08,
0434   AcceptMulticast       = 0x04,
0435   AcceptMyPhys  = 0x02,
0436   AcceptAllPhys = 0x01,
0437 
0438   /* RxConfigBits */
0439   RxCfgFIFOShift        = 13,
0440   RxCfgDMAShift =  8,
0441 
0442   /* TxConfigBits */
0443   TxInterFrameGapShift = 24,
0444   TxDMAShift = 8,       /* DMA burst value (0-7) is shift this many bits */
0445 
0446   /* Config1 register p.24 */
0447   LEDS1         = (1 << 7),
0448   LEDS0         = (1 << 6),
0449   MSIEnable     = (1 << 5),     /* Enable Message Signaled Interrupt */
0450   Speed_down    = (1 << 4),
0451   MEMMAP                = (1 << 3),
0452   IOMAP         = (1 << 2),
0453   VPD           = (1 << 1),
0454   PMEnable      = (1 << 0),     /* Power Management Enable */
0455 
0456   /* Config2 register p. 25 */
0457   PCI_Clock_66MHz = 0x01,
0458   PCI_Clock_33MHz = 0x00,
0459 
0460   /* Config3 register p.25 */
0461   MagicPacket   = (1 << 5),     /* Wake up when receives a Magic Packet */
0462   LinkUp                = (1 << 4),     /* Wake up when the cable connection is re-established */
0463   Beacon_en     = (1 << 0),     /* 8168 only. Reserved in the 8168b */
0464 
0465   /* Config5 register p.27 */
0466   BWF           = (1 << 6),     /* Accept Broadcast wakeup frame */
0467   MWF           = (1 << 5),     /* Accept Multicast wakeup frame */
0468   UWF           = (1 << 4),     /* Accept Unicast wakeup frame */
0469   LanWake               = (1 << 1),     /* LanWake enable/disable */
0470   PMEStatus     = (1 << 0),     /* PME status can be reset by PCI RST# */
0471 
0472   /* TBICSR p.28 */
0473   TBIReset      = 0x80000000,
0474   TBILoopback   = 0x40000000,
0475   TBINwEnable   = 0x20000000,
0476   TBINwRestart  = 0x10000000,
0477   TBILinkOk     = 0x02000000,
0478   TBINwComplete = 0x01000000,
0479 
0480   /* CPlusCmd p.31 */
0481   EnableBist    = (1 << 15),    // 8168 8101
0482   Mac_dbgo_oe   = (1 << 14),    // 8168 8101
0483   Normal_mode   = (1 << 13),    // unused
0484   Force_half_dup        = (1 << 12),    // 8168 8101
0485   Force_rxflow_en       = (1 << 11),    // 8168 8101
0486   Force_txflow_en       = (1 << 10),    // 8168 8101
0487   Cxpl_dbg_sel  = (1 << 9),     // 8168 8101
0488   ASF           = (1 << 8),     // 8168 8101
0489   PktCntrDisable        = (1 << 7),     // 8168 8101
0490   Mac_dbgo_sel  = 0x001c,       // 8168
0491   RxVlan                = (1 << 6),
0492   RxChkSum      = (1 << 5),
0493   PCIDAC                = (1 << 4),
0494   PCIMulRW      = (1 << 3),
0495   INTT_0                = 0x0000,       // 8168
0496   INTT_1                = 0x0001,       // 8168
0497   INTT_2                = 0x0002,       // 8168
0498   INTT_3                = 0x0003,       // 8168
0499 
0500   /* rtl8169_PHYstatus */
0501   TBI_Enable    = 0x80,
0502   TxFlowCtrl    = 0x40,
0503   RxFlowCtrl    = 0x20,
0504   _1000bpsF     = 0x10,
0505   _100bps               = 0x08,
0506   _10bps                = 0x04,
0507   LinkStatus    = 0x02,
0508   FullDup               = 0x01,
0509 
0510   /* _TBICSRBit */
0511   TBILinkOK     = 0x02000000,
0512 
0513   /* DumpCounterCommand */
0514   CounterDump   = 0x8,
0515 };
0516 
0517 enum desc_status_bit {
0518   DescOwn               = (1 << 31), /* Descriptor is owned by NIC */
0519   RingEnd               = (1 << 30), /* End of descriptor ring */
0520   FirstFrag     = (1 << 29), /* First segment of a packet */
0521   LastFrag      = (1 << 28), /* Final segment of a packet */
0522 
0523   /* Tx private */
0524   LargeSend     = (1 << 27), /* TCP Large Send Offload (TSO) */
0525   MSSShift      = 16,        /* MSS value position */
0526   MSSMask               = 0xfff,     /* MSS value + LargeSend bit: 12 bits */
0527   IPCS          = (1 << 18), /* Calculate IP checksum */
0528   UDPCS         = (1 << 17), /* Calculate UDP/IP checksum */
0529   TCPCS         = (1 << 16), /* Calculate TCP/IP checksum */
0530   TxVlanTag     = (1 << 17), /* Add VLAN tag */
0531 
0532   /* Rx private */
0533   PID1          = (1 << 18), /* Protocol ID bit 1/2 */
0534   PID0          = (1 << 17), /* Protocol ID bit 2/2 */
0535 
0536 #define RxProtoUDP      (PID1)
0537 #define RxProtoTCP      (PID0)
0538 #define RxProtoIP       (PID1 | PID0)
0539 #define RxProtoMask     RxProtoIP
0540 
0541   IPFail                = (1 << 16), /* IP checksum failed */
0542   UDPFail               = (1 << 15), /* UDP/IP checksum failed */
0543   TCPFail               = (1 << 14), /* TCP/IP checksum failed */
0544   RxVlanTag     = (1 << 16), /* VLAN tag available */
0545 };
0546 
0547 #define RsvdMask        0x3fffc000
0548 
0549 struct TxDesc {
0550   __le32 opts1;
0551   __le32 opts2;
0552   __le64 addr;
0553 };
0554 
0555 struct RxDesc {
0556   __le32 opts1;
0557   __le32 opts2;
0558   __le64 addr;
0559 };
0560 
0561 struct ring_info {
0562   struct sk_buff        *skb;
0563   u32           len;
0564   u8            __pad[sizeof(void *) - sizeof(u32)];
0565 };
0566 
0567 enum features {
0568   RTL_FEATURE_WOL               = (1 << 0),
0569   RTL_FEATURE_MSI               = (1 << 1),
0570   RTL_FEATURE_GMII      = (1 << 2),
0571 };
0572 
0573 struct rtl8169_counters {
0574   __le64        tx_packets;
0575   __le64        rx_packets;
0576   __le64        tx_errors;
0577   __le32        rx_errors;
0578   __le16        rx_missed;
0579   __le16        align_errors;
0580   __le32        tx_one_collision;
0581   __le32        tx_multi_collision;
0582   __le64        rx_unicast;
0583   __le64        rx_broadcast;
0584   __le32        rx_multicast;
0585   __le16        tx_aborted;
0586   __le16        tx_underun;
0587 };
0588 
0589 typedef spinlock spinlock_t;
0590 struct napi_struct {
0591 };
0592 struct ethtool_cmd {
0593 };
0594 struct mii_ioctl_data {
0595 };
0596 
0597 struct rtl8169_private {
0598   void __iomem *mmio_addr;      /* memory map physical address */
0599   struct pci_dev *pci_dev;      /* Index of PCI device */
0600   struct net_device *dev;
0601   struct napi_struct napi;
0602   spinlock_t lock;              /* spin lock flag */
0603   u32 msg_enable;
0604   int chipset;
0605   int mac_version;
0606   u32 cur_rx; /* Index into the Rx descriptor buffer of next Rx pkt. */
0607   u32 cur_tx; /* Index into the Tx descriptor buffer of next Rx pkt. */
0608   u32 dirty_rx;
0609   u32 dirty_tx;
0610   struct TxDesc *TxDescArray;   /* 256-aligned Tx descriptor ring */
0611   struct RxDesc *RxDescArray;   /* 256-aligned Rx descriptor ring */
0612   dma_addr_t TxPhyAddr;
0613   dma_addr_t RxPhyAddr;
0614   struct sk_buff *Rx_skbuff[NUM_RX_DESC];       /* Rx data buffers */
0615   struct ring_info tx_skb[NUM_TX_DESC]; /* Tx data buffers */
0616   unsigned align;
0617   unsigned rx_buf_sz;
0618   //struct timer_list timer;
0619   u16 cp_cmd;
0620   u16 intr_event;
0621   u16 napi_event;
0622   u16 intr_mask;
0623   int phy_1000_ctrl_reg;
0624 #ifdef CONFIG_R8169_VLAN
0625   struct vlan_group *vlgrp;
0626 #endif
0627   int (*set_speed)(struct net_device *, u8 autoneg, u16 speed, u8 duplex);
0628   int (*get_settings)(struct net_device *, struct ethtool_cmd *);
0629   void (*phy_reset_enable)(void __iomem *);
0630   void (*hw_start)(struct net_device *);
0631   unsigned int (*phy_reset_pending)(void __iomem *);
0632   unsigned int (*link_ok)(void __iomem *);
0633   int (*do_ioctl)(struct rtl8169_private *tp, struct mii_ioctl_data *data, int cmd);
0634   int pcie_cap;
0635   //struct delayed_work task;
0636   unsigned features;
0637 
0638   //struct mii_if_info mii;
0639   struct rtl8169_counters counters;
0640   u32 saved_wolopts;
0641   u8 mac_addr[MAC_ADDR_LEN];
0642   ethernet_device ethdev;
0643 };
0644 
0645 static void
0646 mdio_write(void __iomem *ioaddr, int reg_addr, int value)
0647 {
0648   int i;
0649 
0650   RTL_W32(PHYAR, 0x80000000 | (reg_addr & 0x1f) << 16 | (value & 0xffff));
0651 
0652   for (i = 20; i > 0; i--) {
0653     /*
0654      * Check if the RTL8169 has completed writing to the specified
0655      * MII register.
0656      */
0657     if (!(RTL_R32(PHYAR) & 0x80000000))
0658       break;
0659     udelay(25);
0660   }
0661   /*
0662    * According to hardware specs a 20us delay is required after write
0663    * complete indication, but before sending next command.
0664    */
0665   udelay(20);
0666 }
0667 
0668 static int
0669 mdio_read(void __iomem *ioaddr, int reg_addr)
0670 {
0671   int i, value = -1;
0672 
0673   RTL_W32(PHYAR, 0x0 | (reg_addr & 0x1f) << 16);
0674 
0675   for (i = 20; i > 0; i--) {
0676     /*
0677      * Check if the RTL8169 has completed retrieving data from
0678      * the specified MII register.
0679      */
0680     if (RTL_R32(PHYAR) & 0x80000000) {
0681       value = RTL_R32(PHYAR) & 0xffff;
0682       break;
0683     }
0684     udelay(25);
0685   }
0686   /*
0687    * According to hardware specs a 20us delay is required after read
0688    * complete indication, but before sending next command.
0689    */
0690   udelay(20);
0691 
0692   return value;
0693 }
0694 
0695 static void
0696 mdio_patch(void __iomem *ioaddr, int reg_addr, int value)
0697 {
0698   mdio_write(ioaddr, reg_addr, mdio_read(ioaddr, reg_addr) | value);
0699 }
0700 
0701 static void
0702 mdio_plus_minus(void __iomem *ioaddr, int reg_addr, int p, int m)
0703 {
0704   int val;
0705 
0706   val = mdio_read(ioaddr, reg_addr);
0707   mdio_write(ioaddr, reg_addr, (val | p) & ~m);
0708 }
0709 
0710 static void rtl_ephy_write(void __iomem *ioaddr, int reg_addr, int value)
0711 {
0712   unsigned int i;
0713 
0714   RTL_W32(EPHYAR, EPHYAR_WRITE_CMD | (value & EPHYAR_DATA_MASK) |
0715           (reg_addr & EPHYAR_REG_MASK) << EPHYAR_REG_SHIFT);
0716 
0717   for (i = 0; i < 100; i++) {
0718     if (!(RTL_R32(EPHYAR) & EPHYAR_FLAG))
0719       break;
0720     udelay(10);
0721   }
0722 }
0723 
0724 static u16 rtl_ephy_read(void __iomem *ioaddr, int reg_addr)
0725 {
0726   u16 value = 0xffff;
0727   unsigned int i;
0728 
0729   RTL_W32(EPHYAR, (reg_addr & EPHYAR_REG_MASK) << EPHYAR_REG_SHIFT);
0730 
0731   for (i = 0; i < 100; i++) {
0732     if (RTL_R32(EPHYAR) & EPHYAR_FLAG) {
0733       value = RTL_R32(EPHYAR) & EPHYAR_DATA_MASK;
0734       break;
0735     }
0736     udelay(10);
0737   }
0738 
0739   return value;
0740 }
0741 
0742 static void rtl_csi_write(void __iomem *ioaddr, int addr, int value)
0743 {
0744   unsigned int i;
0745 
0746   RTL_W32(CSIDR, value);
0747   RTL_W32(CSIAR, CSIAR_WRITE_CMD | (addr & CSIAR_ADDR_MASK) |
0748           CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT);
0749 
0750   for (i = 0; i < 100; i++) {
0751     if (!(RTL_R32(CSIAR) & CSIAR_FLAG))
0752       break;
0753     udelay(10);
0754   }
0755 }
0756 
0757 static u32 rtl_csi_read(void __iomem *ioaddr, int addr)
0758 {
0759   u32 value = ~0x00;
0760   unsigned int i;
0761 
0762   RTL_W32(CSIAR, (addr & CSIAR_ADDR_MASK) |
0763           CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT);
0764 
0765   for (i = 0; i < 100; i++) {
0766     if (RTL_R32(CSIAR) & CSIAR_FLAG) {
0767       value = RTL_R32(CSIDR);
0768       break;
0769     }
0770     udelay(10);
0771   }
0772 
0773   return value;
0774 }
0775 
0776 static u8
0777 rtl8168d_efuse_read(void __iomem *ioaddr, int reg_addr)
0778 {
0779   u8 value = 0xff;
0780   unsigned int i;
0781 
0782   RTL_W32(EFUSEAR, (reg_addr & EFUSEAR_REG_MASK) << EFUSEAR_REG_SHIFT);
0783 
0784   for (i = 0; i < 300; i++) {
0785     if (RTL_R32(EFUSEAR) & EFUSEAR_FLAG) {
0786       value = RTL_R32(EFUSEAR) & EFUSEAR_DATA_MASK;
0787       break;
0788     }
0789     udelay(100);
0790   }
0791 
0792   return value;
0793 }
0794 
0795 #define DMA_BIT_MASK(n) (((n) == 64) ? ~0ULL : ((1ULL<<(n))-1))
0796 
0797 static void rtl_set_rx_tx_desc_registers(struct rtl8169_private *tp,
0798                                          void __iomem *ioaddr)
0799 {
0800   /*
0801    * Magic spell: some iop3xx ARM board needs the TxDescAddrHigh
0802    * register to be written before TxDescAddrLow to work.
0803    * Switching from MMIO to I/O access fixes the issue as well.
0804    */
0805   RTL_W32(TxDescStartAddrHigh, ((u64) tp->TxPhyAddr) >> 32);
0806   RTL_W32(TxDescStartAddrLow, ((u64) tp->TxPhyAddr) & DMA_BIT_MASK(32));
0807   RTL_W32(RxDescAddrHigh, ((u64) tp->RxPhyAddr) >> 32);
0808   RTL_W32(RxDescAddrLow, ((u64) tp->RxPhyAddr) & DMA_BIT_MASK(32));
0809 }
0810 
0811 static u16 rtl_rw_cpluscmd(void __iomem *ioaddr)
0812 {
0813   u16 cmd;
0814 
0815   cmd = RTL_R16(CPlusCmd);
0816   RTL_W16(CPlusCmd, cmd);
0817   return cmd;
0818 }
0819 
0820 static void rtl_set_rx_max_size(void __iomem *ioaddr, unsigned int rx_buf_sz)
0821 {
0822   /* Low hurts. Let's disable the filtering. */
0823   RTL_W16(RxMaxSize, rx_buf_sz + 1);
0824 }
0825 
0826 static void rtl8169_set_magic_reg(void __iomem *ioaddr, unsigned mac_version)
0827 {
0828   static const struct {
0829     u32 mac_version;
0830     u32 clk;
0831     u32 val;
0832   } cfg2_info [] = {
0833     { RTL_GIGA_MAC_VER_05, PCI_Clock_33MHz, 0x000fff00 }, // 8110SCd
0834     { RTL_GIGA_MAC_VER_05, PCI_Clock_66MHz, 0x000fffff },
0835     { RTL_GIGA_MAC_VER_06, PCI_Clock_33MHz, 0x00ffff00 }, // 8110SCe
0836     { RTL_GIGA_MAC_VER_06, PCI_Clock_66MHz, 0x00ffffff }
0837   }, *p = cfg2_info;
0838   unsigned int i;
0839   u32 clk;
0840 
0841   clk = RTL_R8(Config2) & PCI_Clock_66MHz;
0842   for (i = 0; i < ARRAY_SIZE(cfg2_info); i++, p++) {
0843     if ((p->mac_version == mac_version) && (p->clk == clk)) {
0844       RTL_W32(0x7c, p->val);
0845       break;
0846     }
0847   }
0848 }
0849 
0850 static const unsigned int rtl8169_rx_config =
0851   (RX_FIFO_THRESH << RxCfgFIFOShift) | (RX_DMA_BURST << RxCfgDMAShift);
0852 
0853 static void rtl_set_rx_tx_config_registers(struct rtl8169_private *tp)
0854 {
0855   void __iomem *ioaddr = tp->mmio_addr;
0856   u32 cfg = rtl8169_rx_config;
0857 
0858   cfg |= (RTL_R32(RxConfig) & rtl_chip_info[tp->chipset].RxConfigMask);
0859   RTL_W32(RxConfig, cfg);
0860 
0861   /* Set DMA burst size and Interframe Gap Time */
0862   RTL_W32(TxConfig, (TX_DMA_BURST << TxDMAShift) |
0863           (InterFrameGap << TxInterFrameGapShift));
0864 }
0865 
0866 static void rtl_set_rx_mode(struct net_device *dev)
0867 {
0868   struct rtl8169_private *tp = netdev_priv(dev);
0869   void __iomem *ioaddr = tp->mmio_addr;
0870   u32 mc_filter[2];     /* Multicast hash filter */
0871   int rx_mode;
0872   u32 tmp = 0;
0873 
0874   rx_mode = AcceptBroadcast | AcceptMyPhys;
0875   mc_filter[1] = mc_filter[0] = 0;
0876   int bit_nr = ether_crc(ETH_ADDR_LEN, tp->mac_addr) >> 26;
0877   mc_filter[bit_nr >> 5] |= 1 << (bit_nr & 31);
0878   rx_mode |= AcceptMulticast;
0879 
0880   spinlock_lock(&tp->lock);
0881 
0882   tmp = rtl8169_rx_config | rx_mode |
0883     (RTL_R32(RxConfig) & rtl_chip_info[tp->chipset].RxConfigMask);
0884 
0885   if (tp->mac_version > RTL_GIGA_MAC_VER_06) {
0886     u32 data = mc_filter[0];
0887 
0888 #define swab32 ___constant_swab32
0889     mc_filter[0] = swab32(mc_filter[1]);
0890     mc_filter[1] = swab32(data);
0891   }
0892 
0893   RTL_W32(MAR0 + 4, mc_filter[1]);
0894   RTL_W32(MAR0 + 0, mc_filter[0]);
0895 
0896   RTL_W32(RxConfig, tmp);
0897 
0898   spinlock_unlock(&tp->lock);
0899 }
0900 
0901 static void rtl_tx_performance_tweak(struct pci_dev *pdev, u16 force)
0902 {
0903   struct net_device *dev = pci_get_drvdata(pdev);
0904   struct rtl8169_private *tp = netdev_priv(dev);
0905   int cap = tp->pcie_cap;
0906 
0907   if (cap) {
0908     u16 ctl;
0909 
0910 #define PCI_EXP_DEVCTL          8       /* Device Control */
0911 #define  PCI_EXP_DEVCTL_READRQ  0x7000  /* Max_Read_Request_Size */
0912     pci_read_config_word(pdev, cap + PCI_EXP_DEVCTL, &ctl);
0913     ctl = (ctl & ~PCI_EXP_DEVCTL_READRQ) | force;
0914     pci_write_config_word(pdev, cap + PCI_EXP_DEVCTL, ctl);
0915   }
0916 }
0917 
0918 static void rtl_csi_access_enable(void __iomem *ioaddr)
0919 {
0920   u32 csi;
0921 
0922   csi = rtl_csi_read(ioaddr, 0x070c) & 0x00ffffff;
0923   rtl_csi_write(ioaddr, 0x070c, csi | 0x27000000);
0924 }
0925 
0926 struct ephy_info {
0927   unsigned int offset;
0928   u16 mask;
0929   u16 bits;
0930 };
0931 
0932 static void rtl_ephy_init(void __iomem *ioaddr, const struct ephy_info *e, int len)
0933 {
0934   u16 w;
0935 
0936   while (len-- > 0) {
0937     w = (rtl_ephy_read(ioaddr, e->offset) & ~e->mask) | e->bits;
0938     rtl_ephy_write(ioaddr, e->offset, w);
0939     e++;
0940   }
0941 }
0942 
0943 static void rtl_disable_clock_request(struct pci_dev *pdev)
0944 {
0945   struct net_device *dev = pci_get_drvdata(pdev);
0946   struct rtl8169_private *tp = netdev_priv(dev);
0947   int cap = tp->pcie_cap;
0948 
0949   if (cap) {
0950     u16 ctl;
0951 
0952 #define PCI_EXP_LNKCTL          16      /* Link Control */
0953 #define  PCI_EXP_LNKCTL_CLKREQ_EN 0x100 /* Enable clkreq */
0954     pci_read_config_word(pdev, cap + PCI_EXP_LNKCTL, &ctl);
0955     ctl &= ~PCI_EXP_LNKCTL_CLKREQ_EN;
0956     pci_write_config_word(pdev, cap + PCI_EXP_LNKCTL, ctl);
0957   }
0958 }
0959 
0960 static void
0961 rtl_hw_start_8169(struct net_device *dev)
0962 {
0963   struct rtl8169_private *tp = netdev_priv(dev);
0964   void __iomem *ioaddr = tp->mmio_addr;
0965   struct pci_dev *pdev = tp->pci_dev;
0966 
0967   if (tp->mac_version == RTL_GIGA_MAC_VER_05) {
0968     RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) | PCIMulRW);
0969     pci_write_config_byte(pdev, PCI_CACHE_LINE_SIZE, 0x08);
0970   }
0971 
0972   RTL_W8(Cfg9346, Cfg9346_Unlock);
0973   if ((tp->mac_version == RTL_GIGA_MAC_VER_01) ||
0974       (tp->mac_version == RTL_GIGA_MAC_VER_02) ||
0975       (tp->mac_version == RTL_GIGA_MAC_VER_03) ||
0976       (tp->mac_version == RTL_GIGA_MAC_VER_04))
0977     RTL_W8(ChipCmd, CmdTxEnb | CmdRxEnb);
0978 
0979   RTL_W8(EarlyTxThres, EarlyTxThld);
0980 
0981   rtl_set_rx_max_size(ioaddr, tp->rx_buf_sz);
0982 
0983   if ((tp->mac_version == RTL_GIGA_MAC_VER_01) ||
0984       (tp->mac_version == RTL_GIGA_MAC_VER_02) ||
0985       (tp->mac_version == RTL_GIGA_MAC_VER_03) ||
0986       (tp->mac_version == RTL_GIGA_MAC_VER_04))
0987     rtl_set_rx_tx_config_registers(tp);
0988 
0989   tp->cp_cmd |= rtl_rw_cpluscmd(ioaddr) | PCIMulRW;
0990 
0991   if ((tp->mac_version == RTL_GIGA_MAC_VER_02) ||
0992       (tp->mac_version == RTL_GIGA_MAC_VER_03)) {
0993     DLOG("Set MAC Reg C+CR Offset 0xE0. "
0994          "Bit-3 and bit-14 MUST be 1");
0995     tp->cp_cmd |= (1 << 14);
0996   }
0997 
0998   RTL_W16(CPlusCmd, tp->cp_cmd);
0999 
1000   rtl8169_set_magic_reg(ioaddr, tp->mac_version);
1001 
1002   /*
1003    * Undocumented corner. Supposedly:
1004    * (TxTimer << 12) | (TxPackets << 8) | (RxTimer << 4) | RxPackets
1005    */
1006   RTL_W16(IntrMitigate, 0x0000);
1007 
1008   rtl_set_rx_tx_desc_registers(tp, ioaddr);
1009 
1010   if ((tp->mac_version != RTL_GIGA_MAC_VER_01) &&
1011       (tp->mac_version != RTL_GIGA_MAC_VER_02) &&
1012       (tp->mac_version != RTL_GIGA_MAC_VER_03) &&
1013       (tp->mac_version != RTL_GIGA_MAC_VER_04)) {
1014     RTL_W8(ChipCmd, CmdTxEnb | CmdRxEnb);
1015     rtl_set_rx_tx_config_registers(tp);
1016   }
1017 
1018   RTL_W8(Cfg9346, Cfg9346_Lock);
1019 
1020   /* Initially a 10 us delay. Turned it into a PCI commit. - FR */
1021   RTL_R8(IntrMask);
1022 
1023   RTL_W32(RxMissed, 0);
1024 
1025   rtl_set_rx_mode(dev);
1026 
1027   /* no early-rx interrupts */
1028   RTL_W16(MultiIntr, RTL_R16(MultiIntr) & 0xF000);
1029 
1030   /* Enable all known interrupts by setting the interrupt mask. */
1031   RTL_W16(IntrMask, tp->intr_event);
1032 }
1033 
1034 #define R8168_CPCMD_QUIRK_MASK (                        \
1035                                 EnableBist |            \
1036                                 Mac_dbgo_oe |           \
1037                                 Force_half_dup |        \
1038                                 Force_rxflow_en |       \
1039                                 Force_txflow_en |       \
1040                                 Cxpl_dbg_sel |          \
1041                                 ASF |                   \
1042                                 PktCntrDisable |        \
1043                                 Mac_dbgo_sel)
1044 
1045 static void rtl_hw_start_8168bb(void __iomem *ioaddr, struct pci_dev *pdev)
1046 {
1047   RTL_W8(Config3, RTL_R8(Config3) & ~Beacon_en);
1048 
1049   RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) & ~R8168_CPCMD_QUIRK_MASK);
1050 
1051 #define  PCI_EXP_DEVCTL_NOSNOOP_EN 0x0800  /* Enable No Snoop */
1052   rtl_tx_performance_tweak(pdev,
1053                            (0x5 << MAX_READ_REQUEST_SHIFT) | PCI_EXP_DEVCTL_NOSNOOP_EN);
1054 }
1055 
1056 static void rtl_hw_start_8168bef(void __iomem *ioaddr, struct pci_dev *pdev)
1057 {
1058   rtl_hw_start_8168bb(ioaddr, pdev);
1059 
1060   RTL_W8(EarlyTxThres, EarlyTxThld);
1061 
1062   RTL_W8(Config4, RTL_R8(Config4) & ~(1 << 0));
1063 }
1064 
1065 static void __rtl_hw_start_8168cp(void __iomem *ioaddr, struct pci_dev *pdev)
1066 {
1067   RTL_W8(Config1, RTL_R8(Config1) | Speed_down);
1068 
1069   RTL_W8(Config3, RTL_R8(Config3) & ~Beacon_en);
1070 
1071   rtl_tx_performance_tweak(pdev, 0x5 << MAX_READ_REQUEST_SHIFT);
1072 
1073   rtl_disable_clock_request(pdev);
1074 
1075   RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) & ~R8168_CPCMD_QUIRK_MASK);
1076 }
1077 
1078 static void rtl_hw_start_8168cp_1(void __iomem *ioaddr, struct pci_dev *pdev)
1079 {
1080   static const struct ephy_info e_info_8168cp[] = {
1081     { 0x01, 0,  0x0001 },
1082     { 0x02, 0x0800,     0x1000 },
1083     { 0x03, 0,  0x0042 },
1084     { 0x06, 0x0080,     0x0000 },
1085     { 0x07, 0,  0x2000 }
1086   };
1087 
1088   rtl_csi_access_enable(ioaddr);
1089 
1090   rtl_ephy_init(ioaddr, e_info_8168cp, ARRAY_SIZE(e_info_8168cp));
1091 
1092   __rtl_hw_start_8168cp(ioaddr, pdev);
1093 }
1094 
1095 static void rtl_hw_start_8168cp_2(void __iomem *ioaddr, struct pci_dev *pdev)
1096 {
1097   rtl_csi_access_enable(ioaddr);
1098 
1099   RTL_W8(Config3, RTL_R8(Config3) & ~Beacon_en);
1100 
1101   rtl_tx_performance_tweak(pdev, 0x5 << MAX_READ_REQUEST_SHIFT);
1102 
1103   RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) & ~R8168_CPCMD_QUIRK_MASK);
1104 }
1105 
1106 static void rtl_hw_start_8168cp_3(void __iomem *ioaddr, struct pci_dev *pdev)
1107 {
1108   rtl_csi_access_enable(ioaddr);
1109 
1110   RTL_W8(Config3, RTL_R8(Config3) & ~Beacon_en);
1111 
1112   /* Magic. */
1113   RTL_W8(DBG_REG, 0x20);
1114 
1115   RTL_W8(EarlyTxThres, EarlyTxThld);
1116 
1117   rtl_tx_performance_tweak(pdev, 0x5 << MAX_READ_REQUEST_SHIFT);
1118 
1119   RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) & ~R8168_CPCMD_QUIRK_MASK);
1120 }
1121 
1122 static void rtl_hw_start_8168c_1(void __iomem *ioaddr, struct pci_dev *pdev)
1123 {
1124   static const struct ephy_info e_info_8168c_1[] = {
1125     { 0x02, 0x0800,     0x1000 },
1126     { 0x03, 0,  0x0002 },
1127     { 0x06, 0x0080,     0x0000 }
1128   };
1129 
1130   rtl_csi_access_enable(ioaddr);
1131 
1132   RTL_W8(DBG_REG, 0x06 | FIX_NAK_1 | FIX_NAK_2);
1133 
1134   rtl_ephy_init(ioaddr, e_info_8168c_1, ARRAY_SIZE(e_info_8168c_1));
1135 
1136   __rtl_hw_start_8168cp(ioaddr, pdev);
1137 }
1138 
1139 static void rtl_hw_start_8168c_2(void __iomem *ioaddr, struct pci_dev *pdev)
1140 {
1141   static const struct ephy_info e_info_8168c_2[] = {
1142     { 0x01, 0,  0x0001 },
1143     { 0x03, 0x0400,     0x0220 }
1144   };
1145 
1146   rtl_csi_access_enable(ioaddr);
1147 
1148   rtl_ephy_init(ioaddr, e_info_8168c_2, ARRAY_SIZE(e_info_8168c_2));
1149 
1150   __rtl_hw_start_8168cp(ioaddr, pdev);
1151 }
1152 
1153 static void rtl_hw_start_8168c_3(void __iomem *ioaddr, struct pci_dev *pdev)
1154 {
1155   rtl_hw_start_8168c_2(ioaddr, pdev);
1156 }
1157 
1158 static void rtl_hw_start_8168c_4(void __iomem *ioaddr, struct pci_dev *pdev)
1159 {
1160   rtl_csi_access_enable(ioaddr);
1161 
1162   __rtl_hw_start_8168cp(ioaddr, pdev);
1163 }
1164 
1165 static void rtl_hw_start_8168d(void __iomem *ioaddr, struct pci_dev *pdev)
1166 {
1167   rtl_csi_access_enable(ioaddr);
1168 
1169   rtl_disable_clock_request(pdev);
1170 
1171   RTL_W8(EarlyTxThres, EarlyTxThld);
1172 
1173   rtl_tx_performance_tweak(pdev, 0x5 << MAX_READ_REQUEST_SHIFT);
1174 
1175   RTL_W16(CPlusCmd, RTL_R16(CPlusCmd) & ~R8168_CPCMD_QUIRK_MASK);
1176 }
1177 
1178 static void
1179 rtl_hw_start_8168(struct net_device *dev)
1180 {
1181   struct rtl8169_private *tp = netdev_priv(dev);
1182   void __iomem *ioaddr = tp->mmio_addr;
1183   struct pci_dev *pdev = tp->pci_dev;
1184 
1185   DLOG ("hw_start_8168 mac_version=0x%X", tp->mac_version);
1186 
1187   RTL_W8(Cfg9346, Cfg9346_Unlock);
1188 
1189   RTL_W8(EarlyTxThres, EarlyTxThld);
1190 
1191   rtl_set_rx_max_size(ioaddr, tp->rx_buf_sz);
1192 
1193   tp->cp_cmd |= RTL_R16(CPlusCmd) | PktCntrDisable | INTT_1;
1194 
1195   RTL_W16(CPlusCmd, tp->cp_cmd);
1196 
1197   RTL_W16(IntrMitigate, 0x5151);
1198 
1199   /* Work around for RxFIFO overflow. */
1200   if (tp->mac_version == RTL_GIGA_MAC_VER_11) {
1201     tp->intr_event |= RxFIFOOver | PCSTimeout;
1202     tp->intr_event &= ~RxOverflow;
1203   }
1204 
1205   rtl_set_rx_tx_desc_registers(tp, ioaddr);
1206 
1207   rtl_set_rx_mode(dev);
1208 
1209   RTL_W32(TxConfig, (TX_DMA_BURST << TxDMAShift) |
1210           (InterFrameGap << TxInterFrameGapShift));
1211 
1212   RTL_R8(IntrMask);
1213 
1214   switch (tp->mac_version) {
1215   case RTL_GIGA_MAC_VER_11:
1216     rtl_hw_start_8168bb(ioaddr, pdev);
1217     break;
1218 
1219   case RTL_GIGA_MAC_VER_12:
1220   case RTL_GIGA_MAC_VER_17:
1221     rtl_hw_start_8168bef(ioaddr, pdev);
1222     break;
1223 
1224   case RTL_GIGA_MAC_VER_18:
1225     rtl_hw_start_8168cp_1(ioaddr, pdev);
1226     break;
1227 
1228   case RTL_GIGA_MAC_VER_19:
1229     rtl_hw_start_8168c_1(ioaddr, pdev);
1230     break;
1231 
1232   case RTL_GIGA_MAC_VER_20:
1233     rtl_hw_start_8168c_2(ioaddr, pdev);
1234     break;
1235 
1236   case RTL_GIGA_MAC_VER_21:
1237     rtl_hw_start_8168c_3(ioaddr, pdev);
1238     break;
1239 
1240   case RTL_GIGA_MAC_VER_22:
1241     rtl_hw_start_8168c_4(ioaddr, pdev);
1242     break;
1243 
1244   case RTL_GIGA_MAC_VER_23:
1245     rtl_hw_start_8168cp_2(ioaddr, pdev);
1246     break;
1247 
1248   case RTL_GIGA_MAC_VER_24:
1249     rtl_hw_start_8168cp_3(ioaddr, pdev);
1250     break;
1251 
1252   case RTL_GIGA_MAC_VER_25:
1253   case RTL_GIGA_MAC_VER_26:
1254   case RTL_GIGA_MAC_VER_27:
1255     rtl_hw_start_8168d(ioaddr, pdev);
1256     break;
1257 
1258   default:
1259     DLOG("unknown chipset (mac_version = %d).",
1260          tp->mac_version);
1261     break;
1262   }
1263 
1264   RTL_W8(ChipCmd, CmdTxEnb | CmdRxEnb);
1265 
1266   RTL_W8(Cfg9346, Cfg9346_Lock);
1267 
1268   RTL_W16(MultiIntr, RTL_R16(MultiIntr) & 0xF000);
1269 
1270   DLOG ("IntrMask <- 0x%.04X", tp->intr_event);
1271   RTL_W16(IntrMask, tp->intr_event);
1272 }
1273 
1274 static void
1275 rtl_hw_start_8101(struct net_device *dev)
1276 {
1277 #if 0
1278   struct rtl8169_private *tp = netdev_priv(dev);
1279   void __iomem *ioaddr = tp->mmio_addr;
1280   struct pci_dev *pdev = tp->pci_dev;
1281 
1282   if ((tp->mac_version == RTL_GIGA_MAC_VER_13) ||
1283       (tp->mac_version == RTL_GIGA_MAC_VER_16)) {
1284     int cap = tp->pcie_cap;
1285 
1286     if (cap) {
1287       pci_write_config_word(pdev, cap + PCI_EXP_DEVCTL,
1288                             PCI_EXP_DEVCTL_NOSNOOP_EN);
1289     }
1290   }
1291 
1292   switch (tp->mac_version) {
1293   case RTL_GIGA_MAC_VER_07:
1294     rtl_hw_start_8102e_1(ioaddr, pdev);
1295     break;
1296 
1297   case RTL_GIGA_MAC_VER_08:
1298     rtl_hw_start_8102e_3(ioaddr, pdev);
1299     break;
1300 
1301   case RTL_GIGA_MAC_VER_09:
1302     rtl_hw_start_8102e_2(ioaddr, pdev);
1303     break;
1304   }
1305 
1306   RTL_W8(Cfg9346, Cfg9346_Unlock);
1307 
1308   RTL_W8(EarlyTxThres, EarlyTxThld);
1309 
1310   rtl_set_rx_max_size(ioaddr, tp->rx_buf_sz);
1311 
1312   tp->cp_cmd |= rtl_rw_cpluscmd(ioaddr) | PCIMulRW;
1313 
1314   RTL_W16(CPlusCmd, tp->cp_cmd);
1315 
1316   RTL_W16(IntrMitigate, 0x0000);
1317 
1318   rtl_set_rx_tx_desc_registers(tp, ioaddr);
1319 
1320   RTL_W8(ChipCmd, CmdTxEnb | CmdRxEnb);
1321   rtl_set_rx_tx_config_registers(tp);
1322 
1323   RTL_W8(Cfg9346, Cfg9346_Lock);
1324 
1325   RTL_R8(IntrMask);
1326 
1327   rtl_set_rx_mode(dev);
1328 
1329   RTL_W8(ChipCmd, CmdTxEnb | CmdRxEnb);
1330 
1331   RTL_W16(MultiIntr, RTL_R16(MultiIntr) & 0xf000);
1332 
1333   RTL_W16(IntrMask, tp->intr_event);
1334 #endif
1335   DLOG ("8101 not supported");
1336 }
1337 
1338 static int
1339 rtl8169_set_speed_tbi(struct net_device *dev,
1340                       u8 autoneg, u16 speed, u8 duplex)
1341 {
1342   return 0;
1343 }
1344 
1345 static int rtl8169_set_speed_xmii(struct net_device *dev,
1346                                   u8 autoneg, u16 speed, u8 duplex)
1347 {
1348   struct rtl8169_private *tp = netdev_priv(dev);
1349   void __iomem *ioaddr = tp->mmio_addr;
1350   int giga_ctrl, bmcr;
1351 
1352   if (autoneg == AUTONEG_ENABLE) {
1353     int auto_nego;
1354 
1355     auto_nego = mdio_read(ioaddr, MII_ADVERTISE);
1356     auto_nego |= (ADVERTISE_10HALF | ADVERTISE_10FULL |
1357                   ADVERTISE_100HALF | ADVERTISE_100FULL);
1358     auto_nego |= ADVERTISE_PAUSE_CAP | ADVERTISE_PAUSE_ASYM;
1359 
1360     giga_ctrl = mdio_read(ioaddr, MII_CTRL1000);
1361     giga_ctrl &= ~(ADVERTISE_1000FULL | ADVERTISE_1000HALF);
1362 
1363     /* The 8100e/8101e/8102e do Fast Ethernet only. */
1364     if ((tp->mac_version != RTL_GIGA_MAC_VER_07) &&
1365         (tp->mac_version != RTL_GIGA_MAC_VER_08) &&
1366         (tp->mac_version != RTL_GIGA_MAC_VER_09) &&
1367         (tp->mac_version != RTL_GIGA_MAC_VER_10) &&
1368         (tp->mac_version != RTL_GIGA_MAC_VER_13) &&
1369         (tp->mac_version != RTL_GIGA_MAC_VER_14) &&
1370         (tp->mac_version != RTL_GIGA_MAC_VER_15) &&
1371         (tp->mac_version != RTL_GIGA_MAC_VER_16)) {
1372       giga_ctrl |= ADVERTISE_1000FULL | ADVERTISE_1000HALF;
1373     } else {
1374       DLOG("PHY does not support 1000Mbps");
1375     }
1376 
1377     bmcr = BMCR_ANENABLE | BMCR_ANRESTART;
1378 
1379     if ((tp->mac_version == RTL_GIGA_MAC_VER_11) ||
1380         (tp->mac_version == RTL_GIGA_MAC_VER_12) ||
1381         (tp->mac_version >= RTL_GIGA_MAC_VER_17)) {
1382       /*
1383        * Wake up the PHY.
1384        * Vendor specific (0x1f) and reserved (0x0e) MII
1385        * registers.
1386        */
1387       mdio_write(ioaddr, 0x1f, 0x0000);
1388       mdio_write(ioaddr, 0x0e, 0x0000);
1389     }
1390 
1391     mdio_write(ioaddr, MII_ADVERTISE, auto_nego);
1392     mdio_write(ioaddr, MII_CTRL1000, giga_ctrl);
1393   } else {
1394     giga_ctrl = 0;
1395 
1396     if (speed == SPEED_10)
1397       bmcr = 0;
1398     else if (speed == SPEED_100)
1399       bmcr = BMCR_SPEED100;
1400     else
1401       return -1;
1402 
1403     if (duplex == DUPLEX_FULL)
1404       bmcr |= BMCR_FULLDPLX;
1405 
1406     mdio_write(ioaddr, 0x1f, 0x0000);
1407   }
1408 
1409   tp->phy_1000_ctrl_reg = giga_ctrl;
1410 
1411   mdio_write(ioaddr, MII_BMCR, bmcr);
1412   DLOG ("set_speed_xmii: bmcr=0x%p", bmcr);
1413 
1414   if ((tp->mac_version == RTL_GIGA_MAC_VER_02) ||
1415       (tp->mac_version == RTL_GIGA_MAC_VER_03)) {
1416     if ((speed == SPEED_100) && (autoneg != AUTONEG_ENABLE)) {
1417       mdio_write(ioaddr, 0x17, 0x2138);
1418       mdio_write(ioaddr, 0x0e, 0x0260);
1419     } else {
1420       mdio_write(ioaddr, 0x17, 0x2108);
1421       mdio_write(ioaddr, 0x0e, 0x0000);
1422     }
1423   }
1424 
1425   return 0;
1426 }
1427 
1428 
1429 static int
1430 rtl8169_gset_tbi(struct net_device *dev, struct ethtool_cmd *cmd)
1431 {
1432 #if 0
1433   struct rtl8169_private *tp = netdev_priv(dev);
1434   void __iomem *ioaddr = tp->mmio_addr;
1435   u32 status;
1436 
1437   cmd->supported =
1438     SUPPORTED_1000baseT_Full | SUPPORTED_Autoneg | SUPPORTED_FIBRE;
1439   cmd->port = PORT_FIBRE;
1440   cmd->transceiver = XCVR_INTERNAL;
1441 
1442   status = RTL_R32(TBICSR);
1443   cmd->advertising = (status & TBINwEnable) ?  ADVERTISED_Autoneg : 0;
1444   cmd->autoneg = !!(status & TBINwEnable);
1445 
1446   cmd->speed = SPEED_1000;
1447   cmd->duplex = DUPLEX_FULL; /* Always set */
1448 #endif
1449   return 0;
1450 }
1451 
1452 static int rtl8169_gset_xmii(struct net_device *dev, struct ethtool_cmd *cmd)
1453 {
1454 #if 0
1455   struct rtl8169_private *tp = netdev_priv(dev);
1456 
1457   return mii_ethtool_gset(&tp->mii, cmd);
1458 #endif
1459   return 0;
1460 }
1461 
1462 static unsigned int
1463 rtl8169_tbi_reset_pending(void __iomem *ioaddr)
1464 {
1465   return RTL_R32(TBICSR) & TBIReset;
1466 }
1467 
1468 static unsigned int
1469 rtl8169_xmii_reset_pending(void __iomem *ioaddr)
1470 {
1471   return mdio_read(ioaddr, MII_BMCR) & BMCR_RESET;
1472 }
1473 
1474 static unsigned int
1475 rtl8169_tbi_link_ok(void __iomem *ioaddr)
1476 {
1477   return RTL_R32(TBICSR) & TBILinkOk;
1478 }
1479 
1480 static unsigned int
1481 rtl8169_xmii_link_ok(void __iomem *ioaddr)
1482 {
1483   return RTL_R8(PHYstatus) & LinkStatus;
1484 }
1485 
1486 static void
1487 rtl8169_tbi_reset_enable(void __iomem *ioaddr)
1488 {
1489   RTL_W32(TBICSR, RTL_R32(TBICSR) | TBIReset);
1490 }
1491 
1492 static void
1493 rtl8169_xmii_reset_enable(void __iomem *ioaddr)
1494 {
1495   unsigned int val;
1496 
1497   val = mdio_read(ioaddr, MII_BMCR) | BMCR_RESET;
1498   mdio_write(ioaddr, MII_BMCR, val & 0xffff);
1499 }
1500 
1501 static void
1502 rtl8169_check_link_status(struct net_device *dev,
1503                           struct rtl8169_private *tp,
1504                           void __iomem *ioaddr)
1505 {
1506   spinlock_lock(&tp->lock);
1507   if (tp->link_ok(ioaddr)) {
1508     DLOG ("link up");
1509   } else {
1510     DLOG ("link down");
1511   }
1512   spinlock_unlock(&tp->lock);
1513 }
1514 
1515 static int
1516 rtl_tbi_ioctl(struct rtl8169_private *tp, struct mii_ioctl_data *data, int cmd)
1517 {
1518   return -1;
1519 }
1520 
1521 static int
1522 rtl_xmii_ioctl(struct rtl8169_private *tp, struct mii_ioctl_data *data, int cmd)
1523 {
1524 #if 0
1525   switch (cmd) {
1526   case SIOCGMIIPHY:
1527     data->phy_id = 32; /* Internal PHY */
1528     return 0;
1529 
1530   case SIOCGMIIREG:
1531     data->val_out = mdio_read(tp->mmio_addr, data->reg_num & 0x1f);
1532     return 0;
1533 
1534   case SIOCSMIIREG:
1535     mdio_write(tp->mmio_addr, data->reg_num & 0x1f, data->val_in);
1536     return 0;
1537   }
1538 #endif
1539   return -1;
1540 }
1541 
1542 
1543 
1544 static const struct rtl_cfg_info {
1545   void (*hw_start)(struct net_device *);
1546   unsigned int region;
1547   unsigned int align;
1548   u16 intr_event;
1549   u16 napi_event;
1550   unsigned features;
1551   u8 default_ver;
1552 } rtl_cfg_infos [] = {
1553   [RTL_CFG_0] = {
1554     .hw_start    = rtl_hw_start_8169,
1555     .region      = 1,
1556     .align       = 0,
1557     .intr_event  = SYSErr | LinkChg | RxOverflow | RxFIFOOver | TxErr | TxOK | RxOK | RxErr,
1558     .napi_event  = RxFIFOOver | TxErr | TxOK | RxOK | RxOverflow,
1559     .features    = RTL_FEATURE_GMII,
1560     .default_ver = RTL_GIGA_MAC_VER_01,
1561   },
1562   [RTL_CFG_1] = {
1563     .hw_start    = rtl_hw_start_8168,
1564     .region      = 2,
1565     .align       = 8,
1566     .intr_event  = SYSErr | RxFIFOOver | LinkChg | RxOverflow | TxErr | TxOK | RxOK | RxErr,
1567     .napi_event  = TxErr | TxOK | RxOK | RxOverflow,
1568     .features    = RTL_FEATURE_GMII | RTL_FEATURE_MSI,
1569     .default_ver = RTL_GIGA_MAC_VER_11,
1570   },
1571   [RTL_CFG_2] = {
1572     .hw_start    = rtl_hw_start_8101,
1573     .region      = 2,
1574     .align       = 8,
1575     .intr_event  = SYSErr | LinkChg | RxOverflow | PCSTimeout | RxFIFOOver | TxErr | TxOK | RxOK | RxErr,
1576     .napi_event  = RxFIFOOver | TxErr | TxOK | RxOK | RxOverflow,
1577     .features    = RTL_FEATURE_MSI,
1578     .default_ver = RTL_GIGA_MAC_VER_13,
1579   }
1580 };
1581 
1582 static uint device_index;
1583 static pci_device pdev;
1584 
1585 static inline void rtl8169_mark_to_asic(struct RxDesc *desc, u32 rx_buf_sz);
1586 
1587 #define MIN(a,b) ((a) < (b) ? (a) : (b))
1588 static void
1589 rx_int (struct rtl8169_private *tp)
1590 {
1591   uint cur_rx;
1592 
1593   cur_rx = tp->cur_rx;
1594   for (;;) {
1595     uint entry = cur_rx & (NUM_RX_DESC - 1);
1596     struct RxDesc *desc = tp->RxDescArray + entry;
1597     u32 status;
1598 
1599     status = __le32_to_cpu (desc->opts1);
1600     if (status & DescOwn)
1601       break;
1602     else {
1603       struct sk_buff *skb = tp->Rx_skbuff[entry];
1604       int pkt_size = (status & 0x00001FFF) - 4;
1605       DLOG ("RX: entry=%d size=%d", entry, pkt_size);
1606       u8 *p = skb->data;
1607       DLOG ("  %.02X %.02X %.02X %.02X %.02X %.02X",
1608             p[0], p[1], p[2], p[3], p[4], p[5]);
1609       p+=6;
1610       DLOG ("  %.02X %.02X %.02X %.02X %.02X %.02X",
1611             p[0], p[1], p[2], p[3], p[4], p[5]);
1612       if (tp->ethdev.recv_func)
1613         tp->ethdev.recv_func (&tp->ethdev, skb->data, pkt_size);
1614       rtl8169_mark_to_asic(desc, tp->rx_buf_sz);
1615     }
1616     cur_rx++;
1617   }
1618   tp->cur_rx = cur_rx;
1619 }
1620 
1621 static inline void free_skb (struct sk_buff *);
1622 static void
1623 tx_int (struct rtl8169_private *tp)
1624 {
1625   void __iomem *ioaddr = tp->mmio_addr;
1626   uint dirty_tx, tx_left;
1627   dirty_tx = tp->dirty_tx;
1628   tx_left = tp->cur_tx - dirty_tx;
1629   while (tx_left > 0) {
1630     uint entry = dirty_tx & (NUM_TX_DESC - 1);
1631     struct ring_info *tx_skb = tp->tx_skb + entry;
1632     struct TxDesc *desc = tp->TxDescArray + entry;
1633     u32 status;
1634 
1635     status = __le32_to_cpu(tp->TxDescArray[entry].opts1);
1636     if (status & DescOwn)
1637       break;
1638 
1639     DLOG ("TX: entry %d sent %d bytes", entry, tx_skb->len);
1640     desc->opts1 = desc->opts2 = desc->addr = 0;
1641     tx_skb->len = 0;
1642     free_skb (tx_skb->skb);
1643 
1644     dirty_tx++;
1645     tx_left--;
1646   }
1647   if (tp->dirty_tx != dirty_tx) {
1648     tp->dirty_tx = dirty_tx;
1649     /*
1650      * 8168 hack: TxPoll requests are lost when the Tx packets are
1651      * too close. Let's kick an extra TxPoll request when a burst
1652      * of start_xmit activity is detected (if it is not detected,
1653      * it is slow enough). -- FR
1654      */
1655     if (tp->cur_tx != dirty_tx)
1656       RTL_W8(TxPoll, NPQ);
1657   }
1658 }
1659 
1660 static u32 r8169_bh_stack[1024] ALIGNED (0x1000);
1661 static task_id r8169_bh_id = 0;
1662 static void
1663 r8169_bh_thread (void)
1664 {
1665   logger_printf ("r8169: bh: hello from 0x%x\n", str ());
1666   for (;;) {
1667     struct rtl8169_private *tp = pci_get_drvdata(&pdev);
1668     int handled = 0;
1669     int status;
1670     void __iomem *ioaddr = tp->mmio_addr;
1671 
1672     status = RTL_R16(IntrStatus);
1673 
1674     while (status && status != 0xffff) {
1675       DLOG ("IRQ status=0x%p", status);
1676       handled = 1;
1677 
1678       /* Handle all of the error cases first. These will reset
1679        * the chip, so just exit the loop.
1680        */
1681 
1682       /* Work around for rx fifo overflow */
1683       if (unlikely(status & RxFIFOOver)) {
1684         //netif_stop_queue(dev);
1685         //rtl8169_tx_timeout(&tp->ethdev);
1686         break;
1687       }
1688 
1689       if (unlikely(status & SYSErr)) {
1690         //rtl8169_pcierr_interrupt(&tp->ethdev);
1691         break;
1692       }
1693 
1694       if (status & LinkChg)
1695         rtl8169_check_link_status(&tp->ethdev, tp, ioaddr);
1696 
1697       if (status & RxOK) {
1698         rx_int (tp);
1699       }
1700 
1701       if (status & TxOK) {
1702         tx_int (tp);
1703       }
1704 
1705       /* We only get a new MSI interrupt when all active irq
1706        * sources on the chip have been acknowledged. So, ack
1707        * everything we've seen and check if new sources have become
1708        * active to avoid blocking all interrupts from the chip.
1709        */
1710       RTL_W16(IntrStatus,
1711               (status & RxFIFOOver) ? (status | RxOverflow) : status);
1712       status = RTL_R16(IntrStatus);
1713     }
1714 
1715     iovcpu_job_completion ();
1716   }
1717 }
1718 
1719 #ifdef TX_TIMING
1720 static u64 tx_start = 0, tx_finish;
1721 #endif
1722 
1723 static uint
1724 irq_handler (u8 vec)
1725 {
1726 #ifdef TX_TIMING
1727   /* assume tx_start != 0 means this is TX IRQ */
1728   if (tx_start > 0) {
1729     SERIALIZE0;
1730     RDTSC (tx_finish);
1731     logger_printf ("r8169: TX: IRQ received: diff=0x%llX\n", tx_finish - tx_start);
1732     tx_start = 0;
1733   }
1734 #endif
1735 
1736   if (r8169_bh_id) {
1737     extern vcpu *vcpu_lookup (int);
1738     /* hack: use VCPU2's period */
1739     iovcpu_job_wakeup (r8169_bh_id, vcpu_lookup (2)->T);
1740   }
1741 
1742   return 0;
1743 }
1744 
1745 static void
1746 get_mac_version(struct rtl8169_private *tp,
1747                 void __iomem *ioaddr)
1748 {
1749   /*
1750    * The driver currently handles the 8168Bf and the 8168Be identically
1751    * but they can be identified more specifically through the test below
1752    * if needed:
1753    *
1754    * (RTL_R32(TxConfig) & 0x700000) == 0x500000 ? 8168Bf : 8168Be
1755    *
1756    * Same thing for the 8101Eb and the 8101Ec:
1757    *
1758    * (RTL_R32(TxConfig) & 0x700000) == 0x200000 ? 8101Eb : 8101Ec
1759    */
1760   static const struct {
1761     u32 mask;
1762     u32 val;
1763     int mac_version;
1764   } mac_info[] = {
1765     /* 8168D family. */
1766     { 0x7cf00000, 0x28300000,   RTL_GIGA_MAC_VER_26 },
1767     { 0x7cf00000, 0x28100000,   RTL_GIGA_MAC_VER_25 },
1768     { 0x7c800000, 0x28800000,   RTL_GIGA_MAC_VER_27 },
1769     { 0x7c800000, 0x28000000,   RTL_GIGA_MAC_VER_26 },
1770 
1771     /* 8168C family. */
1772     { 0x7cf00000, 0x3cb00000,   RTL_GIGA_MAC_VER_24 },
1773     { 0x7cf00000, 0x3c900000,   RTL_GIGA_MAC_VER_23 },
1774     { 0x7cf00000, 0x3c800000,   RTL_GIGA_MAC_VER_18 },
1775     { 0x7c800000, 0x3c800000,   RTL_GIGA_MAC_VER_24 },
1776     { 0x7cf00000, 0x3c000000,   RTL_GIGA_MAC_VER_19 },
1777     { 0x7cf00000, 0x3c200000,   RTL_GIGA_MAC_VER_20 },
1778     { 0x7cf00000, 0x3c300000,   RTL_GIGA_MAC_VER_21 },
1779     { 0x7cf00000, 0x3c400000,   RTL_GIGA_MAC_VER_22 },
1780     { 0x7c800000, 0x3c000000,   RTL_GIGA_MAC_VER_22 },
1781 
1782     /* 8168B family. */
1783     { 0x7cf00000, 0x38000000,   RTL_GIGA_MAC_VER_12 },
1784     { 0x7cf00000, 0x38500000,   RTL_GIGA_MAC_VER_17 },
1785     { 0x7c800000, 0x38000000,   RTL_GIGA_MAC_VER_17 },
1786     { 0x7c800000, 0x30000000,   RTL_GIGA_MAC_VER_11 },
1787 
1788     /* 8101 family. */
1789     { 0x7cf00000, 0x34a00000,   RTL_GIGA_MAC_VER_09 },
1790     { 0x7cf00000, 0x24a00000,   RTL_GIGA_MAC_VER_09 },
1791     { 0x7cf00000, 0x34900000,   RTL_GIGA_MAC_VER_08 },
1792     { 0x7cf00000, 0x24900000,   RTL_GIGA_MAC_VER_08 },
1793     { 0x7cf00000, 0x34800000,   RTL_GIGA_MAC_VER_07 },
1794     { 0x7cf00000, 0x24800000,   RTL_GIGA_MAC_VER_07 },
1795     { 0x7cf00000, 0x34000000,   RTL_GIGA_MAC_VER_13 },
1796     { 0x7cf00000, 0x34300000,   RTL_GIGA_MAC_VER_10 },
1797     { 0x7cf00000, 0x34200000,   RTL_GIGA_MAC_VER_16 },
1798     { 0x7c800000, 0x34800000,   RTL_GIGA_MAC_VER_09 },
1799     { 0x7c800000, 0x24800000,   RTL_GIGA_MAC_VER_09 },
1800     { 0x7c800000, 0x34000000,   RTL_GIGA_MAC_VER_16 },
1801     /* FIXME: where did these entries come from ? -- FR */
1802     { 0xfc800000, 0x38800000,   RTL_GIGA_MAC_VER_15 },
1803     { 0xfc800000, 0x30800000,   RTL_GIGA_MAC_VER_14 },
1804 
1805     /* 8110 family. */
1806     { 0xfc800000, 0x98000000,   RTL_GIGA_MAC_VER_06 },
1807     { 0xfc800000, 0x18000000,   RTL_GIGA_MAC_VER_05 },
1808     { 0xfc800000, 0x10000000,   RTL_GIGA_MAC_VER_04 },
1809     { 0xfc800000, 0x04000000,   RTL_GIGA_MAC_VER_03 },
1810     { 0xfc800000, 0x00800000,   RTL_GIGA_MAC_VER_02 },
1811     { 0xfc800000, 0x00000000,   RTL_GIGA_MAC_VER_01 },
1812 
1813     /* Catch-all */
1814     { 0x00000000, 0x00000000,   RTL_GIGA_MAC_NONE   }
1815   }, *p = mac_info;
1816   u32 reg;
1817 
1818   reg = RTL_R32(TxConfig);
1819   while ((reg & p->mask) != p->val)
1820     p++;
1821   tp->mac_version = p->mac_version;
1822 }
1823 
1824 static void
1825 print_mac_version(struct rtl8169_private *tp)
1826 {
1827   DLOG ("mac_version = 0x%02x", tp->mac_version);
1828 }
1829 
1830 struct phy_reg {
1831   u16 reg;
1832   u16 val;
1833 };
1834 
1835 static void rtl_phy_write(void __iomem *ioaddr, const struct phy_reg *regs, int len)
1836 {
1837   while (len-- > 0) {
1838     mdio_write(ioaddr, regs->reg, regs->val);
1839     regs++;
1840   }
1841 }
1842 
1843 static void rtl8169s_hw_phy_config(void __iomem *ioaddr)
1844 {
1845   static const struct phy_reg phy_reg_init[] = {
1846     { 0x1f, 0x0001 },
1847     { 0x06, 0x006e },
1848     { 0x08, 0x0708 },
1849     { 0x15, 0x4000 },
1850     { 0x18, 0x65c7 },
1851 
1852     { 0x1f, 0x0001 },
1853     { 0x03, 0x00a1 },
1854     { 0x02, 0x0008 },
1855     { 0x01, 0x0120 },
1856     { 0x00, 0x1000 },
1857     { 0x04, 0x0800 },
1858     { 0x04, 0x0000 },
1859 
1860     { 0x03, 0xff41 },
1861     { 0x02, 0xdf60 },
1862     { 0x01, 0x0140 },
1863     { 0x00, 0x0077 },
1864     { 0x04, 0x7800 },
1865     { 0x04, 0x7000 },
1866 
1867     { 0x03, 0x802f },
1868     { 0x02, 0x4f02 },
1869     { 0x01, 0x0409 },
1870     { 0x00, 0xf0f9 },
1871     { 0x04, 0x9800 },
1872     { 0x04, 0x9000 },
1873 
1874     { 0x03, 0xdf01 },
1875     { 0x02, 0xdf20 },
1876     { 0x01, 0xff95 },
1877     { 0x00, 0xba00 },
1878     { 0x04, 0xa800 },
1879     { 0x04, 0xa000 },
1880 
1881     { 0x03, 0xff41 },
1882     { 0x02, 0xdf20 },
1883     { 0x01, 0x0140 },
1884     { 0x00, 0x00bb },
1885     { 0x04, 0xb800 },
1886     { 0x04, 0xb000 },
1887 
1888     { 0x03, 0xdf41 },
1889     { 0x02, 0xdc60 },
1890     { 0x01, 0x6340 },
1891     { 0x00, 0x007d },
1892     { 0x04, 0xd800 },
1893     { 0x04, 0xd000 },
1894 
1895     { 0x03, 0xdf01 },
1896     { 0x02, 0xdf20 },
1897     { 0x01, 0x100a },
1898     { 0x00, 0xa0ff },
1899     { 0x04, 0xf800 },
1900     { 0x04, 0xf000 },
1901 
1902     { 0x1f, 0x0000 },
1903     { 0x0b, 0x0000 },
1904     { 0x00, 0x9200 }
1905   };
1906 
1907   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
1908 }
1909 
1910 static void rtl8169sb_hw_phy_config(void __iomem *ioaddr)
1911 {
1912   static const struct phy_reg phy_reg_init[] = {
1913     { 0x1f, 0x0002 },
1914     { 0x01, 0x90d0 },
1915     { 0x1f, 0x0000 }
1916   };
1917 
1918   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
1919 }
1920 
1921 static void rtl8169scd_hw_phy_config_quirk(struct rtl8169_private *tp,
1922                                            void __iomem *ioaddr)
1923 {
1924   struct pci_dev *pdev = tp->pci_dev;
1925   u16 vendor_id, device_id;
1926 
1927   pci_read_config_word(pdev, PCI_SUBSYSTEM_VENDOR_ID, &vendor_id);
1928   pci_read_config_word(pdev, PCI_SUBSYSTEM_ID, &device_id);
1929 
1930   if ((vendor_id != PCI_VENDOR_ID_GIGABYTE) || (device_id != 0xe000))
1931     return;
1932 
1933   mdio_write(ioaddr, 0x1f, 0x0001);
1934   mdio_write(ioaddr, 0x10, 0xf01b);
1935   mdio_write(ioaddr, 0x1f, 0x0000);
1936 }
1937 
1938 static void rtl8169scd_hw_phy_config(struct rtl8169_private *tp,
1939                                      void __iomem *ioaddr)
1940 {
1941   static const struct phy_reg phy_reg_init[] = {
1942     { 0x1f, 0x0001 },
1943     { 0x04, 0x0000 },
1944     { 0x03, 0x00a1 },
1945     { 0x02, 0x0008 },
1946     { 0x01, 0x0120 },
1947     { 0x00, 0x1000 },
1948     { 0x04, 0x0800 },
1949     { 0x04, 0x9000 },
1950     { 0x03, 0x802f },
1951     { 0x02, 0x4f02 },
1952     { 0x01, 0x0409 },
1953     { 0x00, 0xf099 },
1954     { 0x04, 0x9800 },
1955     { 0x04, 0xa000 },
1956     { 0x03, 0xdf01 },
1957     { 0x02, 0xdf20 },
1958     { 0x01, 0xff95 },
1959     { 0x00, 0xba00 },
1960     { 0x04, 0xa800 },
1961     { 0x04, 0xf000 },
1962     { 0x03, 0xdf01 },
1963     { 0x02, 0xdf20 },
1964     { 0x01, 0x101a },
1965     { 0x00, 0xa0ff },
1966     { 0x04, 0xf800 },
1967     { 0x04, 0x0000 },
1968     { 0x1f, 0x0000 },
1969 
1970     { 0x1f, 0x0001 },
1971     { 0x10, 0xf41b },
1972     { 0x14, 0xfb54 },
1973     { 0x18, 0xf5c7 },
1974     { 0x1f, 0x0000 },
1975 
1976     { 0x1f, 0x0001 },
1977     { 0x17, 0x0cc0 },
1978     { 0x1f, 0x0000 }
1979   };
1980 
1981   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
1982 
1983   rtl8169scd_hw_phy_config_quirk(tp, ioaddr);
1984 }
1985 
1986 static void rtl8169sce_hw_phy_config(void __iomem *ioaddr)
1987 {
1988   static const struct phy_reg phy_reg_init[] = {
1989     { 0x1f, 0x0001 },
1990     { 0x04, 0x0000 },
1991     { 0x03, 0x00a1 },
1992     { 0x02, 0x0008 },
1993     { 0x01, 0x0120 },
1994     { 0x00, 0x1000 },
1995     { 0x04, 0x0800 },
1996     { 0x04, 0x9000 },
1997     { 0x03, 0x802f },
1998     { 0x02, 0x4f02 },
1999     { 0x01, 0x0409 },
2000     { 0x00, 0xf099 },
2001     { 0x04, 0x9800 },
2002     { 0x04, 0xa000 },
2003     { 0x03, 0xdf01 },
2004     { 0x02, 0xdf20 },
2005     { 0x01, 0xff95 },
2006     { 0x00, 0xba00 },
2007     { 0x04, 0xa800 },
2008     { 0x04, 0xf000 },
2009     { 0x03, 0xdf01 },
2010     { 0x02, 0xdf20 },
2011     { 0x01, 0x101a },
2012     { 0x00, 0xa0ff },
2013     { 0x04, 0xf800 },
2014     { 0x04, 0x0000 },
2015     { 0x1f, 0x0000 },
2016 
2017     { 0x1f, 0x0001 },
2018     { 0x0b, 0x8480 },
2019     { 0x1f, 0x0000 },
2020 
2021     { 0x1f, 0x0001 },
2022     { 0x18, 0x67c7 },
2023     { 0x04, 0x2000 },
2024     { 0x03, 0x002f },
2025     { 0x02, 0x4360 },
2026     { 0x01, 0x0109 },
2027     { 0x00, 0x3022 },
2028     { 0x04, 0x2800 },
2029     { 0x1f, 0x0000 },
2030 
2031     { 0x1f, 0x0001 },
2032     { 0x17, 0x0cc0 },
2033     { 0x1f, 0x0000 }
2034   };
2035 
2036   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2037 }
2038 
2039 static void rtl8168bb_hw_phy_config(void __iomem *ioaddr)
2040 {
2041   static const struct phy_reg phy_reg_init[] = {
2042     { 0x10, 0xf41b },
2043     { 0x1f, 0x0000 }
2044   };
2045 
2046   mdio_write(ioaddr, 0x1f, 0x0001);
2047   mdio_patch(ioaddr, 0x16, 1 << 0);
2048 
2049   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2050 }
2051 
2052 static void rtl8168bef_hw_phy_config(void __iomem *ioaddr)
2053 {
2054   static const struct phy_reg phy_reg_init[] = {
2055     { 0x1f, 0x0001 },
2056     { 0x10, 0xf41b },
2057     { 0x1f, 0x0000 }
2058   };
2059 
2060   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2061 }
2062 
2063 static void rtl8168cp_1_hw_phy_config(void __iomem *ioaddr)
2064 {
2065   static const struct phy_reg phy_reg_init[] = {
2066     { 0x1f, 0x0000 },
2067     { 0x1d, 0x0f00 },
2068     { 0x1f, 0x0002 },
2069     { 0x0c, 0x1ec8 },
2070     { 0x1f, 0x0000 }
2071   };
2072 
2073   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2074 }
2075 
2076 static void rtl8168cp_2_hw_phy_config(void __iomem *ioaddr)
2077 {
2078   static const struct phy_reg phy_reg_init[] = {
2079     { 0x1f, 0x0001 },
2080     { 0x1d, 0x3d98 },
2081     { 0x1f, 0x0000 }
2082   };
2083 
2084   mdio_write(ioaddr, 0x1f, 0x0000);
2085   mdio_patch(ioaddr, 0x14, 1 << 5);
2086   mdio_patch(ioaddr, 0x0d, 1 << 5);
2087 
2088   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2089 }
2090 
2091 static void rtl8168c_1_hw_phy_config(void __iomem *ioaddr)
2092 {
2093   static const struct phy_reg phy_reg_init[] = {
2094     { 0x1f, 0x0001 },
2095     { 0x12, 0x2300 },
2096     { 0x1f, 0x0002 },
2097     { 0x00, 0x88d4 },
2098     { 0x01, 0x82b1 },
2099     { 0x03, 0x7002 },
2100     { 0x08, 0x9e30 },
2101     { 0x09, 0x01f0 },
2102     { 0x0a, 0x5500 },
2103     { 0x0c, 0x00c8 },
2104     { 0x1f, 0x0003 },
2105     { 0x12, 0xc096 },
2106     { 0x16, 0x000a },
2107     { 0x1f, 0x0000 },
2108     { 0x1f, 0x0000 },
2109     { 0x09, 0x2000 },
2110     { 0x09, 0x0000 }
2111   };
2112 
2113   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2114 
2115   mdio_patch(ioaddr, 0x14, 1 << 5);
2116   mdio_patch(ioaddr, 0x0d, 1 << 5);
2117   mdio_write(ioaddr, 0x1f, 0x0000);
2118 }
2119 
2120 static void rtl8168c_2_hw_phy_config(void __iomem *ioaddr)
2121 {
2122   static const struct phy_reg phy_reg_init[] = {
2123     { 0x1f, 0x0001 },
2124     { 0x12, 0x2300 },
2125     { 0x03, 0x802f },
2126     { 0x02, 0x4f02 },
2127     { 0x01, 0x0409 },
2128     { 0x00, 0xf099 },
2129     { 0x04, 0x9800 },
2130     { 0x04, 0x9000 },
2131     { 0x1d, 0x3d98 },
2132     { 0x1f, 0x0002 },
2133     { 0x0c, 0x7eb8 },
2134     { 0x06, 0x0761 },
2135     { 0x1f, 0x0003 },
2136     { 0x16, 0x0f0a },
2137     { 0x1f, 0x0000 }
2138   };
2139 
2140   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2141 
2142   mdio_patch(ioaddr, 0x16, 1 << 0);
2143   mdio_patch(ioaddr, 0x14, 1 << 5);
2144   mdio_patch(ioaddr, 0x0d, 1 << 5);
2145   mdio_write(ioaddr, 0x1f, 0x0000);
2146 }
2147 
2148 static void rtl8168c_3_hw_phy_config(void __iomem *ioaddr)
2149 {
2150   static const struct phy_reg phy_reg_init[] = {
2151     { 0x1f, 0x0001 },
2152     { 0x12, 0x2300 },
2153     { 0x1d, 0x3d98 },
2154     { 0x1f, 0x0002 },
2155     { 0x0c, 0x7eb8 },
2156     { 0x06, 0x5461 },
2157     { 0x1f, 0x0003 },
2158     { 0x16, 0x0f0a },
2159     { 0x1f, 0x0000 }
2160   };
2161 
2162   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2163 
2164   mdio_patch(ioaddr, 0x16, 1 << 0);
2165   mdio_patch(ioaddr, 0x14, 1 << 5);
2166   mdio_patch(ioaddr, 0x0d, 1 << 5);
2167   mdio_write(ioaddr, 0x1f, 0x0000);
2168 }
2169 
2170 static void rtl8168c_4_hw_phy_config(void __iomem *ioaddr)
2171 {
2172   rtl8168c_3_hw_phy_config(ioaddr);
2173 }
2174 
2175 static void rtl8168d_1_hw_phy_config(void __iomem *ioaddr)
2176 {
2177   static const struct phy_reg phy_reg_init_0[] = {
2178     { 0x1f, 0x0001 },
2179     { 0x06, 0x4064 },
2180     { 0x07, 0x2863 },
2181     { 0x08, 0x059c },
2182     { 0x09, 0x26b4 },
2183     { 0x0a, 0x6a19 },
2184     { 0x0b, 0xdcc8 },
2185     { 0x10, 0xf06d },
2186     { 0x14, 0x7f68 },
2187     { 0x18, 0x7fd9 },
2188     { 0x1c, 0xf0ff },
2189     { 0x1d, 0x3d9c },
2190     { 0x1f, 0x0003 },
2191     { 0x12, 0xf49f },
2192     { 0x13, 0x070b },
2193     { 0x1a, 0x05ad },
2194     { 0x14, 0x94c0 }
2195   };
2196   static const struct phy_reg phy_reg_init_1[] = {
2197     { 0x1f, 0x0002 },
2198     { 0x06, 0x5561 },
2199     { 0x1f, 0x0005 },
2200     { 0x05, 0x8332 },
2201     { 0x06, 0x5561 }
2202   };
2203   static const struct phy_reg phy_reg_init_2[] = {
2204     { 0x1f, 0x0005 },
2205     { 0x05, 0xffc2 },
2206     { 0x1f, 0x0005 },
2207     { 0x05, 0x8000 },
2208     { 0x06, 0xf8f9 },
2209     { 0x06, 0xfaef },
2210     { 0x06, 0x59ee },
2211     { 0x06, 0xf8ea },
2212     { 0x06, 0x00ee },
2213     { 0x06, 0xf8eb },
2214     { 0x06, 0x00e0 },
2215     { 0x06, 0xf87c },
2216     { 0x06, 0xe1f8 },
2217     { 0x06, 0x7d59 },
2218     { 0x06, 0x0fef },
2219     { 0x06, 0x0139 },
2220     { 0x06, 0x029e },
2221     { 0x06, 0x06ef },
2222     { 0x06, 0x1039 },
2223     { 0x06, 0x089f },
2224     { 0x06, 0x2aee },
2225     { 0x06, 0xf8ea },
2226     { 0x06, 0x00ee },
2227     { 0x06, 0xf8eb },
2228     { 0x06, 0x01e0 },
2229     { 0x06, 0xf87c },
2230     { 0x06, 0xe1f8 },
2231     { 0x06, 0x7d58 },
2232     { 0x06, 0x409e },
2233     { 0x06, 0x0f39 },
2234     { 0x06, 0x46aa },
2235     { 0x06, 0x0bbf },
2236     { 0x06, 0x8290 },
2237     { 0x06, 0xd682 },
2238     { 0x06, 0x9802 },
2239     { 0x06, 0x014f },
2240     { 0x06, 0xae09 },
2241     { 0x06, 0xbf82 },
2242     { 0x06, 0x98d6 },
2243     { 0x06, 0x82a0 },
2244     { 0x06, 0x0201 },
2245     { 0x06, 0x4fef },
2246     { 0x06, 0x95fe },
2247     { 0x06, 0xfdfc },
2248     { 0x06, 0x05f8 },
2249     { 0x06, 0xf9fa },
2250     { 0x06, 0xeef8 },
2251     { 0x06, 0xea00 },
2252     { 0x06, 0xeef8 },
2253     { 0x06, 0xeb00 },
2254     { 0x06, 0xe2f8 },
2255     { 0x06, 0x7ce3 },
2256     { 0x06, 0xf87d },
2257     { 0x06, 0xa511 },
2258     { 0x06, 0x1112 },
2259     { 0x06, 0xd240 },
2260     { 0x06, 0xd644 },
2261     { 0x06, 0x4402 },
2262     { 0x06, 0x8217 },
2263     { 0x06, 0xd2a0 },
2264     { 0x06, 0xd6aa },
2265     { 0x06, 0xaa02 },
2266     { 0x06, 0x8217 },
2267     { 0x06, 0xae0f },
2268     { 0x06, 0xa544 },
2269     { 0x06, 0x4402 },
2270     { 0x06, 0xae4d },
2271     { 0x06, 0xa5aa },
2272     { 0x06, 0xaa02 },
2273     { 0x06, 0xae47 },
2274     { 0x06, 0xaf82 },
2275     { 0x06, 0x13ee },
2276     { 0x06, 0x834e },
2277     { 0x06, 0x00ee },
2278     { 0x06, 0x834d },
2279     { 0x06, 0x0fee },
2280     { 0x06, 0x834c },
2281     { 0x06, 0x0fee },
2282     { 0x06, 0x834f },
2283     { 0x06, 0x00ee },
2284     { 0x06, 0x8351 },
2285     { 0x06, 0x00ee },
2286     { 0x06, 0x834a },
2287     { 0x06, 0xffee },
2288     { 0x06, 0x834b },
2289     { 0x06, 0xffe0 },
2290     { 0x06, 0x8330 },
2291     { 0x06, 0xe183 },
2292     { 0x06, 0x3158 },
2293     { 0x06, 0xfee4 },
2294     { 0x06, 0xf88a },
2295     { 0x06, 0xe5f8 },
2296     { 0x06, 0x8be0 },
2297     { 0x06, 0x8332 },
2298     { 0x06, 0xe183 },
2299     { 0x06, 0x3359 },
2300     { 0x06, 0x0fe2 },
2301     { 0x06, 0x834d },
2302     { 0x06, 0x0c24 },
2303     { 0x06, 0x5af0 },
2304     { 0x06, 0x1e12 },
2305     { 0x06, 0xe4f8 },
2306     { 0x06, 0x8ce5 },
2307     { 0x06, 0xf88d },
2308     { 0x06, 0xaf82 },
2309     { 0x06, 0x13e0 },
2310     { 0x06, 0x834f },
2311     { 0x06, 0x10e4 },
2312     { 0x06, 0x834f },
2313     { 0x06, 0xe083 },
2314     { 0x06, 0x4e78 },
2315     { 0x06, 0x009f },
2316     { 0x06, 0x0ae0 },
2317     { 0x06, 0x834f },
2318     { 0x06, 0xa010 },
2319     { 0x06, 0xa5ee },
2320     { 0x06, 0x834e },
2321     { 0x06, 0x01e0 },
2322     { 0x06, 0x834e },
2323     { 0x06, 0x7805 },
2324     { 0x06, 0x9e9a },
2325     { 0x06, 0xe083 },
2326     { 0x06, 0x4e78 },
2327     { 0x06, 0x049e },
2328     { 0x06, 0x10e0 },
2329     { 0x06, 0x834e },
2330     { 0x06, 0x7803 },
2331     { 0x06, 0x9e0f },
2332     { 0x06, 0xe083 },
2333     { 0x06, 0x4e78 },
2334     { 0x06, 0x019e },
2335     { 0x06, 0x05ae },
2336     { 0x06, 0x0caf },
2337     { 0x06, 0x81f8 },
2338     { 0x06, 0xaf81 },
2339     { 0x06, 0xa3af },
2340     { 0x06, 0x81dc },
2341     { 0x06, 0xaf82 },
2342     { 0x06, 0x13ee },
2343     { 0x06, 0x8348 },
2344     { 0x06, 0x00ee },
2345     { 0x06, 0x8349 },
2346     { 0x06, 0x00e0 },
2347     { 0x06, 0x8351 },
2348     { 0x06, 0x10e4 },
2349     { 0x06, 0x8351 },
2350     { 0x06, 0x5801 },
2351     { 0x06, 0x9fea },
2352     { 0x06, 0xd000 },
2353     { 0x06, 0xd180 },
2354     { 0x06, 0x1f66 },
2355     { 0x06, 0xe2f8 },
2356     { 0x06, 0xeae3 },
2357     { 0x06, 0xf8eb },
2358     { 0x06, 0x5af8 },
2359     { 0x06, 0x1e20 },
2360     { 0x06, 0xe6f8 },
2361     { 0x06, 0xeae5 },
2362     { 0x06, 0xf8eb },
2363     { 0x06, 0xd302 },
2364     { 0x06, 0xb3fe },
2365     { 0x06, 0xe2f8 },
2366     { 0x06, 0x7cef },
2367     { 0x06, 0x325b },
2368     { 0x06, 0x80e3 },
2369     { 0x06, 0xf87d },
2370     { 0x06, 0x9e03 },
2371     { 0x06, 0x7dff },
2372     { 0x06, 0xff0d },
2373     { 0x06, 0x581c },
2374     { 0x06, 0x551a },
2375     { 0x06, 0x6511 },
2376     { 0x06, 0xa190 },
2377     { 0x06, 0xd3e2 },
2378     { 0x06, 0x8348 },
2379     { 0x06, 0xe383 },
2380     { 0x06, 0x491b },
2381     { 0x06, 0x56ab },
2382     { 0x06, 0x08ef },
2383     { 0x06, 0x56e6 },
2384     { 0x06, 0x8348 },
2385     { 0x06, 0xe783 },
2386     { 0x06, 0x4910 },
2387     { 0x06, 0xd180 },
2388     { 0x06, 0x1f66 },
2389     { 0x06, 0xa004 },
2390     { 0x06, 0xb9e2 },
2391     { 0x06, 0x8348 },
2392     { 0x06, 0xe383 },
2393     { 0x06, 0x49ef },
2394     { 0x06, 0x65e2 },
2395     { 0x06, 0x834a },
2396     { 0x06, 0xe383 },
2397     { 0x06, 0x4b1b },
2398     { 0x06, 0x56aa },
2399     { 0x06, 0x0eef },
2400     { 0x06, 0x56e6 },
2401     { 0x06, 0x834a },
2402     { 0x06, 0xe783 },
2403     { 0x06, 0x4be2 },
2404     { 0x06, 0x834d },
2405     { 0x06, 0xe683 },
2406     { 0x06, 0x4ce0 },
2407     { 0x06, 0x834d },
2408     { 0x06, 0xa000 },
2409     { 0x06, 0x0caf },
2410     { 0x06, 0x81dc },
2411     { 0x06, 0xe083 },
2412     { 0x06, 0x4d10 },
2413     { 0x06, 0xe483 },
2414     { 0x06, 0x4dae },
2415     { 0x06, 0x0480 },
2416     { 0x06, 0xe483 },
2417     { 0x06, 0x4de0 },
2418     { 0x06, 0x834e },
2419     { 0x06, 0x7803 },
2420     { 0x06, 0x9e0b },
2421     { 0x06, 0xe083 },
2422     { 0x06, 0x4e78 },
2423     { 0x06, 0x049e },
2424     { 0x06, 0x04ee },
2425     { 0x06, 0x834e },
2426     { 0x06, 0x02e0 },
2427     { 0x06, 0x8332 },
2428     { 0x06, 0xe183 },
2429     { 0x06, 0x3359 },
2430     { 0x06, 0x0fe2 },
2431     { 0x06, 0x834d },
2432     { 0x06, 0x0c24 },
2433     { 0x06, 0x5af0 },
2434     { 0x06, 0x1e12 },
2435     { 0x06, 0xe4f8 },
2436     { 0x06, 0x8ce5 },
2437     { 0x06, 0xf88d },
2438     { 0x06, 0xe083 },
2439     { 0x06, 0x30e1 },
2440     { 0x06, 0x8331 },
2441     { 0x06, 0x6801 },
2442     { 0x06, 0xe4f8 },
2443     { 0x06, 0x8ae5 },
2444     { 0x06, 0xf88b },
2445     { 0x06, 0xae37 },
2446     { 0x06, 0xee83 },
2447     { 0x06, 0x4e03 },
2448     { 0x06, 0xe083 },
2449     { 0x06, 0x4ce1 },
2450     { 0x06, 0x834d },
2451     { 0x06, 0x1b01 },
2452     { 0x06, 0x9e04 },
2453     { 0x06, 0xaaa1 },
2454     { 0x06, 0xaea8 },
2455     { 0x06, 0xee83 },
2456     { 0x06, 0x4e04 },
2457     { 0x06, 0xee83 },
2458     { 0x06, 0x4f00 },
2459     { 0x06, 0xaeab },
2460     { 0x06, 0xe083 },
2461     { 0x06, 0x4f78 },
2462     { 0x06, 0x039f },
2463     { 0x06, 0x14ee },
2464     { 0x06, 0x834e },
2465     { 0x06, 0x05d2 },
2466     { 0x06, 0x40d6 },
2467     { 0x06, 0x5554 },
2468     { 0x06, 0x0282 },
2469     { 0x06, 0x17d2 },
2470     { 0x06, 0xa0d6 },
2471     { 0x06, 0xba00 },
2472     { 0x06, 0x0282 },
2473     { 0x06, 0x17fe },
2474     { 0x06, 0xfdfc },
2475     { 0x06, 0x05f8 },
2476     { 0x06, 0xe0f8 },
2477     { 0x06, 0x60e1 },
2478     { 0x06, 0xf861 },
2479     { 0x06, 0x6802 },
2480     { 0x06, 0xe4f8 },
2481     { 0x06, 0x60e5 },
2482     { 0x06, 0xf861 },
2483     { 0x06, 0xe0f8 },
2484     { 0x06, 0x48e1 },
2485     { 0x06, 0xf849 },
2486     { 0x06, 0x580f },
2487     { 0x06, 0x1e02 },
2488     { 0x06, 0xe4f8 },
2489     { 0x06, 0x48e5 },
2490     { 0x06, 0xf849 },
2491     { 0x06, 0xd000 },
2492     { 0x06, 0x0282 },
2493     { 0x06, 0x5bbf },
2494     { 0x06, 0x8350 },
2495     { 0x06, 0xef46 },
2496     { 0x06, 0xdc19 },
2497     { 0x06, 0xddd0 },
2498     { 0x06, 0x0102 },
2499     { 0x06, 0x825b },
2500     { 0x06, 0x0282 },
2501     { 0x06, 0x77e0 },
2502     { 0x06, 0xf860 },
2503     { 0x06, 0xe1f8 },
2504     { 0x06, 0x6158 },
2505     { 0x06, 0xfde4 },
2506     { 0x06, 0xf860 },
2507     { 0x06, 0xe5f8 },
2508     { 0x06, 0x61fc },
2509     { 0x06, 0x04f9 },
2510     { 0x06, 0xfafb },
2511     { 0x06, 0xc6bf },
2512     { 0x06, 0xf840 },
2513     { 0x06, 0xbe83 },
2514     { 0x06, 0x50a0 },
2515     { 0x06, 0x0101 },
2516     { 0x06, 0x071b },
2517     { 0x06, 0x89cf },
2518     { 0x06, 0xd208 },
2519     { 0x06, 0xebdb },
2520     { 0x06, 0x19b2 },
2521     { 0x06, 0xfbff },
2522     { 0x06, 0xfefd },
2523     { 0x06, 0x04f8 },
2524     { 0x06, 0xe0f8 },
2525     { 0x06, 0x48e1 },
2526     { 0x06, 0xf849 },
2527     { 0x06, 0x6808 },
2528     { 0x06, 0xe4f8 },
2529     { 0x06, 0x48e5 },
2530     { 0x06, 0xf849 },
2531     { 0x06, 0x58f7 },
2532     { 0x06, 0xe4f8 },
2533     { 0x06, 0x48e5 },
2534     { 0x06, 0xf849 },
2535     { 0x06, 0xfc04 },
2536     { 0x06, 0x4d20 },
2537     { 0x06, 0x0002 },
2538     { 0x06, 0x4e22 },
2539     { 0x06, 0x0002 },
2540     { 0x06, 0x4ddf },
2541     { 0x06, 0xff01 },
2542     { 0x06, 0x4edd },
2543     { 0x06, 0xff01 },
2544     { 0x05, 0x83d4 },
2545     { 0x06, 0x8000 },
2546     { 0x05, 0x83d8 },
2547     { 0x06, 0x8051 },
2548     { 0x02, 0x6010 },
2549     { 0x03, 0xdc00 },
2550     { 0x05, 0xfff6 },
2551     { 0x06, 0x00fc },
2552     { 0x1f, 0x0000 },
2553 
2554     { 0x1f, 0x0000 },
2555     { 0x0d, 0xf880 },
2556     { 0x1f, 0x0000 }
2557   };
2558 
2559   rtl_phy_write(ioaddr, phy_reg_init_0, ARRAY_SIZE(phy_reg_init_0));
2560 
2561   mdio_write(ioaddr, 0x1f, 0x0002);
2562   mdio_plus_minus(ioaddr, 0x0b, 0x0010, 0x00ef);
2563   mdio_plus_minus(ioaddr, 0x0c, 0xa200, 0x5d00);
2564 
2565   rtl_phy_write(ioaddr, phy_reg_init_1, ARRAY_SIZE(phy_reg_init_1));
2566 
2567   if (rtl8168d_efuse_read(ioaddr, 0x01) == 0xb1) {
2568     static const struct phy_reg phy_reg_init[] = {
2569       { 0x1f, 0x0002 },
2570       { 0x05, 0x669a },
2571       { 0x1f, 0x0005 },
2572       { 0x05, 0x8330 },
2573       { 0x06, 0x669a },
2574       { 0x1f, 0x0002 }
2575     };
2576     int val;
2577 
2578     rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2579 
2580     val = mdio_read(ioaddr, 0x0d);
2581 
2582     if ((val & 0x00ff) != 0x006c) {
2583       static const u32 set[] = {
2584         0x0065, 0x0066, 0x0067, 0x0068,
2585         0x0069, 0x006a, 0x006b, 0x006c
2586       };
2587       int i;
2588 
2589       mdio_write(ioaddr, 0x1f, 0x0002);
2590 
2591       val &= 0xff00;
2592       for (i = 0; i < ARRAY_SIZE(set); i++)
2593         mdio_write(ioaddr, 0x0d, val | set[i]);
2594     }
2595   } else {
2596     static const struct phy_reg phy_reg_init[] = {
2597       { 0x1f, 0x0002 },
2598       { 0x05, 0x6662 },
2599       { 0x1f, 0x0005 },
2600       { 0x05, 0x8330 },
2601       { 0x06, 0x6662 }
2602     };
2603 
2604     rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2605   }
2606 
2607   mdio_write(ioaddr, 0x1f, 0x0002);
2608   mdio_patch(ioaddr, 0x0d, 0x0300);
2609   mdio_patch(ioaddr, 0x0f, 0x0010);
2610 
2611   mdio_write(ioaddr, 0x1f, 0x0002);
2612   mdio_plus_minus(ioaddr, 0x02, 0x0100, 0x0600);
2613   mdio_plus_minus(ioaddr, 0x03, 0x0000, 0xe000);
2614 
2615   rtl_phy_write(ioaddr, phy_reg_init_2, ARRAY_SIZE(phy_reg_init_2));
2616 }
2617 
2618 static void rtl8168d_2_hw_phy_config(void __iomem *ioaddr)
2619 {
2620   static const struct phy_reg phy_reg_init_0[] = {
2621     { 0x1f, 0x0001 },
2622     { 0x06, 0x4064 },
2623     { 0x07, 0x2863 },
2624     { 0x08, 0x059c },
2625     { 0x09, 0x26b4 },
2626     { 0x0a, 0x6a19 },
2627     { 0x0b, 0xdcc8 },
2628     { 0x10, 0xf06d },
2629     { 0x14, 0x7f68 },
2630     { 0x18, 0x7fd9 },
2631     { 0x1c, 0xf0ff },
2632     { 0x1d, 0x3d9c },
2633     { 0x1f, 0x0003 },
2634     { 0x12, 0xf49f },
2635     { 0x13, 0x070b },
2636     { 0x1a, 0x05ad },
2637     { 0x14, 0x94c0 },
2638 
2639     { 0x1f, 0x0002 },
2640     { 0x06, 0x5561 },
2641     { 0x1f, 0x0005 },
2642     { 0x05, 0x8332 },
2643     { 0x06, 0x5561 }
2644   };
2645   static const struct phy_reg phy_reg_init_1[] = {
2646     { 0x1f, 0x0005 },
2647     { 0x05, 0xffc2 },
2648     { 0x1f, 0x0005 },
2649     { 0x05, 0x8000 },
2650     { 0x06, 0xf8f9 },
2651     { 0x06, 0xfaee },
2652     { 0x06, 0xf8ea },
2653     { 0x06, 0x00ee },
2654     { 0x06, 0xf8eb },
2655     { 0x06, 0x00e2 },
2656     { 0x06, 0xf87c },
2657     { 0x06, 0xe3f8 },
2658     { 0x06, 0x7da5 },
2659     { 0x06, 0x1111 },
2660     { 0x06, 0x12d2 },
2661     { 0x06, 0x40d6 },
2662     { 0x06, 0x4444 },
2663     { 0x06, 0x0281 },
2664     { 0x06, 0xc6d2 },
2665     { 0x06, 0xa0d6 },
2666     { 0x06, 0xaaaa },
2667     { 0x06, 0x0281 },
2668     { 0x06, 0xc6ae },
2669     { 0x06, 0x0fa5 },
2670     { 0x06, 0x4444 },
2671     { 0x06, 0x02ae },
2672     { 0x06, 0x4da5 },
2673     { 0x06, 0xaaaa },
2674     { 0x06, 0x02ae },
2675     { 0x06, 0x47af },
2676     { 0x06, 0x81c2 },
2677     { 0x06, 0xee83 },
2678     { 0x06, 0x4e00 },
2679     { 0x06, 0xee83 },
2680     { 0x06, 0x4d0f },
2681     { 0x06, 0xee83 },
2682     { 0x06, 0x4c0f },
2683     { 0x06, 0xee83 },
2684     { 0x06, 0x4f00 },
2685     { 0x06, 0xee83 },
2686     { 0x06, 0x5100 },
2687     { 0x06, 0xee83 },
2688     { 0x06, 0x4aff },
2689     { 0x06, 0xee83 },
2690     { 0x06, 0x4bff },
2691     { 0x06, 0xe083 },
2692     { 0x06, 0x30e1 },
2693     { 0x06, 0x8331 },
2694     { 0x06, 0x58fe },
2695     { 0x06, 0xe4f8 },
2696     { 0x06, 0x8ae5 },
2697     { 0x06, 0xf88b },
2698     { 0x06, 0xe083 },
2699     { 0x06, 0x32e1 },
2700     { 0x06, 0x8333 },
2701     { 0x06, 0x590f },
2702     { 0x06, 0xe283 },
2703     { 0x06, 0x4d0c },
2704     { 0x06, 0x245a },
2705     { 0x06, 0xf01e },
2706     { 0x06, 0x12e4 },
2707     { 0x06, 0xf88c },
2708     { 0x06, 0xe5f8 },
2709     { 0x06, 0x8daf },
2710     { 0x06, 0x81c2 },
2711     { 0x06, 0xe083 },
2712     { 0x06, 0x4f10 },
2713     { 0x06, 0xe483 },
2714     { 0x06, 0x4fe0 },
2715     { 0x06, 0x834e },
2716     { 0x06, 0x7800 },
2717     { 0x06, 0x9f0a },
2718     { 0x06, 0xe083 },
2719     { 0x06, 0x4fa0 },
2720     { 0x06, 0x10a5 },
2721     { 0x06, 0xee83 },
2722     { 0x06, 0x4e01 },
2723     { 0x06, 0xe083 },
2724     { 0x06, 0x4e78 },
2725     { 0x06, 0x059e },
2726     { 0x06, 0x9ae0 },
2727     { 0x06, 0x834e },
2728     { 0x06, 0x7804 },
2729     { 0x06, 0x9e10 },
2730     { 0x06, 0xe083 },
2731     { 0x06, 0x4e78 },
2732     { 0x06, 0x039e },
2733     { 0x06, 0x0fe0 },
2734     { 0x06, 0x834e },
2735     { 0x06, 0x7801 },
2736     { 0x06, 0x9e05 },
2737     { 0x06, 0xae0c },
2738     { 0x06, 0xaf81 },
2739     { 0x06, 0xa7af },
2740     { 0x06, 0x8152 },
2741     { 0x06, 0xaf81 },
2742     { 0x06, 0x8baf },
2743     { 0x06, 0x81c2 },
2744     { 0x06, 0xee83 },
2745     { 0x06, 0x4800 },
2746     { 0x06, 0xee83 },
2747     { 0x06, 0x4900 },
2748     { 0x06, 0xe083 },
2749     { 0x06, 0x5110 },
2750     { 0x06, 0xe483 },
2751     { 0x06, 0x5158 },
2752     { 0x06, 0x019f },
2753     { 0x06, 0xead0 },
2754     { 0x06, 0x00d1 },
2755     { 0x06, 0x801f },
2756     { 0x06, 0x66e2 },
2757     { 0x06, 0xf8ea },
2758     { 0x06, 0xe3f8 },
2759     { 0x06, 0xeb5a },
2760     { 0x06, 0xf81e },
2761     { 0x06, 0x20e6 },
2762     { 0x06, 0xf8ea },
2763     { 0x06, 0xe5f8 },
2764     { 0x06, 0xebd3 },
2765     { 0x06, 0x02b3 },
2766     { 0x06, 0xfee2 },
2767     { 0x06, 0xf87c },
2768     { 0x06, 0xef32 },
2769     { 0x06, 0x5b80 },
2770     { 0x06, 0xe3f8 },
2771     { 0x06, 0x7d9e },
2772     { 0x06, 0x037d },
2773     { 0x06, 0xffff },
2774     { 0x06, 0x0d58 },
2775     { 0x06, 0x1c55 },
2776     { 0x06, 0x1a65 },
2777     { 0x06, 0x11a1 },
2778     { 0x06, 0x90d3 },
2779     { 0x06, 0xe283 },
2780     { 0x06, 0x48e3 },
2781     { 0x06, 0x8349 },
2782     { 0x06, 0x1b56 },
2783     { 0x06, 0xab08 },
2784     { 0x06, 0xef56 },
2785     { 0x06, 0xe683 },
2786     { 0x06, 0x48e7 },
2787     { 0x06, 0x8349 },
2788     { 0x06, 0x10d1 },
2789     { 0x06, 0x801f },
2790     { 0x06, 0x66a0 },
2791     { 0x06, 0x04b9 },
2792     { 0x06, 0xe283 },
2793     { 0x06, 0x48e3 },
2794     { 0x06, 0x8349 },
2795     { 0x06, 0xef65 },
2796     { 0x06, 0xe283 },
2797     { 0x06, 0x4ae3 },
2798     { 0x06, 0x834b },
2799     { 0x06, 0x1b56 },
2800     { 0x06, 0xaa0e },
2801     { 0x06, 0xef56 },
2802     { 0x06, 0xe683 },
2803     { 0x06, 0x4ae7 },
2804     { 0x06, 0x834b },
2805     { 0x06, 0xe283 },
2806     { 0x06, 0x4de6 },
2807     { 0x06, 0x834c },
2808     { 0x06, 0xe083 },
2809     { 0x06, 0x4da0 },
2810     { 0x06, 0x000c },
2811     { 0x06, 0xaf81 },
2812     { 0x06, 0x8be0 },
2813     { 0x06, 0x834d },
2814     { 0x06, 0x10e4 },
2815     { 0x06, 0x834d },
2816     { 0x06, 0xae04 },
2817     { 0x06, 0x80e4 },
2818     { 0x06, 0x834d },
2819     { 0x06, 0xe083 },
2820     { 0x06, 0x4e78 },
2821     { 0x06, 0x039e },
2822     { 0x06, 0x0be0 },
2823     { 0x06, 0x834e },
2824     { 0x06, 0x7804 },
2825     { 0x06, 0x9e04 },
2826     { 0x06, 0xee83 },
2827     { 0x06, 0x4e02 },
2828     { 0x06, 0xe083 },
2829     { 0x06, 0x32e1 },
2830     { 0x06, 0x8333 },
2831     { 0x06, 0x590f },
2832     { 0x06, 0xe283 },
2833     { 0x06, 0x4d0c },
2834     { 0x06, 0x245a },
2835     { 0x06, 0xf01e },
2836     { 0x06, 0x12e4 },
2837     { 0x06, 0xf88c },
2838     { 0x06, 0xe5f8 },
2839     { 0x06, 0x8de0 },
2840     { 0x06, 0x8330 },
2841     { 0x06, 0xe183 },
2842     { 0x06, 0x3168 },
2843     { 0x06, 0x01e4 },
2844     { 0x06, 0xf88a },
2845     { 0x06, 0xe5f8 },
2846     { 0x06, 0x8bae },
2847     { 0x06, 0x37ee },
2848     { 0x06, 0x834e },
2849     { 0x06, 0x03e0 },
2850     { 0x06, 0x834c },
2851     { 0x06, 0xe183 },
2852     { 0x06, 0x4d1b },
2853     { 0x06, 0x019e },
2854     { 0x06, 0x04aa },
2855     { 0x06, 0xa1ae },
2856     { 0x06, 0xa8ee },
2857     { 0x06, 0x834e },
2858     { 0x06, 0x04ee },
2859     { 0x06, 0x834f },
2860     { 0x06, 0x00ae },
2861     { 0x06, 0xabe0 },
2862     { 0x06, 0x834f },
2863     { 0x06, 0x7803 },
2864     { 0x06, 0x9f14 },
2865     { 0x06, 0xee83 },
2866     { 0x06, 0x4e05 },
2867     { 0x06, 0xd240 },
2868     { 0x06, 0xd655 },
2869     { 0x06, 0x5402 },
2870     { 0x06, 0x81c6 },
2871     { 0x06, 0xd2a0 },
2872     { 0x06, 0xd6ba },
2873     { 0x06, 0x0002 },
2874     { 0x06, 0x81c6 },
2875     { 0x06, 0xfefd },
2876     { 0x06, 0xfc05 },
2877     { 0x06, 0xf8e0 },
2878     { 0x06, 0xf860 },
2879     { 0x06, 0xe1f8 },
2880     { 0x06, 0x6168 },
2881     { 0x06, 0x02e4 },
2882     { 0x06, 0xf860 },
2883     { 0x06, 0xe5f8 },
2884     { 0x06, 0x61e0 },
2885     { 0x06, 0xf848 },
2886     { 0x06, 0xe1f8 },
2887     { 0x06, 0x4958 },
2888     { 0x06, 0x0f1e },
2889     { 0x06, 0x02e4 },
2890     { 0x06, 0xf848 },
2891     { 0x06, 0xe5f8 },
2892     { 0x06, 0x49d0 },
2893     { 0x06, 0x0002 },
2894     { 0x06, 0x820a },
2895     { 0x06, 0xbf83 },
2896     { 0x06, 0x50ef },
2897     { 0x06, 0x46dc },
2898     { 0x06, 0x19dd },
2899     { 0x06, 0xd001 },
2900     { 0x06, 0x0282 },
2901     { 0x06, 0x0a02 },
2902     { 0x06, 0x8226 },
2903     { 0x06, 0xe0f8 },
2904     { 0x06, 0x60e1 },
2905     { 0x06, 0xf861 },
2906     { 0x06, 0x58fd },
2907     { 0x06, 0xe4f8 },
2908     { 0x06, 0x60e5 },
2909     { 0x06, 0xf861 },
2910     { 0x06, 0xfc04 },
2911     { 0x06, 0xf9fa },
2912     { 0x06, 0xfbc6 },
2913     { 0x06, 0xbff8 },
2914     { 0x06, 0x40be },
2915     { 0x06, 0x8350 },
2916     { 0x06, 0xa001 },
2917     { 0x06, 0x0107 },
2918     { 0x06, 0x1b89 },
2919     { 0x06, 0xcfd2 },
2920     { 0x06, 0x08eb },
2921     { 0x06, 0xdb19 },
2922     { 0x06, 0xb2fb },
2923     { 0x06, 0xfffe },
2924     { 0x06, 0xfd04 },
2925     { 0x06, 0xf8e0 },
2926     { 0x06, 0xf848 },
2927     { 0x06, 0xe1f8 },
2928     { 0x06, 0x4968 },
2929     { 0x06, 0x08e4 },
2930     { 0x06, 0xf848 },
2931     { 0x06, 0xe5f8 },
2932     { 0x06, 0x4958 },
2933     { 0x06, 0xf7e4 },
2934     { 0x06, 0xf848 },
2935     { 0x06, 0xe5f8 },
2936     { 0x06, 0x49fc },
2937     { 0x06, 0x044d },
2938     { 0x06, 0x2000 },
2939     { 0x06, 0x024e },
2940     { 0x06, 0x2200 },
2941     { 0x06, 0x024d },
2942     { 0x06, 0xdfff },
2943     { 0x06, 0x014e },
2944     { 0x06, 0xddff },
2945     { 0x06, 0x0100 },
2946     { 0x05, 0x83d8 },
2947     { 0x06, 0x8000 },
2948     { 0x03, 0xdc00 },
2949     { 0x05, 0xfff6 },
2950     { 0x06, 0x00fc },
2951     { 0x1f, 0x0000 },
2952 
2953     { 0x1f, 0x0000 },
2954     { 0x0d, 0xf880 },
2955     { 0x1f, 0x0000 }
2956   };
2957 
2958   rtl_phy_write(ioaddr, phy_reg_init_0, ARRAY_SIZE(phy_reg_init_0));
2959 
2960   if (rtl8168d_efuse_read(ioaddr, 0x01) == 0xb1) {
2961     static const struct phy_reg phy_reg_init[] = {
2962       { 0x1f, 0x0002 },
2963       { 0x05, 0x669a },
2964       { 0x1f, 0x0005 },
2965       { 0x05, 0x8330 },
2966       { 0x06, 0x669a },
2967 
2968       { 0x1f, 0x0002 }
2969     };
2970     int val;
2971 
2972     rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2973 
2974     val = mdio_read(ioaddr, 0x0d);
2975     if ((val & 0x00ff) != 0x006c) {
2976       u32 set[] = {
2977         0x0065, 0x0066, 0x0067, 0x0068,
2978         0x0069, 0x006a, 0x006b, 0x006c
2979       };
2980       int i;
2981 
2982       mdio_write(ioaddr, 0x1f, 0x0002);
2983 
2984       val &= 0xff00;
2985       for (i = 0; i < ARRAY_SIZE(set); i++)
2986         mdio_write(ioaddr, 0x0d, val | set[i]);
2987     }
2988   } else {
2989     static const struct phy_reg phy_reg_init[] = {
2990       { 0x1f, 0x0002 },
2991       { 0x05, 0x2642 },
2992       { 0x1f, 0x0005 },
2993       { 0x05, 0x8330 },
2994       { 0x06, 0x2642 }
2995     };
2996 
2997     rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
2998   }
2999 
3000   mdio_write(ioaddr, 0x1f, 0x0002);
3001   mdio_plus_minus(ioaddr, 0x02, 0x0100, 0x0600);
3002   mdio_plus_minus(ioaddr, 0x03, 0x0000, 0xe000);
3003 
3004   mdio_write(ioaddr, 0x1f, 0x0001);
3005   mdio_write(ioaddr, 0x17, 0x0cc0);
3006 
3007   mdio_write(ioaddr, 0x1f, 0x0002);
3008   mdio_patch(ioaddr, 0x0f, 0x0017);
3009 
3010   rtl_phy_write(ioaddr, phy_reg_init_1, ARRAY_SIZE(phy_reg_init_1));
3011 }
3012 
3013 static void rtl8168d_3_hw_phy_config(void __iomem *ioaddr)
3014 {
3015   static const struct phy_reg phy_reg_init[] = {
3016     { 0x1f, 0x0002 },
3017     { 0x10, 0x0008 },
3018     { 0x0d, 0x006c },
3019 
3020     { 0x1f, 0x0000 },
3021     { 0x0d, 0xf880 },
3022 
3023     { 0x1f, 0x0001 },
3024     { 0x17, 0x0cc0 },
3025 
3026     { 0x1f, 0x0001 },
3027     { 0x0b, 0xa4d8 },
3028     { 0x09, 0x281c },
3029     { 0x07, 0x2883 },
3030     { 0x0a, 0x6b35 },
3031     { 0x1d, 0x3da4 },
3032     { 0x1c, 0xeffd },
3033     { 0x14, 0x7f52 },
3034     { 0x18, 0x7fc6 },
3035     { 0x08, 0x0601 },
3036     { 0x06, 0x4063 },
3037     { 0x10, 0xf074 },
3038     { 0x1f, 0x0003 },
3039     { 0x13, 0x0789 },
3040     { 0x12, 0xf4bd },
3041     { 0x1a, 0x04fd },
3042     { 0x14, 0x84b0 },
3043     { 0x1f, 0x0000 },
3044     { 0x00, 0x9200 },
3045 
3046     { 0x1f, 0x0005 },
3047     { 0x01, 0x0340 },
3048     { 0x1f, 0x0001 },
3049     { 0x04, 0x4000 },
3050     { 0x03, 0x1d21 },
3051     { 0x02, 0x0c32 },
3052     { 0x01, 0x0200 },
3053     { 0x00, 0x5554 },
3054     { 0x04, 0x4800 },
3055     { 0x04, 0x4000 },
3056     { 0x04, 0xf000 },
3057     { 0x03, 0xdf01 },
3058     { 0x02, 0xdf20 },
3059     { 0x01, 0x101a },
3060     { 0x00, 0xa0ff },
3061     { 0x04, 0xf800 },
3062     { 0x04, 0xf000 },
3063     { 0x1f, 0x0000 },
3064 
3065     { 0x1f, 0x0007 },
3066     { 0x1e, 0x0023 },
3067     { 0x16, 0x0000 },
3068     { 0x1f, 0x0000 }
3069   };
3070 
3071   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
3072 }
3073 
3074 static void rtl8102e_hw_phy_config(void __iomem *ioaddr)
3075 {
3076   static const struct phy_reg phy_reg_init[] = {
3077     { 0x1f, 0x0003 },
3078     { 0x08, 0x441d },
3079     { 0x01, 0x9100 },
3080     { 0x1f, 0x0000 }
3081   };
3082 
3083   mdio_write(ioaddr, 0x1f, 0x0000);
3084   mdio_patch(ioaddr, 0x11, 1 << 12);
3085   mdio_patch(ioaddr, 0x19, 1 << 13);
3086   mdio_patch(ioaddr, 0x10, 1 << 15);
3087 
3088   rtl_phy_write(ioaddr, phy_reg_init, ARRAY_SIZE(phy_reg_init));
3089 }
3090 
3091 static void rtl_hw_phy_config(struct net_device *dev)
3092 {
3093   struct rtl8169_private *tp = netdev_priv(dev);
3094   void __iomem *ioaddr = tp->mmio_addr;
3095 
3096   switch (tp->mac_version) {
3097   case RTL_GIGA_MAC_VER_01:
3098     break;
3099   case RTL_GIGA_MAC_VER_02:
3100   case RTL_GIGA_MAC_VER_03:
3101     rtl8169s_hw_phy_config(ioaddr);
3102     break;
3103   case RTL_GIGA_MAC_VER_04:
3104     rtl8169sb_hw_phy_config(ioaddr);
3105     break;
3106   case RTL_GIGA_MAC_VER_05:
3107     rtl8169scd_hw_phy_config(tp, ioaddr);
3108     break;
3109   case RTL_GIGA_MAC_VER_06:
3110     rtl8169sce_hw_phy_config(ioaddr);
3111     break;
3112   case RTL_GIGA_MAC_VER_07:
3113   case RTL_GIGA_MAC_VER_08:
3114   case RTL_GIGA_MAC_VER_09:
3115     rtl8102e_hw_phy_config(ioaddr);
3116     break;
3117   case RTL_GIGA_MAC_VER_11:
3118     rtl8168bb_hw_phy_config(ioaddr);
3119     break;
3120   case RTL_GIGA_MAC_VER_12:
3121     rtl8168bef_hw_phy_config(ioaddr);
3122     break;
3123   case RTL_GIGA_MAC_VER_17:
3124     rtl8168bef_hw_phy_config(ioaddr);
3125     break;
3126   case RTL_GIGA_MAC_VER_18:
3127     rtl8168cp_1_hw_phy_config(ioaddr);
3128     break;
3129   case RTL_GIGA_MAC_VER_19:
3130     rtl8168c_1_hw_phy_config(ioaddr);
3131     break;
3132   case RTL_GIGA_MAC_VER_20:
3133     rtl8168c_2_hw_phy_config(ioaddr);
3134     break;
3135   case RTL_GIGA_MAC_VER_21:
3136     rtl8168c_3_hw_phy_config(ioaddr);
3137     break;
3138   case RTL_GIGA_MAC_VER_22:
3139     rtl8168c_4_hw_phy_config(ioaddr);
3140     break;
3141   case RTL_GIGA_MAC_VER_23:
3142   case RTL_GIGA_MAC_VER_24:
3143     rtl8168cp_2_hw_phy_config(ioaddr);
3144     break;
3145   case RTL_GIGA_MAC_VER_25:
3146     rtl8168d_1_hw_phy_config(ioaddr);
3147     break;
3148   case RTL_GIGA_MAC_VER_26:
3149     rtl8168d_2_hw_phy_config(ioaddr);
3150     break;
3151   case RTL_GIGA_MAC_VER_27:
3152     rtl8168d_3_hw_phy_config(ioaddr);
3153     break;
3154 
3155   default:
3156     break;
3157   }
3158 }
3159 
3160 static int
3161 rtl8169_set_speed(struct net_device *dev,
3162                   u8 autoneg, u16 speed, u8 duplex)
3163 {
3164   struct rtl8169_private *tp = netdev_priv(dev);
3165   int ret;
3166 
3167   ret = tp->set_speed(dev, autoneg, speed, duplex);
3168 
3169   /***************************************************************************
3170    * if (netif_running(dev) && (tp->phy_1000_ctrl_reg & ADVERTISE_1000FULL)) *
3171    *   mod_timer(&tp->timer, jiffies + RTL8169_PHY_TIMEOUT);                 *
3172    ***************************************************************************/
3173 
3174   return ret;
3175 }
3176 
3177 static void
3178 rtl8169_phy_reset(struct net_device *dev,
3179                   struct rtl8169_private *tp)
3180 {
3181   void __iomem *ioaddr = tp->mmio_addr;
3182   unsigned int i;
3183 
3184   tp->phy_reset_enable(ioaddr);
3185   for (i = 0; i < 100; i++) {
3186     if (!tp->phy_reset_pending(ioaddr))
3187       return;
3188     udelay(1000);
3189   }
3190   DLOG("PHY reset failed");
3191 }
3192 
3193 static void
3194 init_phy(struct net_device *dev, struct rtl8169_private *tp)
3195 {
3196   void __iomem *ioaddr = tp->mmio_addr;
3197 
3198   rtl_hw_phy_config(dev);
3199 
3200   if (tp->mac_version <= RTL_GIGA_MAC_VER_06) {
3201     DLOG("Set MAC Reg C+CR Offset 0x82h = 0x01h");
3202     RTL_W8(0x82, 0x01);
3203   }
3204 
3205   pci_write_config_byte(tp->pci_dev, PCI_LATENCY_TIMER, 0x40);
3206 
3207   if (tp->mac_version <= RTL_GIGA_MAC_VER_06)
3208     pci_write_config_byte(tp->pci_dev, PCI_CACHE_LINE_SIZE, 0x08);
3209 
3210   if (tp->mac_version == RTL_GIGA_MAC_VER_02) {
3211     DLOG("Set MAC Reg C+CR Offset 0x82h = 0x01h");
3212     RTL_W8(0x82, 0x01);
3213     DLOG("Set PHY Reg 0x0bh = 0x00h");
3214     mdio_write(ioaddr, 0x0b, 0x0000); //w 0x0b 15 0 0
3215   }
3216 
3217   rtl8169_phy_reset(dev, tp);
3218 
3219   /*
3220    * rtl8169_set_speed_xmii takes good care of the Fast Ethernet
3221    * only 8101. Don't panic.
3222    */
3223   rtl8169_set_speed(dev, AUTONEG_ENABLE, SPEED_1000, DUPLEX_FULL);
3224 
3225   if (RTL_R8(PHYstatus) & TBI_Enable)
3226     DLOG("TBI auto-negotiating");
3227 }
3228 
3229 #define cpu_to_le32 __cpu_to_le32
3230 #define le32_to_cpu __le32_to_cpu
3231 #define cpu_to_le64 __cpu_to_le64
3232 #define wmb() ;
3233 
3234 static inline struct sk_buff *
3235 alloc_skb (u32 size)
3236 {
3237   struct sk_buff *skb;
3238   pow2_alloc (sizeof (struct sk_buff), (u8 **) &skb);
3239   if (!skb) return NULL;
3240   skb->len = size;
3241   pow2_alloc (size, (u8 **) &skb->data);
3242   if (!skb->data) return NULL;
3243   memset (skb->data, 0, size);
3244   return skb;
3245 }
3246 
3247 static inline void
3248 free_skb (struct sk_buff *skb)
3249 {
3250   pow2_free ((u8 *)skb->data);
3251   pow2_free ((u8 *)skb);
3252 }
3253 
3254 static inline void rtl8169_make_unusable_by_asic(struct RxDesc *desc)
3255 {
3256   desc->addr = cpu_to_le64(0x0badbadbadbadbadull);
3257   desc->opts1 &= ~cpu_to_le32(DescOwn | RsvdMask);
3258 }
3259 
3260 static void rtl8169_free_rx_skb(struct rtl8169_private *tp,
3261                                 struct sk_buff **sk_buff, struct RxDesc *desc)
3262 {
3263   free_skb (*sk_buff);
3264   *sk_buff = NULL;
3265   rtl8169_make_unusable_by_asic(desc);
3266 }
3267 
3268 static inline void rtl8169_mark_to_asic(struct RxDesc *desc, u32 rx_buf_sz)
3269 {
3270   u32 eor = le32_to_cpu(desc->opts1) & RingEnd;
3271 
3272   desc->opts1 = cpu_to_le32(DescOwn | eor | rx_buf_sz);
3273 }
3274 
3275 static inline void rtl8169_map_to_asic(struct RxDesc *desc, dma_addr_t mapping,
3276                                        u32 rx_buf_sz)
3277 {
3278   desc->addr = cpu_to_le64(mapping);
3279   wmb();
3280   rtl8169_mark_to_asic(desc, rx_buf_sz);
3281 }
3282 
3283 static void rtl8169_rx_clear(struct rtl8169_private *tp)
3284 {
3285   unsigned int i;
3286 
3287   for (i = 0; i < NUM_RX_DESC; i++) {
3288     if (tp->Rx_skbuff[i]) {
3289       rtl8169_free_rx_skb(tp, tp->Rx_skbuff + i,
3290                           tp->RxDescArray + i);
3291     }
3292   }
3293 }
3294 
3295 typedef int gfp_t;
3296 
3297 static struct sk_buff *rtl8169_alloc_rx_skb(struct pci_dev *pdev,
3298                                             struct net_device *dev,
3299                                             struct RxDesc *desc, int rx_buf_sz,
3300                                             unsigned int align, gfp_t gfp)
3301 {
3302   struct sk_buff *skb;
3303   dma_addr_t mapping;
3304   unsigned int pad;
3305 
3306 #define NET_IP_ALIGN 2
3307   pad = align ? align : NET_IP_ALIGN;
3308 
3309   skb = alloc_skb (rx_buf_sz + pad);
3310   if (!skb)
3311     goto err_out;
3312 
3313   mapping = (uint) get_phys_addr (skb->data);
3314 
3315   rtl8169_map_to_asic(desc, mapping, rx_buf_sz);
3316  out:
3317   return skb;
3318 
3319  err_out:
3320   rtl8169_make_unusable_by_asic(desc);
3321   goto out;
3322 }
3323 
3324 static u32 rtl8169_rx_fill(struct rtl8169_private *tp, struct net_device *dev,
3325                            u32 start, u32 end, gfp_t gfp)
3326 {
3327   u32 cur;
3328 
3329   for (cur = start; end - cur != 0; cur++) {
3330     struct sk_buff *skb;
3331     unsigned int i = cur % NUM_RX_DESC;
3332 
3333     if (tp->Rx_skbuff[i])
3334       continue;
3335 
3336     skb = rtl8169_alloc_rx_skb(tp->pci_dev, dev,
3337                                tp->RxDescArray + i,
3338                                tp->rx_buf_sz, tp->align, gfp);
3339     if (!skb)
3340       break;
3341 
3342     tp->Rx_skbuff[i] = skb;
3343   }
3344   return cur - start;
3345 }
3346 
3347 static inline void rtl8169_mark_as_last_descriptor(struct RxDesc *desc)
3348 {
3349   desc->opts1 |= cpu_to_le32(RingEnd);
3350 }
3351 
3352 static void rtl8169_init_ring_indexes(struct rtl8169_private *tp)
3353 {
3354   tp->dirty_tx = tp->dirty_rx = tp->cur_tx = tp->cur_rx = 0;
3355 }
3356 
3357 static int rtl8169_init_ring(struct net_device *dev)
3358 {
3359   struct rtl8169_private *tp = netdev_priv(dev);
3360 
3361   rtl8169_init_ring_indexes(tp);
3362 
3363   memset(tp->tx_skb, 0x0, NUM_TX_DESC * sizeof(struct ring_info));
3364 
3365   memset(tp->Rx_skbuff, 0x0, NUM_RX_DESC * sizeof(struct sk_buff *));
3366 
3367   if (rtl8169_rx_fill(tp, dev, 0, NUM_RX_DESC, 0) != NUM_RX_DESC)
3368     goto err_out;
3369 
3370   rtl8169_mark_as_last_descriptor(tp->RxDescArray + NUM_RX_DESC - 1);
3371 
3372   return 0;
3373 
3374  err_out:
3375   rtl8169_rx_clear(tp);
3376   return -1;
3377 }
3378 
3379 static void rtl_hw_start(struct net_device *dev)
3380 {
3381   struct rtl8169_private *tp = netdev_priv(dev);
3382   void __iomem *ioaddr = tp->mmio_addr;
3383   unsigned int i;
3384 
3385   /* Soft reset the chip. */
3386   RTL_W8(ChipCmd, CmdReset);
3387 
3388   /* Check that the chip has finished the reset. */
3389   for (i = 0; i < 100; i++) {
3390     if ((RTL_R8(ChipCmd) & CmdReset) == 0)
3391       break;
3392     udelay(1000);
3393   }
3394 
3395   tp->hw_start(dev);
3396 }
3397 
3398 struct rtl8169_private *tp;
3399 
3400 static sint
3401 r8169_transmit (u8 *buffer, sint len)
3402 {
3403   DLOG ("TX: buffer=0x%p len=%d", buffer, len);
3404   u8 *p = buffer;
3405   DLOG ("  %.02X %.02X %.02X %.02X %.02X %.02X",
3406         p[0], p[1], p[2], p[3], p[4], p[5]);
3407   p+=6;
3408   DLOG ("  %.02X %.02X %.02X %.02X %.02X %.02X",
3409         p[0], p[1], p[2], p[3], p[4], p[5]);
3410   uint entry = tp->cur_tx % NUM_TX_DESC;
3411   struct TxDesc *txd = tp->TxDescArray + entry;
3412   void __iomem *ioaddr = tp->mmio_addr;
3413   dma_addr_t mapping;
3414   u32 status;
3415   u32 opts1;
3416 
3417   if (le32_to_cpu (txd->opts1) & DescOwn)
3418     goto abort;
3419   if (len > MAX_FRAME_SIZE)
3420     goto abort;
3421 
3422   opts1 = DescOwn | FirstFrag | LastFrag;
3423   tp->tx_skb[entry].len = len;
3424   struct sk_buff *skb = alloc_skb (len);
3425   if (!skb) goto abort;
3426   memcpy (skb->data, buffer, len);
3427   tp->tx_skb[entry].skb = skb;
3428   mapping = (uint) get_phys_addr (skb->data);
3429   txd->addr = __cpu_to_le64 (mapping);
3430   status = opts1 | len | (RingEnd * !((entry + 1) % NUM_TX_DESC));
3431   DLOG ("  cur_tx=%d mapping=0x%p status=0x%p", tp->cur_tx, mapping, status);
3432 
3433 #ifdef TX_TIMING
3434   SERIALIZE0;
3435   RDTSC (tx_start);
3436 #endif
3437 
3438   /* xmit */
3439   txd->opts2 = 0;
3440   txd->opts1 = __cpu_to_le32 (status);
3441 
3442   tp->cur_tx++;
3443 
3444   RTL_W8 (TxPoll, NPQ); /* set polling bit */
3445 
3446   return len;
3447  abort:
3448   return -1;
3449 }
3450 
3451 #ifdef TX_TIMING
3452 static u32 timing_stack[1024] ALIGNED (0x1000);
3453 static task_id timing_id;
3454 static void timing_thread (void) {
3455   struct udp_pcb *pcb = udp_new ();
3456   struct pbuf *p = pbuf_alloc (PBUF_TRANSPORT, 4, PBUF_RAM);
3457   struct ip_addr ip;
3458   struct in_addr inaddr;
3459   inet_aton ("192.168.2.123", &inaddr); /* made up address */
3460   ip.addr = inaddr.s_addr;
3461   pbuf_take (p, "TEST", 4);
3462   logger_printf ("r8169: timing_thread: id=0x%x\n", timing_id);
3463   for (;;) {
3464     sched_usleep (1000000);
3465     udp_sendto (pcb, p, &ip, 7890);
3466   }
3467 }
3468 #endif
3469 
3470 static void
3471 r8169_poll (void)
3472 {
3473   rx_int (tp);
3474   tx_int (tp);
3475 }
3476 
3477 static bool
3478 r8169_get_hwaddr (u8 addr[ETH_ADDR_LEN])
3479 {
3480   int i;
3481   for (i=0; i<ETH_ADDR_LEN; i++)
3482     addr[i] = tp->mac_addr[i];
3483   return TRUE;
3484 }
3485 
3486 extern bool
3487 r8169_init (void)
3488 {
3489   int i;
3490   if (mp_ISA_PC) {
3491     DLOG ("Requires PCI support");
3492     goto abort;
3493   }
3494 
3495   for (i=0; compatible_ids[i].vendor != 0xFFFF; i++)
3496     if (pci_find_device (compatible_ids[i].vendor, compatible_ids[i].device,
3497                          0xFF, 0xFF, 0, &device_index))
3498       break;
3499     else
3500       device_index = ~0;
3501 
3502   if (device_index == (uint)(~0)) {
3503     DLOG ("Unable to detect compatible device.");
3504     goto abort;
3505   }
3506 
3507   const struct rtl_cfg_info *cfg = &rtl_cfg_infos[compatible_ids[i].cfg];
3508   const unsigned int region = cfg->region;
3509   DLOG ("Found device_index=%d", device_index);
3510 
3511   if (!pci_get_device (device_index, &pdev)) {
3512     DLOG ("pci_get_device");
3513     goto abort;
3514   }
3515 
3516   u32 phys_addr; void *ioaddr;
3517   pci_decode_bar (pdev.index, region, &phys_addr, NULL, NULL);
3518 
3519   uint irq_line, irq_pin;
3520   pci_irq_t irq;
3521   if (!pci_get_interrupt (pdev.index, &irq_line, &irq_pin)) {
3522     DLOG ("Unable to get IRQ");
3523     goto abort;
3524   }
3525 
3526   if (pci_irq_find (pdev.bus, pdev.slot, irq_pin, &irq)) {
3527     /* use PCI routing table */
3528     DLOG ("Found PCI routing entry irq.gsi=0x%x", irq.gsi);
3529     if (!pci_irq_map_handler (&irq, irq_handler, 0x01,
3530                               IOAPIC_DESTINATION_LOGICAL,
3531                               IOAPIC_DELIVERY_FIXED)) {
3532       DLOG ("Failed to map IRQ");
3533       goto abort;
3534     }
3535     irq_line = irq.gsi;
3536     u8 vector;
3537     IOAPIC_get_GSI_mapping (irq.gsi, &vector, NULL);
3538     DLOG ("Using vector=0x%X", vector);
3539   } else {
3540     DLOG ("Unable to find PCI routing entry");
3541     goto abort;
3542   }
3543 
3544   ioaddr = map_virtual_page (phys_addr | 3);
3545 
3546   DLOG ("BAR%d phys=0x%p virt=0x%p", region, phys_addr, ioaddr);
3547 
3548   RTL_W16(IntrMask, 0x0000);
3549 
3550   /* Soft reset the chip. */
3551   RTL_W8(ChipCmd, CmdReset);
3552 
3553   /* Check that the chip has finished the reset. */
3554   for (i = 0; i < 100; i++) {
3555     if ((RTL_R8(ChipCmd) & CmdReset) == 0)
3556       break;
3557     udelay (1000);
3558   }
3559 
3560   RTL_W16(IntrStatus, 0xffff);
3561 
3562   /* enable memory mapped I/O and bus mastering */
3563   pci_write_word (pci_addr (pdev.bus, pdev.slot, pdev.func, 0x04), 0x0006);
3564 
3565   /* Allocate private data struct */
3566   pow2_alloc (sizeof (struct rtl8169_private), (u8 **) &tp);
3567   if (!tp)
3568     goto abort_virt;
3569   DLOG ("tp=0x%p (%d bytes)", tp, sizeof (struct rtl8169_private));
3570 
3571   /* Identify chip attached to board */
3572   get_mac_version(tp, ioaddr);
3573 
3574   /* Use appropriate default if unknown */
3575   if (tp->mac_version == RTL_GIGA_MAC_NONE) {
3576     DLOG ("unknown MAC, using family default");
3577     tp->mac_version = cfg->default_ver;
3578   }
3579 
3580   print_mac_version(tp);
3581 
3582   for (i = 0; i < ARRAY_SIZE(rtl_chip_info); i++) {
3583     if (tp->mac_version == rtl_chip_info[i].mac_version)
3584       break;
3585   }
3586   if (i == ARRAY_SIZE(rtl_chip_info)) {
3587     DLOG ("driver bug, MAC version not found in rtl_chip_info");
3588     goto abort_tp;
3589   }
3590   tp->chipset = i;
3591 
3592   RTL_W8(Cfg9346, Cfg9346_Unlock);
3593   RTL_W8(Config1, RTL_R8(Config1) | PMEnable);
3594   RTL_W8(Config5, RTL_R8(Config5) & PMEStatus);
3595   if ((RTL_R8(Config3) & (LinkUp | MagicPacket)) != 0)
3596     tp->features |= RTL_FEATURE_WOL;
3597   if ((RTL_R8(Config5) & (UWF | BWF | MWF)) != 0)
3598     tp->features |= RTL_FEATURE_WOL;
3599   RTL_W8(Cfg9346, Cfg9346_Lock);
3600 
3601   if ((tp->mac_version <= RTL_GIGA_MAC_VER_06) &&
3602       (RTL_R8(PHYstatus) & TBI_Enable)) {
3603     DLOG ("TBI");
3604     tp->set_speed = rtl8169_set_speed_tbi;
3605     tp->get_settings = rtl8169_gset_tbi;
3606     tp->phy_reset_enable = rtl8169_tbi_reset_enable;
3607     tp->phy_reset_pending = rtl8169_tbi_reset_pending;
3608     tp->link_ok = rtl8169_tbi_link_ok;
3609     tp->do_ioctl = rtl_tbi_ioctl;
3610 
3611     tp->phy_1000_ctrl_reg = ADVERTISE_1000FULL; /* Implied by TBI */
3612   } else {
3613     DLOG ("XMII");
3614     tp->set_speed = rtl8169_set_speed_xmii;
3615     tp->get_settings = rtl8169_gset_xmii;
3616     tp->phy_reset_enable = rtl8169_xmii_reset_enable;
3617     tp->phy_reset_pending = rtl8169_xmii_reset_pending;
3618     tp->link_ok = rtl8169_xmii_link_ok;
3619     tp->do_ioctl = rtl_xmii_ioctl;
3620   }
3621 
3622   spinlock_init (&tp->lock);
3623   tp->mmio_addr = ioaddr;
3624 
3625   /* Get MAC address */
3626   for (i = 0; i < MAC_ADDR_LEN; i++)
3627     tp->mac_addr[i] = RTL_R8(MAC0 + i);
3628   DLOG ("mac_addr=%.02X:%.02X:%.02X:%.02X:%.02X:%.02X",
3629         tp->mac_addr[0], tp->mac_addr[1], tp->mac_addr[2],
3630         tp->mac_addr[3], tp->mac_addr[4], tp->mac_addr[5]);
3631 
3632   tp->intr_mask = 0xffff;
3633   tp->align = cfg->align;
3634   tp->hw_start = cfg->hw_start;
3635   tp->intr_event = cfg->intr_event;
3636   tp->napi_event = cfg->napi_event;
3637 
3638   /* Register network device with net subsystem */
3639   tp->ethdev.recv_func = NULL;
3640   tp->ethdev.send_func = r8169_transmit;
3641   tp->ethdev.get_hwaddr_func = r8169_get_hwaddr;
3642   tp->ethdev.poll_func = r8169_poll;
3643   tp->ethdev.drvdata = tp;
3644 
3645   tp->pci_dev = &pdev;
3646   pdev.drvdata = tp;
3647 
3648   init_phy(&tp->ethdev, tp);
3649 
3650   if (!net_register_device (&tp->ethdev)) {
3651     DLOG ("registration failed");
3652     goto abort_tp;
3653   }
3654 
3655 #define ETH_FCS_LEN 4
3656 #define VLAN_ETH_HLEN 18
3657   uint mtu = MAX_FRAME_SIZE - VLAN_ETH_HLEN - ETH_FCS_LEN;
3658   uint max_frame = mtu + VLAN_ETH_HLEN + ETH_FCS_LEN;
3659   tp->rx_buf_sz = (max_frame > RX_BUF_SIZE) ? max_frame : RX_BUF_SIZE;
3660 
3661   pow2_alloc (R8169_RX_RING_BYTES, (u8 **) &tp->RxDescArray);
3662   if (!tp->RxDescArray)
3663     goto abort_tp;
3664   tp->RxPhyAddr = (uint) get_phys_addr (tp->RxDescArray);
3665 
3666   pow2_alloc (R8169_TX_RING_BYTES, (u8 **) &tp->TxDescArray);
3667   if (!tp->TxDescArray)
3668     goto abort_rxdesc;
3669   tp->TxPhyAddr = (uint) get_phys_addr (tp->TxDescArray);
3670 
3671   sint retval = rtl8169_init_ring(&tp->ethdev);
3672   if (retval < 0)
3673     goto abort_txdesc;
3674 
3675   rtl_hw_start(&tp->ethdev);
3676 
3677   //rtl8169_request_timer(dev);
3678 
3679   rtl8169_check_link_status(&tp->ethdev, tp, tp->mmio_addr);
3680 
3681   r8169_bh_id = create_kernel_thread_args ((u32) r8169_bh_thread,
3682                                            (u32) &r8169_bh_stack[1023],
3683                                            FALSE, 0);
3684   set_iovcpu (r8169_bh_id, IOVCPU_CLASS_NET);
3685 
3686 #ifdef TX_TIMING
3687   timing_id =
3688     start_kernel_thread ((u32) timing_thread, (u32) &timing_stack[1023]);
3689 #endif
3690 
3691   return TRUE;
3692  abort_txdesc:
3693   pow2_free ((u8 *) tp->TxDescArray);
3694  abort_rxdesc:
3695   pow2_free ((u8 *) tp->RxDescArray);
3696  abort_tp:
3697   pow2_free ((u8 *) tp);
3698  abort_virt:
3699   unmap_virtual_page (ioaddr);
3700  abort:
3701   return FALSE;
3702 }
3703 
3704 static const struct module_ops mod_ops = {
3705   .init = r8169_init
3706 };
3707 
3708 DEF_MODULE (net___r8169, "r8169 network driver", &mod_ops, {"net___ethernet", "pci"});
3709 
3710 
3711 /*
3712  * Local Variables:
3713  * indent-tabs-mode: nil
3714  * mode: C
3715  * c-file-style: "gnu"
3716  * c-basic-offset: 2
3717  * End:
3718  */
3719 
3720 /* vi: set et sw=2 sts=2: */