[ARM] S3C24XX: Remove hardware specific registers from DMA
authorBen Dooks <ben@simtec.co.uk>
Thu, 19 Mar 2009 15:02:34 +0000 (15:02 +0000)
committerBen Dooks <ben-linux@fluff.org>
Fri, 1 May 2009 10:39:06 +0000 (11:39 +0100)
calls

The S3C24XX DMA API channel configuration registers are being passed
values comprised of register values which makes it hard to move the
API to cover both the S3C24XX and S3C64XX.

These values can be calculated from knowing which device the channel
is connected to, so remove them from the two calls s3c2410_dma_config
and s3c2410_dma_devconfig.

Signed-off-by: Ben Dooks <ben@simtec.co.uk>
Signed-off-by: Ben Dooks <ben-linux@fluff.org>
arch/arm/mach-s3c2410/include/mach/dma.h
arch/arm/plat-s3c24xx/dma.c
drivers/mmc/host/s3cmci.c
sound/soc/s3c24xx/s3c24xx-pcm.c

index 13358ce2128c7c16346d4d65932c13dbf3630cdf..acaef6784e9529fb3cf2e3505b35dc63f8052376 100644 (file)
@@ -206,10 +206,10 @@ struct s3c2410_dma_chan {
 
        /* channel configuration */
        enum s3c2410_dmasrc      source;
+       enum dma_ch              req_ch;
        unsigned long            dev_addr;
        unsigned long            load_timeout;
        unsigned int             flags;         /* channel flags */
-       unsigned int             hw_cfg;        /* last hw config */
 
        struct s3c24xx_dma_map  *map;           /* channel hw maps */
 
@@ -290,7 +290,7 @@ extern int s3c2410_dma_enqueue(unsigned int channel, void *id,
  * configure the dma channel
 */
 
-extern int s3c2410_dma_config(unsigned int channel, int xferunit, int dcon);
+extern int s3c2410_dma_config(unsigned int channel, int xferunit);
 
 /* s3c2410_dma_devconfig
  *
@@ -298,7 +298,7 @@ extern int s3c2410_dma_config(unsigned int channel, int xferunit, int dcon);
 */
 
 extern int s3c2410_dma_devconfig(int channel, enum s3c2410_dmasrc source,
-                                int hwcfg, unsigned long devaddr);
+                                unsigned long devaddr);
 
 /* s3c2410_dma_getposition
  *
index d3d1375d95b3768efba05799c774f68195b8c277..dc58a0ddc9f602bca55a3eb0d108e56b930dd677 100644 (file)
@@ -1038,14 +1038,13 @@ EXPORT_SYMBOL(s3c2410_dma_ctrl);
 /* s3c2410_dma_config
  *
  * xfersize:     size of unit in bytes (1,2,4)
- * dcon:         base value of the DCONx register
 */
 
 int s3c2410_dma_config(unsigned int channel,
-                      int xferunit,
-                      int dcon)
+                      int xferunit)
 {
        struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
+       unsigned int dcon;
 
        pr_debug("%s: chan=%d, xfer_unit=%d, dcon=%08x\n",
                 __func__, channel, xferunit, dcon);
@@ -1055,10 +1054,33 @@ int s3c2410_dma_config(unsigned int channel,
 
        pr_debug("%s: Initial dcon is %08x\n", __func__, dcon);
 
-       dcon |= chan->dcon & dma_sel.dcon_mask;
+       dcon = chan->dcon & dma_sel.dcon_mask;
 
        pr_debug("%s: New dcon is %08x\n", __func__, dcon);
 
+       switch (chan->req_ch) {
+       case DMACH_I2S_IN:
+       case DMACH_I2S_OUT:
+       case DMACH_PCM_IN:
+       case DMACH_PCM_OUT:
+       case DMACH_MIC_IN:
+       default:
+               dcon |= S3C2410_DCON_HANDSHAKE;
+               dcon |= S3C2410_DCON_SYNC_PCLK;
+               break;
+
+       case DMACH_SDI:
+               /* note, ensure if need HANDSHAKE or not */
+               dcon |= S3C2410_DCON_SYNC_PCLK;
+               break;
+
+       case DMACH_XD0:
+       case DMACH_XD1:
+               dcon |= S3C2410_DCON_HANDSHAKE;
+               dcon |= S3C2410_DCON_SYNC_HCLK;
+               break;
+       }
+
        switch (xferunit) {
        case 1:
                dcon |= S3C2410_DCON_BYTE;
@@ -1150,29 +1172,38 @@ EXPORT_SYMBOL(s3c2410_dma_set_buffdone_fn);
  * source:    S3C2410_DMASRC_HW: source is hardware
  *            S3C2410_DMASRC_MEM: source is memory
  *
- * hwcfg:     the value for xxxSTCn register,
- *            bit 0: 0=increment pointer, 1=leave pointer
- *            bit 1: 0=source is AHB, 1=source is APB
- *
  * devaddr:   physical address of the source
 */
 
 int s3c2410_dma_devconfig(int channel,
                          enum s3c2410_dmasrc source,
-                         int hwcfg,
                          unsigned long devaddr)
 {
        struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
+       unsigned int hwcfg;
 
        if (chan == NULL)
                return -EINVAL;
 
-       pr_debug("%s: source=%d, hwcfg=%08x, devaddr=%08lx\n",
-                __func__, (int)source, hwcfg, devaddr);
+       pr_debug("%s: source=%d, devaddr=%08lx\n",
+                __func__, (int)source, devaddr);
 
        chan->source = source;
        chan->dev_addr = devaddr;
-       chan->hw_cfg = hwcfg;
+
+       switch (chan->req_ch) {
+       case DMACH_XD0:
+       case DMACH_XD1:
+               hwcfg = 0; /* AHB */
+               break;
+
+       default:
+               hwcfg = S3C2410_DISRCC_APB;
+       }
+
+       /* always assume our peripheral desintation is a fixed
+        * address in memory. */
+        hwcfg |= S3C2410_DISRCC_INC;
 
        switch (source) {
        case S3C2410_DMASRC_HW:
@@ -1278,8 +1309,8 @@ static int s3c2410_dma_resume(struct sys_device *dev)
 
        printk(KERN_INFO "dma%d: restoring configuration\n", cp->number);
 
-       s3c2410_dma_config(no, cp->xfer_unit, cp->dcon);
-       s3c2410_dma_devconfig(no, cp->source, cp->hw_cfg, cp->dev_addr);
+       s3c2410_dma_config(no, cp->xfer_unit);
+       s3c2410_dma_devconfig(no, cp->source, cp->dev_addr);
 
        /* re-select the dma source for this channel */
 
@@ -1476,6 +1507,7 @@ static struct s3c2410_dma_chan *s3c2410_dma_map_channel(int channel)
  found:
        dmach = &s3c2410_chans[ch];
        dmach->map = ch_map;
+       dmach->req_ch = channel;
        dma_chan_map[channel] = dmach;
 
        /* select the channel */
index 2db166b7096f42ddf1ed5eac276de476adb9fc3e..889f35047a52635ca77a8fb0bf3b3e073fddc34a 100644 (file)
@@ -789,7 +789,7 @@ static void s3cmci_dma_setup(struct s3cmci_host *host,
 
        last_source = source;
 
-       s3c2410_dma_devconfig(host->dma, source, 3,
+       s3c2410_dma_devconfig(host->dma, source,
                              host->mem->start + host->sdidata);
 
        if (!setup_ok) {
index 169ddad31575e9601e3e703074a75c1fca398533..eecfa5eba06b0bf0b450d518368df1fe90cc52f6 100644 (file)
@@ -218,24 +218,17 @@ static int s3c24xx_pcm_prepare(struct snd_pcm_substream *substream)
         * sync to pclk, half-word transfers to the IIS-FIFO. */
        if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) {
                s3c2410_dma_devconfig(prtd->params->channel,
-                               S3C2410_DMASRC_MEM, S3C2410_DISRCC_INC |
-                               S3C2410_DISRCC_APB, prtd->params->dma_addr);
-
-               s3c2410_dma_config(prtd->params->channel,
-                               prtd->params->dma_size,
-                               S3C2410_DCON_SYNC_PCLK |
-                               S3C2410_DCON_HANDSHAKE);
+                                     S3C2410_DMASRC_MEM,
+                                     prtd->params->dma_addr);
        } else {
-               s3c2410_dma_config(prtd->params->channel,
-                               prtd->params->dma_size,
-                               S3C2410_DCON_HANDSHAKE |
-                               S3C2410_DCON_SYNC_PCLK);
-
                s3c2410_dma_devconfig(prtd->params->channel,
-                                       S3C2410_DMASRC_HW, 0x3,
-                                       prtd->params->dma_addr);
+                                     S3C2410_DMASRC_HW,
+                                     prtd->params->dma_addr);
        }
 
+       s3c2410_dma_config(prtd->params->channel,
+                          prtd->params->dma_size);
+
        /* flush the DMA channel */
        s3c2410_dma_ctrl(prtd->params->channel, S3C2410_DMAOP_FLUSH);
        prtd->dma_loaded = 0;