aboutsummaryrefslogtreecommitdiffstats
path: root/sound/soc/sh/rcar/gen.c
diff options
context:
space:
mode:
authorMark Brown <broonie@linaro.org>2014-08-15 07:51:28 -0400
committerMark Brown <broonie@linaro.org>2014-08-15 07:51:28 -0400
commit543c675482bcf1e7b9f85bb1589314f38f60c520 (patch)
tree904f425393ac99539827d3164d2b0f78ac1607c5 /sound/soc/sh/rcar/gen.c
parent2fa4a285ddfd39cfa711da3f5e898ec2ce80ef87 (diff)
parentae34a78c430c37c06404f032fb04e51315204281 (diff)
Merge tag 'asoc-v3.17' into asoc-linus
ASoC: Updates for v3.17 This has been a pretty exciting release in terms of the framework, we've finally got support for multiple CODECs attached to a single DAI link which has been something there's been interest in as long as I've been working on ASoC. A big thanks to Benoit and Misael for their work on this. Otherwise it's been a fairly standard release for development, including more componentisation work from Lars-Peter and a good selection of both CODEC and CPU drivers. - Support for multiple CODECs attached to a single DAI, enabling systems with for example multiple DAC/speaker drivers on a single link, contributed by Benoit Cousson based on work from Misael Lopez Cruz. - Support for byte controls larger than 256 bytes based on the use of TLVs contributed by Omair Mohammed Abdullah. - More componentisation work from Lars-Peter Clausen. - The remainder of the conversions of CODEC drivers to params_width() - Drivers for Cirrus Logic CS4265, Freescale i.MX ASRC blocks, Realtek RT286 and RT5670, Rockchip RK3xxx I2S controllers and Texas Instruments TAS2552. - Lots of updates and fixes, especially to the DaVinci, Intel, Freescale, Realtek, and rcar drivers. # gpg: Signature made Mon 04 Aug 2014 17:13:21 BST using RSA key ID 7EA229BD # gpg: Good signature from "Mark Brown <broonie@sirena.org.uk>" # gpg: aka "Mark Brown <broonie@debian.org>" # gpg: aka "Mark Brown <broonie@kernel.org>" # gpg: aka "Mark Brown <broonie@tardis.ed.ac.uk>" # gpg: aka "Mark Brown <broonie@linaro.org>" # gpg: aka "Mark Brown <Mark.Brown@linaro.org>"
Diffstat (limited to 'sound/soc/sh/rcar/gen.c')
-rw-r--r--sound/soc/sh/rcar/gen.c553
1 files changed, 252 insertions, 301 deletions
diff --git a/sound/soc/sh/rcar/gen.c b/sound/soc/sh/rcar/gen.c
index 0280a11c0899..3fdf3be7b99a 100644
--- a/sound/soc/sh/rcar/gen.c
+++ b/sound/soc/sh/rcar/gen.c
@@ -15,63 +15,35 @@ struct rsnd_gen {
15 15
16 struct rsnd_gen_ops *ops; 16 struct rsnd_gen_ops *ops;
17 17
18 struct regmap *regmap; 18 struct regmap *regmap[RSND_BASE_MAX];
19 struct regmap_field *regs[RSND_REG_MAX]; 19 struct regmap_field *regs[RSND_REG_MAX];
20}; 20};
21 21
22#define rsnd_priv_to_gen(p) ((struct rsnd_gen *)(p)->gen) 22#define rsnd_priv_to_gen(p) ((struct rsnd_gen *)(p)->gen)
23 23
24#define RSND_REG_SET(gen, id, reg_id, offset, _id_offset, _id_size) \ 24struct rsnd_regmap_field_conf {
25 [id] = { \ 25 int idx;
26 .reg = (unsigned int)gen->base[reg_id] + offset, \ 26 unsigned int reg_offset;
27 .lsb = 0, \ 27 unsigned int id_offset;
28 .msb = 31, \ 28};
29 .id_size = _id_size, \
30 .id_offset = _id_offset, \
31 }
32
33/*
34 * basic function
35 */
36static int rsnd_regmap_write32(void *context, const void *_data, size_t count)
37{
38 struct rsnd_priv *priv = context;
39 struct device *dev = rsnd_priv_to_dev(priv);
40 u32 *data = (u32 *)_data;
41 u32 val = data[1];
42 void __iomem *reg = (void *)data[0];
43
44 iowrite32(val, reg);
45
46 dev_dbg(dev, "w %p : %08x\n", reg, val);
47
48 return 0;
49}
50
51static int rsnd_regmap_read32(void *context,
52 const void *_data, size_t reg_size,
53 void *_val, size_t val_size)
54{
55 struct rsnd_priv *priv = context;
56 struct device *dev = rsnd_priv_to_dev(priv);
57 u32 *data = (u32 *)_data;
58 u32 *val = (u32 *)_val;
59 void __iomem *reg = (void *)data[0];
60
61 *val = ioread32(reg);
62
63 dev_dbg(dev, "r %p : %08x\n", reg, *val);
64 29
65 return 0; 30#define RSND_REG_SET(id, offset, _id_offset) \
31{ \
32 .idx = id, \
33 .reg_offset = offset, \
34 .id_offset = _id_offset, \
66} 35}
36/* single address mapping */
37#define RSND_GEN_S_REG(id, offset) \
38 RSND_REG_SET(RSND_REG_##id, offset, 0)
67 39
68static struct regmap_bus rsnd_regmap_bus = { 40/* multi address mapping */
69 .write = rsnd_regmap_write32, 41#define RSND_GEN_M_REG(id, offset, _id_offset) \
70 .read = rsnd_regmap_read32, 42 RSND_REG_SET(RSND_REG_##id, offset, _id_offset)
71 .reg_format_endian_default = REGMAP_ENDIAN_NATIVE,
72 .val_format_endian_default = REGMAP_ENDIAN_NATIVE,
73};
74 43
44/*
45 * basic function
46 */
75static int rsnd_is_accessible_reg(struct rsnd_priv *priv, 47static int rsnd_is_accessible_reg(struct rsnd_priv *priv,
76 struct rsnd_gen *gen, enum rsnd_reg reg) 48 struct rsnd_gen *gen, enum rsnd_reg reg)
77{ 49{
@@ -88,6 +60,7 @@ static int rsnd_is_accessible_reg(struct rsnd_priv *priv,
88u32 rsnd_read(struct rsnd_priv *priv, 60u32 rsnd_read(struct rsnd_priv *priv,
89 struct rsnd_mod *mod, enum rsnd_reg reg) 61 struct rsnd_mod *mod, enum rsnd_reg reg)
90{ 62{
63 struct device *dev = rsnd_priv_to_dev(priv);
91 struct rsnd_gen *gen = rsnd_priv_to_gen(priv); 64 struct rsnd_gen *gen = rsnd_priv_to_gen(priv);
92 u32 val; 65 u32 val;
93 66
@@ -96,6 +69,8 @@ u32 rsnd_read(struct rsnd_priv *priv,
96 69
97 regmap_fields_read(gen->regs[reg], rsnd_mod_id(mod), &val); 70 regmap_fields_read(gen->regs[reg], rsnd_mod_id(mod), &val);
98 71
72 dev_dbg(dev, "r %s - 0x%04d : %08x\n", rsnd_mod_name(mod), reg, val);
73
99 return val; 74 return val;
100} 75}
101 76
@@ -103,17 +78,21 @@ void rsnd_write(struct rsnd_priv *priv,
103 struct rsnd_mod *mod, 78 struct rsnd_mod *mod,
104 enum rsnd_reg reg, u32 data) 79 enum rsnd_reg reg, u32 data)
105{ 80{
81 struct device *dev = rsnd_priv_to_dev(priv);
106 struct rsnd_gen *gen = rsnd_priv_to_gen(priv); 82 struct rsnd_gen *gen = rsnd_priv_to_gen(priv);
107 83
108 if (!rsnd_is_accessible_reg(priv, gen, reg)) 84 if (!rsnd_is_accessible_reg(priv, gen, reg))
109 return; 85 return;
110 86
111 regmap_fields_write(gen->regs[reg], rsnd_mod_id(mod), data); 87 regmap_fields_write(gen->regs[reg], rsnd_mod_id(mod), data);
88
89 dev_dbg(dev, "w %s - 0x%04d : %08x\n", rsnd_mod_name(mod), reg, data);
112} 90}
113 91
114void rsnd_bset(struct rsnd_priv *priv, struct rsnd_mod *mod, 92void rsnd_bset(struct rsnd_priv *priv, struct rsnd_mod *mod,
115 enum rsnd_reg reg, u32 mask, u32 data) 93 enum rsnd_reg reg, u32 mask, u32 data)
116{ 94{
95 struct device *dev = rsnd_priv_to_dev(priv);
117 struct rsnd_gen *gen = rsnd_priv_to_gen(priv); 96 struct rsnd_gen *gen = rsnd_priv_to_gen(priv);
118 97
119 if (!rsnd_is_accessible_reg(priv, gen, reg)) 98 if (!rsnd_is_accessible_reg(priv, gen, reg))
@@ -121,35 +100,63 @@ void rsnd_bset(struct rsnd_priv *priv, struct rsnd_mod *mod,
121 100
122 regmap_fields_update_bits(gen->regs[reg], rsnd_mod_id(mod), 101 regmap_fields_update_bits(gen->regs[reg], rsnd_mod_id(mod),
123 mask, data); 102 mask, data);
103
104 dev_dbg(dev, "b %s - 0x%04d : %08x/%08x\n",
105 rsnd_mod_name(mod), reg, data, mask);
124} 106}
125 107
126static int rsnd_gen_regmap_init(struct rsnd_priv *priv, 108#define rsnd_gen_regmap_init(priv, id_size, reg_id, conf) \
127 struct rsnd_gen *gen, 109 _rsnd_gen_regmap_init(priv, id_size, reg_id, conf, ARRAY_SIZE(conf))
128 struct reg_field *regf) 110static int _rsnd_gen_regmap_init(struct rsnd_priv *priv,
111 int id_size,
112 int reg_id,
113 struct rsnd_regmap_field_conf *conf,
114 int conf_size)
129{ 115{
130 int i; 116 struct platform_device *pdev = rsnd_priv_to_pdev(priv);
117 struct rsnd_gen *gen = rsnd_priv_to_gen(priv);
131 struct device *dev = rsnd_priv_to_dev(priv); 118 struct device *dev = rsnd_priv_to_dev(priv);
119 struct resource *res;
132 struct regmap_config regc; 120 struct regmap_config regc;
121 struct regmap_field *regs;
122 struct regmap *regmap;
123 struct reg_field regf;
124 void __iomem *base;
125 int i;
133 126
134 memset(&regc, 0, sizeof(regc)); 127 memset(&regc, 0, sizeof(regc));
135 regc.reg_bits = 32; 128 regc.reg_bits = 32;
136 regc.val_bits = 32; 129 regc.val_bits = 32;
130 regc.reg_stride = 4;
137 131
138 gen->regmap = devm_regmap_init(dev, &rsnd_regmap_bus, priv, &regc); 132 res = platform_get_resource(pdev, IORESOURCE_MEM, reg_id);
139 if (IS_ERR(gen->regmap)) { 133 if (!res)
140 dev_err(dev, "regmap error %ld\n", PTR_ERR(gen->regmap)); 134 return -ENODEV;
141 return PTR_ERR(gen->regmap); 135
142 } 136 base = devm_ioremap_resource(dev, res);
137 if (IS_ERR(base))
138 return PTR_ERR(base);
139
140 regmap = devm_regmap_init_mmio(dev, base, &regc);
141 if (IS_ERR(regmap))
142 return PTR_ERR(regmap);
143
144 gen->base[reg_id] = base;
145 gen->regmap[reg_id] = regmap;
143 146
144 for (i = 0; i < RSND_REG_MAX; i++) { 147 for (i = 0; i < conf_size; i++) {
145 gen->regs[i] = NULL;
146 if (!regf[i].reg)
147 continue;
148 148
149 gen->regs[i] = devm_regmap_field_alloc(dev, gen->regmap, regf[i]); 149 regf.reg = conf[i].reg_offset;
150 if (IS_ERR(gen->regs[i])) 150 regf.id_offset = conf[i].id_offset;
151 return PTR_ERR(gen->regs[i]); 151 regf.lsb = 0;
152 regf.msb = 31;
153 regf.id_size = id_size;
152 154
155 regs = devm_regmap_field_alloc(dev, regmap, regf);
156 if (IS_ERR(regs))
157 return PTR_ERR(regs);
158
159 gen->regs[conf[i].idx] = regs;
153 } 160 }
154 161
155 return 0; 162 return 0;
@@ -165,15 +172,19 @@ static int rsnd_gen_regmap_init(struct rsnd_priv *priv,
165 * 172 *
166 * ex) R-Car H2 case 173 * ex) R-Car H2 case
167 * mod / DMAC in / DMAC out / DMAC PP in / DMAC pp out 174 * mod / DMAC in / DMAC out / DMAC PP in / DMAC pp out
168 * SSI : 0xec541000 / 0xec241008 / 0xec24100c / 0xec400000 / 0xec400000 175 * SSI : 0xec541000 / 0xec241008 / 0xec24100c
176 * SSIU: 0xec541000 / 0xec100000 / 0xec100000 / 0xec400000 / 0xec400000
169 * SCU : 0xec500000 / 0xec000000 / 0xec004000 / 0xec300000 / 0xec304000 177 * SCU : 0xec500000 / 0xec000000 / 0xec004000 / 0xec300000 / 0xec304000
170 * CMD : 0xec500000 / 0xec008000 0xec308000 178 * CMD : 0xec500000 / / 0xec008000 0xec308000
171 */ 179 */
172#define RDMA_SSI_I_N(addr, i) (addr ##_reg - 0x00300000 + (0x40 * i) + 0x8) 180#define RDMA_SSI_I_N(addr, i) (addr ##_reg - 0x00300000 + (0x40 * i) + 0x8)
173#define RDMA_SSI_O_N(addr, i) (addr ##_reg - 0x00300000 + (0x40 * i) + 0xc) 181#define RDMA_SSI_O_N(addr, i) (addr ##_reg - 0x00300000 + (0x40 * i) + 0xc)
174 182
175#define RDMA_SSI_I_P(addr, i) (addr ##_reg - 0x00141000 + (0x1000 * i)) 183#define RDMA_SSIU_I_N(addr, i) (addr ##_reg - 0x00441000 + (0x1000 * i))
176#define RDMA_SSI_O_P(addr, i) (addr ##_reg - 0x00141000 + (0x1000 * i)) 184#define RDMA_SSIU_O_N(addr, i) (addr ##_reg - 0x00441000 + (0x1000 * i))
185
186#define RDMA_SSIU_I_P(addr, i) (addr ##_reg - 0x00141000 + (0x1000 * i))
187#define RDMA_SSIU_O_P(addr, i) (addr ##_reg - 0x00141000 + (0x1000 * i))
177 188
178#define RDMA_SRC_I_N(addr, i) (addr ##_reg - 0x00500000 + (0x400 * i)) 189#define RDMA_SRC_I_N(addr, i) (addr ##_reg - 0x00500000 + (0x400 * i))
179#define RDMA_SRC_O_N(addr, i) (addr ##_reg - 0x004fc000 + (0x400 * i)) 190#define RDMA_SRC_O_N(addr, i) (addr ##_reg - 0x004fc000 + (0x400 * i))
@@ -184,14 +195,13 @@ static int rsnd_gen_regmap_init(struct rsnd_priv *priv,
184#define RDMA_CMD_O_N(addr, i) (addr ##_reg - 0x004f8000 + (0x400 * i)) 195#define RDMA_CMD_O_N(addr, i) (addr ##_reg - 0x004f8000 + (0x400 * i))
185#define RDMA_CMD_O_P(addr, i) (addr ##_reg - 0x001f8000 + (0x400 * i)) 196#define RDMA_CMD_O_P(addr, i) (addr ##_reg - 0x001f8000 + (0x400 * i))
186 197
187static void rsnd_gen2_dma_addr(struct rsnd_priv *priv, 198static dma_addr_t
188 struct rsnd_dma *dma, 199rsnd_gen2_dma_addr(struct rsnd_priv *priv,
189 struct dma_slave_config *cfg, 200 struct rsnd_mod *mod,
190 int is_play, int slave_id) 201 int is_play, int is_from)
191{ 202{
192 struct platform_device *pdev = rsnd_priv_to_pdev(priv); 203 struct platform_device *pdev = rsnd_priv_to_pdev(priv);
193 struct device *dev = rsnd_priv_to_dev(priv); 204 struct device *dev = rsnd_priv_to_dev(priv);
194 struct rsnd_mod *mod = rsnd_dma_to_mod(dma);
195 struct rsnd_dai_stream *io = rsnd_mod_to_io(mod); 205 struct rsnd_dai_stream *io = rsnd_mod_to_io(mod);
196 dma_addr_t ssi_reg = platform_get_resource(pdev, 206 dma_addr_t ssi_reg = platform_get_resource(pdev,
197 IORESOURCE_MEM, RSND_GEN2_SSI)->start; 207 IORESOURCE_MEM, RSND_GEN2_SSI)->start;
@@ -202,179 +212,152 @@ static void rsnd_gen2_dma_addr(struct rsnd_priv *priv,
202 int use_dvc = !!rsnd_io_to_mod_dvc(io); 212 int use_dvc = !!rsnd_io_to_mod_dvc(io);
203 int id = rsnd_mod_id(mod); 213 int id = rsnd_mod_id(mod);
204 struct dma_addr { 214 struct dma_addr {
205 dma_addr_t src_addr; 215 dma_addr_t out_addr;
206 dma_addr_t dst_addr; 216 dma_addr_t in_addr;
207 } dma_addrs[2][2][3] = { 217 } dma_addrs[3][2][3] = {
208 { /* SRC */ 218 /* SRC */
209 /* Capture */ 219 {{{ 0, 0 },
210 {{ 0, 0 }, 220 /* Capture */
211 { RDMA_SRC_O_N(src, id), 0 }, 221 { RDMA_SRC_O_N(src, id), RDMA_SRC_I_P(src, id) },
212 { RDMA_CMD_O_N(src, id), 0 }}, 222 { RDMA_CMD_O_N(src, id), RDMA_SRC_I_P(src, id) } },
213 /* Playback */ 223 /* Playback */
214 {{ 0, 0, }, 224 {{ 0, 0, },
215 { 0, RDMA_SRC_I_N(src, id) }, 225 { RDMA_SRC_O_P(src, id), RDMA_SRC_I_N(src, id) },
216 { 0, RDMA_SRC_I_N(src, id) }} 226 { RDMA_CMD_O_P(src, id), RDMA_SRC_I_N(src, id) } }
217 }, { /* SSI */ 227 },
218 /* Capture */ 228 /* SSI */
219 {{ RDMA_SSI_O_N(ssi, id), 0 }, 229 /* Capture */
220 { RDMA_SSI_O_P(ssi, id), RDMA_SRC_I_P(src, id) }, 230 {{{ RDMA_SSI_O_N(ssi, id), 0 },
221 { RDMA_SSI_O_P(ssi, id), RDMA_SRC_I_P(src, id) }}, 231 { RDMA_SSIU_O_P(ssi, id), 0 },
222 /* Playback */ 232 { RDMA_SSIU_O_P(ssi, id), 0 } },
223 {{ 0, RDMA_SSI_I_N(ssi, id) }, 233 /* Playback */
224 { RDMA_SRC_O_P(src, id), RDMA_SSI_I_P(ssi, id) }, 234 {{ 0, RDMA_SSI_I_N(ssi, id) },
225 { RDMA_CMD_O_P(src, id), RDMA_SSI_I_P(ssi, id) }} 235 { 0, RDMA_SSIU_I_P(ssi, id) },
226 } 236 { 0, RDMA_SSIU_I_P(ssi, id) } }
237 },
238 /* SSIU */
239 /* Capture */
240 {{{ RDMA_SSIU_O_N(ssi, id), 0 },
241 { RDMA_SSIU_O_P(ssi, id), 0 },
242 { RDMA_SSIU_O_P(ssi, id), 0 } },
243 /* Playback */
244 {{ 0, RDMA_SSIU_I_N(ssi, id) },
245 { 0, RDMA_SSIU_I_P(ssi, id) },
246 { 0, RDMA_SSIU_I_P(ssi, id) } } },
227 }; 247 };
228 248
229 /* it shouldn't happen */ 249 /* it shouldn't happen */
230 if (use_dvc & !use_src) { 250 if (use_dvc & !use_src)
231 dev_err(dev, "DVC is selected without SRC\n"); 251 dev_err(dev, "DVC is selected without SRC\n");
232 return;
233 }
234 252
235 cfg->src_addr = dma_addrs[is_ssi][is_play][use_src + use_dvc].src_addr; 253 /* use SSIU or SSI ? */
236 cfg->dst_addr = dma_addrs[is_ssi][is_play][use_src + use_dvc].dst_addr; 254 if (is_ssi && (0 == strcmp(rsnd_mod_dma_name(mod), "ssiu")))
255 is_ssi++;
237 256
238 dev_dbg(dev, "dma%d addr - src : %x / dst : %x\n", 257 return (is_from) ?
239 id, cfg->src_addr, cfg->dst_addr); 258 dma_addrs[is_ssi][is_play][use_src + use_dvc].out_addr :
259 dma_addrs[is_ssi][is_play][use_src + use_dvc].in_addr;
240} 260}
241 261
242void rsnd_gen_dma_addr(struct rsnd_priv *priv, 262dma_addr_t rsnd_gen_dma_addr(struct rsnd_priv *priv,
243 struct rsnd_dma *dma, 263 struct rsnd_mod *mod,
244 struct dma_slave_config *cfg, 264 int is_play, int is_from)
245 int is_play, int slave_id)
246{ 265{
247 cfg->slave_id = slave_id;
248 cfg->src_addr = 0;
249 cfg->dst_addr = 0;
250 cfg->direction = is_play ? DMA_MEM_TO_DEV : DMA_DEV_TO_MEM;
251
252 /* 266 /*
253 * gen1 uses default DMA addr 267 * gen1 uses default DMA addr
254 */ 268 */
255 if (rsnd_is_gen1(priv)) 269 if (rsnd_is_gen1(priv))
256 return; 270 return 0;
257 271
258 rsnd_gen2_dma_addr(priv, dma, cfg, is_play, slave_id); 272 if (!mod)
259} 273 return 0;
260 274
275 return rsnd_gen2_dma_addr(priv, mod, is_play, is_from);
276}
261 277
262/* 278/*
263 * Gen2 279 * Gen2
264 */ 280 */
265
266/* single address mapping */
267#define RSND_GEN2_S_REG(gen, reg, id, offset) \
268 RSND_REG_SET(gen, RSND_REG_##id, RSND_GEN2_##reg, offset, 0, 10)
269
270/* multi address mapping */
271#define RSND_GEN2_M_REG(gen, reg, id, offset, _id_offset) \
272 RSND_REG_SET(gen, RSND_REG_##id, RSND_GEN2_##reg, offset, _id_offset, 10)
273
274static int rsnd_gen2_regmap_init(struct rsnd_priv *priv, struct rsnd_gen *gen)
275{
276 struct reg_field regf[RSND_REG_MAX] = {
277 RSND_GEN2_S_REG(gen, SSIU, SSI_MODE0, 0x800),
278 RSND_GEN2_S_REG(gen, SSIU, SSI_MODE1, 0x804),
279 /* FIXME: it needs SSI_MODE2/3 in the future */
280 RSND_GEN2_M_REG(gen, SSIU, SSI_BUSIF_MODE, 0x0, 0x80),
281 RSND_GEN2_M_REG(gen, SSIU, SSI_BUSIF_ADINR,0x4, 0x80),
282 RSND_GEN2_M_REG(gen, SSIU, SSI_CTRL, 0x10, 0x80),
283 RSND_GEN2_M_REG(gen, SSIU, INT_ENABLE, 0x18, 0x80),
284
285 RSND_GEN2_M_REG(gen, SCU, SRC_BUSIF_MODE, 0x0, 0x20),
286 RSND_GEN2_M_REG(gen, SCU, SRC_ROUTE_MODE0,0xc, 0x20),
287 RSND_GEN2_M_REG(gen, SCU, SRC_CTRL, 0x10, 0x20),
288 RSND_GEN2_M_REG(gen, SCU, CMD_ROUTE_SLCT, 0x18c, 0x20),
289 RSND_GEN2_M_REG(gen, SCU, CMD_CTRL, 0x190, 0x20),
290 RSND_GEN2_M_REG(gen, SCU, SRC_SWRSR, 0x200, 0x40),
291 RSND_GEN2_M_REG(gen, SCU, SRC_SRCIR, 0x204, 0x40),
292 RSND_GEN2_M_REG(gen, SCU, SRC_ADINR, 0x214, 0x40),
293 RSND_GEN2_M_REG(gen, SCU, SRC_IFSCR, 0x21c, 0x40),
294 RSND_GEN2_M_REG(gen, SCU, SRC_IFSVR, 0x220, 0x40),
295 RSND_GEN2_M_REG(gen, SCU, SRC_SRCCR, 0x224, 0x40),
296 RSND_GEN2_M_REG(gen, SCU, SRC_BSDSR, 0x22c, 0x40),
297 RSND_GEN2_M_REG(gen, SCU, SRC_BSISR, 0x238, 0x40),
298 RSND_GEN2_M_REG(gen, SCU, DVC_SWRSR, 0xe00, 0x100),
299 RSND_GEN2_M_REG(gen, SCU, DVC_DVUIR, 0xe04, 0x100),
300 RSND_GEN2_M_REG(gen, SCU, DVC_ADINR, 0xe08, 0x100),
301 RSND_GEN2_M_REG(gen, SCU, DVC_DVUCR, 0xe10, 0x100),
302 RSND_GEN2_M_REG(gen, SCU, DVC_ZCMCR, 0xe14, 0x100),
303 RSND_GEN2_M_REG(gen, SCU, DVC_VOL0R, 0xe28, 0x100),
304 RSND_GEN2_M_REG(gen, SCU, DVC_VOL1R, 0xe2c, 0x100),
305 RSND_GEN2_M_REG(gen, SCU, DVC_DVUER, 0xe48, 0x100),
306
307 RSND_GEN2_S_REG(gen, ADG, BRRA, 0x00),
308 RSND_GEN2_S_REG(gen, ADG, BRRB, 0x04),
309 RSND_GEN2_S_REG(gen, ADG, SSICKR, 0x08),
310 RSND_GEN2_S_REG(gen, ADG, AUDIO_CLK_SEL0, 0x0c),
311 RSND_GEN2_S_REG(gen, ADG, AUDIO_CLK_SEL1, 0x10),
312 RSND_GEN2_S_REG(gen, ADG, AUDIO_CLK_SEL2, 0x14),
313 RSND_GEN2_S_REG(gen, ADG, DIV_EN, 0x30),
314 RSND_GEN2_S_REG(gen, ADG, SRCIN_TIMSEL0, 0x34),
315 RSND_GEN2_S_REG(gen, ADG, SRCIN_TIMSEL1, 0x38),
316 RSND_GEN2_S_REG(gen, ADG, SRCIN_TIMSEL2, 0x3c),
317 RSND_GEN2_S_REG(gen, ADG, SRCIN_TIMSEL3, 0x40),
318 RSND_GEN2_S_REG(gen, ADG, SRCIN_TIMSEL4, 0x44),
319 RSND_GEN2_S_REG(gen, ADG, SRCOUT_TIMSEL0, 0x48),
320 RSND_GEN2_S_REG(gen, ADG, SRCOUT_TIMSEL1, 0x4c),
321 RSND_GEN2_S_REG(gen, ADG, SRCOUT_TIMSEL2, 0x50),
322 RSND_GEN2_S_REG(gen, ADG, SRCOUT_TIMSEL3, 0x54),
323 RSND_GEN2_S_REG(gen, ADG, SRCOUT_TIMSEL4, 0x58),
324 RSND_GEN2_S_REG(gen, ADG, CMDOUT_TIMSEL, 0x5c),
325
326 RSND_GEN2_M_REG(gen, SSI, SSICR, 0x00, 0x40),
327 RSND_GEN2_M_REG(gen, SSI, SSISR, 0x04, 0x40),
328 RSND_GEN2_M_REG(gen, SSI, SSITDR, 0x08, 0x40),
329 RSND_GEN2_M_REG(gen, SSI, SSIRDR, 0x0c, 0x40),
330 RSND_GEN2_M_REG(gen, SSI, SSIWSR, 0x20, 0x40),
331 };
332
333 return rsnd_gen_regmap_init(priv, gen, regf);
334}
335
336static int rsnd_gen2_probe(struct platform_device *pdev, 281static int rsnd_gen2_probe(struct platform_device *pdev,
337 struct rsnd_priv *priv) 282 struct rsnd_priv *priv)
338{ 283{
339 struct device *dev = rsnd_priv_to_dev(priv); 284 struct device *dev = rsnd_priv_to_dev(priv);
340 struct rsnd_gen *gen = rsnd_priv_to_gen(priv); 285 struct rsnd_regmap_field_conf conf_ssiu[] = {
341 struct resource *scu_res; 286 RSND_GEN_S_REG(SSI_MODE0, 0x800),
342 struct resource *adg_res; 287 RSND_GEN_S_REG(SSI_MODE1, 0x804),
343 struct resource *ssiu_res; 288 /* FIXME: it needs SSI_MODE2/3 in the future */
344 struct resource *ssi_res; 289 RSND_GEN_M_REG(SSI_BUSIF_MODE, 0x0, 0x80),
345 int ret; 290 RSND_GEN_M_REG(SSI_BUSIF_ADINR, 0x4, 0x80),
346 291 RSND_GEN_M_REG(BUSIF_DALIGN, 0x8, 0x80),
347 /* 292 RSND_GEN_M_REG(SSI_CTRL, 0x10, 0x80),
348 * map address 293 RSND_GEN_M_REG(INT_ENABLE, 0x18, 0x80),
349 */ 294 };
350 scu_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN2_SCU); 295 struct rsnd_regmap_field_conf conf_scu[] = {
351 adg_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN2_ADG); 296 RSND_GEN_M_REG(SRC_BUSIF_MODE, 0x0, 0x20),
352 ssiu_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN2_SSIU); 297 RSND_GEN_M_REG(SRC_ROUTE_MODE0, 0xc, 0x20),
353 ssi_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN2_SSI); 298 RSND_GEN_M_REG(SRC_CTRL, 0x10, 0x20),
354 299 RSND_GEN_M_REG(CMD_ROUTE_SLCT, 0x18c, 0x20),
355 gen->base[RSND_GEN2_SCU] = devm_ioremap_resource(dev, scu_res); 300 RSND_GEN_M_REG(CMD_CTRL, 0x190, 0x20),
356 gen->base[RSND_GEN2_ADG] = devm_ioremap_resource(dev, adg_res); 301 RSND_GEN_M_REG(SRC_SWRSR, 0x200, 0x40),
357 gen->base[RSND_GEN2_SSIU] = devm_ioremap_resource(dev, ssiu_res); 302 RSND_GEN_M_REG(SRC_SRCIR, 0x204, 0x40),
358 gen->base[RSND_GEN2_SSI] = devm_ioremap_resource(dev, ssi_res); 303 RSND_GEN_M_REG(SRC_ADINR, 0x214, 0x40),
359 if (IS_ERR(gen->base[RSND_GEN2_SCU]) || 304 RSND_GEN_M_REG(SRC_IFSCR, 0x21c, 0x40),
360 IS_ERR(gen->base[RSND_GEN2_ADG]) || 305 RSND_GEN_M_REG(SRC_IFSVR, 0x220, 0x40),
361 IS_ERR(gen->base[RSND_GEN2_SSIU]) || 306 RSND_GEN_M_REG(SRC_SRCCR, 0x224, 0x40),
362 IS_ERR(gen->base[RSND_GEN2_SSI])) 307 RSND_GEN_M_REG(SRC_BSDSR, 0x22c, 0x40),
363 return -ENODEV; 308 RSND_GEN_M_REG(SRC_BSISR, 0x238, 0x40),
364 309 RSND_GEN_M_REG(DVC_SWRSR, 0xe00, 0x100),
365 ret = rsnd_gen2_regmap_init(priv, gen); 310 RSND_GEN_M_REG(DVC_DVUIR, 0xe04, 0x100),
366 if (ret < 0) 311 RSND_GEN_M_REG(DVC_ADINR, 0xe08, 0x100),
367 return ret; 312 RSND_GEN_M_REG(DVC_DVUCR, 0xe10, 0x100),
368 313 RSND_GEN_M_REG(DVC_ZCMCR, 0xe14, 0x100),
369 dev_dbg(dev, "Gen2 device probed\n"); 314 RSND_GEN_M_REG(DVC_VOL0R, 0xe28, 0x100),
370 dev_dbg(dev, "SCU : %pap => %p\n", &scu_res->start, 315 RSND_GEN_M_REG(DVC_VOL1R, 0xe2c, 0x100),
371 gen->base[RSND_GEN2_SCU]); 316 RSND_GEN_M_REG(DVC_DVUER, 0xe48, 0x100),
372 dev_dbg(dev, "ADG : %pap => %p\n", &adg_res->start, 317 };
373 gen->base[RSND_GEN2_ADG]); 318 struct rsnd_regmap_field_conf conf_adg[] = {
374 dev_dbg(dev, "SSIU : %pap => %p\n", &ssiu_res->start, 319 RSND_GEN_S_REG(BRRA, 0x00),
375 gen->base[RSND_GEN2_SSIU]); 320 RSND_GEN_S_REG(BRRB, 0x04),
376 dev_dbg(dev, "SSI : %pap => %p\n", &ssi_res->start, 321 RSND_GEN_S_REG(SSICKR, 0x08),
377 gen->base[RSND_GEN2_SSI]); 322 RSND_GEN_S_REG(AUDIO_CLK_SEL0, 0x0c),
323 RSND_GEN_S_REG(AUDIO_CLK_SEL1, 0x10),
324 RSND_GEN_S_REG(AUDIO_CLK_SEL2, 0x14),
325 RSND_GEN_S_REG(DIV_EN, 0x30),
326 RSND_GEN_S_REG(SRCIN_TIMSEL0, 0x34),
327 RSND_GEN_S_REG(SRCIN_TIMSEL1, 0x38),
328 RSND_GEN_S_REG(SRCIN_TIMSEL2, 0x3c),
329 RSND_GEN_S_REG(SRCIN_TIMSEL3, 0x40),
330 RSND_GEN_S_REG(SRCIN_TIMSEL4, 0x44),
331 RSND_GEN_S_REG(SRCOUT_TIMSEL0, 0x48),
332 RSND_GEN_S_REG(SRCOUT_TIMSEL1, 0x4c),
333 RSND_GEN_S_REG(SRCOUT_TIMSEL2, 0x50),
334 RSND_GEN_S_REG(SRCOUT_TIMSEL3, 0x54),
335 RSND_GEN_S_REG(SRCOUT_TIMSEL4, 0x58),
336 RSND_GEN_S_REG(CMDOUT_TIMSEL, 0x5c),
337 };
338 struct rsnd_regmap_field_conf conf_ssi[] = {
339 RSND_GEN_M_REG(SSICR, 0x00, 0x40),
340 RSND_GEN_M_REG(SSISR, 0x04, 0x40),
341 RSND_GEN_M_REG(SSITDR, 0x08, 0x40),
342 RSND_GEN_M_REG(SSIRDR, 0x0c, 0x40),
343 RSND_GEN_M_REG(SSIWSR, 0x20, 0x40),
344 };
345 int ret_ssiu;
346 int ret_scu;
347 int ret_adg;
348 int ret_ssi;
349
350 ret_ssiu = rsnd_gen_regmap_init(priv, 10, RSND_GEN2_SSIU, conf_ssiu);
351 ret_scu = rsnd_gen_regmap_init(priv, 10, RSND_GEN2_SCU, conf_scu);
352 ret_adg = rsnd_gen_regmap_init(priv, 10, RSND_GEN2_ADG, conf_adg);
353 ret_ssi = rsnd_gen_regmap_init(priv, 10, RSND_GEN2_SSI, conf_ssi);
354 if (ret_ssiu < 0 ||
355 ret_scu < 0 ||
356 ret_adg < 0 ||
357 ret_ssi < 0)
358 return ret_ssiu | ret_scu | ret_adg | ret_ssi;
359
360 dev_dbg(dev, "Gen2 is probed\n");
378 361
379 return 0; 362 return 0;
380} 363}
@@ -383,92 +366,60 @@ static int rsnd_gen2_probe(struct platform_device *pdev,
383 * Gen1 366 * Gen1
384 */ 367 */
385 368
386/* single address mapping */
387#define RSND_GEN1_S_REG(gen, reg, id, offset) \
388 RSND_REG_SET(gen, RSND_REG_##id, RSND_GEN1_##reg, offset, 0, 9)
389
390/* multi address mapping */
391#define RSND_GEN1_M_REG(gen, reg, id, offset, _id_offset) \
392 RSND_REG_SET(gen, RSND_REG_##id, RSND_GEN1_##reg, offset, _id_offset, 9)
393
394static int rsnd_gen1_regmap_init(struct rsnd_priv *priv, struct rsnd_gen *gen)
395{
396 struct reg_field regf[RSND_REG_MAX] = {
397 RSND_GEN1_S_REG(gen, SRU, SRC_ROUTE_SEL, 0x00),
398 RSND_GEN1_S_REG(gen, SRU, SRC_TMG_SEL0, 0x08),
399 RSND_GEN1_S_REG(gen, SRU, SRC_TMG_SEL1, 0x0c),
400 RSND_GEN1_S_REG(gen, SRU, SRC_TMG_SEL2, 0x10),
401 RSND_GEN1_S_REG(gen, SRU, SRC_ROUTE_CTRL, 0xc0),
402 RSND_GEN1_S_REG(gen, SRU, SSI_MODE0, 0xD0),
403 RSND_GEN1_S_REG(gen, SRU, SSI_MODE1, 0xD4),
404 RSND_GEN1_M_REG(gen, SRU, SRC_BUSIF_MODE, 0x20, 0x4),
405 RSND_GEN1_M_REG(gen, SRU, SRC_ROUTE_MODE0,0x50, 0x8),
406 RSND_GEN1_M_REG(gen, SRU, SRC_SWRSR, 0x200, 0x40),
407 RSND_GEN1_M_REG(gen, SRU, SRC_SRCIR, 0x204, 0x40),
408 RSND_GEN1_M_REG(gen, SRU, SRC_ADINR, 0x214, 0x40),
409 RSND_GEN1_M_REG(gen, SRU, SRC_IFSCR, 0x21c, 0x40),
410 RSND_GEN1_M_REG(gen, SRU, SRC_IFSVR, 0x220, 0x40),
411 RSND_GEN1_M_REG(gen, SRU, SRC_SRCCR, 0x224, 0x40),
412 RSND_GEN1_M_REG(gen, SRU, SRC_MNFSR, 0x228, 0x40),
413
414 RSND_GEN1_S_REG(gen, ADG, BRRA, 0x00),
415 RSND_GEN1_S_REG(gen, ADG, BRRB, 0x04),
416 RSND_GEN1_S_REG(gen, ADG, SSICKR, 0x08),
417 RSND_GEN1_S_REG(gen, ADG, AUDIO_CLK_SEL0, 0x0c),
418 RSND_GEN1_S_REG(gen, ADG, AUDIO_CLK_SEL1, 0x10),
419 RSND_GEN1_S_REG(gen, ADG, AUDIO_CLK_SEL3, 0x18),
420 RSND_GEN1_S_REG(gen, ADG, AUDIO_CLK_SEL4, 0x1c),
421 RSND_GEN1_S_REG(gen, ADG, AUDIO_CLK_SEL5, 0x20),
422
423 RSND_GEN1_M_REG(gen, SSI, SSICR, 0x00, 0x40),
424 RSND_GEN1_M_REG(gen, SSI, SSISR, 0x04, 0x40),
425 RSND_GEN1_M_REG(gen, SSI, SSITDR, 0x08, 0x40),
426 RSND_GEN1_M_REG(gen, SSI, SSIRDR, 0x0c, 0x40),
427 RSND_GEN1_M_REG(gen, SSI, SSIWSR, 0x20, 0x40),
428 };
429
430 return rsnd_gen_regmap_init(priv, gen, regf);
431}
432
433static int rsnd_gen1_probe(struct platform_device *pdev, 369static int rsnd_gen1_probe(struct platform_device *pdev,
434 struct rsnd_priv *priv) 370 struct rsnd_priv *priv)
435{ 371{
436 struct device *dev = rsnd_priv_to_dev(priv); 372 struct device *dev = rsnd_priv_to_dev(priv);
437 struct rsnd_gen *gen = rsnd_priv_to_gen(priv); 373 struct rsnd_regmap_field_conf conf_sru[] = {
438 struct resource *sru_res; 374 RSND_GEN_S_REG(SRC_ROUTE_SEL, 0x00),
439 struct resource *adg_res; 375 RSND_GEN_S_REG(SRC_TMG_SEL0, 0x08),
440 struct resource *ssi_res; 376 RSND_GEN_S_REG(SRC_TMG_SEL1, 0x0c),
441 int ret; 377 RSND_GEN_S_REG(SRC_TMG_SEL2, 0x10),
442 378 RSND_GEN_S_REG(SRC_ROUTE_CTRL, 0xc0),
443 /* 379 RSND_GEN_S_REG(SSI_MODE0, 0xD0),
444 * map address 380 RSND_GEN_S_REG(SSI_MODE1, 0xD4),
445 */ 381 RSND_GEN_M_REG(SRC_BUSIF_MODE, 0x20, 0x4),
446 sru_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN1_SRU); 382 RSND_GEN_M_REG(SRC_ROUTE_MODE0, 0x50, 0x8),
447 adg_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN1_ADG); 383 RSND_GEN_M_REG(SRC_SWRSR, 0x200, 0x40),
448 ssi_res = platform_get_resource(pdev, IORESOURCE_MEM, RSND_GEN1_SSI); 384 RSND_GEN_M_REG(SRC_SRCIR, 0x204, 0x40),
449 385 RSND_GEN_M_REG(SRC_ADINR, 0x214, 0x40),
450 gen->base[RSND_GEN1_SRU] = devm_ioremap_resource(dev, sru_res); 386 RSND_GEN_M_REG(SRC_IFSCR, 0x21c, 0x40),
451 gen->base[RSND_GEN1_ADG] = devm_ioremap_resource(dev, adg_res); 387 RSND_GEN_M_REG(SRC_IFSVR, 0x220, 0x40),
452 gen->base[RSND_GEN1_SSI] = devm_ioremap_resource(dev, ssi_res); 388 RSND_GEN_M_REG(SRC_SRCCR, 0x224, 0x40),
453 if (IS_ERR(gen->base[RSND_GEN1_SRU]) || 389 RSND_GEN_M_REG(SRC_MNFSR, 0x228, 0x40),
454 IS_ERR(gen->base[RSND_GEN1_ADG]) || 390 };
455 IS_ERR(gen->base[RSND_GEN1_SSI])) 391 struct rsnd_regmap_field_conf conf_adg[] = {
456 return -ENODEV; 392 RSND_GEN_S_REG(BRRA, 0x00),
393 RSND_GEN_S_REG(BRRB, 0x04),
394 RSND_GEN_S_REG(SSICKR, 0x08),
395 RSND_GEN_S_REG(AUDIO_CLK_SEL0, 0x0c),
396 RSND_GEN_S_REG(AUDIO_CLK_SEL1, 0x10),
397 RSND_GEN_S_REG(AUDIO_CLK_SEL3, 0x18),
398 RSND_GEN_S_REG(AUDIO_CLK_SEL4, 0x1c),
399 RSND_GEN_S_REG(AUDIO_CLK_SEL5, 0x20),
400 };
401 struct rsnd_regmap_field_conf conf_ssi[] = {
402 RSND_GEN_M_REG(SSICR, 0x00, 0x40),
403 RSND_GEN_M_REG(SSISR, 0x04, 0x40),
404 RSND_GEN_M_REG(SSITDR, 0x08, 0x40),
405 RSND_GEN_M_REG(SSIRDR, 0x0c, 0x40),
406 RSND_GEN_M_REG(SSIWSR, 0x20, 0x40),
407 };
408 int ret_sru;
409 int ret_adg;
410 int ret_ssi;
457 411
458 ret = rsnd_gen1_regmap_init(priv, gen); 412 ret_sru = rsnd_gen_regmap_init(priv, 9, RSND_GEN1_SRU, conf_sru);
459 if (ret < 0) 413 ret_adg = rsnd_gen_regmap_init(priv, 9, RSND_GEN1_ADG, conf_adg);
460 return ret; 414 ret_ssi = rsnd_gen_regmap_init(priv, 9, RSND_GEN1_SSI, conf_ssi);
415 if (ret_sru < 0 ||
416 ret_adg < 0 ||
417 ret_ssi < 0)
418 return ret_sru | ret_adg | ret_ssi;
461 419
462 dev_dbg(dev, "Gen1 device probed\n"); 420 dev_dbg(dev, "Gen1 is probed\n");
463 dev_dbg(dev, "SRU : %pap => %p\n", &sru_res->start,
464 gen->base[RSND_GEN1_SRU]);
465 dev_dbg(dev, "ADG : %pap => %p\n", &adg_res->start,
466 gen->base[RSND_GEN1_ADG]);
467 dev_dbg(dev, "SSI : %pap => %p\n", &ssi_res->start,
468 gen->base[RSND_GEN1_SSI]);
469 421
470 return 0; 422 return 0;
471
472} 423}
473 424
474/* 425/*