aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/plat-mxc/clock.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/arm/plat-mxc/clock.c')
-rw-r--r--arch/arm/plat-mxc/clock.c170
1 files changed, 9 insertions, 161 deletions
diff --git a/arch/arm/plat-mxc/clock.c b/arch/arm/plat-mxc/clock.c
index 92e13566cd4f..9e8fbd57495c 100644
--- a/arch/arm/plat-mxc/clock.c
+++ b/arch/arm/plat-mxc/clock.c
@@ -39,6 +39,7 @@
39#include <linux/string.h> 39#include <linux/string.h>
40 40
41#include <mach/clock.h> 41#include <mach/clock.h>
42#include <mach/hardware.h>
42 43
43static LIST_HEAD(clocks); 44static LIST_HEAD(clocks);
44static DEFINE_MUTEX(clocks_mutex); 45static DEFINE_MUTEX(clocks_mutex);
@@ -47,76 +48,6 @@ static DEFINE_MUTEX(clocks_mutex);
47 * Standard clock functions defined in include/linux/clk.h 48 * Standard clock functions defined in include/linux/clk.h
48 *-------------------------------------------------------------------------*/ 49 *-------------------------------------------------------------------------*/
49 50
50/*
51 * All the code inside #ifndef CONFIG_COMMON_CLKDEV can be removed once all
52 * MXC architectures have switched to using clkdev.
53 */
54#ifndef CONFIG_COMMON_CLKDEV
55/*
56 * Retrieve a clock by name.
57 *
58 * Note that we first try to use device id on the bus
59 * and clock name. If this fails, we try to use "<name>.<id>". If this fails,
60 * we try to use clock name only.
61 * The reference count to the clock's module owner ref count is incremented.
62 */
63struct clk *clk_get(struct device *dev, const char *id)
64{
65 struct clk *p, *clk = ERR_PTR(-ENOENT);
66 int idno;
67 const char *str;
68
69 if (id == NULL)
70 return clk;
71
72 if (dev == NULL || dev->bus != &platform_bus_type)
73 idno = -1;
74 else
75 idno = to_platform_device(dev)->id;
76
77 mutex_lock(&clocks_mutex);
78
79 list_for_each_entry(p, &clocks, node) {
80 if (p->id == idno &&
81 strcmp(id, p->name) == 0 && try_module_get(p->owner)) {
82 clk = p;
83 goto found;
84 }
85 }
86
87 str = strrchr(id, '.');
88 if (str) {
89 int cnt = str - id;
90 str++;
91 idno = simple_strtol(str, NULL, 10);
92 list_for_each_entry(p, &clocks, node) {
93 if (p->id == idno &&
94 strlen(p->name) == cnt &&
95 strncmp(id, p->name, cnt) == 0 &&
96 try_module_get(p->owner)) {
97 clk = p;
98 goto found;
99 }
100 }
101 }
102
103 list_for_each_entry(p, &clocks, node) {
104 if (strcmp(id, p->name) == 0 && try_module_get(p->owner)) {
105 clk = p;
106 goto found;
107 }
108 }
109
110 printk(KERN_WARNING "clk: Unable to get requested clock: %s\n", id);
111
112found:
113 mutex_unlock(&clocks_mutex);
114
115 return clk;
116}
117EXPORT_SYMBOL(clk_get);
118#endif
119
120static void __clk_disable(struct clk *clk) 51static void __clk_disable(struct clk *clk)
121{ 52{
122 if (clk == NULL || IS_ERR(clk)) 53 if (clk == NULL || IS_ERR(clk))
@@ -193,16 +124,6 @@ unsigned long clk_get_rate(struct clk *clk)
193} 124}
194EXPORT_SYMBOL(clk_get_rate); 125EXPORT_SYMBOL(clk_get_rate);
195 126
196#ifndef CONFIG_COMMON_CLKDEV
197/* Decrement the clock's module reference count */
198void clk_put(struct clk *clk)
199{
200 if (clk && !IS_ERR(clk))
201 module_put(clk->owner);
202}
203EXPORT_SYMBOL(clk_put);
204#endif
205
206/* Round the requested clock rate to the nearest supported 127/* Round the requested clock rate to the nearest supported
207 * rate that is less than or equal to the requested rate. 128 * rate that is less than or equal to the requested rate.
208 * This is dependent on the clock's current parent. 129 * This is dependent on the clock's current parent.
@@ -265,80 +186,6 @@ struct clk *clk_get_parent(struct clk *clk)
265} 186}
266EXPORT_SYMBOL(clk_get_parent); 187EXPORT_SYMBOL(clk_get_parent);
267 188
268#ifndef CONFIG_COMMON_CLKDEV
269/*
270 * Add a new clock to the clock tree.
271 */
272int clk_register(struct clk *clk)
273{
274 if (clk == NULL || IS_ERR(clk))
275 return -EINVAL;
276
277 mutex_lock(&clocks_mutex);
278 list_add(&clk->node, &clocks);
279 mutex_unlock(&clocks_mutex);
280
281 return 0;
282}
283EXPORT_SYMBOL(clk_register);
284
285/* Remove a clock from the clock tree */
286void clk_unregister(struct clk *clk)
287{
288 if (clk == NULL || IS_ERR(clk))
289 return;
290
291 mutex_lock(&clocks_mutex);
292 list_del(&clk->node);
293 mutex_unlock(&clocks_mutex);
294}
295EXPORT_SYMBOL(clk_unregister);
296
297#ifdef CONFIG_PROC_FS
298static int mxc_clock_read_proc(char *page, char **start, off_t off,
299 int count, int *eof, void *data)
300{
301 struct clk *clkp;
302 char *p = page;
303 int len;
304
305 list_for_each_entry(clkp, &clocks, node) {
306 p += sprintf(p, "%s-%d:\t\t%lu, %d", clkp->name, clkp->id,
307 clk_get_rate(clkp), clkp->usecount);
308 if (clkp->parent)
309 p += sprintf(p, ", %s-%d\n", clkp->parent->name,
310 clkp->parent->id);
311 else
312 p += sprintf(p, "\n");
313 }
314
315 len = (p - page) - off;
316 if (len < 0)
317 len = 0;
318
319 *eof = (len <= count) ? 1 : 0;
320 *start = page + off;
321
322 return len;
323}
324
325static int __init mxc_setup_proc_entry(void)
326{
327 struct proc_dir_entry *res;
328
329 res = create_proc_read_entry("cpu/clocks", 0, NULL,
330 mxc_clock_read_proc, NULL);
331 if (!res) {
332 printk(KERN_ERR "Failed to create proc/cpu/clocks\n");
333 return -ENOMEM;
334 }
335 return 0;
336}
337
338late_initcall(mxc_setup_proc_entry);
339#endif /* CONFIG_PROC_FS */
340#endif
341
342/* 189/*
343 * Get the resulting clock rate from a PLL register value and the input 190 * Get the resulting clock rate from a PLL register value and the input
344 * frequency. PLLs with this register layout can at least be found on 191 * frequency. PLLs with this register layout can at least be found on
@@ -363,12 +210,11 @@ unsigned long mxc_decode_pll(unsigned int reg_val, u32 freq)
363 210
364 mfn_abs = mfn; 211 mfn_abs = mfn;
365 212
366#if !defined CONFIG_ARCH_MX1 && !defined CONFIG_ARCH_MX21 213 /* On all i.MXs except i.MX1 and i.MX21 mfn is a 10bit
367 if (mfn >= 0x200) { 214 * 2's complements number
368 mfn |= 0xFFFFFE00; 215 */
369 mfn_abs = -mfn; 216 if (!cpu_is_mx1() && !cpu_is_mx21() && mfn >= 0x200)
370 } 217 mfn_abs = 0x400 - mfn;
371#endif
372 218
373 freq *= 2; 219 freq *= 2;
374 freq /= pd + 1; 220 freq /= pd + 1;
@@ -376,8 +222,10 @@ unsigned long mxc_decode_pll(unsigned int reg_val, u32 freq)
376 ll = (unsigned long long)freq * mfn_abs; 222 ll = (unsigned long long)freq * mfn_abs;
377 223
378 do_div(ll, mfd + 1); 224 do_div(ll, mfd + 1);
379 if (mfn < 0) 225
226 if (!cpu_is_mx1() && !cpu_is_mx21() && mfn >= 0x200)
380 ll = -ll; 227 ll = -ll;
228
381 ll = (freq * mfi) + ll; 229 ll = (freq * mfi) + ll;
382 230
383 return ll; 231 return ll;