2 * Keystone2: pll initialization
4 * (C) Copyright 2012-2014
5 * Texas Instruments Incorporated, <www.ti.com>
7 * SPDX-License-Identifier: GPL-2.0+
11 #include <asm/arch/clock.h>
12 #include <asm/arch/clock_defs.h>
14 /* DEV and ARM speed definitions as specified in DEVSPEED register */
15 int __weak speeds
[DEVSPEED_NUMSPDS
] = {
28 const struct keystone_pll_regs keystone_pll_regs
[] = {
29 [CORE_PLL
] = {KS2_MAINPLLCTL0
, KS2_MAINPLLCTL1
},
30 [PASS_PLL
] = {KS2_PASSPLLCTL0
, KS2_PASSPLLCTL1
},
31 [TETRIS_PLL
] = {KS2_ARMPLLCTL0
, KS2_ARMPLLCTL1
},
32 [DDR3A_PLL
] = {KS2_DDR3APLLCTL0
, KS2_DDR3APLLCTL1
},
33 [DDR3B_PLL
] = {KS2_DDR3BPLLCTL0
, KS2_DDR3BPLLCTL1
},
36 static void wait_for_completion(const struct pll_init_data
*data
)
39 for (i
= 0; i
< 100; i
++) {
41 if (!(pllctl_reg_read(data
->pll
, stat
) & PLLSTAT_GOSTAT_MASK
))
46 static inline void bypass_main_pll(const struct pll_init_data
*data
)
48 pllctl_reg_clrbits(data
->pll
, ctl
, PLLCTL_PLLENSRC_MASK
|
51 /* 4 cycles of reference clock CLKIN*/
55 static void configure_mult_div(const struct pll_init_data
*data
)
57 u32 pllm
, plld
, bwadj
;
59 pllm
= data
->pll_m
- 1;
60 plld
= (data
->pll_d
- 1) & CFG_PLLCTL0_PLLD_MASK
;
62 /* Program Multiplier */
63 if (data
->pll
== MAIN_PLL
)
64 pllctl_reg_write(data
->pll
, mult
, pllm
& PLLM_MULT_LO_MASK
);
66 clrsetbits_le32(keystone_pll_regs
[data
->pll
].reg0
,
67 CFG_PLLCTL0_PLLM_MASK
,
68 pllm
<< CFG_PLLCTL0_PLLM_SHIFT
);
71 bwadj
= (data
->pll_m
- 1) >> 1; /* Divide pllm by 2 */
72 clrsetbits_le32(keystone_pll_regs
[data
->pll
].reg0
,
73 CFG_PLLCTL0_BWADJ_MASK
,
74 (bwadj
<< CFG_PLLCTL0_BWADJ_SHIFT
) &
75 CFG_PLLCTL0_BWADJ_MASK
);
76 bwadj
= bwadj
>> CFG_PLLCTL0_BWADJ_BITS
;
77 clrsetbits_le32(keystone_pll_regs
[data
->pll
].reg1
,
78 CFG_PLLCTL1_BWADJ_MASK
, bwadj
);
81 clrsetbits_le32(keystone_pll_regs
[data
->pll
].reg0
,
82 CFG_PLLCTL0_PLLD_MASK
, plld
);
85 void configure_main_pll(const struct pll_init_data
*data
)
87 u32 tmp
, pllod
, i
, alnctl_val
= 0;
90 pllod
= data
->pll_od
- 1;
92 /* 100 micro sec for stabilization */
95 tmp
= pllctl_reg_read(data
->pll
, secctl
);
97 /* Check for Bypass */
98 if (tmp
& SECCTL_BYPASS_MASK
) {
99 setbits_le32(keystone_pll_regs
[data
->pll
].reg1
,
100 CFG_PLLCTL1_ENSAT_MASK
);
102 bypass_main_pll(data
);
104 /* Powerdown and powerup Main Pll */
105 pllctl_reg_setbits(data
->pll
, secctl
, SECCTL_BYPASS_MASK
);
106 pllctl_reg_setbits(data
->pll
, ctl
, PLLCTL_PLLPWRDN_MASK
);
110 pllctl_reg_clrbits(data
->pll
, ctl
, PLLCTL_PLLPWRDN_MASK
);
112 bypass_main_pll(data
);
115 configure_mult_div(data
);
117 /* Program Output Divider */
118 pllctl_reg_rmw(data
->pll
, secctl
, SECCTL_OP_DIV_MASK
,
119 ((pllod
<< SECCTL_OP_DIV_SHIFT
) & SECCTL_OP_DIV_MASK
));
121 /* Program PLLDIVn */
122 wait_for_completion(data
);
123 for (i
= 0; i
< PLLDIV_MAX
; i
++) {
125 offset
= pllctl_reg(data
->pll
, div1
) + i
;
127 offset
= pllctl_reg(data
->pll
, div4
) + (i
- 3);
129 if (divn_val
[i
] != -1) {
130 __raw_writel(divn_val
[i
] | PLLDIV_ENABLE_MASK
, offset
);
131 alnctl_val
|= BIT(i
);
136 pllctl_reg_setbits(data
->pll
, alnctl
, alnctl_val
);
138 * Set GOSET bit in PLLCMD to initiate the GO operation
139 * to change the divide
141 pllctl_reg_setbits(data
->pll
, cmd
, PLLSTAT_GOSTAT_MASK
);
142 wait_for_completion(data
);
146 pllctl_reg_setbits(data
->pll
, ctl
, PLLCTL_PLLRST_MASK
);
147 sdelay(21000); /* Wait for a minimum of 7 us*/
148 pllctl_reg_clrbits(data
->pll
, ctl
, PLLCTL_PLLRST_MASK
);
149 sdelay(105000); /* Wait for PLL Lock time (min 50 us) */
152 pllctl_reg_clrbits(data
->pll
, secctl
, SECCTL_BYPASS_MASK
);
153 pllctl_reg_setbits(data
->pll
, ctl
, PLLCTL_PLLEN_MASK
);
156 void configure_secondary_pll(const struct pll_init_data
*data
)
158 int pllod
= data
->pll_od
- 1;
160 /* Enable Bypass mode */
161 setbits_le32(keystone_pll_regs
[data
->pll
].reg1
, CFG_PLLCTL1_ENSAT_MASK
);
162 setbits_le32(keystone_pll_regs
[data
->pll
].reg0
,
163 CFG_PLLCTL0_BYPASS_MASK
);
165 /* Enable Glitch free bypass for ARM PLL */
166 if (cpu_is_k2hk() && data
->pll
== TETRIS_PLL
)
167 clrbits_le32(KS2_MISC_CTRL
, MISC_CTL1_ARM_PLL_EN
);
169 configure_mult_div(data
);
171 /* Program Output Divider */
172 clrsetbits_le32(keystone_pll_regs
[data
->pll
].reg0
,
173 CFG_PLLCTL0_CLKOD_MASK
,
174 (pllod
<< CFG_PLLCTL0_CLKOD_SHIFT
) &
175 CFG_PLLCTL0_CLKOD_MASK
);
178 setbits_le32(keystone_pll_regs
[data
->pll
].reg1
, CFG_PLLCTL1_RST_MASK
);
179 /* Wait for 5 micro seconds */
182 /* Select the Output of PASS PLL as input to PASS */
183 if (data
->pll
== PASS_PLL
)
184 setbits_le32(keystone_pll_regs
[data
->pll
].reg1
,
185 CFG_PLLCTL1_PAPLL_MASK
);
187 /* Select the Output of ARM PLL as input to ARM */
188 if (data
->pll
== TETRIS_PLL
)
189 setbits_le32(KS2_MISC_CTRL
, MISC_CTL1_ARM_PLL_EN
);
191 clrbits_le32(keystone_pll_regs
[data
->pll
].reg1
, CFG_PLLCTL1_RST_MASK
);
192 /* Wait for 500 * REFCLK cucles * (PLLD + 1) */
195 /* Switch to PLL mode */
196 clrbits_le32(keystone_pll_regs
[data
->pll
].reg0
,
197 CFG_PLLCTL0_BYPASS_MASK
);
200 void init_pll(const struct pll_init_data
*data
)
202 if (data
->pll
== MAIN_PLL
)
203 configure_main_pll(data
);
205 configure_secondary_pll(data
);
208 * This is required to provide a delay between multiple
209 * consequent PPL configurations
216 struct pll_init_data
*data
;
219 for (pll
= MAIN_PLL
; pll
< MAX_PLL_COUNT
; pll
++) {
220 data
= get_pll_init_data(pll
);
226 static int get_max_speed(u32 val
, u32 speed_supported
)
230 /* Left most setbit gives the speed */
231 for (speed
= DEVSPEED_NUMSPDS
; speed
>= 0; speed
--) {
232 if ((val
& BIT(speed
)) & speed_supported
)
233 return speeds
[speed
];
236 /* If no bit is set, use SPD800 */
240 static inline u32
read_efuse_bootrom(void)
242 if (cpu_is_k2hk() && (cpu_revision() <= 1))
243 return __raw_readl(KS2_REV1_DEVSPEED
);
245 return __raw_readl(KS2_EFUSE_BOOTROM
);
248 int get_max_arm_speed(void)
250 u32 armspeed
= read_efuse_bootrom();
252 armspeed
= (armspeed
& DEVSPEED_ARMSPEED_MASK
) >>
253 DEVSPEED_ARMSPEED_SHIFT
;
255 return get_max_speed(armspeed
, ARM_SUPPORTED_SPEEDS
);
258 int get_max_dev_speed(void)
260 u32 devspeed
= read_efuse_bootrom();
262 devspeed
= (devspeed
& DEVSPEED_DEVSPEED_MASK
) >>
263 DEVSPEED_DEVSPEED_SHIFT
;
265 return get_max_speed(devspeed
, DEV_SUPPORTED_SPEEDS
);