1 #include <linux/slab.h>
3 #include <linux/rockchip/cpu.h>
9 static const struct pll_clk_set rk3188_pll_com_table[] = {
10 _RK3188_PLL_SET_CLKS(1250000, 12, 625, 1),
11 _RK3188_PLL_SET_CLKS(1200000, 1, 50, 1),
12 _RK3188_PLL_SET_CLKS(1188000, 2, 99, 1),
13 _RK3188_PLL_SET_CLKS(891000, 8, 594, 2),
14 _RK3188_PLL_SET_CLKS(768000, 1, 64, 2),
15 _RK3188_PLL_SET_CLKS(594000, 2, 198, 4),
16 _RK3188_PLL_SET_CLKS(500000, 3, 250, 4),
17 _RK3188_PLL_SET_CLKS(408000, 1, 68, 4),
18 _RK3188_PLL_SET_CLKS(396000, 1, 66, 4),
19 _RK3188_PLL_SET_CLKS(384000, 2, 128, 4),
20 _RK3188_PLL_SET_CLKS(360000, 1, 60, 4),
21 _RK3188_PLL_SET_CLKS(300000, 1, 50, 4),
22 _RK3188_PLL_SET_CLKS(297000, 2, 198, 8),
23 _RK3188_PLL_SET_CLKS(148500, 2, 99, 8),
24 _RK3188_PLL_SET_CLKS(0, 0, 0, 0),
27 static const struct pll_clk_set rk3188plus_pll_com_table[] = {
28 _RK3188PLUS_PLL_SET_CLKS(1250000, 12, 625, 1),
29 _RK3188PLUS_PLL_SET_CLKS(1200000, 1, 50, 1),
30 _RK3188PLUS_PLL_SET_CLKS(1188000, 2, 99, 1),
31 _RK3188PLUS_PLL_SET_CLKS(891000, 8, 594, 2),
32 _RK3188PLUS_PLL_SET_CLKS(768000, 1, 64, 2),
33 _RK3188PLUS_PLL_SET_CLKS(594000, 2, 198, 4),
34 _RK3188PLUS_PLL_SET_CLKS(576000, 1, 48, 2),
35 _RK3188PLUS_PLL_SET_CLKS(500000, 3, 250, 4),
36 _RK3188PLUS_PLL_SET_CLKS(408000, 1, 68, 4),
37 _RK3188PLUS_PLL_SET_CLKS(400000, 3, 200, 4),
38 _RK3188PLUS_PLL_SET_CLKS(396000, 1, 66, 4),
39 _RK3188PLUS_PLL_SET_CLKS(384000, 2, 128, 4),
40 _RK3188PLUS_PLL_SET_CLKS(360000, 1, 60, 4),
41 _RK3188PLUS_PLL_SET_CLKS(300000, 1, 50, 4),
42 _RK3188PLUS_PLL_SET_CLKS(297000, 2, 198, 8),
43 _RK3188PLUS_PLL_SET_CLKS(148500, 2, 99, 8),
44 _RK3188PLUS_PLL_SET_CLKS(0, 0, 0, 0),
47 static const struct apll_clk_set rk3188_apll_table[] = {
48 // (_mhz, nr, nf, no, _periph_div, _aclk_div)
49 _RK3188_APLL_SET_CLKS(2208, 1, 92, 1, 8, 81),
50 _RK3188_APLL_SET_CLKS(2184, 1, 91, 1, 8, 81),
51 _RK3188_APLL_SET_CLKS(2160, 1, 90, 1, 8, 81),
52 _RK3188_APLL_SET_CLKS(2136, 1, 89, 1, 8, 81),
53 _RK3188_APLL_SET_CLKS(2112, 1, 88, 1, 8, 81),
54 _RK3188_APLL_SET_CLKS(2088, 1, 87, 1, 8, 81),
55 _RK3188_APLL_SET_CLKS(2064, 1, 86, 1, 8, 81),
56 _RK3188_APLL_SET_CLKS(2040, 1, 85, 1, 8, 81),
57 _RK3188_APLL_SET_CLKS(2016, 1, 84, 1, 8, 81),
58 _RK3188_APLL_SET_CLKS(1992, 1, 83, 1, 8, 81),
59 _RK3188_APLL_SET_CLKS(1968, 1, 82, 1, 8, 81),
60 _RK3188_APLL_SET_CLKS(1944, 1, 81, 1, 8, 81),
61 _RK3188_APLL_SET_CLKS(1920, 1, 80, 1, 8, 81),
62 _RK3188_APLL_SET_CLKS(1896, 1, 79, 1, 8, 81),
63 _RK3188_APLL_SET_CLKS(1872, 1, 78, 1, 8, 81),
64 _RK3188_APLL_SET_CLKS(1848, 1, 77, 1, 8, 81),
65 _RK3188_APLL_SET_CLKS(1824, 1, 76, 1, 8, 81),
66 _RK3188_APLL_SET_CLKS(1800, 1, 75, 1, 8, 81),
67 _RK3188_APLL_SET_CLKS(1776, 1, 74, 1, 8, 81),
68 _RK3188_APLL_SET_CLKS(1752, 1, 73, 1, 8, 81),
69 _RK3188_APLL_SET_CLKS(1728, 1, 72, 1, 8, 81),
70 _RK3188_APLL_SET_CLKS(1704, 1, 71, 1, 8, 81),
71 _RK3188_APLL_SET_CLKS(1680, 1, 70, 1, 8, 41),
72 _RK3188_APLL_SET_CLKS(1656, 1, 69, 1, 8, 41),
73 _RK3188_APLL_SET_CLKS(1632, 1, 68, 1, 8, 41),
74 _RK3188_APLL_SET_CLKS(1608, 1, 67, 1, 8, 41),
75 _RK3188_APLL_SET_CLKS(1560, 1, 65, 1, 8, 41),
76 _RK3188_APLL_SET_CLKS(1512, 1, 63, 1, 8, 41),
77 _RK3188_APLL_SET_CLKS(1488, 1, 62, 1, 8, 41),
78 _RK3188_APLL_SET_CLKS(1464, 1, 61, 1, 8, 41),
79 _RK3188_APLL_SET_CLKS(1440, 1, 60, 1, 8, 41),
80 _RK3188_APLL_SET_CLKS(1416, 1, 59, 1, 8, 41),
81 _RK3188_APLL_SET_CLKS(1392, 1, 58, 1, 8, 41),
82 _RK3188_APLL_SET_CLKS(1368, 1, 57, 1, 8, 41),
83 _RK3188_APLL_SET_CLKS(1344, 1, 56, 1, 8, 41),
84 _RK3188_APLL_SET_CLKS(1320, 1, 55, 1, 8, 41),
85 _RK3188_APLL_SET_CLKS(1296, 1, 54, 1, 8, 41),
86 _RK3188_APLL_SET_CLKS(1272, 1, 53, 1, 8, 41),
87 _RK3188_APLL_SET_CLKS(1248, 1, 52, 1, 8, 41),
88 _RK3188_APLL_SET_CLKS(1224, 1, 51, 1, 8, 41),
89 _RK3188_APLL_SET_CLKS(1200, 1, 50, 1, 8, 41),
90 _RK3188_APLL_SET_CLKS(1176, 1, 49, 1, 8, 41),
91 _RK3188_APLL_SET_CLKS(1128, 1, 47, 1, 8, 41),
92 _RK3188_APLL_SET_CLKS(1104, 1, 46, 1, 8, 41),
93 _RK3188_APLL_SET_CLKS(1008, 1, 84, 2, 8, 41),
94 _RK3188_APLL_SET_CLKS(912, 1, 76, 2, 8, 41),
95 _RK3188_APLL_SET_CLKS(888, 1, 74, 2, 8, 41),
96 _RK3188_APLL_SET_CLKS(816, 1, 68, 2, 8, 41),
97 _RK3188_APLL_SET_CLKS(792, 1, 66, 2, 8, 41),
98 _RK3188_APLL_SET_CLKS(696, 1, 58, 2, 8, 41),
99 _RK3188_APLL_SET_CLKS(600, 1, 50, 2, 4, 41),
100 _RK3188_APLL_SET_CLKS(552, 1, 92, 4, 4, 41),
101 _RK3188_APLL_SET_CLKS(504, 1, 84, 4, 4, 41),
102 _RK3188_APLL_SET_CLKS(408, 1, 68, 4, 4, 21),
103 _RK3188_APLL_SET_CLKS(312, 1, 52, 4, 2, 21),
104 _RK3188_APLL_SET_CLKS(252, 1, 84, 8, 2, 21),
105 _RK3188_APLL_SET_CLKS(216, 1, 72, 8, 2, 21),
106 _RK3188_APLL_SET_CLKS(126, 1, 84, 16, 2, 11),
107 _RK3188_APLL_SET_CLKS(48, 1, 32, 16, 2, 11),
108 _RK3188_APLL_SET_CLKS(0, 1, 32, 16, 2, 11),
111 static const struct apll_clk_set rk3288_apll_table[] = {
112 // (_mhz, nr, nf, no, l2ram, m0, mp, atclk, pclk_dbg)
113 _RK3288_APLL_SET_CLKS(2208, 1, 92, 1, 2, 2, 4, 4, 4),
114 _RK3288_APLL_SET_CLKS(2184, 1, 91, 1, 2, 2, 4, 4, 4),
115 _RK3288_APLL_SET_CLKS(2160, 1, 90, 1, 2, 2, 4, 4, 4),
116 _RK3288_APLL_SET_CLKS(2136, 1, 89, 1, 2, 2, 4, 4, 4),
117 _RK3288_APLL_SET_CLKS(2112, 1, 88, 1, 2, 2, 4, 4, 4),
118 _RK3288_APLL_SET_CLKS(2088, 1, 87, 1, 2, 2, 4, 4, 4),
119 _RK3288_APLL_SET_CLKS(2064, 1, 86, 1, 2, 2, 4, 4, 4),
120 _RK3288_APLL_SET_CLKS(2040, 1, 85, 1, 2, 2, 4, 4, 4),
121 _RK3288_APLL_SET_CLKS(2016, 1, 84, 1, 2, 2, 4, 4, 4),
122 _RK3288_APLL_SET_CLKS(1992, 1, 83, 1, 2, 2, 4, 4, 4),
123 _RK3288_APLL_SET_CLKS(1968, 1, 82, 1, 2, 2, 4, 4, 4),
124 _RK3288_APLL_SET_CLKS(1944, 1, 81, 1, 2, 2, 4, 4, 4),
125 _RK3288_APLL_SET_CLKS(1920, 1, 80, 1, 2, 2, 4, 4, 4),
126 _RK3288_APLL_SET_CLKS(1896, 1, 79, 1, 2, 2, 4, 4, 4),
127 _RK3288_APLL_SET_CLKS(1872, 1, 78, 1, 2, 2, 4, 4, 4),
128 _RK3288_APLL_SET_CLKS(1848, 1, 77, 1, 2, 2, 4, 4, 4),
129 _RK3288_APLL_SET_CLKS(1824, 1, 76, 1, 2, 2, 4, 4, 4),
130 _RK3288_APLL_SET_CLKS(1800, 1, 75, 1, 2, 2, 4, 4, 4),
131 _RK3288_APLL_SET_CLKS(1776, 1, 74, 1, 2, 2, 4, 4, 4),
132 _RK3288_APLL_SET_CLKS(1752, 1, 73, 1, 2, 2, 4, 4, 4),
133 _RK3288_APLL_SET_CLKS(1728, 1, 72, 1, 2, 2, 4, 4, 4),
134 _RK3288_APLL_SET_CLKS(1704, 1, 71, 1, 2, 2, 4, 4, 4),
135 _RK3288_APLL_SET_CLKS(1680, 1, 70, 1, 2, 2, 4, 4, 4),
136 _RK3288_APLL_SET_CLKS(1656, 1, 69, 1, 2, 2, 4, 4, 4),
137 _RK3288_APLL_SET_CLKS(1632, 1, 68, 1, 2, 2, 4, 4, 4),
138 _RK3288_APLL_SET_CLKS(1608, 1, 67, 1, 2, 2, 4, 4, 4),
139 _RK3288_APLL_SET_CLKS(1560, 1, 65, 1, 2, 2, 4, 4, 4),
140 _RK3288_APLL_SET_CLKS(1512, 1, 63, 1, 2, 2, 4, 4, 4),
141 _RK3288_APLL_SET_CLKS(1488, 1, 62, 1, 2, 2, 4, 4, 4),
142 _RK3288_APLL_SET_CLKS(1464, 1, 61, 1, 2, 2, 4, 4, 4),
143 _RK3288_APLL_SET_CLKS(1440, 1, 60, 1, 2, 2, 4, 4, 4),
144 _RK3288_APLL_SET_CLKS(1416, 1, 59, 1, 2, 2, 4, 4, 4),
145 _RK3288_APLL_SET_CLKS(1392, 1, 58, 1, 2, 2, 4, 4, 4),
146 _RK3288_APLL_SET_CLKS(1368, 1, 57, 1, 2, 2, 4, 4, 4),
147 _RK3288_APLL_SET_CLKS(1344, 1, 56, 1, 2, 2, 4, 4, 4),
148 _RK3288_APLL_SET_CLKS(1320, 1, 55, 1, 2, 2, 4, 4, 4),
149 _RK3288_APLL_SET_CLKS(1296, 1, 54, 1, 2, 2, 4, 4, 4),
150 _RK3288_APLL_SET_CLKS(1272, 1, 53, 1, 2, 2, 4, 4, 4),
151 _RK3288_APLL_SET_CLKS(1248, 1, 52, 1, 2, 2, 4, 4, 4),
152 _RK3288_APLL_SET_CLKS(1224, 1, 51, 1, 2, 2, 4, 4, 4),
153 _RK3288_APLL_SET_CLKS(1200, 1, 50, 1, 2, 2, 4, 4, 4),
154 _RK3288_APLL_SET_CLKS(1176, 1, 49, 1, 2, 2, 4, 4, 4),
155 _RK3288_APLL_SET_CLKS(1128, 1, 47, 1, 2, 2, 4, 4, 4),
156 _RK3288_APLL_SET_CLKS(1104, 1, 46, 1, 2, 2, 4, 4, 4),
157 _RK3288_APLL_SET_CLKS(1008, 1, 84, 2, 2, 2, 4, 4, 4),
158 _RK3288_APLL_SET_CLKS(912, 1, 76, 2, 2, 2, 4, 4, 4),
159 _RK3288_APLL_SET_CLKS(888, 1, 74, 2, 2, 2, 4, 4, 4),
160 _RK3288_APLL_SET_CLKS(816, 1, 68, 2, 2, 2, 4, 4, 4),
161 _RK3288_APLL_SET_CLKS(792, 1, 66, 2, 2, 2, 4, 4, 4),
162 _RK3288_APLL_SET_CLKS(696, 1, 58, 2, 2, 2, 4, 4, 4),
163 _RK3288_APLL_SET_CLKS(672, 1, 56, 2, 2, 2, 4, 4, 4),
164 _RK3288_APLL_SET_CLKS(648, 1, 54, 2, 2, 2, 4, 4, 4),
165 _RK3288_APLL_SET_CLKS(624, 1, 52, 2, 2, 2, 4, 4, 4),
166 _RK3288_APLL_SET_CLKS(600, 1, 50, 2, 2, 2, 4, 4, 4),
167 _RK3288_APLL_SET_CLKS(576, 1, 48, 2, 2, 2, 4, 4, 4),
168 _RK3288_APLL_SET_CLKS(552, 1, 92, 4, 2, 2, 4, 4, 4),
169 _RK3288_APLL_SET_CLKS(528, 1, 88, 4, 2, 2, 4, 4, 4),
170 _RK3288_APLL_SET_CLKS(504, 1, 84, 4, 2, 2, 4, 4, 4),
171 _RK3288_APLL_SET_CLKS(480, 1, 80, 4, 2, 2, 4, 4, 4),
172 _RK3288_APLL_SET_CLKS(456, 1, 76, 4, 2, 2, 4, 4, 4),
173 _RK3288_APLL_SET_CLKS(408, 1, 68, 4, 2, 2, 4, 4, 4),
174 _RK3288_APLL_SET_CLKS(312, 1, 52, 4, 2, 2, 4, 4, 4),
175 _RK3288_APLL_SET_CLKS(252, 1, 84, 8, 2, 2, 4, 4, 4),
176 _RK3288_APLL_SET_CLKS(216, 1, 72, 8, 2, 2, 4, 4, 4),
177 _RK3288_APLL_SET_CLKS(126, 2, 84, 8, 2, 2, 4, 4, 4),
178 _RK3288_APLL_SET_CLKS(48, 2, 32, 8, 2, 2, 4, 4, 4),
179 _RK3288_APLL_SET_CLKS(0, 1, 32, 16, 2, 2, 4, 4, 4),
182 static const struct apll_clk_set rk3036_apll_table[] = {
183 _RK3036_APLL_SET_CLKS(1608, 1, 67, 1, 1, 1, 0, 81),
184 _RK3036_APLL_SET_CLKS(1584, 1, 66, 1, 1, 1, 0, 81),
185 _RK3036_APLL_SET_CLKS(1560, 1, 65, 1, 1, 1, 0, 81),
186 _RK3036_APLL_SET_CLKS(1536, 1, 64, 1, 1, 1, 0, 81),
187 _RK3036_APLL_SET_CLKS(1512, 1, 63, 1, 1, 1, 0, 81),
188 _RK3036_APLL_SET_CLKS(1488, 1, 62, 1, 1, 1, 0, 81),
189 _RK3036_APLL_SET_CLKS(1464, 1, 61, 1, 1, 1, 0, 81),
190 _RK3036_APLL_SET_CLKS(1440, 1, 60, 1, 1, 1, 0, 81),
191 _RK3036_APLL_SET_CLKS(1416, 1, 59, 1, 1, 1, 0, 81),
192 _RK3036_APLL_SET_CLKS(1392, 1, 58, 1, 1, 1, 0, 81),
193 _RK3036_APLL_SET_CLKS(1368, 1, 57, 1, 1, 1, 0, 81),
194 _RK3036_APLL_SET_CLKS(1344, 1, 56, 1, 1, 1, 0, 81),
195 _RK3036_APLL_SET_CLKS(1320, 1, 55, 1, 1, 1, 0, 81),
196 _RK3036_APLL_SET_CLKS(1296, 1, 54, 1, 1, 1, 0, 81),
197 _RK3036_APLL_SET_CLKS(1272, 1, 53, 1, 1, 1, 0, 81),
198 _RK3036_APLL_SET_CLKS(1248, 1, 52, 1, 1, 1, 0, 81),
199 _RK3036_APLL_SET_CLKS(1200, 1, 50, 1, 1, 1, 0, 81),
200 _RK3036_APLL_SET_CLKS(1104, 1, 46, 1, 1, 1, 0, 81),
201 _RK3036_APLL_SET_CLKS(1100, 12, 550, 1, 1, 1, 0, 81),
202 _RK3036_APLL_SET_CLKS(1008, 1, 84, 2, 1, 1, 0, 81),
203 _RK3036_APLL_SET_CLKS(1000, 6, 500, 2, 1, 1, 0, 81),
204 _RK3036_APLL_SET_CLKS(984, 1, 82, 2, 1, 1, 0, 81),
205 _RK3036_APLL_SET_CLKS(960, 1, 80, 2, 1, 1, 0, 81),
206 _RK3036_APLL_SET_CLKS(936, 1, 78, 2, 1, 1, 0, 81),
207 _RK3036_APLL_SET_CLKS(912, 1, 76, 2, 1, 1, 0, 41),
208 _RK3036_APLL_SET_CLKS(900, 4, 300, 2, 1, 1, 0, 41),
209 _RK3036_APLL_SET_CLKS(888, 1, 74, 2, 1, 1, 0, 41),
210 _RK3036_APLL_SET_CLKS(864, 1, 72, 2, 1, 1, 0, 41),
211 _RK3036_APLL_SET_CLKS(840, 1, 70, 2, 1, 1, 0, 41),
212 _RK3036_APLL_SET_CLKS(816, 1, 68, 2, 1, 1, 0, 41),
213 _RK3036_APLL_SET_CLKS(800, 6, 400, 2, 1, 1, 0, 41),
214 _RK3036_APLL_SET_CLKS(700, 6, 350, 2, 1, 1, 0, 41),
215 _RK3036_APLL_SET_CLKS(696, 1, 58, 2, 1, 1, 0, 41),
216 _RK3036_APLL_SET_CLKS(600, 1, 75, 3, 1, 1, 0, 41),
217 _RK3036_APLL_SET_CLKS(504, 1, 63, 3, 1, 1, 0, 41),
218 _RK3036_APLL_SET_CLKS(500, 6, 250, 2, 1, 1, 0, 41),
219 _RK3036_APLL_SET_CLKS(408, 1, 68, 2, 2, 1, 0, 41),
220 _RK3036_APLL_SET_CLKS(312, 1, 52, 2, 2, 1, 0, 41),
221 _RK3036_APLL_SET_CLKS(216, 1, 72, 4, 2, 1, 0, 41),
222 _RK3036_APLL_SET_CLKS(96, 1, 64, 4, 4, 1, 0, 21),
223 _RK3036_APLL_SET_CLKS(0, 1, 0, 1, 1, 1, 0, 21),
226 static const struct pll_clk_set rk3036plus_pll_com_table[] = {
227 _RK3036_PLL_SET_CLKS(1188000, 2, 99, 1, 1, 1, 0),
228 _RK3036_PLL_SET_CLKS(594000, 2, 99, 2, 1, 1, 0),
229 /*_RK3036_PLL_SET_CLKS(297000, 2, 99, 4, 1, 1, 0),*/
232 static const struct pll_clk_set rk312xplus_pll_com_table[] = {
233 /*_RK3036_PLL_SET_CLKS(1064000, 3, 133, 1, 1, 1, 0),*/
234 /*_RK3036_PLL_SET_CLKS(798000, 2, 133, 2, 1, 1, 0),*/
235 _RK3036_PLL_SET_CLKS(594000, 2, 99, 2, 1, 1, 0),
236 _RK3036_PLL_SET_CLKS(500000, 6, 250, 2, 1, 1, 0),
237 _RK3036_PLL_SET_CLKS(400000, 6, 400, 2, 2, 1, 0),
240 static const struct apll_clk_set rk3368_apllb_table[] = {
241 /*(_mhz, nr, nf, no, aclkm, atclk, pclk_dbg)*/
242 _RK3368_APLL_SET_CLKS(1608, 1, 67, 1, 2, 6, 6),
243 _RK3368_APLL_SET_CLKS(1560, 1, 65, 1, 2, 6, 6),
244 _RK3368_APLL_SET_CLKS(1512, 1, 63, 1, 2, 6, 6),
245 _RK3368_APLL_SET_CLKS(1488, 1, 62, 1, 2, 5, 5),
246 _RK3368_APLL_SET_CLKS(1464, 1, 61, 1, 2, 5, 5),
247 _RK3368_APLL_SET_CLKS(1440, 1, 60, 1, 2, 5, 5),
248 _RK3368_APLL_SET_CLKS(1416, 1, 59, 1, 2, 5, 5),
249 _RK3368_APLL_SET_CLKS(1392, 1, 58, 1, 2, 5, 5),
250 _RK3368_APLL_SET_CLKS(1368, 1, 57, 1, 2, 5, 5),
251 _RK3368_APLL_SET_CLKS(1344, 1, 56, 1, 2, 5, 5),
252 _RK3368_APLL_SET_CLKS(1320, 1, 55, 1, 2, 5, 5),
253 _RK3368_APLL_SET_CLKS(1296, 1, 54, 1, 2, 5, 5),
254 _RK3368_APLL_SET_CLKS(1272, 1, 53, 1, 2, 5, 5),
255 _RK3368_APLL_SET_CLKS(1248, 1, 52, 1, 2, 5, 5),
256 _RK3368_APLL_SET_CLKS(1224, 1, 51, 1, 2, 5, 5),
257 _RK3368_APLL_SET_CLKS(1200, 1, 50, 1, 2, 4, 4),
258 _RK3368_APLL_SET_CLKS(1176, 1, 49, 1, 2, 4, 4),
259 _RK3368_APLL_SET_CLKS(1128, 1, 47, 1, 2, 4, 4),
260 _RK3368_APLL_SET_CLKS(1104, 1, 46, 1, 2, 4, 4),
261 _RK3368_APLL_SET_CLKS(1008, 1, 84, 2, 2, 4, 4),
262 _RK3368_APLL_SET_CLKS(912, 1, 76, 2, 2, 4, 4),
263 _RK3368_APLL_SET_CLKS(888, 1, 74, 2, 2, 3, 3),
264 _RK3368_APLL_SET_CLKS(816, 1, 68, 2, 2, 3, 3),
265 _RK3368_APLL_SET_CLKS(792, 1, 66, 2, 2, 3, 3),
266 _RK3368_APLL_SET_CLKS(696, 1, 58, 2, 2, 3, 3),
267 _RK3368_APLL_SET_CLKS(672, 1, 56, 2, 2, 3, 3),
268 _RK3368_APLL_SET_CLKS(648, 1, 54, 2, 2, 3, 3),
269 _RK3368_APLL_SET_CLKS(624, 1, 52, 2, 2, 3, 3),
270 _RK3368_APLL_SET_CLKS(600, 1, 50, 2, 2, 2, 2),
271 _RK3368_APLL_SET_CLKS(576, 1, 48, 2, 2, 2, 2),
272 _RK3368_APLL_SET_CLKS(552, 1, 92, 4, 2, 2, 2),
273 _RK3368_APLL_SET_CLKS(528, 1, 88, 4, 2, 2, 2),
274 _RK3368_APLL_SET_CLKS(504, 1, 84, 4, 2, 2, 2),
275 _RK3368_APLL_SET_CLKS(480, 1, 80, 4, 2, 2, 2),
276 _RK3368_APLL_SET_CLKS(456, 1, 76, 4, 2, 2, 2),
277 _RK3368_APLL_SET_CLKS(408, 1, 68, 4, 2, 2, 2),
278 _RK3368_APLL_SET_CLKS(312, 1, 52, 4, 2, 2, 2),
279 _RK3368_APLL_SET_CLKS(252, 1, 84, 8, 2, 1, 1),
280 _RK3368_APLL_SET_CLKS(216, 1, 72, 8, 2, 1, 1),
281 _RK3368_APLL_SET_CLKS(126, 2, 84, 8, 2, 1, 1),
282 _RK3368_APLL_SET_CLKS(48, 2, 32, 8, 2, 1, 1),
283 _RK3368_APLL_SET_CLKS(0, 1, 32, 16, 2, 1, 1),
286 static const struct apll_clk_set rk3368_aplll_table[] = {
287 /*(_mhz, nr, nf, no, aclkm, atclk, pclk_dbg)*/
288 _RK3368_APLL_SET_CLKS(1608, 1, 67, 1, 2, 7, 7),
289 _RK3368_APLL_SET_CLKS(1560, 1, 65, 1, 2, 7, 7),
290 _RK3368_APLL_SET_CLKS(1512, 1, 63, 1, 2, 7, 7),
291 _RK3368_APLL_SET_CLKS(1488, 1, 62, 1, 2, 6, 6),
292 _RK3368_APLL_SET_CLKS(1464, 1, 61, 1, 2, 6, 6),
293 _RK3368_APLL_SET_CLKS(1440, 1, 60, 1, 2, 6, 6),
294 _RK3368_APLL_SET_CLKS(1416, 1, 59, 1, 2, 6, 6),
295 _RK3368_APLL_SET_CLKS(1392, 1, 58, 1, 2, 6, 6),
296 _RK3368_APLL_SET_CLKS(1368, 1, 57, 1, 2, 6, 6),
297 _RK3368_APLL_SET_CLKS(1344, 1, 56, 1, 2, 6, 6),
298 _RK3368_APLL_SET_CLKS(1320, 1, 55, 1, 2, 6, 6),
299 _RK3368_APLL_SET_CLKS(1296, 1, 54, 1, 2, 6, 6),
300 _RK3368_APLL_SET_CLKS(1272, 1, 53, 1, 2, 6, 6),
301 _RK3368_APLL_SET_CLKS(1248, 1, 52, 1, 2, 5, 5),
302 _RK3368_APLL_SET_CLKS(1224, 1, 51, 1, 2, 5, 5),
303 _RK3368_APLL_SET_CLKS(1200, 1, 50, 1, 2, 5, 5),
304 _RK3368_APLL_SET_CLKS(1176, 1, 49, 1, 2, 5, 5),
305 _RK3368_APLL_SET_CLKS(1128, 1, 47, 1, 2, 5, 5),
306 _RK3368_APLL_SET_CLKS(1104, 1, 46, 1, 2, 5, 5),
307 _RK3368_APLL_SET_CLKS(1008, 1, 84, 2, 2, 5, 5),
308 _RK3368_APLL_SET_CLKS(912, 1, 76, 2, 2, 4, 4),
309 _RK3368_APLL_SET_CLKS(888, 1, 74, 2, 2, 4, 4),
310 _RK3368_APLL_SET_CLKS(816, 1, 68, 2, 2, 4, 4),
311 _RK3368_APLL_SET_CLKS(792, 1, 66, 2, 2, 4, 4),
312 _RK3368_APLL_SET_CLKS(696, 1, 58, 2, 2, 3, 3),
313 _RK3368_APLL_SET_CLKS(672, 1, 56, 2, 2, 3, 3),
314 _RK3368_APLL_SET_CLKS(648, 1, 54, 2, 2, 3, 3),
315 _RK3368_APLL_SET_CLKS(624, 1, 52, 2, 2, 3, 3),
316 _RK3368_APLL_SET_CLKS(600, 1, 50, 2, 2, 3, 3),
317 _RK3368_APLL_SET_CLKS(576, 1, 48, 2, 2, 3, 3),
318 _RK3368_APLL_SET_CLKS(552, 1, 92, 4, 2, 3, 3),
319 _RK3368_APLL_SET_CLKS(528, 1, 88, 4, 2, 3, 3),
320 _RK3368_APLL_SET_CLKS(504, 1, 84, 4, 2, 3, 3),
321 _RK3368_APLL_SET_CLKS(480, 1, 80, 4, 2, 2, 2),
322 _RK3368_APLL_SET_CLKS(456, 1, 76, 4, 2, 2, 2),
323 _RK3368_APLL_SET_CLKS(408, 1, 68, 4, 2, 2, 2),
324 _RK3368_APLL_SET_CLKS(312, 1, 52, 4, 2, 2, 2),
325 _RK3368_APLL_SET_CLKS(252, 1, 84, 8, 2, 2, 2),
326 _RK3368_APLL_SET_CLKS(216, 1, 72, 8, 2, 1, 1),
327 _RK3368_APLL_SET_CLKS(126, 2, 84, 8, 2, 1, 1),
328 _RK3368_APLL_SET_CLKS(48, 2, 32, 8, 2, 1, 1),
329 _RK3368_APLL_SET_CLKS(0, 1, 32, 16, 2, 1, 1),
332 static const struct pll_clk_set rk3368_pll_table_low_jitter[] = {
333 /* _khz, nr, nf, no, nb */
334 _RK3188PLUS_PLL_SET_CLKS_NB(1188000, 1, 99, 2, 1),
335 _RK3188PLUS_PLL_SET_CLKS_NB(400000, 1, 100, 6, 1),
336 _RK3188PLUS_PLL_SET_CLKS( 0, 0, 0, 0),
339 static void pll_wait_lock(struct clk_hw *hw)
341 struct clk_pll *pll = to_clk_pll(hw);
342 int delay = 24000000;
345 if (grf_readl(pll->status_offset) & (1 << pll->status_shift))
351 clk_err("pll %s: can't lock! status_shift=%u\n"
352 "pll_con0=%08x\npll_con1=%08x\n"
353 "pll_con2=%08x\npll_con3=%08x\n",
354 __clk_get_name(hw->clk),
356 cru_readl(pll->reg + RK3188_PLL_CON(0)),
357 cru_readl(pll->reg + RK3188_PLL_CON(1)),
358 cru_readl(pll->reg + RK3188_PLL_CON(2)),
359 cru_readl(pll->reg + RK3188_PLL_CON(3)));
365 static void rk3036_pll_wait_lock(struct clk_hw *hw)
367 struct clk_pll *pll = to_clk_pll(hw);
368 int delay = 24000000;
372 if (cru_readl(pll->status_offset) & (1 << pll->status_shift))
378 clk_err("pll %s: can't lock! status_shift=%u\n"
379 "pll_con0=%08x\npll_con1=%08x\n"
381 __clk_get_name(hw->clk),
383 cru_readl(pll->reg + RK3188_PLL_CON(0)),
384 cru_readl(pll->reg + RK3188_PLL_CON(1)),
385 cru_readl(pll->reg + RK3188_PLL_CON(2)));
392 /* get rate that is most close to target */
393 static const struct apll_clk_set *apll_get_best_set(unsigned long rate,
394 const struct apll_clk_set *table)
396 const struct apll_clk_set *ps, *pt;
400 if (pt->rate == rate) {
405 if ((pt->rate > rate || (rate - pt->rate < ps->rate - rate)))
415 /* get rate that is most close to target */
416 static const struct pll_clk_set *pll_com_get_best_set(unsigned long rate,
417 const struct pll_clk_set *table)
419 const struct pll_clk_set *ps, *pt;
423 if (pt->rate == rate) {
428 if ((pt->rate > rate || (rate - pt->rate < ps->rate - rate)))
438 /* CLK_PLL_3188 type ops */
439 static unsigned long clk_pll_recalc_rate_3188(struct clk_hw *hw,
440 unsigned long parent_rate)
442 struct clk_pll *pll = to_clk_pll(hw);
446 if (_RK3188_PLL_MODE_IS_NORM(pll->mode_offset, pll->mode_shift)) {
447 u32 pll_con0 = cru_readl(pll->reg + RK3188_PLL_CON(0));
448 u32 pll_con1 = cru_readl(pll->reg + RK3188_PLL_CON(1));
450 u64 rate64 = (u64)parent_rate * RK3188_PLL_NF(pll_con1);
452 do_div(rate64, RK3188_PLL_NR(pll_con0));
453 do_div(rate64, RK3188_PLL_NO(pll_con0));
459 clk_debug("pll %s is in slow mode\n", __clk_get_name(hw->clk));
462 clk_debug("pll %s recalc rate =%lu\n", __clk_get_name(hw->clk), rate);
467 static long clk_pll_round_rate_3188(struct clk_hw *hw, unsigned long rate,
468 unsigned long *prate)
470 struct clk *parent = __clk_get_parent(hw->clk);
472 if (parent && (rate==__clk_get_rate(parent))) {
473 clk_debug("pll %s round rate=%lu equal to parent rate\n",
474 __clk_get_name(hw->clk), rate);
478 return (pll_com_get_best_set(rate, rk3188_pll_com_table)->rate);
481 static int _pll_clk_set_rate_3188(struct pll_clk_set *clk_set,
484 struct clk_pll *pll = to_clk_pll(hw);
485 unsigned long flags = 0;
488 clk_debug("%s start!\n", __func__);
491 spin_lock_irqsave(pll->lock, flags);
494 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
496 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
503 cru_writel(clk_set->pllcon0, pll->reg + RK3188_PLL_CON(0));
504 cru_writel(clk_set->pllcon1, pll->reg + RK3188_PLL_CON(1));
509 cru_writel((0x1<<(16+1)), pll->reg + RK3188_PLL_CON(3));
514 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);
517 spin_unlock_irqrestore(pll->lock, flags);
519 clk_debug("pll %s dump reg: con0=0x%08x, con1=0x%08x, mode=0x%08x\n",
520 __clk_get_name(hw->clk),
521 cru_readl(pll->reg + RK3188_PLL_CON(0)),
522 cru_readl(pll->reg + RK3188_PLL_CON(1)),
523 cru_readl(pll->mode_offset));
525 clk_debug("%s end!\n", __func__);
530 static int clk_pll_set_rate_3188(struct clk_hw *hw, unsigned long rate,
531 unsigned long parent_rate)
533 struct clk_pll *pll = to_clk_pll(hw);
534 struct pll_clk_set *clk_set = (struct pll_clk_set *)(rk3188_pll_com_table);
538 if (rate == parent_rate) {
539 clk_debug("pll %s set rate=%lu equal to parent rate\n",
540 __clk_get_name(hw->clk), rate);
541 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
544 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
545 clk_debug("pll %s enter slow mode, set rate OK!\n",
546 __clk_get_name(hw->clk));
550 while(clk_set->rate) {
551 if (clk_set->rate == rate) {
557 if (clk_set->rate == rate) {
558 ret = _pll_clk_set_rate_3188(clk_set, hw);
559 clk_debug("pll %s set rate=%lu OK!\n", __clk_get_name(hw->clk),
562 clk_err("pll %s is no corresponding rate=%lu\n",
563 __clk_get_name(hw->clk), rate);
570 static const struct clk_ops clk_pll_ops_3188 = {
571 .recalc_rate = clk_pll_recalc_rate_3188,
572 .round_rate = clk_pll_round_rate_3188,
573 .set_rate = clk_pll_set_rate_3188,
577 /* CLK_PLL_3188_APLL type ops */
578 static unsigned long clk_pll_recalc_rate_3188_apll(struct clk_hw *hw,
579 unsigned long parent_rate)
581 return clk_pll_recalc_rate_3188(hw, parent_rate);
584 static long clk_pll_round_rate_3188_apll(struct clk_hw *hw, unsigned long rate,
585 unsigned long *prate)
587 struct clk *parent = __clk_get_parent(hw->clk);
589 if (parent && (rate==__clk_get_rate(parent))) {
590 clk_debug("pll %s round rate=%lu equal to parent rate\n",
591 __clk_get_name(hw->clk), rate);
595 return (apll_get_best_set(rate, rk3188_apll_table)->rate);
598 /* 1: use, 0: no use */
599 #define RK3188_USE_ARM_GPLL 1
601 static int clk_pll_set_rate_3188_apll(struct clk_hw *hw, unsigned long rate,
602 unsigned long parent_rate)
604 struct clk_pll *pll = to_clk_pll(hw);
605 struct clk *clk = hw->clk;
606 struct clk *arm_gpll = __clk_lookup("clk_arm_gpll");
607 unsigned long arm_gpll_rate;
608 const struct apll_clk_set *ps;
609 u32 old_aclk_div = 0, new_aclk_div = 0;
615 if (rate == parent_rate) {
616 clk_debug("pll %s set rate=%lu equal to parent rate\n",
617 __clk_get_name(hw->clk), rate);
618 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
621 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
622 clk_debug("pll %s enter slow mode, set rate OK!\n",
623 __clk_get_name(hw->clk));
628 #if !RK3188_USE_ARM_GPLL
632 /* prepare arm_gpll before reparent clk_core to it */
634 clk_err("clk arm_gpll is NULL!\n");
638 /* In rk3188, arm_gpll and cpu_gpll share a same gate,
639 * and aclk_cpu selects cpu_gpll as parent, thus this
640 * gate must keep enabled.
643 if (clk_prepare(arm_gpll)) {
644 clk_err("fail to prepare arm_gpll path\n");
645 clk_unprepare(arm_gpll);
649 if (clk_enable(arm_gpll)) {
650 clk_err("fail to enable arm_gpll path\n");
651 clk_disable(arm_gpll);
652 clk_unprepare(arm_gpll);
657 arm_gpll_rate = __clk_get_rate(arm_gpll);
658 temp_div = DIV_ROUND_UP(arm_gpll_rate, __clk_get_rate(clk));
659 temp_div = (temp_div == 0) ? 1 : temp_div;
660 if (temp_div > RK3188_CORE_CLK_MAX_DIV) {
661 clk_debug("temp_div %d > max_div %d\n", temp_div,
662 RK3188_CORE_CLK_MAX_DIV);
663 clk_debug("can't get rate %lu from arm_gpll rate %lu\n",
664 __clk_get_rate(clk), arm_gpll_rate);
665 //clk_disable(arm_gpll);
666 //clk_unprepare(arm_gpll);
670 local_irq_save(flags);
672 /* firstly set div, then select arm_gpll path */
673 cru_writel(RK3188_CORE_CLK_DIV_W_MSK|RK3188_CORE_CLK_DIV(temp_div),
674 RK3188_CRU_CLKSELS_CON(0));
675 cru_writel(RK3188_CORE_SEL_PLL_W_MSK|RK3188_CORE_SEL_GPLL,
676 RK3188_CRU_CLKSELS_CON(0));
679 //loops_per_jiffy = CLK_LOOPS_RECALC(arm_gpll_rate) / temp_div;
682 local_irq_restore(flags);
684 clk_debug("temp select arm_gpll path, get rate %lu\n",
685 arm_gpll_rate/temp_div);
686 clk_debug("from arm_gpll rate %lu, temp_div %d\n", arm_gpll_rate,
690 ps = apll_get_best_set(rate, rk3188_apll_table);
691 clk_debug("apll will set rate %lu\n", ps->rate);
692 clk_debug("table con:%08x,%08x,%08x, sel:%08x,%08x\n",
693 ps->pllcon0, ps->pllcon1, ps->pllcon2,
694 ps->clksel0, ps->clksel1);
696 local_irq_save(flags);
698 /* If core src don't select gpll, apll need to enter slow mode
703 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
706 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
713 cru_writel(ps->pllcon0, pll->reg + RK3188_PLL_CON(0));
714 cru_writel(ps->pllcon1, pll->reg + RK3188_PLL_CON(1));
718 /* PLL power up and wait for locked */
719 cru_writel((0x1<<(16+1)), pll->reg + RK3188_PLL_CON(3));
722 old_aclk_div = RK3188_GET_CORE_ACLK_VAL(cru_readl(RK3188_CRU_CLKSELS_CON(1)) &
723 RK3188_CORE_ACLK_MSK);
724 new_aclk_div = RK3188_GET_CORE_ACLK_VAL(ps->clksel1 & RK3188_CORE_ACLK_MSK);
726 if (new_aclk_div >= old_aclk_div) {
727 cru_writel(ps->clksel0, RK3188_CRU_CLKSELS_CON(0));
728 cru_writel(ps->clksel1, RK3188_CRU_CLKSELS_CON(1));
731 /* PLL return from slow mode */
734 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);
736 /* reparent to apll, and set div to 1 */
738 cru_writel(RK3188_CORE_SEL_PLL_W_MSK|RK3188_CORE_SEL_APLL,
739 RK3188_CRU_CLKSELS_CON(0));
740 cru_writel(RK3188_CORE_CLK_DIV_W_MSK|RK3188_CORE_CLK_DIV(1),
741 RK3188_CRU_CLKSELS_CON(0));
744 if (old_aclk_div > new_aclk_div) {
745 cru_writel(ps->clksel0, RK3188_CRU_CLKSELS_CON(0));
746 cru_writel(ps->clksel1, RK3188_CRU_CLKSELS_CON(1));
749 //loops_per_jiffy = ps->lpj;
752 local_irq_restore(flags);
756 //clk_disable(arm_gpll);
757 //clk_unprepare(arm_gpll);
760 //clk_debug("apll set loops_per_jiffy =%lu\n", loops_per_jiffy);
762 clk_debug("apll set rate %lu, con(%x,%x,%x,%x), sel(%x,%x)\n",
764 cru_readl(pll->reg + RK3188_PLL_CON(0)),
765 cru_readl(pll->reg + RK3188_PLL_CON(1)),
766 cru_readl(pll->reg + RK3188_PLL_CON(2)),
767 cru_readl(pll->reg + RK3188_PLL_CON(3)),
768 cru_readl(RK3188_CRU_CLKSELS_CON(0)),
769 cru_readl(RK3188_CRU_CLKSELS_CON(1)));
774 static const struct clk_ops clk_pll_ops_3188_apll = {
775 .recalc_rate = clk_pll_recalc_rate_3188_apll,
776 .round_rate = clk_pll_round_rate_3188_apll,
777 .set_rate = clk_pll_set_rate_3188_apll,
781 /* CLK_PLL_3188PLUS type ops */
782 static unsigned long clk_pll_recalc_rate_3188plus(struct clk_hw *hw,
783 unsigned long parent_rate)
785 struct clk_pll *pll = to_clk_pll(hw);
789 if (_RK3188_PLL_MODE_IS_NORM(pll->mode_offset, pll->mode_shift)) {
790 u32 pll_con0 = cru_readl(pll->reg + RK3188_PLL_CON(0));
791 u32 pll_con1 = cru_readl(pll->reg + RK3188_PLL_CON(1));
793 u64 rate64 = (u64)parent_rate * RK3188PLUS_PLL_NF(pll_con1);
795 do_div(rate64, RK3188PLUS_PLL_NR(pll_con0));
796 do_div(rate64, RK3188PLUS_PLL_NO(pll_con0));
802 clk_debug("pll %s is in slow mode\n", __clk_get_name(hw->clk));
805 clk_debug("pll %s recalc rate =%lu\n", __clk_get_name(hw->clk), rate);
810 static long clk_pll_round_rate_3188plus(struct clk_hw *hw, unsigned long rate,
811 unsigned long *prate)
813 struct clk *parent = __clk_get_parent(hw->clk);
815 if (parent && (rate==__clk_get_rate(parent))) {
816 clk_debug("pll %s round rate=%lu equal to parent rate\n",
817 __clk_get_name(hw->clk), rate);
821 return (pll_com_get_best_set(rate, rk3188plus_pll_com_table)->rate);
824 static int _pll_clk_set_rate_3188plus(struct pll_clk_set *clk_set,
827 struct clk_pll *pll = to_clk_pll(hw);
828 unsigned long flags = 0;
831 clk_debug("%s start!\n", __func__);
834 spin_lock_irqsave(pll->lock, flags);
837 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
840 cru_writel(_RK3188PLUS_PLL_RESET_SET(1), pll->reg + RK3188_PLL_CON(3));
842 cru_writel(clk_set->pllcon0, pll->reg + RK3188_PLL_CON(0));
843 cru_writel(clk_set->pllcon1, pll->reg + RK3188_PLL_CON(1));
844 cru_writel(clk_set->pllcon2, pll->reg + RK3188_PLL_CON(2));
849 cru_writel(_RK3188PLUS_PLL_RESET_SET(0), pll->reg + RK3188_PLL_CON(3));
852 udelay(clk_set->rst_dly);
857 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);
860 spin_unlock_irqrestore(pll->lock, flags);
862 clk_debug("pll %s dump reg: con0=0x%08x, con1=0x%08x, mode=0x%08x\n",
863 __clk_get_name(hw->clk),
864 cru_readl(pll->reg + RK3188_PLL_CON(0)),
865 cru_readl(pll->reg + RK3188_PLL_CON(1)),
866 cru_readl(pll->mode_offset));
868 clk_debug("%s end!\n", __func__);
873 static int clk_pll_set_rate_3188plus(struct clk_hw *hw, unsigned long rate,
874 unsigned long parent_rate)
876 //struct clk_pll *pll = to_clk_pll(hw);
877 struct pll_clk_set *clk_set = (struct pll_clk_set *)(rk3188plus_pll_com_table);
881 if (rate == parent_rate) {
882 clk_debug("pll %s set rate=%lu equal to parent rate\n",
883 __clk_get_name(hw->clk), rate);
884 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
887 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
888 clk_debug("pll %s enter slow mode, set rate OK!\n",
889 __clk_get_name(hw->clk));
894 while(clk_set->rate) {
895 if (clk_set->rate == rate) {
901 if (cpu_is_rk3288() && ((rate == 297*MHZ) || (rate == 594*MHZ))) {
902 if((strncmp(__clk_get_name(hw->clk), "clk_gpll",
903 strlen("clk_gpll")) == 0)) {
905 printk("rk3288 set GPLL BW 20 for HDMI!\n");
906 clk_set->pllcon2 = RK3188_PLL_CLK_BWADJ_SET(20);
910 if (clk_set->rate == rate) {
911 ret = _pll_clk_set_rate_3188plus(clk_set, hw);
912 clk_debug("pll %s set rate=%lu OK!\n", __clk_get_name(hw->clk),
915 clk_err("pll %s is no corresponding rate=%lu\n",
916 __clk_get_name(hw->clk), rate);
923 static int clk_pll_is_enabled_3188plus(struct clk_hw *hw)
926 struct clk_pll *pll = to_clk_pll(hw);
930 spin_lock_irqsave(pll->lock, flags);
932 if (_RK3188_PLL_MODE_IS_NORM(pll->mode_offset, pll->mode_shift))
938 spin_unlock_irqrestore(pll->lock, flags);
943 static int clk_pll_enable_3188plus(struct clk_hw *hw)
945 struct clk_pll *pll = to_clk_pll(hw);
947 unsigned long rst_dly;
950 clk_debug("%s enter\n", __func__);
952 if (clk_pll_is_enabled_3188plus(hw)) {
953 clk_debug("pll has been enabled\n");
958 spin_lock_irqsave(pll->lock, flags);
961 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
964 cru_writel(_RK3188PLUS_PLL_POWERDOWN_SET(0), pll->reg + RK3188_PLL_CON(3));
967 cru_writel(_RK3188PLUS_PLL_RESET_SET(1), pll->reg + RK3188_PLL_CON(3));
969 //cru_writel(clk_set->pllcon0, pll->reg + RK3188_PLL_CON(0));
970 //cru_writel(clk_set->pllcon1, pll->reg + RK3188_PLL_CON(1));
971 //cru_writel(clk_set->pllcon2, pll->reg + RK3188_PLL_CON(2));
976 cru_writel(_RK3188PLUS_PLL_RESET_SET(0), pll->reg + RK3188_PLL_CON(3));
979 nr = RK3188PLUS_PLL_NR(cru_readl(pll->reg + RK3188_PLL_CON(0)));
980 rst_dly = ((nr*500)/24+1);
986 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);
989 spin_unlock_irqrestore(pll->lock, flags);
991 clk_debug("pll %s dump reg:\n con0=0x%08x,\n con1=0x%08x,\n con2=0x%08x,\n"
992 "con3=0x%08x,\n mode=0x%08x\n",
993 __clk_get_name(hw->clk),
994 cru_readl(pll->reg + RK3188_PLL_CON(0)),
995 cru_readl(pll->reg + RK3188_PLL_CON(1)),
996 cru_readl(pll->reg + RK3188_PLL_CON(2)),
997 cru_readl(pll->reg + RK3188_PLL_CON(3)),
998 cru_readl(pll->mode_offset));
1003 static void clk_pll_disable_3188plus(struct clk_hw *hw)
1005 struct clk_pll *pll = to_clk_pll(hw);
1006 unsigned long flags;
1008 clk_debug("%s enter\n", __func__);
1011 spin_lock_irqsave(pll->lock, flags);
1014 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
1017 cru_writel(_RK3188PLUS_PLL_POWERDOWN_SET(1), pll->reg + RK3188_PLL_CON(3));
1020 spin_unlock_irqrestore(pll->lock, flags);
1023 static const struct clk_ops clk_pll_ops_3188plus = {
1024 .recalc_rate = clk_pll_recalc_rate_3188plus,
1025 .round_rate = clk_pll_round_rate_3188plus,
1026 .set_rate = clk_pll_set_rate_3188plus,
1027 .enable = clk_pll_enable_3188plus,
1028 .disable = clk_pll_disable_3188plus,
1029 .is_enabled = clk_pll_is_enabled_3188plus,
1032 /* CLK_PLL_3188PLUS_AUTO type ops */
1033 #define PLL_FREF_MIN (269*KHZ)
1034 #define PLL_FREF_MAX (2200*MHZ)
1036 #define PLL_FVCO_MIN (440*MHZ)
1037 #define PLL_FVCO_MAX (2200*MHZ)
1039 #define PLL_FOUT_MIN (27500*KHZ)
1040 #define PLL_FOUT_MAX (2200*MHZ)
1042 #define PLL_NF_MAX (4096)
1043 #define PLL_NR_MAX (64)
1044 #define PLL_NO_MAX (16)
1046 static u32 clk_gcd(u32 numerator, u32 denominator)
1050 if (!numerator || !denominator)
1052 if (numerator > denominator) {
1069 static int pll_clk_get_best_set(unsigned long fin_hz, unsigned long fout_hz,
1070 u32 *best_nr, u32 *best_nf, u32 *best_no)
1072 u32 nr, nf, no, nonr;
1073 u32 nr_out, nf_out, no_out;
1077 u64 fref, fvco, fout;
1080 nr_out = PLL_NR_MAX + 1;
1083 if (!fin_hz || !fout_hz || fout_hz == fin_hz)
1085 gcd_val = clk_gcd(fin_hz, fout_hz);
1087 YFfenzi = fout_hz / gcd_val;
1088 YFfenmu = fin_hz / gcd_val;
1093 if (nf > PLL_NF_MAX || nonr > (PLL_NO_MAX * PLL_NR_MAX))
1096 for (no = 1; no <= PLL_NO_MAX; no++) {
1097 if (!(no == 1 || !(no % 2)))
1104 if (nr > PLL_NR_MAX)
1108 if (fref < PLL_FREF_MIN || fref > PLL_FREF_MAX)
1112 if (fvco < PLL_FVCO_MIN || fvco > PLL_FVCO_MAX)
1116 if (fout < PLL_FOUT_MIN || fout > PLL_FOUT_MAX)
1119 /* select the best from all available PLL settings */
1120 if ((no > no_out) || ((no == no_out) && (nr < nr_out))) {
1128 /* output the best PLL setting */
1129 if ((nr_out <= PLL_NR_MAX) && (no_out > 0)) {
1130 if (best_nr && best_nf && best_no) {
1141 static unsigned long clk_pll_recalc_rate_3188plus_auto(struct clk_hw *hw,
1142 unsigned long parent_rate)
1144 return clk_pll_recalc_rate_3188plus(hw, parent_rate);
1147 static long clk_pll_round_rate_3188plus_auto(struct clk_hw *hw, unsigned long rate,
1148 unsigned long *prate)
1152 for(best=rate; best>0; best--){
1153 if(!pll_clk_get_best_set(*prate, best, NULL, NULL, NULL))
1160 static int clk_pll_set_rate_3188plus_auto(struct clk_hw *hw, unsigned long rate,
1161 unsigned long parent_rate)
1165 struct pll_clk_set clk_set;
1169 best = clk_pll_round_rate_3188plus_auto(hw, rate, &parent_rate);
1174 pll_clk_get_best_set(parent_rate, best, &nr, &nf, &no);
1176 /* prepare clk_set */
1177 clk_set.rate = best;
1178 clk_set.pllcon0 = RK3188PLUS_PLL_CLKR_SET(nr)|RK3188PLUS_PLL_CLKOD_SET(no);
1179 clk_set.pllcon1 = RK3188PLUS_PLL_CLKF_SET(nf);
1180 clk_set.pllcon2 = RK3188PLUS_PLL_CLK_BWADJ_SET(nf >> 1);
1181 clk_set.rst_dly = ((nr*500)/24+1);
1183 ret = _pll_clk_set_rate_3188plus(&clk_set, hw);
1184 clk_debug("pll %s set rate=%lu OK!\n", __clk_get_name(hw->clk), best);
1190 static const struct clk_ops clk_pll_ops_3188plus_auto = {
1191 .recalc_rate = clk_pll_recalc_rate_3188plus_auto,
1192 .round_rate = clk_pll_round_rate_3188plus_auto,
1193 .set_rate = clk_pll_set_rate_3188plus_auto,
1194 .enable = clk_pll_enable_3188plus,
1195 .disable = clk_pll_disable_3188plus,
1196 .is_enabled = clk_pll_is_enabled_3188plus,
1199 static long clk_pll_round_rate_3368_low_jitter(struct clk_hw *hw,
1201 unsigned long *prate)
1204 struct pll_clk_set *p_clk_set;
1206 p_clk_set = (struct pll_clk_set *)(rk3368_pll_table_low_jitter);
1208 while (p_clk_set->rate) {
1209 if (p_clk_set->rate == rate)
1214 if (p_clk_set->rate == rate) {
1215 clk_debug("get rate from table\n");
1219 for (best = rate; best > 0; best--) {
1220 if (!pll_clk_get_best_set(*prate, best, NULL, NULL, NULL))
1224 clk_err("%s: can't round rate %lu\n", __func__, rate);
1229 static int clk_pll_set_rate_3368_low_jitter(struct clk_hw *hw,
1231 unsigned long parent_rate)
1235 struct pll_clk_set clk_set, *p_clk_set;
1238 p_clk_set = (struct pll_clk_set *)(rk3368_pll_table_low_jitter);
1240 while (p_clk_set->rate) {
1241 if (p_clk_set->rate == rate)
1246 if (p_clk_set->rate == rate) {
1247 clk_debug("get rate from table\n");
1251 best = clk_pll_round_rate_3188plus_auto(hw, rate, &parent_rate);
1256 pll_clk_get_best_set(parent_rate, best, &nr, &nf, &no);
1258 /* prepare clk_set */
1259 clk_set.rate = best;
1260 clk_set.pllcon0 = RK3188PLUS_PLL_CLKR_SET(nr)|RK3188PLUS_PLL_CLKOD_SET(no);
1261 clk_set.pllcon1 = RK3188PLUS_PLL_CLKF_SET(nf);
1262 clk_set.pllcon2 = RK3188PLUS_PLL_CLK_BWADJ_SET(nf >> 1);
1263 clk_set.rst_dly = ((nr*500)/24+1);
1265 p_clk_set = &clk_set;
1268 ret = _pll_clk_set_rate_3188plus(p_clk_set, hw);
1269 clk_debug("pll %s set rate=%lu OK!\n", __clk_get_name(hw->clk),
1275 static const struct clk_ops clk_pll_ops_3368_low_jitter = {
1276 .recalc_rate = clk_pll_recalc_rate_3188plus_auto,
1277 .round_rate = clk_pll_round_rate_3368_low_jitter,
1278 .set_rate = clk_pll_set_rate_3368_low_jitter,
1279 .enable = clk_pll_enable_3188plus,
1280 .disable = clk_pll_disable_3188plus,
1281 .is_enabled = clk_pll_is_enabled_3188plus,
1284 /* CLK_PLL_3188PLUS_APLL type ops */
1285 static unsigned long clk_pll_recalc_rate_3188plus_apll(struct clk_hw *hw,
1286 unsigned long parent_rate)
1288 return clk_pll_recalc_rate_3188plus(hw, parent_rate);
1291 static long clk_pll_round_rate_3188plus_apll(struct clk_hw *hw, unsigned long rate,
1292 unsigned long *prate)
1294 return clk_pll_round_rate_3188_apll(hw, rate, prate);
1297 /* 1: use, 0: no use */
1298 #define RK3188PLUS_USE_ARM_GPLL 1
1300 static int clk_pll_set_rate_3188plus_apll(struct clk_hw *hw, unsigned long rate,
1301 unsigned long parent_rate)
1303 struct clk_pll *pll = to_clk_pll(hw);
1304 struct clk *clk = hw->clk;
1305 struct clk *arm_gpll = __clk_lookup("clk_arm_gpll");
1306 unsigned long arm_gpll_rate;
1307 const struct apll_clk_set *ps;
1308 u32 old_aclk_div = 0, new_aclk_div = 0;
1310 unsigned long flags;
1314 if (rate == parent_rate) {
1315 clk_debug("pll %s set rate=%lu equal to parent rate\n",
1316 __clk_get_name(hw->clk), rate);
1317 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
1319 /* pll power down */
1320 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
1321 clk_debug("pll %s enter slow mode, set rate OK!\n",
1322 __clk_get_name(hw->clk));
1328 #if !RK3188PLUS_USE_ARM_GPLL
1332 /* prepare arm_gpll before reparent clk_core to it */
1334 clk_err("clk arm_gpll is NULL!\n");
1338 /* In rk3188plus, arm_gpll and cpu_gpll share a same gate,
1339 * and aclk_cpu selects cpu_gpll as parent, thus this
1340 * gate must keep enabled.
1343 if (clk_prepare(arm_gpll)) {
1344 clk_err("fail to prepare arm_gpll path\n");
1345 clk_unprepare(arm_gpll);
1349 if (clk_enable(arm_gpll)) {
1350 clk_err("fail to enable arm_gpll path\n");
1351 clk_disable(arm_gpll);
1352 clk_unprepare(arm_gpll);
1357 arm_gpll_rate = __clk_get_rate(arm_gpll);
1358 temp_div = DIV_ROUND_UP(arm_gpll_rate, __clk_get_rate(clk));
1359 temp_div = (temp_div == 0) ? 1 : temp_div;
1360 if (temp_div > RK3188_CORE_CLK_MAX_DIV) {
1361 clk_debug("temp_div %d > max_div %d\n", temp_div,
1362 RK3188_CORE_CLK_MAX_DIV);
1363 clk_debug("can't get rate %lu from arm_gpll rate %lu\n",
1364 __clk_get_rate(clk), arm_gpll_rate);
1365 //clk_disable(arm_gpll);
1366 //clk_unprepare(arm_gpll);
1370 local_irq_save(flags);
1372 /* firstly set div, then select arm_gpll path */
1373 cru_writel(RK3188_CORE_CLK_DIV_W_MSK|RK3188_CORE_CLK_DIV(temp_div),
1374 RK3188_CRU_CLKSELS_CON(0));
1375 cru_writel(RK3188_CORE_SEL_PLL_W_MSK|RK3188_CORE_SEL_GPLL,
1376 RK3188_CRU_CLKSELS_CON(0));
1379 //loops_per_jiffy = CLK_LOOPS_RECALC(arm_gpll_rate) / temp_div;
1382 local_irq_restore(flags);
1384 clk_debug("temp select arm_gpll path, get rate %lu\n",
1385 arm_gpll_rate/temp_div);
1386 clk_debug("from arm_gpll rate %lu, temp_div %d\n", arm_gpll_rate,
1390 ps = apll_get_best_set(rate, rk3188_apll_table);
1391 clk_debug("apll will set rate %lu\n", ps->rate);
1392 clk_debug("table con:%08x,%08x,%08x, sel:%08x,%08x\n",
1393 ps->pllcon0, ps->pllcon1, ps->pllcon2,
1394 ps->clksel0, ps->clksel1);
1396 local_irq_save(flags);
1398 /* If core src don't select gpll, apll need to enter slow mode
1403 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
1405 /* PLL enter rest */
1406 cru_writel(_RK3188PLUS_PLL_RESET_SET(1), pll->reg + RK3188_PLL_CON(3));
1408 cru_writel(ps->pllcon0, pll->reg + RK3188_PLL_CON(0));
1409 cru_writel(ps->pllcon1, pll->reg + RK3188_PLL_CON(1));
1410 cru_writel(ps->pllcon2, pll->reg + RK3188_PLL_CON(2));
1414 /* return from rest */
1415 cru_writel(_RK3188PLUS_PLL_RESET_SET(0), pll->reg + RK3188_PLL_CON(3));
1418 udelay(ps->rst_dly);
1421 old_aclk_div = RK3188_GET_CORE_ACLK_VAL(cru_readl(RK3188_CRU_CLKSELS_CON(1)) &
1422 RK3188_CORE_ACLK_MSK);
1423 new_aclk_div = RK3188_GET_CORE_ACLK_VAL(ps->clksel1 & RK3188_CORE_ACLK_MSK);
1425 if (new_aclk_div >= old_aclk_div) {
1426 cru_writel(ps->clksel0, RK3188_CRU_CLKSELS_CON(0));
1427 cru_writel(ps->clksel1, RK3188_CRU_CLKSELS_CON(1));
1430 /* PLL return from slow mode */
1433 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);
1435 /* reparent to apll, and set div to 1 */
1437 cru_writel(RK3188_CORE_SEL_PLL_W_MSK|RK3188_CORE_SEL_APLL,
1438 RK3188_CRU_CLKSELS_CON(0));
1439 cru_writel(RK3188_CORE_CLK_DIV_W_MSK|RK3188_CORE_CLK_DIV(1),
1440 RK3188_CRU_CLKSELS_CON(0));
1443 if (old_aclk_div > new_aclk_div) {
1444 cru_writel(ps->clksel0, RK3188_CRU_CLKSELS_CON(0));
1445 cru_writel(ps->clksel1, RK3188_CRU_CLKSELS_CON(1));
1448 //loops_per_jiffy = ps->lpj;
1451 local_irq_restore(flags);
1455 //clk_disable(arm_gpll);
1456 //clk_unprepare(arm_gpll);
1459 //clk_debug("apll set loops_per_jiffy =%lu\n", loops_per_jiffy);
1461 clk_debug("apll set rate %lu, con(%x,%x,%x,%x), sel(%x,%x)\n",
1463 cru_readl(pll->reg + RK3188_PLL_CON(0)),
1464 cru_readl(pll->reg + RK3188_PLL_CON(1)),
1465 cru_readl(pll->reg + RK3188_PLL_CON(2)),
1466 cru_readl(pll->reg + RK3188_PLL_CON(3)),
1467 cru_readl(RK3188_CRU_CLKSELS_CON(0)),
1468 cru_readl(RK3188_CRU_CLKSELS_CON(1)));
1473 static const struct clk_ops clk_pll_ops_3188plus_apll = {
1474 .recalc_rate = clk_pll_recalc_rate_3188plus_apll,
1475 .round_rate = clk_pll_round_rate_3188plus_apll,
1476 .set_rate = clk_pll_set_rate_3188plus_apll,
1479 /* CLK_PLL_3288_APLL type ops */
1480 static unsigned long clk_pll_recalc_rate_3288_apll(struct clk_hw *hw,
1481 unsigned long parent_rate)
1483 return clk_pll_recalc_rate_3188plus(hw, parent_rate);
1486 static long clk_pll_round_rate_3288_apll(struct clk_hw *hw, unsigned long rate,
1487 unsigned long *prate)
1489 struct clk *parent = __clk_get_parent(hw->clk);
1491 if (parent && (rate==__clk_get_rate(parent))) {
1492 clk_debug("pll %s round rate=%lu equal to parent rate\n",
1493 __clk_get_name(hw->clk), rate);
1497 return (apll_get_best_set(rate, rk3288_apll_table)->rate);
1500 /* 1: use, 0: no use */
1501 #define RK3288_USE_ARM_GPLL 1
1503 static int clk_pll_set_rate_3288_apll(struct clk_hw *hw, unsigned long rate,
1504 unsigned long parent_rate)
1506 struct clk_pll *pll = to_clk_pll(hw);
1507 struct clk *clk = hw->clk;
1508 struct clk *arm_gpll = __clk_lookup("clk_arm_gpll");
1509 unsigned long arm_gpll_rate, temp_rate, old_rate;
1510 const struct apll_clk_set *ps;
1511 // u32 old_aclk_div = 0, new_aclk_div = 0;
1513 unsigned long flags;
1518 if (rate == parent_rate) {
1519 clk_debug("pll %s set rate=%lu equal to parent rate\n",
1520 __clk_get_name(hw->clk), rate);
1521 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
1523 /* pll power down */
1524 cru_writel((0x1 << (16+1)) | (0x1<<1), pll->reg + RK3188_PLL_CON(3));
1525 clk_debug("pll %s enter slow mode, set rate OK!\n",
1526 __clk_get_name(hw->clk));
1531 #if !RK3288_USE_ARM_GPLL
1535 /* prepare arm_gpll before reparent clk_core to it */
1537 clk_err("clk arm_gpll is NULL!\n");
1541 arm_gpll_rate = __clk_get_rate(arm_gpll);
1542 old_rate = __clk_get_rate(clk);
1544 temp_rate = (old_rate > rate) ? old_rate : rate;
1545 temp_div = DIV_ROUND_UP(arm_gpll_rate, temp_rate);
1547 if (temp_div > RK3288_CORE_CLK_MAX_DIV) {
1548 clk_debug("temp_div %d > max_div %d\n", temp_div,
1549 RK3288_CORE_CLK_MAX_DIV);
1550 clk_debug("can't get rate %lu from arm_gpll rate %lu\n",
1551 __clk_get_rate(clk), arm_gpll_rate);
1556 if (clk_prepare(arm_gpll)) {
1557 clk_err("fail to prepare arm_gpll path\n");
1558 clk_unprepare(arm_gpll);
1562 if (clk_enable(arm_gpll)) {
1563 clk_err("fail to enable arm_gpll path\n");
1564 clk_disable(arm_gpll);
1565 clk_unprepare(arm_gpll);
1570 local_irq_save(flags);
1573 if (temp_div == 1) {
1574 /* when old_rate/2 < (old_rate-arm_gpll_rate),
1575 we can set div to make rate change more gently */
1576 if (old_rate > (2*arm_gpll_rate)) {
1577 cru_writel(RK3288_CORE_CLK_DIV(2), RK3288_CRU_CLKSELS_CON(0));
1579 cru_writel(RK3288_CORE_CLK_DIV(3), RK3288_CRU_CLKSELS_CON(0));
1581 cru_writel(RK3288_CORE_SEL_PLL_W_MSK|RK3288_CORE_SEL_GPLL,
1582 RK3288_CRU_CLKSELS_CON(0));
1584 cru_writel(RK3288_CORE_CLK_DIV(2), RK3288_CRU_CLKSELS_CON(0));
1586 cru_writel(RK3288_CORE_CLK_DIV(1), RK3288_CRU_CLKSELS_CON(0));
1588 cru_writel(RK3288_CORE_SEL_PLL_W_MSK|RK3288_CORE_SEL_GPLL,
1589 RK3288_CRU_CLKSELS_CON(0));
1592 cru_writel(RK3288_CORE_CLK_DIV(temp_div), RK3288_CRU_CLKSELS_CON(0));
1593 cru_writel(RK3288_CORE_SEL_PLL_W_MSK|RK3288_CORE_SEL_GPLL,
1594 RK3288_CRU_CLKSELS_CON(0));
1598 //loops_per_jiffy = CLK_LOOPS_RECALC(arm_gpll_rate) / temp_div;
1601 local_irq_restore(flags);
1603 clk_debug("temp select arm_gpll path, get rate %lu\n",
1604 arm_gpll_rate/temp_div);
1605 clk_debug("from arm_gpll rate %lu, temp_div %d\n", arm_gpll_rate,
1609 ps = apll_get_best_set(rate, rk3288_apll_table);
1610 clk_debug("apll will set rate %lu\n", ps->rate);
1611 clk_debug("table con:%08x,%08x,%08x, sel:%08x,%08x\n",
1612 ps->pllcon0, ps->pllcon1, ps->pllcon2,
1613 ps->clksel0, ps->clksel1);
1615 local_irq_save(flags);
1617 /* If core src don't select gpll, apll need to enter slow mode
1622 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);
1624 /* PLL enter rest */
1625 cru_writel(_RK3188PLUS_PLL_RESET_SET(1), pll->reg + RK3188_PLL_CON(3));
1627 cru_writel(ps->pllcon0, pll->reg + RK3188_PLL_CON(0));
1628 cru_writel(ps->pllcon1, pll->reg + RK3188_PLL_CON(1));
1629 cru_writel(ps->pllcon2, pll->reg + RK3188_PLL_CON(2));
1633 /* return from rest */
1634 cru_writel(_RK3188PLUS_PLL_RESET_SET(0), pll->reg + RK3188_PLL_CON(3));
1637 udelay(ps->rst_dly);
1640 if (rate >= __clk_get_rate(hw->clk)) {
1641 cru_writel(ps->clksel0, RK3288_CRU_CLKSELS_CON(0));
1642 cru_writel(ps->clksel1, RK3288_CRU_CLKSELS_CON(37));
1645 /* PLL return from slow mode */
1648 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);
1650 /* reparent to apll, and set div to 1 */
1652 if (temp_div == 1) {
1653 /* when rate/2 < (rate-arm_gpll_rate),
1654 we can set div to make rate change more gently */
1655 if (rate > (2*arm_gpll_rate)) {
1656 cru_writel(RK3288_CORE_CLK_DIV(2), RK3288_CRU_CLKSELS_CON(0));
1658 cru_writel(RK3288_CORE_CLK_DIV(3), RK3288_CRU_CLKSELS_CON(0));
1660 cru_writel(RK3288_CORE_SEL_PLL_W_MSK|RK3288_CORE_SEL_APLL,
1661 RK3288_CRU_CLKSELS_CON(0));
1663 cru_writel(RK3288_CORE_CLK_DIV(2), RK3288_CRU_CLKSELS_CON(0));
1665 cru_writel(RK3288_CORE_CLK_DIV(1), RK3288_CRU_CLKSELS_CON(0));
1667 cru_writel(RK3288_CORE_SEL_PLL_W_MSK|RK3288_CORE_SEL_APLL,
1668 RK3288_CRU_CLKSELS_CON(0));
1671 cru_writel(RK3288_CORE_SEL_PLL_W_MSK|RK3288_CORE_SEL_APLL,
1672 RK3288_CRU_CLKSELS_CON(0));
1673 cru_writel(RK3288_CORE_CLK_DIV(1), RK3288_CRU_CLKSELS_CON(0));
1677 if (rate < __clk_get_rate(hw->clk)) {
1678 cru_writel(ps->clksel0, RK3288_CRU_CLKSELS_CON(0));
1679 cru_writel(ps->clksel1, RK3288_CRU_CLKSELS_CON(37));
1682 //loops_per_jiffy = ps->lpj;
1685 local_irq_restore(flags);
1689 //clk_disable(arm_gpll);
1690 //clk_unprepare(arm_gpll);
1693 //clk_debug("apll set loops_per_jiffy =%lu\n", loops_per_jiffy);
1695 clk_debug("apll set rate %lu, con(%x,%x,%x,%x), sel(%x,%x)\n",
1697 cru_readl(pll->reg + RK3188_PLL_CON(0)),
1698 cru_readl(pll->reg + RK3188_PLL_CON(1)),
1699 cru_readl(pll->reg + RK3188_PLL_CON(2)),
1700 cru_readl(pll->reg + RK3188_PLL_CON(3)),
1701 cru_readl(RK3288_CRU_CLKSELS_CON(0)),
1702 cru_readl(RK3288_CRU_CLKSELS_CON(1)));
1708 static const struct clk_ops clk_pll_ops_3288_apll = {
1709 .recalc_rate = clk_pll_recalc_rate_3288_apll,
1710 .round_rate = clk_pll_round_rate_3288_apll,
1711 .set_rate = clk_pll_set_rate_3288_apll,
1714 /* CLK_PLL_3036_APLL type ops */
1716 static unsigned long rk3036_pll_clk_recalc(struct clk_hw *hw,
1717 unsigned long parent_rate)
1719 struct clk_pll *pll = to_clk_pll(hw);
1721 unsigned int dsmp = 0;
1722 u64 rate64 = 0, frac_rate64 = 0;
1724 dsmp = RK3036_PLL_GET_DSMPD(cru_readl(pll->reg + RK3188_PLL_CON(1)));
1726 if (_RK3188_PLL_MODE_IS_NORM(pll->mode_offset, pll->mode_shift)) {
1727 u32 pll_con0 = cru_readl(pll->reg + RK3188_PLL_CON(0));
1728 u32 pll_con1 = cru_readl(pll->reg + RK3188_PLL_CON(1));
1729 u32 pll_con2 = cru_readl(pll->reg + RK3188_PLL_CON(2));
1731 rate64 = (u64)parent_rate * RK3036_PLL_GET_FBDIV(pll_con0);
1732 do_div(rate64, RK3036_PLL_GET_REFDIV(pll_con1));
1734 if (FRAC_MODE == dsmp) {
1736 frac_rate64 = (u64)parent_rate
1737 * RK3036_PLL_GET_FRAC(pll_con2);
1738 do_div(frac_rate64, RK3036_PLL_GET_REFDIV(pll_con1));
1739 rate64 += frac_rate64 >> 24;
1740 clk_debug("%s frac_rate=%llu(%08x/2^24) by pass mode\n",
1741 __func__, frac_rate64 >> 24,
1742 RK3036_PLL_GET_FRAC(pll_con2));
1744 do_div(rate64, RK3036_PLL_GET_POSTDIV1(pll_con0));
1745 do_div(rate64, RK3036_PLL_GET_POSTDIV2(pll_con1));
1750 clk_debug("pll_clk_recalc rate=%lu by pass mode\n", rate);
1755 static unsigned long clk_pll_recalc_rate_3036_apll(struct clk_hw *hw,
1756 unsigned long parent_rate)
1758 return rk3036_pll_clk_recalc(hw, parent_rate);
1761 static long clk_pll_round_rate_3036_apll(struct clk_hw *hw, unsigned long rate,
1762 unsigned long *prate)
1764 struct clk *parent = __clk_get_parent(hw->clk);
1766 if (parent && (rate == __clk_get_rate(parent))) {
1767 clk_debug("pll %s round rate=%lu equal to parent rate\n",
1768 __clk_get_name(hw->clk), rate);
1772 return (apll_get_best_set(rate, rk3036_apll_table)->rate);
1775 static int rk3036_pll_clk_set_rate(struct pll_clk_set *clk_set,
1778 struct clk_pll *pll = to_clk_pll(hw);
1781 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
1784 cru_writel(clk_set->pllcon0, pll->reg + RK3188_PLL_CON(0));
1785 cru_writel(clk_set->pllcon1, pll->reg + RK3188_PLL_CON(1));
1786 cru_writel(clk_set->pllcon2, pll->reg + RK3188_PLL_CON(2));
1788 clk_debug("pllcon0%08x\n", cru_readl(pll->reg + RK3188_PLL_CON(0)));
1789 clk_debug("pllcon1%08x\n", cru_readl(pll->reg + RK3188_PLL_CON(1)));
1790 clk_debug("pllcon2%08x\n", cru_readl(pll->reg + RK3188_PLL_CON(2)));
1791 /*wating lock state*/
1792 udelay(clk_set->rst_dly);
1793 rk3036_pll_wait_lock(hw);
1795 /*return form slow*/
1796 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift),
1802 #define MIN_FOUTVCO_FREQ (400 * 1000 * 1000)
1803 #define MAX_FOUTVCO_FREQ (1600 * 1000 * 1000)
1804 static int rk3036_pll_clk_set_postdiv(unsigned long fout_hz,
1805 u32 *postdiv1, u32 *postdiv2, u32 *foutvco)
1807 if (fout_hz < MIN_FOUTVCO_FREQ) {
1808 for (*postdiv1 = 1; *postdiv1 <= 7; (*postdiv1)++)
1809 for (*postdiv2 = 1; *postdiv2 <= 7; (*postdiv2)++) {
1810 if (fout_hz * (*postdiv1) * (*postdiv2)
1811 >= MIN_FOUTVCO_FREQ && fout_hz
1812 * (*postdiv1) * (*postdiv2)
1813 <= MAX_FOUTVCO_FREQ) {
1814 *foutvco = fout_hz * (*postdiv1)
1819 clk_debug("CANNOT FINE postdiv1/2 to make fout in range from 400M to 1600M, fout = %lu\n",
1828 static int rk3036_pll_clk_get_set(unsigned long fin_hz, unsigned long fout_hz,
1829 u32 *refdiv, u32 *fbdiv, u32 *postdiv1,
1830 u32 *postdiv2, u32 *frac)
1832 /* FIXME set postdiv1/2 always 1*/
1833 u32 gcd, foutvco = fout_hz;
1834 u64 fin_64, frac_64;
1837 if (!fin_hz || !fout_hz || fout_hz == fin_hz)
1840 rk3036_pll_clk_set_postdiv(fout_hz, postdiv1, postdiv2, &foutvco);
1841 if (fin_hz / MHZ * MHZ == fin_hz && fout_hz / MHZ * MHZ == fout_hz) {
1844 gcd = clk_gcd(fin_hz, foutvco);
1845 *refdiv = fin_hz / gcd;
1846 *fbdiv = foutvco / gcd;
1850 clk_debug("fin=%lu,fout=%lu,gcd=%u,refdiv=%u,fbdiv=%u,postdiv1=%u,postdiv2=%u,frac=%u\n",
1851 fin_hz, fout_hz, gcd, *refdiv, *fbdiv, *postdiv1, *postdiv2, *frac);
1853 clk_debug("******frac div running, fin_hz=%lu, fout_hz=%lu,fin_INT_mhz=%lu, fout_INT_mhz=%lu\n",
1854 fin_hz, fout_hz, fin_hz / MHZ * MHZ, fout_hz / MHZ * MHZ);
1855 clk_debug("******frac get postdiv1=%u, postdiv2=%u,foutvco=%u\n",
1856 *postdiv1, *postdiv2, foutvco);
1857 gcd = clk_gcd(fin_hz / MHZ, foutvco / MHZ);
1858 *refdiv = fin_hz / MHZ / gcd;
1859 *fbdiv = foutvco / MHZ / gcd;
1860 clk_debug("******frac get refdiv=%u, fbdiv=%u\n", *refdiv, *fbdiv);
1864 f_frac = (foutvco % MHZ);
1866 do_div(fin_64, (u64)*refdiv);
1867 frac_64 = (u64)f_frac << 24;
1868 do_div(frac_64, fin_64);
1869 *frac = (u32) frac_64;
1870 clk_debug("frac=%x\n", *frac);
1874 static int rk3036_pll_set_con(struct clk_hw *hw, u32 refdiv, u32 fbdiv, u32 postdiv1, u32 postdiv2, u32 frac)
1876 struct pll_clk_set temp_clk_set;
1877 temp_clk_set.pllcon0 = RK3036_PLL_SET_FBDIV(fbdiv) | RK3036_PLL_SET_POSTDIV1(postdiv1);
1878 temp_clk_set.pllcon1 = RK3036_PLL_SET_REFDIV(refdiv) | RK3036_PLL_SET_POSTDIV2(postdiv2);
1880 temp_clk_set.pllcon1 |= RK3036_PLL_SET_DSMPD(0);
1882 temp_clk_set.pllcon1 |= RK3036_PLL_SET_DSMPD(1);
1884 temp_clk_set.pllcon2 = RK3036_PLL_SET_FRAC(frac);
1885 temp_clk_set.rst_dly = 0;
1886 clk_debug("setting....\n");
1887 return rk3036_pll_clk_set_rate(&temp_clk_set, hw);
1890 static int clk_pll_set_rate_3036_apll(struct clk_hw *hw, unsigned long rate,
1891 unsigned long parent_rate)
1893 struct clk_pll *pll = to_clk_pll(hw);
1894 struct apll_clk_set *ps = (struct apll_clk_set *)(rk3036_apll_table);
1895 struct clk *arm_gpll = __clk_lookup("clk_gpll");
1896 struct clk *clk = hw->clk;
1897 unsigned long flags, arm_gpll_rate, old_rate, temp_rate;
1901 if (ps->rate == rate) {
1907 if (ps->rate != rate) {
1908 clk_err("%s: unsupport arm rate %lu\n", __func__, rate);
1913 clk_err("clk arm_gpll is NULL!\n");
1917 old_rate = __clk_get_rate(clk);
1918 arm_gpll_rate = __clk_get_rate(arm_gpll);
1919 if (soc_is_rk3128() || soc_is_rk3126())
1922 temp_rate = (old_rate > rate) ? old_rate : rate;
1923 temp_div = DIV_ROUND_UP(arm_gpll_rate, temp_rate);
1925 local_irq_save(flags);
1927 if (rate >= old_rate) {
1928 cru_writel(ps->clksel0, RK3036_CRU_CLKSELS_CON(0));
1929 cru_writel(ps->clksel1, RK3036_CRU_CLKSELS_CON(1));
1932 /* set div first, then select gpll */
1934 cru_writel(RK3036_CLK_CORE_DIV(temp_div), RK3036_CRU_CLKSELS_CON(0));
1935 cru_writel(RK3036_CORE_SEL_PLL(1), RK3036_CRU_CLKSELS_CON(0));
1937 clk_debug("temp select arm_gpll path, get rate %lu\n",
1938 arm_gpll_rate/temp_div);
1939 clk_debug("from arm_gpll rate %lu, temp_div %d\n", arm_gpll_rate,
1942 /**************enter slow mode 24M***********/
1943 /*cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift), pll->mode_offset);*/
1944 loops_per_jiffy = LPJ_24M;
1946 cru_writel(ps->pllcon0, pll->reg + RK3188_PLL_CON(0));
1947 cru_writel(ps->pllcon1, pll->reg + RK3188_PLL_CON(1));
1948 cru_writel(ps->pllcon2, pll->reg + RK3188_PLL_CON(2));
1950 clk_debug("pllcon0 %08x\n", cru_readl(pll->reg + RK3188_PLL_CON(0)));
1951 clk_debug("pllcon1 %08x\n", cru_readl(pll->reg + RK3188_PLL_CON(1)));
1952 clk_debug("pllcon2 %08x\n", cru_readl(pll->reg + RK3188_PLL_CON(2)));
1953 clk_debug("clksel0 %08x\n", cru_readl(RK3036_CRU_CLKSELS_CON(0)));
1954 clk_debug("clksel1 %08x\n", cru_readl(RK3036_CRU_CLKSELS_CON(1)));
1956 /*wating lock state*/
1957 udelay(ps->rst_dly);
1958 rk3036_pll_wait_lock(hw);
1960 /************select apll******************/
1961 cru_writel(RK3036_CORE_SEL_PLL(0), RK3036_CRU_CLKSELS_CON(0));
1962 /**************return slow mode***********/
1963 /*cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift), pll->mode_offset);*/
1965 cru_writel(RK3036_CLK_CORE_DIV(1), RK3036_CRU_CLKSELS_CON(0));
1967 if (rate < old_rate) {
1968 cru_writel(ps->clksel0, RK3036_CRU_CLKSELS_CON(0));
1969 cru_writel(ps->clksel1, RK3036_CRU_CLKSELS_CON(1));
1972 loops_per_jiffy = ps->lpj;
1973 local_irq_restore(flags);
1977 static const struct clk_ops clk_pll_ops_3036_apll = {
1978 .recalc_rate = clk_pll_recalc_rate_3036_apll,
1979 .round_rate = clk_pll_round_rate_3036_apll,
1980 .set_rate = clk_pll_set_rate_3036_apll,
1984 /* CLK_PLL_3036_plus_autotype ops */
1986 static long clk_pll_round_rate_3036plus_auto(struct clk_hw *hw, unsigned long rate,
1987 unsigned long *prate)
1989 struct clk *parent = __clk_get_parent(hw->clk);
1991 if (parent && (rate == __clk_get_rate(parent))) {
1992 clk_debug("pll %s round rate=%lu equal to parent rate\n",
1993 __clk_get_name(hw->clk), rate);
1997 return (pll_com_get_best_set(rate, rk3036plus_pll_com_table)->rate);
2000 static int clk_pll_set_rate_3036plus_auto(struct clk_hw *hw, unsigned long rate,
2001 unsigned long parent_rate)
2003 struct pll_clk_set *clk_set = (struct pll_clk_set *)(rk3036plus_pll_com_table);
2005 clk_debug("******%s\n", __func__);
2006 while (clk_set->rate) {
2007 clk_debug("******%s clk_set->rate=%lu\n", __func__, clk_set->rate);
2008 if (clk_set->rate == rate) {
2013 if (clk_set->rate == rate) {
2014 rk3036_pll_clk_set_rate(clk_set, hw);
2016 clk_debug("gpll is no corresponding rate=%lu\n", rate);
2019 clk_debug("******%s end\n", __func__);
2024 static const struct clk_ops clk_pll_ops_3036plus_auto = {
2025 .recalc_rate = clk_pll_recalc_rate_3036_apll,
2026 .round_rate = clk_pll_round_rate_3036plus_auto,
2027 .set_rate = clk_pll_set_rate_3036plus_auto,
2030 static long clk_cpll_round_rate_312xplus(struct clk_hw *hw, unsigned long rate,
2031 unsigned long *prate)
2035 for (best = rate; best > 0; best--) {
2036 if (!pll_clk_get_best_set(*prate, best, NULL, NULL, NULL))
2043 static int clk_cpll_set_rate_312xplus(struct clk_hw *hw, unsigned long rate,
2044 unsigned long parent_rate)
2046 struct pll_clk_set *clk_set = (struct pll_clk_set *)(rk312xplus_pll_com_table);
2047 u32 refdiv, fbdiv, postdiv1, postdiv2, frac;
2049 while (clk_set->rate) {
2050 if (clk_set->rate == rate) {
2056 if (clk_set->rate == rate) {
2057 clk_debug("cpll get a rate\n");
2058 rk3036_pll_clk_set_rate(clk_set, hw);
2061 clk_debug("cpll get auto calc a rate\n");
2062 if (rk3036_pll_clk_get_set(parent_rate, rate, &refdiv, &fbdiv, &postdiv1, &postdiv2, &frac) != 0) {
2063 pr_err("cpll auto set rate error\n");
2066 clk_debug("%s get rate=%lu, refdiv=%u, fbdiv=%u, postdiv1=%u, postdiv2=%u",
2067 __func__, rate, refdiv, fbdiv, postdiv1, postdiv2);
2068 rk3036_pll_set_con(hw, refdiv, fbdiv, postdiv1, postdiv2, frac);
2072 clk_debug("setting OK\n");
2076 static const struct clk_ops clk_pll_ops_312xplus = {
2077 .recalc_rate = clk_pll_recalc_rate_3036_apll,
2078 .round_rate = clk_cpll_round_rate_312xplus,
2079 .set_rate = clk_cpll_set_rate_312xplus,
2082 static long clk_pll_round_rate_3368_apllb(struct clk_hw *hw, unsigned long rate,
2083 unsigned long *prate)
2085 struct clk *parent = __clk_get_parent(hw->clk);
2087 if (parent && (rate == __clk_get_rate(parent))) {
2088 clk_debug("pll %s round rate=%lu equal to parent rate\n",
2089 __clk_get_name(hw->clk), rate);
2093 return (apll_get_best_set(rate, rk3368_apllb_table)->rate);
2096 /* 1: use, 0: no use */
2097 #define RK3368_APLLB_USE_GPLL 1
2099 /* when define 1, we will set div to make rate change gently, but it will cost
2101 #define RK3368_APLLB_DIV_MORE 1
2103 static int clk_pll_set_rate_3368_apllb(struct clk_hw *hw, unsigned long rate,
2104 unsigned long parent_rate)
2106 struct clk_pll *pll = to_clk_pll(hw);
2107 struct clk *clk = hw->clk;
2108 struct clk *arm_gpll = __clk_lookup("clk_gpll");
2109 unsigned long arm_gpll_rate, temp_rate, old_rate;
2110 const struct apll_clk_set *ps;
2112 unsigned long flags;
2115 ps = apll_get_best_set(rate, rk3368_apllb_table);
2116 clk_debug("apllb will set rate %lu\n", ps->rate);
2117 clk_debug("table con:%08x,%08x,%08x, sel:%08x,%08x\n",
2118 ps->pllcon0, ps->pllcon1, ps->pllcon2,
2119 ps->clksel0, ps->clksel1);
2121 #if !RK3368_APLLB_USE_GPLL
2125 /* prepare arm_gpll before reparent clk_core to it */
2127 clk_err("clk arm_gpll is NULL!\n");
2131 arm_gpll_rate = __clk_get_rate(arm_gpll);
2132 old_rate = __clk_get_rate(clk);
2134 temp_rate = (old_rate > rate) ? old_rate : rate;
2135 temp_div = DIV_ROUND_UP(arm_gpll_rate, temp_rate);
2137 if (temp_div > RK3368_CORE_CLK_MAX_DIV) {
2138 clk_debug("temp_div %d > max_div %d\n", temp_div,
2139 RK3368_CORE_CLK_MAX_DIV);
2140 clk_debug("can't get rate %lu from arm_gpll rate %lu\n",
2141 __clk_get_rate(clk), arm_gpll_rate);
2145 local_irq_save(flags);
2147 if (rate >= old_rate) {
2148 cru_writel(ps->clksel0, RK3368_CRU_CLKSELS_CON(0));
2149 cru_writel(ps->clksel1, RK3368_CRU_CLKSELS_CON(1));
2153 #if RK3368_APLLB_DIV_MORE
2154 if (temp_div == 1) {
2155 /* when old_rate/2 < (old_rate-arm_gpll_rate),
2156 we can set div to make rate change more gently */
2157 if (old_rate > (2*arm_gpll_rate)) {
2158 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(0));
2160 cru_writel(RK3368_CORE_CLK_DIV(3), RK3368_CRU_CLKSELS_CON(0));
2162 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2163 RK3368_CRU_CLKSELS_CON(0));
2165 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(0));
2167 cru_writel(RK3368_CORE_CLK_DIV(1), RK3368_CRU_CLKSELS_CON(0));
2169 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2170 RK3368_CRU_CLKSELS_CON(0));
2173 cru_writel(RK3368_CORE_CLK_DIV(temp_div), RK3368_CRU_CLKSELS_CON(0));
2174 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2175 RK3368_CRU_CLKSELS_CON(0));
2178 cru_writel(RK3368_CORE_CLK_DIV(temp_div), RK3368_CRU_CLKSELS_CON(0));
2179 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2180 RK3368_CRU_CLKSELS_CON(0));
2187 local_irq_restore(flags);
2189 clk_debug("temp select arm_gpll path, get rate %lu\n",
2190 arm_gpll_rate/temp_div);
2191 clk_debug("from arm_gpll rate %lu, temp_div %d\n", arm_gpll_rate,
2195 local_irq_save(flags);
2197 /* apll enter slow mode */
2198 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
2201 /* PLL enter reset */
2202 cru_writel(_RK3188PLUS_PLL_RESET_SET(1), pll->reg + RK3188_PLL_CON(3));
2204 cru_writel(ps->pllcon0, pll->reg + RK3188_PLL_CON(0));
2205 cru_writel(ps->pllcon1, pll->reg + RK3188_PLL_CON(1));
2206 cru_writel(ps->pllcon2, pll->reg + RK3188_PLL_CON(2));
2210 /* return from rest */
2211 cru_writel(_RK3188PLUS_PLL_RESET_SET(0), pll->reg + RK3188_PLL_CON(3));
2213 /* wating lock state */
2214 udelay(ps->rst_dly);
2218 if (rate >= old_rate) {
2219 cru_writel(ps->clksel0, RK3368_CRU_CLKSELS_CON(0));
2220 cru_writel(ps->clksel1, RK3368_CRU_CLKSELS_CON(1));
2224 /* apll return from slow mode */
2225 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift),
2228 /* reparent to apll, and set div to 1 */
2230 #if RK3368_APLLB_DIV_MORE
2231 /* when rate/2 < (rate-arm_gpll_rate), we can set div to make
2232 rate change more gently */
2233 if ((temp_div == 1) && (rate > (2*arm_gpll_rate))) {
2234 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(0));
2236 cru_writel(RK3368_CORE_CLK_DIV(3), RK3368_CRU_CLKSELS_CON(0));
2238 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_APLL,
2239 RK3368_CRU_CLKSELS_CON(0));
2241 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(0));
2244 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_APLL,
2245 RK3368_CRU_CLKSELS_CON(0));
2247 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_APLL,
2248 RK3368_CRU_CLKSELS_CON(0));
2252 cru_writel(RK3368_CORE_CLK_DIV(1), RK3368_CRU_CLKSELS_CON(0));
2254 if (rate < old_rate) {
2255 cru_writel(ps->clksel0, RK3368_CRU_CLKSELS_CON(0));
2256 cru_writel(ps->clksel1, RK3368_CRU_CLKSELS_CON(1));
2261 local_irq_restore(flags);
2266 clk_debug("apll set rate %lu, con(%x,%x,%x,%x), sel(%x,%x)\n",
2268 cru_readl(pll->reg + RK3188_PLL_CON(0)),
2269 cru_readl(pll->reg + RK3188_PLL_CON(1)),
2270 cru_readl(pll->reg + RK3188_PLL_CON(2)),
2271 cru_readl(pll->reg + RK3188_PLL_CON(3)),
2272 cru_readl(RK3368_CRU_CLKSELS_CON(0)),
2273 cru_readl(RK3368_CRU_CLKSELS_CON(1)));
2278 static const struct clk_ops clk_pll_ops_3368_apllb = {
2279 .recalc_rate = clk_pll_recalc_rate_3188plus,
2280 .round_rate = clk_pll_round_rate_3368_apllb,
2281 .set_rate = clk_pll_set_rate_3368_apllb,
2284 static long clk_pll_round_rate_3368_aplll(struct clk_hw *hw, unsigned long rate,
2285 unsigned long *prate)
2287 struct clk *parent = __clk_get_parent(hw->clk);
2289 if (parent && (rate == __clk_get_rate(parent))) {
2290 clk_debug("pll %s round rate=%lu equal to parent rate\n",
2291 __clk_get_name(hw->clk), rate);
2295 return (apll_get_best_set(rate, rk3368_aplll_table)->rate);
2298 /* 1: use, 0: no use */
2299 #define RK3368_APLLL_USE_GPLL 1
2301 /* when define 1, we will set div to make rate change gently, but it will cost
2303 #define RK3368_APLLL_DIV_MORE 1
2305 static int clk_pll_set_rate_3368_aplll(struct clk_hw *hw, unsigned long rate,
2306 unsigned long parent_rate)
2308 struct clk_pll *pll = to_clk_pll(hw);
2309 struct clk *clk = hw->clk;
2310 struct clk *arm_gpll = __clk_lookup("clk_gpll");
2311 unsigned long arm_gpll_rate, temp_rate, old_rate;
2312 const struct apll_clk_set *ps;
2314 unsigned long flags;
2317 ps = apll_get_best_set(rate, rk3368_aplll_table);
2318 clk_debug("aplll will set rate %lu\n", ps->rate);
2319 clk_debug("table con:%08x,%08x,%08x, sel:%08x,%08x\n",
2320 ps->pllcon0, ps->pllcon1, ps->pllcon2,
2321 ps->clksel0, ps->clksel1);
2323 #if !RK3368_APLLL_USE_GPLL
2327 /* prepare arm_gpll before reparent clk_core to it */
2329 clk_err("clk arm_gpll is NULL!\n");
2333 arm_gpll_rate = __clk_get_rate(arm_gpll);
2334 old_rate = __clk_get_rate(clk);
2336 temp_rate = (old_rate > rate) ? old_rate : rate;
2337 temp_div = DIV_ROUND_UP(arm_gpll_rate, temp_rate);
2339 if (temp_div > RK3368_CORE_CLK_MAX_DIV) {
2340 clk_debug("temp_div %d > max_div %d\n", temp_div,
2341 RK3368_CORE_CLK_MAX_DIV);
2342 clk_debug("can't get rate %lu from arm_gpll rate %lu\n",
2343 __clk_get_rate(clk), arm_gpll_rate);
2347 local_irq_save(flags);
2349 if (rate >= old_rate) {
2350 cru_writel(ps->clksel0, RK3368_CRU_CLKSELS_CON(2));
2351 cru_writel(ps->clksel1, RK3368_CRU_CLKSELS_CON(3));
2355 #if RK3368_APLLL_DIV_MORE
2356 if (temp_div == 1) {
2357 /* when old_rate/2 < (old_rate-arm_gpll_rate),
2358 we can set div to make rate change more gently */
2359 if (old_rate > (2*arm_gpll_rate)) {
2360 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(2));
2362 cru_writel(RK3368_CORE_CLK_DIV(3), RK3368_CRU_CLKSELS_CON(2));
2364 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2365 RK3368_CRU_CLKSELS_CON(2));
2367 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(2));
2369 cru_writel(RK3368_CORE_CLK_DIV(1), RK3368_CRU_CLKSELS_CON(2));
2371 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2372 RK3368_CRU_CLKSELS_CON(2));
2375 cru_writel(RK3368_CORE_CLK_DIV(temp_div), RK3368_CRU_CLKSELS_CON(2));
2376 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2377 RK3368_CRU_CLKSELS_CON(2));
2380 cru_writel(RK3368_CORE_CLK_DIV(temp_div), RK3368_CRU_CLKSELS_CON(2));
2381 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_GPLL,
2382 RK3368_CRU_CLKSELS_CON(2));
2389 local_irq_restore(flags);
2391 clk_debug("temp select arm_gpll path, get rate %lu\n",
2392 arm_gpll_rate/temp_div);
2393 clk_debug("from arm_gpll rate %lu, temp_div %d\n", arm_gpll_rate,
2397 local_irq_save(flags);
2399 /* apll enter slow mode */
2400 cru_writel(_RK3188_PLL_MODE_SLOW_SET(pll->mode_shift),
2403 /* PLL enter reset */
2404 cru_writel(_RK3188PLUS_PLL_RESET_SET(1), pll->reg + RK3188_PLL_CON(3));
2406 cru_writel(ps->pllcon0, pll->reg + RK3188_PLL_CON(0));
2407 cru_writel(ps->pllcon1, pll->reg + RK3188_PLL_CON(1));
2408 cru_writel(ps->pllcon2, pll->reg + RK3188_PLL_CON(2));
2412 /* return from rest */
2413 cru_writel(_RK3188PLUS_PLL_RESET_SET(0), pll->reg + RK3188_PLL_CON(3));
2415 /* wating lock state */
2416 udelay(ps->rst_dly);
2420 if (rate >= old_rate) {
2421 cru_writel(ps->clksel0, RK3368_CRU_CLKSELS_CON(2));
2422 cru_writel(ps->clksel1, RK3368_CRU_CLKSELS_CON(3));
2426 /* apll return from slow mode */
2427 cru_writel(_RK3188_PLL_MODE_NORM_SET(pll->mode_shift),
2430 /* reparent to apll, and set div to 1 */
2432 #if RK3368_APLLL_DIV_MORE
2433 /* when rate/2 < (rate-arm_gpll_rate), we can set div to make
2434 rate change more gently */
2435 if ((temp_div == 1) && (rate > (2*arm_gpll_rate))) {
2436 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(2));
2438 cru_writel(RK3368_CORE_CLK_DIV(3), RK3368_CRU_CLKSELS_CON(2));
2440 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_APLL,
2441 RK3368_CRU_CLKSELS_CON(2));
2443 cru_writel(RK3368_CORE_CLK_DIV(2), RK3368_CRU_CLKSELS_CON(2));
2446 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_APLL,
2447 RK3368_CRU_CLKSELS_CON(2));
2449 cru_writel(RK3368_CORE_SEL_PLL_W_MSK|RK3368_CORE_SEL_APLL,
2450 RK3368_CRU_CLKSELS_CON(2));
2454 cru_writel(RK3368_CORE_CLK_DIV(1), RK3368_CRU_CLKSELS_CON(2));
2456 if (rate < old_rate) {
2457 cru_writel(ps->clksel0, RK3368_CRU_CLKSELS_CON(2));
2458 cru_writel(ps->clksel1, RK3368_CRU_CLKSELS_CON(3));
2463 local_irq_restore(flags);
2468 clk_debug("apll set rate %lu, con(%x,%x,%x,%x), sel(%x,%x)\n",
2470 cru_readl(pll->reg + RK3188_PLL_CON(0)),
2471 cru_readl(pll->reg + RK3188_PLL_CON(1)),
2472 cru_readl(pll->reg + RK3188_PLL_CON(2)),
2473 cru_readl(pll->reg + RK3188_PLL_CON(3)),
2474 cru_readl(RK3368_CRU_CLKSELS_CON(2)),
2475 cru_readl(RK3368_CRU_CLKSELS_CON(3)));
2480 static const struct clk_ops clk_pll_ops_3368_aplll = {
2481 .recalc_rate = clk_pll_recalc_rate_3188plus,
2482 .round_rate = clk_pll_round_rate_3368_aplll,
2483 .set_rate = clk_pll_set_rate_3368_aplll,
2486 const struct clk_ops *rk_get_pll_ops(u32 pll_flags)
2488 switch (pll_flags) {
2490 return &clk_pll_ops_3188;
2492 case CLK_PLL_3188_APLL:
2493 return &clk_pll_ops_3188_apll;
2495 case CLK_PLL_3188PLUS:
2496 return &clk_pll_ops_3188plus;
2498 case CLK_PLL_3188PLUS_APLL:
2499 return &clk_pll_ops_3188plus_apll;
2501 case CLK_PLL_3288_APLL:
2502 return &clk_pll_ops_3288_apll;
2504 case CLK_PLL_3188PLUS_AUTO:
2505 return &clk_pll_ops_3188plus_auto;
2507 case CLK_PLL_3036_APLL:
2508 return &clk_pll_ops_3036_apll;
2510 case CLK_PLL_3036PLUS_AUTO:
2511 return &clk_pll_ops_3036plus_auto;
2513 case CLK_PLL_312XPLUS:
2514 return &clk_pll_ops_312xplus;
2516 case CLK_PLL_3368_APLLB:
2517 return &clk_pll_ops_3368_apllb;
2519 case CLK_PLL_3368_APLLL:
2520 return &clk_pll_ops_3368_aplll;
2522 case CLK_PLL_3368_LOW_JITTER:
2523 return &clk_pll_ops_3368_low_jitter;
2526 clk_err("%s: unknown pll_flags!\n", __func__);
2531 struct clk *rk_clk_register_pll(struct device *dev, const char *name,
2532 const char *parent_name, unsigned long flags, u32 reg,
2533 u32 width, u32 mode_offset, u8 mode_shift,
2534 u32 status_offset, u8 status_shift, u32 pll_flags,
2537 struct clk_pll *pll;
2539 struct clk_init_data init;
2542 clk_debug("%s: pll name = %s, pll_flags = 0x%x, register start!\n",
2543 __func__, name, pll_flags);
2545 /* allocate the pll */
2546 pll = kzalloc(sizeof(struct clk_pll), GFP_KERNEL);
2548 clk_err("%s: could not allocate pll clk\n", __func__);
2549 return ERR_PTR(-ENOMEM);
2554 init.parent_names = (parent_name ? &parent_name: NULL);
2555 init.num_parents = (parent_name ? 1 : 0);
2556 init.ops = rk_get_pll_ops(pll_flags);
2558 /* struct clk_pll assignments */
2561 pll->mode_offset = mode_offset;
2562 pll->mode_shift = mode_shift;
2563 pll->status_offset = status_offset;
2564 pll->status_shift = status_shift;
2565 pll->flags = pll_flags;
2567 pll->hw.init = &init;
2569 /* register the clock */
2570 clk = clk_register(dev, &pll->hw);
2575 clk_debug("%s: pll name = %s, pll_flags = 0x%x, register finish!\n",
2576 __func__, name, pll_flags);