1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Copyright (C) 2016-2018 Intel Corporation <www.intel.com>
4  *
5  */
6 
7 #include <common.h>
8 #include <asm/io.h>
9 #include <asm/arch/clock_manager.h>
10 #include <asm/arch/handoff_s10.h>
11 #include <asm/arch/system_manager.h>
12 
13 DECLARE_GLOBAL_DATA_PTR;
14 
15 static const struct socfpga_clock_manager *clock_manager_base =
16 	(struct socfpga_clock_manager *)SOCFPGA_CLKMGR_ADDRESS;
17 static const struct socfpga_system_manager *sysmgr_regs =
18 		(struct socfpga_system_manager *)SOCFPGA_SYSMGR_ADDRESS;
19 
20 /*
21  * function to write the bypass register which requires a poll of the
22  * busy bit
23  */
cm_write_bypass_mainpll(u32 val)24 static void cm_write_bypass_mainpll(u32 val)
25 {
26 	writel(val, &clock_manager_base->main_pll.bypass);
27 	cm_wait_for_fsm();
28 }
29 
cm_write_bypass_perpll(u32 val)30 static void cm_write_bypass_perpll(u32 val)
31 {
32 	writel(val, &clock_manager_base->per_pll.bypass);
33 	cm_wait_for_fsm();
34 }
35 
36 /* function to write the ctrl register which requires a poll of the busy bit */
cm_write_ctrl(u32 val)37 static void cm_write_ctrl(u32 val)
38 {
39 	writel(val, &clock_manager_base->ctrl);
40 	cm_wait_for_fsm();
41 }
42 
43 /*
44  * Setup clocks while making no assumptions about previous state of the clocks.
45  */
cm_basic_init(const struct cm_config * const cfg)46 void cm_basic_init(const struct cm_config * const cfg)
47 {
48 	u32 mdiv, refclkdiv, mscnt, hscnt, vcocalib;
49 
50 	if (cfg == 0)
51 		return;
52 
53 	/* Put all plls in bypass */
54 	cm_write_bypass_mainpll(CLKMGR_BYPASS_MAINPLL_ALL);
55 	cm_write_bypass_perpll(CLKMGR_BYPASS_PERPLL_ALL);
56 
57 	/* setup main PLL dividers where calculate the vcocalib value */
58 	mdiv = (cfg->main_pll_fdbck >> CLKMGR_FDBCK_MDIV_OFFSET) &
59 		CLKMGR_FDBCK_MDIV_MASK;
60 	refclkdiv = (cfg->main_pll_pllglob >> CLKMGR_PLLGLOB_REFCLKDIV_OFFSET) &
61 		     CLKMGR_PLLGLOB_REFCLKDIV_MASK;
62 	mscnt = CLKMGR_MSCNT_CONST / (CLKMGR_MDIV_CONST + mdiv) / refclkdiv;
63 	hscnt = (mdiv + CLKMGR_MDIV_CONST) * mscnt / refclkdiv -
64 		CLKMGR_HSCNT_CONST;
65 	vcocalib = (hscnt & CLKMGR_VCOCALIB_HSCNT_MASK) |
66 		   ((mscnt & CLKMGR_VCOCALIB_MSCNT_MASK) <<
67 		   CLKMGR_VCOCALIB_MSCNT_OFFSET);
68 
69 	writel((cfg->main_pll_pllglob & ~CLKMGR_PLLGLOB_PD_MASK &
70 		~CLKMGR_PLLGLOB_RST_MASK),
71 		&clock_manager_base->main_pll.pllglob);
72 	writel(cfg->main_pll_fdbck, &clock_manager_base->main_pll.fdbck);
73 	writel(vcocalib, &clock_manager_base->main_pll.vcocalib);
74 	writel(cfg->main_pll_pllc0, &clock_manager_base->main_pll.pllc0);
75 	writel(cfg->main_pll_pllc1, &clock_manager_base->main_pll.pllc1);
76 	writel(cfg->main_pll_nocdiv, &clock_manager_base->main_pll.nocdiv);
77 
78 	/* setup peripheral PLL dividers */
79 	/* calculate the vcocalib value */
80 	mdiv = (cfg->per_pll_fdbck >> CLKMGR_FDBCK_MDIV_OFFSET) &
81 		CLKMGR_FDBCK_MDIV_MASK;
82 	refclkdiv = (cfg->per_pll_pllglob >> CLKMGR_PLLGLOB_REFCLKDIV_OFFSET) &
83 		     CLKMGR_PLLGLOB_REFCLKDIV_MASK;
84 	mscnt = CLKMGR_MSCNT_CONST / (CLKMGR_MDIV_CONST + mdiv) / refclkdiv;
85 	hscnt = (mdiv + CLKMGR_MDIV_CONST) * mscnt / refclkdiv -
86 		CLKMGR_HSCNT_CONST;
87 	vcocalib = (hscnt & CLKMGR_VCOCALIB_HSCNT_MASK) |
88 		   ((mscnt & CLKMGR_VCOCALIB_MSCNT_MASK) <<
89 		   CLKMGR_VCOCALIB_MSCNT_OFFSET);
90 
91 	writel((cfg->per_pll_pllglob & ~CLKMGR_PLLGLOB_PD_MASK &
92 		~CLKMGR_PLLGLOB_RST_MASK),
93 		&clock_manager_base->per_pll.pllglob);
94 	writel(cfg->per_pll_fdbck, &clock_manager_base->per_pll.fdbck);
95 	writel(vcocalib, &clock_manager_base->per_pll.vcocalib);
96 	writel(cfg->per_pll_pllc0, &clock_manager_base->per_pll.pllc0);
97 	writel(cfg->per_pll_pllc1, &clock_manager_base->per_pll.pllc1);
98 	writel(cfg->per_pll_emacctl, &clock_manager_base->per_pll.emacctl);
99 	writel(cfg->per_pll_gpiodiv, &clock_manager_base->per_pll.gpiodiv);
100 
101 	/* Take both PLL out of reset and power up */
102 	setbits_le32(&clock_manager_base->main_pll.pllglob,
103 		     CLKMGR_PLLGLOB_PD_MASK | CLKMGR_PLLGLOB_RST_MASK);
104 	setbits_le32(&clock_manager_base->per_pll.pllglob,
105 		     CLKMGR_PLLGLOB_PD_MASK | CLKMGR_PLLGLOB_RST_MASK);
106 
107 #define LOCKED_MASK \
108 	(CLKMGR_STAT_MAINPLL_LOCKED | \
109 	CLKMGR_STAT_PERPLL_LOCKED)
110 
111 	cm_wait_for_lock(LOCKED_MASK);
112 
113 	/*
114 	 * Dividers for C2 to C9 only init after PLLs are lock. As dividers
115 	 * only take effect upon value change, we shall set a maximum value as
116 	 * default value.
117 	 */
118 	writel(0xff, &clock_manager_base->main_pll.mpuclk);
119 	writel(0xff, &clock_manager_base->main_pll.nocclk);
120 	writel(0xff, &clock_manager_base->main_pll.cntr2clk);
121 	writel(0xff, &clock_manager_base->main_pll.cntr3clk);
122 	writel(0xff, &clock_manager_base->main_pll.cntr4clk);
123 	writel(0xff, &clock_manager_base->main_pll.cntr5clk);
124 	writel(0xff, &clock_manager_base->main_pll.cntr6clk);
125 	writel(0xff, &clock_manager_base->main_pll.cntr7clk);
126 	writel(0xff, &clock_manager_base->main_pll.cntr8clk);
127 	writel(0xff, &clock_manager_base->main_pll.cntr9clk);
128 	writel(0xff, &clock_manager_base->per_pll.cntr2clk);
129 	writel(0xff, &clock_manager_base->per_pll.cntr3clk);
130 	writel(0xff, &clock_manager_base->per_pll.cntr4clk);
131 	writel(0xff, &clock_manager_base->per_pll.cntr5clk);
132 	writel(0xff, &clock_manager_base->per_pll.cntr6clk);
133 	writel(0xff, &clock_manager_base->per_pll.cntr7clk);
134 	writel(0xff, &clock_manager_base->per_pll.cntr8clk);
135 	writel(0xff, &clock_manager_base->per_pll.cntr9clk);
136 
137 	writel(cfg->main_pll_mpuclk, &clock_manager_base->main_pll.mpuclk);
138 	writel(cfg->main_pll_nocclk, &clock_manager_base->main_pll.nocclk);
139 	writel(cfg->main_pll_cntr2clk, &clock_manager_base->main_pll.cntr2clk);
140 	writel(cfg->main_pll_cntr3clk, &clock_manager_base->main_pll.cntr3clk);
141 	writel(cfg->main_pll_cntr4clk, &clock_manager_base->main_pll.cntr4clk);
142 	writel(cfg->main_pll_cntr5clk, &clock_manager_base->main_pll.cntr5clk);
143 	writel(cfg->main_pll_cntr6clk, &clock_manager_base->main_pll.cntr6clk);
144 	writel(cfg->main_pll_cntr7clk, &clock_manager_base->main_pll.cntr7clk);
145 	writel(cfg->main_pll_cntr8clk, &clock_manager_base->main_pll.cntr8clk);
146 	writel(cfg->main_pll_cntr9clk, &clock_manager_base->main_pll.cntr9clk);
147 	writel(cfg->per_pll_cntr2clk, &clock_manager_base->per_pll.cntr2clk);
148 	writel(cfg->per_pll_cntr3clk, &clock_manager_base->per_pll.cntr3clk);
149 	writel(cfg->per_pll_cntr4clk, &clock_manager_base->per_pll.cntr4clk);
150 	writel(cfg->per_pll_cntr5clk, &clock_manager_base->per_pll.cntr5clk);
151 	writel(cfg->per_pll_cntr6clk, &clock_manager_base->per_pll.cntr6clk);
152 	writel(cfg->per_pll_cntr7clk, &clock_manager_base->per_pll.cntr7clk);
153 	writel(cfg->per_pll_cntr8clk, &clock_manager_base->per_pll.cntr8clk);
154 	writel(cfg->per_pll_cntr9clk, &clock_manager_base->per_pll.cntr9clk);
155 
156 	/* Take all PLLs out of bypass */
157 	cm_write_bypass_mainpll(0);
158 	cm_write_bypass_perpll(0);
159 
160 	/* clear safe mode / out of boot mode */
161 	cm_write_ctrl(readl(&clock_manager_base->ctrl)
162 			& ~(CLKMGR_CTRL_SAFEMODE));
163 
164 	/* Now ungate non-hw-managed clocks */
165 	writel(~0, &clock_manager_base->main_pll.en);
166 	writel(~0, &clock_manager_base->per_pll.en);
167 
168 	/* Clear the loss of lock bits (write 1 to clear) */
169 	writel(CLKMGR_INTER_PERPLLLOST_MASK | CLKMGR_INTER_MAINPLLLOST_MASK,
170 	       &clock_manager_base->intrclr);
171 }
172 
cm_get_main_vco_clk_hz(void)173 static unsigned long cm_get_main_vco_clk_hz(void)
174 {
175 	 unsigned long fref, refdiv, mdiv, reg, vco;
176 
177 	reg = readl(&clock_manager_base->main_pll.pllglob);
178 
179 	fref = (reg >> CLKMGR_PLLGLOB_VCO_PSRC_OFFSET) &
180 		CLKMGR_PLLGLOB_VCO_PSRC_MASK;
181 	switch (fref) {
182 	case CLKMGR_VCO_PSRC_EOSC1:
183 		fref = cm_get_osc_clk_hz();
184 		break;
185 	case CLKMGR_VCO_PSRC_INTOSC:
186 		fref = cm_get_intosc_clk_hz();
187 		break;
188 	case CLKMGR_VCO_PSRC_F2S:
189 		fref = cm_get_fpga_clk_hz();
190 		break;
191 	}
192 
193 	refdiv = (reg >> CLKMGR_PLLGLOB_REFCLKDIV_OFFSET) &
194 		  CLKMGR_PLLGLOB_REFCLKDIV_MASK;
195 
196 	reg = readl(&clock_manager_base->main_pll.fdbck);
197 	mdiv = (reg >> CLKMGR_FDBCK_MDIV_OFFSET) & CLKMGR_FDBCK_MDIV_MASK;
198 
199 	vco = fref / refdiv;
200 	vco = vco * (CLKMGR_MDIV_CONST + mdiv);
201 	return vco;
202 }
203 
cm_get_per_vco_clk_hz(void)204 static unsigned long cm_get_per_vco_clk_hz(void)
205 {
206 	unsigned long fref, refdiv, mdiv, reg, vco;
207 
208 	reg = readl(&clock_manager_base->per_pll.pllglob);
209 
210 	fref = (reg >> CLKMGR_PLLGLOB_VCO_PSRC_OFFSET) &
211 		CLKMGR_PLLGLOB_VCO_PSRC_MASK;
212 	switch (fref) {
213 	case CLKMGR_VCO_PSRC_EOSC1:
214 		fref = cm_get_osc_clk_hz();
215 		break;
216 	case CLKMGR_VCO_PSRC_INTOSC:
217 		fref = cm_get_intosc_clk_hz();
218 		break;
219 	case CLKMGR_VCO_PSRC_F2S:
220 		fref = cm_get_fpga_clk_hz();
221 		break;
222 	}
223 
224 	refdiv = (reg >> CLKMGR_PLLGLOB_REFCLKDIV_OFFSET) &
225 		  CLKMGR_PLLGLOB_REFCLKDIV_MASK;
226 
227 	reg = readl(&clock_manager_base->per_pll.fdbck);
228 	mdiv = (reg >> CLKMGR_FDBCK_MDIV_OFFSET) & CLKMGR_FDBCK_MDIV_MASK;
229 
230 	vco = fref / refdiv;
231 	vco = vco * (CLKMGR_MDIV_CONST + mdiv);
232 	return vco;
233 }
234 
cm_get_mpu_clk_hz(void)235 unsigned long cm_get_mpu_clk_hz(void)
236 {
237 	unsigned long clock = readl(&clock_manager_base->main_pll.mpuclk);
238 
239 	clock = (clock >> CLKMGR_CLKSRC_OFFSET) & CLKMGR_CLKSRC_MASK;
240 
241 	switch (clock) {
242 	case CLKMGR_CLKSRC_MAIN:
243 		clock = cm_get_main_vco_clk_hz();
244 		clock /= (readl(&clock_manager_base->main_pll.pllc0) &
245 			  CLKMGR_PLLC0_DIV_MASK);
246 		break;
247 
248 	case CLKMGR_CLKSRC_PER:
249 		clock = cm_get_per_vco_clk_hz();
250 		clock /= (readl(&clock_manager_base->per_pll.pllc0) &
251 			  CLKMGR_CLKCNT_MSK);
252 		break;
253 
254 	case CLKMGR_CLKSRC_OSC1:
255 		clock = cm_get_osc_clk_hz();
256 		break;
257 
258 	case CLKMGR_CLKSRC_INTOSC:
259 		clock = cm_get_intosc_clk_hz();
260 		break;
261 
262 	case CLKMGR_CLKSRC_FPGA:
263 		clock = cm_get_fpga_clk_hz();
264 		break;
265 	}
266 
267 	clock /= 1 + (readl(&clock_manager_base->main_pll.mpuclk) &
268 		CLKMGR_CLKCNT_MSK);
269 	return clock;
270 }
271 
cm_get_l3_main_clk_hz(void)272 unsigned int cm_get_l3_main_clk_hz(void)
273 {
274 	u32 clock = readl(&clock_manager_base->main_pll.nocclk);
275 
276 	clock = (clock >> CLKMGR_CLKSRC_OFFSET) & CLKMGR_CLKSRC_MASK;
277 
278 	switch (clock) {
279 	case CLKMGR_CLKSRC_MAIN:
280 		clock = cm_get_main_vco_clk_hz();
281 		clock /= (readl(&clock_manager_base->main_pll.pllc1) &
282 			  CLKMGR_PLLC0_DIV_MASK);
283 		break;
284 
285 	case CLKMGR_CLKSRC_PER:
286 		clock = cm_get_per_vco_clk_hz();
287 		clock /= (readl(&clock_manager_base->per_pll.pllc1) &
288 			  CLKMGR_CLKCNT_MSK);
289 		break;
290 
291 	case CLKMGR_CLKSRC_OSC1:
292 		clock = cm_get_osc_clk_hz();
293 		break;
294 
295 	case CLKMGR_CLKSRC_INTOSC:
296 		clock = cm_get_intosc_clk_hz();
297 		break;
298 
299 	case CLKMGR_CLKSRC_FPGA:
300 		clock = cm_get_fpga_clk_hz();
301 		break;
302 	}
303 
304 	clock /= 1 + (readl(&clock_manager_base->main_pll.nocclk) &
305 		CLKMGR_CLKCNT_MSK);
306 	return clock;
307 }
308 
cm_get_mmc_controller_clk_hz(void)309 unsigned int cm_get_mmc_controller_clk_hz(void)
310 {
311 	u32 clock = readl(&clock_manager_base->per_pll.cntr6clk);
312 
313 	clock = (clock >> CLKMGR_CLKSRC_OFFSET) & CLKMGR_CLKSRC_MASK;
314 
315 	switch (clock) {
316 	case CLKMGR_CLKSRC_MAIN:
317 		clock = cm_get_l3_main_clk_hz();
318 		clock /= 1 + (readl(&clock_manager_base->main_pll.cntr6clk) &
319 			CLKMGR_CLKCNT_MSK);
320 		break;
321 
322 	case CLKMGR_CLKSRC_PER:
323 		clock = cm_get_l3_main_clk_hz();
324 		clock /= 1 + (readl(&clock_manager_base->per_pll.cntr6clk) &
325 			CLKMGR_CLKCNT_MSK);
326 		break;
327 
328 	case CLKMGR_CLKSRC_OSC1:
329 		clock = cm_get_osc_clk_hz();
330 		break;
331 
332 	case CLKMGR_CLKSRC_INTOSC:
333 		clock = cm_get_intosc_clk_hz();
334 		break;
335 
336 	case CLKMGR_CLKSRC_FPGA:
337 		clock = cm_get_fpga_clk_hz();
338 		break;
339 	}
340 	return clock / 4;
341 }
342 
cm_get_l4_sp_clk_hz(void)343 unsigned int cm_get_l4_sp_clk_hz(void)
344 {
345 	u32 clock = cm_get_l3_main_clk_hz();
346 
347 	clock /= (1 << ((readl(&clock_manager_base->main_pll.nocdiv) >>
348 		  CLKMGR_NOCDIV_L4SPCLK_OFFSET) & CLKMGR_CLKCNT_MSK));
349 	return clock;
350 }
351 
cm_get_qspi_controller_clk_hz(void)352 unsigned int cm_get_qspi_controller_clk_hz(void)
353 {
354 	return readl(&sysmgr_regs->boot_scratch_cold0);
355 }
356 
cm_get_spi_controller_clk_hz(void)357 unsigned int cm_get_spi_controller_clk_hz(void)
358 {
359 	u32 clock = cm_get_l3_main_clk_hz();
360 
361 	clock /= (1 << ((readl(&clock_manager_base->main_pll.nocdiv) >>
362 		  CLKMGR_NOCDIV_L4MAIN_OFFSET) & CLKMGR_CLKCNT_MSK));
363 	return clock;
364 }
365 
cm_get_l4_sys_free_clk_hz(void)366 unsigned int cm_get_l4_sys_free_clk_hz(void)
367 {
368 	return cm_get_l3_main_clk_hz() / 4;
369 }
370 
cm_print_clock_quick_summary(void)371 void cm_print_clock_quick_summary(void)
372 {
373 	printf("MPU         %d kHz\n", (u32)(cm_get_mpu_clk_hz() / 1000));
374 	printf("L3 main     %d kHz\n", cm_get_l3_main_clk_hz() / 1000);
375 	printf("Main VCO    %d kHz\n", (u32)(cm_get_main_vco_clk_hz() / 1000));
376 	printf("Per VCO     %d kHz\n", (u32)(cm_get_per_vco_clk_hz() / 1000));
377 	printf("EOSC1       %d kHz\n", cm_get_osc_clk_hz() / 1000);
378 	printf("HPS MMC     %d kHz\n", cm_get_mmc_controller_clk_hz() / 1000);
379 	printf("UART        %d kHz\n", cm_get_l4_sp_clk_hz() / 1000);
380 }
381