blob: 821791e15d046f756e8d650186c38e32dbabe71f [file] [log] [blame]
Kuninori Morimotodfc94032013-07-21 21:36:46 -07001/*
2 * Helper routines for R-Car sound ADG.
3 *
4 * Copyright (C) 2013 Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
5 *
6 * This file is subject to the terms and conditions of the GNU General Public
7 * License. See the file "COPYING" in the main directory of this archive
8 * for more details.
9 */
10#include <linux/sh_clk.h>
Kuninori Morimotodfc94032013-07-21 21:36:46 -070011#include "rsnd.h"
12
13#define CLKA 0
14#define CLKB 1
15#define CLKC 2
16#define CLKI 3
17#define CLKMAX 4
18
19struct rsnd_adg {
20 struct clk *clk[CLKMAX];
21
Kuninori Morimoto7808aa32013-12-19 19:27:19 -080022 int rbga_rate_for_441khz_div_6; /* RBGA */
23 int rbgb_rate_for_48khz_div_6; /* RBGB */
Kuninori Morimotoefeb9702013-09-23 23:12:17 -070024 u32 ckr;
Kuninori Morimotodfc94032013-07-21 21:36:46 -070025};
26
27#define for_each_rsnd_clk(pos, adg, i) \
28 for (i = 0, (pos) = adg->clk[i]; \
29 i < CLKMAX; \
30 i++, (pos) = adg->clk[i])
31#define rsnd_priv_to_adg(priv) ((struct rsnd_adg *)(priv)->adg)
32
Kuninori Morimoto629509c2014-01-23 18:42:00 -080033
34static u32 rsnd_adg_ssi_ws_timing_gen2(struct rsnd_mod *mod)
35{
36 struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
37 int id = rsnd_mod_id(mod);
38 int ws = id;
39
40 if (rsnd_ssi_is_pin_sharing(rsnd_ssi_mod_get(priv, id))) {
41 switch (id) {
42 case 1:
43 case 2:
44 ws = 0;
45 break;
46 case 4:
47 ws = 3;
48 break;
49 case 8:
50 ws = 7;
51 break;
52 }
53 }
54
55 return (0x6 + ws) << 8;
56}
57
58static int rsnd_adg_set_src_timsel_gen2(struct rsnd_dai *rdai,
59 struct rsnd_mod *mod,
60 struct rsnd_dai_stream *io,
61 u32 timsel)
62{
63 int is_play = rsnd_dai_is_play(rdai, io);
64 int id = rsnd_mod_id(mod);
65 int shift = (id % 2) ? 16 : 0;
66 u32 mask, ws;
67 u32 in, out;
68
69 ws = rsnd_adg_ssi_ws_timing_gen2(mod);
70
71 in = (is_play) ? timsel : ws;
72 out = (is_play) ? ws : timsel;
73
74 in = in << shift;
75 out = out << shift;
76 mask = 0xffff << shift;
77
78 switch (id / 2) {
79 case 0:
80 rsnd_mod_bset(mod, SRCIN_TIMSEL0, mask, in);
81 rsnd_mod_bset(mod, SRCOUT_TIMSEL0, mask, out);
82 break;
83 case 1:
84 rsnd_mod_bset(mod, SRCIN_TIMSEL1, mask, in);
85 rsnd_mod_bset(mod, SRCOUT_TIMSEL1, mask, out);
86 break;
87 case 2:
88 rsnd_mod_bset(mod, SRCIN_TIMSEL2, mask, in);
89 rsnd_mod_bset(mod, SRCOUT_TIMSEL2, mask, out);
90 break;
91 case 3:
92 rsnd_mod_bset(mod, SRCIN_TIMSEL3, mask, in);
93 rsnd_mod_bset(mod, SRCOUT_TIMSEL3, mask, out);
94 break;
95 case 4:
96 rsnd_mod_bset(mod, SRCIN_TIMSEL4, mask, in);
97 rsnd_mod_bset(mod, SRCOUT_TIMSEL4, mask, out);
98 break;
99 }
100
101 return 0;
102}
103
104int rsnd_adg_set_convert_clk_gen2(struct rsnd_mod *mod,
105 struct rsnd_dai *rdai,
106 struct rsnd_dai_stream *io,
107 unsigned int src_rate,
108 unsigned int dst_rate)
109{
110 struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
111 struct rsnd_adg *adg = rsnd_priv_to_adg(priv);
112 struct device *dev = rsnd_priv_to_dev(priv);
113 int idx, sel, div, step;
114 u32 val;
115 unsigned int min, diff;
116 unsigned int sel_rate [] = {
117 clk_get_rate(adg->clk[CLKA]), /* 0000: CLKA */
118 clk_get_rate(adg->clk[CLKB]), /* 0001: CLKB */
119 clk_get_rate(adg->clk[CLKC]), /* 0010: CLKC */
120 adg->rbga_rate_for_441khz_div_6,/* 0011: RBGA */
121 adg->rbgb_rate_for_48khz_div_6, /* 0100: RBGB */
122 };
123
124 min = ~0;
125 val = 0;
126 for (sel = 0; sel < ARRAY_SIZE(sel_rate); sel++) {
127 idx = 0;
128 step = 2;
129
130 if (!sel_rate[sel])
131 continue;
132
133 for (div = 2; div <= 98304; div += step) {
134 diff = abs(src_rate - sel_rate[sel] / div);
135 if (min > diff) {
136 val = (sel << 8) | idx;
137 min = diff;
138 }
139
140 /*
141 * step of 0_0000 / 0_0001 / 0_1101
142 * are out of order
143 */
144 if ((idx > 2) && (idx % 2))
145 step *= 2;
146 if (idx == 0x1c) {
147 div += step;
148 step *= 2;
149 }
150 idx++;
151 }
152 }
153
154 if (min == ~0) {
155 dev_err(dev, "no Input clock\n");
156 return -EIO;
157 }
158
159 return rsnd_adg_set_src_timsel_gen2(rdai, mod, io, val);
160}
161
162int rsnd_adg_set_convert_timing_gen2(struct rsnd_mod *mod,
163 struct rsnd_dai *rdai,
164 struct rsnd_dai_stream *io)
165{
166 u32 val = rsnd_adg_ssi_ws_timing_gen2(mod);
167
168 return rsnd_adg_set_src_timsel_gen2(rdai, mod, io, val);
169}
170
Kuninori Morimoto28dc4b62014-01-23 18:41:10 -0800171int rsnd_adg_set_convert_clk_gen1(struct rsnd_priv *priv,
172 struct rsnd_mod *mod,
173 unsigned int src_rate,
174 unsigned int dst_rate)
Kuninori Morimotoef749402013-12-19 19:28:51 -0800175{
176 struct rsnd_adg *adg = rsnd_priv_to_adg(priv);
177 struct device *dev = rsnd_priv_to_dev(priv);
178 int idx, sel, div, shift;
179 u32 mask, val;
180 int id = rsnd_mod_id(mod);
181 unsigned int sel_rate [] = {
182 clk_get_rate(adg->clk[CLKA]), /* 000: CLKA */
183 clk_get_rate(adg->clk[CLKB]), /* 001: CLKB */
184 clk_get_rate(adg->clk[CLKC]), /* 010: CLKC */
185 0, /* 011: MLBCLK (not used) */
186 adg->rbga_rate_for_441khz_div_6,/* 100: RBGA */
187 adg->rbgb_rate_for_48khz_div_6, /* 101: RBGB */
188 };
189
190 /* find div (= 1/128, 1/256, 1/512, 1/1024, 1/2048 */
191 for (sel = 0; sel < ARRAY_SIZE(sel_rate); sel++) {
192 for (div = 128, idx = 0;
193 div <= 2048;
194 div *= 2, idx++) {
195 if (src_rate == sel_rate[sel] / div) {
196 val = (idx << 4) | sel;
197 goto find_rate;
198 }
199 }
200 }
201 dev_err(dev, "can't find convert src clk\n");
202 return -EINVAL;
203
204find_rate:
205 shift = (id % 4) * 8;
206 mask = 0xFF << shift;
207 val = val << shift;
208
209 dev_dbg(dev, "adg convert src clk = %02x\n", val);
210
211 switch (id / 4) {
212 case 0:
213 rsnd_mod_bset(mod, AUDIO_CLK_SEL3, mask, val);
214 break;
215 case 1:
216 rsnd_mod_bset(mod, AUDIO_CLK_SEL4, mask, val);
217 break;
218 case 2:
219 rsnd_mod_bset(mod, AUDIO_CLK_SEL5, mask, val);
220 break;
221 }
222
223 /*
224 * Gen1 doesn't need dst_rate settings,
225 * since it uses SSI WS pin.
226 * see also rsnd_src_set_route_if_gen1()
227 */
228
229 return 0;
230}
231
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800232static void rsnd_adg_set_ssi_clk(struct rsnd_mod *mod, u32 val)
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700233{
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800234 int id = rsnd_mod_id(mod);
235 int shift = (id % 4) * 8;
236 u32 mask = 0xFF << shift;
237
238 val = val << shift;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700239
240 /*
241 * SSI 8 is not connected to ADG.
242 * it works with SSI 7
243 */
244 if (id == 8)
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800245 return;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700246
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800247 switch (id / 4) {
248 case 0:
249 rsnd_mod_bset(mod, AUDIO_CLK_SEL0, mask, val);
250 break;
251 case 1:
252 rsnd_mod_bset(mod, AUDIO_CLK_SEL1, mask, val);
253 break;
254 case 2:
255 rsnd_mod_bset(mod, AUDIO_CLK_SEL2, mask, val);
256 break;
257 }
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700258}
259
260int rsnd_adg_ssi_clk_stop(struct rsnd_mod *mod)
261{
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700262 /*
263 * "mod" = "ssi" here.
264 * we can get "ssi id" from mod
265 */
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800266 rsnd_adg_set_ssi_clk(mod, 0);
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700267
268 return 0;
269}
270
271int rsnd_adg_ssi_clk_try_start(struct rsnd_mod *mod, unsigned int rate)
272{
273 struct rsnd_priv *priv = rsnd_mod_to_priv(mod);
274 struct rsnd_adg *adg = rsnd_priv_to_adg(priv);
275 struct device *dev = rsnd_priv_to_dev(priv);
276 struct clk *clk;
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800277 int i;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700278 u32 data;
279 int sel_table[] = {
280 [CLKA] = 0x1,
281 [CLKB] = 0x2,
282 [CLKC] = 0x3,
283 [CLKI] = 0x0,
284 };
285
286 dev_dbg(dev, "request clock = %d\n", rate);
287
288 /*
289 * find suitable clock from
290 * AUDIO_CLKA/AUDIO_CLKB/AUDIO_CLKC/AUDIO_CLKI.
291 */
292 data = 0;
293 for_each_rsnd_clk(clk, adg, i) {
294 if (rate == clk_get_rate(clk)) {
295 data = sel_table[i];
296 goto found_clock;
297 }
298 }
299
300 /*
301 * find 1/6 clock from BRGA/BRGB
302 */
Kuninori Morimoto7808aa32013-12-19 19:27:19 -0800303 if (rate == adg->rbga_rate_for_441khz_div_6) {
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700304 data = 0x10;
305 goto found_clock;
306 }
307
Kuninori Morimoto7808aa32013-12-19 19:27:19 -0800308 if (rate == adg->rbgb_rate_for_48khz_div_6) {
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700309 data = 0x20;
310 goto found_clock;
311 }
312
313 return -EIO;
314
315found_clock:
316
Kuninori Morimotoefeb9702013-09-23 23:12:17 -0700317 /* see rsnd_adg_ssi_clk_init() */
318 rsnd_mod_bset(mod, SSICKR, 0x00FF0000, adg->ckr);
319 rsnd_mod_write(mod, BRRA, 0x00000002); /* 1/6 */
320 rsnd_mod_write(mod, BRRB, 0x00000002); /* 1/6 */
321
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700322 /*
323 * This "mod" = "ssi" here.
324 * we can get "ssi id" from mod
325 */
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800326 rsnd_adg_set_ssi_clk(mod, data);
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700327
Kuninori Morimotoe3378532013-12-19 19:26:31 -0800328 dev_dbg(dev, "ADG: ssi%d selects clk%d = %d",
329 rsnd_mod_id(mod), i, rate);
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700330
331 return 0;
332}
333
334static void rsnd_adg_ssi_clk_init(struct rsnd_priv *priv, struct rsnd_adg *adg)
335{
336 struct clk *clk;
337 unsigned long rate;
338 u32 ckr;
339 int i;
340 int brg_table[] = {
341 [CLKA] = 0x0,
342 [CLKB] = 0x1,
343 [CLKC] = 0x4,
344 [CLKI] = 0x2,
345 };
346
347 /*
348 * This driver is assuming that AUDIO_CLKA/AUDIO_CLKB/AUDIO_CLKC
349 * have 44.1kHz or 48kHz base clocks for now.
350 *
351 * SSI itself can divide parent clock by 1/1 - 1/16
352 * So, BRGA outputs 44.1kHz base parent clock 1/32,
353 * and, BRGB outputs 48.0kHz base parent clock 1/32 here.
354 * see
355 * rsnd_adg_ssi_clk_try_start()
356 */
357 ckr = 0;
Kuninori Morimoto7808aa32013-12-19 19:27:19 -0800358 adg->rbga_rate_for_441khz_div_6 = 0;
359 adg->rbgb_rate_for_48khz_div_6 = 0;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700360 for_each_rsnd_clk(clk, adg, i) {
361 rate = clk_get_rate(clk);
362
363 if (0 == rate) /* not used */
364 continue;
365
366 /* RBGA */
Kuninori Morimoto7808aa32013-12-19 19:27:19 -0800367 if (!adg->rbga_rate_for_441khz_div_6 && (0 == rate % 44100)) {
368 adg->rbga_rate_for_441khz_div_6 = rate / 6;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700369 ckr |= brg_table[i] << 20;
370 }
371
372 /* RBGB */
Kuninori Morimoto7808aa32013-12-19 19:27:19 -0800373 if (!adg->rbgb_rate_for_48khz_div_6 && (0 == rate % 48000)) {
374 adg->rbgb_rate_for_48khz_div_6 = rate / 6;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700375 ckr |= brg_table[i] << 16;
376 }
377 }
378
Kuninori Morimotoefeb9702013-09-23 23:12:17 -0700379 adg->ckr = ckr;
Kuninori Morimotodfc94032013-07-21 21:36:46 -0700380}
381
382int rsnd_adg_probe(struct platform_device *pdev,
383 struct rcar_snd_info *info,
384 struct rsnd_priv *priv)
385{
386 struct rsnd_adg *adg;
387 struct device *dev = rsnd_priv_to_dev(priv);
388 struct clk *clk;
389 int i;
390
391 adg = devm_kzalloc(dev, sizeof(*adg), GFP_KERNEL);
392 if (!adg) {
393 dev_err(dev, "ADG allocate failed\n");
394 return -ENOMEM;
395 }
396
397 adg->clk[CLKA] = clk_get(NULL, "audio_clk_a");
398 adg->clk[CLKB] = clk_get(NULL, "audio_clk_b");
399 adg->clk[CLKC] = clk_get(NULL, "audio_clk_c");
400 adg->clk[CLKI] = clk_get(NULL, "audio_clk_internal");
401 for_each_rsnd_clk(clk, adg, i) {
402 if (IS_ERR(clk)) {
403 dev_err(dev, "Audio clock failed\n");
404 return -EIO;
405 }
406 }
407
408 rsnd_adg_ssi_clk_init(priv, adg);
409
410 priv->adg = adg;
411
412 dev_dbg(dev, "adg probed\n");
413
414 return 0;
415}
416
417void rsnd_adg_remove(struct platform_device *pdev,
418 struct rsnd_priv *priv)
419{
420 struct rsnd_adg *adg = priv->adg;
421 struct clk *clk;
422 int i;
423
424 for_each_rsnd_clk(clk, adg, i)
425 clk_put(clk);
426}