xref: /openbmc/linux/drivers/clk/ingenic/jz4780-cgu.c (revision 4b4f3acc)
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * Ingenic JZ4780 SoC CGU driver
4  *
5  * Copyright (c) 2013-2015 Imagination Technologies
6  * Author: Paul Burton <paul.burton@mips.com>
7  */
8 
9 #include <linux/clk-provider.h>
10 #include <linux/delay.h>
11 #include <linux/io.h>
12 #include <linux/of.h>
13 #include <dt-bindings/clock/jz4780-cgu.h>
14 #include "cgu.h"
15 
16 /* CGU register offsets */
17 #define CGU_REG_CLOCKCONTROL	0x00
18 #define CGU_REG_PLLCONTROL	0x0c
19 #define CGU_REG_APLL		0x10
20 #define CGU_REG_MPLL		0x14
21 #define CGU_REG_EPLL		0x18
22 #define CGU_REG_VPLL		0x1c
23 #define CGU_REG_CLKGR0		0x20
24 #define CGU_REG_OPCR		0x24
25 #define CGU_REG_CLKGR1		0x28
26 #define CGU_REG_DDRCDR		0x2c
27 #define CGU_REG_VPUCDR		0x30
28 #define CGU_REG_USBPCR		0x3c
29 #define CGU_REG_USBRDT		0x40
30 #define CGU_REG_USBVBFIL	0x44
31 #define CGU_REG_USBPCR1		0x48
32 #define CGU_REG_LP0CDR		0x54
33 #define CGU_REG_I2SCDR		0x60
34 #define CGU_REG_LP1CDR		0x64
35 #define CGU_REG_MSC0CDR		0x68
36 #define CGU_REG_UHCCDR		0x6c
37 #define CGU_REG_SSICDR		0x74
38 #define CGU_REG_CIMCDR		0x7c
39 #define CGU_REG_PCMCDR		0x84
40 #define CGU_REG_GPUCDR		0x88
41 #define CGU_REG_HDMICDR		0x8c
42 #define CGU_REG_MSC1CDR		0xa4
43 #define CGU_REG_MSC2CDR		0xa8
44 #define CGU_REG_BCHCDR		0xac
45 #define CGU_REG_CLOCKSTATUS	0xd4
46 
47 /* bits within the OPCR register */
48 #define OPCR_SPENDN0		(1 << 7)
49 #define OPCR_SPENDN1		(1 << 6)
50 
51 /* bits within the USBPCR register */
52 #define USBPCR_USB_MODE		BIT(31)
53 #define USBPCR_IDPULLUP_MASK	(0x3 << 28)
54 #define USBPCR_COMMONONN	BIT(25)
55 #define USBPCR_VBUSVLDEXT	BIT(24)
56 #define USBPCR_VBUSVLDEXTSEL	BIT(23)
57 #define USBPCR_POR		BIT(22)
58 #define USBPCR_OTG_DISABLE	BIT(20)
59 #define USBPCR_COMPDISTUNE_MASK	(0x7 << 17)
60 #define USBPCR_OTGTUNE_MASK	(0x7 << 14)
61 #define USBPCR_SQRXTUNE_MASK	(0x7 << 11)
62 #define USBPCR_TXFSLSTUNE_MASK	(0xf << 7)
63 #define USBPCR_TXPREEMPHTUNE	BIT(6)
64 #define USBPCR_TXHSXVTUNE_MASK	(0x3 << 4)
65 #define USBPCR_TXVREFTUNE_MASK	0xf
66 
67 /* bits within the USBPCR1 register */
68 #define USBPCR1_REFCLKSEL_SHIFT	26
69 #define USBPCR1_REFCLKSEL_MASK	(0x3 << USBPCR1_REFCLKSEL_SHIFT)
70 #define USBPCR1_REFCLKSEL_CORE	(0x2 << USBPCR1_REFCLKSEL_SHIFT)
71 #define USBPCR1_REFCLKDIV_SHIFT	24
72 #define USBPCR1_REFCLKDIV_MASK	(0x3 << USBPCR1_REFCLKDIV_SHIFT)
73 #define USBPCR1_REFCLKDIV_19_2	(0x3 << USBPCR1_REFCLKDIV_SHIFT)
74 #define USBPCR1_REFCLKDIV_48	(0x2 << USBPCR1_REFCLKDIV_SHIFT)
75 #define USBPCR1_REFCLKDIV_24	(0x1 << USBPCR1_REFCLKDIV_SHIFT)
76 #define USBPCR1_REFCLKDIV_12	(0x0 << USBPCR1_REFCLKDIV_SHIFT)
77 #define USBPCR1_USB_SEL		BIT(28)
78 #define USBPCR1_WORD_IF0	BIT(19)
79 #define USBPCR1_WORD_IF1	BIT(18)
80 
81 /* bits within the USBRDT register */
82 #define USBRDT_VBFIL_LD_EN	BIT(25)
83 #define USBRDT_USBRDT_MASK	0x7fffff
84 
85 /* bits within the USBVBFIL register */
86 #define USBVBFIL_IDDIGFIL_SHIFT	16
87 #define USBVBFIL_IDDIGFIL_MASK	(0xffff << USBVBFIL_IDDIGFIL_SHIFT)
88 #define USBVBFIL_USBVBFIL_MASK	(0xffff)
89 
90 static struct ingenic_cgu *cgu;
91 
92 static u8 jz4780_otg_phy_get_parent(struct clk_hw *hw)
93 {
94 	/* we only use CLKCORE, revisit if that ever changes */
95 	return 0;
96 }
97 
98 static int jz4780_otg_phy_set_parent(struct clk_hw *hw, u8 idx)
99 {
100 	unsigned long flags;
101 	u32 usbpcr1;
102 
103 	if (idx > 0)
104 		return -EINVAL;
105 
106 	spin_lock_irqsave(&cgu->lock, flags);
107 
108 	usbpcr1 = readl(cgu->base + CGU_REG_USBPCR1);
109 	usbpcr1 &= ~USBPCR1_REFCLKSEL_MASK;
110 	/* we only use CLKCORE */
111 	usbpcr1 |= USBPCR1_REFCLKSEL_CORE;
112 	writel(usbpcr1, cgu->base + CGU_REG_USBPCR1);
113 
114 	spin_unlock_irqrestore(&cgu->lock, flags);
115 	return 0;
116 }
117 
118 static unsigned long jz4780_otg_phy_recalc_rate(struct clk_hw *hw,
119 						unsigned long parent_rate)
120 {
121 	u32 usbpcr1;
122 	unsigned refclk_div;
123 
124 	usbpcr1 = readl(cgu->base + CGU_REG_USBPCR1);
125 	refclk_div = usbpcr1 & USBPCR1_REFCLKDIV_MASK;
126 
127 	switch (refclk_div) {
128 	case USBPCR1_REFCLKDIV_12:
129 		return 12000000;
130 
131 	case USBPCR1_REFCLKDIV_24:
132 		return 24000000;
133 
134 	case USBPCR1_REFCLKDIV_48:
135 		return 48000000;
136 
137 	case USBPCR1_REFCLKDIV_19_2:
138 		return 19200000;
139 	}
140 
141 	BUG();
142 	return parent_rate;
143 }
144 
145 static long jz4780_otg_phy_round_rate(struct clk_hw *hw, unsigned long req_rate,
146 				      unsigned long *parent_rate)
147 {
148 	if (req_rate < 15600000)
149 		return 12000000;
150 
151 	if (req_rate < 21600000)
152 		return 19200000;
153 
154 	if (req_rate < 36000000)
155 		return 24000000;
156 
157 	return 48000000;
158 }
159 
160 static int jz4780_otg_phy_set_rate(struct clk_hw *hw, unsigned long req_rate,
161 				   unsigned long parent_rate)
162 {
163 	unsigned long flags;
164 	u32 usbpcr1, div_bits;
165 
166 	switch (req_rate) {
167 	case 12000000:
168 		div_bits = USBPCR1_REFCLKDIV_12;
169 		break;
170 
171 	case 19200000:
172 		div_bits = USBPCR1_REFCLKDIV_19_2;
173 		break;
174 
175 	case 24000000:
176 		div_bits = USBPCR1_REFCLKDIV_24;
177 		break;
178 
179 	case 48000000:
180 		div_bits = USBPCR1_REFCLKDIV_48;
181 		break;
182 
183 	default:
184 		return -EINVAL;
185 	}
186 
187 	spin_lock_irqsave(&cgu->lock, flags);
188 
189 	usbpcr1 = readl(cgu->base + CGU_REG_USBPCR1);
190 	usbpcr1 &= ~USBPCR1_REFCLKDIV_MASK;
191 	usbpcr1 |= div_bits;
192 	writel(usbpcr1, cgu->base + CGU_REG_USBPCR1);
193 
194 	spin_unlock_irqrestore(&cgu->lock, flags);
195 	return 0;
196 }
197 
198 static const struct clk_ops jz4780_otg_phy_ops = {
199 	.get_parent = jz4780_otg_phy_get_parent,
200 	.set_parent = jz4780_otg_phy_set_parent,
201 
202 	.recalc_rate = jz4780_otg_phy_recalc_rate,
203 	.round_rate = jz4780_otg_phy_round_rate,
204 	.set_rate = jz4780_otg_phy_set_rate,
205 };
206 
207 static const s8 pll_od_encoding[16] = {
208 	0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7,
209 	0x8, 0x9, 0xa, 0xb, 0xc, 0xd, 0xe, 0xf,
210 };
211 
212 static const struct ingenic_cgu_clk_info jz4780_cgu_clocks[] = {
213 
214 	/* External clocks */
215 
216 	[JZ4780_CLK_EXCLK] = { "ext", CGU_CLK_EXT },
217 	[JZ4780_CLK_RTCLK] = { "rtc", CGU_CLK_EXT },
218 
219 	/* PLLs */
220 
221 #define DEF_PLL(name) { \
222 	.reg = CGU_REG_ ## name, \
223 	.m_shift = 19, \
224 	.m_bits = 13, \
225 	.m_offset = 1, \
226 	.n_shift = 13, \
227 	.n_bits = 6, \
228 	.n_offset = 1, \
229 	.od_shift = 9, \
230 	.od_bits = 4, \
231 	.od_max = 16, \
232 	.od_encoding = pll_od_encoding, \
233 	.stable_bit = 6, \
234 	.bypass_bit = 1, \
235 	.enable_bit = 0, \
236 }
237 
238 	[JZ4780_CLK_APLL] = {
239 		"apll", CGU_CLK_PLL,
240 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
241 		.pll = DEF_PLL(APLL),
242 	},
243 
244 	[JZ4780_CLK_MPLL] = {
245 		"mpll", CGU_CLK_PLL,
246 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
247 		.pll = DEF_PLL(MPLL),
248 	},
249 
250 	[JZ4780_CLK_EPLL] = {
251 		"epll", CGU_CLK_PLL,
252 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
253 		.pll = DEF_PLL(EPLL),
254 	},
255 
256 	[JZ4780_CLK_VPLL] = {
257 		"vpll", CGU_CLK_PLL,
258 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
259 		.pll = DEF_PLL(VPLL),
260 	},
261 
262 #undef DEF_PLL
263 
264 	/* Custom (SoC-specific) OTG PHY */
265 
266 	[JZ4780_CLK_OTGPHY] = {
267 		"otg_phy", CGU_CLK_CUSTOM,
268 		.parents = { -1, -1, JZ4780_CLK_EXCLK, -1 },
269 		.custom = { &jz4780_otg_phy_ops },
270 	},
271 
272 	/* Muxes & dividers */
273 
274 	[JZ4780_CLK_SCLKA] = {
275 		"sclk_a", CGU_CLK_MUX,
276 		.parents = { -1, JZ4780_CLK_APLL, JZ4780_CLK_EXCLK,
277 			     JZ4780_CLK_RTCLK },
278 		.mux = { CGU_REG_CLOCKCONTROL, 30, 2 },
279 	},
280 
281 	[JZ4780_CLK_CPUMUX] = {
282 		"cpumux", CGU_CLK_MUX,
283 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
284 			     JZ4780_CLK_EPLL },
285 		.mux = { CGU_REG_CLOCKCONTROL, 28, 2 },
286 	},
287 
288 	[JZ4780_CLK_CPU] = {
289 		"cpu", CGU_CLK_DIV,
290 		.parents = { JZ4780_CLK_CPUMUX, -1, -1, -1 },
291 		.div = { CGU_REG_CLOCKCONTROL, 0, 1, 4, 22, -1, -1 },
292 	},
293 
294 	[JZ4780_CLK_L2CACHE] = {
295 		"l2cache", CGU_CLK_DIV,
296 		.parents = { JZ4780_CLK_CPUMUX, -1, -1, -1 },
297 		.div = { CGU_REG_CLOCKCONTROL, 4, 1, 4, -1, -1, -1 },
298 	},
299 
300 	[JZ4780_CLK_AHB0] = {
301 		"ahb0", CGU_CLK_MUX | CGU_CLK_DIV,
302 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
303 			     JZ4780_CLK_EPLL },
304 		.mux = { CGU_REG_CLOCKCONTROL, 26, 2 },
305 		.div = { CGU_REG_CLOCKCONTROL, 8, 1, 4, 21, -1, -1 },
306 	},
307 
308 	[JZ4780_CLK_AHB2PMUX] = {
309 		"ahb2_apb_mux", CGU_CLK_MUX,
310 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
311 			     JZ4780_CLK_RTCLK },
312 		.mux = { CGU_REG_CLOCKCONTROL, 24, 2 },
313 	},
314 
315 	[JZ4780_CLK_AHB2] = {
316 		"ahb2", CGU_CLK_DIV,
317 		.parents = { JZ4780_CLK_AHB2PMUX, -1, -1, -1 },
318 		.div = { CGU_REG_CLOCKCONTROL, 12, 1, 4, 20, -1, -1 },
319 	},
320 
321 	[JZ4780_CLK_PCLK] = {
322 		"pclk", CGU_CLK_DIV,
323 		.parents = { JZ4780_CLK_AHB2PMUX, -1, -1, -1 },
324 		.div = { CGU_REG_CLOCKCONTROL, 16, 1, 4, 20, -1, -1 },
325 	},
326 
327 	[JZ4780_CLK_DDR] = {
328 		"ddr", CGU_CLK_MUX | CGU_CLK_DIV,
329 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL, -1 },
330 		.mux = { CGU_REG_DDRCDR, 30, 2 },
331 		.div = { CGU_REG_DDRCDR, 0, 1, 4, 29, 28, 27 },
332 	},
333 
334 	[JZ4780_CLK_VPU] = {
335 		"vpu", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE,
336 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
337 			     JZ4780_CLK_EPLL, -1 },
338 		.mux = { CGU_REG_VPUCDR, 30, 2 },
339 		.div = { CGU_REG_VPUCDR, 0, 1, 4, 29, 28, 27 },
340 		.gate = { CGU_REG_CLKGR1, 2 },
341 	},
342 
343 	[JZ4780_CLK_I2SPLL] = {
344 		"i2s_pll", CGU_CLK_MUX | CGU_CLK_DIV,
345 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_EPLL, -1, -1 },
346 		.mux = { CGU_REG_I2SCDR, 30, 1 },
347 		.div = { CGU_REG_I2SCDR, 0, 1, 8, 29, 28, 27 },
348 	},
349 
350 	[JZ4780_CLK_I2S] = {
351 		"i2s", CGU_CLK_MUX,
352 		.parents = { JZ4780_CLK_EXCLK, JZ4780_CLK_I2SPLL, -1, -1 },
353 		.mux = { CGU_REG_I2SCDR, 31, 1 },
354 	},
355 
356 	[JZ4780_CLK_LCD0PIXCLK] = {
357 		"lcd0pixclk", CGU_CLK_MUX | CGU_CLK_DIV,
358 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
359 			     JZ4780_CLK_VPLL, -1 },
360 		.mux = { CGU_REG_LP0CDR, 30, 2 },
361 		.div = { CGU_REG_LP0CDR, 0, 1, 8, 28, 27, 26 },
362 	},
363 
364 	[JZ4780_CLK_LCD1PIXCLK] = {
365 		"lcd1pixclk", CGU_CLK_MUX | CGU_CLK_DIV,
366 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
367 			     JZ4780_CLK_VPLL, -1 },
368 		.mux = { CGU_REG_LP1CDR, 30, 2 },
369 		.div = { CGU_REG_LP1CDR, 0, 1, 8, 28, 27, 26 },
370 	},
371 
372 	[JZ4780_CLK_MSCMUX] = {
373 		"msc_mux", CGU_CLK_MUX,
374 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL, -1 },
375 		.mux = { CGU_REG_MSC0CDR, 30, 2 },
376 	},
377 
378 	[JZ4780_CLK_MSC0] = {
379 		"msc0", CGU_CLK_DIV | CGU_CLK_GATE,
380 		.parents = { JZ4780_CLK_MSCMUX, -1, -1, -1 },
381 		.div = { CGU_REG_MSC0CDR, 0, 2, 8, 29, 28, 27 },
382 		.gate = { CGU_REG_CLKGR0, 3 },
383 	},
384 
385 	[JZ4780_CLK_MSC1] = {
386 		"msc1", CGU_CLK_DIV | CGU_CLK_GATE,
387 		.parents = { JZ4780_CLK_MSCMUX, -1, -1, -1 },
388 		.div = { CGU_REG_MSC1CDR, 0, 2, 8, 29, 28, 27 },
389 		.gate = { CGU_REG_CLKGR0, 11 },
390 	},
391 
392 	[JZ4780_CLK_MSC2] = {
393 		"msc2", CGU_CLK_DIV | CGU_CLK_GATE,
394 		.parents = { JZ4780_CLK_MSCMUX, -1, -1, -1 },
395 		.div = { CGU_REG_MSC2CDR, 0, 2, 8, 29, 28, 27 },
396 		.gate = { CGU_REG_CLKGR0, 12 },
397 	},
398 
399 	[JZ4780_CLK_UHC] = {
400 		"uhc", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE,
401 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
402 			     JZ4780_CLK_EPLL, JZ4780_CLK_OTGPHY },
403 		.mux = { CGU_REG_UHCCDR, 30, 2 },
404 		.div = { CGU_REG_UHCCDR, 0, 1, 8, 29, 28, 27 },
405 		.gate = { CGU_REG_CLKGR0, 24 },
406 	},
407 
408 	[JZ4780_CLK_SSIPLL] = {
409 		"ssi_pll", CGU_CLK_MUX | CGU_CLK_DIV,
410 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL, -1, -1 },
411 		.mux = { CGU_REG_SSICDR, 30, 1 },
412 		.div = { CGU_REG_SSICDR, 0, 1, 8, 29, 28, 27 },
413 	},
414 
415 	[JZ4780_CLK_SSI] = {
416 		"ssi", CGU_CLK_MUX,
417 		.parents = { JZ4780_CLK_EXCLK, JZ4780_CLK_SSIPLL, -1, -1 },
418 		.mux = { CGU_REG_SSICDR, 31, 1 },
419 	},
420 
421 	[JZ4780_CLK_CIMMCLK] = {
422 		"cim_mclk", CGU_CLK_MUX | CGU_CLK_DIV,
423 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL, -1, -1 },
424 		.mux = { CGU_REG_CIMCDR, 31, 1 },
425 		.div = { CGU_REG_CIMCDR, 0, 1, 8, 30, 29, 28 },
426 	},
427 
428 	[JZ4780_CLK_PCMPLL] = {
429 		"pcm_pll", CGU_CLK_MUX | CGU_CLK_DIV,
430 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
431 			     JZ4780_CLK_EPLL, JZ4780_CLK_VPLL },
432 		.mux = { CGU_REG_PCMCDR, 29, 2 },
433 		.div = { CGU_REG_PCMCDR, 0, 1, 8, 28, 27, 26 },
434 	},
435 
436 	[JZ4780_CLK_PCM] = {
437 		"pcm", CGU_CLK_MUX | CGU_CLK_GATE,
438 		.parents = { JZ4780_CLK_EXCLK, JZ4780_CLK_PCMPLL, -1, -1 },
439 		.mux = { CGU_REG_PCMCDR, 31, 1 },
440 		.gate = { CGU_REG_CLKGR1, 3 },
441 	},
442 
443 	[JZ4780_CLK_GPU] = {
444 		"gpu", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE,
445 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
446 			     JZ4780_CLK_EPLL },
447 		.mux = { CGU_REG_GPUCDR, 30, 2 },
448 		.div = { CGU_REG_GPUCDR, 0, 1, 4, 29, 28, 27 },
449 		.gate = { CGU_REG_CLKGR1, 4 },
450 	},
451 
452 	[JZ4780_CLK_HDMI] = {
453 		"hdmi", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE,
454 		.parents = { JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
455 			     JZ4780_CLK_VPLL, -1 },
456 		.mux = { CGU_REG_HDMICDR, 30, 2 },
457 		.div = { CGU_REG_HDMICDR, 0, 1, 8, 29, 28, 26 },
458 		.gate = { CGU_REG_CLKGR1, 9 },
459 	},
460 
461 	[JZ4780_CLK_BCH] = {
462 		"bch", CGU_CLK_MUX | CGU_CLK_DIV | CGU_CLK_GATE,
463 		.parents = { -1, JZ4780_CLK_SCLKA, JZ4780_CLK_MPLL,
464 			     JZ4780_CLK_EPLL },
465 		.mux = { CGU_REG_BCHCDR, 30, 2 },
466 		.div = { CGU_REG_BCHCDR, 0, 1, 4, 29, 28, 27 },
467 		.gate = { CGU_REG_CLKGR0, 1 },
468 	},
469 
470 	/* Gate-only clocks */
471 
472 	[JZ4780_CLK_NEMC] = {
473 		"nemc", CGU_CLK_GATE,
474 		.parents = { JZ4780_CLK_AHB2, -1, -1, -1 },
475 		.gate = { CGU_REG_CLKGR0, 0 },
476 	},
477 
478 	[JZ4780_CLK_OTG0] = {
479 		"otg0", CGU_CLK_GATE,
480 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
481 		.gate = { CGU_REG_CLKGR0, 2 },
482 	},
483 
484 	[JZ4780_CLK_SSI0] = {
485 		"ssi0", CGU_CLK_GATE,
486 		.parents = { JZ4780_CLK_SSI, -1, -1, -1 },
487 		.gate = { CGU_REG_CLKGR0, 4 },
488 	},
489 
490 	[JZ4780_CLK_SMB0] = {
491 		"smb0", CGU_CLK_GATE,
492 		.parents = { JZ4780_CLK_PCLK, -1, -1, -1 },
493 		.gate = { CGU_REG_CLKGR0, 5 },
494 	},
495 
496 	[JZ4780_CLK_SMB1] = {
497 		"smb1", CGU_CLK_GATE,
498 		.parents = { JZ4780_CLK_PCLK, -1, -1, -1 },
499 		.gate = { CGU_REG_CLKGR0, 6 },
500 	},
501 
502 	[JZ4780_CLK_SCC] = {
503 		"scc", CGU_CLK_GATE,
504 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
505 		.gate = { CGU_REG_CLKGR0, 7 },
506 	},
507 
508 	[JZ4780_CLK_AIC] = {
509 		"aic", CGU_CLK_GATE,
510 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
511 		.gate = { CGU_REG_CLKGR0, 8 },
512 	},
513 
514 	[JZ4780_CLK_TSSI0] = {
515 		"tssi0", CGU_CLK_GATE,
516 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
517 		.gate = { CGU_REG_CLKGR0, 9 },
518 	},
519 
520 	[JZ4780_CLK_OWI] = {
521 		"owi", CGU_CLK_GATE,
522 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
523 		.gate = { CGU_REG_CLKGR0, 10 },
524 	},
525 
526 	[JZ4780_CLK_KBC] = {
527 		"kbc", CGU_CLK_GATE,
528 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
529 		.gate = { CGU_REG_CLKGR0, 13 },
530 	},
531 
532 	[JZ4780_CLK_SADC] = {
533 		"sadc", CGU_CLK_GATE,
534 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
535 		.gate = { CGU_REG_CLKGR0, 14 },
536 	},
537 
538 	[JZ4780_CLK_UART0] = {
539 		"uart0", CGU_CLK_GATE,
540 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
541 		.gate = { CGU_REG_CLKGR0, 15 },
542 	},
543 
544 	[JZ4780_CLK_UART1] = {
545 		"uart1", CGU_CLK_GATE,
546 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
547 		.gate = { CGU_REG_CLKGR0, 16 },
548 	},
549 
550 	[JZ4780_CLK_UART2] = {
551 		"uart2", CGU_CLK_GATE,
552 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
553 		.gate = { CGU_REG_CLKGR0, 17 },
554 	},
555 
556 	[JZ4780_CLK_UART3] = {
557 		"uart3", CGU_CLK_GATE,
558 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
559 		.gate = { CGU_REG_CLKGR0, 18 },
560 	},
561 
562 	[JZ4780_CLK_SSI1] = {
563 		"ssi1", CGU_CLK_GATE,
564 		.parents = { JZ4780_CLK_SSI, -1, -1, -1 },
565 		.gate = { CGU_REG_CLKGR0, 19 },
566 	},
567 
568 	[JZ4780_CLK_SSI2] = {
569 		"ssi2", CGU_CLK_GATE,
570 		.parents = { JZ4780_CLK_SSI, -1, -1, -1 },
571 		.gate = { CGU_REG_CLKGR0, 20 },
572 	},
573 
574 	[JZ4780_CLK_PDMA] = {
575 		"pdma", CGU_CLK_GATE,
576 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
577 		.gate = { CGU_REG_CLKGR0, 21 },
578 	},
579 
580 	[JZ4780_CLK_GPS] = {
581 		"gps", CGU_CLK_GATE,
582 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
583 		.gate = { CGU_REG_CLKGR0, 22 },
584 	},
585 
586 	[JZ4780_CLK_MAC] = {
587 		"mac", CGU_CLK_GATE,
588 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
589 		.gate = { CGU_REG_CLKGR0, 23 },
590 	},
591 
592 	[JZ4780_CLK_SMB2] = {
593 		"smb2", CGU_CLK_GATE,
594 		.parents = { JZ4780_CLK_PCLK, -1, -1, -1 },
595 		.gate = { CGU_REG_CLKGR0, 24 },
596 	},
597 
598 	[JZ4780_CLK_CIM] = {
599 		"cim", CGU_CLK_GATE,
600 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
601 		.gate = { CGU_REG_CLKGR0, 26 },
602 	},
603 
604 	[JZ4780_CLK_LCD] = {
605 		"lcd", CGU_CLK_GATE,
606 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
607 		.gate = { CGU_REG_CLKGR0, 28 },
608 	},
609 
610 	[JZ4780_CLK_TVE] = {
611 		"tve", CGU_CLK_GATE,
612 		.parents = { JZ4780_CLK_LCD, -1, -1, -1 },
613 		.gate = { CGU_REG_CLKGR0, 27 },
614 	},
615 
616 	[JZ4780_CLK_IPU] = {
617 		"ipu", CGU_CLK_GATE,
618 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
619 		.gate = { CGU_REG_CLKGR0, 29 },
620 	},
621 
622 	[JZ4780_CLK_DDR0] = {
623 		"ddr0", CGU_CLK_GATE,
624 		.parents = { JZ4780_CLK_DDR, -1, -1, -1 },
625 		.gate = { CGU_REG_CLKGR0, 30 },
626 	},
627 
628 	[JZ4780_CLK_DDR1] = {
629 		"ddr1", CGU_CLK_GATE,
630 		.parents = { JZ4780_CLK_DDR, -1, -1, -1 },
631 		.gate = { CGU_REG_CLKGR0, 31 },
632 	},
633 
634 	[JZ4780_CLK_SMB3] = {
635 		"smb3", CGU_CLK_GATE,
636 		.parents = { JZ4780_CLK_PCLK, -1, -1, -1 },
637 		.gate = { CGU_REG_CLKGR1, 0 },
638 	},
639 
640 	[JZ4780_CLK_TSSI1] = {
641 		"tssi1", CGU_CLK_GATE,
642 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
643 		.gate = { CGU_REG_CLKGR1, 1 },
644 	},
645 
646 	[JZ4780_CLK_COMPRESS] = {
647 		"compress", CGU_CLK_GATE,
648 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
649 		.gate = { CGU_REG_CLKGR1, 5 },
650 	},
651 
652 	[JZ4780_CLK_AIC1] = {
653 		"aic1", CGU_CLK_GATE,
654 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
655 		.gate = { CGU_REG_CLKGR1, 6 },
656 	},
657 
658 	[JZ4780_CLK_GPVLC] = {
659 		"gpvlc", CGU_CLK_GATE,
660 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
661 		.gate = { CGU_REG_CLKGR1, 7 },
662 	},
663 
664 	[JZ4780_CLK_OTG1] = {
665 		"otg1", CGU_CLK_GATE,
666 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
667 		.gate = { CGU_REG_CLKGR1, 8 },
668 	},
669 
670 	[JZ4780_CLK_UART4] = {
671 		"uart4", CGU_CLK_GATE,
672 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
673 		.gate = { CGU_REG_CLKGR1, 10 },
674 	},
675 
676 	[JZ4780_CLK_AHBMON] = {
677 		"ahb_mon", CGU_CLK_GATE,
678 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
679 		.gate = { CGU_REG_CLKGR1, 11 },
680 	},
681 
682 	[JZ4780_CLK_SMB4] = {
683 		"smb4", CGU_CLK_GATE,
684 		.parents = { JZ4780_CLK_PCLK, -1, -1, -1 },
685 		.gate = { CGU_REG_CLKGR1, 12 },
686 	},
687 
688 	[JZ4780_CLK_DES] = {
689 		"des", CGU_CLK_GATE,
690 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
691 		.gate = { CGU_REG_CLKGR1, 13 },
692 	},
693 
694 	[JZ4780_CLK_X2D] = {
695 		"x2d", CGU_CLK_GATE,
696 		.parents = { JZ4780_CLK_EXCLK, -1, -1, -1 },
697 		.gate = { CGU_REG_CLKGR1, 14 },
698 	},
699 
700 	[JZ4780_CLK_CORE1] = {
701 		"core1", CGU_CLK_GATE,
702 		.parents = { JZ4780_CLK_CPU, -1, -1, -1 },
703 		.gate = { CGU_REG_CLKGR1, 15 },
704 	},
705 
706 };
707 
708 static void __init jz4780_cgu_init(struct device_node *np)
709 {
710 	int retval;
711 
712 	cgu = ingenic_cgu_new(jz4780_cgu_clocks,
713 			      ARRAY_SIZE(jz4780_cgu_clocks), np);
714 	if (!cgu) {
715 		pr_err("%s: failed to initialise CGU\n", __func__);
716 		return;
717 	}
718 
719 	retval = ingenic_cgu_register_clocks(cgu);
720 	if (retval) {
721 		pr_err("%s: failed to register CGU Clocks\n", __func__);
722 		return;
723 	}
724 }
725 CLK_OF_DECLARE(jz4780_cgu, "ingenic,jz4780-cgu", jz4780_cgu_init);
726