Merge branch 'next' into for-linus
[linux-2.6-microblaze.git] / drivers / clk / zynqmp / pll.c
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Zynq UltraScale+ MPSoC PLL driver
4  *
5  *  Copyright (C) 2016-2018 Xilinx
6  */
7
8 #include <linux/clk.h>
9 #include <linux/clk-provider.h>
10 #include <linux/slab.h>
11 #include "clk-zynqmp.h"
12
13 /**
14  * struct zynqmp_pll - PLL clock
15  * @hw:         Handle between common and hardware-specific interfaces
16  * @clk_id:     PLL clock ID
17  * @set_pll_mode:       Whether an IOCTL_SET_PLL_FRAC_MODE request be sent to ATF
18  */
19 struct zynqmp_pll {
20         struct clk_hw hw;
21         u32 clk_id;
22         bool set_pll_mode;
23 };
24
25 #define to_zynqmp_pll(_hw)      container_of(_hw, struct zynqmp_pll, hw)
26
27 #define PLL_FBDIV_MIN   25
28 #define PLL_FBDIV_MAX   125
29
30 #define PS_PLL_VCO_MIN 1500000000
31 #define PS_PLL_VCO_MAX 3000000000UL
32
33 enum pll_mode {
34         PLL_MODE_INT,
35         PLL_MODE_FRAC,
36 };
37
38 #define FRAC_OFFSET 0x8
39 #define PLLFCFG_FRAC_EN BIT(31)
40 #define FRAC_DIV  BIT(16)  /* 2^16 */
41
42 /**
43  * zynqmp_pll_get_mode() - Get mode of PLL
44  * @hw:         Handle between common and hardware-specific interfaces
45  *
46  * Return: Mode of PLL
47  */
48 static inline enum pll_mode zynqmp_pll_get_mode(struct clk_hw *hw)
49 {
50         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
51         u32 clk_id = clk->clk_id;
52         const char *clk_name = clk_hw_get_name(hw);
53         u32 ret_payload[PAYLOAD_ARG_CNT];
54         int ret;
55
56         ret = zynqmp_pm_get_pll_frac_mode(clk_id, ret_payload);
57         if (ret)
58                 pr_warn_once("%s() PLL get frac mode failed for %s, ret = %d\n",
59                              __func__, clk_name, ret);
60
61         return ret_payload[1];
62 }
63
64 /**
65  * zynqmp_pll_set_mode() - Set the PLL mode
66  * @hw:         Handle between common and hardware-specific interfaces
67  * @on:         Flag to determine the mode
68  */
69 static inline void zynqmp_pll_set_mode(struct clk_hw *hw, bool on)
70 {
71         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
72         u32 clk_id = clk->clk_id;
73         const char *clk_name = clk_hw_get_name(hw);
74         int ret;
75         u32 mode;
76
77         if (on)
78                 mode = PLL_MODE_FRAC;
79         else
80                 mode = PLL_MODE_INT;
81
82         ret = zynqmp_pm_set_pll_frac_mode(clk_id, mode);
83         if (ret)
84                 pr_warn_once("%s() PLL set frac mode failed for %s, ret = %d\n",
85                              __func__, clk_name, ret);
86         else
87                 clk->set_pll_mode = true;
88 }
89
90 /**
91  * zynqmp_pll_round_rate() - Round a clock frequency
92  * @hw:         Handle between common and hardware-specific interfaces
93  * @rate:       Desired clock frequency
94  * @prate:      Clock frequency of parent clock
95  *
96  * Return: Frequency closest to @rate the hardware can generate
97  */
98 static long zynqmp_pll_round_rate(struct clk_hw *hw, unsigned long rate,
99                                   unsigned long *prate)
100 {
101         u32 fbdiv;
102         long rate_div, f;
103
104         /* Enable the fractional mode if needed */
105         rate_div = (rate * FRAC_DIV) / *prate;
106         f = rate_div % FRAC_DIV;
107         if (f) {
108                 if (rate > PS_PLL_VCO_MAX) {
109                         fbdiv = rate / PS_PLL_VCO_MAX;
110                         rate = rate / (fbdiv + 1);
111                 }
112                 if (rate < PS_PLL_VCO_MIN) {
113                         fbdiv = DIV_ROUND_UP(PS_PLL_VCO_MIN, rate);
114                         rate = rate * fbdiv;
115                 }
116                 return rate;
117         }
118
119         fbdiv = DIV_ROUND_CLOSEST(rate, *prate);
120         fbdiv = clamp_t(u32, fbdiv, PLL_FBDIV_MIN, PLL_FBDIV_MAX);
121         return *prate * fbdiv;
122 }
123
124 /**
125  * zynqmp_pll_recalc_rate() - Recalculate clock frequency
126  * @hw:                 Handle between common and hardware-specific interfaces
127  * @parent_rate:        Clock frequency of parent clock
128  *
129  * Return: Current clock frequency
130  */
131 static unsigned long zynqmp_pll_recalc_rate(struct clk_hw *hw,
132                                             unsigned long parent_rate)
133 {
134         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
135         u32 clk_id = clk->clk_id;
136         const char *clk_name = clk_hw_get_name(hw);
137         u32 fbdiv, data;
138         unsigned long rate, frac;
139         u32 ret_payload[PAYLOAD_ARG_CNT];
140         int ret;
141
142         ret = zynqmp_pm_clock_getdivider(clk_id, &fbdiv);
143         if (ret)
144                 pr_warn_once("%s() get divider failed for %s, ret = %d\n",
145                              __func__, clk_name, ret);
146
147         rate =  parent_rate * fbdiv;
148         if (zynqmp_pll_get_mode(hw) == PLL_MODE_FRAC) {
149                 zynqmp_pm_get_pll_frac_data(clk_id, ret_payload);
150                 data = ret_payload[1];
151                 frac = (parent_rate * data) / FRAC_DIV;
152                 rate = rate + frac;
153         }
154
155         return rate;
156 }
157
158 /**
159  * zynqmp_pll_set_rate() - Set rate of PLL
160  * @hw:                 Handle between common and hardware-specific interfaces
161  * @rate:               Frequency of clock to be set
162  * @parent_rate:        Clock frequency of parent clock
163  *
164  * Set PLL divider to set desired rate.
165  *
166  * Returns:            rate which is set on success else error code
167  */
168 static int zynqmp_pll_set_rate(struct clk_hw *hw, unsigned long rate,
169                                unsigned long parent_rate)
170 {
171         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
172         u32 clk_id = clk->clk_id;
173         const char *clk_name = clk_hw_get_name(hw);
174         u32 fbdiv;
175         long rate_div, frac, m, f;
176         int ret;
177
178         rate_div = (rate * FRAC_DIV) / parent_rate;
179         f = rate_div % FRAC_DIV;
180         zynqmp_pll_set_mode(hw, !!f);
181
182         if (f) {
183                 m = rate_div / FRAC_DIV;
184                 m = clamp_t(u32, m, (PLL_FBDIV_MIN), (PLL_FBDIV_MAX));
185                 rate = parent_rate * m;
186                 frac = (parent_rate * f) / FRAC_DIV;
187
188                 ret = zynqmp_pm_clock_setdivider(clk_id, m);
189                 if (ret == -EUSERS)
190                         WARN(1, "More than allowed devices are using the %s, which is forbidden\n",
191                              clk_name);
192                 else if (ret)
193                         pr_warn_once("%s() set divider failed for %s, ret = %d\n",
194                                      __func__, clk_name, ret);
195                 zynqmp_pm_set_pll_frac_data(clk_id, f);
196
197                 return rate + frac;
198         }
199
200         fbdiv = DIV_ROUND_CLOSEST(rate, parent_rate);
201         fbdiv = clamp_t(u32, fbdiv, PLL_FBDIV_MIN, PLL_FBDIV_MAX);
202         ret = zynqmp_pm_clock_setdivider(clk_id, fbdiv);
203         if (ret)
204                 pr_warn_once("%s() set divider failed for %s, ret = %d\n",
205                              __func__, clk_name, ret);
206
207         return parent_rate * fbdiv;
208 }
209
210 /**
211  * zynqmp_pll_is_enabled() - Check if a clock is enabled
212  * @hw:         Handle between common and hardware-specific interfaces
213  *
214  * Return: 1 if the clock is enabled, 0 otherwise
215  */
216 static int zynqmp_pll_is_enabled(struct clk_hw *hw)
217 {
218         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
219         const char *clk_name = clk_hw_get_name(hw);
220         u32 clk_id = clk->clk_id;
221         unsigned int state;
222         int ret;
223
224         ret = zynqmp_pm_clock_getstate(clk_id, &state);
225         if (ret) {
226                 pr_warn_once("%s() clock get state failed for %s, ret = %d\n",
227                              __func__, clk_name, ret);
228                 return -EIO;
229         }
230
231         return state ? 1 : 0;
232 }
233
234 /**
235  * zynqmp_pll_enable() - Enable clock
236  * @hw:         Handle between common and hardware-specific interfaces
237  *
238  * Return: 0 on success else error code
239  */
240 static int zynqmp_pll_enable(struct clk_hw *hw)
241 {
242         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
243         const char *clk_name = clk_hw_get_name(hw);
244         u32 clk_id = clk->clk_id;
245         int ret;
246
247         /*
248          * Don't skip enabling clock if there is an IOCTL_SET_PLL_FRAC_MODE request
249          * that has been sent to ATF.
250          */
251         if (zynqmp_pll_is_enabled(hw) && (!clk->set_pll_mode))
252                 return 0;
253
254         clk->set_pll_mode = false;
255
256         ret = zynqmp_pm_clock_enable(clk_id);
257         if (ret)
258                 pr_warn_once("%s() clock enable failed for %s, ret = %d\n",
259                              __func__, clk_name, ret);
260
261         return ret;
262 }
263
264 /**
265  * zynqmp_pll_disable() - Disable clock
266  * @hw:         Handle between common and hardware-specific interfaces
267  */
268 static void zynqmp_pll_disable(struct clk_hw *hw)
269 {
270         struct zynqmp_pll *clk = to_zynqmp_pll(hw);
271         const char *clk_name = clk_hw_get_name(hw);
272         u32 clk_id = clk->clk_id;
273         int ret;
274
275         if (!zynqmp_pll_is_enabled(hw))
276                 return;
277
278         ret = zynqmp_pm_clock_disable(clk_id);
279         if (ret)
280                 pr_warn_once("%s() clock disable failed for %s, ret = %d\n",
281                              __func__, clk_name, ret);
282 }
283
284 static const struct clk_ops zynqmp_pll_ops = {
285         .enable = zynqmp_pll_enable,
286         .disable = zynqmp_pll_disable,
287         .is_enabled = zynqmp_pll_is_enabled,
288         .round_rate = zynqmp_pll_round_rate,
289         .recalc_rate = zynqmp_pll_recalc_rate,
290         .set_rate = zynqmp_pll_set_rate,
291 };
292
293 /**
294  * zynqmp_clk_register_pll() - Register PLL with the clock framework
295  * @name:               PLL name
296  * @clk_id:             Clock ID
297  * @parents:            Name of this clock's parents
298  * @num_parents:        Number of parents
299  * @nodes:              Clock topology node
300  *
301  * Return: clock hardware to the registered clock
302  */
303 struct clk_hw *zynqmp_clk_register_pll(const char *name, u32 clk_id,
304                                        const char * const *parents,
305                                        u8 num_parents,
306                                        const struct clock_topology *nodes)
307 {
308         struct zynqmp_pll *pll;
309         struct clk_hw *hw;
310         struct clk_init_data init;
311         int ret;
312
313         init.name = name;
314         init.ops = &zynqmp_pll_ops;
315         init.flags = nodes->flag;
316         init.parent_names = parents;
317         init.num_parents = 1;
318
319         pll = kzalloc(sizeof(*pll), GFP_KERNEL);
320         if (!pll)
321                 return ERR_PTR(-ENOMEM);
322
323         pll->hw.init = &init;
324         pll->clk_id = clk_id;
325
326         hw = &pll->hw;
327         ret = clk_hw_register(NULL, hw);
328         if (ret) {
329                 kfree(pll);
330                 return ERR_PTR(ret);
331         }
332
333         clk_hw_set_rate_range(hw, PS_PLL_VCO_MIN, PS_PLL_VCO_MAX);
334         if (ret < 0)
335                 pr_err("%s:ERROR clk_set_rate_range failed %d\n", name, ret);
336
337         return hw;
338 }