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.
This commit is contained in:
jlemon 2001-03-14 19:50:35 +00:00
parent db4760d36b
commit 71a0040fe0
3 changed files with 74 additions and 28 deletions

View File

@ -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,13 +432,36 @@ 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 &&
(data & FXP_PHY_SERIAL_ONLY))
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.
*/
@ -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 @@ fxp_start(struct ifnet *ifp)
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 @@ fxp_start(struct ifnet *ifp)
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];
}
/*

View File

@ -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];
};

View File

@ -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 */