Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/dev/pci - Add PCH2 support.



details:   https://anonhg.NetBSD.org/src/rev/b0580ff24dd8
branches:  trunk
changeset: 765127:b0580ff24dd8
user:      msaitoh <msaitoh%NetBSD.org@localhost>
date:      Fri May 20 00:57:42 2011 +0000

description:
- Add PCH2 support.
  - Add 82579 support.
  - Change PBA size for PCH from 10K to 26K as FreeBSD's em-7.1.7
- Add yet another 82567V support.
- Add ICH10+HANKSVILL support.
- Add 82580 quad-1000BaseX support.

diffstat:

 sys/dev/pci/if_wm.c |  180 +++++++++++++++++++++++++++++++++++++++++++++------
 1 files changed, 156 insertions(+), 24 deletions(-)

diffs (truncated from 520 to 300 lines):

diff -r d0a2bcf79c1f -r b0580ff24dd8 sys/dev/pci/if_wm.c
--- a/sys/dev/pci/if_wm.c       Fri May 20 00:50:47 2011 +0000
+++ b/sys/dev/pci/if_wm.c       Fri May 20 00:57:42 2011 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: if_wm.c,v 1.220 2011/02/22 21:19:30 dyoung Exp $       */
+/*     $NetBSD: if_wm.c,v 1.221 2011/05/20 00:57:42 msaitoh Exp $      */
 
 /*
  * Copyright (c) 2001, 2002, 2003, 2004 Wasabi Systems, Inc.
@@ -76,7 +76,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: if_wm.c,v 1.220 2011/02/22 21:19:30 dyoung Exp $");
+__KERNEL_RCSID(0, "$NetBSD: if_wm.c,v 1.221 2011/05/20 00:57:42 msaitoh Exp $");
 
 #include "rnd.h"
 
@@ -579,6 +579,7 @@
 static int32_t wm_read_ich8_byte(struct wm_softc *, uint32_t, uint8_t *);
 static int32_t wm_read_ich8_word(struct wm_softc *, uint32_t, uint16_t *);
 static void    wm_82547_txfifo_stall(void *);
+static void    wm_gate_hw_phy_config_ich8lan(struct wm_softc *, int);
 static int     wm_check_mng_mode(struct wm_softc *);
 static int     wm_check_mng_mode_ich8lan(struct wm_softc *);
 static int     wm_check_mng_mode_82574(struct wm_softc *);
@@ -593,8 +594,11 @@
 static void    wm_igp3_phy_powerdown_workaround_ich8lan(struct wm_softc *);
 #endif
 static void    wm_hv_phy_workaround_ich8lan(struct wm_softc *);
+static void    wm_lv_phy_workaround_ich8lan(struct wm_softc *);
 static void    wm_k1_gig_workaround_hv(struct wm_softc *, int);
+static void    wm_set_mdio_slow_mode_hv(struct wm_softc *);
 static void    wm_configure_k1_ich8lan(struct wm_softc *, int);
+static void    wm_smbustopci(struct wm_softc *);
 static void    wm_set_pcie_completion_timeout(struct wm_softc *);
 static void    wm_reset_init_script_82575(struct wm_softc *);
 static void    wm_release_manageability(struct wm_softc *);
@@ -910,6 +914,12 @@
        { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_82801J_R_BM_V,
          "82567V-2 LAN Controller",
          WM_T_ICH10,           WMP_F_1000T },
+       { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_82801J_D_BM_V,
+         "82567V-3? LAN Controller",
+         WM_T_ICH10,           WMP_F_1000T },
+       { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_HANKSVILLE,
+         "HANKSVILLE LAN Controller",
+         WM_T_ICH10,           WMP_F_1000T },
        { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_PCH_M_LM,
          "PCH LAN (82577LM) Controller",
          WM_T_PCH,             WMP_F_1000T },
@@ -921,6 +931,12 @@
          WM_T_PCH,             WMP_F_1000T },
        { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_PCH_D_DC,
          "PCH LAN (82578DC) Controller",
+         WM_T_PCH2,            WMP_F_1000T },
+       { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_PCH2_LV_LM,
+         "PCH2 LAN (82579LM) Controller",
+         WM_T_PCH2,            WMP_F_1000T },
+       { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_PCH2_LV_V,
+         "PCH2 LAN (82579V) Controller",
          WM_T_PCH,             WMP_F_1000T },
        { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_82575EB_COPPER,
          "82575EB dual-1000baseT Ethernet",
@@ -988,6 +1004,9 @@
        { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_82580_ER_DUAL,
          "82580 dual-1000BaseT Ethernet",
          WM_T_82580ER,         WMP_F_1000T },
+       { PCI_VENDOR_INTEL,     PCI_PRODUCT_INTEL_82580_QUAD_FIBER,
+         "82580 quad-1000BaseX Ethernet",
+         WM_T_82580,           WMP_F_1000X },
        { 0,                    0,
          NULL,
          0,                    0 },
@@ -1284,9 +1303,10 @@
                sc->sc_flags |= WM_F_PCIE;
                if ((sc->sc_type != WM_T_ICH8) && (sc->sc_type != WM_T_ICH9)
                    && (sc->sc_type != WM_T_ICH10)
-                   && (sc->sc_type != WM_T_PCH)) {
+                   && (sc->sc_type != WM_T_PCH)
+                   && (sc->sc_type != WM_T_PCH2)) {
                        sc->sc_flags |= WM_F_EEPROM_SEMAPHORE;
-                       /* ICH* and PCH have no PCIe capability registers */
+                       /* ICH* and PCH* have no PCIe capability registers */
                        if (pci_get_capability(pa->pa_pc, pa->pa_tag,
                                PCI_CAP_PCIEXPRESS, &sc->sc_pcixe_capoff,
                                NULL) == 0)
@@ -1452,6 +1472,10 @@
        CSR_READ(sc, WMREG_COLC);
        CSR_READ(sc, WMREG_RXERRC);
 
+       /* get PHY control from SMBus to PCIe */
+       if ((sc->sc_type == WM_T_PCH) || (sc->sc_type == WM_T_PCH2))
+               wm_smbustopci(sc);
+
        /*
         * Reset the chip to a known state.
         */
@@ -1468,6 +1492,7 @@
        case WM_T_ICH9:
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                if (wm_check_mng_mode(sc) != 0)
                        wm_get_hw_control(sc);
                break;
@@ -1542,6 +1567,7 @@
        case WM_T_ICH9:
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                /* FLASH */
                sc->sc_flags |= WM_F_EEPROM_FLASH | WM_F_SWFWHW_SYNC;
                memtype = pci_mapreg_type(pa->pa_pc, pa->pa_tag, WM_ICH8_FLASH);
@@ -1681,6 +1707,7 @@
        case WM_T_ICH9:
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                apme_mask = WUC_APME;
                eeprom_data = CSR_READ(sc, WMREG_WUC);
                break;
@@ -1782,7 +1809,7 @@
         */
        if (sc->sc_type == WM_T_ICH8 || sc->sc_type == WM_T_ICH9
            || sc->sc_type == WM_T_ICH10 || sc->sc_type == WM_T_PCH
-           || sc->sc_type == WM_T_82573
+           || sc->sc_type == WM_T_PCH2 || sc->sc_type == WM_T_82573
            || sc->sc_type == WM_T_82574 || sc->sc_type == WM_T_82583) {
                /* STATUS_TBIMODE reserved/reused, can't rely on it */
                wm_gmii_mediainit(sc, wmp->wmp_product);
@@ -1861,6 +1888,7 @@
        case WM_T_80003:
        case WM_T_ICH9:
        case WM_T_ICH10:
+       case WM_T_PCH2: /* PCH2 supports 9K frame size */
                /* XXX limited to 9234 */
                sc->sc_ethercom.ec_capabilities |= ETHERCAP_JUMBO_MTU;
                break;
@@ -2351,6 +2379,21 @@
        splx(s);
 }
 
+static void
+wm_gate_hw_phy_config_ich8lan(struct wm_softc *sc, int on)
+{
+       uint32_t reg;
+
+       reg = CSR_READ(sc, WMREG_EXTCNFCTR);
+
+       if (on != 0)
+               reg |= EXTCNFCTR_GATE_PHY_CFG;
+       else
+               reg &= ~EXTCNFCTR_GATE_PHY_CFG;
+
+       CSR_WRITE(sc, WMREG_EXTCNFCTR, reg);
+}
+
 /*
  * wm_82547_txfifo_bugchk:
  *
@@ -3438,8 +3481,10 @@
                break;
        case WM_T_ICH9:
        case WM_T_ICH10:
+               sc->sc_pba = PBA_10K;
        case WM_T_PCH:
-               sc->sc_pba = PBA_10K;
+       case WM_T_PCH2:
+               sc->sc_pba = PBA_26K;
                break;
        default:
                sc->sc_pba = sc->sc_ethercom.ec_if.if_mtu > 8192 ?
@@ -3550,15 +3595,18 @@
        case WM_T_ICH9:
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                reg = CSR_READ(sc, WMREG_CTRL) | CTRL_RST;
                if (wm_check_reset_block(sc) == 0) {
-                       if (sc->sc_type >= WM_T_PCH) {
-                               uint32_t status;
-
-                               status = CSR_READ(sc, WMREG_STATUS);
-                               CSR_WRITE(sc, WMREG_STATUS,
-                                   status & ~STATUS_PHYRA);
-                       }
+                       /*
+                        * Gate automatic PHY configuration by hardware on
+                        * manaed 82579
+                        */
+                       if ((sc->sc_type == WM_T_PCH2)
+                           && ((CSR_READ(sc, WMREG_FWSM) & FWSM_FW_VALID)
+                               != 0))
+                               wm_gate_hw_phy_config_ich8lan(sc, 1);
+
 
                        reg |= CTRL_PHY_RESET;
                        phy_reset = 1;
@@ -3650,6 +3698,7 @@
                break;
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                wm_lan_init_done(sc);
                break;
        default:
@@ -3776,6 +3825,7 @@
        case WM_T_ICH9:
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                if (wm_check_mng_mode(sc) != 0)
                        wm_get_hw_control(sc);
                break;
@@ -3789,7 +3839,7 @@
 
        reg = CSR_READ(sc, WMREG_CTRL_EXT);
        /* Enable PHY low-power state when MAC is at D3 w/o WoL */
-       if (sc->sc_type == WM_T_PCH)
+       if ((sc->sc_type == WM_T_PCH) && (sc->sc_type == WM_T_PCH2))
                CSR_WRITE(sc, WMREG_CTRL_EXT, reg | CTRL_EXT_PHYPDEN);
 
        /* Initialize the transmit descriptor ring. */
@@ -3919,7 +3969,8 @@
         * XXX Values could probably stand some tuning.
         */
        if ((sc->sc_type != WM_T_ICH8) && (sc->sc_type != WM_T_ICH9)
-           && (sc->sc_type != WM_T_ICH10) && (sc->sc_type != WM_T_PCH)) {
+           && (sc->sc_type != WM_T_ICH10) && (sc->sc_type != WM_T_PCH)
+           && (sc->sc_type != WM_T_PCH2)) {
                CSR_WRITE(sc, WMREG_FCAL, FCAL_CONST);
                CSR_WRITE(sc, WMREG_FCAH, FCAH_CONST);
                CSR_WRITE(sc, WMREG_FCT, ETHERTYPE_FLOWCONTROL);
@@ -3951,6 +4002,7 @@
                case WM_T_ICH9:
                case WM_T_ICH10:
                case WM_T_PCH:
+               case WM_T_PCH2:
                        /*
                         * Set the mac to wait the maximum time between each
                         * iteration and increase the max iterations when
@@ -4014,7 +4066,8 @@
        CSR_WRITE(sc, WMREG_IMS, sc->sc_icr);
 
        if ((sc->sc_type == WM_T_ICH8) || (sc->sc_type == WM_T_ICH9)
-           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH)) {
+           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH)
+                || (sc->sc_type == WM_T_PCH2)) {
                reg = CSR_READ(sc, WMREG_KABGTXD);
                reg |= KABGTXD_BGSQLBIAS;
                CSR_WRITE(sc, WMREG_KABGTXD, reg);
@@ -4279,6 +4332,7 @@
        switch (sc->sc_type) {
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                for (i = 0; i < WM_ICH8_LAN_INIT_TIMEOUT; i++) {
                        reg = CSR_READ(sc, WMREG_STATUS);
                        if ((reg & STATUS_LAN_INIT_DONE) != 0)
@@ -4356,6 +4410,7 @@
        case WM_T_ICH9:
        case WM_T_ICH10:
        case WM_T_PCH:
+       case WM_T_PCH2:
                if (sc->sc_type >= WM_T_PCH) {
                        reg = CSR_READ(sc, WMREG_STATUS);
                        if ((reg & STATUS_PHYRA) != 0)
@@ -4670,7 +4725,8 @@
                return 1;
 
        if ((sc->sc_type == WM_T_ICH8) || (sc->sc_type == WM_T_ICH9)
-           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH))
+           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH)
+                || (sc->sc_type == WM_T_PCH2))
                rv = wm_read_eeprom_ich8(sc, word, wordcnt, data);
        else if (sc->sc_flags & WM_F_EEPROM_EERDEEWR)
                rv = wm_read_eeprom_eerd(sc, word, wordcnt, data);
@@ -4946,7 +5002,8 @@
        uint32_t hash;
 
        if ((sc->sc_type == WM_T_ICH8) || (sc->sc_type == WM_T_ICH9)
-           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH)) {
+           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH)
+           || (sc->sc_type == WM_T_PCH2)) {
                hash = (enaddr[4] >> ich8_lo_shift[sc->sc_mchash_type]) |
                    (((uint16_t) enaddr[5]) << ich8_hi_shift[sc->sc_mchash_type]);
                return (hash & 0x3ff);
@@ -4992,7 +5049,8 @@
         * clear the remaining slots.
         */
        if ((sc->sc_type == WM_T_ICH8) || (sc->sc_type == WM_T_ICH9)
-           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH))
+           || (sc->sc_type == WM_T_ICH10) || (sc->sc_type == WM_T_PCH)
+           || (sc->sc_type == WM_T_PCH2))
                size = WM_ICH8_RAL_TABSIZE;
        else
                size = WM_RAL_TABSIZE;
@@ -5001,7 +5059,8 @@
                wm_set_ral(sc, NULL, i);



Home | Main Index | Thread Index | Old Index