ARM: uniphier: add PLL init code for LD20 SoC
Initialize the DPLL (PLL for DRAM) in SPL, and others in U-Boot proper. Split the common code into pll-base-ld20.c for easier re-use. Signed-off-by: Masahiro Yamada <yamada.masahiro@socionext.com>
This commit is contained in:
		
							parent
							
								
									fcc238baee
								
							
						
					
					
						commit
						682e09ff9f
					
				|  | @ -58,8 +58,14 @@ static void uniphier_nand_pin_init(bool cs2) | ||||||
| 
 | 
 | ||||||
| int board_init(void) | int board_init(void) | ||||||
| { | { | ||||||
|  | 	const struct uniphier_board_data *bd; | ||||||
|  | 
 | ||||||
| 	led_puts("U0"); | 	led_puts("U0"); | ||||||
| 
 | 
 | ||||||
|  | 	bd = uniphier_get_board_param(); | ||||||
|  | 	if (!bd) | ||||||
|  | 		return -ENODEV; | ||||||
|  | 
 | ||||||
| 	switch (uniphier_get_soc_type()) { | 	switch (uniphier_get_soc_type()) { | ||||||
| #if defined(CONFIG_ARCH_UNIPHIER_SLD3) | #if defined(CONFIG_ARCH_UNIPHIER_SLD3) | ||||||
| 	case SOC_UNIPHIER_SLD3: | 	case SOC_UNIPHIER_SLD3: | ||||||
|  | @ -133,6 +139,7 @@ int board_init(void) | ||||||
| 		sg_set_pinsel(153, 14, 8, 4);	/* XIRQ4    -> XIRQ4 */ | 		sg_set_pinsel(153, 14, 8, 4);	/* XIRQ4    -> XIRQ4 */ | ||||||
| 		sg_set_iectrl(153); | 		sg_set_iectrl(153); | ||||||
| 		led_puts("U1"); | 		led_puts("U1"); | ||||||
|  | 		uniphier_ld20_pll_init(bd); | ||||||
| 		uniphier_ld20_clk_init(); | 		uniphier_ld20_clk_init(); | ||||||
| 		cci500_init(2); | 		cci500_init(2); | ||||||
| 		break; | 		break; | ||||||
|  |  | ||||||
|  | @ -12,7 +12,7 @@ obj-$(CONFIG_ARCH_UNIPHIER_PRO5)	+= early-clk-pro5.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_PXS2)	+= early-clk-pxs2.o | obj-$(CONFIG_ARCH_UNIPHIER_PXS2)	+= early-clk-pxs2.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_LD6B)	+= early-clk-pxs2.o | obj-$(CONFIG_ARCH_UNIPHIER_LD6B)	+= early-clk-pxs2.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_LD11)	+= early-clk-ld11.o | obj-$(CONFIG_ARCH_UNIPHIER_LD11)	+= early-clk-ld11.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_LD20)	+= early-clk-ld20.o | obj-$(CONFIG_ARCH_UNIPHIER_LD20)	+= early-clk-ld20.o dpll-ld20.o | ||||||
| 
 | 
 | ||||||
| else | else | ||||||
| 
 | 
 | ||||||
|  | @ -24,6 +24,8 @@ obj-$(CONFIG_ARCH_UNIPHIER_PRO5)	+= clk-pro5.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_PXS2)	+= clk-pxs2.o | obj-$(CONFIG_ARCH_UNIPHIER_PXS2)	+= clk-pxs2.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_LD6B)	+= clk-pxs2.o | obj-$(CONFIG_ARCH_UNIPHIER_LD6B)	+= clk-pxs2.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_LD11)	+= clk-ld11.o | obj-$(CONFIG_ARCH_UNIPHIER_LD11)	+= clk-ld11.o | ||||||
| obj-$(CONFIG_ARCH_UNIPHIER_LD20)	+= clk-ld20.o | obj-$(CONFIG_ARCH_UNIPHIER_LD20)	+= clk-ld20.o pll-ld20.o | ||||||
| 
 | 
 | ||||||
| endif | endif | ||||||
|  | 
 | ||||||
|  | obj-$(CONFIG_ARCH_UNIPHIER_LD20)	+= pll-base-ld20.o | ||||||
|  |  | ||||||
|  | @ -0,0 +1,22 @@ | ||||||
|  | /*
 | ||||||
|  |  * Copyright (C) 2016 Socionext Inc. | ||||||
|  |  *   Author: Masahiro Yamada <yamada.masahiro@socionext.com> | ||||||
|  |  * | ||||||
|  |  * SPDX-License-Identifier:	GPL-2.0+ | ||||||
|  |  */ | ||||||
|  | 
 | ||||||
|  | #include "../init.h" | ||||||
|  | #include "../sc64-regs.h" | ||||||
|  | #include "pll.h" | ||||||
|  | 
 | ||||||
|  | int uniphier_ld20_dpll_init(const struct uniphier_board_data *bd) | ||||||
|  | { | ||||||
|  | 	unsigned int dpll_ssc_rate = UNIPHIER_BD_DPLL_SSC_GET_RATE(bd->flags); | ||||||
|  | 	unsigned int dram_freq = bd->dram_freq; | ||||||
|  | 
 | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_DPLL0CTRL, dram_freq, dpll_ssc_rate, 2); | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_DPLL1CTRL, dram_freq, dpll_ssc_rate, 2); | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_DPLL2CTRL, dram_freq, dpll_ssc_rate, 2); | ||||||
|  | 
 | ||||||
|  | 	return 0; | ||||||
|  | } | ||||||
|  | @ -0,0 +1,123 @@ | ||||||
|  | /*
 | ||||||
|  |  * Copyright (C) 2016 Socionext Inc. | ||||||
|  |  *   Author: Masahiro Yamada <yamada.masahiro@socionext.com> | ||||||
|  |  * | ||||||
|  |  * SPDX-License-Identifier:	GPL-2.0+ | ||||||
|  |  */ | ||||||
|  | 
 | ||||||
|  | #include <common.h> | ||||||
|  | #include <linux/bitops.h> | ||||||
|  | #include <linux/io.h> | ||||||
|  | #include <linux/sizes.h> | ||||||
|  | 
 | ||||||
|  | #include "pll.h" | ||||||
|  | 
 | ||||||
|  | /* PLL type: SSC */ | ||||||
|  | #define SC_PLLCTRL_SSC_DK_MASK		GENMASK(14, 0) | ||||||
|  | #define SC_PLLCTRL_SSC_EN		BIT(31) | ||||||
|  | #define SC_PLLCTRL2_NRSTDS		BIT(28) | ||||||
|  | #define SC_PLLCTRL2_SSC_JK_MASK		GENMASK(26, 0) | ||||||
|  | 
 | ||||||
|  | /* PLL type: VPLL27 */ | ||||||
|  | #define SC_VPLL27CTRL_WP		BIT(0) | ||||||
|  | #define SC_VPLL27CTRL3_K_LD		BIT(28) | ||||||
|  | 
 | ||||||
|  | /* PLL type: DSPLL */ | ||||||
|  | #define SC_DSPLLCTRL2_K_LD		BIT(28) | ||||||
|  | 
 | ||||||
|  | int uniphier_ld20_sscpll_init(unsigned long reg_base, unsigned int freq, | ||||||
|  | 			      unsigned int ssc_rate, unsigned int divn) | ||||||
|  | { | ||||||
|  | 	void __iomem *base; | ||||||
|  | 	u32 tmp; | ||||||
|  | 
 | ||||||
|  | 	base = ioremap(reg_base, SZ_16); | ||||||
|  | 	if (!base) | ||||||
|  | 		return -ENOMEM; | ||||||
|  | 
 | ||||||
|  | 	if (freq != UNIPHIER_PLL_FREQ_DEFAULT) { | ||||||
|  | 		tmp = readl(base);	/* SSCPLLCTRL */ | ||||||
|  | 		tmp &= ~SC_PLLCTRL_SSC_DK_MASK; | ||||||
|  | 		tmp |= (487 * freq * ssc_rate / divn / 512) & | ||||||
|  | 							SC_PLLCTRL_SSC_DK_MASK; | ||||||
|  | 		writel(tmp, base); | ||||||
|  | 
 | ||||||
|  | 		tmp = readl(base + 4); | ||||||
|  | 		tmp &= ~SC_PLLCTRL2_SSC_JK_MASK; | ||||||
|  | 		tmp |= (41859 * freq / divn) & SC_PLLCTRL2_SSC_JK_MASK; | ||||||
|  | 
 | ||||||
|  | 		udelay(50); | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	tmp = readl(base + 4);		/* SSCPLLCTRL2 */ | ||||||
|  | 	tmp |= SC_PLLCTRL2_NRSTDS; | ||||||
|  | 	writel(tmp, base + 4); | ||||||
|  | 
 | ||||||
|  | 	iounmap(base); | ||||||
|  | 
 | ||||||
|  | 	return 0; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | int uniphier_ld20_sscpll_ssc_en(unsigned long reg_base) | ||||||
|  | { | ||||||
|  | 	void __iomem *base; | ||||||
|  | 	u32 tmp; | ||||||
|  | 
 | ||||||
|  | 	base = ioremap(reg_base, SZ_16); | ||||||
|  | 	if (!base) | ||||||
|  | 		return -ENOMEM; | ||||||
|  | 
 | ||||||
|  | 	mdelay(1); | ||||||
|  | 
 | ||||||
|  | 	tmp = readl(base);	/* SSCPLLCTRL */ | ||||||
|  | 	tmp |= SC_PLLCTRL_SSC_EN; | ||||||
|  | 	writel(tmp, base); | ||||||
|  | 
 | ||||||
|  | 	iounmap(base); | ||||||
|  | 
 | ||||||
|  | 	return 0; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | int uniphier_ld20_vpll27_init(unsigned long reg_base) | ||||||
|  | { | ||||||
|  | 	void __iomem *base; | ||||||
|  | 	u32 tmp; | ||||||
|  | 
 | ||||||
|  | 	base = ioremap(reg_base, SZ_16); | ||||||
|  | 	if (!base) | ||||||
|  | 		return -ENOMEM; | ||||||
|  | 
 | ||||||
|  | 	tmp = readl(base);		/* VPLL27CTRL */ | ||||||
|  | 	tmp |= SC_VPLL27CTRL_WP;	/* write protect off */ | ||||||
|  | 	writel(tmp, base); | ||||||
|  | 
 | ||||||
|  | 	tmp = readl(base + 8);		/* VPLL27CTRL3 */ | ||||||
|  | 	tmp |= SC_VPLL27CTRL3_K_LD; | ||||||
|  | 	writel(tmp, base + 8); | ||||||
|  | 
 | ||||||
|  | 	tmp = readl(base);		/* VPLL27CTRL */ | ||||||
|  | 	tmp &= ~SC_VPLL27CTRL_WP;	/* write protect on */ | ||||||
|  | 	writel(tmp, base); | ||||||
|  | 
 | ||||||
|  | 	iounmap(base); | ||||||
|  | 
 | ||||||
|  | 	return 0; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | int uniphier_ld20_dspll_init(unsigned long reg_base) | ||||||
|  | { | ||||||
|  | 	void __iomem *base; | ||||||
|  | 	u32 tmp; | ||||||
|  | 
 | ||||||
|  | 	base = ioremap(reg_base, SZ_16); | ||||||
|  | 	if (!base) | ||||||
|  | 		return -ENOMEM; | ||||||
|  | 
 | ||||||
|  | 	tmp = readl(base + 8);		/* DSPLLCTRL2 */ | ||||||
|  | 	tmp |= SC_DSPLLCTRL2_K_LD; | ||||||
|  | 	writel(tmp, base + 8); | ||||||
|  | 
 | ||||||
|  | 	iounmap(base); | ||||||
|  | 
 | ||||||
|  | 	return 0; | ||||||
|  | } | ||||||
|  | @ -0,0 +1,40 @@ | ||||||
|  | /*
 | ||||||
|  |  * Copyright (C) 2016 Socionext Inc. | ||||||
|  |  *   Author: Masahiro Yamada <yamada.masahiro@socionext.com> | ||||||
|  |  * | ||||||
|  |  * SPDX-License-Identifier:	GPL-2.0+ | ||||||
|  |  */ | ||||||
|  | 
 | ||||||
|  | #include <common.h> | ||||||
|  | 
 | ||||||
|  | #include "../init.h" | ||||||
|  | #include "../sc64-regs.h" | ||||||
|  | #include "pll.h" | ||||||
|  | 
 | ||||||
|  | int uniphier_ld20_pll_init(const struct uniphier_board_data *bd) | ||||||
|  | { | ||||||
|  | 	unsigned int dpll_ssc_rate = UNIPHIER_BD_DPLL_SSC_GET_RATE(bd->flags); | ||||||
|  | 
 | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_CPLLCTRL, UNIPHIER_PLL_FREQ_DEFAULT, 0, 4); | ||||||
|  | 	/* do nothing for SPLL */ | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_SPLL2CTRL, UNIPHIER_PLL_FREQ_DEFAULT, 0, 4); | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_MPLLCTRL, UNIPHIER_PLL_FREQ_DEFAULT, 0, 2); | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_VPPLLCTRL, UNIPHIER_PLL_FREQ_DEFAULT, 0, 4); | ||||||
|  | 	uniphier_ld20_sscpll_init(SC_GPPLLCTRL, UNIPHIER_PLL_FREQ_DEFAULT, 0, 2); | ||||||
|  | 
 | ||||||
|  | 	mdelay(1); | ||||||
|  | 
 | ||||||
|  | 	if (dpll_ssc_rate > 0) { | ||||||
|  | 		uniphier_ld20_sscpll_ssc_en(SC_DPLL0CTRL); | ||||||
|  | 		uniphier_ld20_sscpll_ssc_en(SC_DPLL1CTRL); | ||||||
|  | 		uniphier_ld20_sscpll_ssc_en(SC_DPLL2CTRL); | ||||||
|  | 	} | ||||||
|  | 
 | ||||||
|  | 	uniphier_ld20_vpll27_init(SC_VPLL27FCTRL); | ||||||
|  | 	uniphier_ld20_vpll27_init(SC_VPLL27ACTRL); | ||||||
|  | 
 | ||||||
|  | 	uniphier_ld20_dspll_init(SC_VPLL8KCTRL); | ||||||
|  | 	uniphier_ld20_dspll_init(SC_A2PLLCTRL); | ||||||
|  | 
 | ||||||
|  | 	return 0; | ||||||
|  | } | ||||||
|  | @ -8,6 +8,14 @@ | ||||||
| #ifndef MACH_PLL_H | #ifndef MACH_PLL_H | ||||||
| #define MACH_PLL_H | #define MACH_PLL_H | ||||||
| 
 | 
 | ||||||
|  | #define UNIPHIER_PLL_FREQ_DEFAULT	(0) | ||||||
|  | 
 | ||||||
| void uniphier_ld4_dpll_ssc_en(void); | void uniphier_ld4_dpll_ssc_en(void); | ||||||
| 
 | 
 | ||||||
|  | int uniphier_ld20_sscpll_init(unsigned long reg_base, unsigned int freq, | ||||||
|  | 			      unsigned int ssc_rate, unsigned int divn); | ||||||
|  | int uniphier_ld20_sscpll_ssc_en(unsigned long reg_base); | ||||||
|  | int uniphier_ld20_vpll27_init(unsigned long reg_base); | ||||||
|  | int uniphier_ld20_dspll_init(unsigned long reg_base); | ||||||
|  | 
 | ||||||
| #endif /* MACH_PLL_H */ | #endif /* MACH_PLL_H */ | ||||||
|  |  | ||||||
|  | @ -24,6 +24,9 @@ struct uniphier_board_data { | ||||||
| 	struct uniphier_dram_ch dram_ch[UNIPHIER_MAX_NR_DRAM_CH]; | 	struct uniphier_dram_ch dram_ch[UNIPHIER_MAX_NR_DRAM_CH]; | ||||||
| 	unsigned int flags; | 	unsigned int flags; | ||||||
| 
 | 
 | ||||||
|  | #define UNIPHIER_BD_DPLL_SSC_GET_RATE(f)	(((f) >> 8) & 0x3) | ||||||
|  | #define UNIPHIER_BD_DPLL_SSC_RATE(r)		(((r) & 0x3) << 8) | ||||||
|  | 
 | ||||||
| #define UNIPHIER_BD_DDR3PLUS			BIT(2) | #define UNIPHIER_BD_DDR3PLUS			BIT(2) | ||||||
| 
 | 
 | ||||||
| #define UNIPHIER_BD_BOARD_GET_TYPE(f)		((f) & 0x3) | #define UNIPHIER_BD_BOARD_GET_TYPE(f)		((f) & 0x3) | ||||||
|  | @ -84,6 +87,7 @@ int uniphier_sld3_dpll_init(const struct uniphier_board_data *bd); | ||||||
| int uniphier_ld4_dpll_init(const struct uniphier_board_data *bd); | int uniphier_ld4_dpll_init(const struct uniphier_board_data *bd); | ||||||
| int uniphier_pro4_dpll_init(const struct uniphier_board_data *bd); | int uniphier_pro4_dpll_init(const struct uniphier_board_data *bd); | ||||||
| int uniphier_sld8_dpll_init(const struct uniphier_board_data *bd); | int uniphier_sld8_dpll_init(const struct uniphier_board_data *bd); | ||||||
|  | int uniphier_ld20_dpll_init(const struct uniphier_board_data *bd); | ||||||
| 
 | 
 | ||||||
| int uniphier_ld4_early_clk_init(const struct uniphier_board_data *bd); | int uniphier_ld4_early_clk_init(const struct uniphier_board_data *bd); | ||||||
| int uniphier_pro5_early_clk_init(const struct uniphier_board_data *bd); | int uniphier_pro5_early_clk_init(const struct uniphier_board_data *bd); | ||||||
|  | @ -101,6 +105,7 @@ int uniphier_ld11_umc_init(const struct uniphier_board_data *bd); | ||||||
| void uniphier_sld3_pll_init(void); | void uniphier_sld3_pll_init(void); | ||||||
| void uniphier_ld4_pll_init(void); | void uniphier_ld4_pll_init(void); | ||||||
| void uniphier_pro4_pll_init(void); | void uniphier_pro4_pll_init(void); | ||||||
|  | int uniphier_ld20_pll_init(const struct uniphier_board_data *bd); | ||||||
| 
 | 
 | ||||||
| void uniphier_ld4_clk_init(void); | void uniphier_ld4_clk_init(void); | ||||||
| void uniphier_pro4_clk_init(void); | void uniphier_pro4_clk_init(void); | ||||||
|  |  | ||||||
|  | @ -32,12 +32,14 @@ int uniphier_ld20_init(const struct uniphier_board_data *bd) | ||||||
| 
 | 
 | ||||||
| 	led_puts("L2"); | 	led_puts("L2"); | ||||||
| 
 | 
 | ||||||
| 	led_puts("L3"); |  | ||||||
| 
 |  | ||||||
| #ifdef CONFIG_SPL_SERIAL_SUPPORT | #ifdef CONFIG_SPL_SERIAL_SUPPORT | ||||||
| 	preloader_console_init(); | 	preloader_console_init(); | ||||||
| #endif | #endif | ||||||
| 
 | 
 | ||||||
|  | 	led_puts("L3"); | ||||||
|  | 
 | ||||||
|  | 	uniphier_ld20_dpll_init(bd); | ||||||
|  | 
 | ||||||
| 	led_puts("L4"); | 	led_puts("L4"); | ||||||
| 
 | 
 | ||||||
| 	{ | 	{ | ||||||
|  |  | ||||||
|  | @ -1,7 +1,8 @@ | ||||||
| /*
 | /*
 | ||||||
|  * UniPhier SC (System Control) block registers for ARMv8 SoCs |  * UniPhier SC (System Control) block registers for ARMv8 SoCs | ||||||
|  * |  * | ||||||
|  * Copyright (C) 2016 Masahiro Yamada <yamada.masahiro@socionext.com> |  * Copyright (C) 2016 Socionext Inc. | ||||||
|  |  *   Author: Masahiro Yamada <yamada.masahiro@socionext.com> | ||||||
|  * |  * | ||||||
|  * SPDX-License-Identifier:	GPL-2.0+ |  * SPDX-License-Identifier:	GPL-2.0+ | ||||||
|  */ |  */ | ||||||
|  | @ -11,6 +12,25 @@ | ||||||
| 
 | 
 | ||||||
| #define SC_BASE_ADDR		0x61840000 | #define SC_BASE_ADDR		0x61840000 | ||||||
| 
 | 
 | ||||||
|  | /* PLL type: SSC */ | ||||||
|  | #define SC_CPLLCTRL	(SC_BASE_ADDR | 0x1400)	/* LD20: CPU/ARM */ | ||||||
|  | #define SC_SPLLCTRL	(SC_BASE_ADDR | 0x1410)	/* LD20: misc */ | ||||||
|  | #define SC_SPLL2CTRL	(SC_BASE_ADDR | 0x1420)	/* LD20: IPP */ | ||||||
|  | #define SC_MPLLCTRL	(SC_BASE_ADDR | 0x1430)	/* LD20: Video codec */ | ||||||
|  | #define SC_VPPLLCTRL	(SC_BASE_ADDR | 0x1440)	/* LD20: VPE etc. */ | ||||||
|  | #define SC_GPPLLCTRL	(SC_BASE_ADDR | 0x1450)	/* LD20: GPU/Mali */ | ||||||
|  | #define SC_DPLL0CTRL	(SC_BASE_ADDR | 0x1460)	/* LD20: DDR memory 0 */ | ||||||
|  | #define SC_DPLL1CTRL	(SC_BASE_ADDR | 0x1470)	/* LD20: DDR memory 1 */ | ||||||
|  | #define SC_DPLL2CTRL	(SC_BASE_ADDR | 0x1480)	/* LD20: DDR memory 2 */ | ||||||
|  | 
 | ||||||
|  | /* PLL type: VPLL27 */ | ||||||
|  | #define SC_VPLL27FCTRL	(SC_BASE_ADDR | 0x1500) | ||||||
|  | #define SC_VPLL27ACTRL	(SC_BASE_ADDR | 0x1520) | ||||||
|  | 
 | ||||||
|  | /* PLL type: DSPLL */ | ||||||
|  | #define SC_VPLL8KCTRL	(SC_BASE_ADDR | 0x1540) | ||||||
|  | #define SC_A2PLLCTRL	(SC_BASE_ADDR | 0x15C0) | ||||||
|  | 
 | ||||||
| #define SC_RSTCTRL		(SC_BASE_ADDR | 0x2000) | #define SC_RSTCTRL		(SC_BASE_ADDR | 0x2000) | ||||||
| #define SC_RSTCTRL3		(SC_BASE_ADDR | 0x2008) | #define SC_RSTCTRL3		(SC_BASE_ADDR | 0x2008) | ||||||
| #define SC_RSTCTRL4		(SC_BASE_ADDR | 0x200c) | #define SC_RSTCTRL4		(SC_BASE_ADDR | 0x200c) | ||||||
|  |  | ||||||
		Loading…
	
		Reference in New Issue