Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/dev/ic Add support for the SMC91C111 chip, with its inte...
details: https://anonhg.NetBSD.org/src/rev/6c612945c3e0
branches: trunk
changeset: 546440:6c612945c3e0
user: scw <scw%NetBSD.org@localhost>
date: Tue Apr 29 08:47:29 2003 +0000
description:
Add support for the SMC91C111 chip, with its internal PHY.
diffstat:
sys/dev/ic/smc91cxx.c | 69 +++++++++++++++++++++++++++++++++++++++++------
sys/dev/ic/smc91cxxreg.h | 28 ++++++++++++++++++-
sys/dev/ic/smc91cxxvar.h | 3 +-
3 files changed, 88 insertions(+), 12 deletions(-)
diffs (224 lines):
diff -r b0b1780611f9 -r 6c612945c3e0 sys/dev/ic/smc91cxx.c
--- a/sys/dev/ic/smc91cxx.c Tue Apr 29 07:45:23 2003 +0000
+++ b/sys/dev/ic/smc91cxx.c Tue Apr 29 08:47:29 2003 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: smc91cxx.c,v 1.44 2002/10/22 00:01:57 fair Exp $ */
+/* $NetBSD: smc91cxx.c,v 1.45 2003/04/29 08:47:29 scw Exp $ */
/*-
* Copyright (c) 1997 The NetBSD Foundation, Inc.
@@ -78,7 +78,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: smc91cxx.c,v 1.44 2002/10/22 00:01:57 fair Exp $");
+__KERNEL_RCSID(0, "$NetBSD: smc91cxx.c,v 1.45 2003/04/29 08:47:29 scw Exp $");
#include "opt_inet.h"
#include "opt_ccitt.h"
@@ -165,7 +165,7 @@
NULL, /* 6 */
"SMC91C100", /* 7 */
"SMC91C100FD", /* 8 */
- NULL, /* 9 */
+ "SMC91C111", /* 9 */
NULL, /* 10 */
NULL, /* 11 */
NULL, /* 12 */
@@ -245,7 +245,7 @@
u_int32_t miicapabilities;
u_int16_t tmp;
u_int8_t enaddr[ETHER_ADDR_LEN];
- int i, aui, mult, memsize;
+ int i, aui, mult, scale, memsize;
char pbuf[9];
/* Make sure the chip is stopped. */
@@ -268,10 +268,19 @@
printf("revision %d, ", RR_REV(tmp));
SMC_SELECT_BANK(sc, 0);
- mult = MCR_MEM_MULT(bus_space_read_2(bst, bsh, MEM_CFG_REG_W));
+ switch (sc->sc_chipid) {
+ default:
+ mult = MCR_MEM_MULT(bus_space_read_2(bst, bsh, MEM_CFG_REG_W));
+ scale = MIR_SCALE_91C9x;
+ break;
+
+ case CHIP_91C111:
+ mult = MIR_MULT_91C111;
+ scale = MIR_SCALE_91C111;
+ }
memsize = bus_space_read_2(bst, bsh, MEM_INFO_REG_W) & MIR_TOTAL_MASK;
if (memsize == 255) memsize++;
- memsize *= 256 * mult;
+ memsize *= scale * mult;
format_bytes(pbuf, sizeof(pbuf), memsize);
printf("buffer size: %s\n", pbuf);
@@ -325,8 +334,15 @@
*/
miicapabilities &= ~(BMSR_100TXFDX | BMSR_10TFDX);
case CHIP_91100FD:
+ case CHIP_91C111:
if (tmp & CR_MII_SELECT) {
- printf("default media MII\n");
+ printf("default media MII");
+ if (sc->sc_chipid == CHIP_91C111) {
+ printf(" (%s PHY)\n", (tmp & CR_AUI_SELECT) ?
+ "external" : "internal");
+ sc->sc_internal_phy = !(tmp & CR_AUI_SELECT);
+ } else
+ printf("\n");
mii_attach(&sc->sc_dev, &sc->sc_mii, miicapabilities,
MII_PHY_ANY, MII_OFFSET_ANY, 0);
if (LIST_FIRST(&sc->sc_mii.mii_phys) == NULL) {
@@ -340,6 +356,14 @@
}
sc->sc_flags |= SMC_FLAGS_HAS_MII;
break;
+ } else
+ if (sc->sc_chipid == CHIP_91C111) {
+ /*
+ * XXX: Should bring it out of low-power mode
+ */
+ printf("EPH interface in low power mode\n");
+ sc->sc_internal_phy = 0;
+ return;
}
/*FALLTHROUGH*/
default:
@@ -511,6 +535,19 @@
bus_space_write_1(bst, bsh, INTR_MASK_REG_B, 0);
/*
+ * On the 91c111, enable auto-negotiation, and set the LED
+ * status pins to something sane.
+ * XXX: Should be some way for MD code to decide the latter.
+ */
+ SMC_SELECT_BANK(sc, 0);
+ if (sc->sc_chipid == CHIP_91C111) {
+ bus_space_write_2(bst, bsh, RX_PHY_CONTROL_REG_W,
+ RPC_ANEG |
+ (RPC_LS_LINK_DETECT << RPC_LSA_SHIFT) |
+ (RPC_LS_TXRX << RPC_LSB_SHIFT));
+ }
+
+ /*
* Set current media.
*/
smc91cxx_set_media(sc, sc->sc_mii.mii_media.ifm_cur->ifm_media);
@@ -551,8 +588,14 @@
*/
SMC_SELECT_BANK(sc, 2);
- bus_space_write_1(bst, bsh, INTR_MASK_REG_B,
- IM_EPH_INT | IM_RX_OVRN_INT | IM_RCV_INT | IM_TX_INT);
+ if (sc->sc_chipid == CHIP_91C111 && sc->sc_internal_phy) {
+ bus_space_write_1(bst, bsh, INTR_MASK_REG_B,
+ IM_EPH_INT | IM_RX_OVRN_INT |
+ IM_RCV_INT | IM_TX_INT | IM_MD_INT);
+ } else {
+ bus_space_write_1(bst, bsh, INTR_MASK_REG_B,
+ IM_EPH_INT | IM_RX_OVRN_INT | IM_RCV_INT | IM_TX_INT);
+ }
/* Interface is now running, with no output active. */
ifp->if_flags |= IFF_RUNNING;
@@ -996,6 +1039,14 @@
ifp->if_timer = 0;
}
+ if (sc->sc_chipid == CHIP_91C111 && sc->sc_internal_phy &&
+ (status & IM_MD_INT)) {
+ /*
+ * Internal PHY status change
+ */
+ mii_tick(&sc->sc_mii);
+ }
+
/*
* Other errors. Reset the interface.
*/
diff -r b0b1780611f9 -r 6c612945c3e0 sys/dev/ic/smc91cxxreg.h
--- a/sys/dev/ic/smc91cxxreg.h Tue Apr 29 07:45:23 2003 +0000
+++ b/sys/dev/ic/smc91cxxreg.h Tue Apr 29 08:47:29 2003 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: smc91cxxreg.h,v 1.4 2001/06/12 15:17:23 wiz Exp $ */
+/* $NetBSD: smc91cxxreg.h,v 1.5 2003/04/29 08:47:30 scw Exp $ */
/*
* Copyright (c) 1996 Gardner Buchanan <gbuchanan%shl.com@localhost>
@@ -172,16 +172,38 @@
#define MIR_FREE_MASK 0xff00 /* Free memory pages available */
#define MIR_TOTAL_MASK 0x00ff /* Total memory pages available */
+#define MIR_MULT_91C111 1
+#define MIR_SCALE_91C9x 256
+#define MIR_SCALE_91C111 2048
/*
* Memory Configuration
*/
-#define MEM_CFG_REG_W 0x0a
+#define MEM_CFG_REG_W 0x0a
#define MCR_MEM_MULT(x) (((x)>>9)&7) /* Memory size multiplier */
#define MCR_TXRSV_MASK 0x001f /* Count of pages reserved for transmit */
+/*
+ * Receive/PHY Control Register (SM91C111 only)
+ */
+#define RX_PHY_CONTROL_REG_W 0x0a /* 91C111 only */
+
+#define RPC_LSB_SHIFT 2 /* Shift for LED-B select bits */
+#define RPC_LSA_SHIFT 5 /* Shift for LED-A select bits */
+#define RPC_LS_MASK 0x7 /* LED Select mask */
+#define RPC_LS_LINK_DETECT 0x0 /* 10/100 link detected */
+#define RPC_LS_LINK_10MBPS 0x2 /* 10 MBPS link detected */
+#define RPC_LS_FULL_DUPLEX 0x3 /* Full duplex operation */
+#define RPC_LS_TXRX 0x4 /* Tx/Rx packet */
+#define RPC_LS_LINK_100MBPS 0x5 /* 100 MBPS link detected */
+#define RPC_LS_RX 0x6 /* Rx packet */
+#define RPC_LS_TX 0x7 /* Tx packet */
+#define RPC_ANEG 0x0800 /* Autonegotiate enable */
+#define RPC_DPLX 0x1000 /* Duplex select (set = Full) */
+#define RPC_SPEED 0x2000 /* Speed (set = 100mbps) */
+
/*
* Bank 0, Register 0x0c is unused in the SMC91C92
@@ -346,6 +368,7 @@
#define IM_RX_OVRN_INT 0x10 /* Receiver was overrun */
#define IM_EPH_INT 0x20 /* Misc. EPH conditions (see CONTROL_REG_W) */
#define IM_ERCV_INT 0x40 /* not on SMC9192 */
+#define IM_MD_INT 0x80 /* SMC91C111 Internal PHY status change */
/*
@@ -396,6 +419,7 @@
#define CHIP_9195 5
#define CHIP_91100 7
#define CHIP_91100FD 8
+#define CHIP_91C111 9
/*
diff -r b0b1780611f9 -r 6c612945c3e0 sys/dev/ic/smc91cxxvar.h
--- a/sys/dev/ic/smc91cxxvar.h Tue Apr 29 07:45:23 2003 +0000
+++ b/sys/dev/ic/smc91cxxvar.h Tue Apr 29 08:47:29 2003 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: smc91cxxvar.h,v 1.10 2002/09/04 14:54:37 scw Exp $ */
+/* $NetBSD: smc91cxxvar.h,v 1.11 2003/04/29 08:47:30 scw Exp $ */
/*-
* Copyright (c) 1997 The NetBSD Foundation, Inc.
@@ -63,6 +63,7 @@
#define SMC_FLAGS_32BIT_READ 0x0008 /* reads are always 32-bits */
u_int8_t sc_chipid;
+ u_int8_t sc_internal_phy; /* 91C111 only */
#if NRND > 0
rndsource_element_t rnd_source;
Home |
Main Index |
Thread Index |
Old Index