Skip site navigation (1)Skip section navigation (2)
Date:      Sat, 26 Aug 2000 21:31:21 -0400 (EDT)
From:      Jonathan Chen <jon@spock.org>
To:        FreeBSD-gnats-submit@freebsd.org
Subject:   kern/20878: if_xl support for 3com MiniPCI cards
Message-ID:  <200008270131.VAA09387@spock.org>

next in thread | raw e-mail | index | archive | help

>Number:         20878
>Category:       kern
>Synopsis:       Patch to add support for the 3c556B MiniPCI
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          change-request
>Submitter-Id:   current-users
>Arrival-Date:   Sat Aug 26 18:40:01 PDT 2000
>Closed-Date:
>Last-Modified:
>Originator:     Jonathan Chen
>Release:        FreeBSD 4.1-20000825-STABLE i386
>Organization:
>Environment:

FreeBSD 4-STABLE / CURRENT
	

>Description:

This patch adds support for the 3com 3c556B MiniPCI 10/100 Ethernet Card.
(id: 0x6056)  This card can be found on certain models of the IBM T20
laptop.

>How-To-Repeat:

	

>Fix:

patch follows: (also available on ftp://ftp.spock.org/pub/minipci.diff)

Index: if_xl.c
===================================================================
RCS file: /export/ncvs/src/sys/pci/if_xl.c,v
retrieving revision 1.72.2.3
diff -u -r1.72.2.3 if_xl.c
--- if_xl.c	2000/08/04 23:45:29	1.72.2.3
+++ if_xl.c	2000/08/24 05:07:09
@@ -55,6 +55,7 @@
  * 3Com 3c980C-TX	10/100Mbps server adapter (Tornado ASIC)
  * 3Com 3cSOHO100-TX	10/100Mbps/RJ-45 (Hurricane ASIC)
  * 3Com 3c450-TX	10/100Mbps/RJ-45 (Tornado ASIC)
+ * 3Com 3c556B		10/100Mbps/RJ-45 (MiniPCI)
  * Dell Optiplex GX1 on-board 3c918 10/100Mbps/RJ-45
  * Dell on-board 3c920 10/100Mbps/RJ-45
  * Dell Precision on-board 3c905B 10/100Mbps/RJ-45
@@ -184,6 +185,8 @@
 		"3Com 3cSOHO100-TX OfficeConnect" },
 	{ TC_VENDORID, TC_DEVICEID_TORNADO_HOMECONNECT,
 		"3Com 3c450-TX HomeConnect" },
+	{ TC_VENDORID, TC_DEVICEID_MINIPCI_556B,
+		"3Com 3c556B MINIPCI-TX" },
 	{ 0, 0, NULL }
 };
 
@@ -530,6 +533,8 @@
 	struct xl_softc		*sc;
 	struct xl_mii_frame	frame;
 
+	sc = device_get_softc(dev);
+
 	/*
 	 * Pretend that PHYs are only available at MII address 24.
 	 * This is to guard against problems with certain 3Com ASIC
@@ -537,11 +542,9 @@
 	 * control registers at all MII addresses. This can cause
 	 * the miibus code to attach the same PHY several times over.
 	 */
-	if (phy != 24)
+	if ((!(sc->xl_flags & XL_FLAG_PHYOK)) && phy != 24)
 		return(0);
 
-	sc = device_get_softc(dev);
-
 	bzero((char *)&frame, sizeof(frame));
 
 	frame.mii_phyaddr = phy;
@@ -558,11 +561,11 @@
 	struct xl_softc		*sc;
 	struct xl_mii_frame	frame;
 
-	if (phy != 24)
-		return(0);
-
 	sc = device_get_softc(dev);
 
+	if ((!(sc->xl_flags & XL_FLAG_PHYOK)) && phy != 24)
+		return(0);
+
 	bzero((char *)&frame, sizeof(frame));
 
 	frame.mii_phyaddr = phy;
@@ -684,14 +687,21 @@
 {
 	int			err = 0, i;
 	u_int16_t		word = 0, *ptr;
-
+#define EEPROM_5BIT_OFFSET(A) ((((A) << 2) & 0x7F00) | ((A) & 0x003F))
+	/* WARNING! DANGER!
+	 * It's easy to accidentally overwrite the rom content!
+	 * Note: the 3c575 uses 8bit EEPROM offsets.
+	 */
 	XL_SEL_WIN(0);
 
 	if (xl_eeprom_wait(sc))
 		return(1);
 
+	if (sc->xl_flags & XL_FLAG_EEPROM_OFFSET_30)
+		off += 0x30;
+
 	for (i = 0; i < cnt; i++) {
-		CSR_WRITE_2(sc, XL_W0_EE_CMD, XL_EE_READ | (off + i));
+		CSR_WRITE_2(sc, XL_W0_EE_CMD, XL_EE_READ | EEPROM_5BIT_OFFSET(off + i));
 		err = xl_eeprom_wait(sc);
 		if (err)
 			break;
@@ -982,7 +992,8 @@
 	register int		i;
 
 	XL_SEL_WIN(0);
-	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_RESET);
+	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_RESET | 
+		    ((sc->xl_flags & XL_FLAG_WEIRDRESET)?0xFF:0));
 
 	for (i = 0; i < XL_TIMEOUT; i++) {
 		DELAY(10);
@@ -1184,6 +1195,12 @@
 	sc = device_get_softc(dev);
 	unit = device_get_unit(dev);
 
+	sc->xl_flags = 0;
+	switch (pci_get_device(dev)) {
+	case TC_DEVICEID_MINIPCI_556B:
+		sc->xl_flags |= XL_FLAG_FUNCREG | XL_FLAG_PHYOK | XL_FLAG_EEPROM_OFFSET_30 | XL_FLAG_WEIRDRESET;
+	}
+
 	/*
 	 * If this is a 3c905B, we have to check one extra thing.
 	 * The 905B supports power management and may be placed in
@@ -1262,12 +1279,29 @@
 	sc->xl_btag = rman_get_bustag(sc->xl_res);
 	sc->xl_bhandle = rman_get_bushandle(sc->xl_res);
 
+	if (sc->xl_flags & XL_FLAG_FUNCREG) {
+		rid = XL_PCI_FUNCMEM;
+		sc->xl_fres = bus_alloc_resource(dev, SYS_RES_MEMORY, &rid,
+		    0, ~0, 1, RF_ACTIVE);
+
+		if (sc->xl_fres == NULL) {
+			printf ("xl%d: couldn't map ports/memory\n", unit);
+			bus_release_resource(dev, XL_RES, XL_RID, sc->xl_res);
+			error = ENXIO;
+			goto fail;
+		}
+
+		sc->xl_ftag = rman_get_bustag(sc->xl_fres);
+		sc->xl_fhandle = rman_get_bushandle(sc->xl_fres);
+	}
+
 	rid = 0;
 	sc->xl_irq = bus_alloc_resource(dev, SYS_RES_IRQ, &rid, 0, ~0, 1,
 	    RF_SHAREABLE | RF_ACTIVE);
 
 	if (sc->xl_irq == NULL) {
 		printf("xl%d: couldn't map interrupt\n", unit);
+		bus_release_resource(dev, SYS_RES_MEMORY, XL_PCI_FUNCMEM, sc->xl_fres);
 		bus_release_resource(dev, XL_RES, XL_RID, sc->xl_res);
 		error = ENXIO;
 		goto fail;
@@ -1278,6 +1312,7 @@
 
 	if (error) {
 		bus_release_resource(dev, SYS_RES_IRQ, 0, sc->xl_irq);
+		bus_release_resource(dev, SYS_RES_MEMORY, XL_PCI_FUNCMEM, sc->xl_fres);
 		bus_release_resource(dev, XL_RES, XL_RID, sc->xl_res);
 		printf("xl%d: couldn't set up irq\n", unit);
 		goto fail;
@@ -1293,6 +1328,7 @@
 		printf("xl%d: failed to read station address\n", sc->xl_unit);
 		bus_teardown_intr(dev, sc->xl_irq, sc->xl_intrhand);
 		bus_release_resource(dev, SYS_RES_IRQ, 0, sc->xl_irq);
+		bus_release_resource(dev, SYS_RES_MEMORY, XL_PCI_FUNCMEM, sc->xl_fres);
 		bus_release_resource(dev, XL_RES, XL_RID, sc->xl_res);
 		error = ENXIO;
 		goto fail;
@@ -2543,6 +2579,7 @@
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_INTR_ACK|0xFF);
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_STAT_ENB|XL_INTRS);
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_INTR_ENB|XL_INTRS);
+	if (sc->xl_flags & XL_FLAG_FUNCREG) bus_space_write_4 (sc->xl_ftag, sc->xl_fhandle, 4, 0x8000);
 
 	/* Set the RX early threshold */
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_RX_SET_THRESH|(XL_PACKET_SIZE >>2));
@@ -2812,6 +2849,7 @@
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_INTR_ACK|XL_STAT_INTLATCH);
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_STAT_ENB|0);
 	CSR_WRITE_2(sc, XL_COMMAND, XL_CMD_INTR_ENB|0);
+	if (sc->xl_flags & XL_FLAG_FUNCREG) bus_space_write_4 (sc->xl_ftag, sc->xl_fhandle, 4, 0x8000);
 
 	/* Stop the stats updater. */
 	untimeout(xl_stats_update, sc, sc->xl_stat_ch);
Index: if_xlreg.h
===================================================================
RCS file: /export/ncvs/src/sys/pci/if_xlreg.h,v
retrieving revision 1.25
diff -u -r1.25 if_xlreg.h
--- if_xlreg.h	1999/12/16 18:33:57	1.25
+++ if_xlreg.h	2000/08/24 05:05:41
@@ -548,6 +548,12 @@
 #define XL_TYPE_905B	1
 #define XL_TYPE_90X	2
 
+#define XL_FLAG_FUNCREG			0x0001
+#define XL_FLAG_PHYOK			0x0002
+#define XL_FLAG_EEPROM_OFFSET_30	0x0004
+#define XL_FLAG_WEIRDRESET		0x0008
+
+
 struct xl_softc {
 	struct arpcom		arpcom;		/* interface info */
 	struct ifmedia		ifmedia;	/* media info */
@@ -569,6 +575,10 @@
 	struct xl_list_data	*xl_ldata;
 	struct xl_chain_data	xl_cdata;
 	struct callout_handle	xl_stat_ch;
+	int			xl_flags;
+	struct resource		*xl_fres;
+	bus_space_handle_t	xl_fhandle;
+	bus_space_tag_t		xl_ftag;
 };
 
 #define xl_rx_goodframes(x) \
@@ -641,6 +651,7 @@
 #define TC_DEVICEID_TORNADO_10_100BT_SERV	0x9805
 #define TC_DEVICEID_HURRICANE_SOHO100TX		0x7646
 #define TC_DEVICEID_TORNADO_HOMECONNECT		0x4500
+#define TC_DEVICEID_MINIPCI_556B		0x6056
 
 /*
  * PCI low memory base and low I/O base register, and
@@ -657,6 +668,7 @@
 #define XL_PCI_HEADER_TYPE	0x0E
 #define XL_PCI_LOIO		0x10
 #define XL_PCI_LOMEM		0x14
+#define XL_PCI_FUNCMEM		0x18
 #define XL_PCI_BIOSROM		0x30
 #define XL_PCI_INTLINE		0x3C
 #define XL_PCI_INTPIN		0x3D

>Release-Note:
>Audit-Trail:
>Unformatted:


To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-bugs" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200008270131.VAA09387>