Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch/sun3/dev Make "dma" a real device so it can attach ...
details: https://anonhg.NetBSD.org/src/rev/c43c162277d3
branches: trunk
changeset: 471690:c43c162277d3
user: gwr <gwr%NetBSD.org@localhost>
date: Thu Apr 08 04:46:41 1999 +0000
description:
Make "dma" a real device so it can attach before esp.
Also pull in some changes from the sparc version.
diffstat:
sys/arch/sun3/dev/dma.c | 228 ++++++++++++++++++++++----------------------
sys/arch/sun3/dev/dmareg.h | 84 ++++++++--------
sys/arch/sun3/dev/dmavar.h | 19 +--
sys/arch/sun3/dev/esp.c | 93 +++++-------------
4 files changed, 186 insertions(+), 238 deletions(-)
diffs (truncated from 700 to 300 lines):
diff -r 20b78b014e5b -r c43c162277d3 sys/arch/sun3/dev/dma.c
--- a/sys/arch/sun3/dev/dma.c Thu Apr 08 04:37:00 1999 +0000
+++ b/sys/arch/sun3/dev/dma.c Thu Apr 08 04:46:41 1999 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: dma.c,v 1.9 1998/12/13 18:00:10 kleink Exp $ */
+/* $NetBSD: dma.c,v 1.10 1999/04/08 04:46:41 gwr Exp $ */
/*
* Copyright (c) 1994 Paul Kranenburg. All rights reserved.
@@ -35,12 +35,8 @@
#include <sys/systm.h>
#include <sys/kernel.h>
#include <sys/errno.h>
-#include <sys/ioctl.h>
#include <sys/device.h>
#include <sys/malloc.h>
-#include <sys/buf.h>
-#include <sys/proc.h>
-#include <sys/user.h>
#include <machine/autoconf.h>
#include <machine/dvma.h>
@@ -55,81 +51,95 @@
#include <sun3/dev/dmareg.h>
#include <sun3/dev/dmavar.h>
-/*
- * Pseudo-attach function. Called from the esp driver during its
- * attach function. This needs to be silent.
- */
-void
+#define MAX_DMA_SZ 0x01000000 /* 16MB */
+
+static int dmamatch __P((struct device *, struct cfdata *, void *));
+static void dmaattach __P((struct device *, struct device *, void *));
+
+struct cfattach dma_ca = {
+ sizeof(struct dma_softc), dmamatch, dmaattach
+};
+
+extern struct cfdriver dma_cd;
+
+static int
+dmamatch(parent, cf, aux)
+ struct device *parent;
+ struct cfdata *cf;
+ void *aux;
+{
+ struct confargs *ca = aux;
+
+ /*
+ * Check for the DMA registers.
+ */
+ if (bus_peek(ca->ca_bustype, ca->ca_paddr, 4) == -1)
+ return (0);
+
+ /* If default ipl, fill it in. */
+ if (ca->ca_intpri == -1)
+ ca->ca_intpri = 2;
+
+ return (1);
+}
+
+static void
dmaattach(parent, self, aux)
struct device *parent, *self;
void *aux;
{
+ struct confargs *ca = aux;
struct dma_softc *sc = (void *)self;
-
- /*
- * The esp driver has filled in the virtual address used to
- * address the dma registers at this point. Normally we would
- * map them in here and assign them ourselves.
- *
- * It has also filled itself in to our sc->sc_esp register.
- */
-
- /*
- * Get transfer burst size from PROM and plug it into the
- * controller registers. This is needed on the Sun4m; do
- * others need it too?
- *
- * Sun3x works ok (so far) without it.
- */
-
- sc->sc_rev = sc->sc_regs->csr & D_DEV_ID;
+ int id;
#if 0
/* indirect functions */
sc->intr = espdmaintr;
- sc->enintr = dma_enintr;
- sc->isintr = dma_isintr;
+ sc->setup = dma_setup;
sc->reset = dma_reset;
- sc->setup = dma_setup;
- sc->go = dma_go;
#endif
-}
-void
-dma_print_rev(sc)
- struct dma_softc *sc;
-{
+ /*
+ * Map in the registers.
+ */
+ sc->sc_regs = bus_mapin(ca->ca_bustype, ca->ca_paddr,
+ sizeof(struct dma_regs));
+ sc->sc_rev = DMACSR(sc) & D_DEV_ID;
+ id = (sc->sc_rev >> 28) & 0xf;
+ printf(": rev %d\n", id);
- printf("espdma: rev ");
+ /*
+ * Make sure the DMA chip is supported revision.
+ * The Sun3/80 used only the old rev zero chip,
+ * so the initialization has been simplified.
+ */
switch (sc->sc_rev) {
case DMAREV_0:
- printf("0");
- break;
- case DMAREV_ESC:
- printf("esc");
- break;
case DMAREV_1:
- printf("1");
- break;
- case DMAREV_PLUS:
- printf("1+");
- break;
- case DMAREV_2:
- printf("2");
break;
default:
- printf("unknown (0x%x)", sc->sc_rev);
+ panic("unsupported dma rev");
}
- printf("\n");
}
+/*
+ * This is called by espattach to get our softc.
+ */
+struct dma_softc *
+espdmafind(int unit)
+{
+ if (unit < 0 || unit >= dma_cd.cd_ndevs ||
+ dma_cd.cd_devs[unit] == NULL)
+ panic("no dma");
+ return (dma_cd.cd_devs[unit]);
+}
#define DMAWAIT(SC, COND, MSG, DONTPANIC) do if (COND) { \
- int count = 500000; \
- while ((COND) && --count > 0) DELAY(1); \
+ int count = 100000; \
+ while ((COND) && --count > 0) DELAY(5); \
if (count == 0) { \
- printf("%s: line %d: CSR = 0x%lx\n", __FILE__, __LINE__, \
- (SC)->sc_regs->csr); \
+ printf("%s: line %d: CSR = 0x%x\n", \
+ __FILE__, __LINE__, DMACSR(SC)); \
if (DONTPANIC) \
printf(MSG); \
else \
@@ -144,54 +154,55 @@
* request. \
* other revs: D_R_PEND bit reads as 0 \
*/ \
- DMAWAIT(sc, sc->sc_regs->csr & D_R_PEND, "R_PEND", dontpanic); \
+ DMAWAIT(sc, DMACSR(sc) & D_R_PEND, "R_PEND", dontpanic); \
/* \
- * Select drain bit based on revision \
+ * Select drain bit (always rev 0,1) \
* also clears errors and D_TC flag \
*/ \
- if (sc->sc_rev == DMAREV_1 || sc->sc_rev == DMAREV_0) \
- DMACSR(sc) |= D_DRAIN; \
- else \
- DMACSR(sc) |= D_INVALIDATE; \
+ DMACSR(sc) |= D_DRAIN; \
/* \
* Wait for draining to finish \
- * rev0 & rev1 call this PACKCNT \
*/ \
- DMAWAIT(sc, sc->sc_regs->csr & D_DRAINING, "DRAINING", dontpanic);\
+ DMAWAIT(sc, DMACSR(sc) & D_PACKCNT, "DRAINING", dontpanic); \
+} while(0)
+
+#define DMA_FLUSH(sc, dontpanic) do { \
+ /* \
+ * DMA rev0 & rev1: we are not allowed to touch the DMA "flush" \
+ * and "drain" bits while it is still thinking about a \
+ * request. \
+ * other revs: D_R_PEND bit reads as 0 \
+ */ \
+ DMAWAIT(sc, DMACSR(sc) & D_R_PEND, "R_PEND", dontpanic); \
+ DMACSR(sc) &= ~(D_WRITE|D_EN_DMA); \
+ DMACSR(sc) |= D_FLUSH; \
} while(0)
void
dma_reset(sc)
struct dma_softc *sc;
{
- DMA_DRAIN(sc, 1);
- DMACSR(sc) &= ~D_EN_DMA; /* Stop DMA */
- DMACSR(sc) |= D_RESET; /* reset DMA */
- DELAY(200); /* what should this be ? */
+
+ DMA_FLUSH(sc, 1);
+ DMACSR(sc) |= D_RESET; /* reset DMA */
+ DELAY(200); /* what should this be ? */
/*DMAWAIT1(sc); why was this here? */
- DMACSR(sc) &= ~D_RESET; /* de-assert reset line */
- DMACSR(sc) |= D_INT_EN; /* enable interrupts */
+ DMACSR(sc) &= ~D_RESET; /* de-assert reset line */
+ DELAY(5); /* allow a few ticks to settle */
- sc->sc_active = 0; /* and of course we aren't */
+ /*
+ * Get transfer burst size from (?) and plug it into the
+ * controller registers. This is needed on the Sun4m...
+ * Do we need it too? Apparently not, because the 3/80
+ * always has the old, REV zero DMA chip.
+ */
+ DMACSR(sc) |= D_INT_EN; /* enable interrupts */
+
+ sc->sc_active = 0;
}
-void
-dma_enintr(sc)
- struct dma_softc *sc;
-{
- sc->sc_regs->csr |= D_INT_EN;
-}
-
-int
-dma_isintr(sc)
- struct dma_softc *sc;
-{
- return (sc->sc_regs->csr & (D_INT_PEND|D_ERR_PEND));
-}
-
-#define DMAMAX(a) (0x01000000 - ((a) & 0x00ffffff))
-
+#define DMAMAX(a) (MAX_DMA_SZ - ((a) & (MAX_DMA_SZ-1)))
/*
* setup a dma transfer
@@ -204,9 +215,9 @@
int datain;
size_t *dmasize; /* IN-OUT */
{
- u_long csr;
+ u_int32_t csr;
- DMA_DRAIN(sc, 0);
+ DMA_FLUSH(sc, 0);
#if 0
DMACSR(sc) &= ~D_INT_EN;
@@ -239,17 +250,13 @@
panic("dma: cannot allocate DVMA address");
sc->sc_dmasaddr = dvma_kvtopa(sc->sc_dvmakaddr, BUS_OBIO);
DMADDR(sc) = sc->sc_dmasaddr;
- } else
- DMADDR(sc) = (u_long) *sc->sc_dmaaddr;
+ } else {
+ /* XXX: What is this about? -gwr */
+ DMADDR(sc) = (u_int32_t) *sc->sc_dmaaddr;
+ }
- if (sc->sc_rev == DMAREV_ESC) {
- /* DMA ESC chip bug work-around */
- register long bcnt = sc->sc_dmasize;
- register long eaddr = bcnt + (long)*sc->sc_dmaaddr;
- if ((eaddr & PGOFSET) != 0)
- bcnt = roundup(bcnt, NBPG);
- DMACNT(sc) = bcnt;
- }
+ /* We never have DMAREV_ESC. */
+
/* Setup DMA control register */
csr = DMACSR(sc);
if (datain)
@@ -262,19 +269,9 @@
return 0;
}
-void
-dma_go(sc)
- struct dma_softc *sc;
-{
Home |
Main Index |
Thread Index |
Old Index