xref: /rk3399_ARM-atf/plat/intel/soc/stratix10/soc/s10_clock_manager.c (revision 70b0f2789e93f253bec5cbd2986d0de023c1bdf4)
1 /*
2  * Copyright (c) 2019, Intel Corporation. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include <arch.h>
8 #include <arch_helpers.h>
9 #include <assert.h>
10 #include <drivers/delay_timer.h>
11 #include <lib/mmio.h>
12 #include <platform_def.h>
13 #include <platform_private.h>
14 
15 #include "s10_clock_manager.h"
16 #include "s10_handoff.h"
17 
18 
19 void wait_pll_lock(void)
20 {
21 	uint32_t data;
22 
23 	do {
24 		data = mmio_read_32(ALT_CLKMGR + ALT_CLKMGR_STAT);
25 	} while ((ALT_CLKMGR_STAT_MAINPLLLOCKED(data) == 0) ||
26 			(ALT_CLKMGR_STAT_PERPLLLOCKED(data) == 0));
27 }
28 
29 void wait_fsm(void)
30 {
31 	uint32_t data;
32 
33 	do {
34 		data = mmio_read_32(ALT_CLKMGR + ALT_CLKMGR_STAT);
35 	} while (ALT_CLKMGR_STAT_BUSY(data) == ALT_CLKMGR_STAT_BUSY_E_BUSY);
36 }
37 
38 void config_clkmgr_handoff(handoff *hoff_ptr)
39 {
40 	uint32_t m_div, refclk_div, mscnt, hscnt;
41 
42 	/* Bypass all mainpllgrp's clocks */
43 	mmio_write_32(ALT_CLKMGR_MAINPLL +
44 			ALT_CLKMGR_MAINPLL_BYPASS,
45 			0x7);
46 	wait_fsm();
47 	/* Bypass all perpllgrp's clocks */
48 	mmio_write_32(ALT_CLKMGR_PERPLL +
49 			ALT_CLKMGR_PERPLL_BYPASS,
50 			0x7f);
51 	wait_fsm();
52 
53 	/* Setup main PLL dividers */
54 	m_div = ALT_CLKMGR_MAINPLL_FDBCK_MDIV(hoff_ptr->main_pll_fdbck);
55 	refclk_div = ALT_CLKMGR_MAINPLL_PLLGLOB_REFCLKDIV(
56 			hoff_ptr->main_pll_pllglob);
57 	mscnt = 200 / ((6 + m_div) / refclk_div);
58 	hscnt = (m_div + 6) * mscnt / refclk_div - 9;
59 
60 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_PLLGLOB,
61 			hoff_ptr->main_pll_pllglob);
62 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_FDBCK,
63 			hoff_ptr->main_pll_fdbck);
64 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_VCOCALIB,
65 			ALT_CLKMGR_MAINPLL_VCOCALIB_HSCNT_SET(hscnt) |
66 			ALT_CLKMGR_MAINPLL_VCOCALIB_MSCNT_SET(mscnt));
67 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_PLLC0,
68 			hoff_ptr->main_pll_pllc0);
69 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_PLLC1,
70 			hoff_ptr->main_pll_pllc1);
71 
72 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_NOCDIV,
73 			hoff_ptr->main_pll_nocdiv);
74 
75 	/* Setup peripheral PLL dividers */
76 	m_div = ALT_CLKMGR_PERPLL_FDBCK_MDIV(hoff_ptr->per_pll_fdbck);
77 	refclk_div = ALT_CLKMGR_PERPLL_PLLGLOB_REFCLKDIV(
78 			hoff_ptr->per_pll_pllglob);
79 	mscnt = 200 / ((6 + m_div) / refclk_div);
80 	hscnt = (m_div + 6) * mscnt / refclk_div - 9;
81 
82 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_PLLGLOB,
83 			hoff_ptr->per_pll_pllglob);
84 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_FDBCK,
85 			hoff_ptr->per_pll_fdbck);
86 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_VCOCALIB,
87 			ALT_CLKMGR_PERPLL_VCOCALIB_HSCNT_SET(hscnt) |
88 			ALT_CLKMGR_PERPLL_VCOCALIB_MSCNT_SET(mscnt));
89 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_PLLC0,
90 			hoff_ptr->per_pll_pllc0);
91 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_PLLC1,
92 			hoff_ptr->per_pll_pllc1);
93 
94 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_GPIODIV,
95 			ALT_CLKMGR_PERPLL_GPIODIV_GPIODBCLK_SET(
96 			hoff_ptr->per_pll_gpiodiv));
97 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_EMACCTL,
98 			hoff_ptr->per_pll_emacctl);
99 
100 
101 	/* Take both PLL out of reset and power up */
102 	mmio_setbits_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_PLLGLOB,
103 			ALT_CLKMGR_MAINPLL_PLLGLOB_PD_SET_MSK |
104 			ALT_CLKMGR_MAINPLL_PLLGLOB_RST_SET_MSK);
105 	mmio_setbits_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_PLLGLOB,
106 			ALT_CLKMGR_PERPLL_PLLGLOB_PD_SET_MSK |
107 			ALT_CLKMGR_PERPLL_PLLGLOB_RST_SET_MSK);
108 
109 	wait_pll_lock();
110 
111 	/* Dividers for C2 to C9 only init after PLLs are lock. */
112 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_MPUCLK, 0xff);
113 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_NOCCLK, 0xff);
114 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR2CLK, 0xff);
115 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR3CLK, 0xff);
116 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR4CLK, 0xff);
117 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR5CLK, 0xff);
118 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR6CLK, 0xff);
119 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR7CLK, 0xff);
120 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR8CLK, 0xff);
121 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR9CLK, 0xff);
122 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR2CLK, 0xff);
123 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR3CLK, 0xff);
124 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR4CLK, 0xff);
125 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR5CLK, 0xff);
126 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR6CLK, 0xff);
127 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR7CLK, 0xff);
128 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR8CLK, 0xff);
129 
130 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_MPUCLK,
131 			hoff_ptr->main_pll_mpuclk);
132 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_NOCCLK,
133 			hoff_ptr->main_pll_nocclk);
134 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR2CLK,
135 			hoff_ptr->main_pll_cntr2clk);
136 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR3CLK,
137 			hoff_ptr->main_pll_cntr3clk);
138 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR4CLK,
139 			hoff_ptr->main_pll_cntr4clk);
140 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR5CLK,
141 			hoff_ptr->main_pll_cntr5clk);
142 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR6CLK,
143 			hoff_ptr->main_pll_cntr6clk);
144 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR7CLK,
145 			hoff_ptr->main_pll_cntr7clk);
146 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR8CLK,
147 			hoff_ptr->main_pll_cntr8clk);
148 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_CNTR9CLK,
149 			hoff_ptr->main_pll_cntr9clk);
150 
151 	/* Peripheral PLL Clock Source and Counters/Divider */
152 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR2CLK,
153 			hoff_ptr->per_pll_cntr2clk);
154 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR3CLK,
155 			hoff_ptr->per_pll_cntr3clk);
156 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR4CLK,
157 			hoff_ptr->per_pll_cntr4clk);
158 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR5CLK,
159 			hoff_ptr->per_pll_cntr5clk);
160 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR6CLK,
161 			hoff_ptr->per_pll_cntr6clk);
162 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR7CLK,
163 			hoff_ptr->per_pll_cntr7clk);
164 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR8CLK,
165 			hoff_ptr->per_pll_cntr8clk);
166 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_CNTR9CLK,
167 			hoff_ptr->per_pll_cntr9clk);
168 
169 	/* Take all PLLs out of bypass */
170 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_BYPASS, 0);
171 	wait_fsm();
172 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_BYPASS, 0);
173 	wait_fsm();
174 
175 	/* Set safe mode/ out of boot mode */
176 	mmio_clrbits_32(ALT_CLKMGR + ALT_CLKMGR_CTRL,
177 		ALT_CLKMGR_CTRL_BOOTMODE_SET_MSK);
178 	wait_fsm();
179 
180 	/* 10 Enable mainpllgrp's software-managed clock */
181 	mmio_write_32(ALT_CLKMGR_MAINPLL + ALT_CLKMGR_MAINPLL_EN,
182 			ALT_CLKMGR_MAINPLL_EN_RESET);
183 	mmio_write_32(ALT_CLKMGR_PERPLL + ALT_CLKMGR_PERPLL_EN,
184 			ALT_CLKMGR_PERPLL_EN_RESET);
185 
186 	/* Clear loss lock  interrupt status register that */
187 	/* might be set during configuration */
188 	mmio_write_32(ALT_CLKMGR + ALT_CLKMGR_INTRCLR,
189 			ALT_CLKMGR_INTRCLR_MAINLOCKLOST_SET_MSK |
190 			ALT_CLKMGR_INTRCLR_PERLOCKLOST_SET_MSK);
191 }
192 
193