ARM: ux500: add an SMP enablement type and move cpu nodes
[deliverable/linux.git] / arch / arm / mach-shmobile / clock-sh73a0.c
1 /*
2 * sh73a0 clock framework support
3 *
4 * Copyright (C) 2010 Magnus Damm
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 */
15 #include <linux/init.h>
16 #include <linux/kernel.h>
17 #include <linux/io.h>
18 #include <linux/sh_clk.h>
19 #include <linux/clkdev.h>
20 #include <asm/processor.h>
21 #include "clock.h"
22 #include "common.h"
23
24 #define FRQCRA IOMEM(0xe6150000)
25 #define FRQCRB IOMEM(0xe6150004)
26 #define FRQCRD IOMEM(0xe61500e4)
27 #define VCLKCR1 IOMEM(0xe6150008)
28 #define VCLKCR2 IOMEM(0xe615000C)
29 #define VCLKCR3 IOMEM(0xe615001C)
30 #define ZBCKCR IOMEM(0xe6150010)
31 #define FLCKCR IOMEM(0xe6150014)
32 #define SD0CKCR IOMEM(0xe6150074)
33 #define SD1CKCR IOMEM(0xe6150078)
34 #define SD2CKCR IOMEM(0xe615007C)
35 #define FSIACKCR IOMEM(0xe6150018)
36 #define FSIBCKCR IOMEM(0xe6150090)
37 #define SUBCKCR IOMEM(0xe6150080)
38 #define SPUACKCR IOMEM(0xe6150084)
39 #define SPUVCKCR IOMEM(0xe6150094)
40 #define MSUCKCR IOMEM(0xe6150088)
41 #define HSICKCR IOMEM(0xe615008C)
42 #define MFCK1CR IOMEM(0xe6150098)
43 #define MFCK2CR IOMEM(0xe615009C)
44 #define DSITCKCR IOMEM(0xe6150060)
45 #define DSI0PCKCR IOMEM(0xe6150064)
46 #define DSI1PCKCR IOMEM(0xe6150068)
47 #define DSI0PHYCR 0xe615006C
48 #define DSI1PHYCR 0xe6150070
49 #define PLLECR IOMEM(0xe61500d0)
50 #define PLL0CR IOMEM(0xe61500d8)
51 #define PLL1CR IOMEM(0xe6150028)
52 #define PLL2CR IOMEM(0xe615002c)
53 #define PLL3CR IOMEM(0xe61500dc)
54 #define SMSTPCR0 IOMEM(0xe6150130)
55 #define SMSTPCR1 IOMEM(0xe6150134)
56 #define SMSTPCR2 IOMEM(0xe6150138)
57 #define SMSTPCR3 IOMEM(0xe615013c)
58 #define SMSTPCR4 IOMEM(0xe6150140)
59 #define SMSTPCR5 IOMEM(0xe6150144)
60 #define CKSCR IOMEM(0xe61500c0)
61
62 /* Fixed 32 KHz root clock from EXTALR pin */
63 static struct clk r_clk = {
64 .rate = 32768,
65 };
66
67 /*
68 * 26MHz default rate for the EXTAL1 root input clock.
69 * If needed, reset this with clk_set_rate() from the platform code.
70 */
71 struct clk sh73a0_extal1_clk = {
72 .rate = 26000000,
73 };
74
75 /*
76 * 48MHz default rate for the EXTAL2 root input clock.
77 * If needed, reset this with clk_set_rate() from the platform code.
78 */
79 struct clk sh73a0_extal2_clk = {
80 .rate = 48000000,
81 };
82
83 static struct sh_clk_ops main_clk_ops = {
84 .recalc = followparent_recalc,
85 };
86
87 /* Main clock */
88 static struct clk main_clk = {
89 /* .parent wll be set on sh73a0_clock_init() */
90 .ops = &main_clk_ops,
91 };
92
93 /* PLL0, PLL1, PLL2, PLL3 */
94 static unsigned long pll_recalc(struct clk *clk)
95 {
96 unsigned long mult = 1;
97
98 if (__raw_readl(PLLECR) & (1 << clk->enable_bit)) {
99 mult = (((__raw_readl(clk->enable_reg) >> 24) & 0x3f) + 1);
100 /* handle CFG bit for PLL1 and PLL2 */
101 switch (clk->enable_bit) {
102 case 1:
103 case 2:
104 if (__raw_readl(clk->enable_reg) & (1 << 20))
105 mult *= 2;
106 }
107 }
108
109 return clk->parent->rate * mult;
110 }
111
112 static struct sh_clk_ops pll_clk_ops = {
113 .recalc = pll_recalc,
114 };
115
116 static struct clk pll0_clk = {
117 .ops = &pll_clk_ops,
118 .flags = CLK_ENABLE_ON_INIT,
119 .parent = &main_clk,
120 .enable_reg = (void __iomem *)PLL0CR,
121 .enable_bit = 0,
122 };
123
124 static struct clk pll1_clk = {
125 .ops = &pll_clk_ops,
126 .flags = CLK_ENABLE_ON_INIT,
127 .parent = &main_clk,
128 .enable_reg = (void __iomem *)PLL1CR,
129 .enable_bit = 1,
130 };
131
132 static struct clk pll2_clk = {
133 .ops = &pll_clk_ops,
134 .flags = CLK_ENABLE_ON_INIT,
135 .parent = &main_clk,
136 .enable_reg = (void __iomem *)PLL2CR,
137 .enable_bit = 2,
138 };
139
140 static struct clk pll3_clk = {
141 .ops = &pll_clk_ops,
142 .flags = CLK_ENABLE_ON_INIT,
143 .parent = &main_clk,
144 .enable_reg = (void __iomem *)PLL3CR,
145 .enable_bit = 3,
146 };
147
148 /* A fixed divide block */
149 SH_CLK_RATIO(div2, 1, 2);
150 SH_CLK_RATIO(div7, 1, 7);
151 SH_CLK_RATIO(div13, 1, 13);
152
153 SH_FIXED_RATIO_CLK(extal1_div2_clk, sh73a0_extal1_clk, div2);
154 SH_FIXED_RATIO_CLK(extal2_div2_clk, sh73a0_extal2_clk, div2);
155 SH_FIXED_RATIO_CLK(main_div2_clk, main_clk, div2);
156 SH_FIXED_RATIO_CLK(pll1_div2_clk, pll1_clk, div2);
157 SH_FIXED_RATIO_CLK(pll1_div7_clk, pll1_clk, div7);
158 SH_FIXED_RATIO_CLK(pll1_div13_clk, pll1_clk, div13);
159
160 /* External input clock */
161 struct clk sh73a0_extcki_clk = {
162 };
163
164 struct clk sh73a0_extalr_clk = {
165 };
166
167 static struct clk *main_clks[] = {
168 &r_clk,
169 &sh73a0_extal1_clk,
170 &sh73a0_extal2_clk,
171 &extal1_div2_clk,
172 &extal2_div2_clk,
173 &main_clk,
174 &main_div2_clk,
175 &pll0_clk,
176 &pll1_clk,
177 &pll2_clk,
178 &pll3_clk,
179 &pll1_div2_clk,
180 &pll1_div7_clk,
181 &pll1_div13_clk,
182 &sh73a0_extcki_clk,
183 &sh73a0_extalr_clk,
184 };
185
186 static int frqcr_kick(void)
187 {
188 int i;
189
190 /* set KICK bit in FRQCRB to update hardware setting, check success */
191 __raw_writel(__raw_readl(FRQCRB) | (1 << 31), FRQCRB);
192 for (i = 1000; i; i--)
193 if (__raw_readl(FRQCRB) & (1 << 31))
194 cpu_relax();
195 else
196 return i;
197
198 return -ETIMEDOUT;
199 }
200
201 static void div4_kick(struct clk *clk)
202 {
203 frqcr_kick();
204 }
205
206 static int divisors[] = { 2, 3, 4, 6, 8, 12, 16, 18,
207 24, 0, 36, 48, 7 };
208
209 static struct clk_div_mult_table div4_div_mult_table = {
210 .divisors = divisors,
211 .nr_divisors = ARRAY_SIZE(divisors),
212 };
213
214 static struct clk_div4_table div4_table = {
215 .div_mult_table = &div4_div_mult_table,
216 .kick = div4_kick,
217 };
218
219 enum { DIV4_I, DIV4_ZG, DIV4_M3, DIV4_B, DIV4_M1, DIV4_M2,
220 DIV4_Z, DIV4_ZX, DIV4_HP, DIV4_NR };
221
222 #define DIV4(_reg, _bit, _mask, _flags) \
223 SH_CLK_DIV4(&pll1_clk, _reg, _bit, _mask, _flags)
224
225 static struct clk div4_clks[DIV4_NR] = {
226 [DIV4_I] = DIV4(FRQCRA, 20, 0xdff, CLK_ENABLE_ON_INIT),
227 /*
228 * ZG clock is dividing PLL0 frequency to supply SGX. Make sure not to
229 * exceed maximum frequencies of 201.5MHz for VDD_DVFS=1.175 and
230 * 239.2MHz for VDD_DVFS=1.315V.
231 */
232 [DIV4_ZG] = SH_CLK_DIV4(&pll0_clk, FRQCRA, 16, 0xd7f, CLK_ENABLE_ON_INIT),
233 [DIV4_M3] = DIV4(FRQCRA, 12, 0x1dff, CLK_ENABLE_ON_INIT),
234 [DIV4_B] = DIV4(FRQCRA, 8, 0xdff, CLK_ENABLE_ON_INIT),
235 [DIV4_M1] = DIV4(FRQCRA, 4, 0x1dff, 0),
236 [DIV4_M2] = DIV4(FRQCRA, 0, 0x1dff, 0),
237 [DIV4_Z] = SH_CLK_DIV4(&pll0_clk, FRQCRB, 24, 0x97f, 0),
238 [DIV4_ZX] = DIV4(FRQCRB, 12, 0xdff, 0),
239 [DIV4_HP] = DIV4(FRQCRB, 4, 0xdff, 0),
240 };
241
242 static unsigned long twd_recalc(struct clk *clk)
243 {
244 return clk_get_rate(clk->parent) / 4;
245 }
246
247 static struct sh_clk_ops twd_clk_ops = {
248 .recalc = twd_recalc,
249 };
250
251 static struct clk twd_clk = {
252 .parent = &div4_clks[DIV4_Z],
253 .ops = &twd_clk_ops,
254 };
255
256 static struct sh_clk_ops zclk_ops, kicker_ops;
257 static const struct sh_clk_ops *div4_clk_ops;
258
259 static int zclk_set_rate(struct clk *clk, unsigned long rate)
260 {
261 int ret;
262
263 if (!clk->parent || !__clk_get(clk->parent))
264 return -ENODEV;
265
266 if (readl(FRQCRB) & (1 << 31))
267 return -EBUSY;
268
269 if (rate == clk_get_rate(clk->parent)) {
270 /* 1:1 - switch off divider */
271 __raw_writel(__raw_readl(FRQCRB) & ~(1 << 28), FRQCRB);
272 /* nullify the divider to prepare for the next time */
273 ret = div4_clk_ops->set_rate(clk, rate / 2);
274 if (!ret)
275 ret = frqcr_kick();
276 if (ret > 0)
277 ret = 0;
278 } else {
279 /* Enable the divider */
280 __raw_writel(__raw_readl(FRQCRB) | (1 << 28), FRQCRB);
281
282 ret = frqcr_kick();
283 if (ret >= 0)
284 /*
285 * set the divider - call the DIV4 method, it will kick
286 * FRQCRB too
287 */
288 ret = div4_clk_ops->set_rate(clk, rate);
289 if (ret < 0)
290 goto esetrate;
291 }
292
293 esetrate:
294 __clk_put(clk->parent);
295 return ret;
296 }
297
298 static long zclk_round_rate(struct clk *clk, unsigned long rate)
299 {
300 unsigned long div_freq = div4_clk_ops->round_rate(clk, rate),
301 parent_freq = clk_get_rate(clk->parent);
302
303 if (rate > div_freq && abs(parent_freq - rate) < rate - div_freq)
304 return parent_freq;
305
306 return div_freq;
307 }
308
309 static unsigned long zclk_recalc(struct clk *clk)
310 {
311 /*
312 * Must recalculate frequencies in case PLL0 has been changed, even if
313 * the divisor is unused ATM!
314 */
315 unsigned long div_freq = div4_clk_ops->recalc(clk);
316
317 if (__raw_readl(FRQCRB) & (1 << 28))
318 return div_freq;
319
320 return clk_get_rate(clk->parent);
321 }
322
323 static int kicker_set_rate(struct clk *clk, unsigned long rate)
324 {
325 if (__raw_readl(FRQCRB) & (1 << 31))
326 return -EBUSY;
327
328 return div4_clk_ops->set_rate(clk, rate);
329 }
330
331 static void div4_clk_extend(void)
332 {
333 int i;
334
335 div4_clk_ops = div4_clks[0].ops;
336
337 /* Add a kicker-busy check before changing the rate */
338 kicker_ops = *div4_clk_ops;
339 /* We extend the DIV4 clock with a 1:1 pass-through case */
340 zclk_ops = *div4_clk_ops;
341
342 kicker_ops.set_rate = kicker_set_rate;
343 zclk_ops.set_rate = zclk_set_rate;
344 zclk_ops.round_rate = zclk_round_rate;
345 zclk_ops.recalc = zclk_recalc;
346
347 for (i = 0; i < DIV4_NR; i++)
348 div4_clks[i].ops = i == DIV4_Z ? &zclk_ops : &kicker_ops;
349 }
350
351 enum { DIV6_VCK1, DIV6_VCK2, DIV6_VCK3, DIV6_ZB1,
352 DIV6_FLCTL, DIV6_SDHI0, DIV6_SDHI1, DIV6_SDHI2,
353 DIV6_FSIA, DIV6_FSIB, DIV6_SUB,
354 DIV6_SPUA, DIV6_SPUV, DIV6_MSU,
355 DIV6_HSI, DIV6_MFG1, DIV6_MFG2,
356 DIV6_DSIT, DIV6_DSI0P, DIV6_DSI1P,
357 DIV6_NR };
358
359 static struct clk *vck_parent[8] = {
360 [0] = &pll1_div2_clk,
361 [1] = &pll2_clk,
362 [2] = &sh73a0_extcki_clk,
363 [3] = &sh73a0_extal2_clk,
364 [4] = &main_div2_clk,
365 [5] = &sh73a0_extalr_clk,
366 [6] = &main_clk,
367 };
368
369 static struct clk *pll_parent[4] = {
370 [0] = &pll1_div2_clk,
371 [1] = &pll2_clk,
372 [2] = &pll1_div13_clk,
373 };
374
375 static struct clk *hsi_parent[4] = {
376 [0] = &pll1_div2_clk,
377 [1] = &pll2_clk,
378 [2] = &pll1_div7_clk,
379 };
380
381 static struct clk *pll_extal2_parent[] = {
382 [0] = &pll1_div2_clk,
383 [1] = &pll2_clk,
384 [2] = &sh73a0_extal2_clk,
385 [3] = &sh73a0_extal2_clk,
386 };
387
388 static struct clk *dsi_parent[8] = {
389 [0] = &pll1_div2_clk,
390 [1] = &pll2_clk,
391 [2] = &main_clk,
392 [3] = &sh73a0_extal2_clk,
393 [4] = &sh73a0_extcki_clk,
394 };
395
396 static struct clk div6_clks[DIV6_NR] = {
397 [DIV6_VCK1] = SH_CLK_DIV6_EXT(VCLKCR1, 0,
398 vck_parent, ARRAY_SIZE(vck_parent), 12, 3),
399 [DIV6_VCK2] = SH_CLK_DIV6_EXT(VCLKCR2, 0,
400 vck_parent, ARRAY_SIZE(vck_parent), 12, 3),
401 [DIV6_VCK3] = SH_CLK_DIV6_EXT(VCLKCR3, 0,
402 vck_parent, ARRAY_SIZE(vck_parent), 12, 3),
403 [DIV6_ZB1] = SH_CLK_DIV6_EXT(ZBCKCR, CLK_ENABLE_ON_INIT,
404 pll_parent, ARRAY_SIZE(pll_parent), 7, 1),
405 [DIV6_FLCTL] = SH_CLK_DIV6_EXT(FLCKCR, 0,
406 pll_parent, ARRAY_SIZE(pll_parent), 7, 1),
407 [DIV6_SDHI0] = SH_CLK_DIV6_EXT(SD0CKCR, 0,
408 pll_parent, ARRAY_SIZE(pll_parent), 6, 2),
409 [DIV6_SDHI1] = SH_CLK_DIV6_EXT(SD1CKCR, 0,
410 pll_parent, ARRAY_SIZE(pll_parent), 6, 2),
411 [DIV6_SDHI2] = SH_CLK_DIV6_EXT(SD2CKCR, 0,
412 pll_parent, ARRAY_SIZE(pll_parent), 6, 2),
413 [DIV6_FSIA] = SH_CLK_DIV6_EXT(FSIACKCR, 0,
414 pll_parent, ARRAY_SIZE(pll_parent), 6, 1),
415 [DIV6_FSIB] = SH_CLK_DIV6_EXT(FSIBCKCR, 0,
416 pll_parent, ARRAY_SIZE(pll_parent), 6, 1),
417 [DIV6_SUB] = SH_CLK_DIV6_EXT(SUBCKCR, 0,
418 pll_extal2_parent, ARRAY_SIZE(pll_extal2_parent), 6, 2),
419 [DIV6_SPUA] = SH_CLK_DIV6_EXT(SPUACKCR, 0,
420 pll_extal2_parent, ARRAY_SIZE(pll_extal2_parent), 6, 2),
421 [DIV6_SPUV] = SH_CLK_DIV6_EXT(SPUVCKCR, 0,
422 pll_extal2_parent, ARRAY_SIZE(pll_extal2_parent), 6, 2),
423 [DIV6_MSU] = SH_CLK_DIV6_EXT(MSUCKCR, 0,
424 pll_parent, ARRAY_SIZE(pll_parent), 7, 1),
425 [DIV6_HSI] = SH_CLK_DIV6_EXT(HSICKCR, 0,
426 hsi_parent, ARRAY_SIZE(hsi_parent), 6, 2),
427 [DIV6_MFG1] = SH_CLK_DIV6_EXT(MFCK1CR, 0,
428 pll_parent, ARRAY_SIZE(pll_parent), 7, 1),
429 [DIV6_MFG2] = SH_CLK_DIV6_EXT(MFCK2CR, 0,
430 pll_parent, ARRAY_SIZE(pll_parent), 7, 1),
431 [DIV6_DSIT] = SH_CLK_DIV6_EXT(DSITCKCR, 0,
432 pll_parent, ARRAY_SIZE(pll_parent), 7, 1),
433 [DIV6_DSI0P] = SH_CLK_DIV6_EXT(DSI0PCKCR, 0,
434 dsi_parent, ARRAY_SIZE(dsi_parent), 12, 3),
435 [DIV6_DSI1P] = SH_CLK_DIV6_EXT(DSI1PCKCR, 0,
436 dsi_parent, ARRAY_SIZE(dsi_parent), 12, 3),
437 };
438
439 /* DSI DIV */
440 static unsigned long dsiphy_recalc(struct clk *clk)
441 {
442 u32 value;
443
444 value = __raw_readl(clk->mapping->base);
445
446 /* FIXME */
447 if (!(value & 0x000B8000))
448 return clk->parent->rate;
449
450 value &= 0x3f;
451 value += 1;
452
453 if ((value < 12) ||
454 (value > 33)) {
455 pr_err("DSIPHY has wrong value (%d)", value);
456 return 0;
457 }
458
459 return clk->parent->rate / value;
460 }
461
462 static long dsiphy_round_rate(struct clk *clk, unsigned long rate)
463 {
464 return clk_rate_mult_range_round(clk, 12, 33, rate);
465 }
466
467 static void dsiphy_disable(struct clk *clk)
468 {
469 u32 value;
470
471 value = __raw_readl(clk->mapping->base);
472 value &= ~0x000B8000;
473
474 __raw_writel(value , clk->mapping->base);
475 }
476
477 static int dsiphy_enable(struct clk *clk)
478 {
479 u32 value;
480 int multi;
481
482 value = __raw_readl(clk->mapping->base);
483 multi = (value & 0x3f) + 1;
484
485 if ((multi < 12) || (multi > 33))
486 return -EIO;
487
488 __raw_writel(value | 0x000B8000, clk->mapping->base);
489
490 return 0;
491 }
492
493 static int dsiphy_set_rate(struct clk *clk, unsigned long rate)
494 {
495 u32 value;
496 int idx;
497
498 idx = rate / clk->parent->rate;
499 if ((idx < 12) || (idx > 33))
500 return -EINVAL;
501
502 idx += -1;
503
504 value = __raw_readl(clk->mapping->base);
505 value = (value & ~0x3f) + idx;
506
507 __raw_writel(value, clk->mapping->base);
508
509 return 0;
510 }
511
512 static struct sh_clk_ops dsiphy_clk_ops = {
513 .recalc = dsiphy_recalc,
514 .round_rate = dsiphy_round_rate,
515 .set_rate = dsiphy_set_rate,
516 .enable = dsiphy_enable,
517 .disable = dsiphy_disable,
518 };
519
520 static struct clk_mapping dsi0phy_clk_mapping = {
521 .phys = DSI0PHYCR,
522 .len = 4,
523 };
524
525 static struct clk_mapping dsi1phy_clk_mapping = {
526 .phys = DSI1PHYCR,
527 .len = 4,
528 };
529
530 static struct clk dsi0phy_clk = {
531 .ops = &dsiphy_clk_ops,
532 .parent = &div6_clks[DIV6_DSI0P], /* late install */
533 .mapping = &dsi0phy_clk_mapping,
534 };
535
536 static struct clk dsi1phy_clk = {
537 .ops = &dsiphy_clk_ops,
538 .parent = &div6_clks[DIV6_DSI1P], /* late install */
539 .mapping = &dsi1phy_clk_mapping,
540 };
541
542 static struct clk *late_main_clks[] = {
543 &dsi0phy_clk,
544 &dsi1phy_clk,
545 &twd_clk,
546 };
547
548 enum { MSTP001,
549 MSTP129, MSTP128, MSTP127, MSTP126, MSTP125, MSTP118, MSTP116, MSTP112, MSTP100,
550 MSTP219, MSTP218, MSTP217,
551 MSTP207, MSTP206, MSTP204, MSTP203, MSTP202, MSTP201, MSTP200,
552 MSTP331, MSTP329, MSTP328, MSTP325, MSTP323, MSTP322,
553 MSTP314, MSTP313, MSTP312, MSTP311,
554 MSTP304, MSTP303, MSTP302, MSTP301, MSTP300,
555 MSTP411, MSTP410, MSTP403,
556 MSTP508,
557 MSTP_NR };
558
559 #define MSTP(_parent, _reg, _bit, _flags) \
560 SH_CLK_MSTP32(_parent, _reg, _bit, _flags)
561
562 static struct clk mstp_clks[MSTP_NR] = {
563 [MSTP001] = MSTP(&div4_clks[DIV4_HP], SMSTPCR0, 1, 0), /* IIC2 */
564 [MSTP129] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 29, 0), /* CEU1 */
565 [MSTP128] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 28, 0), /* CSI2-RX1 */
566 [MSTP127] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 27, 0), /* CEU0 */
567 [MSTP126] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 26, 0), /* CSI2-RX0 */
568 [MSTP125] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR1, 25, 0), /* TMU0 */
569 [MSTP118] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 18, 0), /* DSITX0 */
570 [MSTP116] = MSTP(&div4_clks[DIV4_HP], SMSTPCR1, 16, 0), /* IIC0 */
571 [MSTP112] = MSTP(&div4_clks[DIV4_ZG], SMSTPCR1, 12, 0), /* SGX */
572 [MSTP100] = MSTP(&div4_clks[DIV4_B], SMSTPCR1, 0, 0), /* LCDC0 */
573 [MSTP219] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 19, 0), /* SCIFA7 */
574 [MSTP218] = MSTP(&div4_clks[DIV4_HP], SMSTPCR2, 18, 0), /* SY-DMAC */
575 [MSTP217] = MSTP(&div4_clks[DIV4_HP], SMSTPCR2, 17, 0), /* MP-DMAC */
576 [MSTP207] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 7, 0), /* SCIFA5 */
577 [MSTP206] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 6, 0), /* SCIFB */
578 [MSTP204] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 4, 0), /* SCIFA0 */
579 [MSTP203] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 3, 0), /* SCIFA1 */
580 [MSTP202] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 2, 0), /* SCIFA2 */
581 [MSTP201] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 1, 0), /* SCIFA3 */
582 [MSTP200] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR2, 0, 0), /* SCIFA4 */
583 [MSTP331] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR3, 31, 0), /* SCIFA6 */
584 [MSTP329] = MSTP(&r_clk, SMSTPCR3, 29, 0), /* CMT10 */
585 [MSTP328] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 28, 0), /*FSI*/
586 [MSTP325] = MSTP(&div6_clks[DIV6_SUB], SMSTPCR3, 25, 0), /* IrDA */
587 [MSTP323] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 23, 0), /* IIC1 */
588 [MSTP322] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 22, 0), /* USB */
589 [MSTP314] = MSTP(&div6_clks[DIV6_SDHI0], SMSTPCR3, 14, 0), /* SDHI0 */
590 [MSTP313] = MSTP(&div6_clks[DIV6_SDHI1], SMSTPCR3, 13, 0), /* SDHI1 */
591 [MSTP312] = MSTP(&div4_clks[DIV4_HP], SMSTPCR3, 12, 0), /* MMCIF0 */
592 [MSTP311] = MSTP(&div6_clks[DIV6_SDHI2], SMSTPCR3, 11, 0), /* SDHI2 */
593 [MSTP304] = MSTP(&main_div2_clk, SMSTPCR3, 4, 0), /* TPU0 */
594 [MSTP303] = MSTP(&main_div2_clk, SMSTPCR3, 3, 0), /* TPU1 */
595 [MSTP302] = MSTP(&main_div2_clk, SMSTPCR3, 2, 0), /* TPU2 */
596 [MSTP301] = MSTP(&main_div2_clk, SMSTPCR3, 1, 0), /* TPU3 */
597 [MSTP300] = MSTP(&main_div2_clk, SMSTPCR3, 0, 0), /* TPU4 */
598 [MSTP411] = MSTP(&div4_clks[DIV4_HP], SMSTPCR4, 11, 0), /* IIC3 */
599 [MSTP410] = MSTP(&div4_clks[DIV4_HP], SMSTPCR4, 10, 0), /* IIC4 */
600 [MSTP403] = MSTP(&r_clk, SMSTPCR4, 3, 0), /* KEYSC */
601 [MSTP508] = MSTP(&div4_clks[DIV4_HP], SMSTPCR5, 8, 0), /* INTCA0 */
602 };
603
604 /* The lookups structure below includes duplicate entries for some clocks
605 * with alternate names.
606 * - The traditional name used when a device is initialised with platform data
607 * - The name used when a device is initialised using device tree
608 * The longer-term aim is to remove these duplicates, and indeed the
609 * lookups table entirely, by describing clocks using device tree.
610 */
611 static struct clk_lookup lookups[] = {
612 /* main clocks */
613 CLKDEV_CON_ID("r_clk", &r_clk),
614 CLKDEV_DEV_ID("smp_twd", &twd_clk), /* smp_twd */
615
616 /* DIV4 clocks */
617 CLKDEV_DEV_ID("cpu0", &div4_clks[DIV4_Z]),
618
619 /* DIV6 clocks */
620 CLKDEV_CON_ID("vck1_clk", &div6_clks[DIV6_VCK1]),
621 CLKDEV_CON_ID("vck2_clk", &div6_clks[DIV6_VCK2]),
622 CLKDEV_CON_ID("vck3_clk", &div6_clks[DIV6_VCK3]),
623 CLKDEV_CON_ID("sdhi0_clk", &div6_clks[DIV6_SDHI0]),
624 CLKDEV_CON_ID("sdhi1_clk", &div6_clks[DIV6_SDHI1]),
625 CLKDEV_CON_ID("sdhi2_clk", &div6_clks[DIV6_SDHI2]),
626
627 /* MSTP32 clocks */
628 CLKDEV_DEV_ID("i2c-sh_mobile.2", &mstp_clks[MSTP001]), /* I2C2 */
629 CLKDEV_DEV_ID("e6824000.i2c", &mstp_clks[MSTP001]), /* I2C2 */
630 CLKDEV_DEV_ID("sh_mobile_ceu.1", &mstp_clks[MSTP129]), /* CEU1 */
631 CLKDEV_DEV_ID("sh-mobile-csi2.1", &mstp_clks[MSTP128]), /* CSI2-RX1 */
632 CLKDEV_DEV_ID("sh_mobile_ceu.0", &mstp_clks[MSTP127]), /* CEU0 */
633 CLKDEV_DEV_ID("sh-mobile-csi2.0", &mstp_clks[MSTP126]), /* CSI2-RX0 */
634 CLKDEV_DEV_ID("sh-mipi-dsi.0", &mstp_clks[MSTP118]), /* DSITX */
635 CLKDEV_DEV_ID("i2c-sh_mobile.0", &mstp_clks[MSTP116]), /* I2C0 */
636 CLKDEV_DEV_ID("e6820000.i2c", &mstp_clks[MSTP116]), /* I2C0 */
637 CLKDEV_DEV_ID("sh_mobile_lcdc_fb.0", &mstp_clks[MSTP100]), /* LCDC0 */
638 CLKDEV_DEV_ID("sh-sci.7", &mstp_clks[MSTP219]), /* SCIFA7 */
639 CLKDEV_DEV_ID("e6cd0000.serial", &mstp_clks[MSTP219]), /* SCIFA7 */
640 CLKDEV_DEV_ID("sh-dma-engine.0", &mstp_clks[MSTP218]), /* SY-DMAC */
641 CLKDEV_DEV_ID("sh-dma-engine.1", &mstp_clks[MSTP217]), /* MP-DMAC */
642 CLKDEV_DEV_ID("sh-sci.5", &mstp_clks[MSTP207]), /* SCIFA5 */
643 CLKDEV_DEV_ID("e6cb0000.serial", &mstp_clks[MSTP207]), /* SCIFA5 */
644 CLKDEV_DEV_ID("sh-sci.8", &mstp_clks[MSTP206]), /* SCIFB */
645 CLKDEV_DEV_ID("e6c3000.serial", &mstp_clks[MSTP206]), /* SCIFB */
646 CLKDEV_DEV_ID("sh-sci.0", &mstp_clks[MSTP204]), /* SCIFA0 */
647 CLKDEV_DEV_ID("e6c40000.serial", &mstp_clks[MSTP204]), /* SCIFA0 */
648 CLKDEV_DEV_ID("sh-sci.1", &mstp_clks[MSTP203]), /* SCIFA1 */
649 CLKDEV_DEV_ID("e6c50000.serial", &mstp_clks[MSTP203]), /* SCIFA1 */
650 CLKDEV_DEV_ID("sh-sci.2", &mstp_clks[MSTP202]), /* SCIFA2 */
651 CLKDEV_DEV_ID("e6c60000.serial", &mstp_clks[MSTP202]), /* SCIFA2 */
652 CLKDEV_DEV_ID("sh-sci.3", &mstp_clks[MSTP201]), /* SCIFA3 */
653 CLKDEV_DEV_ID("e6c70000.serial", &mstp_clks[MSTP201]), /* SCIFA3 */
654 CLKDEV_DEV_ID("sh-sci.4", &mstp_clks[MSTP200]), /* SCIFA4 */
655 CLKDEV_DEV_ID("e6c80000.serial", &mstp_clks[MSTP200]), /* SCIFA4 */
656 CLKDEV_DEV_ID("sh-sci.6", &mstp_clks[MSTP331]), /* SCIFA6 */
657 CLKDEV_DEV_ID("e6cc0000.serial", &mstp_clks[MSTP331]), /* SCIFA6 */
658 CLKDEV_DEV_ID("sh_fsi2", &mstp_clks[MSTP328]), /* FSI */
659 CLKDEV_DEV_ID("ec230000.sound", &mstp_clks[MSTP328]), /* FSI */
660 CLKDEV_DEV_ID("sh_irda.0", &mstp_clks[MSTP325]), /* IrDA */
661 CLKDEV_DEV_ID("i2c-sh_mobile.1", &mstp_clks[MSTP323]), /* I2C1 */
662 CLKDEV_DEV_ID("e6822000.i2c", &mstp_clks[MSTP323]), /* I2C1 */
663 CLKDEV_DEV_ID("renesas_usbhs", &mstp_clks[MSTP322]), /* USB */
664 CLKDEV_DEV_ID("sh_mobile_sdhi.0", &mstp_clks[MSTP314]), /* SDHI0 */
665 CLKDEV_DEV_ID("ee100000.sd", &mstp_clks[MSTP314]), /* SDHI0 */
666 CLKDEV_DEV_ID("sh_mobile_sdhi.1", &mstp_clks[MSTP313]), /* SDHI1 */
667 CLKDEV_DEV_ID("ee120000.sd", &mstp_clks[MSTP313]), /* SDHI1 */
668 CLKDEV_DEV_ID("sh_mmcif.0", &mstp_clks[MSTP312]), /* MMCIF0 */
669 CLKDEV_DEV_ID("e6bd0000.mmc", &mstp_clks[MSTP312]), /* MMCIF0 */
670 CLKDEV_DEV_ID("sh_mobile_sdhi.2", &mstp_clks[MSTP311]), /* SDHI2 */
671 CLKDEV_DEV_ID("ee140000.sd", &mstp_clks[MSTP311]), /* SDHI2 */
672 CLKDEV_DEV_ID("renesas-tpu-pwm.0", &mstp_clks[MSTP304]), /* TPU0 */
673 CLKDEV_DEV_ID("renesas-tpu-pwm.1", &mstp_clks[MSTP303]), /* TPU1 */
674 CLKDEV_DEV_ID("renesas-tpu-pwm.2", &mstp_clks[MSTP302]), /* TPU2 */
675 CLKDEV_DEV_ID("renesas-tpu-pwm.3", &mstp_clks[MSTP301]), /* TPU3 */
676 CLKDEV_DEV_ID("renesas-tpu-pwm.4", &mstp_clks[MSTP300]), /* TPU4 */
677 CLKDEV_DEV_ID("i2c-sh_mobile.3", &mstp_clks[MSTP411]), /* I2C3 */
678 CLKDEV_DEV_ID("e6826000.i2c", &mstp_clks[MSTP411]), /* I2C3 */
679 CLKDEV_DEV_ID("i2c-sh_mobile.4", &mstp_clks[MSTP410]), /* I2C4 */
680 CLKDEV_DEV_ID("e6828000.i2c", &mstp_clks[MSTP410]), /* I2C4 */
681 CLKDEV_DEV_ID("sh_keysc.0", &mstp_clks[MSTP403]), /* KEYSC */
682 CLKDEV_DEV_ID("renesas_intc_irqpin.0", &mstp_clks[MSTP508]), /* INTCA0 */
683 CLKDEV_DEV_ID("e6900000.irqpin", &mstp_clks[MSTP508]), /* INTCA0 */
684 CLKDEV_DEV_ID("renesas_intc_irqpin.1", &mstp_clks[MSTP508]), /* INTCA0 */
685 CLKDEV_DEV_ID("e6900004.irqpin", &mstp_clks[MSTP508]), /* INTCA0 */
686 CLKDEV_DEV_ID("renesas_intc_irqpin.2", &mstp_clks[MSTP508]), /* INTCA0 */
687 CLKDEV_DEV_ID("e6900008.irqpin", &mstp_clks[MSTP508]), /* INTCA0 */
688 CLKDEV_DEV_ID("renesas_intc_irqpin.3", &mstp_clks[MSTP508]), /* INTCA0 */
689 CLKDEV_DEV_ID("e690000c.irqpin", &mstp_clks[MSTP508]), /* INTCA0 */
690
691 /* ICK */
692 CLKDEV_ICK_ID("dsit_clk", "sh-mipi-dsi.0", &div6_clks[DIV6_DSIT]),
693 CLKDEV_ICK_ID("dsit_clk", "sh-mipi-dsi.1", &div6_clks[DIV6_DSIT]),
694 CLKDEV_ICK_ID("dsip_clk", "sh-mipi-dsi.0", &div6_clks[DIV6_DSI0P]),
695 CLKDEV_ICK_ID("dsip_clk", "sh-mipi-dsi.1", &div6_clks[DIV6_DSI1P]),
696 CLKDEV_ICK_ID("dsiphy_clk", "sh-mipi-dsi.0", &dsi0phy_clk),
697 CLKDEV_ICK_ID("dsiphy_clk", "sh-mipi-dsi.1", &dsi1phy_clk),
698 CLKDEV_ICK_ID("fck", "sh-cmt-48.1", &mstp_clks[MSTP329]), /* CMT1 */
699 CLKDEV_ICK_ID("fck", "e6138000.timer", &mstp_clks[MSTP329]), /* CMT1 */
700 CLKDEV_ICK_ID("fck", "sh-tmu.0", &mstp_clks[MSTP125]), /* TMU0 */
701 };
702
703 void __init sh73a0_clock_init(void)
704 {
705 int k, ret = 0;
706
707 /* Set SDHI clocks to a known state */
708 __raw_writel(0x108, SD0CKCR);
709 __raw_writel(0x108, SD1CKCR);
710 __raw_writel(0x108, SD2CKCR);
711
712 /* detect main clock parent */
713 switch ((__raw_readl(CKSCR) >> 28) & 0x03) {
714 case 0:
715 main_clk.parent = &sh73a0_extal1_clk;
716 break;
717 case 1:
718 main_clk.parent = &extal1_div2_clk;
719 break;
720 case 2:
721 main_clk.parent = &sh73a0_extal2_clk;
722 break;
723 case 3:
724 main_clk.parent = &extal2_div2_clk;
725 break;
726 }
727
728 for (k = 0; !ret && (k < ARRAY_SIZE(main_clks)); k++)
729 ret = clk_register(main_clks[k]);
730
731 if (!ret) {
732 ret = sh_clk_div4_register(div4_clks, DIV4_NR, &div4_table);
733 if (!ret)
734 div4_clk_extend();
735 }
736
737 if (!ret)
738 ret = sh_clk_div6_reparent_register(div6_clks, DIV6_NR);
739
740 if (!ret)
741 ret = sh_clk_mstp_register(mstp_clks, MSTP_NR);
742
743 for (k = 0; !ret && (k < ARRAY_SIZE(late_main_clks)); k++)
744 ret = clk_register(late_main_clks[k]);
745
746 clkdev_add_table(lookups, ARRAY_SIZE(lookups));
747
748 if (!ret)
749 shmobile_clk_init();
750 else
751 panic("failed to setup sh73a0 clocks\n");
752 }
This page took 0.067514 seconds and 5 git commands to generate.