Source-Changes-HG archive

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

[src/trunk]: src/sys/arch/arm/allwinner Split awindma into a frontend and A10...



details:   https://anonhg.NetBSD.org/src/rev/65ece0132744
branches:  trunk
changeset: 803132:65ece0132744
user:      jmcneill <jmcneill%NetBSD.org@localhost>
date:      Mon Oct 13 12:34:00 2014 +0000

description:
Split awindma into a frontend and A10/A20 backend; add an A31 DMA backend.

diffstat:

 sys/arch/arm/allwinner/awin_ac.c      |   26 +-
 sys/arch/arm/allwinner/awin_dma.c     |  271 +++++---------------------
 sys/arch/arm/allwinner/awin_dma.h     |   85 ++++++++
 sys/arch/arm/allwinner/awin_dma_a10.c |  333 ++++++++++++++++++++++++++++++++++
 sys/arch/arm/allwinner/awin_dma_a31.c |  332 +++++++++++++++++++++++++++++++++
 sys/arch/arm/allwinner/awin_reg.h     |   90 +++++++++
 sys/arch/arm/allwinner/awin_var.h     |   20 +-
 sys/arch/arm/allwinner/files.awin     |    4 +-
 8 files changed, 926 insertions(+), 235 deletions(-)

diffs (truncated from 1360 to 300 lines):

diff -r b37359c5fdc2 -r 65ece0132744 sys/arch/arm/allwinner/awin_ac.c
--- a/sys/arch/arm/allwinner/awin_ac.c  Mon Oct 13 11:07:38 2014 +0000
+++ b/sys/arch/arm/allwinner/awin_ac.c  Mon Oct 13 12:34:00 2014 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: awin_ac.c,v 1.13 2014/10/12 17:25:35 jmcneill Exp $ */
+/* $NetBSD: awin_ac.c,v 1.14 2014/10/13 12:34:00 jmcneill Exp $ */
 
 /*-
  * Copyright (c) 2014 Jared D. McNeill <jmcneill%invisible.ca@localhost>
@@ -30,7 +30,7 @@
 #include "opt_ddb.h"
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: awin_ac.c,v 1.13 2014/10/12 17:25:35 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: awin_ac.c,v 1.14 2014/10/13 12:34:00 jmcneill Exp $");
 
 #include <sys/param.h>
 #include <sys/bus.h>
@@ -179,6 +179,9 @@
 
        LIST_HEAD(, awinac_dma) sc_dmalist;
 
+       uint8_t                 sc_drqtype_codec;
+       uint8_t                 sc_drqtype_sdram;
+
        kmutex_t                sc_lock;
        kmutex_t                sc_intr_lock;
 
@@ -361,12 +364,19 @@
 
        awinac_init(sc);
 
-       sc->sc_pdma = awin_dma_alloc(AWIN_DMA_TYPE_NDMA, awinac_pint, sc);
+       sc->sc_drqtype_codec = awin_chip_id() == AWIN_CHIP_ID_A31 ?
+           AWIN_A31_DMA_DRQ_TYPE_AUDIOCODEC :
+           AWIN_NDMA_CTL_DRQ_CODEC;
+       sc->sc_drqtype_sdram = awin_chip_id() == AWIN_CHIP_ID_A31 ?
+           AWIN_A31_DMA_DRQ_TYPE_SDRAM :
+           AWIN_NDMA_CTL_DRQ_SDRAM;
+
+       sc->sc_pdma = awin_dma_alloc("codec-play", awinac_pint, sc);
        if (sc->sc_pdma == NULL) {
                aprint_error_dev(self, "couldn't allocate play DMA channel\n");
                return;
        }
-       sc->sc_rdma = awin_dma_alloc(AWIN_DMA_TYPE_NDMA, awinac_rint, sc);
+       sc->sc_rdma = awin_dma_alloc("codec-rec", awinac_rint, sc);
        if (sc->sc_rdma == NULL) {
                aprint_error_dev(self, "couldn't allocate rec DMA channel\n");
                return;
@@ -967,9 +977,9 @@
                            AWIN_DMA_CTL_SRC_BURST_LEN);
        dmacfg |= AWIN_DMA_CTL_BC_REMAINING;
        dmacfg |= AWIN_NDMA_CTL_DST_ADDR_NOINCR;
-       dmacfg |= __SHIFTIN(AWIN_NDMA_CTL_DRQ_CODEC,
+       dmacfg |= __SHIFTIN(sc->sc_drqtype_codec,
                            AWIN_DMA_CTL_DST_DRQ_TYPE);
-       dmacfg |= __SHIFTIN(AWIN_NDMA_CTL_DRQ_SDRAM,
+       dmacfg |= __SHIFTIN(sc->sc_drqtype_sdram,
                            AWIN_DMA_CTL_SRC_DRQ_TYPE);
        awin_dma_set_config(sc->sc_pdma, dmacfg);
 
@@ -1035,9 +1045,9 @@
                            AWIN_DMA_CTL_SRC_BURST_LEN);
        dmacfg |= AWIN_DMA_CTL_BC_REMAINING;
        dmacfg |= AWIN_NDMA_CTL_SRC_ADDR_NOINCR;
-       dmacfg |= __SHIFTIN(AWIN_NDMA_CTL_DRQ_SDRAM,
+       dmacfg |= __SHIFTIN(sc->sc_drqtype_sdram,
                            AWIN_DMA_CTL_DST_DRQ_TYPE);
-       dmacfg |= __SHIFTIN(AWIN_NDMA_CTL_DRQ_CODEC,
+       dmacfg |= __SHIFTIN(sc->sc_drqtype_codec,
                            AWIN_DMA_CTL_SRC_DRQ_TYPE);
        awin_dma_set_config(sc->sc_rdma, dmacfg);
 
diff -r b37359c5fdc2 -r 65ece0132744 sys/arch/arm/allwinner/awin_dma.c
--- a/sys/arch/arm/allwinner/awin_dma.c Mon Oct 13 11:07:38 2014 +0000
+++ b/sys/arch/arm/allwinner/awin_dma.c Mon Oct 13 12:34:00 2014 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: awin_dma.c,v 1.4 2014/09/06 17:10:17 jmcneill Exp $ */
+/* $NetBSD: awin_dma.c,v 1.5 2014/10/13 12:34:00 jmcneill Exp $ */
 
 /*-
  * Copyright (c) 2014 Jared D. McNeill <jmcneill%invisible.ca@localhost>
@@ -27,9 +27,10 @@
  */
 
 #include "opt_ddb.h"
+#include "opt_allwinner.h"
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: awin_dma.c,v 1.4 2014/09/06 17:10:17 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: awin_dma.c,v 1.5 2014/10/13 12:34:00 jmcneill Exp $");
 
 #include <sys/param.h>
 #include <sys/bus.h>
@@ -40,44 +41,13 @@
 
 #include <arm/allwinner/awin_reg.h>
 #include <arm/allwinner/awin_var.h>
-
-#define NDMA_CHANNELS  8
-#define DDMA_CHANNELS  8
-
-struct awin_dma_channel {
-       uint8_t ch_index;
-       enum awin_dma_type ch_type;
-       void (*ch_callback)(void *);
-       void *ch_callbackarg;
-       uint32_t ch_regoff;
-};
-
-struct awin_dma_softc {
-       device_t sc_dev;
-       bus_space_tag_t sc_bst;
-       bus_space_handle_t sc_bsh;
-       void *sc_ih;
-};
-
-#define DMA_READ(reg)                  \
-    bus_space_read_4(awin_dma_sc->sc_bst, awin_dma_sc->sc_bsh, (reg))
-#define DMA_WRITE(reg, val)            \
-    bus_space_write_4(awin_dma_sc->sc_bst, awin_dma_sc->sc_bsh, (reg), (val))
-#define DMACH_READ(ch, reg)            \
-    DMA_READ((reg) + (ch)->ch_regoff)
-#define DMACH_WRITE(ch, reg, val)      \
-    DMA_WRITE((reg) + (ch)->ch_regoff, (val))
+#include <arm/allwinner/awin_dma.h>
 
 static struct awin_dma_softc *awin_dma_sc;
-static kmutex_t awin_dma_lock;
-static struct awin_dma_channel awin_ndma_channels[NDMA_CHANNELS];
-static struct awin_dma_channel awin_ddma_channels[DDMA_CHANNELS];
 
 static int     awin_dma_match(device_t, cfdata_t, void *);
 static void    awin_dma_attach(device_t, device_t, void *);
 
-static int     awin_dma_intr(void *);
-
 #if defined(DDB)
 void           awin_dma_dump_regs(void);
 #endif
@@ -88,7 +58,11 @@
 static int
 awin_dma_match(device_t parent, cfdata_t cf, void *aux)
 {
+#if defined(ALLWINNER_A10) || defined(ALLWINNER_A20) || defined(ALLWINNER_A31)
        return awin_dma_sc == NULL;
+#else
+       return 0;
+#endif
 }
 
 static void
@@ -97,235 +71,106 @@
        struct awin_dma_softc *sc = device_private(self);
        struct awinio_attach_args * const aio = aux;
        const struct awin_locators * const loc = &aio->aio_loc;
-       uint8_t index;
 
        KASSERT(awin_dma_sc == NULL);
        awin_dma_sc = sc;
 
        sc->sc_dev = self;
        sc->sc_bst = aio->aio_core_bst;
+       sc->sc_dmat = aio->aio_dmat;
        bus_space_subregion(sc->sc_bst, aio->aio_core_bsh,
            loc->loc_offset, loc->loc_size, &sc->sc_bsh);
 
        aprint_naive("\n");
        aprint_normal(": DMA\n");
 
-       mutex_init(&awin_dma_lock, MUTEX_DEFAULT, IPL_SCHED);
-
-       awin_reg_set_clear(aio->aio_core_bst, aio->aio_ccm_bsh,
-           AWIN_AHB_GATING0_REG, AWIN_AHB_GATING0_DMA, 0);
-
-       DMA_WRITE(AWIN_DMA_IRQ_EN_REG, 0);
-       DMA_WRITE(AWIN_DMA_IRQ_PEND_STA_REG, ~0);
-
-       for (index = 0; index < NDMA_CHANNELS; index++) {
-               awin_ndma_channels[index].ch_index = index;
-               awin_ndma_channels[index].ch_type = AWIN_DMA_TYPE_NDMA;
-               awin_ndma_channels[index].ch_callback = NULL;
-               awin_ndma_channels[index].ch_callbackarg = NULL;
-               awin_ndma_channels[index].ch_regoff = AWIN_NDMA_REG(index);
-               DMACH_WRITE(&awin_ndma_channels[index], AWIN_NDMA_CTL_REG, 0);
-       }
-       for (index = 0; index < DDMA_CHANNELS; index++) {
-               awin_ddma_channels[index].ch_index = index;
-               awin_ddma_channels[index].ch_type = AWIN_DMA_TYPE_DDMA;
-               awin_ddma_channels[index].ch_callback = NULL;
-               awin_ddma_channels[index].ch_callbackarg = NULL;
-               awin_ddma_channels[index].ch_regoff = AWIN_DDMA_REG(index);
-               DMACH_WRITE(&awin_ddma_channels[index], AWIN_DDMA_CTL_REG, 0);
+       switch (awin_chip_id()) {
+#if defined(ALLWINNER_A10) || defined(ALLWINNER_A20)
+       case AWIN_CHIP_ID_A10:
+       case AWIN_CHIP_ID_A20:
+               awin_dma_a10_attach(sc, aio, loc);
+               break;
+#endif
+#if defined(ALLWINNER_A31)
+       case AWIN_CHIP_ID_A31:
+               awin_dma_a31_attach(sc, aio, loc);
+               break;
+#endif
        }
 
-       sc->sc_ih = intr_establish(loc->loc_intr, IPL_SCHED, IST_LEVEL,
-           awin_dma_intr, sc);
-       if (sc->sc_ih == NULL) {
-               aprint_error_dev(self, "couldn't establish interrupt %d\n",
-                   loc->loc_intr);
-               return;
-       }
-       aprint_normal_dev(self, "interrupting on irq %d\n", loc->loc_intr);
+       KASSERT(sc->sc_dc != NULL);
 }
 
-static int
-awin_dma_intr(void *priv)
+void *
+awin_dma_alloc(const char *type, void (*cb)(void *), void *cbarg)
 {
-       uint32_t sta, bit, mask;
-       uint8_t index;
-
-       sta = DMA_READ(AWIN_DMA_IRQ_PEND_STA_REG);
-       if (!sta)
-               return 0;
-
-       DMA_WRITE(AWIN_DMA_IRQ_PEND_STA_REG, sta);
-
-       while ((bit = ffs(sta & AWIN_DMA_IRQ_END_MASK)) != 0) {
-               mask = __BIT(bit - 1);
-               sta &= ~mask;
-               index = ((bit - 1) / 2) & 7;
-               if (mask & AWIN_DMA_IRQ_NDMA) {
-                       if (awin_ndma_channels[index].ch_callback == NULL)
-                               continue;
-                       awin_ndma_channels[index].ch_callback(
-                           awin_ndma_channels[index].ch_callbackarg);
-               } else {
-                       if (awin_ddma_channels[index].ch_callback == NULL)
-                               continue;
-                       awin_ddma_channels[index].ch_callback(
-                           awin_ddma_channels[index].ch_callbackarg);
-               }
-       }
-
-       return 1;
-}
+       struct awin_dma_softc *sc = awin_dma_sc;
 
-struct awin_dma_channel *
-awin_dma_alloc(enum awin_dma_type type, void (*cb)(void *), void *cbarg)
-{
-       struct awin_dma_channel *ch_list;
-       struct awin_dma_channel *ch = NULL;
-       uint32_t irqen;
-       uint8_t ch_count, index;
-
-       if (type == AWIN_DMA_TYPE_NDMA) {
-               ch_list = awin_ndma_channels;
-               ch_count = NDMA_CHANNELS;
-       } else {
-               ch_list = awin_ndma_channels;
-               ch_count = DDMA_CHANNELS;
-       }
+       if (sc == NULL)
+               return NULL;
 
-       mutex_enter(&awin_dma_lock);
-       for (index = 0; index < ch_count; index++) {
-               if (ch_list[index].ch_callback == NULL) {
-                       ch = &ch_list[index];
-                       ch->ch_callback = cb;
-                       ch->ch_callbackarg = cbarg;
-
-                       irqen = DMA_READ(AWIN_DMA_IRQ_EN_REG);
-                       if (type == AWIN_DMA_TYPE_NDMA)
-                               irqen |= AWIN_DMA_IRQ_NDMA_END(index);
-                       else
-                               irqen |= AWIN_DMA_IRQ_DDMA_END(index);
-                       DMA_WRITE(AWIN_DMA_IRQ_EN_REG, irqen);
-
-                       break;
-               }
-       }
-       mutex_exit(&awin_dma_lock);
-
-       return ch;
+       return sc->sc_dc->dma_alloc(sc, type, cb, cbarg);
 }
 
 void
-awin_dma_free(struct awin_dma_channel *ch)
+awin_dma_free(void *ch)
 {
-       uint32_t irqen, cfg;



Home | Main Index | Thread Index | Old Index