Source-Changes-HG archive

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

[src/trunk]: src/sys/arch/amiga Added two new macros to device.h:



details:   https://anonhg.NetBSD.org/src/rev/b7e9f68f0b58
branches:  trunk
changeset: 751477:b7e9f68f0b58
user:      phx <phx%NetBSD.org@localhost>
date:      Fri Feb 05 12:13:36 2010 +0000

description:
Added two new macros to device.h:
amiga_membarrier() enforces a reorder protection on memory read/writes.
amiga_cpu_sync() makes sure the instruction pipelines are flushed.
Both macros may be used in all amiga device drivers for compatibility with
amigappc. For the start I fixed some SCSI drivers.
cbiiisc and ahsc were tested and seem to work really fast with DMA now.
Some stability problems with amigappc remain nevertheless (spontaneous
kernel DSI traps with high CPU/SCSI load).

diffstat:

 sys/arch/amiga/amiga/device.h  |  20 +++++++++++++++++++-
 sys/arch/amiga/dev/ahsc.c      |  35 +++++++++++++++++++++++++++++------
 sys/arch/amiga/dev/atzsc.c     |  37 ++++++++++++++++++++++++++++++-------
 sys/arch/amiga/dev/cbiiisc.c   |   6 ++++--
 sys/arch/amiga/dev/grf_cv.c    |  22 +++++++++++-----------
 sys/arch/amiga/dev/grf_cvreg.h |  29 ++++++++++-------------------
 sys/arch/amiga/dev/gtsc.c      |  30 +++++++++++++++++++++++++-----
 sys/arch/amiga/dev/sbic.c      |   7 +++++--
 sys/arch/amiga/dev/sbicreg.h   |   6 +++++-
 sys/arch/amiga/dev/siop2.c     |  40 +++++++++++++++++++++++++++++++++-------
 10 files changed, 171 insertions(+), 61 deletions(-)

diffs (truncated from 835 to 300 lines):

diff -r 7ca0deb4f7d8 -r b7e9f68f0b58 sys/arch/amiga/amiga/device.h
--- a/sys/arch/amiga/amiga/device.h     Fri Feb 05 12:05:25 2010 +0000
+++ b/sys/arch/amiga/amiga/device.h     Fri Feb 05 12:13:36 2010 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: device.h,v 1.11 2008/06/11 12:59:10 tsutsui Exp $      */
+/*     $NetBSD: device.h,v 1.12 2010/02/05 12:13:36 phx Exp $  */
 
 /*
  * Copyright (c) 1994 Christian E. Hopps
@@ -49,4 +49,22 @@
 
 #define getsoftc(cdnam, unit)  device_lookup_private(&(cdnam), (unit))
 
+/*
+ * Reorder protection when accessing device registers.
+ */
+#if defined(__m68k__)
+#define amiga_membarrier()
+#elif defined(__powerpc__)
+#define amiga_membarrier() __asm volatile ("eieio")
+#endif
+
+/*
+ * Finish all bus operations and flush pipelines.
+ */
+#if defined(__m68k__)
+#define amiga_cpu_sync() __asm volatile ("nop")
+#elif defined(__powerpc__)
+#define amiga_cpu_sync() __asm volatile ("sync; isync")
+#endif
+
 #endif /* _AMIGA_DEVICE_H_ */
diff -r 7ca0deb4f7d8 -r b7e9f68f0b58 sys/arch/amiga/dev/ahsc.c
--- a/sys/arch/amiga/dev/ahsc.c Fri Feb 05 12:05:25 2010 +0000
+++ b/sys/arch/amiga/dev/ahsc.c Fri Feb 05 12:13:36 2010 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: ahsc.c,v 1.36 2008/06/13 08:13:37 cegger Exp $ */
+/*     $NetBSD: ahsc.c,v 1.37 2010/02/05 12:13:36 phx Exp $ */
 
 /*
  * Copyright (c) 1982, 1990 The Regents of the University of California.
@@ -66,7 +66,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ahsc.c,v 1.36 2008/06/13 08:13:37 cegger Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ahsc.c,v 1.37 2010/02/05 12:13:36 phx Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -144,7 +144,9 @@
         * disable ints and reset bank register
         */
        rp->CNTR = CNTR_PDMD;
+       amiga_membarrier();
        rp->DAWR = DAWR_AHSC;
+       amiga_membarrier();
        sc->sc_enintr = ahsc_enintr;
        sc->sc_dmago = ahsc_dmago;
        sc->sc_dmanext = ahsc_dmanext;
@@ -212,6 +214,7 @@
 
        dev->sc_flags |= SBICF_INTR;
        sdp->CNTR = CNTR_PDMD | CNTR_INTEN;
+       amiga_membarrier();
 }
 
 int
@@ -233,8 +236,11 @@
 
        dev->sc_flags |= SBICF_INTR;
        sdp->CNTR = dev->sc_dmacmd;
+       amiga_membarrier();
        sdp->ACR = (u_int) dev->sc_cur->dc_addr;
+       amiga_membarrier();
        sdp->ST_DMA = 1;
+       amiga_membarrier();
 
        return(dev->sc_tcnt);
 }
@@ -244,6 +250,7 @@
 {
        volatile struct sdmac *sdp;
        int s;
+       vu_short istr;
 
        sdp = dev->sc_cregs;
 
@@ -259,14 +266,19 @@
                         * and reading from peripheral
                         */
                        sdp->FLUSH = 1;
-                       while ((sdp->ISTR & ISTR_FE_FLG) == 0)
-                               ;
+                       amiga_membarrier();
+                       do {
+                               istr = sdp->ISTR;
+                               amiga_membarrier();
+                       } while ((istr & ISTR_FE_FLG) == 0);
                }
                /*
                 * clear possible interrupt and stop DMA
                 */
                sdp->CINT = 1;
+               amiga_membarrier();
                sdp->SP_DMA = 1;
+               amiga_membarrier();
                dev->sc_dmacmd = 0;
                splx(s);
        }
@@ -281,6 +293,7 @@
 
        sdp = dev->sc_cregs;
        stat = sdp->ISTR;
+       amiga_membarrier();
 
        if ((stat & (ISTR_INT_F|ISTR_INT_P)) == 0)
                return (0);
@@ -300,6 +313,7 @@
                ++found;
 
                sdp->CINT = 1;  /* clear possible interrupt */
+               amiga_membarrier();
 
                /*
                 * check for SCSI ints in the same go and
@@ -317,6 +331,7 @@
 ahsc_dmanext(struct sbic_softc *dev)
 {
        volatile struct sdmac *sdp;
+       vu_short istr;
 
        sdp = dev->sc_cregs;
 
@@ -332,17 +347,25 @@
                   * and reading from peripheral
                   */
                sdp->FLUSH = 1;
-               while ((sdp->ISTR & ISTR_FE_FLG) == 0)
-                       ;
+               amiga_membarrier();
+               do {
+                       istr = sdp->ISTR;
+                       amiga_membarrier();
+               } while ((istr & ISTR_FE_FLG) == 0);
        }
        /*
         * clear possible interrupt and stop DMA
         */
        sdp->CINT = 1;  /* clear possible interrupt */
+       amiga_membarrier();
        sdp->SP_DMA = 1;        /* stop DMA */
+       amiga_membarrier();
        sdp->CNTR = dev->sc_dmacmd;
+       amiga_membarrier();
        sdp->ACR = (u_int)dev->sc_cur->dc_addr;
+       amiga_membarrier();
        sdp->ST_DMA = 1;
+       amiga_membarrier();
 
        dev->sc_tcnt = dev->sc_cur->dc_count << 1;
        return(dev->sc_tcnt);
diff -r 7ca0deb4f7d8 -r b7e9f68f0b58 sys/arch/amiga/dev/atzsc.c
--- a/sys/arch/amiga/dev/atzsc.c        Fri Feb 05 12:05:25 2010 +0000
+++ b/sys/arch/amiga/dev/atzsc.c        Fri Feb 05 12:13:36 2010 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: atzsc.c,v 1.39 2009/10/16 09:36:35 phx Exp $ */
+/*     $NetBSD: atzsc.c,v 1.40 2010/02/05 12:13:36 phx Exp $ */
 
 /*
  * Copyright (c) 1982, 1990 The Regents of the University of California.
@@ -66,7 +66,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: atzsc.c,v 1.39 2009/10/16 09:36:35 phx Exp $");
+__KERNEL_RCSID(0, "$NetBSD: atzsc.c,v 1.40 2010/02/05 12:13:36 phx Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -107,7 +107,7 @@
     atzscmatch, atzscattach, NULL, NULL);
 
 /*
- * if we are an A3000 we are here.
+ * if we are a A2091 SCSI
  */
 int
 atzscmatch(struct device *pdp, struct cfdata *cfp, void *auxp)
@@ -142,7 +142,9 @@
         * disable ints and reset bank register
         */
        rp->CNTR = CNTR_PDMD;
+       amiga_membarrier();
        rp->DAWR = DAWR_ATZSC;
+       amiga_membarrier();
        sc->sc_enintr = atzsc_enintr;
        sc->sc_dmago = atzsc_dmago;
        sc->sc_dmanext = atzsc_dmanext;
@@ -219,12 +221,14 @@
 
        dev->sc_flags |= SBICF_INTR;
        sdp->CNTR = CNTR_PDMD | CNTR_INTEN;
+       amiga_membarrier();
 }
 
 int
 atzsc_dmago(struct sbic_softc *dev, char *addr, int count, int flags)
 {
        volatile struct sdmac *sdp;
+       vu_short istr;
 
        sdp = dev->sc_cregs;
        /*
@@ -240,8 +244,11 @@
 
        dev->sc_flags |= SBICF_INTR;
        sdp->CNTR = dev->sc_dmacmd;
+       amiga_membarrier();
        sdp->ACR = (u_int) dev->sc_cur->dc_addr;
+       amiga_membarrier();
        sdp->ST_DMA = 1;
+       amiga_membarrier();
 
        return(dev->sc_tcnt);
 }
@@ -251,6 +258,7 @@
 {
        volatile struct sdmac *sdp;
        int s;
+       vu_short istr;
 
        sdp = dev->sc_cregs;
 
@@ -266,14 +274,19 @@
                         * and reading from peripheral
                         */
                        sdp->FLUSH = 1;
-                       while ((sdp->ISTR & ISTR_FE_FLG) == 0)
-                               ;
+                       amiga_membarrier();
+                       do {
+                               istr = sdp->ISTR;
+                               amiga_membarrier();
+                       } while ((istr & ISTR_FE_FLG) == 0);
                }
                /*
                 * clear possible interrupt and stop DMA
                 */
                sdp->CINT = 1;
+               amiga_membarrier();
                sdp->SP_DMA = 1;
+               amiga_membarrier();
                dev->sc_dmacmd = 0;
                splx(s);
        }
@@ -307,6 +320,7 @@
                found++;
 
                sdp->CINT = 1;  /* clear possible interrupt */
+               amiga_membarrier();
 
                /*
                 * check for SCSI ints in the same go and
@@ -324,6 +338,7 @@
 atzsc_dmanext(struct sbic_softc *dev)
 {
        volatile struct sdmac *sdp;
+       vu_short istr;
 
        sdp = dev->sc_cregs;
 
@@ -339,17 +354,25 @@
                   * and reading from peripheral
                   */
                sdp->FLUSH = 1;
-               while ((sdp->ISTR & ISTR_FE_FLG) == 0)
-                       ;
+               amiga_membarrier();
+               do {
+                       istr = sdp->ISTR;
+                       amiga_membarrier();
+               } while ((istr & ISTR_FE_FLG) == 0);
        }
        /*
         * clear possible interrupt and stop DMA
         */
        sdp->CINT = 1;  /* clear possible interrupt */
+       amiga_membarrier();
        sdp->SP_DMA = 1;        /* stop DMA */
+       amiga_membarrier();
        sdp->CNTR = dev->sc_dmacmd;
+       amiga_membarrier();
        sdp->ACR = (u_int)dev->sc_cur->dc_addr;
+       amiga_membarrier();
        sdp->ST_DMA = 1;
+       amiga_membarrier();
 
        dev->sc_tcnt = dev->sc_cur->dc_count << 1;
        return(dev->sc_tcnt);



Home | Main Index | Thread Index | Old Index