xref: /openbmc/linux/drivers/clk/imx/clk.h (revision 752beb5e)
1 /* SPDX-License-Identifier: GPL-2.0 */
2 #ifndef __MACH_IMX_CLK_H
3 #define __MACH_IMX_CLK_H
4 
5 #include <linux/spinlock.h>
6 #include <linux/clk-provider.h>
7 
8 extern spinlock_t imx_ccm_lock;
9 
10 void imx_check_clocks(struct clk *clks[], unsigned int count);
11 void imx_check_clk_hws(struct clk_hw *clks[], unsigned int count);
12 void imx_register_uart_clocks(struct clk ** const clks[]);
13 
14 extern void imx_cscmr1_fixup(u32 *val);
15 
16 enum imx_pllv1_type {
17 	IMX_PLLV1_IMX1,
18 	IMX_PLLV1_IMX21,
19 	IMX_PLLV1_IMX25,
20 	IMX_PLLV1_IMX27,
21 	IMX_PLLV1_IMX31,
22 	IMX_PLLV1_IMX35,
23 };
24 
25 enum imx_sccg_pll_type {
26 	SCCG_PLL1,
27 	SCCG_PLL2,
28 };
29 
30 enum imx_pll14xx_type {
31 	PLL_1416X,
32 	PLL_1443X,
33 };
34 
35 /* NOTE: Rate table should be kept sorted in descending order. */
36 struct imx_pll14xx_rate_table {
37 	unsigned int rate;
38 	unsigned int pdiv;
39 	unsigned int mdiv;
40 	unsigned int sdiv;
41 	unsigned int kdiv;
42 };
43 
44 struct imx_pll14xx_clk {
45 	enum imx_pll14xx_type type;
46 	const struct imx_pll14xx_rate_table *rate_table;
47 	int rate_count;
48 	int flags;
49 };
50 
51 struct clk *imx_clk_pll14xx(const char *name, const char *parent_name,
52 		 void __iomem *base, const struct imx_pll14xx_clk *pll_clk);
53 
54 struct clk *imx_clk_pllv1(enum imx_pllv1_type type, const char *name,
55 		const char *parent, void __iomem *base);
56 
57 struct clk *imx_clk_pllv2(const char *name, const char *parent,
58 		void __iomem *base);
59 
60 struct clk *imx_clk_frac_pll(const char *name, const char *parent_name,
61 			     void __iomem *base);
62 
63 struct clk *imx_clk_sccg_pll(const char *name,
64 				const char * const *parent_names,
65 				u8 num_parents,
66 				u8 parent, u8 bypass1, u8 bypass2,
67 				void __iomem *base,
68 				unsigned long flags);
69 
70 enum imx_pllv3_type {
71 	IMX_PLLV3_GENERIC,
72 	IMX_PLLV3_SYS,
73 	IMX_PLLV3_USB,
74 	IMX_PLLV3_USB_VF610,
75 	IMX_PLLV3_AV,
76 	IMX_PLLV3_ENET,
77 	IMX_PLLV3_ENET_IMX7,
78 	IMX_PLLV3_SYS_VF610,
79 	IMX_PLLV3_DDR_IMX7,
80 	IMX_PLLV3_AV_IMX7,
81 };
82 
83 struct clk *imx_clk_pllv3(enum imx_pllv3_type type, const char *name,
84 		const char *parent_name, void __iomem *base, u32 div_mask);
85 
86 struct clk_hw *imx_clk_pllv4(const char *name, const char *parent_name,
87 			     void __iomem *base);
88 
89 struct clk *clk_register_gate2(struct device *dev, const char *name,
90 		const char *parent_name, unsigned long flags,
91 		void __iomem *reg, u8 bit_idx, u8 cgr_val,
92 		u8 clk_gate_flags, spinlock_t *lock,
93 		unsigned int *share_count);
94 
95 struct clk * imx_obtain_fixed_clock(
96 			const char *name, unsigned long rate);
97 
98 struct clk_hw *imx_obtain_fixed_clk_hw(struct device_node *np,
99 				       const char *name);
100 
101 struct clk *imx_clk_gate_exclusive(const char *name, const char *parent,
102 	 void __iomem *reg, u8 shift, u32 exclusive_mask);
103 
104 struct clk *imx_clk_pfd(const char *name, const char *parent_name,
105 		void __iomem *reg, u8 idx);
106 
107 struct clk_hw *imx_clk_pfdv2(const char *name, const char *parent_name,
108 			     void __iomem *reg, u8 idx);
109 
110 struct clk *imx_clk_busy_divider(const char *name, const char *parent_name,
111 				 void __iomem *reg, u8 shift, u8 width,
112 				 void __iomem *busy_reg, u8 busy_shift);
113 
114 struct clk *imx_clk_busy_mux(const char *name, void __iomem *reg, u8 shift,
115 			     u8 width, void __iomem *busy_reg, u8 busy_shift,
116 			     const char * const *parent_names, int num_parents);
117 
118 struct clk_hw *imx7ulp_clk_composite(const char *name,
119 				     const char * const *parent_names,
120 				     int num_parents, bool mux_present,
121 				     bool rate_present, bool gate_present,
122 				     void __iomem *reg);
123 
124 struct clk *imx_clk_fixup_divider(const char *name, const char *parent,
125 				  void __iomem *reg, u8 shift, u8 width,
126 				  void (*fixup)(u32 *val));
127 
128 struct clk *imx_clk_fixup_mux(const char *name, void __iomem *reg,
129 			      u8 shift, u8 width, const char * const *parents,
130 			      int num_parents, void (*fixup)(u32 *val));
131 
132 static inline struct clk *imx_clk_fixed(const char *name, int rate)
133 {
134 	return clk_register_fixed_rate(NULL, name, NULL, 0, rate);
135 }
136 
137 static inline struct clk_hw *imx_clk_hw_fixed(const char *name, int rate)
138 {
139 	return clk_hw_register_fixed_rate(NULL, name, NULL, 0, rate);
140 }
141 
142 static inline struct clk *imx_clk_mux_ldb(const char *name, void __iomem *reg,
143 			u8 shift, u8 width, const char * const *parents,
144 			int num_parents)
145 {
146 	return clk_register_mux(NULL, name, parents, num_parents,
147 			CLK_SET_RATE_NO_REPARENT | CLK_SET_RATE_PARENT, reg,
148 			shift, width, CLK_MUX_READ_ONLY, &imx_ccm_lock);
149 }
150 
151 static inline struct clk *imx_clk_fixed_factor(const char *name,
152 		const char *parent, unsigned int mult, unsigned int div)
153 {
154 	return clk_register_fixed_factor(NULL, name, parent,
155 			CLK_SET_RATE_PARENT, mult, div);
156 }
157 
158 static inline struct clk *imx_clk_divider(const char *name, const char *parent,
159 		void __iomem *reg, u8 shift, u8 width)
160 {
161 	return clk_register_divider(NULL, name, parent, CLK_SET_RATE_PARENT,
162 			reg, shift, width, 0, &imx_ccm_lock);
163 }
164 
165 static inline struct clk_hw *imx_clk_hw_divider(const char *name,
166 						const char *parent,
167 						void __iomem *reg, u8 shift,
168 						u8 width)
169 {
170 	return clk_hw_register_divider(NULL, name, parent, CLK_SET_RATE_PARENT,
171 				       reg, shift, width, 0, &imx_ccm_lock);
172 }
173 
174 static inline struct clk *imx_clk_divider_flags(const char *name,
175 		const char *parent, void __iomem *reg, u8 shift, u8 width,
176 		unsigned long flags)
177 {
178 	return clk_register_divider(NULL, name, parent, flags,
179 			reg, shift, width, 0, &imx_ccm_lock);
180 }
181 
182 static inline struct clk_hw *imx_clk_hw_divider_flags(const char *name,
183 						   const char *parent,
184 						   void __iomem *reg, u8 shift,
185 						   u8 width, unsigned long flags)
186 {
187 	return clk_hw_register_divider(NULL, name, parent, flags,
188 				       reg, shift, width, 0, &imx_ccm_lock);
189 }
190 
191 static inline struct clk *imx_clk_divider2(const char *name, const char *parent,
192 		void __iomem *reg, u8 shift, u8 width)
193 {
194 	return clk_register_divider(NULL, name, parent,
195 			CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
196 			reg, shift, width, 0, &imx_ccm_lock);
197 }
198 
199 static inline struct clk *imx_clk_divider2_flags(const char *name,
200 		const char *parent, void __iomem *reg, u8 shift, u8 width,
201 		unsigned long flags)
202 {
203 	return clk_register_divider(NULL, name, parent,
204 			flags | CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
205 			reg, shift, width, 0, &imx_ccm_lock);
206 }
207 
208 static inline struct clk *imx_clk_gate(const char *name, const char *parent,
209 		void __iomem *reg, u8 shift)
210 {
211 	return clk_register_gate(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
212 			shift, 0, &imx_ccm_lock);
213 }
214 
215 static inline struct clk *imx_clk_gate_flags(const char *name, const char *parent,
216 		void __iomem *reg, u8 shift, unsigned long flags)
217 {
218 	return clk_register_gate(NULL, name, parent, flags | CLK_SET_RATE_PARENT, reg,
219 			shift, 0, &imx_ccm_lock);
220 }
221 
222 static inline struct clk_hw *imx_clk_hw_gate(const char *name, const char *parent,
223 					     void __iomem *reg, u8 shift)
224 {
225 	return clk_hw_register_gate(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
226 				    shift, 0, &imx_ccm_lock);
227 }
228 
229 static inline struct clk *imx_clk_gate_dis(const char *name, const char *parent,
230 		void __iomem *reg, u8 shift)
231 {
232 	return clk_register_gate(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
233 			shift, CLK_GATE_SET_TO_DISABLE, &imx_ccm_lock);
234 }
235 
236 static inline struct clk *imx_clk_gate_dis_flags(const char *name, const char *parent,
237 		void __iomem *reg, u8 shift, unsigned long flags)
238 {
239 	return clk_register_gate(NULL, name, parent, flags | CLK_SET_RATE_PARENT, reg,
240 			shift, CLK_GATE_SET_TO_DISABLE, &imx_ccm_lock);
241 }
242 
243 static inline struct clk *imx_clk_gate2(const char *name, const char *parent,
244 		void __iomem *reg, u8 shift)
245 {
246 	return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
247 			shift, 0x3, 0, &imx_ccm_lock, NULL);
248 }
249 
250 static inline struct clk *imx_clk_gate2_flags(const char *name, const char *parent,
251 		void __iomem *reg, u8 shift, unsigned long flags)
252 {
253 	return clk_register_gate2(NULL, name, parent, flags | CLK_SET_RATE_PARENT, reg,
254 			shift, 0x3, 0, &imx_ccm_lock, NULL);
255 }
256 
257 static inline struct clk *imx_clk_gate2_shared(const char *name,
258 		const char *parent, void __iomem *reg, u8 shift,
259 		unsigned int *share_count)
260 {
261 	return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
262 			shift, 0x3, 0, &imx_ccm_lock, share_count);
263 }
264 
265 static inline struct clk *imx_clk_gate2_shared2(const char *name,
266 		const char *parent, void __iomem *reg, u8 shift,
267 		unsigned int *share_count)
268 {
269 	return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT |
270 				  CLK_OPS_PARENT_ENABLE, reg, shift, 0x3, 0,
271 				  &imx_ccm_lock, share_count);
272 }
273 
274 static inline struct clk *imx_clk_gate2_cgr(const char *name,
275 		const char *parent, void __iomem *reg, u8 shift, u8 cgr_val)
276 {
277 	return clk_register_gate2(NULL, name, parent, CLK_SET_RATE_PARENT, reg,
278 			shift, cgr_val, 0, &imx_ccm_lock, NULL);
279 }
280 
281 static inline struct clk *imx_clk_gate3(const char *name, const char *parent,
282 		void __iomem *reg, u8 shift)
283 {
284 	return clk_register_gate(NULL, name, parent,
285 			CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
286 			reg, shift, 0, &imx_ccm_lock);
287 }
288 
289 static inline struct clk *imx_clk_gate3_flags(const char *name,
290 		const char *parent, void __iomem *reg, u8 shift,
291 		unsigned long flags)
292 {
293 	return clk_register_gate(NULL, name, parent,
294 			flags | CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
295 			reg, shift, 0, &imx_ccm_lock);
296 }
297 
298 static inline struct clk *imx_clk_gate4(const char *name, const char *parent,
299 		void __iomem *reg, u8 shift)
300 {
301 	return clk_register_gate2(NULL, name, parent,
302 			CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
303 			reg, shift, 0x3, 0, &imx_ccm_lock, NULL);
304 }
305 
306 static inline struct clk *imx_clk_gate4_flags(const char *name,
307 		const char *parent, void __iomem *reg, u8 shift,
308 		unsigned long flags)
309 {
310 	return clk_register_gate2(NULL, name, parent,
311 			flags | CLK_SET_RATE_PARENT | CLK_OPS_PARENT_ENABLE,
312 			reg, shift, 0x3, 0, &imx_ccm_lock, NULL);
313 }
314 
315 static inline struct clk *imx_clk_mux(const char *name, void __iomem *reg,
316 			u8 shift, u8 width, const char * const *parents,
317 			int num_parents)
318 {
319 	return clk_register_mux(NULL, name, parents, num_parents,
320 			CLK_SET_RATE_NO_REPARENT, reg, shift,
321 			width, 0, &imx_ccm_lock);
322 }
323 
324 static inline struct clk *imx_clk_mux2(const char *name, void __iomem *reg,
325 			u8 shift, u8 width, const char * const *parents,
326 			int num_parents)
327 {
328 	return clk_register_mux(NULL, name, parents, num_parents,
329 			CLK_SET_RATE_NO_REPARENT | CLK_OPS_PARENT_ENABLE,
330 			reg, shift, width, 0, &imx_ccm_lock);
331 }
332 
333 static inline struct clk_hw *imx_clk_hw_mux2(const char *name, void __iomem *reg,
334 					     u8 shift, u8 width,
335 					     const char * const *parents,
336 					     int num_parents)
337 {
338 	return clk_hw_register_mux(NULL, name, parents, num_parents,
339 				   CLK_SET_RATE_NO_REPARENT |
340 				   CLK_OPS_PARENT_ENABLE,
341 				   reg, shift, width, 0, &imx_ccm_lock);
342 }
343 
344 static inline struct clk *imx_clk_mux_flags(const char *name,
345 			void __iomem *reg, u8 shift, u8 width,
346 			const char * const *parents, int num_parents,
347 			unsigned long flags)
348 {
349 	return clk_register_mux(NULL, name, parents, num_parents,
350 			flags | CLK_SET_RATE_NO_REPARENT, reg, shift, width, 0,
351 			&imx_ccm_lock);
352 }
353 
354 static inline struct clk *imx_clk_mux2_flags(const char *name,
355 		void __iomem *reg, u8 shift, u8 width,
356 		const char * const *parents,
357 		int num_parents, unsigned long flags)
358 {
359 	return clk_register_mux(NULL, name, parents, num_parents,
360 			flags | CLK_SET_RATE_NO_REPARENT | CLK_OPS_PARENT_ENABLE,
361 			reg, shift, width, 0, &imx_ccm_lock);
362 }
363 
364 static inline struct clk_hw *imx_clk_hw_mux_flags(const char *name,
365 						  void __iomem *reg, u8 shift,
366 						  u8 width,
367 						  const char * const *parents,
368 						  int num_parents,
369 						  unsigned long flags)
370 {
371 	return clk_hw_register_mux(NULL, name, parents, num_parents,
372 				   flags | CLK_SET_RATE_NO_REPARENT,
373 				   reg, shift, width, 0, &imx_ccm_lock);
374 }
375 
376 struct clk *imx_clk_cpu(const char *name, const char *parent_name,
377 		struct clk *div, struct clk *mux, struct clk *pll,
378 		struct clk *step);
379 
380 struct clk *imx8m_clk_composite_flags(const char *name,
381 					const char * const *parent_names,
382 					int num_parents, void __iomem *reg,
383 					unsigned long flags);
384 
385 #define __imx8m_clk_composite(name, parent_names, reg, flags) \
386 	imx8m_clk_composite_flags(name, parent_names, \
387 		ARRAY_SIZE(parent_names), reg, \
388 		flags | CLK_SET_RATE_NO_REPARENT | CLK_OPS_PARENT_ENABLE)
389 
390 #define imx8m_clk_composite(name, parent_names, reg) \
391 	__imx8m_clk_composite(name, parent_names, reg, 0)
392 
393 #define imx8m_clk_composite_critical(name, parent_names, reg) \
394 	__imx8m_clk_composite(name, parent_names, reg, CLK_IS_CRITICAL)
395 
396 struct clk_hw *imx_clk_divider_gate(const char *name, const char *parent_name,
397 		unsigned long flags, void __iomem *reg, u8 shift, u8 width,
398 		u8 clk_divider_flags, const struct clk_div_table *table,
399 		spinlock_t *lock);
400 #endif
401