xref: /openbmc/linux/drivers/clk/samsung/clk.h (revision e6dec923)
1 /*
2  * Copyright (c) 2013 Samsung Electronics Co., Ltd.
3  * Copyright (c) 2013 Linaro Ltd.
4  * Author: Thomas Abraham <thomas.ab@samsung.com>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation.
9  *
10  * Common Clock Framework support for all Samsung platforms
11 */
12 
13 #ifndef __SAMSUNG_CLK_H
14 #define __SAMSUNG_CLK_H
15 
16 #include <linux/clk-provider.h>
17 #include "clk-pll.h"
18 
19 /**
20  * struct samsung_clk_provider: information about clock provider
21  * @reg_base: virtual address for the register base.
22  * @lock: maintains exclusion between callbacks for a given clock-provider.
23  * @clk_data: holds clock related data like clk_hw* and number of clocks.
24  */
25 struct samsung_clk_provider {
26 	void __iomem *reg_base;
27 	spinlock_t lock;
28 	/* clk_data must be the last entry due to variable lenght 'hws' array */
29 	struct clk_hw_onecell_data clk_data;
30 };
31 
32 /**
33  * struct samsung_clock_alias: information about mux clock
34  * @id: platform specific id of the clock.
35  * @dev_name: name of the device to which this clock belongs.
36  * @alias: optional clock alias name to be assigned to this clock.
37  */
38 struct samsung_clock_alias {
39 	unsigned int		id;
40 	const char		*dev_name;
41 	const char		*alias;
42 };
43 
44 #define ALIAS(_id, dname, a)	\
45 	{							\
46 		.id		= _id,				\
47 		.dev_name	= dname,			\
48 		.alias		= a,				\
49 	}
50 
51 #define MHZ (1000 * 1000)
52 
53 /**
54  * struct samsung_fixed_rate_clock: information about fixed-rate clock
55  * @id: platform specific id of the clock.
56  * @name: name of this fixed-rate clock.
57  * @parent_name: optional parent clock name.
58  * @flags: optional fixed-rate clock flags.
59  * @fixed-rate: fixed clock rate of this clock.
60  */
61 struct samsung_fixed_rate_clock {
62 	unsigned int		id;
63 	char			*name;
64 	const char		*parent_name;
65 	unsigned long		flags;
66 	unsigned long		fixed_rate;
67 };
68 
69 #define FRATE(_id, cname, pname, f, frate)		\
70 	{						\
71 		.id		= _id,			\
72 		.name		= cname,		\
73 		.parent_name	= pname,		\
74 		.flags		= f,			\
75 		.fixed_rate	= frate,		\
76 	}
77 
78 /*
79  * struct samsung_fixed_factor_clock: information about fixed-factor clock
80  * @id: platform specific id of the clock.
81  * @name: name of this fixed-factor clock.
82  * @parent_name: parent clock name.
83  * @mult: fixed multiplication factor.
84  * @div: fixed division factor.
85  * @flags: optional fixed-factor clock flags.
86  */
87 struct samsung_fixed_factor_clock {
88 	unsigned int		id;
89 	char			*name;
90 	const char		*parent_name;
91 	unsigned long		mult;
92 	unsigned long		div;
93 	unsigned long		flags;
94 };
95 
96 #define FFACTOR(_id, cname, pname, m, d, f)		\
97 	{						\
98 		.id		= _id,			\
99 		.name		= cname,		\
100 		.parent_name	= pname,		\
101 		.mult		= m,			\
102 		.div		= d,			\
103 		.flags		= f,			\
104 	}
105 
106 /**
107  * struct samsung_mux_clock: information about mux clock
108  * @id: platform specific id of the clock.
109  * @dev_name: name of the device to which this clock belongs.
110  * @name: name of this mux clock.
111  * @parent_names: array of pointer to parent clock names.
112  * @num_parents: number of parents listed in @parent_names.
113  * @flags: optional flags for basic clock.
114  * @offset: offset of the register for configuring the mux.
115  * @shift: starting bit location of the mux control bit-field in @reg.
116  * @width: width of the mux control bit-field in @reg.
117  * @mux_flags: flags for mux-type clock.
118  * @alias: optional clock alias name to be assigned to this clock.
119  */
120 struct samsung_mux_clock {
121 	unsigned int		id;
122 	const char		*dev_name;
123 	const char		*name;
124 	const char		*const *parent_names;
125 	u8			num_parents;
126 	unsigned long		flags;
127 	unsigned long		offset;
128 	u8			shift;
129 	u8			width;
130 	u8			mux_flags;
131 	const char		*alias;
132 };
133 
134 #define __MUX(_id, dname, cname, pnames, o, s, w, f, mf, a)	\
135 	{							\
136 		.id		= _id,				\
137 		.dev_name	= dname,			\
138 		.name		= cname,			\
139 		.parent_names	= pnames,			\
140 		.num_parents	= ARRAY_SIZE(pnames),		\
141 		.flags		= (f) | CLK_SET_RATE_NO_REPARENT, \
142 		.offset		= o,				\
143 		.shift		= s,				\
144 		.width		= w,				\
145 		.mux_flags	= mf,				\
146 		.alias		= a,				\
147 	}
148 
149 #define MUX(_id, cname, pnames, o, s, w)			\
150 	__MUX(_id, NULL, cname, pnames, o, s, w, 0, 0, NULL)
151 
152 #define MUX_A(_id, cname, pnames, o, s, w, a)			\
153 	__MUX(_id, NULL, cname, pnames, o, s, w, 0, 0, a)
154 
155 #define MUX_F(_id, cname, pnames, o, s, w, f, mf)		\
156 	__MUX(_id, NULL, cname, pnames, o, s, w, f, mf, NULL)
157 
158 #define MUX_FA(_id, cname, pnames, o, s, w, f, mf, a)		\
159 	__MUX(_id, NULL, cname, pnames, o, s, w, f, mf, a)
160 
161 /**
162  * @id: platform specific id of the clock.
163  * struct samsung_div_clock: information about div clock
164  * @dev_name: name of the device to which this clock belongs.
165  * @name: name of this div clock.
166  * @parent_name: name of the parent clock.
167  * @flags: optional flags for basic clock.
168  * @offset: offset of the register for configuring the div.
169  * @shift: starting bit location of the div control bit-field in @reg.
170  * @div_flags: flags for div-type clock.
171  * @alias: optional clock alias name to be assigned to this clock.
172  */
173 struct samsung_div_clock {
174 	unsigned int		id;
175 	const char		*dev_name;
176 	const char		*name;
177 	const char		*parent_name;
178 	unsigned long		flags;
179 	unsigned long		offset;
180 	u8			shift;
181 	u8			width;
182 	u8			div_flags;
183 	const char		*alias;
184 	struct clk_div_table	*table;
185 };
186 
187 #define __DIV(_id, dname, cname, pname, o, s, w, f, df, a, t)	\
188 	{							\
189 		.id		= _id,				\
190 		.dev_name	= dname,			\
191 		.name		= cname,			\
192 		.parent_name	= pname,			\
193 		.flags		= f,				\
194 		.offset		= o,				\
195 		.shift		= s,				\
196 		.width		= w,				\
197 		.div_flags	= df,				\
198 		.alias		= a,				\
199 		.table		= t,				\
200 	}
201 
202 #define DIV(_id, cname, pname, o, s, w)				\
203 	__DIV(_id, NULL, cname, pname, o, s, w, 0, 0, NULL, NULL)
204 
205 #define DIV_A(_id, cname, pname, o, s, w, a)			\
206 	__DIV(_id, NULL, cname, pname, o, s, w, 0, 0, a, NULL)
207 
208 #define DIV_F(_id, cname, pname, o, s, w, f, df)		\
209 	__DIV(_id, NULL, cname, pname, o, s, w, f, df, NULL, NULL)
210 
211 #define DIV_T(_id, cname, pname, o, s, w, t)			\
212 	__DIV(_id, NULL, cname, pname, o, s, w, 0, 0, NULL, t)
213 
214 /**
215  * struct samsung_gate_clock: information about gate clock
216  * @id: platform specific id of the clock.
217  * @dev_name: name of the device to which this clock belongs.
218  * @name: name of this gate clock.
219  * @parent_name: name of the parent clock.
220  * @flags: optional flags for basic clock.
221  * @offset: offset of the register for configuring the gate.
222  * @bit_idx: bit index of the gate control bit-field in @reg.
223  * @gate_flags: flags for gate-type clock.
224  * @alias: optional clock alias name to be assigned to this clock.
225  */
226 struct samsung_gate_clock {
227 	unsigned int		id;
228 	const char		*dev_name;
229 	const char		*name;
230 	const char		*parent_name;
231 	unsigned long		flags;
232 	unsigned long		offset;
233 	u8			bit_idx;
234 	u8			gate_flags;
235 	const char		*alias;
236 };
237 
238 #define __GATE(_id, dname, cname, pname, o, b, f, gf, a)	\
239 	{							\
240 		.id		= _id,				\
241 		.dev_name	= dname,			\
242 		.name		= cname,			\
243 		.parent_name	= pname,			\
244 		.flags		= f,				\
245 		.offset		= o,				\
246 		.bit_idx	= b,				\
247 		.gate_flags	= gf,				\
248 		.alias		= a,				\
249 	}
250 
251 #define GATE(_id, cname, pname, o, b, f, gf)			\
252 	__GATE(_id, NULL, cname, pname, o, b, f, gf, NULL)
253 
254 #define GATE_A(_id, cname, pname, o, b, f, gf, a)		\
255 	__GATE(_id, NULL, cname, pname, o, b, f, gf, a)
256 
257 #define GATE_D(_id, dname, cname, pname, o, b, f, gf)		\
258 	__GATE(_id, dname, cname, pname, o, b, f, gf, NULL)
259 
260 #define GATE_DA(_id, dname, cname, pname, o, b, f, gf, a)	\
261 	__GATE(_id, dname, cname, pname, o, b, f, gf, a)
262 
263 #define PNAME(x) static const char * const x[] __initconst
264 
265 /**
266  * struct samsung_clk_reg_dump: register dump of clock controller registers.
267  * @offset: clock register offset from the controller base address.
268  * @value: the value to be register at offset.
269  */
270 struct samsung_clk_reg_dump {
271 	u32	offset;
272 	u32	value;
273 };
274 
275 /**
276  * struct samsung_pll_clock: information about pll clock
277  * @id: platform specific id of the clock.
278  * @dev_name: name of the device to which this clock belongs.
279  * @name: name of this pll clock.
280  * @parent_name: name of the parent clock.
281  * @flags: optional flags for basic clock.
282  * @con_offset: offset of the register for configuring the PLL.
283  * @lock_offset: offset of the register for locking the PLL.
284  * @type: Type of PLL to be registered.
285  * @alias: optional clock alias name to be assigned to this clock.
286  */
287 struct samsung_pll_clock {
288 	unsigned int		id;
289 	const char		*dev_name;
290 	const char		*name;
291 	const char		*parent_name;
292 	unsigned long		flags;
293 	int			con_offset;
294 	int			lock_offset;
295 	enum samsung_pll_type	type;
296 	const struct samsung_pll_rate_table *rate_table;
297 	const char              *alias;
298 };
299 
300 #define __PLL(_typ, _id, _dname, _name, _pname, _flags, _lock, _con,	\
301 		_rtable, _alias)					\
302 	{								\
303 		.id		= _id,					\
304 		.type		= _typ,					\
305 		.dev_name	= _dname,				\
306 		.name		= _name,				\
307 		.parent_name	= _pname,				\
308 		.flags		= CLK_GET_RATE_NOCACHE,			\
309 		.con_offset	= _con,					\
310 		.lock_offset	= _lock,				\
311 		.rate_table	= _rtable,				\
312 		.alias		= _alias,				\
313 	}
314 
315 #define PLL(_typ, _id, _name, _pname, _lock, _con, _rtable)	\
316 	__PLL(_typ, _id, NULL, _name, _pname, CLK_GET_RATE_NOCACHE,	\
317 		_lock, _con, _rtable, _name)
318 
319 #define PLL_A(_typ, _id, _name, _pname, _lock, _con, _alias, _rtable) \
320 	__PLL(_typ, _id, NULL, _name, _pname, CLK_GET_RATE_NOCACHE,	\
321 		_lock, _con, _rtable, _alias)
322 
323 struct samsung_clock_reg_cache {
324 	struct list_head node;
325 	void __iomem *reg_base;
326 	struct samsung_clk_reg_dump *rdump;
327 	unsigned int rd_num;
328 };
329 
330 struct samsung_cmu_info {
331 	/* list of pll clocks and respective count */
332 	const struct samsung_pll_clock *pll_clks;
333 	unsigned int nr_pll_clks;
334 	/* list of mux clocks and respective count */
335 	const struct samsung_mux_clock *mux_clks;
336 	unsigned int nr_mux_clks;
337 	/* list of div clocks and respective count */
338 	const struct samsung_div_clock *div_clks;
339 	unsigned int nr_div_clks;
340 	/* list of gate clocks and respective count */
341 	const struct samsung_gate_clock *gate_clks;
342 	unsigned int nr_gate_clks;
343 	/* list of fixed clocks and respective count */
344 	const struct samsung_fixed_rate_clock *fixed_clks;
345 	unsigned int nr_fixed_clks;
346 	/* list of fixed factor clocks and respective count */
347 	const struct samsung_fixed_factor_clock *fixed_factor_clks;
348 	unsigned int nr_fixed_factor_clks;
349 	/* total number of clocks with IDs assigned*/
350 	unsigned int nr_clk_ids;
351 
352 	/* list and number of clocks registers */
353 	const unsigned long *clk_regs;
354 	unsigned int nr_clk_regs;
355 };
356 
357 extern struct samsung_clk_provider *__init samsung_clk_init(
358 			struct device_node *np, void __iomem *base,
359 			unsigned long nr_clks);
360 extern void __init samsung_clk_of_add_provider(struct device_node *np,
361 			struct samsung_clk_provider *ctx);
362 extern void __init samsung_clk_of_register_fixed_ext(
363 			struct samsung_clk_provider *ctx,
364 			struct samsung_fixed_rate_clock *fixed_rate_clk,
365 			unsigned int nr_fixed_rate_clk,
366 			const struct of_device_id *clk_matches);
367 
368 extern void samsung_clk_add_lookup(struct samsung_clk_provider *ctx,
369 			struct clk_hw *clk_hw, unsigned int id);
370 
371 extern void __init samsung_clk_register_alias(struct samsung_clk_provider *ctx,
372 			const struct samsung_clock_alias *list,
373 			unsigned int nr_clk);
374 extern void __init samsung_clk_register_fixed_rate(
375 			struct samsung_clk_provider *ctx,
376 			const struct samsung_fixed_rate_clock *clk_list,
377 			unsigned int nr_clk);
378 extern void __init samsung_clk_register_fixed_factor(
379 			struct samsung_clk_provider *ctx,
380 			const struct samsung_fixed_factor_clock *list,
381 			unsigned int nr_clk);
382 extern void __init samsung_clk_register_mux(struct samsung_clk_provider *ctx,
383 			const struct samsung_mux_clock *clk_list,
384 			unsigned int nr_clk);
385 extern void __init samsung_clk_register_div(struct samsung_clk_provider *ctx,
386 			const struct samsung_div_clock *clk_list,
387 			unsigned int nr_clk);
388 extern void __init samsung_clk_register_gate(struct samsung_clk_provider *ctx,
389 			const struct samsung_gate_clock *clk_list,
390 			unsigned int nr_clk);
391 extern void __init samsung_clk_register_pll(struct samsung_clk_provider *ctx,
392 			const struct samsung_pll_clock *pll_list,
393 			unsigned int nr_clk, void __iomem *base);
394 
395 extern struct samsung_clk_provider __init *samsung_cmu_register_one(
396 			struct device_node *,
397 			const struct samsung_cmu_info *);
398 
399 extern unsigned long _get_rate(const char *clk_name);
400 
401 extern void samsung_clk_sleep_init(void __iomem *reg_base,
402 			const unsigned long *rdump,
403 			unsigned long nr_rdump);
404 
405 extern void samsung_clk_save(void __iomem *base,
406 			struct samsung_clk_reg_dump *rd,
407 			unsigned int num_regs);
408 extern void samsung_clk_restore(void __iomem *base,
409 			const struct samsung_clk_reg_dump *rd,
410 			unsigned int num_regs);
411 extern struct samsung_clk_reg_dump *samsung_clk_alloc_reg_dump(
412 			const unsigned long *rdump,
413 			unsigned long nr_rdump);
414 
415 #endif /* __SAMSUNG_CLK_H */
416