summaryrefslogtreecommitdiff
path: root/sys
diff options
context:
space:
mode:
authorAaron Campbell <aaron@cvs.openbsd.org>2001-04-06 17:14:15 +0000
committerAaron Campbell <aaron@cvs.openbsd.org>2001-04-06 17:14:15 +0000
commitf67f86e6bf0c7085a6ee865a10e6d5e1676e4fd3 (patch)
tree55af680b03f8502c577f58ad7417ed3d6a29486d /sys
parent3bad4cdb0cb491946c31d3d458bb5e9ae4ec7419 (diff)
- For CardBus 21143 cards, parse the SROM. Makes my SMC EZ CardBus 10/100 work.
- General cleanup in the dc CardBus attachment. - Split detach up into bus-dependent and bus-independent parts. - Some function and variable renaming for consistency.
Diffstat (limited to 'sys')
-rw-r--r--sys/dev/cardbus/if_dc_cardbus.c169
-rw-r--r--sys/dev/ic/dc.c38
-rw-r--r--sys/dev/ic/dcreg.h13
-rw-r--r--sys/dev/pci/if_dc_pci.c25
4 files changed, 117 insertions, 128 deletions
diff --git a/sys/dev/cardbus/if_dc_cardbus.c b/sys/dev/cardbus/if_dc_cardbus.c
index 12c56d7a915..a221eb8dcdc 100644
--- a/sys/dev/cardbus/if_dc_cardbus.c
+++ b/sys/dev/cardbus/if_dc_cardbus.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: if_dc_cardbus.c,v 1.4 2001/03/25 06:12:28 csapuntz Exp $ */
+/* $OpenBSD: if_dc_cardbus.c,v 1.5 2001/04/06 17:14:14 aaron Exp $ */
#include <sys/param.h>
#include <sys/systm.h>
@@ -41,26 +41,29 @@
#define DC_CFDA_SUSPEND 0x80000000
#define DC_CFDA_STANDBY 0x40000000
-struct dc_cardbus_softc {
- struct dc_softc sc_dc;
- int sc_intrline;
+struct dc_cardbus_softc {
+ struct dc_softc sc_dc;
+ int sc_intrline;
- cardbus_devfunc_t sc_ct;
- cardbustag_t sc_tag;
- bus_size_t sc_mapsize;
- int sc_actype;
+ cardbus_devfunc_t sc_ct;
+ cardbustag_t sc_tag;
+ bus_size_t sc_mapsize;
+ int sc_actype;
};
-int dc_cardbus_match __P((struct device *, void *, void *));
-void dc_cardbus_attach __P((struct device *, struct device *,void *));
-int dc_cardbus_detach __P((struct device *, int));
-int dc_cardbus_activate __P((struct device *, enum devact));
-void dc_cardbus_setup __P((struct dc_cardbus_softc *csc));
+int dc_cardbus_match __P((struct device *, void *, void *));
+void dc_cardbus_attach __P((struct device *, struct device *,void *));
+int dc_cardbus_detach __P((struct device *, int));
+
+void dc_cardbus_setup __P((struct dc_cardbus_softc *csc));
+
+extern void dc_eeprom_width __P((struct dc_softc *));
+extern void dc_read_srom __P((struct dc_softc *, int));
+extern void dc_parse_21143_srom __P((struct dc_softc *));
struct cfattach dc_cardbus_ca = {
- sizeof(struct dc_cardbus_softc), dc_cardbus_match,
- dc_cardbus_attach, dc_cardbus_detach,
- dc_cardbus_activate
+ sizeof(struct dc_cardbus_softc), dc_cardbus_match, dc_cardbus_attach,
+ dc_cardbus_detach
};
struct dc_type dc_cardbus_devs[] = {
@@ -107,14 +110,35 @@ dc_cardbus_attach(parent, self, aux)
Cardbus_function_enable(ct);
+ if (Cardbus_mapreg_map(ct, PCI_CBIO,
+ PCI_MAPREG_TYPE_IO, 0, &sc->dc_btag, &sc->dc_bhandle, &addr,
+ &csc->sc_mapsize) == 0) {
+
+ csc->sc_actype = CARDBUS_IO_ENABLE;
+ } else if (Cardbus_mapreg_map(ct, PCI_CBMEM,
+ PCI_MAPREG_TYPE_MEM|PCI_MAPREG_MEM_TYPE_32BIT, 0,
+ &sc->dc_btag, &sc->dc_bhandle, &addr, &csc->sc_mapsize) == 0) {
+ csc->sc_actype = CARDBUS_MEM_ENABLE;
+ } else {
+ printf(": can\'t map device registers\n");
+ return;
+ }
+
+ csc->sc_intrline = ca->ca_intrline;
+
+ sc->dc_cachesize = pci_conf_read(cc, ca->ca_tag, DC_PCI_CFLT) & 0xFF;
+
+ dc_cardbus_setup(csc);
+
switch (PCI_VENDOR(ca->ca_id)) {
case PCI_VENDOR_DEC:
if (PCI_PRODUCT(ca->ca_id) == PCI_PRODUCT_DEC_21142) {
sc->dc_type = DC_TYPE_21143;
sc->dc_flags |= DC_TX_POLL|DC_TX_USE_TX_INTR;
sc->dc_flags |= DC_REDUCED_MII_POLL;
-
- sc->dc_pmode = DC_PMODE_MII;
+ dc_eeprom_width(sc);
+ dc_read_srom(sc, sc->dc_romwidth);
+ dc_parse_21143_srom(sc);
}
break;
case PCI_VENDOR_XIRCOM:
@@ -134,6 +158,7 @@ dc_cardbus_attach(parent, self, aux)
sc->dc_type = DC_TYPE_AN983;
sc->dc_flags |= DC_TX_USE_TX_INTR|DC_TX_ADMTEK_WAR;
sc->dc_pmode = DC_PMODE_MII;
+ dc_eeprom_width(sc);
}
break;
default:
@@ -141,41 +166,20 @@ dc_cardbus_attach(parent, self, aux)
return;
}
- if (Cardbus_mapreg_map(ct, PCI_CBIO,
- PCI_MAPREG_TYPE_IO, 0, &sc->dc_btag, &sc->dc_bhandle, &addr,
- &csc->sc_mapsize) == 0) {
-
- csc->sc_actype = CARDBUS_IO_ENABLE;
- } else if (Cardbus_mapreg_map(ct, PCI_CBMEM,
- PCI_MAPREG_TYPE_MEM|PCI_MAPREG_MEM_TYPE_32BIT, 0,
- &sc->dc_btag, &sc->dc_bhandle, &addr, &csc->sc_mapsize) == 0) {
- csc->sc_actype = CARDBUS_MEM_ENABLE;
- } else {
- printf(": can\'t map device registers\n");
- return;
- }
-
- csc->sc_intrline = ca->ca_intrline;
-
- sc->dc_cachesize = pci_conf_read(cc, ca->ca_tag, DC_PCI_CFLT) & 0xFF;
-
- dc_cardbus_setup(csc);
- cardbus_save_bar(ct);
-
/*
* set latency timer, do we really need this?
*/
- reg = cardbus_conf_read(cc, cf, ca->ca_tag, CARDBUS_BHLC_REG);
- if (CARDBUS_LATTIMER(reg) < 0x20) {
- reg &= ~(CARDBUS_LATTIMER_MASK << CARDBUS_LATTIMER_SHIFT);
- reg |= (0x20 << CARDBUS_LATTIMER_SHIFT);
- cardbus_conf_write(cc, cf, ca->ca_tag, CARDBUS_BHLC_REG, reg);
+ reg = cardbus_conf_read(cc, cf, ca->ca_tag, PCI_BHLC_REG);
+ if (PCI_LATTIMER(reg) < 0x20) {
+ reg &= ~(PCI_LATTIMER_MASK << PCI_LATTIMER_SHIFT);
+ reg |= (0x20 << PCI_LATTIMER_SHIFT);
+ cardbus_conf_write(cc, cf, ca->ca_tag, PCI_BHLC_REG, reg);
}
- sc->sc_ih = cardbus_intr_establish(cc, cf,
- ca->ca_intrline, IPL_NET, dc_intr, csc);
+ sc->sc_ih = cardbus_intr_establish(cc, cf, ca->ca_intrline, IPL_NET,
+ dc_intr, csc);
if (sc->sc_ih == NULL) {
- printf(": can\'t establish interrupt at %d\n",
+ printf(": can't establish interrupt at %d\n",
ca->ca_intrline);
return;
} else
@@ -183,8 +187,8 @@ dc_cardbus_attach(parent, self, aux)
dc_reset(sc);
- sc->dc_revision = CARDBUS_REVISION(ca->ca_class);
- dc_attach_common(sc);
+ sc->dc_revision = PCI_REVISION(ca->ca_class);
+ dc_attach(sc);
}
int
@@ -195,63 +199,22 @@ dc_cardbus_detach(self, flags)
struct dc_cardbus_softc *csc = (struct dc_cardbus_softc *)self;
struct dc_softc *sc = &csc->sc_dc;
struct cardbus_devfunc *ct = csc->sc_ct;
- struct ifnet *ifp = &sc->arpcom.ac_if;
int rv = 0;
- if (LIST_FIRST(&sc->sc_mii.mii_phys) != NULL)
- mii_detach(&sc->sc_mii, MII_PHY_ANY, MII_OFFSET_ANY);
+ rv = dc_detach(sc);
+ if (rv)
+ return (rv);
+
+ cardbus_intr_disestablish(ct->ct_cc, ct->ct_cf, sc->sc_ih);
/* unmap cardbus resources */
Cardbus_mapreg_unmap(ct,
csc->sc_actype == CARDBUS_IO_ENABLE ? PCI_CBIO : PCI_CBMEM,
sc->dc_btag, sc->dc_bhandle, csc->sc_mapsize);
- ether_ifdetach(ifp);
- if_detach(ifp);
-
return (rv);
}
-int
-dc_cardbus_activate(dev, act)
- struct device *dev;
- enum devact act;
-{
- struct dc_cardbus_softc *csc = (struct dc_cardbus_softc *)dev;
- struct dc_softc *sc = &csc->sc_dc;
- cardbus_devfunc_t ct = csc->sc_ct;
- int s;
-
- s = splnet();
- switch (act) {
- case DVACT_ACTIVATE:
- Cardbus_function_enable(ct);
- cardbus_restore_bar(ct);
- dc_cardbus_setup(csc);
- sc->sc_ih = cardbus_intr_establish(ct->ct_cc, ct->ct_cf,
- csc->sc_intrline, IPL_NET, dc_intr, csc);
- if (sc->sc_ih == NULL) {
- printf(": can\'t establish interrupt at %d\n",
- csc->sc_intrline);
- Cardbus_function_disable(ct);
- splx(s);
- return -1;
- } else
- printf("%s: interrupting at %d",
- sc->sc_dev.dv_xname, csc->sc_intrline);
- break;
-
- case DVACT_DEACTIVATE:
- cardbus_save_bar(ct);
- cardbus_intr_disestablish(ct->ct_cc, ct->ct_cf, sc->sc_ih);
- Cardbus_function_disable(ct);
- break;
- }
-
- splx(s);
- return 0;
-}
-
void
dc_cardbus_setup(csc)
struct dc_cardbus_softc *csc;
@@ -267,12 +230,10 @@ dc_cardbus_setup(csc)
if (reg | (DC_CFDA_SUSPEND|DC_CFDA_STANDBY)) {
cardbus_conf_write(cc, cf, csc->sc_tag, PCI_CFDA,
reg & ~(DC_CFDA_SUSPEND|DC_CFDA_STANDBY));
-#if 0
-printf("wakeup %x\n", cardbus_conf_read(cc, cf, csc->sc_tag, PCI_CFDA));
-#endif
}
- if (cardbus_get_capability(cc, cf, csc->sc_tag, PCI_CAP_PWRMGMT, &r, 0)) {
+ if (cardbus_get_capability(cc, cf, csc->sc_tag, PCI_CAP_PWRMGMT, &r,
+ 0)) {
r = cardbus_conf_read(cc, cf, csc->sc_tag, r + 4) & 3;
if (r) {
printf("%s: awakening from state D%d\n",
@@ -284,9 +245,9 @@ printf("wakeup %x\n", cardbus_conf_read(cc, cf, csc->sc_tag, PCI_CFDA));
(*ct->ct_cf->cardbus_ctrl)(cc, csc->sc_actype);
(*ct->ct_cf->cardbus_ctrl)(cc, CARDBUS_BM_ENABLE);
- reg = cardbus_conf_read(cc, cf, csc->sc_tag, CARDBUS_COMMAND_STATUS_REG);
- reg |= CARDBUS_COMMAND_IO_ENABLE | CARDBUS_COMMAND_MEM_ENABLE |
- CARDBUS_COMMAND_MASTER_ENABLE;
- cardbus_conf_write(cc, cf, csc->sc_tag, CARDBUS_COMMAND_STATUS_REG, reg);
- reg = cardbus_conf_read(cc, cf, csc->sc_tag, CARDBUS_COMMAND_STATUS_REG);
+ reg = cardbus_conf_read(cc, cf, csc->sc_tag, PCI_COMMAND_STATUS_REG);
+ reg |= PCI_COMMAND_IO_ENABLE | PCI_COMMAND_MEM_ENABLE |
+ PCI_COMMAND_MASTER_ENABLE;
+ cardbus_conf_write(cc, cf, csc->sc_tag, PCI_COMMAND_STATUS_REG, reg);
+ reg = cardbus_conf_read(cc, cf, csc->sc_tag, PCI_COMMAND_STATUS_REG);
}
diff --git a/sys/dev/ic/dc.c b/sys/dev/ic/dc.c
index 1282bcdbbca..761c1c5b53f 100644
--- a/sys/dev/ic/dc.c
+++ b/sys/dev/ic/dc.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: dc.c,v 1.24 2001/02/20 19:39:38 mickey Exp $ */
+/* $OpenBSD: dc.c,v 1.25 2001/04/06 17:14:13 aaron Exp $ */
/*
* Copyright (c) 1997, 1998, 1999
@@ -191,6 +191,7 @@ void dc_reset __P((struct dc_softc *));
int dc_list_rx_init __P((struct dc_softc *));
int dc_list_tx_init __P((struct dc_softc *));
+void dc_read_srom __P((struct dc_softc *, int));
void dc_parse_21143_srom __P((struct dc_softc *));
void dc_decode_leaf_sia __P((struct dc_softc *,
struct dc_eblock_sia *));
@@ -1533,6 +1534,17 @@ void dc_decode_leaf_mii(sc, l)
return;
}
+void dc_read_srom(sc, bits)
+ struct dc_softc *sc;
+ int bits;
+{
+ int size;
+
+ size = 2 << bits;
+ sc->dc_srom = malloc(size, M_DEVBUF, M_NOWAIT);
+ dc_read_eeprom(sc, (caddr_t)sc->dc_srom, 0, (size / 2), 0);
+}
+
void dc_parse_21143_srom(sc)
struct dc_softc *sc;
{
@@ -1573,15 +1585,12 @@ void dc_parse_21143_srom(sc)
* Attach the interface. Allocate softc structures, do ifmedia
* setup and ethernet/BPF attach.
*/
-void dc_attach_common(sc)
+void dc_attach(sc)
struct dc_softc *sc;
{
struct ifnet *ifp;
int error = 0, mac_offset, tmp;
- if (!DC_IS_XIRCOM(sc))
- dc_eeprom_width(sc);
-
/*
* Get station address from the EEPROM.
*/
@@ -1720,6 +1729,25 @@ fail:
return;
}
+int dc_detach(sc)
+ struct dc_softc *sc;
+{
+ struct ifnet *ifp = &sc->arpcom.ac_if;
+
+ if (LIST_FIRST(&sc->sc_mii.mii_phys) != NULL)
+ mii_detach(&sc->sc_mii, MII_PHY_ANY, MII_OFFSET_ANY);
+
+ if (sc->dc_srom)
+ free(sc->dc_srom, M_DEVBUF);
+
+ timeout_del(&sc->dc_tick_tmo);
+
+ ether_ifdetach(ifp);
+ if_detach(ifp);
+
+ return (0);
+}
+
/*
* Initialize the transmit descriptors.
*/
diff --git a/sys/dev/ic/dcreg.h b/sys/dev/ic/dcreg.h
index 5d4814e2237..f03436c6336 100644
--- a/sys/dev/ic/dcreg.h
+++ b/sys/dev/ic/dcreg.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: dcreg.h,v 1.11 2001/02/09 03:45:54 aaron Exp $ */
+/* $OpenBSD: dcreg.h,v 1.12 2001/04/06 17:14:14 aaron Exp $ */
/*
* Copyright (c) 1997, 1998, 1999
@@ -524,7 +524,7 @@ struct dc_mii_frame {
#define DC_AL_ANER 0xCC /* built in PHY autoneg expansion */
#define DC_ADMTEK_PHYADDR 0x1
-#define DC_AL_EE_NODEADDR 4
+#define DC_AL_EE_NODEADDR 8
/* End of ADMtek specific registers */
/*
@@ -691,7 +691,7 @@ struct dc_softc {
int dc_if_media;
u_int32_t dc_flags;
u_int32_t dc_txthresh;
- u_int8_t dc_srom[1024];
+ u_int8_t *dc_srom;
struct dc_mediainfo *dc_mi;
struct dc_list_data *dc_ldata;
caddr_t dc_ldata_ptr;
@@ -995,6 +995,7 @@ struct dc_eblock_reset {
#define ETHER_CRC_LEN 4
#endif
-extern void dc_attach_common __P((struct dc_softc *));
-extern int dc_intr __P((void *));
-extern void dc_reset __P((struct dc_softc *));
+extern void dc_attach __P((struct dc_softc *));
+extern int dc_detach __P((struct dc_softc *));
+extern int dc_intr __P((void *));
+extern void dc_reset __P((struct dc_softc *));
diff --git a/sys/dev/pci/if_dc_pci.c b/sys/dev/pci/if_dc_pci.c
index ff2b0aa6b38..4650d726aed 100644
--- a/sys/dev/pci/if_dc_pci.c
+++ b/sys/dev/pci/if_dc_pci.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: if_dc_pci.c,v 1.12 2001/02/09 02:23:36 aaron Exp $ */
+/* $OpenBSD: if_dc_pci.c,v 1.13 2001/04/06 17:14:14 aaron Exp $ */
/*
* Copyright (c) 1997, 1998, 1999
@@ -100,12 +100,12 @@ struct dc_type dc_devs[] = {
{ 0, 0 }
};
-int dc_pci_probe __P((struct device *, void *, void *));
-void dc_pci_attach __P((struct device *, struct device *, void *));
-void dc_pci_acpi __P((struct device *, void *));
+int dc_pci_match __P((struct device *, void *, void *));
+void dc_pci_attach __P((struct device *, struct device *, void *));
+void dc_pci_acpi __P((struct device *, void *));
-extern void dc_read_eeprom __P((struct dc_softc *, caddr_t, int, int,
- int));
+extern void dc_eeprom_width __P((struct dc_softc *));
+extern void dc_read_srom __P((struct dc_softc *, int));
extern void dc_parse_21143_srom __P((struct dc_softc *));
/*
@@ -113,7 +113,7 @@ extern void dc_parse_21143_srom __P((struct dc_softc *));
* IDs against our list and return a device name if we find a match.
*/
int
-dc_pci_probe(parent, match, aux)
+dc_pci_match(parent, match, aux)
struct device *parent;
void *match, *aux;
{
@@ -267,8 +267,7 @@ void dc_pci_attach(parent, self, aux)
sc->dc_type = DC_TYPE_21143;
sc->dc_flags |= DC_TX_POLL|DC_TX_USE_TX_INTR;
sc->dc_flags |= DC_REDUCED_MII_POLL;
- /* Save EEPROM contents so we can parse them later. */
- dc_read_eeprom(sc, (caddr_t)&sc->dc_srom, 0, 512, 0);
+ dc_read_srom(sc, 9);
}
break;
case PCI_VENDOR_DAVICOM:
@@ -407,7 +406,7 @@ void dc_pci_attach(parent, self, aux)
}
/*
- * If we discover later (in dc_attach_common()) that we have an
+ * If we discover later (in dc_attach) that we have an
* MII with no PHY, we need to have the 21143 drive the LEDs.
* Except there are some systems like the NEC VersaPro NoteBook PC
* which have no LEDs, and twiddling these bits has adverse effects
@@ -465,13 +464,13 @@ void dc_pci_attach(parent, self, aux)
sc->dc_srm_media |= IFM_ACTIVE | IFM_ETHER;
}
#endif
-
- dc_attach_common(sc);
+ dc_eeprom_width(sc);
+ dc_attach(sc);
fail:
splx(s);
}
struct cfattach dc_pci_ca = {
- sizeof(struct dc_softc), dc_pci_probe, dc_pci_attach
+ sizeof(struct dc_softc), dc_pci_match, dc_pci_attach
};