d0d5076a9b94b078f1d78a0c8c4d598c56e8c00a
[cascardo/linux.git] / drivers / clk / at91 / clk-slow.c
1 /*
2  * drivers/clk/at91/clk-slow.c
3  *
4  *  Copyright (C) 2013 Boris BREZILLON <b.brezillon@overkiz.com>
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, or
9  * (at your option) any later version.
10  *
11  */
12
13 #include <linux/clk.h>
14 #include <linux/clk-provider.h>
15 #include <linux/clkdev.h>
16 #include <linux/slab.h>
17 #include <linux/clk/at91_pmc.h>
18 #include <linux/delay.h>
19 #include <linux/of.h>
20 #include <linux/of_address.h>
21 #include <linux/of_irq.h>
22 #include <linux/io.h>
23 #include <linux/interrupt.h>
24 #include <linux/irq.h>
25 #include <linux/sched.h>
26 #include <linux/wait.h>
27
28 #include "pmc.h"
29 #include "sckc.h"
30
31 #define SLOW_CLOCK_FREQ         32768
32 #define SLOWCK_SW_CYCLES        5
33 #define SLOWCK_SW_TIME_USEC     ((SLOWCK_SW_CYCLES * USEC_PER_SEC) / \
34                                  SLOW_CLOCK_FREQ)
35
36 #define AT91_SCKC_CR                    0x00
37 #define         AT91_SCKC_RCEN          (1 << 0)
38 #define         AT91_SCKC_OSC32EN       (1 << 1)
39 #define         AT91_SCKC_OSC32BYP      (1 << 2)
40 #define         AT91_SCKC_OSCSEL        (1 << 3)
41
42 struct clk_slow_osc {
43         struct clk_hw hw;
44         void __iomem *sckcr;
45         unsigned long startup_usec;
46 };
47
48 #define to_clk_slow_osc(hw) container_of(hw, struct clk_slow_osc, hw)
49
50 struct clk_slow_rc_osc {
51         struct clk_hw hw;
52         void __iomem *sckcr;
53         unsigned long frequency;
54         unsigned long accuracy;
55         unsigned long startup_usec;
56 };
57
58 #define to_clk_slow_rc_osc(hw) container_of(hw, struct clk_slow_rc_osc, hw)
59
60 struct clk_sam9260_slow {
61         struct clk_hw hw;
62         struct at91_pmc *pmc;
63 };
64
65 #define to_clk_sam9260_slow(hw) container_of(hw, struct clk_sam9260_slow, hw)
66
67 struct clk_sam9x5_slow {
68         struct clk_hw hw;
69         void __iomem *sckcr;
70         u8 parent;
71 };
72
73 #define to_clk_sam9x5_slow(hw) container_of(hw, struct clk_sam9x5_slow, hw)
74
75 static struct clk *slow_clk;
76
77 static int clk_slow_osc_prepare(struct clk_hw *hw)
78 {
79         struct clk_slow_osc *osc = to_clk_slow_osc(hw);
80         void __iomem *sckcr = osc->sckcr;
81         u32 tmp = readl(sckcr);
82
83         if (tmp & AT91_SCKC_OSC32BYP)
84                 return 0;
85
86         writel(tmp | AT91_SCKC_OSC32EN, sckcr);
87
88         usleep_range(osc->startup_usec, osc->startup_usec + 1);
89
90         return 0;
91 }
92
93 static void clk_slow_osc_unprepare(struct clk_hw *hw)
94 {
95         struct clk_slow_osc *osc = to_clk_slow_osc(hw);
96         void __iomem *sckcr = osc->sckcr;
97         u32 tmp = readl(sckcr);
98
99         if (tmp & AT91_SCKC_OSC32BYP)
100                 return;
101
102         writel(tmp & ~AT91_SCKC_OSC32EN, sckcr);
103 }
104
105 static int clk_slow_osc_is_prepared(struct clk_hw *hw)
106 {
107         struct clk_slow_osc *osc = to_clk_slow_osc(hw);
108         void __iomem *sckcr = osc->sckcr;
109         u32 tmp = readl(sckcr);
110
111         if (tmp & AT91_SCKC_OSC32BYP)
112                 return 1;
113
114         return !!(tmp & AT91_SCKC_OSC32EN);
115 }
116
117 static const struct clk_ops slow_osc_ops = {
118         .prepare = clk_slow_osc_prepare,
119         .unprepare = clk_slow_osc_unprepare,
120         .is_prepared = clk_slow_osc_is_prepared,
121 };
122
123 static struct clk * __init
124 at91_clk_register_slow_osc(void __iomem *sckcr,
125                            const char *name,
126                            const char *parent_name,
127                            unsigned long startup,
128                            bool bypass)
129 {
130         struct clk_slow_osc *osc;
131         struct clk *clk = NULL;
132         struct clk_init_data init;
133
134         if (!sckcr || !name || !parent_name)
135                 return ERR_PTR(-EINVAL);
136
137         osc = kzalloc(sizeof(*osc), GFP_KERNEL);
138         if (!osc)
139                 return ERR_PTR(-ENOMEM);
140
141         init.name = name;
142         init.ops = &slow_osc_ops;
143         init.parent_names = &parent_name;
144         init.num_parents = 1;
145         init.flags = CLK_IGNORE_UNUSED;
146
147         osc->hw.init = &init;
148         osc->sckcr = sckcr;
149         osc->startup_usec = startup;
150
151         if (bypass)
152                 writel((readl(sckcr) & ~AT91_SCKC_OSC32EN) | AT91_SCKC_OSC32BYP,
153                        sckcr);
154
155         clk = clk_register(NULL, &osc->hw);
156         if (IS_ERR(clk))
157                 kfree(osc);
158
159         return clk;
160 }
161
162 void __init of_at91sam9x5_clk_slow_osc_setup(struct device_node *np,
163                                              void __iomem *sckcr)
164 {
165         struct clk *clk;
166         const char *parent_name;
167         const char *name = np->name;
168         u32 startup;
169         bool bypass;
170
171         parent_name = of_clk_get_parent_name(np, 0);
172         of_property_read_string(np, "clock-output-names", &name);
173         of_property_read_u32(np, "atmel,startup-time-usec", &startup);
174         bypass = of_property_read_bool(np, "atmel,osc-bypass");
175
176         clk = at91_clk_register_slow_osc(sckcr, name, parent_name, startup,
177                                          bypass);
178         if (IS_ERR(clk))
179                 return;
180
181         of_clk_add_provider(np, of_clk_src_simple_get, clk);
182 }
183
184 static unsigned long clk_slow_rc_osc_recalc_rate(struct clk_hw *hw,
185                                                  unsigned long parent_rate)
186 {
187         struct clk_slow_rc_osc *osc = to_clk_slow_rc_osc(hw);
188
189         return osc->frequency;
190 }
191
192 static unsigned long clk_slow_rc_osc_recalc_accuracy(struct clk_hw *hw,
193                                                      unsigned long parent_acc)
194 {
195         struct clk_slow_rc_osc *osc = to_clk_slow_rc_osc(hw);
196
197         return osc->accuracy;
198 }
199
200 static int clk_slow_rc_osc_prepare(struct clk_hw *hw)
201 {
202         struct clk_slow_rc_osc *osc = to_clk_slow_rc_osc(hw);
203         void __iomem *sckcr = osc->sckcr;
204
205         writel(readl(sckcr) | AT91_SCKC_RCEN, sckcr);
206
207         usleep_range(osc->startup_usec, osc->startup_usec + 1);
208
209         return 0;
210 }
211
212 static void clk_slow_rc_osc_unprepare(struct clk_hw *hw)
213 {
214         struct clk_slow_rc_osc *osc = to_clk_slow_rc_osc(hw);
215         void __iomem *sckcr = osc->sckcr;
216
217         writel(readl(sckcr) & ~AT91_SCKC_RCEN, sckcr);
218 }
219
220 static int clk_slow_rc_osc_is_prepared(struct clk_hw *hw)
221 {
222         struct clk_slow_rc_osc *osc = to_clk_slow_rc_osc(hw);
223
224         return !!(readl(osc->sckcr) & AT91_SCKC_RCEN);
225 }
226
227 static const struct clk_ops slow_rc_osc_ops = {
228         .prepare = clk_slow_rc_osc_prepare,
229         .unprepare = clk_slow_rc_osc_unprepare,
230         .is_prepared = clk_slow_rc_osc_is_prepared,
231         .recalc_rate = clk_slow_rc_osc_recalc_rate,
232         .recalc_accuracy = clk_slow_rc_osc_recalc_accuracy,
233 };
234
235 static struct clk * __init
236 at91_clk_register_slow_rc_osc(void __iomem *sckcr,
237                               const char *name,
238                               unsigned long frequency,
239                               unsigned long accuracy,
240                               unsigned long startup)
241 {
242         struct clk_slow_rc_osc *osc;
243         struct clk *clk = NULL;
244         struct clk_init_data init;
245
246         if (!sckcr || !name)
247                 return ERR_PTR(-EINVAL);
248
249         osc = kzalloc(sizeof(*osc), GFP_KERNEL);
250         if (!osc)
251                 return ERR_PTR(-ENOMEM);
252
253         init.name = name;
254         init.ops = &slow_rc_osc_ops;
255         init.parent_names = NULL;
256         init.num_parents = 0;
257         init.flags = CLK_IS_ROOT | CLK_IGNORE_UNUSED;
258
259         osc->hw.init = &init;
260         osc->sckcr = sckcr;
261         osc->frequency = frequency;
262         osc->accuracy = accuracy;
263         osc->startup_usec = startup;
264
265         clk = clk_register(NULL, &osc->hw);
266         if (IS_ERR(clk))
267                 kfree(osc);
268
269         return clk;
270 }
271
272 void __init of_at91sam9x5_clk_slow_rc_osc_setup(struct device_node *np,
273                                                 void __iomem *sckcr)
274 {
275         struct clk *clk;
276         u32 frequency = 0;
277         u32 accuracy = 0;
278         u32 startup = 0;
279         const char *name = np->name;
280
281         of_property_read_string(np, "clock-output-names", &name);
282         of_property_read_u32(np, "clock-frequency", &frequency);
283         of_property_read_u32(np, "clock-accuracy", &accuracy);
284         of_property_read_u32(np, "atmel,startup-time-usec", &startup);
285
286         clk = at91_clk_register_slow_rc_osc(sckcr, name, frequency, accuracy,
287                                             startup);
288         if (IS_ERR(clk))
289                 return;
290
291         of_clk_add_provider(np, of_clk_src_simple_get, clk);
292 }
293
294 static int clk_sam9x5_slow_set_parent(struct clk_hw *hw, u8 index)
295 {
296         struct clk_sam9x5_slow *slowck = to_clk_sam9x5_slow(hw);
297         void __iomem *sckcr = slowck->sckcr;
298         u32 tmp;
299
300         if (index > 1)
301                 return -EINVAL;
302
303         tmp = readl(sckcr);
304
305         if ((!index && !(tmp & AT91_SCKC_OSCSEL)) ||
306             (index && (tmp & AT91_SCKC_OSCSEL)))
307                 return 0;
308
309         if (index)
310                 tmp |= AT91_SCKC_OSCSEL;
311         else
312                 tmp &= ~AT91_SCKC_OSCSEL;
313
314         writel(tmp, sckcr);
315
316         usleep_range(SLOWCK_SW_TIME_USEC, SLOWCK_SW_TIME_USEC + 1);
317
318         return 0;
319 }
320
321 static u8 clk_sam9x5_slow_get_parent(struct clk_hw *hw)
322 {
323         struct clk_sam9x5_slow *slowck = to_clk_sam9x5_slow(hw);
324
325         return !!(readl(slowck->sckcr) & AT91_SCKC_OSCSEL);
326 }
327
328 static const struct clk_ops sam9x5_slow_ops = {
329         .set_parent = clk_sam9x5_slow_set_parent,
330         .get_parent = clk_sam9x5_slow_get_parent,
331 };
332
333 static struct clk * __init
334 at91_clk_register_sam9x5_slow(void __iomem *sckcr,
335                               const char *name,
336                               const char **parent_names,
337                               int num_parents)
338 {
339         struct clk_sam9x5_slow *slowck;
340         struct clk *clk = NULL;
341         struct clk_init_data init;
342
343         if (!sckcr || !name || !parent_names || !num_parents)
344                 return ERR_PTR(-EINVAL);
345
346         slowck = kzalloc(sizeof(*slowck), GFP_KERNEL);
347         if (!slowck)
348                 return ERR_PTR(-ENOMEM);
349
350         init.name = name;
351         init.ops = &sam9x5_slow_ops;
352         init.parent_names = parent_names;
353         init.num_parents = num_parents;
354         init.flags = 0;
355
356         slowck->hw.init = &init;
357         slowck->sckcr = sckcr;
358         slowck->parent = !!(readl(sckcr) & AT91_SCKC_OSCSEL);
359
360         clk = clk_register(NULL, &slowck->hw);
361         if (IS_ERR(clk))
362                 kfree(slowck);
363         else
364                 slow_clk = clk;
365
366         return clk;
367 }
368
369 void __init of_at91sam9x5_clk_slow_setup(struct device_node *np,
370                                          void __iomem *sckcr)
371 {
372         struct clk *clk;
373         const char *parent_names[2];
374         int num_parents;
375         const char *name = np->name;
376
377         num_parents = of_clk_get_parent_count(np);
378         if (num_parents <= 0 || num_parents > 2)
379                 return;
380
381         of_clk_parent_fill(np, parent_names, num_parents);
382
383         of_property_read_string(np, "clock-output-names", &name);
384
385         clk = at91_clk_register_sam9x5_slow(sckcr, name, parent_names,
386                                             num_parents);
387         if (IS_ERR(clk))
388                 return;
389
390         of_clk_add_provider(np, of_clk_src_simple_get, clk);
391 }
392
393 static u8 clk_sam9260_slow_get_parent(struct clk_hw *hw)
394 {
395         struct clk_sam9260_slow *slowck = to_clk_sam9260_slow(hw);
396
397         return !!(pmc_read(slowck->pmc, AT91_PMC_SR) & AT91_PMC_OSCSEL);
398 }
399
400 static const struct clk_ops sam9260_slow_ops = {
401         .get_parent = clk_sam9260_slow_get_parent,
402 };
403
404 static struct clk * __init
405 at91_clk_register_sam9260_slow(struct at91_pmc *pmc,
406                                const char *name,
407                                const char **parent_names,
408                                int num_parents)
409 {
410         struct clk_sam9260_slow *slowck;
411         struct clk *clk = NULL;
412         struct clk_init_data init;
413
414         if (!pmc || !name)
415                 return ERR_PTR(-EINVAL);
416
417         if (!parent_names || !num_parents)
418                 return ERR_PTR(-EINVAL);
419
420         slowck = kzalloc(sizeof(*slowck), GFP_KERNEL);
421         if (!slowck)
422                 return ERR_PTR(-ENOMEM);
423
424         init.name = name;
425         init.ops = &sam9260_slow_ops;
426         init.parent_names = parent_names;
427         init.num_parents = num_parents;
428         init.flags = 0;
429
430         slowck->hw.init = &init;
431         slowck->pmc = pmc;
432
433         clk = clk_register(NULL, &slowck->hw);
434         if (IS_ERR(clk))
435                 kfree(slowck);
436         else
437                 slow_clk = clk;
438
439         return clk;
440 }
441
442 void __init of_at91sam9260_clk_slow_setup(struct device_node *np,
443                                           struct at91_pmc *pmc)
444 {
445         struct clk *clk;
446         const char *parent_names[2];
447         int num_parents;
448         const char *name = np->name;
449
450         num_parents = of_clk_get_parent_count(np);
451         if (num_parents != 2)
452                 return;
453
454         of_clk_parent_fill(np, parent_names, num_parents);
455
456         of_property_read_string(np, "clock-output-names", &name);
457
458         clk = at91_clk_register_sam9260_slow(pmc, name, parent_names,
459                                              num_parents);
460         if (IS_ERR(clk))
461                 return;
462
463         of_clk_add_provider(np, of_clk_src_simple_get, clk);
464 }
465
466 /*
467  * FIXME: All slow clk users are not properly claiming it (get + prepare +
468  * enable) before using it.
469  * If all users properly claiming this clock decide that they don't need it
470  * anymore (or are removed), it is disabled while faulty users are still
471  * requiring it, and the system hangs.
472  * Prevent this clock from being disabled until all users are properly
473  * requesting it.
474  * Once this is done we should remove this function and the slow_clk variable.
475  */
476 static int __init of_at91_clk_slow_retain(void)
477 {
478         if (!slow_clk)
479                 return 0;
480
481         __clk_get(slow_clk);
482         clk_prepare_enable(slow_clk);
483
484         return 0;
485 }
486 arch_initcall(of_at91_clk_slow_retain);