summaryrefslogtreecommitdiffstats
path: root/sys/pci/if_xl.c
diff options
context:
space:
mode:
authorwpaul <wpaul@FreeBSD.org>1999-09-20 20:26:14 +0000
committerwpaul <wpaul@FreeBSD.org>1999-09-20 20:26:14 +0000
commitc248feb383a5c1f3b3c20ad1eb7f7082d51aa19e (patch)
tree79a4f8e9259cac15cc29b147fae61cc5bf23fc13 /sys/pci/if_xl.c
parentb2a7a63df77ed3bffd9a435a7a072fcef0d0ac84 (diff)
downloadFreeBSD-src-c248feb383a5c1f3b3c20ad1eb7f7082d51aa19e.zip
FreeBSD-src-c248feb383a5c1f3b3c20ad1eb7f7082d51aa19e.tar.gz
Close PR #13665. I managed to figure out the problem, no thanks to the
submitter, who *still* hasn't bothered to answer me back. The thing which the submitter completely failed to mention is that his 3c900B-TPO card has the transceiver selection in the EEPROM set to "auto." You can tweak the setting using the 3C90XCFG.EXE utility that 3Com provides with the card. I'm not sure if it's supposed to default to auto or if the user fiddled with it. Currently, the xl driver only does autoselection for 10/100 NICs (i.e. those with NWAY autonegotiation capabilities). For the 10baseT, 10base5, 10base2, 10baseFL and 100baseFX cards, the driver sets the default media to whatever the EEPROM transceiver selector says. The problem is that the "auto" selection is mistakenly identified as "10/100 NWAY autoselection mode" and this is not handled correctly: the default media ends up being chosen as 100baseTX, which doesn't work because we've only added 10baseT media types to the ifmedia word. This leads to a panic in ifmedia_set() (something else which the submitter never bothered to mention). A workaround for this is to re-run the 3C90XCFG.EXE utility and change the transceiver selection to something besides "auto." I have also patched the driver to watch for the "auto" setting in the non-miibus case and select a reasonable default based on the card type instead of falling through to 100baseTX and exploding. PR: misc/13665
Diffstat (limited to 'sys/pci/if_xl.c')
-rw-r--r--sys/pci/if_xl.c54
1 files changed, 38 insertions, 16 deletions
diff --git a/sys/pci/if_xl.c b/sys/pci/if_xl.c
index 36ff5a2..9f667c7 100644
--- a/sys/pci/if_xl.c
+++ b/sys/pci/if_xl.c
@@ -239,6 +239,7 @@ static int xl_list_tx_init __P((struct xl_softc *));
static int xl_list_tx_init_90xB __P((struct xl_softc *));
static void xl_wait __P((struct xl_softc *));
static void xl_mediacheck __P((struct xl_softc *));
+static void xl_choose_xcvr __P((struct xl_softc *, int));
#ifdef notdef
static void xl_testpacket __P((struct xl_softc *));
#endif
@@ -1046,7 +1047,6 @@ static int xl_probe(dev)
static void xl_mediacheck(sc)
struct xl_softc *sc;
{
- u_int16_t devid;
/*
* If some of the media options bits are set, assume they are
@@ -1079,6 +1079,16 @@ static void xl_mediacheck(sc)
"should probably consult your vendor\n", sc->xl_unit);
}
+ xl_choose_xcvr(sc, 1);
+
+ return;
+}
+
+static void xl_choose_xcvr(sc, verbose)
+ struct xl_softc *sc;
+ int verbose;
+{
+ u_int16_t devid;
/*
* Read the device ID from the EEPROM.
@@ -1092,34 +1102,42 @@ static void xl_mediacheck(sc)
case TC_DEVICEID_KRAKATOA_10BT: /* 3c900B-TPO */
sc->xl_media = XL_MEDIAOPT_BT;
sc->xl_xcvr = XL_XCVR_10BT;
- printf("xl%d: guessing 10BaseT transceiver\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing 10BaseT "
+ "transceiver\n", sc->xl_unit);
break;
case TC_DEVICEID_BOOMERANG_10BT_COMBO: /* 3c900-COMBO */
case TC_DEVICEID_KRAKATOA_10BT_COMBO: /* 3c900B-COMBO */
sc->xl_media = XL_MEDIAOPT_BT|XL_MEDIAOPT_BNC|XL_MEDIAOPT_AUI;
sc->xl_xcvr = XL_XCVR_10BT;
- printf("xl%d: guessing COMBO (AUI/BNC/TP)\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing COMBO "
+ "(AUI/BNC/TP)\n", sc->xl_unit);
break;
case TC_DEVICEID_KRAKATOA_10BT_TPC: /* 3c900B-TPC */
sc->xl_media = XL_MEDIAOPT_BT|XL_MEDIAOPT_BNC;
sc->xl_xcvr = XL_XCVR_10BT;
- printf("xl%d: guessing TPC (BNC/TP)\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing TPC (BNC/TP)\n", sc->xl_unit);
break;
case TC_DEVICEID_CYCLONE_10FL: /* 3c900B-FL */
sc->xl_media = XL_MEDIAOPT_10FL;
sc->xl_xcvr = XL_XCVR_AUI;
- printf("xl%d: guessing 10baseFL\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing 10baseFL\n", sc->xl_unit);
break;
case TC_DEVICEID_BOOMERANG_10_100BT: /* 3c905-TX */
sc->xl_media = XL_MEDIAOPT_MII;
sc->xl_xcvr = XL_XCVR_MII;
- printf("xl%d: guessing MII\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing MII\n", sc->xl_unit);
break;
case TC_DEVICEID_BOOMERANG_100BT4: /* 3c905-T4 */
case TC_DEVICEID_CYCLONE_10_100BT4: /* 3c905B-T4 */
sc->xl_media = XL_MEDIAOPT_BT4;
sc->xl_xcvr = XL_XCVR_MII;
- printf("xl%d: guessing 100BaseT4/MII\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing 100BaseT4/MII\n", sc->xl_unit);
break;
case TC_DEVICEID_HURRICANE_10_100BT: /* 3c905B-TX */
case TC_DEVICEID_HURRICANE_10_100BT_SERV:/*3c980-TX */
@@ -1128,12 +1146,15 @@ static void xl_mediacheck(sc)
case TC_DEVICEID_TORNADO_10_100BT: /* 3c905C-TX */
sc->xl_media = XL_MEDIAOPT_BTX;
sc->xl_xcvr = XL_XCVR_AUTO;
- printf("xl%d: guessing 10/100 internal\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing 10/100 internal\n", sc->xl_unit);
break;
case TC_DEVICEID_CYCLONE_10_100_COMBO: /* 3c905B-COMBO */
sc->xl_media = XL_MEDIAOPT_BTX|XL_MEDIAOPT_BNC|XL_MEDIAOPT_AUI;
sc->xl_xcvr = XL_XCVR_AUTO;
- printf("xl%d: guessing 10/100 plus BNC/AUI\n", sc->xl_unit);
+ if (verbose)
+ printf("xl%d: guessing 10/100 "
+ "plus BNC/AUI\n", sc->xl_unit);
break;
default:
printf("xl%d: unknown device ID: %x -- "
@@ -1368,6 +1389,14 @@ static int xl_attach(dev)
}
/*
+ * Sanity check. If the user has selected "auto" and this isn't
+ * a 10/100 card of some kind, we need to force the transceiver
+ * type to something sane.
+ */
+ if (sc->xl_xcvr == XL_XCVR_AUTO)
+ xl_choose_xcvr(sc, bootverbose);
+
+ /*
* Do ifmedia setup.
*/
@@ -2539,13 +2568,6 @@ static void xl_init(xsc)
if (mii != NULL)
mii_mediachg(mii);
- XL_SEL_WIN(7);
- CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_UP_STALL);
- xl_wait(sc);
- CSR_WRITE_4(sc, XL_UPLIST_PTR, vtophys(&sc->xl_ldata->xl_rx_list[0]));
- CSR_WRITE_1(sc, XL_UP_POLL, 8);
- CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_UP_UNSTALL);
- xl_wait(sc);
/* Select window 7 for normal operations. */
XL_SEL_WIN(7);
OpenPOWER on IntegriCloud