summaryrefslogtreecommitdiff
path: root/sys/dev/pci
diff options
context:
space:
mode:
authormjacob <mjacob@cvs.openbsd.org>2000-12-06 01:02:16 +0000
committermjacob <mjacob@cvs.openbsd.org>2000-12-06 01:02:16 +0000
commita3c56baf1776d67e865aedba84545540a5da2da0 (patch)
tree881c6fe4060dd572471d5702c58de4ed1cb0cf43 /sys/dev/pci
parent8fd2efa30bc0a2f8f599a4cf8129184e7b2953a1 (diff)
Merge together FreeBSD && OpenBSD versions, benefitting OpenBSD with
getting LIVENGOOD (newer chipset) support. There will be a bit more coming down the pipe with this in a couple of weeks when I get the board that does 10/100/1000 all through CAT-5 cable....
Diffstat (limited to 'sys/dev/pci')
-rw-r--r--sys/dev/pci/if_wx.c216
-rw-r--r--sys/dev/pci/if_wxreg.h47
-rw-r--r--sys/dev/pci/if_wxvar.h44
3 files changed, 219 insertions, 88 deletions
diff --git a/sys/dev/pci/if_wx.c b/sys/dev/pci/if_wx.c
index 9aced5fd9e0..cb7338ec132 100644
--- a/sys/dev/pci/if_wx.c
+++ b/sys/dev/pci/if_wx.c
@@ -1,5 +1,4 @@
-/* $OpenBSD: if_wx.c,v 1.6 2000/08/11 15:11:39 deraadt Exp $ */
-
+/* $OpenBSD: if_wx.c,v 1.7 2000/12/06 01:02:14 mjacob Exp $ */
/*
* Copyright (c) 1999, Traakan Software
* All rights reserved.
@@ -26,7 +25,6 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $FreeBSD: src/sys/pci/if_wx.c,v 1.5 2000/01/25 06:09:53 mjacob Exp $
*/
/*
@@ -182,7 +180,12 @@ wx_match(parent, match, aux)
if (PCI_VENDOR(pa->pa_id) != WX_VENDOR_INTEL) {
return (0);
}
- if (PCI_PRODUCT(pa->pa_id) != WX_PRODUCT_82452) {
+ switch (PCI_PRODUCT(pa->pa_id)) {
+ case WX_PRODUCT_82452:
+ case WX_PRODUCT_LIVENGOOD:
+ case WX_PRODUCT_82452_SC:
+ break;
+ default:
return (0);
}
return (1);
@@ -212,6 +215,7 @@ wx_attach(parent, self, aux)
printf(": can't map registers\n");
return;
}
+ printf(": Intel GigaBit Ethernet\n");
/*
* Allocate our interrupt.
@@ -229,14 +233,15 @@ wx_attach(parent, self, aux)
sc->w.ih = pci_intr_establish(pc, ih, IPL_NET, wx_intr, sc);
#endif
if (sc->w.ih == NULL) {
- printf("couldn't establish interrupt");
+ printf("%s: couldn't establish interrupt", sc->wx_name);
if (intrstr != NULL)
printf(" at %s", intrstr);
printf("\n");
return;
}
- sc->revision =
- pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_CLASS_REG) & 0xff;
+ printf("%s: interrupting at %s\n", sc->wx_name, intrstr);
+ sc->wx_idnrev = (PCI_PRODUCT(pa->pa_id) << 16) |
+ (pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_CLASS_REG) & 0xff);
data = pci_conf_read(pa->pa_pc, pa->pa_tag, PCI_BHLC_REG);
data &= ~(PCI_CACHELINE_MASK << PCI_CACHELINE_SHIFT);
@@ -247,7 +252,8 @@ wx_attach(parent, self, aux)
return;
}
- printf(": %s, address %s\n", intrstr, ether_sprintf(sc->wx_enaddr));
+ printf("%s: Ethernet address %s\n",
+ sc->wx_name, ether_sprintf(sc->wx_enaddr));
ifp = &sc->wx_if;
bcopy(sc->wx_name, ifp->if_xname, IFNAMSIZ);
@@ -534,12 +540,22 @@ static wx_softc_t *wxlist;
static int
wx_probe(device_t dev)
{
- if ((pci_get_vendor(dev) == WX_VENDOR_INTEL) &&
- (pci_get_device(dev) == WX_PRODUCT_82452)) {
- device_set_desc(dev, "Intel GigaBit Ethernet");
- return 0;
+ if (pci_get_vendor(dev) != WX_VENDOR_INTEL) {
+ return (ENXIO);
+ }
+ switch (pci_get_device(dev)) {
+ case WX_PRODUCT_82452:
+ device_set_desc(dev, "Intel GigaBit Ethernet (WISEMAN)");
+ break;
+ case WX_PRODUCT_LIVENGOOD:
+ device_set_desc(dev, "Intel GigaBit Ethernet (LIVENGOOD)");
+ case WX_PRODUCT_82452_SC:
+ device_set_desc(dev, "Intel GigaBit Ethernet (LIVENGOOD_SC)");
+ break;
+ default:
+ return (ENXIO);
}
- return (ENXIO);
+ return (0);
}
static int
@@ -548,7 +564,6 @@ wx_attach(device_t dev)
int error = 0;
wx_softc_t *tmp, *sc = device_get_softc(dev);
struct ifnet *ifp;
- int s;
u_long val;
int rid;
@@ -581,7 +596,16 @@ wx_attach(device_t dev)
}
}
- s = splimp();
+#ifdef SMPNG
+ mtx_init(&sc->wx_mtx, device_get_nameunit(dev), MTX_DEF);
+#endif
+
+ WX_LOCK(sc);
+ /*
+ * get revision && id...
+ */
+ sc->wx_idnrev = (pci_get_device(dev) << 16) | (pci_get_revid(dev));
+
/*
* Enable bus mastering, make sure that the cache line size is right.
*/
@@ -594,10 +618,6 @@ wx_attach(device_t dev)
pci_write_config(dev, PCIR_CACHELNSZ, 0x10, 1);
}
- /*
- * get revision
- */
- sc->revision = pci_read_config(dev, PCIR_CLASS, 1);
/*
* Map control/status registers.
@@ -640,6 +660,7 @@ wx_attach(device_t dev)
sc->w.arpcom.ac_enaddr[4], sc->w.arpcom.ac_enaddr[5]);
(void) snprintf(sc->wx_name, sizeof (sc->wx_name) - 1, "wx%d",
device_get_unit(dev));
+
ifp = &sc->w.arpcom.ac_if;
ifp->if_unit = device_get_unit(dev);
ifp->if_name = "wx";
@@ -652,10 +673,8 @@ wx_attach(device_t dev)
ifp->if_ioctl = wx_ioctl;
ifp->if_start = wx_start;
ifp->if_watchdog = wx_txwatchdog;
- if_attach(ifp);
ifp->if_snd.ifq_maxlen = WX_MAX_TDESC - 1;
- ether_ifattach(ifp);
- bpfattach(ifp, DLT_EN10MB, sizeof(struct ether_header));
+ ether_ifattach(ifp, ETHER_BPF_SUPPORTED);
tmp = wxlist;
if (tmp) {
while (tmp->wx_next)
@@ -665,7 +684,7 @@ wx_attach(device_t dev)
wxlist = sc;
}
out:
- splx(s);
+ WX_UNLOCK(sc);
return (error);
}
@@ -673,13 +692,14 @@ static int
wx_detach(device_t dev)
{
wx_softc_t *sc = device_get_softc(dev);
- int s = splimp();
- if_detach(&sc->w.arpcom.ac_if);
+
+ WX_LOCK(sc);
+ ether_ifdetach(&sc->w.arpcom.ac_if, ETHER_BPF_SUPPORTED);
wx_stop(sc);
bus_teardown_intr(dev, sc->w.irq, sc->w.ih);
bus_release_resource(dev, SYS_RES_IRQ, 0, sc->w.irq);
bus_release_resource(dev, SYS_RES_MEMORY, WX_MMBA, sc->w.mem);
- splx(s);
+ WX_UNLOCK(sc);
return (0);
}
@@ -721,6 +741,8 @@ wx_dring_setup(sc)
return (-1);
}
if (((u_long)sc->rdescriptors) & 0xfff) {
+ contigfree(sc->rdescriptors, len, M_DEVBUF);
+ sc->rdescriptors = NULL;
printf("%s: rcv descriptors not 4KB aligned\n", sc->wx_name);
return (-1);
}
@@ -730,10 +752,16 @@ wx_dring_setup(sc)
sc->tdescriptors = (wxtd_t *)
contigmalloc(len, M_DEVBUF, M_NOWAIT, 0, ~0, 4096, 0);
if (sc->tdescriptors == NULL) {
+ contigfree(sc->rdescriptors,
+ sizeof (wxrd_t) * WX_MAX_RDESC, M_DEVBUF);
+ sc->rdescriptors = NULL;
printf("%s: could not allocate xmt descriptors\n", sc->wx_name);
return (-1);
}
if (((u_long)sc->tdescriptors) & 0xfff) {
+ contigfree(sc->rdescriptors,
+ sizeof (wxrd_t) * WX_MAX_RDESC, M_DEVBUF);
+ sc->rdescriptors = NULL;
printf("%s: xmt descriptors not 4KB aligned\n", sc->wx_name);
return (-1);
}
@@ -746,11 +774,13 @@ wx_dring_teardown(sc)
wx_softc_t *sc;
{
if (sc->rdescriptors) {
- WXFREE(sc->rdescriptors);
+ contigfree(sc->rdescriptors,
+ sizeof (wxrd_t) * WX_MAX_RDESC, M_DEVBUF);
sc->rdescriptors = NULL;
}
if (sc->tdescriptors) {
- WXFREE(sc->tdescriptors);
+ contigfree(sc->tdescriptors,
+ sizeof (wxtd_t) * WX_MAX_TDESC, M_DEVBUF);
sc->tdescriptors = NULL;
}
}
@@ -787,9 +817,9 @@ wx_attach_common(sc)
/*
* First, check for revision support.
*/
- if (sc->revision < 2) {
- printf("%s: cannot support revision %d chips\n",
- sc->wx_name, sc->revision);
+ if (sc->wx_idnrev < WX_WISEMAN_2_0) {
+ printf("%s: cannot support ID 0x%x, revision %d chips\n",
+ sc->wx_name, sc->wx_idnrev >> 16, sc->wx_idnrev & 0xffff);
return (ENXIO);
}
@@ -1001,6 +1031,7 @@ wx_start(ifp)
wx_softc_t *sc = SOFTC_IFP(ifp);
u_int16_t cidx, nactv;
+ WX_LOCK(sc);
nactv = sc->tactive;
while (nactv < WX_MAX_TDESC) {
int ndesc;
@@ -1178,6 +1209,7 @@ again:
sc->wx_xmitblocked++;
ifp->if_flags |= IFF_OACTIVE;
}
+ WX_UNLOCK(sc);
}
/*
@@ -1190,6 +1222,7 @@ wx_intr(arg)
wx_softc_t *sc = arg;
int claimed = 0;
+ WX_ILOCK(sc);
/*
* Read interrupt cause register. Reading it clears bits.
*/
@@ -1210,6 +1243,7 @@ wx_intr(arg)
}
WX_ENABLE_INT(sc);
}
+ WX_IUNLK(sc);
return (claimed);
}
@@ -1245,11 +1279,13 @@ wx_handle_link_intr(sc)
if (sc->wx_icr & WXISR_LSC) {
if (READ_CSR(sc, WXREG_DSR) & WXDSR_LU) {
- /* printf("%s: gigabit link now up\n", sc->wx_name); */
+ if (sc->wx_debug)
+ printf("%s: gigabit link up\n", sc->wx_name);
sc->linkup = 1;
sc->wx_dcr |= (WXDCR_SWDPIO0|WXDCR_SWDPIN0);
} else {
- /* printf("%s: gigabit link now down\n", sc->wx_name); */
+ if (sc->wx_debug)
+ printf("%s: gigabit link down\n", sc->wx_name);
sc->linkup = 0;
sc->wx_dcr &= ~(WXDCR_SWDPIO0|WXDCR_SWDPIN0);
}
@@ -1280,7 +1316,7 @@ wx_check_link(sc)
sc->wx_name);
}
WRITE_CSR(sc, WXREG_XMIT_CFGW, WXTXCW_DEFAULT & ~WXTXCW_ANE);
- if (sc->revision == 2)
+ if (sc->wx_idnrev < WX_WISEMAN_2_1)
sc->wx_dcr &= ~WXDCR_TFCE;
sc->wx_dcr |= WXDCR_SLU;
WRITE_CSR(sc, WXREG_DCR, sc->wx_dcr);
@@ -1434,22 +1470,13 @@ wx_handle_rxint(sc)
m0->m_pkthdr.len = tlen - WX_CRC_LENGTH;
mb->m_len -= WX_CRC_LENGTH;
-#ifdef __OpenBSD__
- pending[npkts++] = m0;
-#else
eh = mtod(m0, struct ether_header *);
- if ((ifp->if_flags & IFF_PROMISC) &&
- (bcmp(eh->ether_dhost, sc->wx_enaddr, ETHER_ADDR_LEN) &&
- (eh->ether_dhost[0] & 1) == 0)) {
- m_freem(m0);
- if (sc->rpending) {
- m_freem(sc->rpending);
- sc->rpending = NULL;
- }
- } else {
- pending[npkts++] = m0;
- }
-#endif
+ /*
+ * No need to check for promiscous mode since
+ * the decision to keep or drop the packet is
+ * handled by ether_input()
+ */
+ pending[npkts++] = m0;
m0 = NULL;
tlen = 0;
}
@@ -1488,11 +1515,12 @@ wx_gc(sc)
wx_softc_t *sc;
{
struct ifnet *ifp = &sc->wx_if;
- txpkt_t *txpkt = sc->tbsyf;
- u_int32_t tdh = READ_CSR(sc, WXREG_TDH);
- int s;
+ txpkt_t *txpkt;
+ u_int32_t tdh;
- s = splimp();
+ WX_LOCK(sc);
+ txpkt = sc->tbsyf;
+ tdh = READ_CSR(sc, WXREG_TDH);
while (txpkt != NULL) {
u_int32_t end = txpkt->eidx, cidx = tdh;
@@ -1541,12 +1569,16 @@ wx_gc(sc)
td = &sc->tdescriptors[cidx];
if (td->status & TXSTS_EC) {
- /* printf("%s: excess collisions\n", sc->wx_name); */
+ if (sc->wx_debug)
+ printf("%s: excess collisions\n",
+ sc->wx_name);
ifp->if_collisions++;
ifp->if_oerrors++;
}
if (td->status & TXSTS_LC) {
- /* printf("%s: lost carrier\n", sc->wx_name); */
+ if (sc->wx_debug)
+ printf("%s: lost carrier\n",
+ sc->wx_name);
ifp->if_oerrors++;
}
tmp = &sc->tbase[cidx];
@@ -1570,7 +1602,7 @@ wx_gc(sc)
ifp->if_timer = 0;
ifp->if_flags &= ~IFF_OACTIVE;
}
- splx(s);
+ WX_UNLOCK(sc);
}
/*
@@ -1583,17 +1615,16 @@ wx_watchdog(arg)
void *arg;
{
wx_softc_t *sc = arg;
- int s;
- s = splimp();
+ WX_LOCK(sc);
wx_gc(sc);
wx_check_link(sc);
- splx(s);
+ WX_UNLOCK(sc);
/*
* Schedule another timeout one second from now.
*/
- TIMEOUT(sc, wx_watchdog, sc, hz);
+ VTIMEOUT(sc, wx_watchdog, sc, hz);
}
/*
@@ -1604,14 +1635,14 @@ wx_hw_stop(sc)
wx_softc_t *sc;
{
u_int32_t icr;
- if (sc->revision == 2) {
+ if (sc->wx_idnrev < WX_WISEMAN_2_1) {
wx_mwi_whackon(sc);
}
WRITE_CSR(sc, WXREG_DCR, WXDCR_RST);
DELAY(20 * 1000);
WRITE_CSR(sc, WXREG_IMASK, ~0);
icr = READ_CSR(sc, WXREG_ICR);
- if (sc->revision == 2) {
+ if (sc->wx_idnrev < WX_WISEMAN_2_1) {
wx_mwi_unwhack(sc);
}
WX_DISABLE_INT(sc);
@@ -1637,11 +1668,18 @@ wx_hw_initialize(sc)
{
int i;
+ if (IS_LIVENGOOD(sc)) {
+ if ((READ_CSR(sc, WXREG_DSR) & WXDSR_TBIMODE) == 0) {
+ printf("%s: no fibre mode detected\n", sc->wx_name);
+ return (-1);
+ }
+ }
+
WRITE_CSR(sc, WXREG_VET, 0);
for (i = 0; i < (WX_VLAN_TAB_SIZE << 2); i += 4) {
WRITE_CSR(sc, (WXREG_VFTA + i), 0);
}
- if (sc->revision == 2) {
+ if (sc->wx_idnrev < WX_WISEMAN_2_1) {
wx_mwi_whackon(sc);
WRITE_CSR(sc, WXREG_RCTL, WXRCTL_RST);
DELAY(5 * 1000);
@@ -1666,7 +1704,7 @@ wx_hw_initialize(sc)
i++;
}
- if (sc->revision == 2) {
+ if (sc->wx_idnrev < WX_WISEMAN_2_1) {
WRITE_CSR(sc, WXREG_RCTL, 0);
DELAY(1 * 1000);
wx_mwi_unwhack(sc);
@@ -1685,6 +1723,14 @@ wx_hw_initialize(sc)
WRITE_CSR(sc, WXREG_DCR, sc->wx_dcr | WXDCR_LRST);
DELAY(50 * 1000);
+
+ if (IS_LIVENGOOD(sc)) {
+ u_int16_t tew;
+ wx_read_eeprom(sc, &tew, WX_EEPROM_CTLR2_OFF, 1);
+ tew = (tew & WX_EEPROM_CTLR2_SWDPIO) << WX_EEPROM_EXT_SHIFT;
+ WRITE_CSR(sc, WXREG_EXCT, (u_int32_t)tew);
+ }
+
if (sc->wx_dcr & (WXDCR_RFCE|WXDCR_TFCE)) {
WRITE_CSR(sc, WXREG_FCAL, FC_FRM_CONST_LO);
WRITE_CSR(sc, WXREG_FCAH, FC_FRM_CONST_HI);
@@ -1695,7 +1741,8 @@ wx_hw_initialize(sc)
WRITE_CSR(sc, WXREG_FCT, 0);
}
WRITE_CSR(sc, WXREG_FLOW_XTIMER, WX_XTIMER_DFLT);
- if (sc->revision == 2) {
+
+ if (sc->wx_idnrev < WX_WISEMAN_2_1) {
WRITE_CSR(sc, WXREG_FLOW_RCV_HI, 0);
WRITE_CSR(sc, WXREG_FLOW_RCV_LO, 0);
sc->wx_dcr &= ~(WXDCR_RFCE|WXDCR_TFCE);
@@ -1812,9 +1859,9 @@ wx_init(xsc)
rxpkt_t *rxpkt;
wxrd_t *rd;
size_t len;
- int s, i, bflags;
+ int i, bflags;
- s = splimp();
+ WX_LOCK(sc);
/*
* Cancel any pending I/O by resetting things.
@@ -1828,6 +1875,7 @@ wx_init(xsc)
*/
if (wx_hw_initialize(sc)) {
+ WX_UNLOCK(sc);
return (EIO);
}
@@ -1847,6 +1895,7 @@ wx_init(xsc)
if (i != WX_MAX_RDESC) {
printf("%s: could not set up rbufs\n", sc->wx_name);
wx_stop(sc);
+ WX_UNLOCK(sc);
return (ENOMEM);
}
@@ -1865,7 +1914,11 @@ wx_init(xsc)
WRITE_CSR(sc, WXREG_TDT, 0);
WRITE_CSR(sc, WXREG_TQSA_HI, 0);
WRITE_CSR(sc, WXREG_TQSA_LO, 0);
- WRITE_CSR(sc, WXREG_TIPG, WX_TIPG_DFLT);
+ if (IS_WISEMAN(sc)) {
+ WRITE_CSR(sc, WXREG_TIPG, WX_WISEMAN_TIPG_DFLT);
+ } else {
+ WRITE_CSR(sc, WXREG_TIPG, WX_LIVENGOOD_TIPG_DFLT);
+ }
WRITE_CSR(sc, WXREG_TIDV, sc->wx_txint_delay);
WRITE_CSR(sc, WXREG_TCTL, (WXTCTL_CT(WX_COLLISION_THRESHOLD) |
WXTCTL_COLD(WX_FDX_COLLISION_DX) | WXTCTL_EN));
@@ -1891,7 +1944,6 @@ wx_init(xsc)
WRITE_CSR(sc, WXREG_RDT1, 0);
if (ifp->if_mtu > ETHERMTU) {
- /* printf("%s: enabling for jumbo packets\n", sc->wx_name); */
bflags = WXRCTL_EN | WXRCTL_LPE | WXRCTL_2KRBUF;
} else {
bflags = WXRCTL_EN | WXRCTL_2KRBUF;
@@ -1918,7 +1970,7 @@ wx_init(xsc)
ifm->ifm_media = ifm->ifm_cur->ifm_media;
wx_ifmedia_upd(ifp);
ifm->ifm_media = i;
- splx(s);
+ WX_UNLOCK(sc);
/*
* Start stats updater.
@@ -1981,9 +2033,9 @@ wx_ioctl(ifp, command, data)
{
wx_softc_t *sc = SOFTC_IFP(ifp);
struct ifreq *ifr = (struct ifreq *) data;
- int s, error = 0;
+ int error = 0;
- s = splimp();
+ WX_LOCK(sc);
switch (command) {
case SIOCSIFADDR:
#if !defined(__NetBSD__) && !defined(__OpenBSD__)
@@ -2050,7 +2102,7 @@ wx_ioctl(ifp, command, data)
error = EINVAL;
}
- (void) splx(s);
+ WX_UNLOCK(sc);
return (error);
}
@@ -2071,6 +2123,7 @@ wx_ifmedia_sts(ifp, ifmr)
struct ifnet *ifp;
struct ifmediareq *ifmr;
{
+ u_int32_t dsr;
struct wx_softc *sc = SOFTC_IFP(ifp);
ifmr->ifm_status = IFM_AVALID;
@@ -2079,7 +2132,20 @@ wx_ifmedia_sts(ifp, ifmr)
if (sc->linkup == 0)
return;
- ifmr->ifm_status |= IFM_ACTIVE|IFM_1000_SX;
- if (READ_CSR(sc, WXREG_DSR) & WXDSR_FD)
+ ifmr->ifm_status |= IFM_ACTIVE;
+ dsr = READ_CSR(sc, WXREG_DSR);
+ if (IS_LIVENGOOD(sc)) {
+ if (dsr & WXDSR_1000BT) {
+ ifmr->ifm_status |= IFM_1000_SX;
+ } else if (dsr & WXDSR_100BT) {
+ ifmr->ifm_status |= IFM_100_FX; /* ?? */
+ } else {
+ ifmr->ifm_status |= IFM_10_T; /* ?? */
+ }
+ } else {
+ ifmr->ifm_status |= IFM_1000_SX;
+ }
+ if (dsr & WXDSR_FD) {
ifmr->ifm_active |= IFM_FDX;
+ }
}
diff --git a/sys/dev/pci/if_wxreg.h b/sys/dev/pci/if_wxreg.h
index a95f0dfd64e..d07002fe05e 100644
--- a/sys/dev/pci/if_wxreg.h
+++ b/sys/dev/pci/if_wxreg.h
@@ -1,5 +1,4 @@
-/* $OpenBSD: if_wxreg.h,v 1.2 2000/07/06 06:19:08 mjacob Exp $ */
-
+/* $OpenBSD: if_wxreg.h,v 1.3 2000/12/06 01:02:15 mjacob Exp $ */
/*
* Copyright (c) 1999, Traakan Software
* All rights reserved.
@@ -26,15 +25,25 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $FreeBSD: src/sys/pci/if_wxreg.h,v 1.3 2000/01/25 04:11:33 mjacob Exp $
*/
#define WX_VENDOR_INTEL 0x8086
#define WX_PRODUCT_82452 0x1000
+#define WX_PRODUCT_LIVENGOOD 0x1001
+#define WX_PRODUCT_82452_SC 0x1003
#define WX_MMBA 0x10
#define MWI 0x10 /* Memory Write Invalidate */
#define WX_CACHELINE_SIZE 0x20
+/* Join PCI ID and revision into one value */
+#define WX_WISEMAN_0 0x10000000
+#define WX_WISEMAN_2_0 0x10000002
+#define WX_WISEMAN_2_1 0x10000003
+#define WX_LIVENGOOD 0x10010000
+
+#define IS_WISEMAN(sc) ((sc)->wx_idnrev < WX_LIVENGOOD)
+#define IS_LIVENGOOD(sc) (!IS_WISEMAN(sc))
+
/*
* Information about this chipset gathered from a released Intel Linux driver,
* which was clearly a port of an NT driver.
@@ -109,6 +118,8 @@ typedef struct {
#define WXREG_DCR 0x00000000
#define WXREG_DSR 0x00000008
#define WXREG_EECDR 0x00000010
+#define WXREG_EXCT 0x00000018
+#define WXREG_MDIC 0x00000020
#define WXREG_FCAL 0x00000028
#define WXREG_FCAH 0x0000002C
#define WXREG_FCT 0x00000030
@@ -167,6 +178,11 @@ typedef struct {
#define WXDCR_LRST 0x8 /* Link Reset */
#define WXDCR_SLU 0x40 /* Set Link Up */
#define WXDCR_ILOS 0x80 /* Invert Loss-of-Signal */
+#define WXDCR_100BT 0x100 /* LIVENGOOD: Set 100BaseT */
+#define WXDCR_1000BT 0x200 /* LIVENGOOD: Set 1000BaseT */
+#define WXDCR_BEM32 0x400 /* LIVENGOOD: Set Big Endian 32 (?) */
+#define WXDCR_FRCSPD 0x800 /* LIVENGOOD: Force Speed (?) */
+#define WXDCR_FRCDPX 0x1000 /* LIVENGOOD: Force Full Duplex */
/*
* General purpose I/O pins
@@ -203,6 +219,13 @@ typedef struct {
#define WXDSR_TXCLK 0x4 /* transmit clock running */
#define WXDSR_RBCLK 0x8 /* receive clock running */
#define WXDSR_TXOFF 0x10 /* transmit paused */
+#define WXDSR_TBIMODE 0x20 /* LIVENGOOD: Fibre Mode */
+#define WXDSR_100BT 0x40 /* LIVENGOOD: 100BaseT */
+#define WXDSR_1000BT 0x80 /* LIVENGOOD: 1000BaseT */
+#define WXDSR_ASDV 0x300 /* LIVENGOOD: ?? */
+#define WXDSR_MTXCKOK 0x400 /* LIVENGOOD: ?? */
+#define WXDSR_PCI66 0x800 /* LIVENGOOD: 66 MHz bus */
+#define WXDSR_BUS64 0x1000 /* LIVENGOOD: In 64 bit slot */
/*
* EEPROM Register Defines
@@ -238,8 +261,10 @@ typedef struct {
#define WXISR_LSC 0x4 /* link status change */
#define WXISR_RXSEQ 0x8 /* receive sequence error */
#define WXISR_RXDMT0 0x10 /* receiver ring 0 getting empty */
+#define WXISR_RXDMT1 0x20 /* receiver ring 1 getting empty */
#define WXISR_RXO 0x40 /* receiver overrun */
#define WXISR_RXT0 0x80 /* ring 0 receiver timer interrupt */
+#define WXISR_RXT1 0x100 /* ring 1 receiver timer interrupt */
#define WXISR_PCIE 0x200 /* ?? Probably PCI interface error... */
#define WXIENABLE_DEFAULT \
@@ -258,12 +283,17 @@ typedef struct {
#define WXRCTL_MPE 0x10 /* multicast promiscuous mode */
#define WXRCTL_LPE 0x20 /* large packet enable */
#define WXRCTL_BAM 0x8000 /* broadcast accept mode */
+#define WXRCTL_BSEX 0x2000000 /* LIVENGOOD: Buffer Size Extension */
-#define WXRCTL_2KRBUF (0 << 16) /* 2-Kbyte Receive Buffers */
-#define WXRCTL_1KRBUF (1 << 16) /* 1-Kbyte Receive Buffers */
+#define WXRCTL_2KRBUF (0 << 16) /* 2KB Receive Buffers */
+#define WXRCTL_1KRBUF (1 << 16) /* 1KB Receive Buffers */
#define WXRCTL_512BRBUF (2 << 16) /* 512 Byte Receive Buffers */
#define WXRCTL_256BRBUF (3 << 16) /* 256 Byte Receive Buffers */
+#define WXRCTL_4KRBUF (3 << 16) /* LIVENGOOD: 4KB Receive Buffers */
+#define WXRCTL_8KRBUF (2 << 16) /* LIVENGOOD: 8KB Receive Buffers */
+#define WXRCTL_16KRBUF (1 << 16) /* LIVENGOOD: 16KB Receive Buffers */
+
/*
* Receive Delay Timer Register bits.
@@ -329,12 +359,17 @@ typedef struct {
#define WX_EEPROM_CTLR1_SWDPIO_SHIFT 5
#define WX_EEPROM_CTLR1_ILOS (1 << 4)
+#define WX_EEPROM_CTLR2_OFF 0xF
+#define WX_EEPROM_CTLR2_SWDPIO 0xF0
+#define WX_EEPROM_EXT_SHIFT 4
+
#define WX_XTIMER_DFLT 0x100
#define WX_RCV_FLOW_HI_DFLT 0x8000
#define WX_RCV_FLOW_LO_DFLT 0x4000
-#define WX_TIPG_DFLT (10 | (2 << 10) | (10 << 20))
+#define WX_WISEMAN_TIPG_DFLT (10 | (2 << 10) | (10 << 20))
+#define WX_LIVENGOOD_TIPG_DFLT (6 | (8 << 10) | (6 << 20))
#define WX_CRC_LENGTH 4
diff --git a/sys/dev/pci/if_wxvar.h b/sys/dev/pci/if_wxvar.h
index a343ce18fb1..6295268d5b1 100644
--- a/sys/dev/pci/if_wxvar.h
+++ b/sys/dev/pci/if_wxvar.h
@@ -1,5 +1,4 @@
-/* $OpenBSD: if_wxvar.h,v 1.2 2000/07/06 06:19:08 mjacob Exp $ */
-
+/* $OpenBSD: if_wxvar.h,v 1.3 2000/12/06 01:02:15 mjacob Exp $ */
/*
* Copyright (c) 1999, Traakan Software
* All rights reserved.
@@ -26,7 +25,6 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $FreeBSD: src/sys/pci/if_wxvar.h,v 1.4 2000/01/23 03:18:14 mjacob Exp $
*/
/*
@@ -104,6 +102,7 @@ struct wxmdvar {
bus_space_handle_t sh; /* bus space handle */
struct ifmedia ifm;
struct wx_softc * next;
+ int spl;
};
#define wx_dev w.dev
#define wx_enaddr w.enaddr
@@ -123,6 +122,10 @@ struct wxmdvar {
#define VTIMEOUT(sc, func, arg, time) timeout(func, arg, time)
#define UNTIMEOUT(f, arg, sc) untimeout(f, arg)
#define INLINE inline
+#define WX_LOCK(_sc) _sc->w.spl = splimp()
+#define WX_UNLOCK(_sc) splx(_sc->w.spl)
+#define WX_ILOCK(_sc)
+#define WX_IUNLK(_sc)
#define vm_offset_t vaddr_t
#ifndef IFM_1000_SX
@@ -132,6 +135,11 @@ struct wxmdvar {
#define WRITE_CSR _write_csr
#elif defined(__FreeBSD__)
+/*
+ * Enable for FreeBSD 5.0 SMP code
+ */
+/* #define SMPNG 1 */
+
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/mbuf.h>
@@ -180,6 +188,11 @@ struct wxmdvar {
bus_space_handle_t sh; /* bus space handle */
struct ifmedia ifm;
struct wx_softc * next;
+#ifdef SMPNG
+ struct mtx wxmtx;
+#else
+ int spl;
+#endif
};
#define wx_dev w.dev
#define wx_enaddr w.arpcom.ac_enaddr
@@ -189,6 +202,7 @@ struct wxmdvar {
#define wx_if w.arpcom.ac_if
#define wx_name w.name
+#define wx_mtx w.wxmtx
#define IOCTL_CMD_TYPE u_long
#define WXMALLOC(len) malloc(len, M_DEVBUF, M_NOWAIT)
@@ -199,6 +213,18 @@ struct wxmdvar {
#define TIMEOUT(sc, func, arg, time) (sc)->w.sch = timeout(func, arg, time)
#define UNTIMEOUT(f, arg, sc) untimeout(f, arg, (sc)->w.sch)
#define INLINE __inline
+#ifdef SMPNG
+#define WX_LOCK(_sc) mtx_enter(&(_sc)->wx_mtx, MTX_DEF)
+#define WX_UNLOCK(_sc) mtx_exit(&(_sc)->wx_mtx, MTX_DEF)
+#define WX_ILOCK(_sc) mtx_enter(&(_sc)->wx_mtx, MTX_DEF)
+#define WX_IUNLK(_sc) mtx_exit(&(_sc)->wx_mtx, MTX_DEF)
+#else
+#define WX_LOCK(_sc) _sc->w.spl = splimp()
+#define WX_UNLOCK(_sc) splx(_sc->w.spl)
+#define WX_ILOCK(_sc)
+#define WX_IUNLK(_sc)
+#endif
+
#define READ_CSR(sc, reg) \
bus_space_read_4((sc)->w.st, (sc)->w.sh, (reg))
@@ -262,6 +288,7 @@ struct wxmdvar {
bus_space_handle_t sh; /* bus space handle */
struct ifmedia ifm;
struct wx_softc * next;
+ int spl;
};
#define wx_dev w.dev
#define wx_enaddr w.arpcom.ac_enaddr
@@ -281,6 +308,10 @@ struct wxmdvar {
#define VTIMEOUT(sc, func, arg, time) timeout(func, arg, time)
#define UNTIMEOUT(f, arg, sc) untimeout(f, arg)
#define INLINE inline
+#define WX_LOCK(_sc) _sc->w.spl = splimp()
+#define WX_UNLOCK(_sc) splx(_sc->w.spl)
+#define WX_ILOCK(_sc)
+#define WX_IUNLK(_sc)
#define vm_offset_t vaddr_t
#define READ_CSR _read_csr
@@ -318,16 +349,15 @@ typedef struct wx_softc {
/*
* misc goodies
*/
- u_int32_t : 17,
+ u_int32_t : 25,
wx_no_flow : 1,
wx_ilos : 1,
wx_no_ilos : 1,
wx_debug : 1,
ane_failed : 1,
linkup : 1,
- all_mcasts : 1,
- revision : 8; /* chip revision */
-
+ all_mcasts : 1;
+ u_int32_t wx_idnrev; /* chip revision && PCI ID */
u_int16_t wx_cfg1;
u_int16_t wx_txint_delay;
u_int32_t wx_ienable; /* current ienable to use */