Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/netbsd-1-6]: src/sys/dev/pci Pull up revision 1.2 (requested by mrg in t...
details: https://anonhg.NetBSD.org/src/rev/c2363dfdd682
branches: netbsd-1-6
changeset: 530822:c2363dfdd682
user: tron <tron%NetBSD.org@localhost>
date: Sun Oct 05 11:51:16 2003 +0000
description:
Pull up revision 1.2 (requested by mrg in ticket #1486):
from Izumi Tsutsui <tsutsui%ceres.dti.ne.jp@localhost>:
- if_bcereg.h should only have register definitions, so declarations
of softc structure etc. should be in if_bce.c.
- The types of DMA descriptors should be u_int32_t, not unsigned long.
- netinet headers are not required here.
- Values passed via bce_tx_ring should also be byte-swapped.
- byte-swapping is not needed for bus_space access.
from me:
- KNF
- mark all magic numbers with /* MAGIC */ so they can be identified at
some point. there are 33 in total though many appear to be the same
value, or related (eg, the 6 emac points.)
leaves these issues:
- RX pre-packet headers need to be byte-swapped or not?
- PAGE_SIZE bytes are allocated for both TX and RX DMA ring descriptors,
but they should be 1024 (== sizeof(struct bce_dma_slot) * N[TR]XDESC).
- the mcast filter.
diffstat:
sys/dev/pci/if_bce.c | 539 ++++++++++++++++++++++++++++-------------------
sys/dev/pci/if_bcereg.h | 70 +------
2 files changed, 321 insertions(+), 288 deletions(-)
diffs (truncated from 1208 to 300 lines):
diff -r 1d6ff1dd5447 -r c2363dfdd682 sys/dev/pci/if_bce.c
--- a/sys/dev/pci/if_bce.c Sun Oct 05 11:49:27 2003 +0000
+++ b/sys/dev/pci/if_bce.c Sun Oct 05 11:51:16 2003 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: if_bce.c,v 1.3.2.2 2003/10/05 11:47:15 tron Exp $ */
+/* $NetBSD: if_bce.c,v 1.3.2.3 2003/10/05 11:51:16 tron Exp $ */
/*
* Copyright (c) 2003 Clifford Wright. All rights reserved.
@@ -52,13 +52,6 @@
#include <net/if_media.h>
#include <net/if_ether.h>
-#ifdef INET
-#include <netinet/in.h>
-#include <netinet/in_systm.h>
-#include <netinet/in_var.h>
-#include <netinet/ip.h>
-#endif
-
#if NBPFILTER > 0
#include <net/bpf.h>
#endif
@@ -76,38 +69,73 @@
#include <uvm/uvm_extern.h>
-static int bce_probe(struct device *, struct cfdata *, void *);
-static void bce_attach(struct device *, struct device *, void *);
-static int bce_ioctl(struct ifnet *, u_long, caddr_t);
-static void bce_start __P((struct ifnet *));
-static void bce_watchdog __P((struct ifnet *));
-static int bce_intr(void *);
-static void bce_rxintr __P((struct bce_softc *));
-static void bce_txintr __P((struct bce_softc *));
-static int bce_init __P((struct ifnet *));
-static void bce_add_mac
- __P((struct bce_softc *, unsigned char *, unsigned long));
-static int bce_add_rxbuf __P((struct bce_softc *, int));
-static void bce_rxdrain __P((struct bce_softc *));
-static void bce_stop __P((struct ifnet *, int));
-static void bce_reset __P((struct bce_softc *));
-static void bce_set_filter __P((struct ifnet *));
-static int bce_mii_read __P((struct device *, int, int));
-static void bce_mii_write __P((struct device *, int, int, int));
-static void bce_statchg __P((struct device *));
-static int bce_mediachange __P((struct ifnet *));
-static void bce_mediastatus __P((struct ifnet *, struct ifmediareq *));
-static void bce_tick __P((void *));
+/* transmit buffer max frags allowed */
+#define BCE_NTXFRAGS 16
+
+/* ring descriptor */
+struct bce_dma_slot {
+ u_int32_t ctrl;
+ u_int32_t addr;
+};
+#define CTRL_BC_MASK 0x1fff /* buffer byte count */
+#define CTRL_EOT 0x10000000 /* end of descriptor table */
+#define CTRL_IOC 0x20000000 /* interrupt on completion */
+#define CTRL_EOF 0x40000000 /* end of frame */
+#define CTRL_SOF 0x80000000 /* start of frame */
+
+/* Packet status is returned in a pre-packet header */
+struct rx_pph {
+ u_int16_t len;
+ u_int16_t flags;
+ u_int16_t pad[12];
+};
+
+/* packet status flags bits */
+#define RXF_NO 0x8 /* odd number of nibbles */
+#define RXF_RXER 0x4 /* receive symbol error */
+#define RXF_CRC 0x2 /* crc error */
+#define RXF_OV 0x1 /* fifo overflow */
+
+/* number of descriptors used in a ring */
+#define BCE_NRXDESC 128
+#define BCE_NTXDESC 128
-#define BCE_DEBUG
-#ifdef BCE_DEBUG
-#define DPRINTF(x) if (bcedebug) printf x
-#define DPRINTFN(n,x) if (bcedebug >= (n)) printf x
-int bcedebug = 0;
-#else
-#define DPRINTF(x)
-#define DPRINTFN(n,x)
-#endif
+/*
+ * Mbuf pointers. We need these to keep track of the virtual addresses
+ * of our mbuf chains since we can only convert from physical to virtual,
+ * not the other way around.
+ */
+struct bce_chain_data {
+ struct mbuf *bce_tx_chain[BCE_NTXDESC];
+ struct mbuf *bce_rx_chain[BCE_NRXDESC];
+ bus_dmamap_t bce_tx_map[BCE_NTXDESC];
+ bus_dmamap_t bce_rx_map[BCE_NRXDESC];
+};
+
+#define BCE_TIMEOUT 100 /* # 10us for mii read/write */
+
+struct bce_softc {
+ struct device bce_dev;
+ bus_space_tag_t bce_btag;
+ bus_space_handle_t bce_bhandle;
+ bus_dma_tag_t bce_dmatag;
+ struct ethercom ethercom; /* interface info */
+ void *bce_intrhand;
+ struct pci_attach_args bce_pa;
+ struct mii_data bce_mii;
+ u_int32_t bce_phy; /* eeprom indicated phy */
+ struct ifmedia bce_ifmedia; /* media info *//* Check */
+ u_int8_t enaddr[ETHER_ADDR_LEN];
+ struct bce_dma_slot *bce_rx_ring; /* receive ring */
+ struct bce_dma_slot *bce_tx_ring; /* transmit ring */
+ struct bce_chain_data bce_cdata; /* mbufs */
+ bus_dmamap_t bce_ring_map;
+ u_int32_t bce_rxin; /* last rx descriptor seen */
+ u_int32_t bce_txin; /* last tx descriptor seen */
+ int bce_txsfree; /* no. tx slots available */
+ int bce_txsnext; /* next available tx slot */
+ struct callout bce_timeout;
+};
/* for ring descriptors */
#define BCE_RXBUF_LEN (MCLBYTES - 4)
@@ -115,7 +143,7 @@
do { \
struct bce_dma_slot *__bced = &sc->bce_rx_ring[x]; \
\
- *mtod(sc->bce_cdata.bce_rx_chain[x], long *) = 0; \
+ *mtod(sc->bce_cdata.bce_rx_chain[x], u_int32_t *) = 0; \
__bced->addr = \
htole32(sc->bce_cdata.bce_rx_map[x]->dm_segs[0].ds_addr \
+ 0x40000000); \
@@ -127,7 +155,45 @@
sizeof(struct bce_dma_slot) * x, \
sizeof(struct bce_dma_slot), \
BUS_DMASYNC_PREREAD|BUS_DMASYNC_PREWRITE); \
-} while(0)
+} while (/* CONSTCOND */ 0)
+
+static int bce_probe(struct device *, struct cfdata *, void *);
+static void bce_attach(struct device *, struct device *, void *);
+static int bce_ioctl(struct ifnet *, u_long, caddr_t);
+static void bce_start(struct ifnet *);
+static void bce_watchdog(struct ifnet *);
+static int bce_intr(void *);
+static void bce_rxintr(struct bce_softc *);
+static void bce_txintr(struct bce_softc *);
+static int bce_init(struct ifnet *);
+static void bce_add_mac(struct bce_softc *, u_int8_t *, unsigned long);
+static int bce_add_rxbuf(struct bce_softc *, int);
+static void bce_rxdrain(struct bce_softc *);
+static void bce_stop(struct ifnet *, int);
+static void bce_reset(struct bce_softc *);
+static void bce_set_filter(struct ifnet *);
+static int bce_mii_read(struct device *, int, int);
+static void bce_mii_write(struct device *, int, int, int);
+static void bce_statchg(struct device *);
+static int bce_mediachange(struct ifnet *);
+static void bce_mediastatus(struct ifnet *, struct ifmediareq *);
+static void bce_tick(void *);
+
+#define BCE_DEBUG
+#ifdef BCE_DEBUG
+#define DPRINTF(x) do { \
+ if (bcedebug) \
+ printf x; \
+} while (/* CONSTCOND */ 0)
+#define DPRINTFN(n,x) do { \
+ if (bcedebug >= (n)) \
+ printf x; \
+} while (/* CONSTCOND */ 0)
+int bcedebug = 0;
+#else
+#define DPRINTF(x)
+#define DPRINTFN(n,x)
+#endif
#ifdef OLDNETBSD
struct cfattach bce_ca = {
@@ -138,10 +204,11 @@
bce_probe, bce_attach, NULL, NULL);
#endif
+
static const struct bce_product {
pci_vendor_id_t bp_vendor;
pci_product_id_t bp_product;
- const char *bp_name;
+ const char *bp_name;
} bce_products[] = {
{
PCI_VENDOR_BROADCOM,
@@ -244,9 +311,8 @@
switch (memtype) {
case PCI_MAPREG_TYPE_MEM | PCI_MAPREG_MEM_TYPE_32BIT:
case PCI_MAPREG_TYPE_MEM | PCI_MAPREG_MEM_TYPE_64BIT:
- if (pci_mapreg_map(pa, BCE_PCI_BAR0,
- memtype, 0, &sc->bce_btag, &sc->bce_bhandle,
- &memaddr, &memsize) == 0)
+ if (pci_mapreg_map(pa, BCE_PCI_BAR0, memtype, 0, &sc->bce_btag,
+ &sc->bce_bhandle, &memaddr, &memsize) == 0)
break;
default:
printf("%s: unable to find mem space\n",
@@ -321,8 +387,12 @@
* The receive, and transmit rings can not share the same
* 4k space, however both are allocated at once here.
*/
+ /*
+ * XXX PAGE_SIZE is wasteful; we only need 1KB + 1KB, but
+ * due to the limition above.
+ */
if ((error = bus_dmamem_alloc(sc->bce_dmatag,
- 2 * PAGE_SIZE, PAGE_SIZE, 2 * PAGE_SIZE,
+ 2 * PAGE_SIZE, PAGE_SIZE, 2 * PAGE_SIZE,
&seg, 1, &rseg, BUS_DMA_NOWAIT))) {
printf("%s: unable to alloc space for ring descriptors, "
"error = %d\n", sc->bce_dev.dv_xname, error);
@@ -330,25 +400,25 @@
}
/* map ring space to kernel */
if ((error = bus_dmamem_map(sc->bce_dmatag, &seg, rseg,
- 2 * PAGE_SIZE, &kva, BUS_DMA_NOWAIT))) {
+ 2 * PAGE_SIZE, &kva, BUS_DMA_NOWAIT))) {
printf("%s: unable to map DMA buffers, error = %d\n",
- sc->bce_dev.dv_xname, error);
+ sc->bce_dev.dv_xname, error);
bus_dmamem_free(sc->bce_dmatag, &seg, rseg);
return;
}
/* create a dma map for the ring */
if ((error = bus_dmamap_create(sc->bce_dmatag,
- 2 * PAGE_SIZE, 1, 2 * PAGE_SIZE, 0, BUS_DMA_NOWAIT,
+ 2 * PAGE_SIZE, 1, 2 * PAGE_SIZE, 0, BUS_DMA_NOWAIT,
&sc->bce_ring_map))) {
printf("%s: unable to create ring DMA map, error = %d\n",
- sc->bce_dev.dv_xname, error);
+ sc->bce_dev.dv_xname, error);
bus_dmamem_unmap(sc->bce_dmatag, kva, 2 * PAGE_SIZE);
bus_dmamem_free(sc->bce_dmatag, &seg, rseg);
return;
}
/* connect the ring space to the dma map */
if (bus_dmamap_load(sc->bce_dmatag, sc->bce_ring_map, kva,
- 2 * PAGE_SIZE, NULL, BUS_DMA_NOWAIT)) {
+ 2 * PAGE_SIZE, NULL, BUS_DMA_NOWAIT)) {
bus_dmamap_destroy(sc->bce_dmatag, sc->bce_ring_map);
bus_dmamem_unmap(sc->bce_dmatag, kva, 2 * PAGE_SIZE);
bus_dmamem_free(sc->bce_dmatag, &seg, rseg);
@@ -361,9 +431,9 @@
/* Create the transmit buffer DMA maps. */
for (i = 0; i < BCE_NTXDESC; i++) {
if ((error = bus_dmamap_create(sc->bce_dmatag, MCLBYTES,
- BCE_NTXFRAGS, MCLBYTES, 0, 0, &sc->bce_cdata.bce_tx_map[i])) != 0) {
+ BCE_NTXFRAGS, MCLBYTES, 0, 0, &sc->bce_cdata.bce_tx_map[i])) != 0) {
printf("%s: unable to create tx DMA map, error = %d\n",
- sc->bce_dev.dv_xname, error);
+ sc->bce_dev.dv_xname, error);
}
sc->bce_cdata.bce_tx_chain[i] = NULL;
}
@@ -371,9 +441,9 @@
/* Create the receive buffer DMA maps. */
for (i = 0; i < BCE_NRXDESC; i++) {
if ((error = bus_dmamap_create(sc->bce_dmatag, MCLBYTES, 1,
- MCLBYTES, 0, 0, &sc->bce_cdata.bce_rx_map[i])) != 0) {
+ MCLBYTES, 0, 0, &sc->bce_cdata.bce_rx_map[i])) != 0) {
printf("%s: unable to create rx DMA map, error = %d\n",
- sc->bce_dev.dv_xname, error);
+ sc->bce_dev.dv_xname, error);
}
sc->bce_cdata.bce_rx_chain[i] = NULL;
}
@@ -397,9 +467,9 @@
sc->bce_mii.mii_writereg = bce_mii_write;
sc->bce_mii.mii_statchg = bce_statchg;
ifmedia_init(&sc->bce_mii.mii_media, 0, bce_mediachange,
- bce_mediastatus);
+ bce_mediastatus);
mii_attach(&sc->bce_dev, &sc->bce_mii, 0xffffffff, MII_PHY_ANY,
- MII_OFFSET_ANY, 0);
+ MII_OFFSET_ANY, 0);
if (LIST_FIRST(&sc->bce_mii.mii_phys) == NULL) {
ifmedia_add(&sc->bce_mii.mii_media, IFM_ETHER | IFM_NONE, 0, NULL);
ifmedia_set(&sc->bce_mii.mii_media, IFM_ETHER | IFM_NONE);
@@ -407,32 +477,32 @@
ifmedia_set(&sc->bce_mii.mii_media, IFM_ETHER | IFM_AUTO);
/* get the phy */
sc->bce_phy =
- bus_space_read_1(sc->bce_btag, sc->bce_bhandle, 4096 + 90) & 0x1f;
+ bus_space_read_1(sc->bce_btag, sc->bce_bhandle, 4096 + 90) & 0x1f; /* MAGIC */
/*
* Enable activity led.
* XXX This should be in a phy driver, but not currently.
*/
Home |
Main Index |
Thread Index |
Old Index