linux/sound/soc/sh/rcar/dma.c
<<
>>
Prefs
   1/*
   2 * Renesas R-Car Audio DMAC support
   3 *
   4 * Copyright (C) 2015 Renesas Electronics Corp.
   5 * Copyright (c) 2015 Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
   6 *
   7 * This program is free software; you can redistribute it and/or modify
   8 * it under the terms of the GNU General Public License version 2 as
   9 * published by the Free Software Foundation.
  10 */
  11#include <linux/delay.h>
  12#include <linux/of_dma.h>
  13#include "rsnd.h"
  14
  15/*
  16 * Audio DMAC peri peri register
  17 */
  18#define PDMASAR         0x00
  19#define PDMADAR         0x04
  20#define PDMACHCR        0x0c
  21
  22/* PDMACHCR */
  23#define PDMACHCR_DE             (1 << 0)
  24
  25
  26struct rsnd_dmaen {
  27        struct dma_chan         *chan;
  28        dma_cookie_t            cookie;
  29        unsigned int            dma_len;
  30};
  31
  32struct rsnd_dmapp {
  33        int                     dmapp_id;
  34        u32                     chcr;
  35};
  36
  37struct rsnd_dma {
  38        struct rsnd_mod         mod;
  39        struct rsnd_mod         *mod_from;
  40        struct rsnd_mod         *mod_to;
  41        dma_addr_t              src_addr;
  42        dma_addr_t              dst_addr;
  43        union {
  44                struct rsnd_dmaen en;
  45                struct rsnd_dmapp pp;
  46        } dma;
  47};
  48
  49struct rsnd_dma_ctrl {
  50        void __iomem *base;
  51        int dmaen_num;
  52        int dmapp_num;
  53};
  54
  55#define rsnd_priv_to_dmac(p)    ((struct rsnd_dma_ctrl *)(p)->dma)
  56#define rsnd_mod_to_dma(_mod) container_of((_mod), struct rsnd_dma, mod)
  57#define rsnd_dma_to_dmaen(dma)  (&(dma)->dma.en)
  58#define rsnd_dma_to_dmapp(dma)  (&(dma)->dma.pp)
  59
  60/* for DEBUG */
  61static struct rsnd_mod_ops mem_ops = {
  62        .name = "mem",
  63};
  64
  65static struct rsnd_mod mem = {
  66};
  67
  68/*
  69 *              Audio DMAC
  70 */
  71static void __rsnd_dmaen_complete(struct rsnd_mod *mod,
  72                                  struct rsnd_dai_stream *io)
  73{
  74        if (rsnd_io_is_working(io))
  75                rsnd_dai_period_elapsed(io);
  76}
  77
  78static void rsnd_dmaen_complete(void *data)
  79{
  80        struct rsnd_mod *mod = data;
  81
  82        rsnd_mod_interrupt(mod, __rsnd_dmaen_complete);
  83}
  84
  85static struct dma_chan *rsnd_dmaen_request_channel(struct rsnd_dai_stream *io,
  86                                                   struct rsnd_mod *mod_from,
  87                                                   struct rsnd_mod *mod_to)
  88{
  89        if ((!mod_from && !mod_to) ||
  90            (mod_from && mod_to))
  91                return NULL;
  92
  93        if (mod_from)
  94                return rsnd_mod_dma_req(io, mod_from);
  95        else
  96                return rsnd_mod_dma_req(io, mod_to);
  97}
  98
  99static int rsnd_dmaen_stop(struct rsnd_mod *mod,
 100                           struct rsnd_dai_stream *io,
 101                           struct rsnd_priv *priv)
 102{
 103        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 104        struct rsnd_dmaen *dmaen = rsnd_dma_to_dmaen(dma);
 105
 106        if (dmaen->chan)
 107                dmaengine_terminate_all(dmaen->chan);
 108
 109        return 0;
 110}
 111
 112static int rsnd_dmaen_nolock_stop(struct rsnd_mod *mod,
 113                                   struct rsnd_dai_stream *io,
 114                                   struct rsnd_priv *priv)
 115{
 116        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 117        struct rsnd_dmaen *dmaen = rsnd_dma_to_dmaen(dma);
 118
 119        /*
 120         * DMAEngine release uses mutex lock.
 121         * Thus, it shouldn't be called under spinlock.
 122         * Let's call it under nolock_start
 123         */
 124        if (dmaen->chan)
 125                dma_release_channel(dmaen->chan);
 126
 127        dmaen->chan = NULL;
 128
 129        return 0;
 130}
 131
 132static int rsnd_dmaen_nolock_start(struct rsnd_mod *mod,
 133                            struct rsnd_dai_stream *io,
 134                            struct rsnd_priv *priv)
 135{
 136        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 137        struct rsnd_dmaen *dmaen = rsnd_dma_to_dmaen(dma);
 138        struct device *dev = rsnd_priv_to_dev(priv);
 139
 140        if (dmaen->chan) {
 141                dev_err(dev, "it already has dma channel\n");
 142                return -EIO;
 143        }
 144
 145        /*
 146         * DMAEngine request uses mutex lock.
 147         * Thus, it shouldn't be called under spinlock.
 148         * Let's call it under nolock_start
 149         */
 150        dmaen->chan = rsnd_dmaen_request_channel(io,
 151                                                 dma->mod_from,
 152                                                 dma->mod_to);
 153        if (IS_ERR_OR_NULL(dmaen->chan)) {
 154                dmaen->chan = NULL;
 155                dev_err(dev, "can't get dma channel\n");
 156                return -EIO;
 157        }
 158
 159        return 0;
 160}
 161
 162static int rsnd_dmaen_start(struct rsnd_mod *mod,
 163                            struct rsnd_dai_stream *io,
 164                            struct rsnd_priv *priv)
 165{
 166        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 167        struct rsnd_dmaen *dmaen = rsnd_dma_to_dmaen(dma);
 168        struct snd_pcm_substream *substream = io->substream;
 169        struct device *dev = rsnd_priv_to_dev(priv);
 170        struct dma_async_tx_descriptor *desc;
 171        struct dma_slave_config cfg = {};
 172        int is_play = rsnd_io_is_play(io);
 173        int ret;
 174
 175        cfg.direction   = is_play ? DMA_MEM_TO_DEV : DMA_DEV_TO_MEM;
 176        cfg.src_addr    = dma->src_addr;
 177        cfg.dst_addr    = dma->dst_addr;
 178        cfg.src_addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
 179        cfg.dst_addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
 180
 181        dev_dbg(dev, "%s[%d] %pad -> %pad\n",
 182                rsnd_mod_name(mod), rsnd_mod_id(mod),
 183                &cfg.src_addr, &cfg.dst_addr);
 184
 185        ret = dmaengine_slave_config(dmaen->chan, &cfg);
 186        if (ret < 0)
 187                return ret;
 188
 189        desc = dmaengine_prep_dma_cyclic(dmaen->chan,
 190                                         substream->runtime->dma_addr,
 191                                         snd_pcm_lib_buffer_bytes(substream),
 192                                         snd_pcm_lib_period_bytes(substream),
 193                                         is_play ? DMA_MEM_TO_DEV : DMA_DEV_TO_MEM,
 194                                         DMA_PREP_INTERRUPT | DMA_CTRL_ACK);
 195
 196        if (!desc) {
 197                dev_err(dev, "dmaengine_prep_slave_sg() fail\n");
 198                return -EIO;
 199        }
 200
 201        desc->callback          = rsnd_dmaen_complete;
 202        desc->callback_param    = rsnd_mod_get(dma);
 203
 204        dmaen->dma_len          = snd_pcm_lib_buffer_bytes(substream);
 205
 206        dmaen->cookie = dmaengine_submit(desc);
 207        if (dmaen->cookie < 0) {
 208                dev_err(dev, "dmaengine_submit() fail\n");
 209                return -EIO;
 210        }
 211
 212        dma_async_issue_pending(dmaen->chan);
 213
 214        return 0;
 215}
 216
 217struct dma_chan *rsnd_dma_request_channel(struct device_node *of_node,
 218                                          struct rsnd_mod *mod, char *name)
 219{
 220        struct dma_chan *chan = NULL;
 221        struct device_node *np;
 222        int i = 0;
 223
 224        for_each_child_of_node(of_node, np) {
 225                if (i == rsnd_mod_id(mod) && (!chan))
 226                        chan = of_dma_request_slave_channel(np, name);
 227                i++;
 228        }
 229
 230        /* It should call of_node_put(), since, it is rsnd_xxx_of_node() */
 231        of_node_put(of_node);
 232
 233        return chan;
 234}
 235
 236static int rsnd_dmaen_attach(struct rsnd_dai_stream *io,
 237                           struct rsnd_dma *dma,
 238                           struct rsnd_mod *mod_from, struct rsnd_mod *mod_to)
 239{
 240        struct rsnd_priv *priv = rsnd_io_to_priv(io);
 241        struct rsnd_dma_ctrl *dmac = rsnd_priv_to_dmac(priv);
 242        struct dma_chan *chan;
 243
 244        /* try to get DMAEngine channel */
 245        chan = rsnd_dmaen_request_channel(io, mod_from, mod_to);
 246        if (IS_ERR_OR_NULL(chan)) {
 247                /*
 248                 * DMA failed. try to PIO mode
 249                 * see
 250                 *      rsnd_ssi_fallback()
 251                 *      rsnd_rdai_continuance_probe()
 252                 */
 253                return -EAGAIN;
 254        }
 255
 256        dma_release_channel(chan);
 257
 258        dmac->dmaen_num++;
 259
 260        return 0;
 261}
 262
 263static int rsnd_dmaen_pointer(struct rsnd_mod *mod,
 264                              struct rsnd_dai_stream *io,
 265                              snd_pcm_uframes_t *pointer)
 266{
 267        struct snd_pcm_runtime *runtime = rsnd_io_to_runtime(io);
 268        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 269        struct rsnd_dmaen *dmaen = rsnd_dma_to_dmaen(dma);
 270        struct dma_tx_state state;
 271        enum dma_status status;
 272        unsigned int pos = 0;
 273
 274        status = dmaengine_tx_status(dmaen->chan, dmaen->cookie, &state);
 275        if (status == DMA_IN_PROGRESS || status == DMA_PAUSED) {
 276                if (state.residue > 0 && state.residue <= dmaen->dma_len)
 277                        pos = dmaen->dma_len - state.residue;
 278        }
 279        *pointer = bytes_to_frames(runtime, pos);
 280
 281        return 0;
 282}
 283
 284static struct rsnd_mod_ops rsnd_dmaen_ops = {
 285        .name   = "audmac",
 286        .nolock_start = rsnd_dmaen_nolock_start,
 287        .nolock_stop  = rsnd_dmaen_nolock_stop,
 288        .start  = rsnd_dmaen_start,
 289        .stop   = rsnd_dmaen_stop,
 290        .pointer= rsnd_dmaen_pointer,
 291};
 292
 293/*
 294 *              Audio DMAC peri peri
 295 */
 296static const u8 gen2_id_table_ssiu[] = {
 297        0x00, /* SSI00 */
 298        0x04, /* SSI10 */
 299        0x08, /* SSI20 */
 300        0x0c, /* SSI3  */
 301        0x0d, /* SSI4  */
 302        0x0e, /* SSI5  */
 303        0x0f, /* SSI6  */
 304        0x10, /* SSI7  */
 305        0x11, /* SSI8  */
 306        0x12, /* SSI90 */
 307};
 308static const u8 gen2_id_table_scu[] = {
 309        0x2d, /* SCU_SRCI0 */
 310        0x2e, /* SCU_SRCI1 */
 311        0x2f, /* SCU_SRCI2 */
 312        0x30, /* SCU_SRCI3 */
 313        0x31, /* SCU_SRCI4 */
 314        0x32, /* SCU_SRCI5 */
 315        0x33, /* SCU_SRCI6 */
 316        0x34, /* SCU_SRCI7 */
 317        0x35, /* SCU_SRCI8 */
 318        0x36, /* SCU_SRCI9 */
 319};
 320static const u8 gen2_id_table_cmd[] = {
 321        0x37, /* SCU_CMD0 */
 322        0x38, /* SCU_CMD1 */
 323};
 324
 325static u32 rsnd_dmapp_get_id(struct rsnd_dai_stream *io,
 326                             struct rsnd_mod *mod)
 327{
 328        struct rsnd_mod *ssi = rsnd_io_to_mod_ssi(io);
 329        struct rsnd_mod *src = rsnd_io_to_mod_src(io);
 330        struct rsnd_mod *dvc = rsnd_io_to_mod_dvc(io);
 331        const u8 *entry = NULL;
 332        int id = rsnd_mod_id(mod);
 333        int size = 0;
 334
 335        if (mod == ssi) {
 336                entry = gen2_id_table_ssiu;
 337                size = ARRAY_SIZE(gen2_id_table_ssiu);
 338        } else if (mod == src) {
 339                entry = gen2_id_table_scu;
 340                size = ARRAY_SIZE(gen2_id_table_scu);
 341        } else if (mod == dvc) {
 342                entry = gen2_id_table_cmd;
 343                size = ARRAY_SIZE(gen2_id_table_cmd);
 344        }
 345
 346        if ((!entry) || (size <= id)) {
 347                struct device *dev = rsnd_priv_to_dev(rsnd_io_to_priv(io));
 348
 349                dev_err(dev, "unknown connection (%s[%d])\n",
 350                        rsnd_mod_name(mod), rsnd_mod_id(mod));
 351
 352                /* use non-prohibited SRS number as error */
 353                return 0x00; /* SSI00 */
 354        }
 355
 356        return entry[id];
 357}
 358
 359static u32 rsnd_dmapp_get_chcr(struct rsnd_dai_stream *io,
 360                               struct rsnd_mod *mod_from,
 361                               struct rsnd_mod *mod_to)
 362{
 363        return  (rsnd_dmapp_get_id(io, mod_from) << 24) +
 364                (rsnd_dmapp_get_id(io, mod_to) << 16);
 365}
 366
 367#define rsnd_dmapp_addr(dmac, dma, reg) \
 368        (dmac->base + 0x20 + reg + \
 369         (0x10 * rsnd_dma_to_dmapp(dma)->dmapp_id))
 370static void rsnd_dmapp_write(struct rsnd_dma *dma, u32 data, u32 reg)
 371{
 372        struct rsnd_mod *mod = rsnd_mod_get(dma);
 373        struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
 374        struct rsnd_dma_ctrl *dmac = rsnd_priv_to_dmac(priv);
 375        struct device *dev = rsnd_priv_to_dev(priv);
 376
 377        dev_dbg(dev, "w %p : %08x\n", rsnd_dmapp_addr(dmac, dma, reg), data);
 378
 379        iowrite32(data, rsnd_dmapp_addr(dmac, dma, reg));
 380}
 381
 382static u32 rsnd_dmapp_read(struct rsnd_dma *dma, u32 reg)
 383{
 384        struct rsnd_mod *mod = rsnd_mod_get(dma);
 385        struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
 386        struct rsnd_dma_ctrl *dmac = rsnd_priv_to_dmac(priv);
 387
 388        return ioread32(rsnd_dmapp_addr(dmac, dma, reg));
 389}
 390
 391static void rsnd_dmapp_bset(struct rsnd_dma *dma, u32 data, u32 mask, u32 reg)
 392{
 393        struct rsnd_mod *mod = rsnd_mod_get(dma);
 394        struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
 395        struct rsnd_dma_ctrl *dmac = rsnd_priv_to_dmac(priv);
 396        void __iomem *addr = rsnd_dmapp_addr(dmac, dma, reg);
 397        u32 val = ioread32(addr);
 398
 399        val &= ~mask;
 400        val |= (data & mask);
 401
 402        iowrite32(val, addr);
 403}
 404
 405static int rsnd_dmapp_stop(struct rsnd_mod *mod,
 406                           struct rsnd_dai_stream *io,
 407                           struct rsnd_priv *priv)
 408{
 409        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 410        int i;
 411
 412        rsnd_dmapp_bset(dma, 0,  PDMACHCR_DE, PDMACHCR);
 413
 414        for (i = 0; i < 1024; i++) {
 415                if (0 == (rsnd_dmapp_read(dma, PDMACHCR) & PDMACHCR_DE))
 416                        return 0;
 417                udelay(1);
 418        }
 419
 420        return -EIO;
 421}
 422
 423static int rsnd_dmapp_start(struct rsnd_mod *mod,
 424                            struct rsnd_dai_stream *io,
 425                            struct rsnd_priv *priv)
 426{
 427        struct rsnd_dma *dma = rsnd_mod_to_dma(mod);
 428        struct rsnd_dmapp *dmapp = rsnd_dma_to_dmapp(dma);
 429
 430        rsnd_dmapp_write(dma, dma->src_addr,    PDMASAR);
 431        rsnd_dmapp_write(dma, dma->dst_addr,    PDMADAR);
 432        rsnd_dmapp_write(dma, dmapp->chcr,      PDMACHCR);
 433
 434        return 0;
 435}
 436
 437static int rsnd_dmapp_attach(struct rsnd_dai_stream *io,
 438                             struct rsnd_dma *dma,
 439                             struct rsnd_mod *mod_from, struct rsnd_mod *mod_to)
 440{
 441        struct rsnd_dmapp *dmapp = rsnd_dma_to_dmapp(dma);
 442        struct rsnd_priv *priv = rsnd_io_to_priv(io);
 443        struct rsnd_dma_ctrl *dmac = rsnd_priv_to_dmac(priv);
 444        struct device *dev = rsnd_priv_to_dev(priv);
 445
 446        dmapp->dmapp_id = dmac->dmapp_num;
 447        dmapp->chcr = rsnd_dmapp_get_chcr(io, mod_from, mod_to) | PDMACHCR_DE;
 448
 449        dmac->dmapp_num++;
 450
 451        dev_dbg(dev, "id/src/dst/chcr = %d/%pad/%pad/%08x\n",
 452                dmapp->dmapp_id, &dma->src_addr, &dma->dst_addr, dmapp->chcr);
 453
 454        return 0;
 455}
 456
 457static struct rsnd_mod_ops rsnd_dmapp_ops = {
 458        .name   = "audmac-pp",
 459        .start  = rsnd_dmapp_start,
 460        .stop   = rsnd_dmapp_stop,
 461        .quit   = rsnd_dmapp_stop,
 462};
 463
 464/*
 465 *              Common DMAC Interface
 466 */
 467
 468/*
 469 *      DMA read/write register offset
 470 *
 471 *      RSND_xxx_I_N    for Audio DMAC input
 472 *      RSND_xxx_O_N    for Audio DMAC output
 473 *      RSND_xxx_I_P    for Audio DMAC peri peri input
 474 *      RSND_xxx_O_P    for Audio DMAC peri peri output
 475 *
 476 *      ex) R-Car H2 case
 477 *            mod        / DMAC in    / DMAC out   / DMAC PP in / DMAC pp out
 478 *      SSI : 0xec541000 / 0xec241008 / 0xec24100c
 479 *      SSIU: 0xec541000 / 0xec100000 / 0xec100000 / 0xec400000 / 0xec400000
 480 *      SCU : 0xec500000 / 0xec000000 / 0xec004000 / 0xec300000 / 0xec304000
 481 *      CMD : 0xec500000 /            / 0xec008000                0xec308000
 482 */
 483#define RDMA_SSI_I_N(addr, i)   (addr ##_reg - 0x00300000 + (0x40 * i) + 0x8)
 484#define RDMA_SSI_O_N(addr, i)   (addr ##_reg - 0x00300000 + (0x40 * i) + 0xc)
 485
 486#define RDMA_SSIU_I_N(addr, i)  (addr ##_reg - 0x00441000 + (0x1000 * i))
 487#define RDMA_SSIU_O_N(addr, i)  (addr ##_reg - 0x00441000 + (0x1000 * i))
 488
 489#define RDMA_SSIU_I_P(addr, i)  (addr ##_reg - 0x00141000 + (0x1000 * i))
 490#define RDMA_SSIU_O_P(addr, i)  (addr ##_reg - 0x00141000 + (0x1000 * i))
 491
 492#define RDMA_SRC_I_N(addr, i)   (addr ##_reg - 0x00500000 + (0x400 * i))
 493#define RDMA_SRC_O_N(addr, i)   (addr ##_reg - 0x004fc000 + (0x400 * i))
 494
 495#define RDMA_SRC_I_P(addr, i)   (addr ##_reg - 0x00200000 + (0x400 * i))
 496#define RDMA_SRC_O_P(addr, i)   (addr ##_reg - 0x001fc000 + (0x400 * i))
 497
 498#define RDMA_CMD_O_N(addr, i)   (addr ##_reg - 0x004f8000 + (0x400 * i))
 499#define RDMA_CMD_O_P(addr, i)   (addr ##_reg - 0x001f8000 + (0x400 * i))
 500
 501static dma_addr_t
 502rsnd_gen2_dma_addr(struct rsnd_dai_stream *io,
 503                   struct rsnd_mod *mod,
 504                   int is_play, int is_from)
 505{
 506        struct rsnd_priv *priv = rsnd_io_to_priv(io);
 507        struct device *dev = rsnd_priv_to_dev(priv);
 508        phys_addr_t ssi_reg = rsnd_gen_get_phy_addr(priv, RSND_GEN2_SSI);
 509        phys_addr_t src_reg = rsnd_gen_get_phy_addr(priv, RSND_GEN2_SCU);
 510        int is_ssi = !!(rsnd_io_to_mod_ssi(io) == mod);
 511        int use_src = !!rsnd_io_to_mod_src(io);
 512        int use_cmd = !!rsnd_io_to_mod_dvc(io) ||
 513                      !!rsnd_io_to_mod_mix(io) ||
 514                      !!rsnd_io_to_mod_ctu(io);
 515        int id = rsnd_mod_id(mod);
 516        struct dma_addr {
 517                dma_addr_t out_addr;
 518                dma_addr_t in_addr;
 519        } dma_addrs[3][2][3] = {
 520                /* SRC */
 521                /* Capture */
 522                {{{ 0,                          0 },
 523                  { RDMA_SRC_O_N(src, id),      RDMA_SRC_I_P(src, id) },
 524                  { RDMA_CMD_O_N(src, id),      RDMA_SRC_I_P(src, id) } },
 525                 /* Playback */
 526                 {{ 0,                          0, },
 527                  { RDMA_SRC_O_P(src, id),      RDMA_SRC_I_N(src, id) },
 528                  { RDMA_CMD_O_P(src, id),      RDMA_SRC_I_N(src, id) } }
 529                },
 530                /* SSI */
 531                /* Capture */
 532                {{{ RDMA_SSI_O_N(ssi, id),      0 },
 533                  { RDMA_SSIU_O_P(ssi, id),     0 },
 534                  { RDMA_SSIU_O_P(ssi, id),     0 } },
 535                 /* Playback */
 536                 {{ 0,                          RDMA_SSI_I_N(ssi, id) },
 537                  { 0,                          RDMA_SSIU_I_P(ssi, id) },
 538                  { 0,                          RDMA_SSIU_I_P(ssi, id) } }
 539                },
 540                /* SSIU */
 541                /* Capture */
 542                {{{ RDMA_SSIU_O_N(ssi, id),     0 },
 543                  { RDMA_SSIU_O_P(ssi, id),     0 },
 544                  { RDMA_SSIU_O_P(ssi, id),     0 } },
 545                 /* Playback */
 546                 {{ 0,                          RDMA_SSIU_I_N(ssi, id) },
 547                  { 0,                          RDMA_SSIU_I_P(ssi, id) },
 548                  { 0,                          RDMA_SSIU_I_P(ssi, id) } } },
 549        };
 550
 551        /* it shouldn't happen */
 552        if (use_cmd && !use_src)
 553                dev_err(dev, "DVC is selected without SRC\n");
 554
 555        /* use SSIU or SSI ? */
 556        if (is_ssi && rsnd_ssi_use_busif(io))
 557                is_ssi++;
 558
 559        return (is_from) ?
 560                dma_addrs[is_ssi][is_play][use_src + use_cmd].out_addr :
 561                dma_addrs[is_ssi][is_play][use_src + use_cmd].in_addr;
 562}
 563
 564static dma_addr_t rsnd_dma_addr(struct rsnd_dai_stream *io,
 565                                struct rsnd_mod *mod,
 566                                int is_play, int is_from)
 567{
 568        struct rsnd_priv *priv = rsnd_io_to_priv(io);
 569
 570        /*
 571         * gen1 uses default DMA addr
 572         */
 573        if (rsnd_is_gen1(priv))
 574                return 0;
 575
 576        if (!mod)
 577                return 0;
 578
 579        return rsnd_gen2_dma_addr(io, mod, is_play, is_from);
 580}
 581
 582#define MOD_MAX (RSND_MOD_MAX + 1) /* +Memory */
 583static void rsnd_dma_of_path(struct rsnd_mod *this,
 584                             struct rsnd_dai_stream *io,
 585                             int is_play,
 586                             struct rsnd_mod **mod_from,
 587                             struct rsnd_mod **mod_to)
 588{
 589        struct rsnd_mod *ssi = rsnd_io_to_mod_ssi(io);
 590        struct rsnd_mod *src = rsnd_io_to_mod_src(io);
 591        struct rsnd_mod *ctu = rsnd_io_to_mod_ctu(io);
 592        struct rsnd_mod *mix = rsnd_io_to_mod_mix(io);
 593        struct rsnd_mod *dvc = rsnd_io_to_mod_dvc(io);
 594        struct rsnd_mod *mod[MOD_MAX];
 595        struct rsnd_mod *mod_start, *mod_end;
 596        struct rsnd_priv *priv = rsnd_mod_to_priv(this);
 597        struct device *dev = rsnd_priv_to_dev(priv);
 598        int nr, i, idx;
 599
 600        if (!ssi)
 601                return;
 602
 603        nr = 0;
 604        for (i = 0; i < MOD_MAX; i++) {
 605                mod[i] = NULL;
 606                nr += !!rsnd_io_to_mod(io, i);
 607        }
 608
 609        /*
 610         * [S] -*-> [E]
 611         * [S] -*-> SRC -o-> [E]
 612         * [S] -*-> SRC -> DVC -o-> [E]
 613         * [S] -*-> SRC -> CTU -> MIX -> DVC -o-> [E]
 614         *
 615         * playback     [S] = mem
 616         *              [E] = SSI
 617         *
 618         * capture      [S] = SSI
 619         *              [E] = mem
 620         *
 621         * -*->         Audio DMAC
 622         * -o->         Audio DMAC peri peri
 623         */
 624        mod_start       = (is_play) ? NULL : ssi;
 625        mod_end         = (is_play) ? ssi  : NULL;
 626
 627        idx = 0;
 628        mod[idx++] = mod_start;
 629        for (i = 1; i < nr; i++) {
 630                if (src) {
 631                        mod[idx++] = src;
 632                        src = NULL;
 633                } else if (ctu) {
 634                        mod[idx++] = ctu;
 635                        ctu = NULL;
 636                } else if (mix) {
 637                        mod[idx++] = mix;
 638                        mix = NULL;
 639                } else if (dvc) {
 640                        mod[idx++] = dvc;
 641                        dvc = NULL;
 642                }
 643        }
 644        mod[idx] = mod_end;
 645
 646        /*
 647         *              | SSI | SRC |
 648         * -------------+-----+-----+
 649         *  is_play     |  o  |  *  |
 650         * !is_play     |  *  |  o  |
 651         */
 652        if ((this == ssi) == (is_play)) {
 653                *mod_from       = mod[idx - 1];
 654                *mod_to         = mod[idx];
 655        } else {
 656                *mod_from       = mod[0];
 657                *mod_to         = mod[1];
 658        }
 659
 660        dev_dbg(dev, "module connection (this is %s[%d])\n",
 661                rsnd_mod_name(this), rsnd_mod_id(this));
 662        for (i = 0; i <= idx; i++) {
 663                dev_dbg(dev, "  %s[%d]%s\n",
 664                        rsnd_mod_name(mod[i] ? mod[i] : &mem),
 665                        rsnd_mod_id  (mod[i] ? mod[i] : &mem),
 666                        (mod[i] == *mod_from) ? " from" :
 667                        (mod[i] == *mod_to)   ? " to" : "");
 668        }
 669}
 670
 671static int rsnd_dma_alloc(struct rsnd_dai_stream *io, struct rsnd_mod *mod,
 672                          struct rsnd_mod **dma_mod)
 673{
 674        struct rsnd_mod *mod_from = NULL;
 675        struct rsnd_mod *mod_to = NULL;
 676        struct rsnd_priv *priv = rsnd_io_to_priv(io);
 677        struct rsnd_dma_ctrl *dmac = rsnd_priv_to_dmac(priv);
 678        struct device *dev = rsnd_priv_to_dev(priv);
 679        struct rsnd_dma *dma;
 680        struct rsnd_mod_ops *ops;
 681        enum rsnd_mod_type type;
 682        int (*attach)(struct rsnd_dai_stream *io, struct rsnd_dma *dma,
 683                      struct rsnd_mod *mod_from, struct rsnd_mod *mod_to);
 684        int is_play = rsnd_io_is_play(io);
 685        int ret, dma_id;
 686
 687        /*
 688         * DMA failed. try to PIO mode
 689         * see
 690         *      rsnd_ssi_fallback()
 691         *      rsnd_rdai_continuance_probe()
 692         */
 693        if (!dmac)
 694                return -EAGAIN;
 695
 696        rsnd_dma_of_path(mod, io, is_play, &mod_from, &mod_to);
 697
 698        /* for Gen2 */
 699        if (mod_from && mod_to) {
 700                ops     = &rsnd_dmapp_ops;
 701                attach  = rsnd_dmapp_attach;
 702                dma_id  = dmac->dmapp_num;
 703                type    = RSND_MOD_AUDMAPP;
 704        } else {
 705                ops     = &rsnd_dmaen_ops;
 706                attach  = rsnd_dmaen_attach;
 707                dma_id  = dmac->dmaen_num;
 708                type    = RSND_MOD_AUDMA;
 709        }
 710
 711        /* for Gen1, overwrite */
 712        if (rsnd_is_gen1(priv)) {
 713                ops     = &rsnd_dmaen_ops;
 714                attach  = rsnd_dmaen_attach;
 715                dma_id  = dmac->dmaen_num;
 716                type    = RSND_MOD_AUDMA;
 717        }
 718
 719        dma = devm_kzalloc(dev, sizeof(*dma), GFP_KERNEL);
 720        if (!dma)
 721                return -ENOMEM;
 722
 723        *dma_mod = rsnd_mod_get(dma);
 724
 725        ret = rsnd_mod_init(priv, *dma_mod, ops, NULL,
 726                            rsnd_mod_get_status, type, dma_id);
 727        if (ret < 0)
 728                return ret;
 729
 730        dev_dbg(dev, "%s[%d] %s[%d] -> %s[%d]\n",
 731                rsnd_mod_name(*dma_mod), rsnd_mod_id(*dma_mod),
 732                rsnd_mod_name(mod_from ? mod_from : &mem),
 733                rsnd_mod_id  (mod_from ? mod_from : &mem),
 734                rsnd_mod_name(mod_to   ? mod_to   : &mem),
 735                rsnd_mod_id  (mod_to   ? mod_to   : &mem));
 736
 737        ret = attach(io, dma, mod_from, mod_to);
 738        if (ret < 0)
 739                return ret;
 740
 741        dma->src_addr = rsnd_dma_addr(io, mod_from, is_play, 1);
 742        dma->dst_addr = rsnd_dma_addr(io, mod_to,   is_play, 0);
 743        dma->mod_from = mod_from;
 744        dma->mod_to   = mod_to;
 745
 746        return 0;
 747}
 748
 749int rsnd_dma_attach(struct rsnd_dai_stream *io, struct rsnd_mod *mod,
 750                    struct rsnd_mod **dma_mod)
 751{
 752        if (!(*dma_mod)) {
 753                int ret = rsnd_dma_alloc(io, mod, dma_mod);
 754
 755                if (ret < 0)
 756                        return ret;
 757        }
 758
 759        return rsnd_dai_connect(*dma_mod, io, (*dma_mod)->type);
 760}
 761
 762int rsnd_dma_probe(struct rsnd_priv *priv)
 763{
 764        struct platform_device *pdev = rsnd_priv_to_pdev(priv);
 765        struct device *dev = rsnd_priv_to_dev(priv);
 766        struct rsnd_dma_ctrl *dmac;
 767        struct resource *res;
 768
 769        /*
 770         * for Gen1
 771         */
 772        if (rsnd_is_gen1(priv))
 773                return 0;
 774
 775        /*
 776         * for Gen2
 777         */
 778        res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "audmapp");
 779        dmac = devm_kzalloc(dev, sizeof(*dmac), GFP_KERNEL);
 780        if (!dmac || !res) {
 781                dev_err(dev, "dma allocate failed\n");
 782                return 0; /* it will be PIO mode */
 783        }
 784
 785        dmac->dmapp_num = 0;
 786        dmac->base = devm_ioremap_resource(dev, res);
 787        if (IS_ERR(dmac->base))
 788                return PTR_ERR(dmac->base);
 789
 790        priv->dma = dmac;
 791
 792        /* dummy mem mod for debug */
 793        return rsnd_mod_init(NULL, &mem, &mem_ops, NULL, NULL, 0, 0);
 794}
 795