1 /*
2  * Copyright (c) 2015-2019, Renesas Electronics Corporation. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include <stdint.h>
8 
9 #include <common/debug.h>
10 #include <lib/mmio.h>
11 
12 #include "qos_init.h"
13 #include "qos_common.h"
14 #include "qos_reg.h"
15 #include "rcar_def.h"
16 #if RCAR_LSI == RCAR_AUTO
17 #include "H3/qos_init_h3_v10.h"
18 #include "H3/qos_init_h3_v11.h"
19 #include "H3/qos_init_h3_v20.h"
20 #include "H3/qos_init_h3_v30.h"
21 #include "M3/qos_init_m3_v10.h"
22 #include "M3/qos_init_m3_v11.h"
23 #include "M3/qos_init_m3_v30.h"
24 #include "M3N/qos_init_m3n_v10.h"
25 #include "V3M/qos_init_v3m.h"
26 #endif
27 #if RCAR_LSI == RCAR_H3		/* H3 */
28 #include "H3/qos_init_h3_v10.h"
29 #include "H3/qos_init_h3_v11.h"
30 #include "H3/qos_init_h3_v20.h"
31 #include "H3/qos_init_h3_v30.h"
32 #endif
33 #if RCAR_LSI == RCAR_H3N	/* H3 */
34 #include "H3/qos_init_h3n_v30.h"
35 #endif
36 #if RCAR_LSI == RCAR_M3		/* M3 */
37 #include "M3/qos_init_m3_v10.h"
38 #include "M3/qos_init_m3_v11.h"
39 #include "M3/qos_init_m3_v30.h"
40 #endif
41 #if RCAR_LSI == RCAR_M3N	/* M3N */
42 #include "M3N/qos_init_m3n_v10.h"
43 #endif
44 #if RCAR_LSI == RCAR_V3M	/* V3M */
45 #include "V3M/qos_init_v3m.h"
46 #endif
47 #if RCAR_LSI == RCAR_E3		/* E3 */
48 #include "E3/qos_init_e3_v10.h"
49 #endif
50 #if RCAR_LSI == RCAR_D3		/* D3 */
51 #include "D3/qos_init_d3.h"
52 #endif
53 
54 #if (RCAR_LSI != RCAR_E3) && (RCAR_LSI != RCAR_D3) && (RCAR_LSI != RCAR_V3M)
55 
56 #define DRAM_CH_CNT			0x04
57 uint32_t qos_init_ddr_ch;
58 uint8_t qos_init_ddr_phyvalid;
59 #endif
60 
61 #define PRR_PRODUCT_ERR(reg)				\
62 	do {						\
63 		ERROR("LSI Product ID(PRR=0x%x) QoS "	\
64 		"initialize not supported.\n", reg);	\
65 		panic();				\
66 	} while (0)
67 
68 #define PRR_CUT_ERR(reg)				\
69 	do {						\
70 		ERROR("LSI Cut ID(PRR=0x%x) QoS "	\
71 		"initialize not supported.\n", reg);	\
72 		panic();				\
73 	} while (0)
74 
rcar_qos_init(void)75 void rcar_qos_init(void)
76 {
77 	uint32_t reg;
78 #if (RCAR_LSI != RCAR_E3) && (RCAR_LSI != RCAR_D3) && (RCAR_LSI != RCAR_V3M)
79 	uint32_t i;
80 
81 	qos_init_ddr_ch = 0;
82 	qos_init_ddr_phyvalid = get_boardcnf_phyvalid();
83 	for (i = 0; i < DRAM_CH_CNT; i++) {
84 		if ((qos_init_ddr_phyvalid & (1 << i))) {
85 			qos_init_ddr_ch++;
86 		}
87 	}
88 #endif
89 
90 	reg = mmio_read_32(PRR);
91 #if (RCAR_LSI == RCAR_AUTO) || RCAR_LSI_CUT_COMPAT
92 	switch (reg & PRR_PRODUCT_MASK) {
93 	case PRR_PRODUCT_H3:
94 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_H3)
95 		switch (reg & PRR_CUT_MASK) {
96 		case PRR_PRODUCT_10:
97 			qos_init_h3_v10();
98 			break;
99 		case PRR_PRODUCT_11:
100 			qos_init_h3_v11();
101 			break;
102 		case PRR_PRODUCT_20:
103 			qos_init_h3_v20();
104 			break;
105 		case PRR_PRODUCT_30:
106 		default:
107 			qos_init_h3_v30();
108 			break;
109 		}
110 #elif (RCAR_LSI == RCAR_H3N)
111 		switch (reg & PRR_CUT_MASK) {
112 		case PRR_PRODUCT_30:
113 		default:
114 			qos_init_h3n_v30();
115 			break;
116 		}
117 #else
118 		PRR_PRODUCT_ERR(reg);
119 #endif
120 		break;
121 	case PRR_PRODUCT_M3:
122 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3)
123 		switch (reg & PRR_CUT_MASK) {
124 		case PRR_PRODUCT_10:
125 			qos_init_m3_v10();
126 			break;
127 		case PRR_PRODUCT_21: /* M3 Cut 13 */
128 			qos_init_m3_v11();
129 			break;
130 		case PRR_PRODUCT_30: /* M3 Cut 30 */
131 		default:
132 			qos_init_m3_v30();
133 			break;
134 		}
135 #else
136 		PRR_PRODUCT_ERR(reg);
137 #endif
138 		break;
139 	case PRR_PRODUCT_M3N:
140 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3N)
141 		switch (reg & PRR_CUT_MASK) {
142 		case PRR_PRODUCT_10:
143 		default:
144 			qos_init_m3n_v10();
145 			break;
146 		}
147 #else
148 		PRR_PRODUCT_ERR(reg);
149 #endif
150 		break;
151 	case PRR_PRODUCT_V3M:
152 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_V3M)
153 		switch (reg & PRR_CUT_MASK) {
154 		case PRR_PRODUCT_10:
155 		case PRR_PRODUCT_20:
156 		default:
157 			qos_init_v3m();
158 			break;
159 		}
160 #else
161 		PRR_PRODUCT_ERR(reg);
162 #endif
163 		break;
164 	case PRR_PRODUCT_E3:
165 #if (RCAR_LSI == RCAR_E3)
166 		switch (reg & PRR_CUT_MASK) {
167 		case PRR_PRODUCT_10:
168 		default:
169 			qos_init_e3_v10();
170 			break;
171 		}
172 #else
173 		PRR_PRODUCT_ERR(reg);
174 #endif
175 		break;
176 	case PRR_PRODUCT_D3:
177 #if (RCAR_LSI == RCAR_D3)
178 		switch (reg & PRR_CUT_MASK) {
179 		case PRR_PRODUCT_10:
180 		default:
181 			qos_init_d3();
182 			break;
183 		}
184 #else
185 		PRR_PRODUCT_ERR(reg);
186 #endif
187 		break;
188 	default:
189 		PRR_PRODUCT_ERR(reg);
190 		break;
191 	}
192 #else
193 #if RCAR_LSI == RCAR_H3		/* H3 */
194 #if RCAR_LSI_CUT == RCAR_CUT_10
195 	/* H3 Cut 10 */
196 	if ((PRR_PRODUCT_H3 | PRR_PRODUCT_10)
197 	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
198 		PRR_PRODUCT_ERR(reg);
199 	}
200 	qos_init_h3_v10();
201 #elif RCAR_LSI_CUT == RCAR_CUT_11
202 	/* H3 Cut 11 */
203 	if ((PRR_PRODUCT_H3 | PRR_PRODUCT_11)
204 	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
205 		PRR_PRODUCT_ERR(reg);
206 	}
207 	qos_init_h3_v11();
208 #elif RCAR_LSI_CUT == RCAR_CUT_20
209 	/* H3 Cut 20 */
210 	if ((PRR_PRODUCT_H3 | PRR_PRODUCT_20)
211 	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
212 		PRR_PRODUCT_ERR(reg);
213 	}
214 	qos_init_h3_v20();
215 #else
216 	/* H3 Cut 30 or later */
217 	if ((PRR_PRODUCT_H3)
218 	    != (reg & (PRR_PRODUCT_MASK))) {
219 		PRR_PRODUCT_ERR(reg);
220 	}
221 	qos_init_h3_v30();
222 #endif
223 #elif RCAR_LSI == RCAR_H3N	/* H3 */
224 	/* H3N Cut 30 or later */
225 	if ((PRR_PRODUCT_H3)
226 	    != (reg & (PRR_PRODUCT_MASK))) {
227 		PRR_PRODUCT_ERR(reg);
228 	}
229 	qos_init_h3n_v30();
230 #elif RCAR_LSI == RCAR_M3	/* M3 */
231 #if RCAR_LSI_CUT == RCAR_CUT_10
232 	/* M3 Cut 10 */
233 	if ((PRR_PRODUCT_M3 | PRR_PRODUCT_10)
234 	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
235 		PRR_PRODUCT_ERR(reg);
236 	}
237 	qos_init_m3_v10();
238 #elif RCAR_LSI_CUT == RCAR_CUT_11
239 	/* M3 Cut 11 */
240 	if ((PRR_PRODUCT_M3 | PRR_PRODUCT_20)
241 	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
242 		PRR_PRODUCT_ERR(reg);
243 	}
244 	qos_init_m3_v11();
245 #elif RCAR_LSI_CUT == RCAR_CUT_13
246 	/* M3 Cut 13 */
247 	if ((PRR_PRODUCT_M3 | PRR_PRODUCT_21)
248 	    != (reg & (PRR_PRODUCT_MASK | PRR_CUT_MASK))) {
249 		PRR_PRODUCT_ERR(reg);
250 	}
251 	qos_init_m3_v11();
252 #else
253 	/* M3 Cut 30 or later */
254 	if ((PRR_PRODUCT_M3)
255 	    != (reg & (PRR_PRODUCT_MASK))) {
256 		PRR_PRODUCT_ERR(reg);
257 	}
258 	qos_init_m3_v30();
259 #endif
260 #elif RCAR_LSI == RCAR_M3N	/* M3N */
261 	/* M3N Cut 10 or later */
262 	if ((PRR_PRODUCT_M3N)
263 	    != (reg & (PRR_PRODUCT_MASK))) {
264 		PRR_PRODUCT_ERR(reg);
265 	}
266 	qos_init_m3n_v10();
267 #elif RCAR_LSI == RCAR_V3M	/* V3M */
268 	/* V3M Cut 10 or later */
269 	if ((PRR_PRODUCT_V3M)
270 			!= (reg & (PRR_PRODUCT_MASK))) {
271 		PRR_PRODUCT_ERR(reg);
272 	}
273 	qos_init_v3m();
274 #elif RCAR_LSI == RCAR_D3	/* D3 */
275 	/* D3 Cut 10 or later */
276 	if ((PRR_PRODUCT_D3)
277 	    != (reg & (PRR_PRODUCT_MASK))) {
278 		PRR_PRODUCT_ERR(reg);
279 	}
280 	qos_init_d3();
281 #elif RCAR_LSI == RCAR_E3	/* E3 */
282 	/* E3 Cut 10 or later */
283 	if ((PRR_PRODUCT_E3)
284 	    != (reg & (PRR_PRODUCT_MASK))) {
285 		PRR_PRODUCT_ERR(reg);
286 	}
287 	qos_init_e3_v10();
288 #else
289 #error "Don't have QoS initialize routine(Unknown chip)."
290 #endif
291 #endif
292 }
293 
294 #if (RCAR_LSI != RCAR_E3) && (RCAR_LSI != RCAR_D3) && (RCAR_LSI != RCAR_V3M)
get_refperiod(void)295 uint32_t get_refperiod(void)
296 {
297 	uint32_t refperiod = QOSWT_WTSET0_CYCLE;
298 
299 #if (RCAR_LSI == RCAR_AUTO) || RCAR_LSI_CUT_COMPAT
300 	uint32_t reg;
301 
302 	reg = mmio_read_32(PRR);
303 	switch (reg & PRR_PRODUCT_MASK) {
304 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_H3)
305 	case PRR_PRODUCT_H3:
306 		switch (reg & PRR_CUT_MASK) {
307 		case PRR_PRODUCT_10:
308 		case PRR_PRODUCT_11:
309 			break;
310 		case PRR_PRODUCT_20:
311 		case PRR_PRODUCT_30:
312 		default:
313 			refperiod = REFPERIOD_CYCLE;
314 			break;
315 		}
316 		break;
317 #elif (RCAR_LSI == RCAR_H3N)
318 	case PRR_PRODUCT_H3:
319 		switch (reg & PRR_CUT_MASK) {
320 		case PRR_PRODUCT_30:
321 		default:
322 			refperiod = REFPERIOD_CYCLE;
323 			break;
324 		}
325 		break;
326 #endif
327 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3)
328 	case PRR_PRODUCT_M3:
329 		switch (reg & PRR_CUT_MASK) {
330 		case PRR_PRODUCT_10:
331 			break;
332 		case PRR_PRODUCT_20: /* M3 Cut 11 */
333 		case PRR_PRODUCT_21: /* M3 Cut 13 */
334 		case PRR_PRODUCT_30: /* M3 Cut 30 */
335 		default:
336 			refperiod = REFPERIOD_CYCLE;
337 			break;
338 		}
339 		break;
340 #endif
341 #if (RCAR_LSI == RCAR_AUTO) || (RCAR_LSI == RCAR_M3N)
342 	case PRR_PRODUCT_M3N:
343 		refperiod = REFPERIOD_CYCLE;
344 		break;
345 #endif
346 	default:
347 		break;
348 	}
349 #elif RCAR_LSI == RCAR_H3
350 #if RCAR_LSI_CUT == RCAR_CUT_10
351 	/* H3 Cut 10 */
352 #elif RCAR_LSI_CUT == RCAR_CUT_11
353 	/* H3 Cut 11 */
354 #else
355 	/* H3 Cut 20 */
356 	/* H3 Cut 30 or later */
357 	refperiod = REFPERIOD_CYCLE;
358 #endif
359 #elif RCAR_LSI == RCAR_H3N
360 	/* H3N Cut 30 or later */
361 	refperiod = REFPERIOD_CYCLE;
362 #elif RCAR_LSI == RCAR_M3
363 #if RCAR_LSI_CUT == RCAR_CUT_10
364 	/* M3 Cut 10 */
365 #else
366 	/* M3 Cut 11 */
367 	/* M3 Cut 13 */
368 	/* M3 Cut 30 or later */
369 	refperiod = REFPERIOD_CYCLE;
370 #endif
371 #elif RCAR_LSI == RCAR_M3N	/* for M3N */
372 	refperiod = REFPERIOD_CYCLE;
373 #endif
374 
375 	return refperiod;
376 }
377 #endif
378 
rcar_qos_dbsc_setting(struct rcar_gen3_dbsc_qos_settings * qos,unsigned int qos_size,bool dbsc_wren)379 void rcar_qos_dbsc_setting(struct rcar_gen3_dbsc_qos_settings *qos,
380 			   unsigned int qos_size, bool dbsc_wren)
381 {
382 	int i;
383 
384 	/* Register write enable */
385 	if (dbsc_wren)
386 		io_write_32(DBSC_DBSYSCNT0, 0x00001234U);
387 
388 	for (i = 0; i < qos_size; i++)
389 		io_write_32(qos[i].reg, qos[i].val);
390 
391 	/* Register write protect */
392 	if (dbsc_wren)
393 		io_write_32(DBSC_DBSYSCNT0, 0x00000000U);
394 }
395