]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - lib_blackfin/clocks.c
0be395bb30f7b1ab99319ac9d605b68a4291130d
[karo-tx-uboot.git] / lib_blackfin / clocks.c
1 /*
2  * clocks.c - figure out sclk/cclk/vco and such
3  *
4  * Copyright (c) 2005-2008 Analog Devices Inc.
5  *
6  * Licensed under the GPL-2 or later.
7  */
8
9 #include <common.h>
10 #include <asm/blackfin.h>
11
12 /* Get the voltage input multiplier */
13 static u_long cached_vco_pll_ctl, cached_vco;
14 u_long get_vco(void)
15 {
16         u_long msel;
17
18         u_long pll_ctl = bfin_read_PLL_CTL();
19         if (pll_ctl == cached_vco_pll_ctl)
20                 return cached_vco;
21         else
22                 cached_vco_pll_ctl = pll_ctl;
23
24         msel = (pll_ctl >> 9) & 0x3F;
25         if (0 == msel)
26                 msel = 64;
27
28         cached_vco = CONFIG_CLKIN_HZ;
29         cached_vco >>= (1 & pll_ctl);   /* DF bit */
30         cached_vco *= msel;
31         return cached_vco;
32 }
33
34 /* Get the Core clock */
35 static u_long cached_cclk_pll_div, cached_cclk;
36 u_long get_cclk(void)
37 {
38         u_long csel, ssel;
39
40         if (bfin_read_PLL_STAT() & 0x1)
41                 return CONFIG_CLKIN_HZ;
42
43         ssel = bfin_read_PLL_DIV();
44         if (ssel == cached_cclk_pll_div)
45                 return cached_cclk;
46         else
47                 cached_cclk_pll_div = ssel;
48
49         csel = ((ssel >> 4) & 0x03);
50         ssel &= 0xf;
51         if (ssel && ssel < (1 << csel)) /* SCLK > CCLK */
52                 cached_cclk = get_vco() / ssel;
53         else
54                 cached_cclk = get_vco() >> csel;
55         return cached_cclk;
56 }
57
58 /* Get the System clock */
59 static u_long cached_sclk_pll_div, cached_sclk;
60 u_long get_sclk(void)
61 {
62         u_long ssel;
63
64         if (bfin_read_PLL_STAT() & 0x1)
65                 return CONFIG_CLKIN_HZ;
66
67         ssel = bfin_read_PLL_DIV();
68         if (ssel == cached_sclk_pll_div)
69                 return cached_sclk;
70         else
71                 cached_sclk_pll_div = ssel;
72
73         ssel &= 0xf;
74
75         cached_sclk = get_vco() / ssel;
76         return cached_sclk;
77 }