Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/arm/ep93xx dont use TX intrs and various other perf...



details:   https://anonhg.NetBSD.org/src/rev/38f9fab53d92
branches:  trunk
changeset: 573002:38f9fab53d92
user:      joff <joff%NetBSD.org@localhost>
date:      Mon Jan 17 02:32:29 2005 +0000

description:
dont use TX intrs and various other performance improvements

diffstat:

 sys/arch/arm/ep93xx/epe.c    |  200 +++++++++++++++++++++++++-----------------
 sys/arch/arm/ep93xx/epereg.h |    4 +-
 sys/arch/arm/ep93xx/epevar.h |    3 +-
 3 files changed, 122 insertions(+), 85 deletions(-)

diffs (truncated from 420 to 300 lines):

diff -r 5ac36d5a376f -r 38f9fab53d92 sys/arch/arm/ep93xx/epe.c
--- a/sys/arch/arm/ep93xx/epe.c Mon Jan 17 01:48:56 2005 +0000
+++ b/sys/arch/arm/ep93xx/epe.c Mon Jan 17 02:32:29 2005 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: epe.c,v 1.1 2004/12/22 19:11:10 joff Exp $     */
+/*     $NetBSD: epe.c,v 1.2 2005/01/17 02:32:29 joff Exp $     */
 
 /*
  * Copyright (c) 2004 Jesse Off
@@ -34,7 +34,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: epe.c,v 1.1 2004/12/22 19:11:10 joff Exp $");
+__KERNEL_RCSID(0, "$NetBSD: epe.c,v 1.2 2005/01/17 02:32:29 joff Exp $");
 
 #include <sys/types.h>
 #include <sys/param.h>
@@ -89,19 +89,34 @@
 #include <ipkdb/ipkdb.h>
 #endif
 
+#include <arm/ep93xx/ep93xxreg.h>
 #include <arm/ep93xx/epereg.h> 
 #include <arm/ep93xx/epevar.h> 
 
+#ifndef EPE_FAST
+#define EPE_FAST
+#endif
 
+#ifndef EPE_FAST
 #define EPE_READ(x) \
        bus_space_read_4(sc->sc_iot, sc->sc_ioh, (EPE_ ## x))
 #define EPE_WRITE(x, y) \
        bus_space_write_4(sc->sc_iot, sc->sc_ioh, (EPE_ ## x), (y))
+#define CTRLPAGE_DMASYNC(x, y, z) \
+       bus_dmamap_sync(sc->sc_dmat, sc->ctrlpage_dmamap, (x), (y), (z))
+#else
+#define EPE_READ(x) *(__volatile u_int32_t *) \
+       (EP93XX_AHB_VBASE + EP93XX_AHB_EPE + (EPE_ ## x))
+#define EPE_WRITE(x, y) *(__volatile u_int32_t *) \
+       (EP93XX_AHB_VBASE + EP93XX_AHB_EPE + (EPE_ ## x)) = y
+#define CTRLPAGE_DMASYNC(x, y, z)
+#endif /* ! EPE_FAST */
 
 static int     epe_match(struct device *, struct cfdata *, void *);
 static void    epe_attach(struct device *, struct device *, void *);
 static void    epe_init(struct epe_softc *);
 static int      epe_intr(void* arg);
+static int     epe_gctx(struct epe_softc *);
 static int     epe_mediachange(struct ifnet *);
 static void    epe_mediastatus(struct ifnet *, struct ifmediareq *);
 int            epe_mii_readreg (struct device *, int, int);
@@ -146,6 +161,54 @@
 }
 
 static int
+epe_gctx(struct epe_softc *sc)
+{
+       struct ifnet * ifp = &sc->sc_ec.ec_if;
+       u_int32_t *cur, ndq = 0;
+
+       /* Handle transmit completions */
+       cur = (u_int32_t *)(EPE_READ(TXStsQCurAdd) -
+               sc->ctrlpage_dsaddr + sc->ctrlpage);
+
+       if (sc->TXStsQ_cur != cur) { 
+               CTRLPAGE_DMASYNC(TX_QLEN * 2 * sizeof(u_int32_t), 
+                       TX_QLEN * sizeof(u_int32_t), BUS_DMASYNC_PREREAD);
+       } else {
+               return 0;
+       }
+
+       do {
+               u_int32_t tbi = *sc->TXStsQ_cur & 0x7fff;
+               struct mbuf *m = sc->txq[tbi].m;
+
+               if ((*sc->TXStsQ_cur & TXStsQ_TxWE) == 0) {
+                       ifp->if_oerrors++;
+               }
+               bus_dmamap_unload(sc->sc_dmat, sc->txq[tbi].m_dmamap);
+               m_freem(m);
+               do {
+                       sc->txq[tbi].m = NULL;
+                       ndq++;
+                       tbi = (tbi + 1) % TX_QLEN;
+               } while (sc->txq[tbi].m == m);
+
+               ifp->if_opackets++;
+               sc->TXStsQ_cur++;
+               if (sc->TXStsQ_cur >= sc->TXStsQ + TX_QLEN) {
+                       sc->TXStsQ_cur = sc->TXStsQ;
+               }
+       } while (sc->TXStsQ_cur != cur); 
+
+       sc->TXDQ_avail += ndq;
+       if (ifp->if_flags & IFF_OACTIVE) {
+               ifp->if_flags &= ~IFF_OACTIVE;
+               /* Disable end-of-tx-chain interrupt */
+               EPE_WRITE(IntEn, IntEn_REOFIE);
+       }
+       return ndq;
+}
+
+static int
 epe_intr(void *arg)
 {
        struct epe_softc *sc = (struct epe_softc *)arg;
@@ -154,12 +217,9 @@
 
        irq = EPE_READ(IntStsC);
 begin:
-       if ((irq & IntSts_RxSQ) == 0) goto txq;
        cur = (u_int32_t *)(EPE_READ(RXStsQCurAdd) -
-               sc->ctrlpage_dmamap->dm_segs[0].ds_addr +
-               sc->ctrlpage);
-       bus_dmamap_sync(sc->sc_dmat, sc->ctrlpage_dmamap, 
-               TX_QLEN * 3 * sizeof(u_int32_t),
+               sc->ctrlpage_dsaddr + sc->ctrlpage);
+       CTRLPAGE_DMASYNC(TX_QLEN * 3 * sizeof(u_int32_t),
                RX_QLEN * 4 * sizeof(u_int32_t), 
                BUS_DMASYNC_PREREAD);
        while (sc->RXStsQ_cur != cur) {
@@ -169,8 +229,6 @@
                        u_int32_t fl = sc->RXStsQ_cur[1] & 0xffff;
                        struct mbuf *m;
 
-                       bus_dmamap_sync(sc->sc_dmat, sc->rxq[bi].m_dmamap,
-                               0, fl, BUS_DMASYNC_PREREAD);
                        MGETHDR(m, M_DONTWAIT, MT_DATA);
                        if (m != NULL) MCLGET(m, M_DONTWAIT);
                        if (m != NULL && (m->m_flags & M_EXT)) {
@@ -191,9 +249,6 @@
                                        NULL, BUS_DMA_NOWAIT);
                                sc->RXDQ[bi * 2] = 
                                        sc->rxq[bi].m_dmamap->dm_segs[0].ds_addr;
-                               bus_dmamap_sync(sc->sc_dmat, 
-                                       sc->rxq[bi].m_dmamap, 0, MCLBYTES,
-                                       BUS_DMASYNC_PREREAD);
                        } else {
                                /* Drop packets until we can get replacement
                                 * empty mbufs for the RXDQ.
@@ -217,8 +272,7 @@
 
        if (ndq > 0) {
                ifp->if_ipackets += ndq;
-               bus_dmamap_sync(sc->sc_dmat, sc->ctrlpage_dmamap, 
-                       TX_QLEN * 3 * sizeof(u_int32_t),
+               CTRLPAGE_DMASYNC(TX_QLEN * 3 * sizeof(u_int32_t),
                        RX_QLEN * 4 * sizeof(u_int32_t), 
                        BUS_DMASYNC_PREWRITE|BUS_DMASYNC_PREREAD);
                EPE_WRITE(RXStsEnq, ndq);
@@ -226,56 +280,14 @@
                ndq = 0;
        }
 
-txq:
-       if ((irq & IntSts_TxSQ) == 0)
-               goto end;
-
-       /* Handle transmit completions */
-       cur = (u_int32_t *)(EPE_READ(TXStsQCurAdd) -
-               sc->ctrlpage_dmamap->dm_segs[0].ds_addr +
-               sc->ctrlpage);
-       bus_dmamap_sync(sc->sc_dmat, sc->ctrlpage_dmamap, 
-               TX_QLEN * 2 * sizeof(u_int32_t), 
-               TX_QLEN * sizeof(u_int32_t), BUS_DMASYNC_PREREAD);
-       while (sc->TXStsQ_cur != cur) {
-               u_int32_t tbi = *sc->TXStsQ_cur & 0x7fff;
-               struct mbuf *m = sc->txq[tbi].m;
+       if (epe_gctx(sc) > 0 && IFQ_IS_EMPTY(&ifp->if_snd) == 0) {
+               epe_ifstart(ifp);
+       } 
 
-               if ((*sc->TXStsQ_cur & TXStsQ_TxWE) == 0) {
-                       ifp->if_oerrors++;
-               }
-               bus_dmamap_unload(sc->sc_dmat, sc->txq[tbi].m_dmamap);
-               m_freem(m);
-               do {
-                       sc->txq[tbi].m = NULL;
-                       ndq++;
-                       tbi = (tbi + 1) % TX_QLEN;
-               } while (sc->txq[tbi].m == m);
-
-               ifp->if_opackets++;
-               sc->TXStsQ_cur++;
-               if (sc->TXStsQ_cur >= sc->TXStsQ + TX_QLEN) {
-                       sc->TXStsQ_cur = sc->TXStsQ;
-               }
-       }
+       irq = EPE_READ(IntStsC);
+       if ((irq & (IntSts_RxSQ|IntSts_ECI)) != 0)
+               goto begin;
 
-       if (ndq > 0) {
-               sc->TXDQ_avail += ndq;
-               if (sc->TXDQ_avail == TX_QLEN - 1) {
-                       ifp->if_flags &= ~IFF_OACTIVE;
-                       ifp->if_timer = 0;
-               } else {
-                       ifp->if_timer = 10;
-               }
-               if (IFQ_IS_EMPTY(&ifp->if_snd) == 0 &&
-                       sc->TXDQ_avail > TX_QLEN / 2) epe_ifstart(ifp);
-               ndq = 0;
-       }
-
-end:
-       irq = EPE_READ(IntStsC);
-       if ((irq & (IntSts_TxSQ|IntSts_RxSQ)) != 0)
-               goto begin;
        return (1);
 }
 
@@ -315,7 +327,7 @@
                &segs, 1, &rsegs, BUS_DMA_WAITOK);
        if (err == 0) {
                err = bus_dmamem_map(sc->sc_dmat, &segs, 1, PAGE_SIZE, 
-                       &sc->ctrlpage, (BUS_DMA_WAITOK));
+                       &sc->ctrlpage, (BUS_DMA_WAITOK|BUS_DMA_COHERENT));
        }
        if (err == 0) {
                err = bus_dmamap_create(sc->sc_dmat, PAGE_SIZE, 1, PAGE_SIZE,
@@ -328,6 +340,7 @@
        if (err != 0) {
                panic("%s: Cannot get DMA memory", sc->sc_dev.dv_xname);
        }
+       sc->ctrlpage_dsaddr = sc->ctrlpage_dmamap->dm_segs[0].ds_addr;
        bzero(sc->ctrlpage, PAGE_SIZE);
        
        /* Set up pointers to start of each queue in kernel addr space.
@@ -406,14 +419,13 @@
        ifmedia_set(&sc->sc_mii.mii_media, IFM_ETHER|IFM_AUTO);
 
        EPE_WRITE(BMCtl, BMCtl_RxEn|BMCtl_TxEn);
-       EPE_WRITE(IntEn, IntEn_TSQIE|IntEn_REOFIE);
+       EPE_WRITE(IntEn, IntEn_REOFIE);
        /* maximum valid max frame length */
        EPE_WRITE(MaxFrmLen, (0x7ff << 16)|MHLEN);
        /* wait for receiver ready */
        while((EPE_READ(BMSts) & BMSts_RxAct) == 0); 
        /* enqueue the entries in RXStsQ and RXDQ */
-       bus_dmamap_sync(sc->sc_dmat, sc->ctrlpage_dmamap, 0,
-               sc->ctrlpage_dmamap->dm_mapsize, 
+       CTRLPAGE_DMASYNC(0, sc->ctrlpage_dmamap->dm_mapsize, 
                BUS_DMASYNC_PREWRITE|BUS_DMASYNC_PREREAD);
        EPE_WRITE(RXDEnq, RX_QLEN - 1);
        EPE_WRITE(RXStsEnq, RX_QLEN - 1);
@@ -464,9 +476,10 @@
        struct device *self;
        int phy, reg;
 {
-       struct epe_softc *sc = (struct epe_softc *)self;
        u_int32_t d, v;
+       struct epe_softc *sc;
 
+       sc = (struct epe_softc *)self;
        d = EPE_READ(SelfCtl);
        EPE_WRITE(SelfCtl, d & ~SelfCtl_PSPRS); /* no preamble suppress */
        EPE_WRITE(MIICmd, (MIICmd_READ | (phy << 5) | reg));
@@ -481,9 +494,10 @@
        struct device *self;
        int phy, reg, val;
 {
-       struct epe_softc *sc = (struct epe_softc *)self;
+       struct epe_softc *sc;
        u_int32_t d;
 
+       sc = (struct epe_softc *)self;
        d = EPE_READ(SelfCtl);
        EPE_WRITE(SelfCtl, d & ~SelfCtl_PSPRS); /* no preamble suppress */
        EPE_WRITE(MIICmd, (MIICmd_WRITE | (phy << 5) | reg));
@@ -518,6 +532,7 @@
 {
        struct epe_softc* sc = (struct epe_softc *)arg;
        struct ifnet * ifp = &sc->sc_ec.ec_if;
+       int s;
        u_int32_t misses;
 
        ifp->if_collisions += EPE_READ(TXCollCnt);
@@ -526,6 +541,12 @@
        if (misses > 0) 
                printf("%s: %d rx misses\n", sc->sc_dev.dv_xname, misses);
        
+       s = splnet();
+       if (epe_gctx(sc) > 0 && IFQ_IS_EMPTY(&ifp->if_snd) == 0) {
+               epe_ifstart(ifp);
+       }
+       splx(s);
+
        mii_tick(&sc->sc_mii);
        callout_reset(&sc->epe_tick_ch, hz, epe_tick, sc);
 }
@@ -566,13 +587,22 @@
        struct epe_softc *sc = (struct epe_softc *)ifp->if_softc;
        struct mbuf *m;
        bus_dma_segment_t *segs;
-       int s, bi, err, nsegs, ndq = 0;
-       



Home | Main Index | Thread Index | Old Index