1// SPDX-License-Identifier: GPL-2.0+
2/*
3 * Copyright (C) 2010-2011 Freescale Semiconductor, Inc.
4 */
5
6#include <common.h>
7#include <command.h>
8#include <div64.h>
9#include <log.h>
10#include <asm/io.h>
11#include <linux/errno.h>
12#include <asm/arch/imx-regs.h>
13#include <asm/arch/crm_regs.h>
14#include <asm/arch/clock.h>
15#include <asm/arch/sys_proto.h>
16
17enum pll_clocks {
18	PLL_SYS,	/* System PLL */
19	PLL_BUS,	/* System Bus PLL*/
20	PLL_USBOTG,	/* OTG USB PLL */
21	PLL_ENET,	/* ENET PLL */
22	PLL_AUDIO,	/* AUDIO PLL */
23	PLL_VIDEO,	/* VIDEO PLL */
24};
25
26struct mxc_ccm_reg *imx_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
27
28#ifdef CONFIG_MXC_OCOTP
29void enable_ocotp_clk(unsigned char enable)
30{
31	u32 reg;
32
33	reg = __raw_readl(&imx_ccm->CCGR2);
34	if (enable)
35		reg |= MXC_CCM_CCGR2_OCOTP_CTRL_MASK;
36	else
37		reg &= ~MXC_CCM_CCGR2_OCOTP_CTRL_MASK;
38	__raw_writel(reg, &imx_ccm->CCGR2);
39}
40#endif
41
42#ifdef CONFIG_NAND_MXS
43void setup_gpmi_io_clk(u32 cfg)
44{
45	/* Disable clocks per ERR007177 from MX6 errata */
46	clrbits_le32(&imx_ccm->CCGR4,
47		     MXC_CCM_CCGR4_RAWNAND_U_BCH_INPUT_APB_MASK |
48		     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_BCH_MASK |
49		     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_GPMI_IO_MASK |
50		     MXC_CCM_CCGR4_RAWNAND_U_GPMI_INPUT_APB_MASK |
51		     MXC_CCM_CCGR4_PL301_MX6QPER1_BCH_MASK);
52
53#if defined(CONFIG_MX6SX)
54	clrbits_le32(&imx_ccm->CCGR4, MXC_CCM_CCGR4_QSPI2_ENFC_MASK);
55
56	clrsetbits_le32(&imx_ccm->cs2cdr,
57			MXC_CCM_CS2CDR_QSPI2_CLK_PODF_MASK |
58			MXC_CCM_CS2CDR_QSPI2_CLK_PRED_MASK |
59			MXC_CCM_CS2CDR_QSPI2_CLK_SEL_MASK,
60			cfg);
61
62	setbits_le32(&imx_ccm->CCGR4, MXC_CCM_CCGR4_QSPI2_ENFC_MASK);
63#else
64	clrbits_le32(&imx_ccm->CCGR2, MXC_CCM_CCGR2_IOMUX_IPT_CLK_IO_MASK);
65
66	clrsetbits_le32(&imx_ccm->cs2cdr,
67			MXC_CCM_CS2CDR_ENFC_CLK_PODF_MASK |
68			MXC_CCM_CS2CDR_ENFC_CLK_PRED_MASK |
69			MXC_CCM_CS2CDR_ENFC_CLK_SEL_MASK,
70			cfg);
71
72	setbits_le32(&imx_ccm->CCGR2, MXC_CCM_CCGR2_IOMUX_IPT_CLK_IO_MASK);
73#endif
74	setbits_le32(&imx_ccm->CCGR4,
75		     MXC_CCM_CCGR4_RAWNAND_U_BCH_INPUT_APB_MASK |
76		     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_BCH_MASK |
77		     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_GPMI_IO_MASK |
78		     MXC_CCM_CCGR4_RAWNAND_U_GPMI_INPUT_APB_MASK |
79		     MXC_CCM_CCGR4_PL301_MX6QPER1_BCH_MASK);
80}
81#endif
82
83void enable_usboh3_clk(unsigned char enable)
84{
85	u32 reg;
86
87	reg = __raw_readl(&imx_ccm->CCGR6);
88	if (enable)
89		reg |= MXC_CCM_CCGR6_USBOH3_MASK;
90	else
91		reg &= ~(MXC_CCM_CCGR6_USBOH3_MASK);
92	__raw_writel(reg, &imx_ccm->CCGR6);
93
94}
95
96#if defined(CONFIG_FEC_MXC) && !defined(CONFIG_MX6SX)
97void enable_enet_clk(unsigned char enable)
98{
99	u32 mask, *addr;
100
101	if (is_mx6ull()) {
102		mask = MXC_CCM_CCGR0_ENET_CLK_ENABLE_MASK;
103		addr = &imx_ccm->CCGR0;
104	} else if (is_mx6ul()) {
105		mask = MXC_CCM_CCGR3_ENET_MASK;
106		addr = &imx_ccm->CCGR3;
107	} else {
108		mask = MXC_CCM_CCGR1_ENET_MASK;
109		addr = &imx_ccm->CCGR1;
110	}
111
112	if (enable)
113		setbits_le32(addr, mask);
114	else
115		clrbits_le32(addr, mask);
116}
117#endif
118
119#ifdef CONFIG_MXC_UART
120void enable_uart_clk(unsigned char enable)
121{
122	u32 mask;
123
124	if (is_mx6ul() || is_mx6ull())
125		mask = MXC_CCM_CCGR5_UART_MASK;
126	else
127		mask = MXC_CCM_CCGR5_UART_MASK | MXC_CCM_CCGR5_UART_SERIAL_MASK;
128
129	if (enable)
130		setbits_le32(&imx_ccm->CCGR5, mask);
131	else
132		clrbits_le32(&imx_ccm->CCGR5, mask);
133}
134#endif
135
136#ifdef CONFIG_MMC
137int enable_usdhc_clk(unsigned char enable, unsigned bus_num)
138{
139	u32 mask;
140
141	if (bus_num > 3)
142		return -EINVAL;
143
144	mask = MXC_CCM_CCGR_CG_MASK << (bus_num * 2 + 2);
145	if (enable)
146		setbits_le32(&imx_ccm->CCGR6, mask);
147	else
148		clrbits_le32(&imx_ccm->CCGR6, mask);
149
150	return 0;
151}
152#endif
153
154#ifdef CONFIG_SYS_I2C_MXC
155/* i2c_num can be from 0 - 3 */
156int enable_i2c_clk(unsigned char enable, unsigned i2c_num)
157{
158	u32 reg;
159	u32 mask;
160	u32 *addr;
161
162	if (i2c_num > 3)
163		return -EINVAL;
164	if (i2c_num < 3) {
165		mask = MXC_CCM_CCGR_CG_MASK
166			<< (MXC_CCM_CCGR2_I2C1_SERIAL_OFFSET
167			+ (i2c_num << 1));
168		reg = __raw_readl(&imx_ccm->CCGR2);
169		if (enable)
170			reg |= mask;
171		else
172			reg &= ~mask;
173		__raw_writel(reg, &imx_ccm->CCGR2);
174	} else {
175		if (is_mx6sll())
176			return -EINVAL;
177		if (is_mx6sx() || is_mx6ul() || is_mx6ull()) {
178			mask = MXC_CCM_CCGR6_I2C4_MASK;
179			addr = &imx_ccm->CCGR6;
180		} else {
181			mask = MXC_CCM_CCGR1_I2C4_SERIAL_MASK;
182			addr = &imx_ccm->CCGR1;
183		}
184		reg = __raw_readl(addr);
185		if (enable)
186			reg |= mask;
187		else
188			reg &= ~mask;
189		__raw_writel(reg, addr);
190	}
191	return 0;
192}
193#endif
194
195/* spi_num can be from 0 - SPI_MAX_NUM */
196int enable_spi_clk(unsigned char enable, unsigned spi_num)
197{
198	u32 reg;
199	u32 mask;
200
201	if (spi_num > SPI_MAX_NUM)
202		return -EINVAL;
203
204	mask = MXC_CCM_CCGR_CG_MASK << (spi_num << 1);
205	reg = __raw_readl(&imx_ccm->CCGR1);
206	if (enable)
207		reg |= mask;
208	else
209		reg &= ~mask;
210	__raw_writel(reg, &imx_ccm->CCGR1);
211	return 0;
212}
213static u32 decode_pll(enum pll_clocks pll, u32 infreq)
214{
215	u32 div, test_div, pll_num, pll_denom;
216	u64 temp64;
217
218	switch (pll) {
219	case PLL_SYS:
220		div = __raw_readl(&imx_ccm->analog_pll_sys);
221		div &= BM_ANADIG_PLL_SYS_DIV_SELECT;
222
223		return (infreq * div) >> 1;
224	case PLL_BUS:
225		div = __raw_readl(&imx_ccm->analog_pll_528);
226		div &= BM_ANADIG_PLL_528_DIV_SELECT;
227
228		return infreq * (20 + (div << 1));
229	case PLL_USBOTG:
230		div = __raw_readl(&imx_ccm->analog_usb1_pll_480_ctrl);
231		div &= BM_ANADIG_USB1_PLL_480_CTRL_DIV_SELECT;
232
233		return infreq * (20 + (div << 1));
234	case PLL_ENET:
235		div = __raw_readl(&imx_ccm->analog_pll_enet);
236		div &= BM_ANADIG_PLL_ENET_DIV_SELECT;
237
238		return 25000000 * (div + (div >> 1) + 1);
239	case PLL_AUDIO:
240		div = __raw_readl(&imx_ccm->analog_pll_audio);
241		if (!(div & BM_ANADIG_PLL_AUDIO_ENABLE))
242			return 0;
243		/* BM_ANADIG_PLL_AUDIO_BYPASS_CLK_SRC is ignored */
244		if (div & BM_ANADIG_PLL_AUDIO_BYPASS)
245			return MXC_HCLK;
246		pll_num = __raw_readl(&imx_ccm->analog_pll_audio_num);
247		pll_denom = __raw_readl(&imx_ccm->analog_pll_audio_denom);
248		test_div = (div & BM_ANADIG_PLL_AUDIO_TEST_DIV_SELECT) >>
249			BP_ANADIG_PLL_AUDIO_TEST_DIV_SELECT;
250		div &= BM_ANADIG_PLL_AUDIO_DIV_SELECT;
251		if (test_div == 3) {
252			debug("Error test_div\n");
253			return 0;
254		}
255		test_div = 1 << (2 - test_div);
256
257		return infreq * (div + pll_num / pll_denom) / test_div;
258	case PLL_VIDEO:
259		div = __raw_readl(&imx_ccm->analog_pll_video);
260		if (!(div & BM_ANADIG_PLL_VIDEO_ENABLE))
261			return 0;
262		/* BM_ANADIG_PLL_AUDIO_BYPASS_CLK_SRC is ignored */
263		if (div & BM_ANADIG_PLL_VIDEO_BYPASS)
264			return MXC_HCLK;
265		pll_num = __raw_readl(&imx_ccm->analog_pll_video_num);
266		pll_denom = __raw_readl(&imx_ccm->analog_pll_video_denom);
267		test_div = (div & BM_ANADIG_PLL_VIDEO_POST_DIV_SELECT) >>
268			BP_ANADIG_PLL_VIDEO_POST_DIV_SELECT;
269		div &= BM_ANADIG_PLL_VIDEO_DIV_SELECT;
270		if (test_div == 3) {
271			debug("Error test_div\n");
272			return 0;
273		}
274		test_div = 1 << (2 - test_div);
275
276		temp64 = (u64)infreq;
277		temp64 *= pll_num;
278		do_div(temp64, pll_denom);
279		return infreq * div + (unsigned long)temp64;
280	default:
281		return 0;
282	}
283	/* NOTREACHED */
284}
285static u32 mxc_get_pll_pfd(enum pll_clocks pll, int pfd_num)
286{
287	u32 div;
288	u64 freq;
289
290	switch (pll) {
291	case PLL_BUS:
292		if (!is_mx6ul() && !is_mx6ull()) {
293			if (pfd_num == 3) {
294				/* No PFD3 on PLL2 */
295				return 0;
296			}
297		}
298		div = __raw_readl(&imx_ccm->analog_pfd_528);
299		freq = (u64)decode_pll(PLL_BUS, MXC_HCLK);
300		break;
301	case PLL_USBOTG:
302		div = __raw_readl(&imx_ccm->analog_pfd_480);
303		freq = (u64)decode_pll(PLL_USBOTG, MXC_HCLK);
304		break;
305	default:
306		/* No PFD on other PLL					     */
307		return 0;
308	}
309
310	return lldiv(freq * 18, (div & ANATOP_PFD_FRAC_MASK(pfd_num)) >>
311			      ANATOP_PFD_FRAC_SHIFT(pfd_num));
312}
313
314static u32 get_mcu_main_clk(void)
315{
316	u32 reg, freq;
317
318	reg = __raw_readl(&imx_ccm->cacrr);
319	reg &= MXC_CCM_CACRR_ARM_PODF_MASK;
320	reg >>= MXC_CCM_CACRR_ARM_PODF_OFFSET;
321	freq = decode_pll(PLL_SYS, MXC_HCLK);
322
323	return freq / (reg + 1);
324}
325
326u32 get_periph_clk(void)
327{
328	u32 reg, div = 0, freq = 0;
329
330	reg = __raw_readl(&imx_ccm->cbcdr);
331	if (reg & MXC_CCM_CBCDR_PERIPH_CLK_SEL) {
332		div = (reg & MXC_CCM_CBCDR_PERIPH_CLK2_PODF_MASK) >>
333		       MXC_CCM_CBCDR_PERIPH_CLK2_PODF_OFFSET;
334		reg = __raw_readl(&imx_ccm->cbcmr);
335		reg &= MXC_CCM_CBCMR_PERIPH_CLK2_SEL_MASK;
336		reg >>= MXC_CCM_CBCMR_PERIPH_CLK2_SEL_OFFSET;
337
338		switch (reg) {
339		case 0:
340			freq = decode_pll(PLL_USBOTG, MXC_HCLK);
341			break;
342		case 1:
343		case 2:
344			freq = MXC_HCLK;
345			break;
346		default:
347			break;
348		}
349	} else {
350		reg = __raw_readl(&imx_ccm->cbcmr);
351		reg &= MXC_CCM_CBCMR_PRE_PERIPH_CLK_SEL_MASK;
352		reg >>= MXC_CCM_CBCMR_PRE_PERIPH_CLK_SEL_OFFSET;
353
354		switch (reg) {
355		case 0:
356			freq = decode_pll(PLL_BUS, MXC_HCLK);
357			break;
358		case 1:
359			freq = mxc_get_pll_pfd(PLL_BUS, 2);
360			break;
361		case 2:
362			freq = mxc_get_pll_pfd(PLL_BUS, 0);
363			break;
364		case 3:
365			/* static / 2 divider */
366			freq = mxc_get_pll_pfd(PLL_BUS, 2) / 2;
367			break;
368		default:
369			break;
370		}
371	}
372
373	return freq / (div + 1);
374}
375
376static u32 get_ipg_clk(void)
377{
378	u32 reg, ipg_podf;
379
380	reg = __raw_readl(&imx_ccm->cbcdr);
381	reg &= MXC_CCM_CBCDR_IPG_PODF_MASK;
382	ipg_podf = reg >> MXC_CCM_CBCDR_IPG_PODF_OFFSET;
383
384	return get_ahb_clk() / (ipg_podf + 1);
385}
386
387static u32 get_ipg_per_clk(void)
388{
389	u32 reg, perclk_podf;
390
391	reg = __raw_readl(&imx_ccm->cscmr1);
392	if (is_mx6sll() || is_mx6sl() || is_mx6sx() ||
393	    is_mx6dqp() || is_mx6ul() || is_mx6ull()) {
394		if (reg & MXC_CCM_CSCMR1_PER_CLK_SEL_MASK)
395			return MXC_HCLK; /* OSC 24Mhz */
396	}
397
398	perclk_podf = reg & MXC_CCM_CSCMR1_PERCLK_PODF_MASK;
399
400	return get_ipg_clk() / (perclk_podf + 1);
401}
402
403static u32 get_uart_clk(void)
404{
405	u32 reg, uart_podf;
406	u32 freq = decode_pll(PLL_USBOTG, MXC_HCLK) / 6; /* static divider */
407	reg = __raw_readl(&imx_ccm->cscdr1);
408
409	if (is_mx6sl() || is_mx6sx() || is_mx6dqp() || is_mx6ul() ||
410	    is_mx6sll() || is_mx6ull()) {
411		if (reg & MXC_CCM_CSCDR1_UART_CLK_SEL)
412			freq = MXC_HCLK;
413	}
414
415	reg &= MXC_CCM_CSCDR1_UART_CLK_PODF_MASK;
416	uart_podf = reg >> MXC_CCM_CSCDR1_UART_CLK_PODF_OFFSET;
417
418	return freq / (uart_podf + 1);
419}
420
421static u32 get_lcd_clk(unsigned int ifnum)
422{
423	u32 pll_rate;
424	u32 pred, postd;
425
426	if (!is_mx6sx() && !is_mx6ul() && !is_mx6ull() && !is_mx6sl() &&
427	    !is_mx6sll()) {
428		debug("This chip does't support lcd\n");
429		return 0;
430	}
431
432	pll_rate = decode_pll(PLL_VIDEO, MXC_HCLK);
433	if (ifnum == 1) {
434		if (!is_mx6sl()) {
435			pred = __raw_readl(&imx_ccm->cscdr2);
436			pred &= MXC_CCM_CSCDR2_LCDIF1_PRE_DIV_MASK;
437			pred = pred >> MXC_CCM_CSCDR2_LCDIF1_PRE_DIV_OFFSET;
438
439			postd = readl(&imx_ccm->cbcmr);
440			postd &= MXC_CCM_CBCMR_LCDIF1_PODF_MASK;
441			postd = postd >> MXC_CCM_CBCMR_LCDIF1_PODF_OFFSET;
442		} else {
443			pred = __raw_readl(&imx_ccm->cscdr2);
444			pred &= MXC_CCM_CSCDR2_LCDIF_PIX_PRE_DIV_MASK;
445			pred = pred >> MXC_CCM_CSCDR2_LCDIF_PIX_PRE_DIV_OFFSET;
446
447			postd = readl(&imx_ccm->cscmr1);
448			postd &= MXC_CCM_CSCMR1_LCDIF_PIX_PODF_OFFSET;
449			postd = postd >> MXC_CCM_CBCMR_LCDIF1_PODF_OFFSET;
450		}
451	} else if (ifnum == 2) {
452		if (is_mx6sx()) {
453			pred = __raw_readl(&imx_ccm->cscdr2);
454			pred &= MXC_CCM_CSCDR2_LCDIF2_PRE_DIV_MASK;
455			pred = pred >> MXC_CCM_CSCDR2_LCDIF2_PRE_DIV_OFFSET;
456
457			postd = readl(&imx_ccm->cscmr1);
458			postd &= MXC_CCM_CSCMR1_LCDIF2_PODF_MASK;
459			postd = postd >> MXC_CCM_CSCMR1_LCDIF2_PODF_OFFSET;
460
461		} else {
462			goto if_err;
463		}
464	} else {
465		goto if_err;
466	}
467
468	return DIV_ROUND_UP_ULL((u64)pll_rate, (postd + 1) * (pred + 1));
469
470if_err:
471	debug("This chip not support lcd iterface %d\n", ifnum);
472	return 0;
473}
474
475static u32 get_cspi_clk(void)
476{
477	u32 reg, cspi_podf;
478
479	reg = __raw_readl(&imx_ccm->cscdr2);
480	cspi_podf = (reg & MXC_CCM_CSCDR2_ECSPI_CLK_PODF_MASK) >>
481		     MXC_CCM_CSCDR2_ECSPI_CLK_PODF_OFFSET;
482
483	if (is_mx6dqp() || is_mx6sl() || is_mx6sx() || is_mx6ul() ||
484	    is_mx6sll() || is_mx6ull()) {
485		if (reg & MXC_CCM_CSCDR2_ECSPI_CLK_SEL_MASK)
486			return MXC_HCLK / (cspi_podf + 1);
487	}
488
489	return	decode_pll(PLL_USBOTG, MXC_HCLK) / (8 * (cspi_podf + 1));
490}
491
492static u32 get_axi_clk(void)
493{
494	u32 root_freq, axi_podf;
495	u32 cbcdr =  __raw_readl(&imx_ccm->cbcdr);
496
497	axi_podf = cbcdr & MXC_CCM_CBCDR_AXI_PODF_MASK;
498	axi_podf >>= MXC_CCM_CBCDR_AXI_PODF_OFFSET;
499
500	if (cbcdr & MXC_CCM_CBCDR_AXI_SEL) {
501		if (cbcdr & MXC_CCM_CBCDR_AXI_ALT_SEL)
502			root_freq = mxc_get_pll_pfd(PLL_USBOTG, 1);
503		else
504			root_freq = mxc_get_pll_pfd(PLL_BUS, 2);
505	} else
506		root_freq = get_periph_clk();
507
508	return  root_freq / (axi_podf + 1);
509}
510
511static u32 get_emi_slow_clk(void)
512{
513	u32 emi_clk_sel, emi_slow_podf, cscmr1, root_freq = 0;
514
515	cscmr1 =  __raw_readl(&imx_ccm->cscmr1);
516	emi_clk_sel = cscmr1 & MXC_CCM_CSCMR1_ACLK_EMI_SLOW_MASK;
517	emi_clk_sel >>= MXC_CCM_CSCMR1_ACLK_EMI_SLOW_OFFSET;
518	emi_slow_podf = cscmr1 & MXC_CCM_CSCMR1_ACLK_EMI_SLOW_PODF_MASK;
519	emi_slow_podf >>= MXC_CCM_CSCMR1_ACLK_EMI_SLOW_PODF_OFFSET;
520
521	switch (emi_clk_sel) {
522	case 0:
523		root_freq = get_axi_clk();
524		break;
525	case 1:
526		root_freq = decode_pll(PLL_USBOTG, MXC_HCLK);
527		break;
528	case 2:
529		root_freq =  mxc_get_pll_pfd(PLL_BUS, 2);
530		break;
531	case 3:
532		root_freq =  mxc_get_pll_pfd(PLL_BUS, 0);
533		break;
534	}
535
536	return root_freq / (emi_slow_podf + 1);
537}
538
539static u32 get_mmdc_ch0_clk(void)
540{
541	u32 cbcmr = __raw_readl(&imx_ccm->cbcmr);
542	u32 cbcdr = __raw_readl(&imx_ccm->cbcdr);
543
544	u32 freq, podf, per2_clk2_podf, pmu_misc2_audio_div;
545
546	if (is_mx6sx() || is_mx6ul() || is_mx6ull() || is_mx6sl() ||
547	    is_mx6sll()) {
548		podf = (cbcdr & MXC_CCM_CBCDR_MMDC_CH1_PODF_MASK) >>
549			MXC_CCM_CBCDR_MMDC_CH1_PODF_OFFSET;
550		if (cbcdr & MXC_CCM_CBCDR_PERIPH2_CLK_SEL) {
551			per2_clk2_podf = (cbcdr & MXC_CCM_CBCDR_PERIPH2_CLK2_PODF_MASK) >>
552				MXC_CCM_CBCDR_PERIPH2_CLK2_PODF_OFFSET;
553			if (is_mx6sl()) {
554				if (cbcmr & MXC_CCM_CBCMR_PERIPH2_CLK2_SEL)
555					freq = MXC_HCLK;
556				else
557					freq = decode_pll(PLL_USBOTG, MXC_HCLK);
558			} else {
559				if (cbcmr & MXC_CCM_CBCMR_PERIPH2_CLK2_SEL)
560					freq = decode_pll(PLL_BUS, MXC_HCLK);
561				else
562					freq = decode_pll(PLL_USBOTG, MXC_HCLK);
563			}
564		} else {
565			per2_clk2_podf = 0;
566			switch ((cbcmr &
567				MXC_CCM_CBCMR_PRE_PERIPH2_CLK_SEL_MASK) >>
568				MXC_CCM_CBCMR_PRE_PERIPH2_CLK_SEL_OFFSET) {
569			case 0:
570				freq = decode_pll(PLL_BUS, MXC_HCLK);
571				break;
572			case 1:
573				freq = mxc_get_pll_pfd(PLL_BUS, 2);
574				break;
575			case 2:
576				freq = mxc_get_pll_pfd(PLL_BUS, 0);
577				break;
578			case 3:
579				if (is_mx6sl()) {
580					freq = mxc_get_pll_pfd(PLL_BUS, 2) >> 1;
581					break;
582				}
583
584				pmu_misc2_audio_div = PMU_MISC2_AUDIO_DIV(__raw_readl(&imx_ccm->pmu_misc2));
585				switch (pmu_misc2_audio_div) {
586				case 0:
587				case 2:
588					pmu_misc2_audio_div = 1;
589					break;
590				case 1:
591					pmu_misc2_audio_div = 2;
592					break;
593				case 3:
594					pmu_misc2_audio_div = 4;
595					break;
596				}
597				freq = decode_pll(PLL_AUDIO, MXC_HCLK) /
598					pmu_misc2_audio_div;
599				break;
600			}
601		}
602		return freq / (podf + 1) / (per2_clk2_podf + 1);
603	} else {
604		podf = (cbcdr & MXC_CCM_CBCDR_MMDC_CH0_PODF_MASK) >>
605			MXC_CCM_CBCDR_MMDC_CH0_PODF_OFFSET;
606		return get_periph_clk() / (podf + 1);
607	}
608}
609
610#if defined(CONFIG_VIDEO_MXS)
611static int enable_pll_video(u32 pll_div, u32 pll_num, u32 pll_denom,
612			    u32 post_div)
613{
614	u32 reg = 0;
615	ulong start;
616
617	debug("pll5 div = %d, num = %d, denom = %d\n",
618	      pll_div, pll_num, pll_denom);
619
620	/* Power up PLL5 video */
621	writel(BM_ANADIG_PLL_VIDEO_POWERDOWN |
622	       BM_ANADIG_PLL_VIDEO_BYPASS |
623	       BM_ANADIG_PLL_VIDEO_DIV_SELECT |
624	       BM_ANADIG_PLL_VIDEO_POST_DIV_SELECT,
625	       &imx_ccm->analog_pll_video_clr);
626
627	/* Set div, num and denom */
628	switch (post_div) {
629	case 1:
630		writel(BF_ANADIG_PLL_VIDEO_DIV_SELECT(pll_div) |
631		       BF_ANADIG_PLL_VIDEO_POST_DIV_SELECT(0x2),
632		       &imx_ccm->analog_pll_video_set);
633		break;
634	case 2:
635		writel(BF_ANADIG_PLL_VIDEO_DIV_SELECT(pll_div) |
636		       BF_ANADIG_PLL_VIDEO_POST_DIV_SELECT(0x1),
637		       &imx_ccm->analog_pll_video_set);
638		break;
639	case 4:
640		writel(BF_ANADIG_PLL_VIDEO_DIV_SELECT(pll_div) |
641		       BF_ANADIG_PLL_VIDEO_POST_DIV_SELECT(0x0),
642		       &imx_ccm->analog_pll_video_set);
643		break;
644	default:
645		puts("Wrong test_div!\n");
646		return -EINVAL;
647	}
648
649	writel(BF_ANADIG_PLL_VIDEO_NUM_A(pll_num),
650	       &imx_ccm->analog_pll_video_num);
651	writel(BF_ANADIG_PLL_VIDEO_DENOM_B(pll_denom),
652	       &imx_ccm->analog_pll_video_denom);
653
654	/* Wait PLL5 lock */
655	start = get_timer(0);	/* Get current timestamp */
656
657	do {
658		reg = readl(&imx_ccm->analog_pll_video);
659		if (reg & BM_ANADIG_PLL_VIDEO_LOCK) {
660			/* Enable PLL out */
661			writel(BM_ANADIG_PLL_VIDEO_ENABLE,
662			       &imx_ccm->analog_pll_video_set);
663			return 0;
664		}
665	} while (get_timer(0) < (start + 10)); /* Wait 10ms */
666
667	puts("Lock PLL5 timeout\n");
668
669	return -ETIME;
670}
671
672/*
673 * 24M--> PLL_VIDEO -> LCDIFx_PRED -> LCDIFx_PODF -> LCD
674 *
675 * 'freq' using KHz as unit, see driver/video/mxsfb.c.
676 */
677void mxs_set_lcdclk(u32 base_addr, u32 freq)
678{
679	u32 reg = 0;
680	u32 hck = MXC_HCLK / 1000;
681	/* DIV_SELECT ranges from 27 to 54 */
682	u32 min = hck * 27;
683	u32 max = hck * 54;
684	u32 temp, best = 0;
685	u32 i, j, max_pred = 8, max_postd = 8, pred = 1, postd = 1;
686	u32 pll_div, pll_num, pll_denom, post_div = 1;
687
688	debug("mxs_set_lcdclk, freq = %dKHz\n", freq);
689
690	if (!is_mx6sx() && !is_mx6ul() && !is_mx6ull() && !is_mx6sl() &&
691	    !is_mx6sll()) {
692		debug("This chip not support lcd!\n");
693		return;
694	}
695
696	if (!is_mx6sl()) {
697		if (base_addr == LCDIF1_BASE_ADDR) {
698			reg = readl(&imx_ccm->cscdr2);
699			/* Can't change clocks when clock not from pre-mux */
700			if ((reg & MXC_CCM_CSCDR2_LCDIF1_CLK_SEL_MASK) != 0)
701				return;
702		}
703	}
704
705	if (is_mx6sx()) {
706		reg = readl(&imx_ccm->cscdr2);
707		/* Can't change clocks when clock not from pre-mux */
708		if ((reg & MXC_CCM_CSCDR2_LCDIF2_CLK_SEL_MASK) != 0)
709			return;
710	}
711
712	temp = freq * max_pred * max_postd;
713	if (temp < min) {
714		/*
715		 * Register: PLL_VIDEO
716		 * Bit Field: POST_DIV_SELECT
717		 * 00 - Divide by 4.
718		 * 01 - Divide by 2.
719		 * 10 - Divide by 1.
720		 * 11 - Reserved
721		 * No need to check post_div(1)
722		 */
723		for (post_div = 2; post_div <= 4; post_div <<= 1) {
724			if ((temp * post_div) > min) {
725				freq *= post_div;
726				break;
727			}
728		}
729
730		if (post_div > 4) {
731			printf("Fail to set rate to %dkhz", freq);
732			return;
733		}
734	}
735
736	/* Choose the best pred and postd to match freq for lcd */
737	for (i = 1; i <= max_pred; i++) {
738		for (j = 1; j <= max_postd; j++) {
739			temp = freq * i * j;
740			if (temp > max || temp < min)
741				continue;
742			if (best == 0 || temp < best) {
743				best = temp;
744				pred = i;
745				postd = j;
746			}
747		}
748	}
749
750	if (best == 0) {
751		printf("Fail to set rate to %dKHz", freq);
752		return;
753	}
754
755	debug("best %d, pred = %d, postd = %d\n", best, pred, postd);
756
757	pll_div = best / hck;
758	pll_denom = 1000000;
759	pll_num = (best - hck * pll_div) * pll_denom / hck;
760
761	/*
762	 *                                  pll_num
763	 *             (24MHz * (pll_div + --------- ))
764	 *                                 pll_denom
765	 *freq KHz =  --------------------------------
766	 *             post_div * pred * postd * 1000
767	 */
768
769	if (base_addr == LCDIF1_BASE_ADDR) {
770		if (enable_pll_video(pll_div, pll_num, pll_denom, post_div))
771			return;
772
773		enable_lcdif_clock(base_addr, 0);
774		if (!is_mx6sl()) {
775			/* Select pre-lcd clock to PLL5 and set pre divider */
776			clrsetbits_le32(&imx_ccm->cscdr2,
777					MXC_CCM_CSCDR2_LCDIF1_PRED_SEL_MASK |
778					MXC_CCM_CSCDR2_LCDIF1_PRE_DIV_MASK,
779					(0x2 << MXC_CCM_CSCDR2_LCDIF1_PRED_SEL_OFFSET) |
780					((pred - 1) <<
781					 MXC_CCM_CSCDR2_LCDIF1_PRE_DIV_OFFSET));
782
783			/* Set the post divider */
784			clrsetbits_le32(&imx_ccm->cbcmr,
785					MXC_CCM_CBCMR_LCDIF1_PODF_MASK,
786					((postd - 1) <<
787					MXC_CCM_CBCMR_LCDIF1_PODF_OFFSET));
788		} else {
789			/* Select pre-lcd clock to PLL5 and set pre divider */
790			clrsetbits_le32(&imx_ccm->cscdr2,
791					MXC_CCM_CSCDR2_LCDIF_PIX_CLK_SEL_MASK |
792					MXC_CCM_CSCDR2_LCDIF_PIX_PRE_DIV_MASK,
793					(0x2 << MXC_CCM_CSCDR2_LCDIF_PIX_CLK_SEL_OFFSET) |
794					((pred - 1) <<
795					 MXC_CCM_CSCDR2_LCDIF_PIX_PRE_DIV_OFFSET));
796
797			/* Set the post divider */
798			clrsetbits_le32(&imx_ccm->cscmr1,
799					MXC_CCM_CSCMR1_LCDIF_PIX_PODF_MASK,
800					(((postd - 1)^0x6) <<
801					 MXC_CCM_CSCMR1_LCDIF_PIX_PODF_OFFSET));
802		}
803
804		enable_lcdif_clock(base_addr, 1);
805		debug("pixel clock = %u\n", mxc_get_clock(MXC_LCDIF1_CLK));
806	} else if (is_mx6sx()) {
807		/* Setting LCDIF2 for i.MX6SX */
808		if (enable_pll_video(pll_div, pll_num, pll_denom, post_div))
809			return;
810
811		enable_lcdif_clock(base_addr, 0);
812		/* Select pre-lcd clock to PLL5 and set pre divider */
813		clrsetbits_le32(&imx_ccm->cscdr2,
814				MXC_CCM_CSCDR2_LCDIF2_PRED_SEL_MASK |
815				MXC_CCM_CSCDR2_LCDIF2_PRE_DIV_MASK,
816				(0x2 << MXC_CCM_CSCDR2_LCDIF2_PRED_SEL_OFFSET) |
817				((pred - 1) <<
818				 MXC_CCM_CSCDR2_LCDIF2_PRE_DIV_OFFSET));
819
820		/* Set the post divider */
821		clrsetbits_le32(&imx_ccm->cscmr1,
822				MXC_CCM_CSCMR1_LCDIF2_PODF_MASK,
823				((postd - 1) <<
824				 MXC_CCM_CSCMR1_LCDIF2_PODF_OFFSET));
825
826		enable_lcdif_clock(base_addr, 1);
827		debug("pixel clock = %u\n", mxc_get_clock(MXC_LCDIF2_CLK));
828	}
829}
830
831int enable_lcdif_clock(u32 base_addr, bool enable)
832{
833	u32 reg = 0;
834	u32 lcdif_clk_sel_mask, lcdif_ccgr3_mask;
835
836	if (is_mx6sx()) {
837		if ((base_addr != LCDIF1_BASE_ADDR) &&
838		    (base_addr != LCDIF2_BASE_ADDR)) {
839			puts("Wrong LCD interface!\n");
840			return -EINVAL;
841		}
842		/* Set to pre-mux clock at default */
843		lcdif_clk_sel_mask = (base_addr == LCDIF2_BASE_ADDR) ?
844			MXC_CCM_CSCDR2_LCDIF2_CLK_SEL_MASK :
845			MXC_CCM_CSCDR2_LCDIF1_CLK_SEL_MASK;
846		lcdif_ccgr3_mask = (base_addr == LCDIF2_BASE_ADDR) ?
847			(MXC_CCM_CCGR3_LCDIF2_PIX_MASK |
848			 MXC_CCM_CCGR3_DISP_AXI_MASK) :
849			(MXC_CCM_CCGR3_LCDIF1_PIX_MASK |
850			 MXC_CCM_CCGR3_DISP_AXI_MASK);
851	} else if (is_mx6ul() || is_mx6ull() || is_mx6sll()) {
852		if (base_addr != LCDIF1_BASE_ADDR) {
853			puts("Wrong LCD interface!\n");
854			return -EINVAL;
855		}
856		/* Set to pre-mux clock at default */
857		lcdif_clk_sel_mask = MXC_CCM_CSCDR2_LCDIF1_CLK_SEL_MASK;
858		lcdif_ccgr3_mask =  MXC_CCM_CCGR3_LCDIF1_PIX_MASK;
859	} else if (is_mx6sl()) {
860		if (base_addr != LCDIF1_BASE_ADDR) {
861			puts("Wrong LCD interface!\n");
862			return -EINVAL;
863		}
864
865		reg = readl(&imx_ccm->CCGR3);
866		reg &= ~(MXC_CCM_CCGR3_LCDIF_AXI_MASK |
867			 MXC_CCM_CCGR3_LCDIF_PIX_MASK);
868		writel(reg, &imx_ccm->CCGR3);
869
870		if (enable) {
871			reg = readl(&imx_ccm->cscdr3);
872			reg &= ~MXC_CCM_CSCDR3_LCDIF_AXI_CLK_SEL_MASK;
873			reg |= 1 << MXC_CCM_CSCDR3_LCDIF_AXI_CLK_SEL_OFFSET;
874			writel(reg, &imx_ccm->cscdr3);
875
876			reg = readl(&imx_ccm->CCGR3);
877			reg |= MXC_CCM_CCGR3_LCDIF_AXI_MASK |
878				MXC_CCM_CCGR3_LCDIF_PIX_MASK;
879			writel(reg, &imx_ccm->CCGR3);
880		}
881
882		return 0;
883	} else {
884		return 0;
885	}
886
887	/* Gate LCDIF clock first */
888	reg = readl(&imx_ccm->CCGR3);
889	reg &= ~lcdif_ccgr3_mask;
890	writel(reg, &imx_ccm->CCGR3);
891
892	reg = readl(&imx_ccm->CCGR2);
893	reg &= ~MXC_CCM_CCGR2_LCD_MASK;
894	writel(reg, &imx_ccm->CCGR2);
895
896	if (enable) {
897		/* Select pre-mux */
898		reg = readl(&imx_ccm->cscdr2);
899		reg &= ~lcdif_clk_sel_mask;
900		writel(reg, &imx_ccm->cscdr2);
901
902		/* Enable the LCDIF pix clock */
903		reg = readl(&imx_ccm->CCGR3);
904		reg |= lcdif_ccgr3_mask;
905		writel(reg, &imx_ccm->CCGR3);
906
907		reg = readl(&imx_ccm->CCGR2);
908		reg |= MXC_CCM_CCGR2_LCD_MASK;
909		writel(reg, &imx_ccm->CCGR2);
910	}
911
912	return 0;
913}
914#endif
915
916#ifdef CONFIG_FSL_QSPI
917/* qspi_num can be from 0 - 1 */
918void enable_qspi_clk(int qspi_num)
919{
920	u32 reg = 0;
921	/* Enable QuadSPI clock */
922	switch (qspi_num) {
923	case 0:
924		/* disable the clock gate */
925		clrbits_le32(&imx_ccm->CCGR3, MXC_CCM_CCGR3_QSPI1_MASK);
926
927		/* set 50M  : (50 = 396 / 2 / 4) */
928		reg = readl(&imx_ccm->cscmr1);
929		reg &= ~(MXC_CCM_CSCMR1_QSPI1_PODF_MASK |
930			 MXC_CCM_CSCMR1_QSPI1_CLK_SEL_MASK);
931		reg |= ((1 << MXC_CCM_CSCMR1_QSPI1_PODF_OFFSET) |
932			(2 << MXC_CCM_CSCMR1_QSPI1_CLK_SEL_OFFSET));
933		writel(reg, &imx_ccm->cscmr1);
934
935		/* enable the clock gate */
936		setbits_le32(&imx_ccm->CCGR3, MXC_CCM_CCGR3_QSPI1_MASK);
937		break;
938	case 1:
939		/*
940		 * disable the clock gate
941		 * QSPI2 and GPMI_BCH_INPUT_GPMI_IO share the same clock gate,
942		 * disable both of them.
943		 */
944		clrbits_le32(&imx_ccm->CCGR4, MXC_CCM_CCGR4_QSPI2_ENFC_MASK |
945			     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_GPMI_IO_MASK);
946
947		/* set 50M  : (50 = 396 / 2 / 4) */
948		reg = readl(&imx_ccm->cs2cdr);
949		reg &= ~(MXC_CCM_CS2CDR_QSPI2_CLK_PODF_MASK |
950			 MXC_CCM_CS2CDR_QSPI2_CLK_PRED_MASK |
951			 MXC_CCM_CS2CDR_QSPI2_CLK_SEL_MASK);
952		reg |= (MXC_CCM_CS2CDR_QSPI2_CLK_PRED(0x1) |
953			MXC_CCM_CS2CDR_QSPI2_CLK_SEL(0x3));
954		writel(reg, &imx_ccm->cs2cdr);
955
956		/*enable the clock gate*/
957		setbits_le32(&imx_ccm->CCGR4, MXC_CCM_CCGR4_QSPI2_ENFC_MASK |
958			     MXC_CCM_CCGR4_RAWNAND_U_GPMI_BCH_INPUT_GPMI_IO_MASK);
959		break;
960	default:
961		break;
962	}
963}
964#endif
965
966#ifdef CONFIG_FEC_MXC
967int enable_fec_anatop_clock(int fec_id, enum enet_freq freq)
968{
969	u32 reg = 0;
970	s32 timeout = 100000;
971
972	struct anatop_regs __iomem *anatop =
973		(struct anatop_regs __iomem *)ANATOP_BASE_ADDR;
974
975	if (freq < ENET_25MHZ || freq > ENET_125MHZ)
976		return -EINVAL;
977
978	reg = readl(&anatop->pll_enet);
979
980	if (fec_id == 0) {
981		reg &= ~BM_ANADIG_PLL_ENET_DIV_SELECT;
982		reg |= BF_ANADIG_PLL_ENET_DIV_SELECT(freq);
983	} else if (fec_id == 1) {
984		/* Only i.MX6SX/UL support ENET2 */
985		if (!(is_mx6sx() || is_mx6ul() || is_mx6ull()))
986			return -EINVAL;
987		reg &= ~BM_ANADIG_PLL_ENET2_DIV_SELECT;
988		reg |= BF_ANADIG_PLL_ENET2_DIV_SELECT(freq);
989	} else {
990		return -EINVAL;
991	}
992
993	if ((reg & BM_ANADIG_PLL_ENET_POWERDOWN) ||
994	    (!(reg & BM_ANADIG_PLL_ENET_LOCK))) {
995		reg &= ~BM_ANADIG_PLL_ENET_POWERDOWN;
996		writel(reg, &anatop->pll_enet);
997		while (timeout--) {
998			if (readl(&anatop->pll_enet) & BM_ANADIG_PLL_ENET_LOCK)
999				break;
1000		}
1001		if (timeout < 0)
1002			return -ETIMEDOUT;
1003	}
1004
1005	/* Enable FEC clock */
1006	if (fec_id == 0)
1007		reg |= BM_ANADIG_PLL_ENET_ENABLE;
1008	else
1009		reg |= BM_ANADIG_PLL_ENET2_ENABLE;
1010	reg &= ~BM_ANADIG_PLL_ENET_BYPASS;
1011	writel(reg, &anatop->pll_enet);
1012
1013#ifdef CONFIG_MX6SX
1014	/* Disable enet system clcok before switching clock parent */
1015	reg = readl(&imx_ccm->CCGR3);
1016	reg &= ~MXC_CCM_CCGR3_ENET_MASK;
1017	writel(reg, &imx_ccm->CCGR3);
1018
1019	/*
1020	 * Set enet ahb clock to 200MHz
1021	 * pll2_pfd2_396m-> ENET_PODF-> ENET_AHB
1022	 */
1023	reg = readl(&imx_ccm->chsccdr);
1024	reg &= ~(MXC_CCM_CHSCCDR_ENET_PRE_CLK_SEL_MASK
1025		 | MXC_CCM_CHSCCDR_ENET_PODF_MASK
1026		 | MXC_CCM_CHSCCDR_ENET_CLK_SEL_MASK);
1027	/* PLL2 PFD2 */
1028	reg |= (4 << MXC_CCM_CHSCCDR_ENET_PRE_CLK_SEL_OFFSET);
1029	/* Div = 2*/
1030	reg |= (1 << MXC_CCM_CHSCCDR_ENET_PODF_OFFSET);
1031	reg |= (0 << MXC_CCM_CHSCCDR_ENET_CLK_SEL_OFFSET);
1032	writel(reg, &imx_ccm->chsccdr);
1033
1034	/* Enable enet system clock */
1035	reg = readl(&imx_ccm->CCGR3);
1036	reg |= MXC_CCM_CCGR3_ENET_MASK;
1037	writel(reg, &imx_ccm->CCGR3);
1038#endif
1039	return 0;
1040}
1041#endif
1042
1043static u32 get_usdhc_clk(u32 port)
1044{
1045	u32 root_freq = 0, usdhc_podf = 0, clk_sel = 0;
1046	u32 cscmr1 = __raw_readl(&imx_ccm->cscmr1);
1047	u32 cscdr1 = __raw_readl(&imx_ccm->cscdr1);
1048
1049	if (is_mx6ul() || is_mx6ull()) {
1050		if (port > 1)
1051			return 0;
1052	}
1053
1054	if (is_mx6sll()) {
1055		if (port > 2)
1056			return 0;
1057	}
1058
1059	switch (port) {
1060	case 0:
1061		usdhc_podf = (cscdr1 & MXC_CCM_CSCDR1_USDHC1_PODF_MASK) >>
1062					MXC_CCM_CSCDR1_USDHC1_PODF_OFFSET;
1063		clk_sel = cscmr1 & MXC_CCM_CSCMR1_USDHC1_CLK_SEL;
1064
1065		break;
1066	case 1:
1067		usdhc_podf = (cscdr1 & MXC_CCM_CSCDR1_USDHC2_PODF_MASK) >>
1068					MXC_CCM_CSCDR1_USDHC2_PODF_OFFSET;
1069		clk_sel = cscmr1 & MXC_CCM_CSCMR1_USDHC2_CLK_SEL;
1070
1071		break;
1072	case 2:
1073		usdhc_podf = (cscdr1 & MXC_CCM_CSCDR1_USDHC3_PODF_MASK) >>
1074					MXC_CCM_CSCDR1_USDHC3_PODF_OFFSET;
1075		clk_sel = cscmr1 & MXC_CCM_CSCMR1_USDHC3_CLK_SEL;
1076
1077		break;
1078	case 3:
1079		usdhc_podf = (cscdr1 & MXC_CCM_CSCDR1_USDHC4_PODF_MASK) >>
1080					MXC_CCM_CSCDR1_USDHC4_PODF_OFFSET;
1081		clk_sel = cscmr1 & MXC_CCM_CSCMR1_USDHC4_CLK_SEL;
1082
1083		break;
1084	default:
1085		break;
1086	}
1087
1088	if (clk_sel)
1089		root_freq = mxc_get_pll_pfd(PLL_BUS, 0);
1090	else
1091		root_freq = mxc_get_pll_pfd(PLL_BUS, 2);
1092
1093	return root_freq / (usdhc_podf + 1);
1094}
1095
1096u32 imx_get_uartclk(void)
1097{
1098	return get_uart_clk();
1099}
1100
1101u32 imx_get_fecclk(void)
1102{
1103	return mxc_get_clock(MXC_IPG_CLK);
1104}
1105
1106#if defined(CONFIG_SATA) || defined(CONFIG_PCIE_IMX)
1107static int enable_enet_pll(uint32_t en)
1108{
1109	struct mxc_ccm_reg *const imx_ccm
1110		= (struct mxc_ccm_reg *) CCM_BASE_ADDR;
1111	s32 timeout = 100000;
1112	u32 reg = 0;
1113
1114	/* Enable PLLs */
1115	reg = readl(&imx_ccm->analog_pll_enet);
1116	reg &= ~BM_ANADIG_PLL_SYS_POWERDOWN;
1117	writel(reg, &imx_ccm->analog_pll_enet);
1118	reg |= BM_ANADIG_PLL_SYS_ENABLE;
1119	while (timeout--) {
1120		if (readl(&imx_ccm->analog_pll_enet) & BM_ANADIG_PLL_SYS_LOCK)
1121			break;
1122	}
1123	if (timeout <= 0)
1124		return -EIO;
1125	reg &= ~BM_ANADIG_PLL_SYS_BYPASS;
1126	writel(reg, &imx_ccm->analog_pll_enet);
1127	reg |= en;
1128	writel(reg, &imx_ccm->analog_pll_enet);
1129	return 0;
1130}
1131#endif
1132
1133#ifdef CONFIG_SATA
1134static void ungate_sata_clock(void)
1135{
1136	struct mxc_ccm_reg *const imx_ccm =
1137		(struct mxc_ccm_reg *)CCM_BASE_ADDR;
1138
1139	/* Enable SATA clock. */
1140	setbits_le32(&imx_ccm->CCGR5, MXC_CCM_CCGR5_SATA_MASK);
1141}
1142
1143int enable_sata_clock(void)
1144{
1145	ungate_sata_clock();
1146	return enable_enet_pll(BM_ANADIG_PLL_ENET_ENABLE_SATA);
1147}
1148
1149void disable_sata_clock(void)
1150{
1151	struct mxc_ccm_reg *const imx_ccm =
1152		(struct mxc_ccm_reg *)CCM_BASE_ADDR;
1153
1154	clrbits_le32(&imx_ccm->CCGR5, MXC_CCM_CCGR5_SATA_MASK);
1155}
1156#endif
1157
1158#ifdef CONFIG_PCIE_IMX
1159static void ungate_pcie_clock(void)
1160{
1161	struct mxc_ccm_reg *const imx_ccm =
1162		(struct mxc_ccm_reg *)CCM_BASE_ADDR;
1163
1164	/* Enable PCIe clock. */
1165	setbits_le32(&imx_ccm->CCGR4, MXC_CCM_CCGR4_PCIE_MASK);
1166}
1167
1168int enable_pcie_clock(void)
1169{
1170	struct anatop_regs *anatop_regs =
1171		(struct anatop_regs *)ANATOP_BASE_ADDR;
1172	struct mxc_ccm_reg *ccm_regs = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
1173	u32 lvds1_clk_sel;
1174
1175	/*
1176	 * Here be dragons!
1177	 *
1178	 * The register ANATOP_MISC1 is not documented in the Freescale
1179	 * MX6RM. The register that is mapped in the ANATOP space and
1180	 * marked as ANATOP_MISC1 is actually documented in the PMU section
1181	 * of the datasheet as PMU_MISC1.
1182	 *
1183	 * Switch LVDS clock source to SATA (0xb) on mx6q/dl or PCI (0xa) on
1184	 * mx6sx, disable clock INPUT and enable clock OUTPUT. This is important
1185	 * for PCI express link that is clocked from the i.MX6.
1186	 */
1187#define ANADIG_ANA_MISC1_LVDSCLK1_IBEN		(1 << 12)
1188#define ANADIG_ANA_MISC1_LVDSCLK1_OBEN		(1 << 10)
1189#define ANADIG_ANA_MISC1_LVDS1_CLK_SEL_MASK	0x0000001F
1190#define ANADIG_ANA_MISC1_LVDS1_CLK_SEL_PCIE_REF	0xa
1191#define ANADIG_ANA_MISC1_LVDS1_CLK_SEL_SATA_REF	0xb
1192
1193	if (is_mx6sx())
1194		lvds1_clk_sel = ANADIG_ANA_MISC1_LVDS1_CLK_SEL_PCIE_REF;
1195	else
1196		lvds1_clk_sel = ANADIG_ANA_MISC1_LVDS1_CLK_SEL_SATA_REF;
1197
1198	clrsetbits_le32(&anatop_regs->ana_misc1,
1199			ANADIG_ANA_MISC1_LVDSCLK1_IBEN |
1200			ANADIG_ANA_MISC1_LVDS1_CLK_SEL_MASK,
1201			ANADIG_ANA_MISC1_LVDSCLK1_OBEN | lvds1_clk_sel);
1202
1203	/* PCIe reference clock sourced from AXI. */
1204	clrbits_le32(&ccm_regs->cbcmr, MXC_CCM_CBCMR_PCIE_AXI_CLK_SEL);
1205
1206	/* Party time! Ungate the clock to the PCIe. */
1207#ifdef CONFIG_SATA
1208	ungate_sata_clock();
1209#endif
1210	ungate_pcie_clock();
1211
1212	return enable_enet_pll(BM_ANADIG_PLL_ENET_ENABLE_SATA |
1213			       BM_ANADIG_PLL_ENET_ENABLE_PCIE);
1214}
1215#endif
1216
1217#ifdef CONFIG_IMX_HAB
1218void hab_caam_clock_enable(unsigned char enable)
1219{
1220	u32 reg;
1221
1222	if (is_mx6ull() || is_mx6sll()) {
1223		/* CG5, DCP clock */
1224		reg = __raw_readl(&imx_ccm->CCGR0);
1225		if (enable)
1226			reg |= MXC_CCM_CCGR0_DCP_CLK_MASK;
1227		else
1228			reg &= ~MXC_CCM_CCGR0_DCP_CLK_MASK;
1229		__raw_writel(reg, &imx_ccm->CCGR0);
1230	} else {
1231		/* CG4 ~ CG6, CAAM clocks */
1232		reg = __raw_readl(&imx_ccm->CCGR0);
1233		if (enable)
1234			reg |= (MXC_CCM_CCGR0_CAAM_WRAPPER_IPG_MASK |
1235				MXC_CCM_CCGR0_CAAM_WRAPPER_ACLK_MASK |
1236				MXC_CCM_CCGR0_CAAM_SECURE_MEM_MASK);
1237		else
1238			reg &= ~(MXC_CCM_CCGR0_CAAM_WRAPPER_IPG_MASK |
1239				MXC_CCM_CCGR0_CAAM_WRAPPER_ACLK_MASK |
1240				MXC_CCM_CCGR0_CAAM_SECURE_MEM_MASK);
1241		__raw_writel(reg, &imx_ccm->CCGR0);
1242	}
1243
1244	/* EMI slow clk */
1245	reg = __raw_readl(&imx_ccm->CCGR6);
1246	if (enable)
1247		reg |= MXC_CCM_CCGR6_EMI_SLOW_MASK;
1248	else
1249		reg &= ~MXC_CCM_CCGR6_EMI_SLOW_MASK;
1250	__raw_writel(reg, &imx_ccm->CCGR6);
1251}
1252#endif
1253
1254static void enable_pll3(void)
1255{
1256	struct anatop_regs __iomem *anatop =
1257		(struct anatop_regs __iomem *)ANATOP_BASE_ADDR;
1258
1259	/* make sure pll3 is enabled */
1260	if ((readl(&anatop->usb1_pll_480_ctrl) &
1261			BM_ANADIG_USB1_PLL_480_CTRL_LOCK) == 0) {
1262		/* enable pll's power */
1263		writel(BM_ANADIG_USB1_PLL_480_CTRL_POWER,
1264		       &anatop->usb1_pll_480_ctrl_set);
1265		writel(0x80, &anatop->ana_misc2_clr);
1266		/* wait for pll lock */
1267		while ((readl(&anatop->usb1_pll_480_ctrl) &
1268			BM_ANADIG_USB1_PLL_480_CTRL_LOCK) == 0)
1269			;
1270		/* disable bypass */
1271		writel(BM_ANADIG_USB1_PLL_480_CTRL_BYPASS,
1272		       &anatop->usb1_pll_480_ctrl_clr);
1273		/* enable pll output */
1274		writel(BM_ANADIG_USB1_PLL_480_CTRL_ENABLE,
1275		       &anatop->usb1_pll_480_ctrl_set);
1276	}
1277}
1278
1279void enable_thermal_clk(void)
1280{
1281	enable_pll3();
1282}
1283
1284#ifdef CONFIG_MTD_NOR_FLASH
1285void enable_eim_clk(unsigned char enable)
1286{
1287	u32 reg;
1288
1289	reg = __raw_readl(&imx_ccm->CCGR6);
1290	if (enable)
1291		reg |= MXC_CCM_CCGR6_EMI_SLOW_MASK;
1292	else
1293		reg &= ~MXC_CCM_CCGR6_EMI_SLOW_MASK;
1294	__raw_writel(reg, &imx_ccm->CCGR6);
1295}
1296#endif
1297
1298unsigned int mxc_get_clock(enum mxc_clock clk)
1299{
1300	switch (clk) {
1301	case MXC_ARM_CLK:
1302		return get_mcu_main_clk();
1303	case MXC_PER_CLK:
1304		return get_periph_clk();
1305	case MXC_AHB_CLK:
1306		return get_ahb_clk();
1307	case MXC_IPG_CLK:
1308		return get_ipg_clk();
1309	case MXC_IPG_PERCLK:
1310	case MXC_I2C_CLK:
1311		return get_ipg_per_clk();
1312	case MXC_UART_CLK:
1313		return get_uart_clk();
1314	case MXC_CSPI_CLK:
1315		return get_cspi_clk();
1316	case MXC_AXI_CLK:
1317		return get_axi_clk();
1318	case MXC_EMI_SLOW_CLK:
1319		return get_emi_slow_clk();
1320	case MXC_DDR_CLK:
1321		return get_mmdc_ch0_clk();
1322	case MXC_ESDHC_CLK:
1323		return get_usdhc_clk(0);
1324	case MXC_ESDHC2_CLK:
1325		return get_usdhc_clk(1);
1326	case MXC_ESDHC3_CLK:
1327		return get_usdhc_clk(2);
1328	case MXC_ESDHC4_CLK:
1329		return get_usdhc_clk(3);
1330	case MXC_SATA_CLK:
1331		return get_ahb_clk();
1332	case MXC_LCDIF1_CLK:
1333		return get_lcd_clk(1);
1334	case MXC_LCDIF2_CLK:
1335		return get_lcd_clk(2);
1336	default:
1337		printf("Unsupported MXC CLK: %d\n", clk);
1338		break;
1339	}
1340
1341	return 0;
1342}
1343
1344#ifndef CONFIG_MX6SX
1345void enable_ipu_clock(void)
1346{
1347	struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
1348
1349	setbits_le32(&mxc_ccm->CCGR3, MXC_CCM_CCGR3_IPU1_IPU_MASK);
1350
1351	if (is_mx6dqp()) {
1352		setbits_le32(&mxc_ccm->CCGR6, MXC_CCM_CCGR6_PRG_CLK0_MASK);
1353		setbits_le32(&mxc_ccm->CCGR3, MXC_CCM_CCGR3_IPU2_IPU_MASK);
1354	}
1355}
1356
1357void disable_ipu_clock(void)
1358{
1359	struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
1360
1361	clrbits_le32(&mxc_ccm->CCGR3, MXC_CCM_CCGR3_IPU1_IPU_MASK);
1362
1363	if (is_mx6dqp()) {
1364		clrbits_le32(&mxc_ccm->CCGR6, MXC_CCM_CCGR6_PRG_CLK0_MASK);
1365		clrbits_le32(&mxc_ccm->CCGR3, MXC_CCM_CCGR3_IPU2_IPU_MASK);
1366	}
1367}
1368#endif
1369
1370#ifndef CONFIG_SPL_BUILD
1371/*
1372 * Dump some core clockes.
1373 */
1374int do_mx6_showclocks(struct cmd_tbl *cmdtp, int flag, int argc,
1375		      char *const argv[])
1376{
1377	u32 freq;
1378	freq = decode_pll(PLL_SYS, MXC_HCLK);
1379	printf("PLL_SYS    %8d MHz\n", freq / 1000000);
1380	freq = decode_pll(PLL_BUS, MXC_HCLK);
1381	printf("PLL_BUS    %8d MHz\n", freq / 1000000);
1382	freq = decode_pll(PLL_USBOTG, MXC_HCLK);
1383	printf("PLL_OTG    %8d MHz\n", freq / 1000000);
1384	freq = decode_pll(PLL_ENET, MXC_HCLK);
1385	printf("PLL_NET    %8d MHz\n", freq / 1000000);
1386
1387	printf("\n");
1388	printf("ARM        %8d kHz\n", mxc_get_clock(MXC_ARM_CLK) / 1000);
1389	printf("IPG        %8d kHz\n", mxc_get_clock(MXC_IPG_CLK) / 1000);
1390	printf("UART       %8d kHz\n", mxc_get_clock(MXC_UART_CLK) / 1000);
1391#ifdef CONFIG_MXC_SPI
1392	printf("CSPI       %8d kHz\n", mxc_get_clock(MXC_CSPI_CLK) / 1000);
1393#endif
1394	printf("AHB        %8d kHz\n", mxc_get_clock(MXC_AHB_CLK) / 1000);
1395	printf("AXI        %8d kHz\n", mxc_get_clock(MXC_AXI_CLK) / 1000);
1396	printf("DDR        %8d kHz\n", mxc_get_clock(MXC_DDR_CLK) / 1000);
1397	printf("USDHC1     %8d kHz\n", mxc_get_clock(MXC_ESDHC_CLK) / 1000);
1398	printf("USDHC2     %8d kHz\n", mxc_get_clock(MXC_ESDHC2_CLK) / 1000);
1399	printf("USDHC3     %8d kHz\n", mxc_get_clock(MXC_ESDHC3_CLK) / 1000);
1400	printf("USDHC4     %8d kHz\n", mxc_get_clock(MXC_ESDHC4_CLK) / 1000);
1401	printf("EMI SLOW   %8d kHz\n", mxc_get_clock(MXC_EMI_SLOW_CLK) / 1000);
1402	printf("IPG PERCLK %8d kHz\n", mxc_get_clock(MXC_IPG_PERCLK) / 1000);
1403
1404	return 0;
1405}
1406
1407#if defined(CONFIG_MX6Q) || defined(CONFIG_MX6D) || defined(CONFIG_MX6DL) || \
1408	defined(CONFIG_MX6S) || defined(CONFIG_MX6QDL)
1409static void disable_ldb_di_clock_sources(void)
1410{
1411	struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
1412	int reg;
1413
1414	/* Make sure PFDs are disabled at boot. */
1415	reg = readl(&mxc_ccm->analog_pfd_528);
1416	/* Cannot disable pll2_pfd2_396M, as it is the MMDC clock in iMX6DL */
1417	if (is_mx6sdl())
1418		reg |= 0x80008080;
1419	else
1420		reg |= 0x80808080;
1421	writel(reg, &mxc_ccm->analog_pfd_528);
1422
1423	/* Disable PLL3 PFDs */
1424	reg = readl(&mxc_ccm->analog_pfd_480);
1425	reg |= 0x80808080;
1426	writel(reg, &mxc_ccm->analog_pfd_480);
1427
1428	/* Disable PLL5 */
1429	reg = readl(&mxc_ccm->analog_pll_video);
1430	reg &= ~(1 << 13);
1431	writel(reg, &mxc_ccm->analog_pll_video);
1432}
1433
1434static void enable_ldb_di_clock_sources(void)
1435{
1436	struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
1437	int reg;
1438
1439	reg = readl(&mxc_ccm->analog_pfd_528);
1440	if (is_mx6sdl())
1441		reg &= ~(0x80008080);
1442	else
1443		reg &= ~(0x80808080);
1444	writel(reg, &mxc_ccm->analog_pfd_528);
1445
1446	reg = readl(&mxc_ccm->analog_pfd_480);
1447	reg &= ~(0x80808080);
1448	writel(reg, &mxc_ccm->analog_pfd_480);
1449}
1450
1451/*
1452 * Try call this function as early in the boot process as possible since the
1453 * function temporarily disables PLL2 PFD's, PLL3 PFD's and PLL5.
1454 */
1455void select_ldb_di_clock_source(enum ldb_di_clock clk)
1456{
1457	struct mxc_ccm_reg *mxc_ccm = (struct mxc_ccm_reg *)CCM_BASE_ADDR;
1458	int reg;
1459
1460	/*
1461	 * Need to follow a strict procedure when changing the LDB
1462	 * clock, else we can introduce a glitch. Things to keep in
1463	 * mind:
1464	 * 1. The current and new parent clocks must be disabled.
1465	 * 2. The default clock for ldb_dio_clk is mmdc_ch1 which has
1466	 * no CG bit.
1467	 * 3. In the RTL implementation of the LDB_DI_CLK_SEL mux
1468	 * the top four options are in one mux and the PLL3 option along
1469	 * with another option is in the second mux. There is third mux
1470	 * used to decide between the first and second mux.
1471	 * The code below switches the parent to the bottom mux first
1472	 * and then manipulates the top mux. This ensures that no glitch
1473	 * will enter the divider.
1474	 *
1475	 * Need to disable MMDC_CH1 clock manually as there is no CG bit
1476	 * for this clock. The only way to disable this clock is to move
1477	 * it to pll3_sw_clk and then to disable pll3_sw_clk
1478	 * Make sure periph2_clk2_sel is set to pll3_sw_clk
1479	 */
1480
1481	/* Disable all ldb_di clock parents */
1482	disable_ldb_di_clock_sources();
1483
1484	/* Set MMDC_CH1 mask bit */
1485	reg = readl(&mxc_ccm->ccdr);
1486	reg |= MXC_CCM_CCDR_MMDC_CH1_HS_MASK;
1487	writel(reg, &mxc_ccm->ccdr);
1488
1489	/* Set periph2_clk2_sel to be sourced from PLL3_sw_clk */
1490	reg = readl(&mxc_ccm->cbcmr);
1491	reg &= ~MXC_CCM_CBCMR_PERIPH2_CLK2_SEL;
1492	writel(reg, &mxc_ccm->cbcmr);
1493
1494	/*
1495	 * Set the periph2_clk_sel to the top mux so that
1496	 * mmdc_ch1 is from pll3_sw_clk.
1497	 */
1498	reg = readl(&mxc_ccm->cbcdr);
1499	reg |= MXC_CCM_CBCDR_PERIPH2_CLK_SEL;
1500	writel(reg, &mxc_ccm->cbcdr);
1501
1502	/* Wait for the clock switch */
1503	while (readl(&mxc_ccm->cdhipr))
1504		;
1505	/* Disable pll3_sw_clk by selecting bypass clock source */
1506	reg = readl(&mxc_ccm->ccsr);
1507	reg |= MXC_CCM_CCSR_PLL3_SW_CLK_SEL;
1508	writel(reg, &mxc_ccm->ccsr);
1509
1510	/* Set the ldb_di0_clk and ldb_di1_clk to 111b */
1511	reg = readl(&mxc_ccm->cs2cdr);
1512	reg |= ((7 << MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_OFFSET)
1513	      | (7 << MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_OFFSET));
1514	writel(reg, &mxc_ccm->cs2cdr);
1515
1516	/* Set the ldb_di0_clk and ldb_di1_clk to 100b */
1517	reg = readl(&mxc_ccm->cs2cdr);
1518	reg &= ~(MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_MASK
1519	      | MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_MASK);
1520	reg |= ((4 << MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_OFFSET)
1521	      | (4 << MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_OFFSET));
1522	writel(reg, &mxc_ccm->cs2cdr);
1523
1524	/* Set the ldb_di0_clk and ldb_di1_clk to desired source */
1525	reg = readl(&mxc_ccm->cs2cdr);
1526	reg &= ~(MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_MASK
1527	      | MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_MASK);
1528	reg |= ((clk << MXC_CCM_CS2CDR_LDB_DI1_CLK_SEL_OFFSET)
1529	      | (clk << MXC_CCM_CS2CDR_LDB_DI0_CLK_SEL_OFFSET));
1530	writel(reg, &mxc_ccm->cs2cdr);
1531
1532	/* Unbypass pll3_sw_clk */
1533	reg = readl(&mxc_ccm->ccsr);
1534	reg &= ~MXC_CCM_CCSR_PLL3_SW_CLK_SEL;
1535	writel(reg, &mxc_ccm->ccsr);
1536
1537	/*
1538	 * Set the periph2_clk_sel back to the bottom mux so that
1539	 * mmdc_ch1 is from its original parent.
1540	 */
1541	reg = readl(&mxc_ccm->cbcdr);
1542	reg &= ~MXC_CCM_CBCDR_PERIPH2_CLK_SEL;
1543	writel(reg, &mxc_ccm->cbcdr);
1544
1545	/* Wait for the clock switch */
1546	while (readl(&mxc_ccm->cdhipr))
1547		;
1548	/* Clear MMDC_CH1 mask bit */
1549	reg = readl(&mxc_ccm->ccdr);
1550	reg &= ~MXC_CCM_CCDR_MMDC_CH1_HS_MASK;
1551	writel(reg, &mxc_ccm->ccdr);
1552
1553	enable_ldb_di_clock_sources();
1554}
1555#endif
1556
1557/***************************************************/
1558
1559U_BOOT_CMD(
1560	clocks,	CONFIG_SYS_MAXARGS, 1, do_mx6_showclocks,
1561	"display clocks",
1562	""
1563);
1564#endif
1565