summaryrefslogtreecommitdiffstats
path: root/sys/dev/fxp
diff options
context:
space:
mode:
authorjlemon <jlemon@FreeBSD.org>2001-03-14 19:50:35 +0000
committerjlemon <jlemon@FreeBSD.org>2001-03-14 19:50:35 +0000
commit71a0040fe08bf4a0d07d5d4c75094e94b5715b58 (patch)
tree6cfc20a448ccddec1855373ec4db8439e59b4ce3 /sys/dev/fxp
parentdb4760d36b7961c113a683d669802cb03d229ac2 (diff)
downloadFreeBSD-src-71a0040fe08bf4a0d07d5d4c75094e94b5715b58.zip
FreeBSD-src-71a0040fe08bf4a0d07d5d4c75094e94b5715b58.tar.gz
Add some performance features to the fxp driver. If the chip is not
a 82557 (e.g.: a newer chip) then: + enable MWI, if the PCI configuration indicates the system supports it + enable usage of extended TxCB, for better performance + enable hardware flow control. FC frames will be passed up to the host only if promiscuous mode is enabled.
Diffstat (limited to 'sys/dev/fxp')
-rw-r--r--sys/dev/fxp/if_fxp.c92
-rw-r--r--sys/dev/fxp/if_fxpreg.h7
-rw-r--r--sys/dev/fxp/if_fxpvar.h3
3 files changed, 74 insertions, 28 deletions
diff --git a/sys/dev/fxp/if_fxp.c b/sys/dev/fxp/if_fxp.c
index b10c2a7..a06e5b6 100644
--- a/sys/dev/fxp/if_fxp.c
+++ b/sys/dev/fxp/if_fxp.c
@@ -1,6 +1,6 @@
/*-
- * Copyright (c) 2001 Jonathan Lemon <jlemon@freebsd.org>
* Copyright (c) 1995, David Greenman
+ * Copyright (c) 2001 Jonathan Lemon <jlemon@freebsd.org>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -432,7 +432,7 @@ fxp_attach(device_t dev)
fxp_autosize_eeprom(sc);
/*
- * Determine in whether we must use the 503 serial interface.
+ * Determine whether we must use the 503 serial interface.
*/
fxp_read_eeprom(sc, &data, 6, 1);
if ((data & FXP_PHY_DEVICE_MASK) != 0 &&
@@ -440,6 +440,29 @@ fxp_attach(device_t dev)
sc->flags &= FXP_FLAG_SERIAL_MEDIA;
/*
+ * Find out the basic controller type; we currently only
+ * differentiate between a 82557 and greater.
+ */
+ fxp_read_eeprom(sc, &data, 5, 1);
+ if ((data >> 8) == 1)
+ sc->chip = FXP_CHIP_82557;
+
+ /*
+ * If we are not a 82557 chip, we can enable extended features.
+ */
+ if (sc->chip != FXP_CHIP_82557) {
+ /*
+ * If there is a valid cacheline size (8 or 16 dwords),
+ * then turn on MWI.
+ */
+ if (pci_read_config(dev, PCIR_CACHELNSZ, 1) != 0)
+ sc->flags |= FXP_FLAG_MWI_ENABLE;
+
+ /* turn on the extended TxCB feature */
+ sc->flags |= FXP_FLAG_EXT_TXCB;
+ }
+
+ /*
* Read MAC address.
*/
fxp_read_eeprom(sc, (u_int16_t *)sc->arpcom.ac_enaddr, 0, 3);
@@ -517,10 +540,9 @@ static void
fxp_release(struct fxp_softc *sc)
{
- if (sc->miibus) {
- bus_generic_detach(sc->dev);
+ bus_generic_detach(sc->dev);
+ if (sc->miibus)
device_delete_child(sc->dev, sc->miibus);
- }
if (sc->cbl_base)
free(sc->cbl_base, M_DEVBUF);
@@ -838,8 +860,9 @@ tbdinit:
struct mbuf *mn;
/*
- * We ran out of segments. We have to recopy this mbuf
- * chain first. Bail out if we can't get the new buffers.
+ * We ran out of segments. We have to recopy this
+ * mbuf chain first. Bail out if we can't get the
+ * new buffers.
*/
MGETHDR(mn, M_DONTWAIT, MT_DATA);
if (mn == NULL) {
@@ -867,13 +890,15 @@ tbdinit:
txp->cb_status = 0;
if (sc->tx_queued != FXP_CXINT_THRESH - 1) {
txp->cb_command =
- FXP_CB_COMMAND_XMIT | FXP_CB_COMMAND_SF | FXP_CB_COMMAND_S;
+ FXP_CB_COMMAND_XMIT | FXP_CB_COMMAND_SF |
+ FXP_CB_COMMAND_S;
} else {
txp->cb_command =
- FXP_CB_COMMAND_XMIT | FXP_CB_COMMAND_SF | FXP_CB_COMMAND_S | FXP_CB_COMMAND_I;
+ FXP_CB_COMMAND_XMIT | FXP_CB_COMMAND_SF |
+ FXP_CB_COMMAND_S | FXP_CB_COMMAND_I;
/*
- * Set a 5 second timer just in case we don't hear from the
- * card again.
+ * Set a 5 second timer just in case we don't hear
+ * from the card again.
*/
ifp->if_timer = 5;
}
@@ -1328,19 +1353,6 @@ fxp_init(void *xsc)
cbp->crc16_en = 0; /* (don't) enable crc-16 algorithm */
cbp->crscdt = sc->flags & FXP_FLAG_SERIAL_MEDIA ? 1 : 0;
- /*
- * we may want to move all FC stuff to a separate section.
- * the values here are 82557 compatible.
- */
- cbp->fc_delay_lsb = 0;
- cbp->fc_delay_msb = 0x40;
- cbp->pri_fc_thresh = 0x03;
- cbp->tx_fc_dis = 0; /* (don't) disable transmit FC */
- cbp->rx_fc_restop = 0; /* (don't) enable FC stop frame */
- cbp->rx_fc_restart = 0; /* (don't) enable FC start frame */
- cbp->fc_filter = 0; /* (do) pass FC frames to host */
- cbp->pri_fc_loc = 1; /* location of priority in FC frame */
-
cbp->stripping = !prm; /* truncate rx packet to byte count */
cbp->padding = 1; /* (do) pad short tx packets */
cbp->rcv_crc_xfer = 0; /* (don't) xfer CRC to host */
@@ -1353,6 +1365,30 @@ fxp_init(void *xsc)
cbp->multi_ia = 0; /* (don't) accept multiple IAs */
cbp->mc_all = sc->flags & FXP_FLAG_ALL_MCAST ? 1 : 0;
+ if (sc->chip == FXP_CHIP_82557) {
+ /*
+ * The 82557 has no hardware flow control, the values
+ * below are the defaults for the chip.
+ */
+ cbp->fc_delay_lsb = 0;
+ cbp->fc_delay_msb = 0x40;
+ cbp->pri_fc_thresh = 3;
+ cbp->tx_fc_dis = 0;
+ cbp->rx_fc_restop = 0;
+ cbp->rx_fc_restart = 0;
+ cbp->fc_filter = 0;
+ cbp->pri_fc_loc = 1;
+ } else {
+ cbp->fc_delay_lsb = 0x1f;
+ cbp->fc_delay_msb = 0x01;
+ cbp->pri_fc_thresh = 3;
+ cbp->tx_fc_dis = 0; /* enable transmit FC */
+ cbp->rx_fc_restop = 1; /* enable FC restop frames */
+ cbp->rx_fc_restart = 1; /* enable FC restart frames */
+ cbp->fc_filter = !prm; /* drop FC frames to host */
+ cbp->pri_fc_loc = 1; /* FC pri location (byte31) */
+ }
+
/*
* Start the config command/DMA.
*/
@@ -1391,8 +1427,12 @@ fxp_init(void *xsc)
for (i = 0; i < FXP_NTXCB; i++) {
txp[i].cb_status = FXP_CB_STATUS_C | FXP_CB_STATUS_OK;
txp[i].cb_command = FXP_CB_COMMAND_NOP;
- txp[i].link_addr = vtophys(&txp[(i + 1) & FXP_TXCB_MASK].cb_status);
- txp[i].tbd_array_addr = vtophys(&txp[i].tbd[0]);
+ txp[i].link_addr =
+ vtophys(&txp[(i + 1) & FXP_TXCB_MASK].cb_status);
+ if (sc->flags & FXP_FLAG_EXT_TXCB)
+ txp[i].tbd_array_addr = vtophys(&txp[i].tbd[2]);
+ else
+ txp[i].tbd_array_addr = vtophys(&txp[i].tbd[0]);
txp[i].next = &txp[(i + 1) & FXP_TXCB_MASK];
}
/*
diff --git a/sys/dev/fxp/if_fxpreg.h b/sys/dev/fxp/if_fxpreg.h
index 3d32fb6..591b620 100644
--- a/sys/dev/fxp/if_fxpreg.h
+++ b/sys/dev/fxp/if_fxpreg.h
@@ -1,6 +1,6 @@
/*
- * Copyright (c) 2001 Jonathan Lemon <jlemon@freebsd.org>
* Copyright (c) 1995, David Greenman
+ * Copyright (c) 2001 Jonathan Lemon <jlemon@freebsd.org>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -236,7 +236,10 @@ struct fxp_cb_tx {
volatile u_int8_t tx_threshold;
volatile u_int8_t tbd_number;
/*
- * The following isn't actually part of the TxCB.
+ * The following structure isn't actually part of the TxCB,
+ * unless the extended TxCB feature is being used. In this
+ * case, the first two elements of the structure below are
+ * fetched along with the TxCB.
*/
volatile struct fxp_tbd tbd[FXP_NTXSEG];
};
diff --git a/sys/dev/fxp/if_fxpvar.h b/sys/dev/fxp/if_fxpvar.h
index 244c447..d993888 100644
--- a/sys/dev/fxp/if_fxpvar.h
+++ b/sys/dev/fxp/if_fxpvar.h
@@ -113,6 +113,7 @@ struct fxp_softc {
device_t dev;
int eeprom_size; /* size of serial EEPROM */
int suspended; /* 0 = normal 1 = suspended (APM) */
+ int chip;
int flags;
u_int32_t saved_maps[5]; /* pci data */
u_int32_t saved_biosaddr;
@@ -121,6 +122,8 @@ struct fxp_softc {
u_int8_t saved_lattimer;
};
+#define FXP_CHIP_82557 1 /* 82557 chip type */
+
#define FXP_FLAG_MWI_ENABLE 0x0001 /* MWI enable */
#define FXP_FLAG_READ_ALIGN 0x0002 /* align read access with cacheline */
#define FXP_FLAG_WRITE_ALIGN 0x0004 /* end write on cacheline */
OpenPOWER on IntegriCloud