xref: /freebsd/sys/arm/mv/mv_common.c (revision 1e4896b176ff664dc9c2fce5426bf2fdf8017a7d)
1 /*-
2  * SPDX-License-Identifier: BSD-3-Clause
3  *
4  * Copyright (C) 2008-2011 MARVELL INTERNATIONAL LTD.
5  * All rights reserved.
6  *
7  * Developed by Semihalf.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  * 2. Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in the
16  *    documentation and/or other materials provided with the distribution.
17  * 3. Neither the name of MARVELL nor the names of contributors
18  *    may be used to endorse or promote products derived from this software
19  *    without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY AUTHOR AND CONTRIBUTORS ``AS IS'' AND
22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED.  IN NO EVENT SHALL AUTHOR OR CONTRIBUTORS BE LIABLE
25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  */
33 
34 #include <sys/cdefs.h>
35 __FBSDID("$FreeBSD$");
36 
37 #include <sys/param.h>
38 #include <sys/systm.h>
39 #include <sys/bus.h>
40 #include <sys/kernel.h>
41 #include <sys/malloc.h>
42 #include <sys/kdb.h>
43 #include <sys/reboot.h>
44 
45 #include <dev/fdt/fdt_common.h>
46 #include <dev/ofw/openfirm.h>
47 #include <dev/ofw/ofw_bus_subr.h>
48 
49 #include <machine/bus.h>
50 #include <machine/fdt.h>
51 #include <machine/vmparam.h>
52 #include <machine/intr.h>
53 
54 #include <arm/mv/mvreg.h>
55 #include <arm/mv/mvvar.h>
56 #include <arm/mv/mvwin.h>
57 
58 MALLOC_DEFINE(M_IDMA, "idma", "idma dma test memory");
59 
60 #define IDMA_DEBUG
61 #undef IDMA_DEBUG
62 
63 #define MAX_CPU_WIN	5
64 
65 #ifdef DEBUG
66 #define debugf(fmt, args...) do { printf("%s(): ", __func__);	\
67     printf(fmt,##args); } while (0)
68 #else
69 #define debugf(fmt, args...)
70 #endif
71 
72 #ifdef DEBUG
73 #define MV_DUMP_WIN	1
74 #else
75 #define MV_DUMP_WIN	0
76 #endif
77 
78 struct soc_node_spec;
79 
80 static enum soc_family soc_family;
81 
82 static int mv_win_cesa_attr(int wng_sel);
83 static int mv_win_cesa_attr_armv5(int eng_sel);
84 static int mv_win_cesa_attr_armada38x(int eng_sel);
85 static int mv_win_cesa_attr_armadaxp(int eng_sel);
86 
87 uint32_t read_cpu_ctrl_armv5(uint32_t reg);
88 uint32_t read_cpu_ctrl_armv7(uint32_t reg);
89 
90 void write_cpu_ctrl_armv5(uint32_t reg, uint32_t val);
91 void write_cpu_ctrl_armv7(uint32_t reg, uint32_t val);
92 
93 static int win_eth_can_remap(int i);
94 
95 static int decode_win_cesa_valid(void);
96 static int decode_win_cpu_valid(void);
97 static int decode_win_usb_valid(void);
98 static int decode_win_usb3_valid(void);
99 static int decode_win_eth_valid(void);
100 static int decode_win_pcie_valid(void);
101 static int decode_win_sata_valid(void);
102 static int decode_win_sdhci_valid(void);
103 
104 static int decode_win_idma_valid(void);
105 static int decode_win_xor_valid(void);
106 
107 static void decode_win_cpu_setup(void);
108 static int decode_win_sdram_fixup(void);
109 static void decode_win_cesa_setup(u_long);
110 static void decode_win_a38x_cesa_setup(u_long);
111 static void decode_win_usb_setup(u_long);
112 static void decode_win_usb3_setup(u_long);
113 static void decode_win_eth_setup(u_long);
114 static void decode_win_neta_setup(u_long);
115 static void decode_win_sata_setup(u_long);
116 static void decode_win_ahci_setup(u_long);
117 static void decode_win_sdhci_setup(u_long);
118 
119 static void decode_win_idma_setup(u_long);
120 static void decode_win_xor_setup(u_long);
121 
122 static void decode_win_cesa_dump(u_long);
123 static void decode_win_a38x_cesa_dump(u_long);
124 static void decode_win_usb_dump(u_long);
125 static void decode_win_usb3_dump(u_long);
126 static void decode_win_eth_dump(u_long base);
127 static void decode_win_neta_dump(u_long base);
128 static void decode_win_idma_dump(u_long base);
129 static void decode_win_xor_dump(u_long base);
130 static void decode_win_ahci_dump(u_long base);
131 static void decode_win_sdhci_dump(u_long);
132 static void decode_win_pcie_dump(u_long);
133 
134 static uint32_t win_cpu_cr_read(int);
135 static uint32_t win_cpu_armv5_cr_read(int);
136 static uint32_t win_cpu_armv7_cr_read(int);
137 static uint32_t win_cpu_br_read(int);
138 static uint32_t win_cpu_armv5_br_read(int);
139 static uint32_t win_cpu_armv7_br_read(int);
140 static uint32_t win_cpu_remap_l_read(int);
141 static uint32_t win_cpu_armv5_remap_l_read(int);
142 static uint32_t win_cpu_armv7_remap_l_read(int);
143 static uint32_t win_cpu_remap_h_read(int);
144 static uint32_t win_cpu_armv5_remap_h_read(int);
145 static uint32_t win_cpu_armv7_remap_h_read(int);
146 
147 static void win_cpu_cr_write(int, uint32_t);
148 static void win_cpu_armv5_cr_write(int, uint32_t);
149 static void win_cpu_armv7_cr_write(int, uint32_t);
150 static void win_cpu_br_write(int, uint32_t);
151 static void win_cpu_armv5_br_write(int, uint32_t);
152 static void win_cpu_armv7_br_write(int, uint32_t);
153 static void win_cpu_remap_l_write(int, uint32_t);
154 static void win_cpu_armv5_remap_l_write(int, uint32_t);
155 static void win_cpu_armv7_remap_l_write(int, uint32_t);
156 static void win_cpu_remap_h_write(int, uint32_t);
157 static void win_cpu_armv5_remap_h_write(int, uint32_t);
158 static void win_cpu_armv7_remap_h_write(int, uint32_t);
159 
160 static uint32_t ddr_br_read(int);
161 static uint32_t ddr_sz_read(int);
162 static uint32_t ddr_armv5_br_read(int);
163 static uint32_t ddr_armv5_sz_read(int);
164 static uint32_t ddr_armv7_br_read(int);
165 static uint32_t ddr_armv7_sz_read(int);
166 static void ddr_br_write(int, uint32_t);
167 static void ddr_sz_write(int, uint32_t);
168 static void ddr_armv5_br_write(int, uint32_t);
169 static void ddr_armv5_sz_write(int, uint32_t);
170 static void ddr_armv7_br_write(int, uint32_t);
171 static void ddr_armv7_sz_write(int, uint32_t);
172 
173 static int fdt_get_ranges(const char *, void *, int, int *, int *);
174 int gic_decode_fdt(phandle_t iparent, pcell_t *intr, int *interrupt,
175     int *trig, int *pol);
176 
177 static int win_cpu_from_dt(void);
178 static int fdt_win_setup(void);
179 
180 static int fdt_win_process_child(phandle_t, struct soc_node_spec *, const char*);
181 
182 static void soc_identify(uint32_t, uint32_t);
183 
184 static uint32_t dev_mask = 0;
185 static int cpu_wins_no = 0;
186 static int eth_port = 0;
187 static int usb_port = 0;
188 static boolean_t platform_io_coherent = false;
189 
190 static struct decode_win cpu_win_tbl[MAX_CPU_WIN];
191 
192 const struct decode_win *cpu_wins = cpu_win_tbl;
193 
194 typedef void (*decode_win_setup_t)(u_long);
195 typedef void (*dump_win_t)(u_long);
196 typedef int (*valid_t)(void);
197 
198 /*
199  * The power status of device feature is only supported on
200  * Kirkwood and Discovery SoCs.
201  */
202 #if defined(SOC_MV_KIRKWOOD) || defined(SOC_MV_DISCOVERY)
203 #define	SOC_MV_POWER_STAT_SUPPORTED		1
204 #else
205 #define	SOC_MV_POWER_STAT_SUPPORTED		0
206 #endif
207 
208 struct soc_node_spec {
209 	const char		*compat;
210 	decode_win_setup_t	decode_handler;
211 	dump_win_t		dump_handler;
212 	valid_t			valid_handler;
213 };
214 
215 static struct soc_node_spec soc_nodes[] = {
216 	{ "mrvl,ge", &decode_win_eth_setup, &decode_win_eth_dump, &decode_win_eth_valid},
217 	{ "marvell,armada-370-neta", &decode_win_neta_setup,
218 	    &decode_win_neta_dump, NULL },
219 	{ "mrvl,usb-ehci", &decode_win_usb_setup, &decode_win_usb_dump, &decode_win_usb_valid},
220 	{ "marvell,orion-ehci", &decode_win_usb_setup, &decode_win_usb_dump, &decode_win_usb_valid },
221 	{ "marvell,armada-380-xhci", &decode_win_usb3_setup,
222 	    &decode_win_usb3_dump, &decode_win_usb3_valid },
223 	{ "marvell,armada-380-ahci", &decode_win_ahci_setup,
224 	    &decode_win_ahci_dump, NULL },
225 	{ "marvell,armada-380-sdhci", &decode_win_sdhci_setup,
226 	    &decode_win_sdhci_dump, &decode_win_sdhci_valid},
227 	{ "mrvl,sata", &decode_win_sata_setup, NULL, &decode_win_sata_valid},
228 	{ "mrvl,xor", &decode_win_xor_setup, &decode_win_xor_dump, &decode_win_xor_valid},
229 	{ "mrvl,idma", &decode_win_idma_setup, &decode_win_idma_dump, &decode_win_idma_valid},
230 	{ "mrvl,cesa", &decode_win_cesa_setup, &decode_win_cesa_dump, &decode_win_cesa_valid},
231 	{ "mrvl,pcie", &decode_win_pcie_setup, &decode_win_pcie_dump, &decode_win_pcie_valid},
232 	{ "marvell,armada-38x-crypto", &decode_win_a38x_cesa_setup,
233 	    &decode_win_a38x_cesa_dump, &decode_win_cesa_valid},
234 	{ NULL, NULL, NULL, NULL },
235 };
236 
237 #define	SOC_NODE_PCIE_ENTRY_IDX		11
238 
239 typedef uint32_t(*read_cpu_ctrl_t)(uint32_t);
240 typedef void(*write_cpu_ctrl_t)(uint32_t, uint32_t);
241 typedef uint32_t (*win_read_t)(int);
242 typedef void (*win_write_t)(int, uint32_t);
243 typedef int (*win_cesa_attr_t)(int);
244 typedef uint32_t (*get_t)(void);
245 
246 struct decode_win_spec {
247 	read_cpu_ctrl_t  read_cpu_ctrl;
248 	write_cpu_ctrl_t write_cpu_ctrl;
249 	win_read_t	cr_read;
250 	win_read_t	br_read;
251 	win_read_t	remap_l_read;
252 	win_read_t	remap_h_read;
253 	win_write_t	cr_write;
254 	win_write_t	br_write;
255 	win_write_t	remap_l_write;
256 	win_write_t	remap_h_write;
257 	uint32_t	mv_win_cpu_max;
258 	win_cesa_attr_t win_cesa_attr;
259 	int 		win_cesa_target;
260 	win_read_t	ddr_br_read;
261 	win_read_t	ddr_sz_read;
262 	win_write_t	ddr_br_write;
263 	win_write_t	ddr_sz_write;
264 #if __ARM_ARCH >= 6
265 	get_t		get_tclk;
266 	get_t		get_cpu_freq;
267 #endif
268 };
269 
270 struct decode_win_spec *soc_decode_win_spec;
271 
272 static struct decode_win_spec decode_win_specs[] =
273 {
274 	{
275 		&read_cpu_ctrl_armv7,
276 		&write_cpu_ctrl_armv7,
277 		&win_cpu_armv7_cr_read,
278 		&win_cpu_armv7_br_read,
279 		&win_cpu_armv7_remap_l_read,
280 		&win_cpu_armv7_remap_h_read,
281 		&win_cpu_armv7_cr_write,
282 		&win_cpu_armv7_br_write,
283 		&win_cpu_armv7_remap_l_write,
284 		&win_cpu_armv7_remap_h_write,
285 		MV_WIN_CPU_MAX_ARMV7,
286 		&mv_win_cesa_attr_armada38x,
287 		MV_WIN_CESA_TARGET_ARMADA38X,
288 		&ddr_armv7_br_read,
289 		&ddr_armv7_sz_read,
290 		&ddr_armv7_br_write,
291 		&ddr_armv7_sz_write,
292 #if __ARM_ARCH >= 6
293 		&get_tclk_armada38x,
294 		&get_cpu_freq_armada38x,
295 #endif
296 	},
297 	{
298 		&read_cpu_ctrl_armv7,
299 		&write_cpu_ctrl_armv7,
300 		&win_cpu_armv7_cr_read,
301 		&win_cpu_armv7_br_read,
302 		&win_cpu_armv7_remap_l_read,
303 		&win_cpu_armv7_remap_h_read,
304 		&win_cpu_armv7_cr_write,
305 		&win_cpu_armv7_br_write,
306 		&win_cpu_armv7_remap_l_write,
307 		&win_cpu_armv7_remap_h_write,
308 		MV_WIN_CPU_MAX_ARMV7,
309 		&mv_win_cesa_attr_armadaxp,
310 		MV_WIN_CESA_TARGET_ARMADAXP,
311 		&ddr_armv7_br_read,
312 		&ddr_armv7_sz_read,
313 		&ddr_armv7_br_write,
314 		&ddr_armv7_sz_write,
315 #if __ARM_ARCH >= 6
316 		&get_tclk_armadaxp,
317 		&get_cpu_freq_armadaxp,
318 #endif
319 	},
320 	{
321 		&read_cpu_ctrl_armv5,
322 		&write_cpu_ctrl_armv5,
323 		&win_cpu_armv5_cr_read,
324 		&win_cpu_armv5_br_read,
325 		&win_cpu_armv5_remap_l_read,
326 		&win_cpu_armv5_remap_h_read,
327 		&win_cpu_armv5_cr_write,
328 		&win_cpu_armv5_br_write,
329 		&win_cpu_armv5_remap_l_write,
330 		&win_cpu_armv5_remap_h_write,
331 		MV_WIN_CPU_MAX,
332 		&mv_win_cesa_attr_armv5,
333 		MV_WIN_CESA_TARGET,
334 		&ddr_armv5_br_read,
335 		&ddr_armv5_sz_read,
336 		&ddr_armv5_br_write,
337 		&ddr_armv5_sz_write,
338 #if __ARM_ARCH >= 6
339 		NULL,
340 		NULL,
341 #endif
342 	},
343 };
344 
345 struct fdt_pm_mask_entry {
346 	char		*compat;
347 	uint32_t	mask;
348 };
349 
350 static struct fdt_pm_mask_entry fdt_pm_mask_table[] = {
351 	{ "mrvl,ge",		CPU_PM_CTRL_GE(0) },
352 	{ "mrvl,ge",		CPU_PM_CTRL_GE(1) },
353 	{ "mrvl,usb-ehci",	CPU_PM_CTRL_USB(0) },
354 	{ "mrvl,usb-ehci",	CPU_PM_CTRL_USB(1) },
355 	{ "mrvl,usb-ehci",	CPU_PM_CTRL_USB(2) },
356 	{ "mrvl,xor",		CPU_PM_CTRL_XOR },
357 	{ "mrvl,sata",		CPU_PM_CTRL_SATA },
358 	{ NULL, 0 }
359 };
360 
361 static __inline int
362 pm_is_disabled(uint32_t mask)
363 {
364 #if SOC_MV_POWER_STAT_SUPPORTED
365 	return (soc_power_ctrl_get(mask) == mask ? 0 : 1);
366 #else
367 	return (0);
368 #endif
369 }
370 
371 /*
372  * Disable device using power management register.
373  * 1 - Device Power On
374  * 0 - Device Power Off
375  * Mask can be set in loader.
376  * EXAMPLE:
377  * loader> set hw.pm-disable-mask=0x2
378  *
379  * Common mask:
380  * |-------------------------------|
381  * | Device | Kirkwood | Discovery |
382  * |-------------------------------|
383  * | USB0   | 0x00008  | 0x020000  |
384  * |-------------------------------|
385  * | USB1   |     -    | 0x040000  |
386  * |-------------------------------|
387  * | USB2   |     -    | 0x080000  |
388  * |-------------------------------|
389  * | GE0    | 0x00001  | 0x000002  |
390  * |-------------------------------|
391  * | GE1    |     -    | 0x000004  |
392  * |-------------------------------|
393  * | IDMA   |     -    | 0x100000  |
394  * |-------------------------------|
395  * | XOR    | 0x10000  | 0x200000  |
396  * |-------------------------------|
397  * | CESA   | 0x20000  | 0x400000  |
398  * |-------------------------------|
399  * | SATA   | 0x04000  | 0x004000  |
400  * --------------------------------|
401  * This feature can be used only on Kirkwood and Discovery
402  * machines.
403  */
404 
405 static int mv_win_cesa_attr(int eng_sel)
406 {
407 
408 	if (soc_decode_win_spec->win_cesa_attr != NULL)
409 		return (soc_decode_win_spec->win_cesa_attr(eng_sel));
410 
411 	return (-1);
412 }
413 
414 static int mv_win_cesa_attr_armv5(int eng_sel)
415 {
416 
417 	return MV_WIN_CESA_ATTR(eng_sel);
418 }
419 
420 static int mv_win_cesa_attr_armada38x(int eng_sel)
421 {
422 
423 	return MV_WIN_CESA_ATTR_ARMADA38X(eng_sel);
424 }
425 
426 static int mv_win_cesa_attr_armadaxp(int eng_sel)
427 {
428 
429 	return MV_WIN_CESA_ATTR_ARMADAXP(eng_sel);
430 }
431 
432 enum soc_family
433 mv_check_soc_family()
434 {
435 	uint32_t dev, rev;
436 
437 	soc_id(&dev, &rev);
438 	switch (dev) {
439 	case MV_DEV_MV78230:
440 	case MV_DEV_MV78260:
441 	case MV_DEV_MV78460:
442 		soc_decode_win_spec = &decode_win_specs[MV_SOC_ARMADA_XP];
443 		soc_family = MV_SOC_ARMADA_XP;
444 		break;
445 	case MV_DEV_88F6828:
446 	case MV_DEV_88F6820:
447 	case MV_DEV_88F6810:
448 		soc_decode_win_spec = &decode_win_specs[MV_SOC_ARMADA_38X];
449 		soc_family = MV_SOC_ARMADA_38X;
450 		break;
451 	case MV_DEV_88F5181:
452 	case MV_DEV_88F5182:
453 	case MV_DEV_88F5281:
454 	case MV_DEV_88F6281:
455 	case MV_DEV_88RC8180:
456 	case MV_DEV_88RC9480:
457 	case MV_DEV_88RC9580:
458 	case MV_DEV_88F6781:
459 	case MV_DEV_88F6282:
460 	case MV_DEV_MV78100_Z0:
461 	case MV_DEV_MV78100:
462 	case MV_DEV_MV78160:
463 		soc_decode_win_spec = &decode_win_specs[MV_SOC_ARMV5];
464 		soc_family = MV_SOC_ARMV5;
465 		break;
466 	default:
467 		soc_family = MV_SOC_UNSUPPORTED;
468 		return (MV_SOC_UNSUPPORTED);
469 	}
470 
471 	soc_identify(dev, rev);
472 
473 	return (soc_family);
474 }
475 
476 static __inline void
477 pm_disable_device(int mask)
478 {
479 #ifdef DIAGNOSTIC
480 	uint32_t reg;
481 
482 	reg = soc_power_ctrl_get(CPU_PM_CTRL_ALL);
483 	printf("Power Management Register: 0%x\n", reg);
484 
485 	reg &= ~mask;
486 	soc_power_ctrl_set(reg);
487 	printf("Device %x is disabled\n", mask);
488 
489 	reg = soc_power_ctrl_get(CPU_PM_CTRL_ALL);
490 	printf("Power Management Register: 0%x\n", reg);
491 #endif
492 }
493 
494 int
495 mv_fdt_is_type(phandle_t node, const char *typestr)
496 {
497 #define FDT_TYPE_LEN	64
498 	char type[FDT_TYPE_LEN];
499 
500 	if (OF_getproplen(node, "device_type") <= 0)
501 		return (0);
502 
503 	if (OF_getprop(node, "device_type", type, FDT_TYPE_LEN) < 0)
504 		return (0);
505 
506 	if (strncasecmp(type, typestr, FDT_TYPE_LEN) == 0)
507 		/* This fits. */
508 		return (1);
509 
510 	return (0);
511 #undef FDT_TYPE_LEN
512 }
513 
514 int
515 mv_fdt_pm(phandle_t node)
516 {
517 	uint32_t cpu_pm_ctrl;
518 	int i, ena, compat;
519 
520 	ena = 1;
521 	cpu_pm_ctrl = read_cpu_ctrl(CPU_PM_CTRL);
522 	for (i = 0; fdt_pm_mask_table[i].compat != NULL; i++) {
523 		if (dev_mask & (1 << i))
524 			continue;
525 
526 		compat = ofw_bus_node_is_compatible(node,
527 		    fdt_pm_mask_table[i].compat);
528 #if defined(SOC_MV_KIRKWOOD)
529 		if (compat && (cpu_pm_ctrl & fdt_pm_mask_table[i].mask)) {
530 			dev_mask |= (1 << i);
531 			ena = 0;
532 			break;
533 		} else if (compat) {
534 			dev_mask |= (1 << i);
535 			break;
536 		}
537 #else
538 		if (compat && (~cpu_pm_ctrl & fdt_pm_mask_table[i].mask)) {
539 			dev_mask |= (1 << i);
540 			ena = 0;
541 			break;
542 		} else if (compat) {
543 			dev_mask |= (1 << i);
544 			break;
545 		}
546 #endif
547 	}
548 
549 	return (ena);
550 }
551 
552 uint32_t
553 read_cpu_ctrl(uint32_t reg)
554 {
555 
556 	if (soc_decode_win_spec->read_cpu_ctrl != NULL)
557 		return (soc_decode_win_spec->read_cpu_ctrl(reg));
558 	return (-1);
559 }
560 
561 uint32_t
562 read_cpu_ctrl_armv5(uint32_t reg)
563 {
564 
565 	return (bus_space_read_4(fdtbus_bs_tag, MV_CPU_CONTROL_BASE, reg));
566 }
567 
568 uint32_t
569 read_cpu_ctrl_armv7(uint32_t reg)
570 {
571 
572 	return (bus_space_read_4(fdtbus_bs_tag, MV_CPU_CONTROL_BASE_ARMV7, reg));
573 }
574 
575 void
576 write_cpu_ctrl(uint32_t reg, uint32_t val)
577 {
578 
579 	if (soc_decode_win_spec->write_cpu_ctrl != NULL)
580 		soc_decode_win_spec->write_cpu_ctrl(reg, val);
581 }
582 
583 void
584 write_cpu_ctrl_armv5(uint32_t reg, uint32_t val)
585 {
586 
587 	bus_space_write_4(fdtbus_bs_tag, MV_CPU_CONTROL_BASE, reg, val);
588 }
589 
590 void
591 write_cpu_ctrl_armv7(uint32_t reg, uint32_t val)
592 {
593 
594 	bus_space_write_4(fdtbus_bs_tag, MV_CPU_CONTROL_BASE_ARMV7, reg, val);
595 }
596 
597 uint32_t
598 read_cpu_mp_clocks(uint32_t reg)
599 {
600 
601 	return (bus_space_read_4(fdtbus_bs_tag, MV_MP_CLOCKS_BASE, reg));
602 }
603 
604 void
605 write_cpu_mp_clocks(uint32_t reg, uint32_t val)
606 {
607 
608 	bus_space_write_4(fdtbus_bs_tag, MV_MP_CLOCKS_BASE, reg, val);
609 }
610 
611 uint32_t
612 read_cpu_misc(uint32_t reg)
613 {
614 
615 	return (bus_space_read_4(fdtbus_bs_tag, MV_MISC_BASE, reg));
616 }
617 
618 void
619 write_cpu_misc(uint32_t reg, uint32_t val)
620 {
621 
622 	bus_space_write_4(fdtbus_bs_tag, MV_MISC_BASE, reg, val);
623 }
624 
625 uint32_t
626 cpu_extra_feat(void)
627 {
628 	uint32_t dev, rev;
629 	uint32_t ef = 0;
630 
631 	soc_id(&dev, &rev);
632 
633 	switch (dev) {
634 	case MV_DEV_88F6281:
635 	case MV_DEV_88F6282:
636 	case MV_DEV_88RC8180:
637 	case MV_DEV_MV78100_Z0:
638 	case MV_DEV_MV78100:
639 		__asm __volatile("mrc p15, 1, %0, c15, c1, 0" : "=r" (ef));
640 		break;
641 	case MV_DEV_88F5182:
642 	case MV_DEV_88F5281:
643 		__asm __volatile("mrc p15, 0, %0, c14, c0, 0" : "=r" (ef));
644 		break;
645 	default:
646 		if (bootverbose)
647 			printf("This ARM Core does not support any extra features\n");
648 	}
649 
650 	return (ef);
651 }
652 
653 /*
654  * Get the power status of device. This feature is only supported on
655  * Kirkwood and Discovery SoCs.
656  */
657 uint32_t
658 soc_power_ctrl_get(uint32_t mask)
659 {
660 
661 #if SOC_MV_POWER_STAT_SUPPORTED
662 	if (mask != CPU_PM_CTRL_NONE)
663 		mask &= read_cpu_ctrl(CPU_PM_CTRL);
664 
665 	return (mask);
666 #else
667 	return (mask);
668 #endif
669 }
670 
671 /*
672  * Set the power status of device. This feature is only supported on
673  * Kirkwood and Discovery SoCs.
674  */
675 void
676 soc_power_ctrl_set(uint32_t mask)
677 {
678 
679 #if !defined(SOC_MV_ORION)
680 	if (mask != CPU_PM_CTRL_NONE)
681 		write_cpu_ctrl(CPU_PM_CTRL, mask);
682 #endif
683 }
684 
685 void
686 soc_id(uint32_t *dev, uint32_t *rev)
687 {
688 	uint64_t mv_pcie_base = MV_PCIE_BASE;
689 	phandle_t node;
690 
691 	/*
692 	 * Notice: system identifiers are available in the registers range of
693 	 * PCIE controller, so using this function is only allowed (and
694 	 * possible) after the internal registers range has been mapped in via
695 	 * devmap_bootstrap().
696 	 */
697 	*dev = 0;
698 	*rev = 0;
699 	if ((node = OF_finddevice("/")) == -1)
700 		return;
701 	if (ofw_bus_node_is_compatible(node, "marvell,armada380"))
702 		mv_pcie_base = MV_PCIE_BASE_ARMADA38X;
703 
704 	*dev = bus_space_read_4(fdtbus_bs_tag, mv_pcie_base, 0) >> 16;
705 	*rev = bus_space_read_4(fdtbus_bs_tag, mv_pcie_base, 8) & 0xff;
706 }
707 
708 static void
709 soc_identify(uint32_t d, uint32_t r)
710 {
711 	uint32_t size, mode, freq;
712 	const char *dev;
713 	const char *rev;
714 
715 	printf("SOC: ");
716 	if (bootverbose)
717 		printf("(0x%4x:0x%02x) ", d, r);
718 
719 	rev = "";
720 	switch (d) {
721 	case MV_DEV_88F5181:
722 		dev = "Marvell 88F5181";
723 		if (r == 3)
724 			rev = "B1";
725 		break;
726 	case MV_DEV_88F5182:
727 		dev = "Marvell 88F5182";
728 		if (r == 2)
729 			rev = "A2";
730 		break;
731 	case MV_DEV_88F5281:
732 		dev = "Marvell 88F5281";
733 		if (r == 4)
734 			rev = "D0";
735 		else if (r == 5)
736 			rev = "D1";
737 		else if (r == 6)
738 			rev = "D2";
739 		break;
740 	case MV_DEV_88F6281:
741 		dev = "Marvell 88F6281";
742 		if (r == 0)
743 			rev = "Z0";
744 		else if (r == 2)
745 			rev = "A0";
746 		else if (r == 3)
747 			rev = "A1";
748 		break;
749 	case MV_DEV_88RC8180:
750 		dev = "Marvell 88RC8180";
751 		break;
752 	case MV_DEV_88RC9480:
753 		dev = "Marvell 88RC9480";
754 		break;
755 	case MV_DEV_88RC9580:
756 		dev = "Marvell 88RC9580";
757 		break;
758 	case MV_DEV_88F6781:
759 		dev = "Marvell 88F6781";
760 		if (r == 2)
761 			rev = "Y0";
762 		break;
763 	case MV_DEV_88F6282:
764 		dev = "Marvell 88F6282";
765 		if (r == 0)
766 			rev = "A0";
767 		else if (r == 1)
768 			rev = "A1";
769 		break;
770 	case MV_DEV_88F6828:
771 		dev = "Marvell 88F6828";
772 		break;
773 	case MV_DEV_88F6820:
774 		dev = "Marvell 88F6820";
775 		break;
776 	case MV_DEV_88F6810:
777 		dev = "Marvell 88F6810";
778 		break;
779 	case MV_DEV_MV78100_Z0:
780 		dev = "Marvell MV78100 Z0";
781 		break;
782 	case MV_DEV_MV78100:
783 		dev = "Marvell MV78100";
784 		break;
785 	case MV_DEV_MV78160:
786 		dev = "Marvell MV78160";
787 		break;
788 	case MV_DEV_MV78260:
789 		dev = "Marvell MV78260";
790 		break;
791 	case MV_DEV_MV78460:
792 		dev = "Marvell MV78460";
793 		break;
794 	default:
795 		dev = "UNKNOWN";
796 		break;
797 	}
798 
799 	printf("%s", dev);
800 	if (*rev != '\0')
801 		printf(" rev %s", rev);
802 	printf(", TClock %dMHz", get_tclk() / 1000 / 1000);
803 	freq = get_cpu_freq();
804 	if (freq != 0)
805 		printf(", Frequency %dMHz", freq / 1000 / 1000);
806 	printf("\n");
807 
808 	mode = read_cpu_ctrl(CPU_CONFIG);
809 	printf("  Instruction cache prefetch %s, data cache prefetch %s\n",
810 	    (mode & CPU_CONFIG_IC_PREF) ? "enabled" : "disabled",
811 	    (mode & CPU_CONFIG_DC_PREF) ? "enabled" : "disabled");
812 
813 	switch (d) {
814 	case MV_DEV_88F6281:
815 	case MV_DEV_88F6282:
816 		mode = read_cpu_ctrl(CPU_L2_CONFIG) & CPU_L2_CONFIG_MODE;
817 		printf("  256KB 4-way set-associative %s unified L2 cache\n",
818 		    mode ? "write-through" : "write-back");
819 		break;
820 	case MV_DEV_MV78100:
821 		mode = read_cpu_ctrl(CPU_CONTROL);
822 		size = mode & CPU_CONTROL_L2_SIZE;
823 		mode = mode & CPU_CONTROL_L2_MODE;
824 		printf("  %s set-associative %s unified L2 cache\n",
825 		    size ? "256KB 4-way" : "512KB 8-way",
826 		    mode ? "write-through" : "write-back");
827 		break;
828 	default:
829 		break;
830 	}
831 }
832 
833 #ifdef KDB
834 static void
835 mv_enter_debugger(void *dummy)
836 {
837 
838 	if (boothowto & RB_KDB)
839 		kdb_enter(KDB_WHY_BOOTFLAGS, "Boot flags requested debugger");
840 }
841 SYSINIT(mv_enter_debugger, SI_SUB_CPU, SI_ORDER_ANY, mv_enter_debugger, NULL);
842 #endif
843 
844 int
845 soc_decode_win(void)
846 {
847 	uint32_t dev, rev;
848 	int mask, err;
849 
850 	mask = 0;
851 	TUNABLE_INT_FETCH("hw.pm-disable-mask", &mask);
852 
853 	if (mask != 0)
854 		pm_disable_device(mask);
855 
856 	/* Retrieve data about physical addresses from device tree. */
857 	if ((err = win_cpu_from_dt()) != 0)
858 		return (err);
859 
860 	/* Retrieve our ID: some windows facilities vary between SoC models */
861 	soc_id(&dev, &rev);
862 
863 	if (soc_family == MV_SOC_ARMADA_XP)
864 		if ((err = decode_win_sdram_fixup()) != 0)
865 			return(err);
866 
867 	decode_win_cpu_setup();
868 	if (MV_DUMP_WIN)
869 		soc_dump_decode_win();
870 
871 	eth_port = 0;
872 	usb_port = 0;
873 	if ((err = fdt_win_setup()) != 0)
874 		return (err);
875 
876 	return (0);
877 }
878 
879 /**************************************************************************
880  * Decode windows registers accessors
881  **************************************************************************/
882 WIN_REG_IDX_RD(win_cpu_armv5, cr, MV_WIN_CPU_CTRL_ARMV5, MV_MBUS_BRIDGE_BASE)
883 WIN_REG_IDX_RD(win_cpu_armv5, br, MV_WIN_CPU_BASE_ARMV5, MV_MBUS_BRIDGE_BASE)
884 WIN_REG_IDX_RD(win_cpu_armv5, remap_l, MV_WIN_CPU_REMAP_LO_ARMV5, MV_MBUS_BRIDGE_BASE)
885 WIN_REG_IDX_RD(win_cpu_armv5, remap_h, MV_WIN_CPU_REMAP_HI_ARMV5, MV_MBUS_BRIDGE_BASE)
886 WIN_REG_IDX_WR(win_cpu_armv5, cr, MV_WIN_CPU_CTRL_ARMV5, MV_MBUS_BRIDGE_BASE)
887 WIN_REG_IDX_WR(win_cpu_armv5, br, MV_WIN_CPU_BASE_ARMV5, MV_MBUS_BRIDGE_BASE)
888 WIN_REG_IDX_WR(win_cpu_armv5, remap_l, MV_WIN_CPU_REMAP_LO_ARMV5, MV_MBUS_BRIDGE_BASE)
889 WIN_REG_IDX_WR(win_cpu_armv5, remap_h, MV_WIN_CPU_REMAP_HI_ARMV5, MV_MBUS_BRIDGE_BASE)
890 
891 WIN_REG_IDX_RD(win_cpu_armv7, cr, MV_WIN_CPU_CTRL_ARMV7, MV_MBUS_BRIDGE_BASE)
892 WIN_REG_IDX_RD(win_cpu_armv7, br, MV_WIN_CPU_BASE_ARMV7, MV_MBUS_BRIDGE_BASE)
893 WIN_REG_IDX_RD(win_cpu_armv7, remap_l, MV_WIN_CPU_REMAP_LO_ARMV7, MV_MBUS_BRIDGE_BASE)
894 WIN_REG_IDX_RD(win_cpu_armv7, remap_h, MV_WIN_CPU_REMAP_HI_ARMV7, MV_MBUS_BRIDGE_BASE)
895 WIN_REG_IDX_WR(win_cpu_armv7, cr, MV_WIN_CPU_CTRL_ARMV7, MV_MBUS_BRIDGE_BASE)
896 WIN_REG_IDX_WR(win_cpu_armv7, br, MV_WIN_CPU_BASE_ARMV7, MV_MBUS_BRIDGE_BASE)
897 WIN_REG_IDX_WR(win_cpu_armv7, remap_l, MV_WIN_CPU_REMAP_LO_ARMV7, MV_MBUS_BRIDGE_BASE)
898 WIN_REG_IDX_WR(win_cpu_armv7, remap_h, MV_WIN_CPU_REMAP_HI_ARMV7, MV_MBUS_BRIDGE_BASE)
899 
900 static uint32_t
901 win_cpu_cr_read(int i)
902 {
903 
904 	if (soc_decode_win_spec->cr_read != NULL)
905 		return (soc_decode_win_spec->cr_read(i));
906 	return (-1);
907 }
908 
909 static uint32_t
910 win_cpu_br_read(int i)
911 {
912 
913 	if (soc_decode_win_spec->br_read != NULL)
914 		return (soc_decode_win_spec->br_read(i));
915 	return (-1);
916 }
917 
918 static uint32_t
919 win_cpu_remap_l_read(int i)
920 {
921 
922 	if (soc_decode_win_spec->remap_l_read != NULL)
923 		return (soc_decode_win_spec->remap_l_read(i));
924 	return (-1);
925 }
926 
927 static uint32_t
928 win_cpu_remap_h_read(int i)
929 {
930 
931 	if (soc_decode_win_spec->remap_h_read != NULL)
932 		return soc_decode_win_spec->remap_h_read(i);
933 	return (-1);
934 }
935 
936 static void
937 win_cpu_cr_write(int i, uint32_t val)
938 {
939 
940 	if (soc_decode_win_spec->cr_write != NULL)
941 		soc_decode_win_spec->cr_write(i, val);
942 }
943 
944 static void
945 win_cpu_br_write(int i, uint32_t val)
946 {
947 
948 	if (soc_decode_win_spec->br_write != NULL)
949 		soc_decode_win_spec->br_write(i, val);
950 }
951 
952 static void
953 win_cpu_remap_l_write(int i, uint32_t val)
954 {
955 
956 	if (soc_decode_win_spec->remap_l_write != NULL)
957 		soc_decode_win_spec->remap_l_write(i, val);
958 }
959 
960 static void
961 win_cpu_remap_h_write(int i, uint32_t val)
962 {
963 
964 	if (soc_decode_win_spec->remap_h_write != NULL)
965 		soc_decode_win_spec->remap_h_write(i, val);
966 }
967 
968 WIN_REG_BASE_IDX_RD(win_cesa, cr, MV_WIN_CESA_CTRL)
969 WIN_REG_BASE_IDX_RD(win_cesa, br, MV_WIN_CESA_BASE)
970 WIN_REG_BASE_IDX_WR(win_cesa, cr, MV_WIN_CESA_CTRL)
971 WIN_REG_BASE_IDX_WR(win_cesa, br, MV_WIN_CESA_BASE)
972 
973 WIN_REG_BASE_IDX_RD(win_usb, cr, MV_WIN_USB_CTRL)
974 WIN_REG_BASE_IDX_RD(win_usb, br, MV_WIN_USB_BASE)
975 WIN_REG_BASE_IDX_WR(win_usb, cr, MV_WIN_USB_CTRL)
976 WIN_REG_BASE_IDX_WR(win_usb, br, MV_WIN_USB_BASE)
977 
978 WIN_REG_BASE_IDX_RD(win_usb3, cr, MV_WIN_USB3_CTRL)
979 WIN_REG_BASE_IDX_RD(win_usb3, br, MV_WIN_USB3_BASE)
980 WIN_REG_BASE_IDX_WR(win_usb3, cr, MV_WIN_USB3_CTRL)
981 WIN_REG_BASE_IDX_WR(win_usb3, br, MV_WIN_USB3_BASE)
982 
983 WIN_REG_BASE_IDX_RD(win_eth, br, MV_WIN_ETH_BASE)
984 WIN_REG_BASE_IDX_RD(win_eth, sz, MV_WIN_ETH_SIZE)
985 WIN_REG_BASE_IDX_RD(win_eth, har, MV_WIN_ETH_REMAP)
986 WIN_REG_BASE_IDX_WR(win_eth, br, MV_WIN_ETH_BASE)
987 WIN_REG_BASE_IDX_WR(win_eth, sz, MV_WIN_ETH_SIZE)
988 WIN_REG_BASE_IDX_WR(win_eth, har, MV_WIN_ETH_REMAP)
989 
990 WIN_REG_BASE_IDX_RD2(win_xor, br, MV_WIN_XOR_BASE)
991 WIN_REG_BASE_IDX_RD2(win_xor, sz, MV_WIN_XOR_SIZE)
992 WIN_REG_BASE_IDX_RD2(win_xor, har, MV_WIN_XOR_REMAP)
993 WIN_REG_BASE_IDX_RD2(win_xor, ctrl, MV_WIN_XOR_CTRL)
994 WIN_REG_BASE_IDX_WR2(win_xor, br, MV_WIN_XOR_BASE)
995 WIN_REG_BASE_IDX_WR2(win_xor, sz, MV_WIN_XOR_SIZE)
996 WIN_REG_BASE_IDX_WR2(win_xor, har, MV_WIN_XOR_REMAP)
997 WIN_REG_BASE_IDX_WR2(win_xor, ctrl, MV_WIN_XOR_CTRL)
998 
999 WIN_REG_BASE_RD(win_eth, bare, 0x290)
1000 WIN_REG_BASE_RD(win_eth, epap, 0x294)
1001 WIN_REG_BASE_WR(win_eth, bare, 0x290)
1002 WIN_REG_BASE_WR(win_eth, epap, 0x294)
1003 
1004 WIN_REG_BASE_IDX_RD(win_pcie, cr, MV_WIN_PCIE_CTRL);
1005 WIN_REG_BASE_IDX_RD(win_pcie, br, MV_WIN_PCIE_BASE);
1006 WIN_REG_BASE_IDX_RD(win_pcie, remap, MV_WIN_PCIE_REMAP);
1007 WIN_REG_BASE_IDX_WR(win_pcie, cr, MV_WIN_PCIE_CTRL);
1008 WIN_REG_BASE_IDX_WR(win_pcie, br, MV_WIN_PCIE_BASE);
1009 WIN_REG_BASE_IDX_WR(win_pcie, remap, MV_WIN_PCIE_REMAP);
1010 WIN_REG_BASE_IDX_RD(pcie_bar, br, MV_PCIE_BAR_BASE);
1011 WIN_REG_BASE_IDX_RD(pcie_bar, brh, MV_PCIE_BAR_BASE_H);
1012 WIN_REG_BASE_IDX_RD(pcie_bar, cr, MV_PCIE_BAR_CTRL);
1013 WIN_REG_BASE_IDX_WR(pcie_bar, br, MV_PCIE_BAR_BASE);
1014 WIN_REG_BASE_IDX_WR(pcie_bar, brh, MV_PCIE_BAR_BASE_H);
1015 WIN_REG_BASE_IDX_WR(pcie_bar, cr, MV_PCIE_BAR_CTRL);
1016 
1017 WIN_REG_BASE_IDX_RD(win_idma, br, MV_WIN_IDMA_BASE)
1018 WIN_REG_BASE_IDX_RD(win_idma, sz, MV_WIN_IDMA_SIZE)
1019 WIN_REG_BASE_IDX_RD(win_idma, har, MV_WIN_IDMA_REMAP)
1020 WIN_REG_BASE_IDX_RD(win_idma, cap, MV_WIN_IDMA_CAP)
1021 WIN_REG_BASE_IDX_WR(win_idma, br, MV_WIN_IDMA_BASE)
1022 WIN_REG_BASE_IDX_WR(win_idma, sz, MV_WIN_IDMA_SIZE)
1023 WIN_REG_BASE_IDX_WR(win_idma, har, MV_WIN_IDMA_REMAP)
1024 WIN_REG_BASE_IDX_WR(win_idma, cap, MV_WIN_IDMA_CAP)
1025 WIN_REG_BASE_RD(win_idma, bare, 0xa80)
1026 WIN_REG_BASE_WR(win_idma, bare, 0xa80)
1027 
1028 WIN_REG_BASE_IDX_RD(win_sata, cr, MV_WIN_SATA_CTRL);
1029 WIN_REG_BASE_IDX_RD(win_sata, br, MV_WIN_SATA_BASE);
1030 WIN_REG_BASE_IDX_WR(win_sata, cr, MV_WIN_SATA_CTRL);
1031 WIN_REG_BASE_IDX_WR(win_sata, br, MV_WIN_SATA_BASE);
1032 
1033 WIN_REG_BASE_IDX_RD(win_sata_armada38x, sz, MV_WIN_SATA_SIZE_ARMADA38X);
1034 WIN_REG_BASE_IDX_WR(win_sata_armada38x, sz, MV_WIN_SATA_SIZE_ARMADA38X);
1035 WIN_REG_BASE_IDX_RD(win_sata_armada38x, cr, MV_WIN_SATA_CTRL_ARMADA38X);
1036 WIN_REG_BASE_IDX_RD(win_sata_armada38x, br, MV_WIN_SATA_BASE_ARMADA38X);
1037 WIN_REG_BASE_IDX_WR(win_sata_armada38x, cr, MV_WIN_SATA_CTRL_ARMADA38X);
1038 WIN_REG_BASE_IDX_WR(win_sata_armada38x, br, MV_WIN_SATA_BASE_ARMADA38X);
1039 
1040 WIN_REG_BASE_IDX_RD(win_sdhci, cr, MV_WIN_SDHCI_CTRL);
1041 WIN_REG_BASE_IDX_RD(win_sdhci, br, MV_WIN_SDHCI_BASE);
1042 WIN_REG_BASE_IDX_WR(win_sdhci, cr, MV_WIN_SDHCI_CTRL);
1043 WIN_REG_BASE_IDX_WR(win_sdhci, br, MV_WIN_SDHCI_BASE);
1044 
1045 #ifndef SOC_MV_DOVE
1046 WIN_REG_IDX_RD(ddr_armv5, br, MV_WIN_DDR_BASE, MV_DDR_CADR_BASE)
1047 WIN_REG_IDX_RD(ddr_armv5, sz, MV_WIN_DDR_SIZE, MV_DDR_CADR_BASE)
1048 WIN_REG_IDX_WR(ddr_armv5, br, MV_WIN_DDR_BASE, MV_DDR_CADR_BASE)
1049 WIN_REG_IDX_WR(ddr_armv5, sz, MV_WIN_DDR_SIZE, MV_DDR_CADR_BASE)
1050 
1051 WIN_REG_IDX_RD(ddr_armv7, br, MV_WIN_DDR_BASE, MV_DDR_CADR_BASE_ARMV7)
1052 WIN_REG_IDX_RD(ddr_armv7, sz, MV_WIN_DDR_SIZE, MV_DDR_CADR_BASE_ARMV7)
1053 WIN_REG_IDX_WR(ddr_armv7, br, MV_WIN_DDR_BASE, MV_DDR_CADR_BASE_ARMV7)
1054 WIN_REG_IDX_WR(ddr_armv7, sz, MV_WIN_DDR_SIZE, MV_DDR_CADR_BASE_ARMV7)
1055 
1056 static inline uint32_t
1057 ddr_br_read(int i)
1058 {
1059 
1060 	if (soc_decode_win_spec->ddr_br_read != NULL)
1061 		return (soc_decode_win_spec->ddr_br_read(i));
1062 	return (-1);
1063 }
1064 
1065 static inline uint32_t
1066 ddr_sz_read(int i)
1067 {
1068 
1069 	if (soc_decode_win_spec->ddr_sz_read != NULL)
1070 		return (soc_decode_win_spec->ddr_sz_read(i));
1071 	return (-1);
1072 }
1073 
1074 static inline void
1075 ddr_br_write(int i, uint32_t val)
1076 {
1077 
1078 	if (soc_decode_win_spec->ddr_br_write != NULL)
1079 		soc_decode_win_spec->ddr_br_write(i, val);
1080 }
1081 
1082 static inline void
1083 ddr_sz_write(int i, uint32_t val)
1084 {
1085 
1086 	if (soc_decode_win_spec->ddr_sz_write != NULL)
1087 		soc_decode_win_spec->ddr_sz_write(i, val);
1088 }
1089 #else
1090 /*
1091  * On 88F6781 (Dove) SoC DDR Controller is accessed through
1092  * single MBUS <-> AXI bridge. In this case we provide emulated
1093  * ddr_br_read() and ddr_sz_read() functions to keep compatibility
1094  * with common decoding windows setup code.
1095  */
1096 
1097 static inline uint32_t ddr_br_read(int i)
1098 {
1099 	uint32_t mmap;
1100 
1101 	/* Read Memory Address Map Register for CS i */
1102 	mmap = bus_space_read_4(fdtbus_bs_tag, MV_DDR_CADR_BASE + (i * 0x10), 0);
1103 
1104 	/* Return CS i base address */
1105 	return (mmap & 0xFF000000);
1106 }
1107 
1108 static inline uint32_t ddr_sz_read(int i)
1109 {
1110 	uint32_t mmap, size;
1111 
1112 	/* Read Memory Address Map Register for CS i */
1113 	mmap = bus_space_read_4(fdtbus_bs_tag, MV_DDR_CADR_BASE + (i * 0x10), 0);
1114 
1115 	/* Extract size of CS space in 64kB units */
1116 	size = (1 << ((mmap >> 16) & 0x0F));
1117 
1118 	/* Return CS size and enable/disable status */
1119 	return (((size - 1) << 16) | (mmap & 0x01));
1120 }
1121 #endif
1122 
1123 /**************************************************************************
1124  * Decode windows helper routines
1125  **************************************************************************/
1126 void
1127 soc_dump_decode_win(void)
1128 {
1129 	int i;
1130 
1131 	for (i = 0; i < soc_decode_win_spec->mv_win_cpu_max; i++) {
1132 		printf("CPU window#%d: c 0x%08x, b 0x%08x", i,
1133 		    win_cpu_cr_read(i),
1134 		    win_cpu_br_read(i));
1135 
1136 		if (win_cpu_can_remap(i))
1137 			printf(", rl 0x%08x, rh 0x%08x",
1138 			    win_cpu_remap_l_read(i),
1139 			    win_cpu_remap_h_read(i));
1140 
1141 		printf("\n");
1142 	}
1143 	printf("Internal regs base: 0x%08x\n",
1144 	    bus_space_read_4(fdtbus_bs_tag, MV_INTREGS_BASE, 0));
1145 
1146 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
1147 		printf("DDR CS#%d: b 0x%08x, s 0x%08x\n", i,
1148 		    ddr_br_read(i), ddr_sz_read(i));
1149 }
1150 
1151 /**************************************************************************
1152  * CPU windows routines
1153  **************************************************************************/
1154 int
1155 win_cpu_can_remap(int i)
1156 {
1157 	uint32_t dev, rev;
1158 
1159 	soc_id(&dev, &rev);
1160 
1161 	/* Depending on the SoC certain windows have remap capability */
1162 	if ((dev == MV_DEV_88F5182 && i < 2) ||
1163 	    (dev == MV_DEV_88F5281 && i < 4) ||
1164 	    (dev == MV_DEV_88F6281 && i < 4) ||
1165 	    (dev == MV_DEV_88F6282 && i < 4) ||
1166 	    (dev == MV_DEV_88F6828 && i < 20) ||
1167 	    (dev == MV_DEV_88F6820 && i < 20) ||
1168 	    (dev == MV_DEV_88F6810 && i < 20) ||
1169 	    (dev == MV_DEV_88RC8180 && i < 2) ||
1170 	    (dev == MV_DEV_88F6781 && i < 4) ||
1171 	    (dev == MV_DEV_MV78100_Z0 && i < 8) ||
1172 	    ((dev & MV_DEV_FAMILY_MASK) == MV_DEV_DISCOVERY && i < 8))
1173 		return (1);
1174 
1175 	return (0);
1176 }
1177 
1178 /* XXX This should check for overlapping remap fields too.. */
1179 int
1180 decode_win_overlap(int win, int win_no, const struct decode_win *wintab)
1181 {
1182 	const struct decode_win *tab;
1183 	int i;
1184 
1185 	tab = wintab;
1186 
1187 	for (i = 0; i < win_no; i++, tab++) {
1188 		if (i == win)
1189 			/* Skip self */
1190 			continue;
1191 
1192 		if ((tab->base + tab->size - 1) < (wintab + win)->base)
1193 			continue;
1194 
1195 		else if (((wintab + win)->base + (wintab + win)->size - 1) <
1196 		    tab->base)
1197 			continue;
1198 		else
1199 			return (i);
1200 	}
1201 
1202 	return (-1);
1203 }
1204 
1205 static int
1206 decode_win_cpu_valid(void)
1207 {
1208 	int i, j, rv;
1209 	uint32_t b, e, s;
1210 
1211 	if (cpu_wins_no > soc_decode_win_spec->mv_win_cpu_max) {
1212 		printf("CPU windows: too many entries: %d\n", cpu_wins_no);
1213 		return (0);
1214 	}
1215 
1216 	rv = 1;
1217 	for (i = 0; i < cpu_wins_no; i++) {
1218 		if (cpu_wins[i].target == 0) {
1219 			printf("CPU window#%d: DDR target window is not "
1220 			    "supposed to be reprogrammed!\n", i);
1221 			rv = 0;
1222 		}
1223 
1224 		if (cpu_wins[i].remap != ~0 && win_cpu_can_remap(i) != 1) {
1225 			printf("CPU window#%d: not capable of remapping, but "
1226 			    "val 0x%08x defined\n", i, cpu_wins[i].remap);
1227 			rv = 0;
1228 		}
1229 
1230 		s = cpu_wins[i].size;
1231 		b = cpu_wins[i].base;
1232 		e = b + s - 1;
1233 		if (s > (0xFFFFFFFF - b + 1)) {
1234 			/*
1235 			 * XXX this boundary check should account for 64bit
1236 			 * and remapping..
1237 			 */
1238 			printf("CPU window#%d: no space for size 0x%08x at "
1239 			    "0x%08x\n", i, s, b);
1240 			rv = 0;
1241 			continue;
1242 		}
1243 
1244 		if (b != rounddown2(b, s)) {
1245 			printf("CPU window#%d: address 0x%08x is not aligned "
1246 			    "to 0x%08x\n", i, b, s);
1247 			rv = 0;
1248 			continue;
1249 		}
1250 
1251 		j = decode_win_overlap(i, cpu_wins_no, &cpu_wins[0]);
1252 		if (j >= 0) {
1253 			printf("CPU window#%d: (0x%08x - 0x%08x) overlaps "
1254 			    "with #%d (0x%08x - 0x%08x)\n", i, b, e, j,
1255 			    cpu_wins[j].base,
1256 			    cpu_wins[j].base + cpu_wins[j].size - 1);
1257 			rv = 0;
1258 		}
1259 	}
1260 
1261 	return (rv);
1262 }
1263 
1264 int
1265 decode_win_cpu_set(int target, int attr, vm_paddr_t base, uint32_t size,
1266     vm_paddr_t remap)
1267 {
1268 	uint32_t br, cr;
1269 	int win, i;
1270 
1271 	if (remap == ~0) {
1272 		win = soc_decode_win_spec->mv_win_cpu_max - 1;
1273 		i = -1;
1274 	} else {
1275 		win = 0;
1276 		i = 1;
1277 	}
1278 
1279 	while ((win >= 0) && (win < soc_decode_win_spec->mv_win_cpu_max)) {
1280 		cr = win_cpu_cr_read(win);
1281 		if ((cr & MV_WIN_CPU_ENABLE_BIT) == 0)
1282 			break;
1283 		if ((cr & ((0xff << MV_WIN_CPU_ATTR_SHIFT) |
1284 		    (0x1f << MV_WIN_CPU_TARGET_SHIFT))) ==
1285 		    ((attr << MV_WIN_CPU_ATTR_SHIFT) |
1286 		    (target << MV_WIN_CPU_TARGET_SHIFT)))
1287 			break;
1288 		win += i;
1289 	}
1290 	if ((win < 0) || (win >= soc_decode_win_spec->mv_win_cpu_max) ||
1291 	    ((remap != ~0) && (win_cpu_can_remap(win) == 0)))
1292 		return (-1);
1293 
1294 	br = base & 0xffff0000;
1295 	win_cpu_br_write(win, br);
1296 
1297 	if (win_cpu_can_remap(win)) {
1298 		if (remap != ~0) {
1299 			win_cpu_remap_l_write(win, remap & 0xffff0000);
1300 			win_cpu_remap_h_write(win, 0);
1301 		} else {
1302 			/*
1303 			 * Remap function is not used for a given window
1304 			 * (capable of remapping) - set remap field with the
1305 			 * same value as base.
1306 			 */
1307 			win_cpu_remap_l_write(win, base & 0xffff0000);
1308 			win_cpu_remap_h_write(win, 0);
1309 		}
1310 	}
1311 
1312 	cr = ((size - 1) & 0xffff0000) | (attr << MV_WIN_CPU_ATTR_SHIFT) |
1313 	    (target << MV_WIN_CPU_TARGET_SHIFT) | MV_WIN_CPU_ENABLE_BIT;
1314 	win_cpu_cr_write(win, cr);
1315 
1316 	return (0);
1317 }
1318 
1319 static void
1320 decode_win_cpu_setup(void)
1321 {
1322 	int i;
1323 
1324 	/* Disable all CPU windows */
1325 	for (i = 0; i < soc_decode_win_spec->mv_win_cpu_max; i++) {
1326 		win_cpu_cr_write(i, 0);
1327 		win_cpu_br_write(i, 0);
1328 		if (win_cpu_can_remap(i)) {
1329 			win_cpu_remap_l_write(i, 0);
1330 			win_cpu_remap_h_write(i, 0);
1331 		}
1332 	}
1333 
1334 	for (i = 0; i < cpu_wins_no; i++)
1335 		if (cpu_wins[i].target > 0)
1336 			decode_win_cpu_set(cpu_wins[i].target,
1337 			    cpu_wins[i].attr, cpu_wins[i].base,
1338 			    cpu_wins[i].size, cpu_wins[i].remap);
1339 
1340 }
1341 
1342 static int
1343 decode_win_sdram_fixup(void)
1344 {
1345 	struct mem_region mr[FDT_MEM_REGIONS];
1346 	uint8_t window_valid[MV_WIN_DDR_MAX];
1347 	int mr_cnt, err, i, j;
1348 	uint32_t valid_win_num = 0;
1349 
1350 	/* Grab physical memory regions information from device tree. */
1351 	err = fdt_get_mem_regions(mr, &mr_cnt, NULL);
1352 	if (err != 0)
1353 		return (err);
1354 
1355 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
1356 		window_valid[i] = 0;
1357 
1358 	/* Try to match entries from device tree with settings from u-boot */
1359 	for (i = 0; i < mr_cnt; i++) {
1360 		for (j = 0; j < MV_WIN_DDR_MAX; j++) {
1361 			if (ddr_is_active(j) &&
1362 			    (ddr_base(j) == mr[i].mr_start) &&
1363 			    (ddr_size(j) == mr[i].mr_size)) {
1364 				window_valid[j] = 1;
1365 				valid_win_num++;
1366 			}
1367 		}
1368 	}
1369 
1370 	if (mr_cnt != valid_win_num)
1371 		return (EINVAL);
1372 
1373 	/* Destroy windows without corresponding device tree entry */
1374 	for (j = 0; j < MV_WIN_DDR_MAX; j++) {
1375 		if (ddr_is_active(j) && (window_valid[j] != 1)) {
1376 			printf("Disabling SDRAM decoding window: %d\n", j);
1377 			ddr_disable(j);
1378 		}
1379 	}
1380 
1381 	return (0);
1382 }
1383 /*
1384  * Check if we're able to cover all active DDR banks.
1385  */
1386 static int
1387 decode_win_can_cover_ddr(int max)
1388 {
1389 	int i, c;
1390 
1391 	c = 0;
1392 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
1393 		if (ddr_is_active(i))
1394 			c++;
1395 
1396 	if (c > max) {
1397 		printf("Unable to cover all active DDR banks: "
1398 		    "%d, available windows: %d\n", c, max);
1399 		return (0);
1400 	}
1401 
1402 	return (1);
1403 }
1404 
1405 /**************************************************************************
1406  * DDR windows routines
1407  **************************************************************************/
1408 int
1409 ddr_is_active(int i)
1410 {
1411 
1412 	if (ddr_sz_read(i) & 0x1)
1413 		return (1);
1414 
1415 	return (0);
1416 }
1417 
1418 void
1419 ddr_disable(int i)
1420 {
1421 
1422 	ddr_sz_write(i, 0);
1423 	ddr_br_write(i, 0);
1424 }
1425 
1426 uint32_t
1427 ddr_base(int i)
1428 {
1429 
1430 	return (ddr_br_read(i) & 0xff000000);
1431 }
1432 
1433 uint32_t
1434 ddr_size(int i)
1435 {
1436 
1437 	return ((ddr_sz_read(i) | 0x00ffffff) + 1);
1438 }
1439 
1440 uint32_t
1441 ddr_attr(int i)
1442 {
1443 	uint32_t dev, rev, attr;
1444 
1445 	soc_id(&dev, &rev);
1446 	if (dev == MV_DEV_88RC8180)
1447 		return ((ddr_sz_read(i) & 0xf0) >> 4);
1448 	if (dev == MV_DEV_88F6781)
1449 		return (0);
1450 
1451 	attr = (i == 0 ? 0xe :
1452 	    (i == 1 ? 0xd :
1453 	    (i == 2 ? 0xb :
1454 	    (i == 3 ? 0x7 : 0xff))));
1455 	if (platform_io_coherent)
1456 		attr |= 0x10;
1457 
1458 	return (attr);
1459 }
1460 
1461 uint32_t
1462 ddr_target(int i)
1463 {
1464 	uint32_t dev, rev;
1465 
1466 	soc_id(&dev, &rev);
1467 	if (dev == MV_DEV_88RC8180) {
1468 		i = (ddr_sz_read(i) & 0xf0) >> 4;
1469 		return (i == 0xe ? 0xc :
1470 		    (i == 0xd ? 0xd :
1471 		    (i == 0xb ? 0xe :
1472 		    (i == 0x7 ? 0xf : 0xc))));
1473 	}
1474 
1475 	/*
1476 	 * On SOCs other than 88RC8180 Mbus unit ID for
1477 	 * DDR SDRAM controller is always 0x0.
1478 	 */
1479 	return (0);
1480 }
1481 
1482 /**************************************************************************
1483  * CESA windows routines
1484  **************************************************************************/
1485 static int
1486 decode_win_cesa_valid(void)
1487 {
1488 
1489 	return (decode_win_can_cover_ddr(MV_WIN_CESA_MAX));
1490 }
1491 
1492 static void
1493 decode_win_cesa_dump(u_long base)
1494 {
1495 	int i;
1496 
1497 	for (i = 0; i < MV_WIN_CESA_MAX; i++)
1498 		printf("CESA window#%d: c 0x%08x, b 0x%08x\n", i,
1499 		    win_cesa_cr_read(base, i), win_cesa_br_read(base, i));
1500 }
1501 
1502 /*
1503  * Set CESA decode windows.
1504  */
1505 static void
1506 decode_win_cesa_setup(u_long base)
1507 {
1508 	uint32_t br, cr;
1509 	uint64_t size;
1510 	int i, j;
1511 
1512 	for (i = 0; i < MV_WIN_CESA_MAX; i++) {
1513 		win_cesa_cr_write(base, i, 0);
1514 		win_cesa_br_write(base, i, 0);
1515 	}
1516 
1517 	/* Only access to active DRAM banks is required */
1518 	for (i = 0; i < MV_WIN_DDR_MAX; i++) {
1519 		if (ddr_is_active(i)) {
1520 			br = ddr_base(i);
1521 
1522 			size = ddr_size(i);
1523 			/*
1524 			 * Armada 38x SoC's equipped with 4GB DRAM
1525 			 * suffer freeze during CESA operation, if
1526 			 * MBUS window opened at given DRAM CS reaches
1527 			 * end of the address space. Apply a workaround
1528 			 * by setting the window size to the closest possible
1529 			 * value, i.e. divide it by 2.
1530 			 */
1531 			if ((soc_family == MV_SOC_ARMADA_38X) &&
1532 			    (size + ddr_base(i) == 0x100000000ULL))
1533 				size /= 2;
1534 
1535 			cr = (((size - 1) & 0xffff0000) |
1536 			    (ddr_attr(i) << IO_WIN_ATTR_SHIFT) |
1537 			    (ddr_target(i) << IO_WIN_TGT_SHIFT) |
1538 			    IO_WIN_ENA_MASK);
1539 
1540 			/* Set the first free CESA window */
1541 			for (j = 0; j < MV_WIN_CESA_MAX; j++) {
1542 				if (win_cesa_cr_read(base, j) & 0x1)
1543 					continue;
1544 
1545 				win_cesa_br_write(base, j, br);
1546 				win_cesa_cr_write(base, j, cr);
1547 				break;
1548 			}
1549 		}
1550 	}
1551 }
1552 
1553 static void
1554 decode_win_a38x_cesa_setup(u_long base)
1555 {
1556 	decode_win_cesa_setup(base);
1557 	decode_win_cesa_setup(base + MV_WIN_CESA_OFFSET);
1558 }
1559 
1560 static void
1561 decode_win_a38x_cesa_dump(u_long base)
1562 {
1563 	decode_win_cesa_dump(base);
1564 	decode_win_cesa_dump(base + MV_WIN_CESA_OFFSET);
1565 }
1566 
1567 /**************************************************************************
1568  * USB windows routines
1569  **************************************************************************/
1570 static int
1571 decode_win_usb_valid(void)
1572 {
1573 
1574 	return (decode_win_can_cover_ddr(MV_WIN_USB_MAX));
1575 }
1576 
1577 static void
1578 decode_win_usb_dump(u_long base)
1579 {
1580 	int i;
1581 
1582 	if (pm_is_disabled(CPU_PM_CTRL_USB(usb_port - 1)))
1583 		return;
1584 
1585 	for (i = 0; i < MV_WIN_USB_MAX; i++)
1586 		printf("USB window#%d: c 0x%08x, b 0x%08x\n", i,
1587 		    win_usb_cr_read(base, i), win_usb_br_read(base, i));
1588 }
1589 
1590 /*
1591  * Set USB decode windows.
1592  */
1593 static void
1594 decode_win_usb_setup(u_long base)
1595 {
1596 	uint32_t br, cr;
1597 	int i, j;
1598 
1599 	if (pm_is_disabled(CPU_PM_CTRL_USB(usb_port)))
1600 		return;
1601 
1602 	usb_port++;
1603 
1604 	for (i = 0; i < MV_WIN_USB_MAX; i++) {
1605 		win_usb_cr_write(base, i, 0);
1606 		win_usb_br_write(base, i, 0);
1607 	}
1608 
1609 	/* Only access to active DRAM banks is required */
1610 	for (i = 0; i < MV_WIN_DDR_MAX; i++) {
1611 		if (ddr_is_active(i)) {
1612 			br = ddr_base(i);
1613 			/*
1614 			 * XXX for 6281 we should handle Mbus write
1615 			 * burst limit field in the ctrl reg
1616 			 */
1617 			cr = (((ddr_size(i) - 1) & 0xffff0000) |
1618 			    (ddr_attr(i) << 8) |
1619 			    (ddr_target(i) << 4) | 1);
1620 
1621 			/* Set the first free USB window */
1622 			for (j = 0; j < MV_WIN_USB_MAX; j++) {
1623 				if (win_usb_cr_read(base, j) & 0x1)
1624 					continue;
1625 
1626 				win_usb_br_write(base, j, br);
1627 				win_usb_cr_write(base, j, cr);
1628 				break;
1629 			}
1630 		}
1631 	}
1632 }
1633 
1634 /**************************************************************************
1635  * USB3 windows routines
1636  **************************************************************************/
1637 static int
1638 decode_win_usb3_valid(void)
1639 {
1640 
1641 	return (decode_win_can_cover_ddr(MV_WIN_USB3_MAX));
1642 }
1643 
1644 static void
1645 decode_win_usb3_dump(u_long base)
1646 {
1647 	int i;
1648 
1649 	for (i = 0; i < MV_WIN_USB3_MAX; i++)
1650 		printf("USB3.0 window#%d: c 0x%08x, b 0x%08x\n", i,
1651 		    win_usb3_cr_read(base, i), win_usb3_br_read(base, i));
1652 }
1653 
1654 /*
1655  * Set USB3 decode windows
1656  */
1657 static void
1658 decode_win_usb3_setup(u_long base)
1659 {
1660 	uint32_t br, cr;
1661 	int i, j;
1662 
1663 	for (i = 0; i < MV_WIN_USB3_MAX; i++) {
1664 		win_usb3_cr_write(base, i, 0);
1665 		win_usb3_br_write(base, i, 0);
1666 	}
1667 
1668 	/* Only access to active DRAM banks is required */
1669 	for (i = 0; i < MV_WIN_DDR_MAX; i++) {
1670 		if (ddr_is_active(i)) {
1671 			br = ddr_base(i);
1672 			cr = (((ddr_size(i) - 1) &
1673 			    (IO_WIN_SIZE_MASK << IO_WIN_SIZE_SHIFT)) |
1674 			    (ddr_attr(i) << IO_WIN_ATTR_SHIFT) |
1675 			    (ddr_target(i) << IO_WIN_TGT_SHIFT) |
1676 			    IO_WIN_ENA_MASK);
1677 
1678 			/* Set the first free USB3.0 window */
1679 			for (j = 0; j < MV_WIN_USB3_MAX; j++) {
1680 				if (win_usb3_cr_read(base, j) & IO_WIN_ENA_MASK)
1681 					continue;
1682 
1683 				win_usb3_br_write(base, j, br);
1684 				win_usb3_cr_write(base, j, cr);
1685 				break;
1686 			}
1687 		}
1688 	}
1689 }
1690 
1691 /**************************************************************************
1692  * ETH windows routines
1693  **************************************************************************/
1694 
1695 static int
1696 win_eth_can_remap(int i)
1697 {
1698 
1699 	/* ETH encode windows 0-3 have remap capability */
1700 	if (i < 4)
1701 		return (1);
1702 
1703 	return (0);
1704 }
1705 
1706 static int
1707 eth_bare_read(uint32_t base, int i)
1708 {
1709 	uint32_t v;
1710 
1711 	v = win_eth_bare_read(base);
1712 	v &= (1 << i);
1713 
1714 	return (v >> i);
1715 }
1716 
1717 static void
1718 eth_bare_write(uint32_t base, int i, int val)
1719 {
1720 	uint32_t v;
1721 
1722 	v = win_eth_bare_read(base);
1723 	v &= ~(1 << i);
1724 	v |= (val << i);
1725 	win_eth_bare_write(base, v);
1726 }
1727 
1728 static void
1729 eth_epap_write(uint32_t base, int i, int val)
1730 {
1731 	uint32_t v;
1732 
1733 	v = win_eth_epap_read(base);
1734 	v &= ~(0x3 << (i * 2));
1735 	v |= (val << (i * 2));
1736 	win_eth_epap_write(base, v);
1737 }
1738 
1739 static void
1740 decode_win_eth_dump(u_long base)
1741 {
1742 	int i;
1743 
1744 	if (pm_is_disabled(CPU_PM_CTRL_GE(eth_port - 1)))
1745 		return;
1746 
1747 	for (i = 0; i < MV_WIN_ETH_MAX; i++) {
1748 		printf("ETH window#%d: b 0x%08x, s 0x%08x", i,
1749 		    win_eth_br_read(base, i),
1750 		    win_eth_sz_read(base, i));
1751 
1752 		if (win_eth_can_remap(i))
1753 			printf(", ha 0x%08x",
1754 			    win_eth_har_read(base, i));
1755 
1756 		printf("\n");
1757 	}
1758 	printf("ETH windows: bare 0x%08x, epap 0x%08x\n",
1759 	    win_eth_bare_read(base),
1760 	    win_eth_epap_read(base));
1761 }
1762 
1763 #define MV_WIN_ETH_DDR_TRGT(n)	ddr_target(n)
1764 
1765 static void
1766 decode_win_eth_setup(u_long base)
1767 {
1768 	uint32_t br, sz;
1769 	int i, j;
1770 
1771 	if (pm_is_disabled(CPU_PM_CTRL_GE(eth_port)))
1772 		return;
1773 
1774 	eth_port++;
1775 
1776 	/* Disable, clear and revoke protection for all ETH windows */
1777 	for (i = 0; i < MV_WIN_ETH_MAX; i++) {
1778 		eth_bare_write(base, i, 1);
1779 		eth_epap_write(base, i, 0);
1780 		win_eth_br_write(base, i, 0);
1781 		win_eth_sz_write(base, i, 0);
1782 		if (win_eth_can_remap(i))
1783 			win_eth_har_write(base, i, 0);
1784 	}
1785 
1786 	/* Only access to active DRAM banks is required */
1787 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
1788 		if (ddr_is_active(i)) {
1789 			br = ddr_base(i) | (ddr_attr(i) << 8) | MV_WIN_ETH_DDR_TRGT(i);
1790 			sz = ((ddr_size(i) - 1) & 0xffff0000);
1791 
1792 			/* Set the first free ETH window */
1793 			for (j = 0; j < MV_WIN_ETH_MAX; j++) {
1794 				if (eth_bare_read(base, j) == 0)
1795 					continue;
1796 
1797 				win_eth_br_write(base, j, br);
1798 				win_eth_sz_write(base, j, sz);
1799 
1800 				/* XXX remapping ETH windows not supported */
1801 
1802 				/* Set protection RW */
1803 				eth_epap_write(base, j, 0x3);
1804 
1805 				/* Enable window */
1806 				eth_bare_write(base, j, 0);
1807 				break;
1808 			}
1809 		}
1810 }
1811 
1812 static void
1813 decode_win_neta_dump(u_long base)
1814 {
1815 
1816 	decode_win_eth_dump(base + MV_WIN_NETA_OFFSET);
1817 }
1818 
1819 static void
1820 decode_win_neta_setup(u_long base)
1821 {
1822 
1823 	decode_win_eth_setup(base + MV_WIN_NETA_OFFSET);
1824 }
1825 
1826 static int
1827 decode_win_eth_valid(void)
1828 {
1829 
1830 	return (decode_win_can_cover_ddr(MV_WIN_ETH_MAX));
1831 }
1832 
1833 /**************************************************************************
1834  * PCIE windows routines
1835  **************************************************************************/
1836 static void
1837 decode_win_pcie_dump(u_long base)
1838 {
1839 	int i;
1840 
1841 	printf("PCIE windows base 0x%08lx\n", base);
1842 	for (i = 0; i < MV_WIN_PCIE_MAX; i++)
1843 		printf("PCIE window#%d: cr 0x%08x br 0x%08x remap 0x%08x\n",
1844 		    i, win_pcie_cr_read(base, i),
1845 		    win_pcie_br_read(base, i), win_pcie_remap_read(base, i));
1846 
1847 	for (i = 0; i < MV_PCIE_BAR_MAX; i++)
1848 		printf("PCIE bar#%d: cr 0x%08x br 0x%08x brh 0x%08x\n",
1849 		    i, pcie_bar_cr_read(base, i),
1850 		    pcie_bar_br_read(base, i), pcie_bar_brh_read(base, i));
1851 }
1852 
1853 void
1854 decode_win_pcie_setup(u_long base)
1855 {
1856 	uint32_t size = 0, ddrbase = ~0;
1857 	uint32_t cr, br;
1858 	int i, j;
1859 
1860 	for (i = 0; i < MV_PCIE_BAR_MAX; i++) {
1861 		pcie_bar_br_write(base, i,
1862 		    MV_PCIE_BAR_64BIT | MV_PCIE_BAR_PREFETCH_EN);
1863 		if (i < 3)
1864 			pcie_bar_brh_write(base, i, 0);
1865 		if (i > 0)
1866 			pcie_bar_cr_write(base, i, 0);
1867 	}
1868 
1869 	for (i = 0; i < MV_WIN_PCIE_MAX; i++) {
1870 		win_pcie_cr_write(base, i, 0);
1871 		win_pcie_br_write(base, i, 0);
1872 		win_pcie_remap_write(base, i, 0);
1873 	}
1874 
1875 	/* On End-Point only set BAR size to 1MB regardless of DDR size */
1876 	if ((bus_space_read_4(fdtbus_bs_tag, base, MV_PCIE_CONTROL)
1877 	    & MV_PCIE_ROOT_CMPLX) == 0) {
1878 		pcie_bar_cr_write(base, 1, 0xf0000 | 1);
1879 		return;
1880 	}
1881 
1882 	for (i = 0; i < MV_WIN_DDR_MAX; i++) {
1883 		if (ddr_is_active(i)) {
1884 			/* Map DDR to BAR 1 */
1885 			cr = (ddr_size(i) - 1) & 0xffff0000;
1886 			size += ddr_size(i) & 0xffff0000;
1887 			cr |= (ddr_attr(i) << 8) | (ddr_target(i) << 4) | 1;
1888 			br = ddr_base(i);
1889 			if (br < ddrbase)
1890 				ddrbase = br;
1891 
1892 			/* Use the first available PCIE window */
1893 			for (j = 0; j < MV_WIN_PCIE_MAX; j++) {
1894 				if (win_pcie_cr_read(base, j) != 0)
1895 					continue;
1896 
1897 				win_pcie_br_write(base, j, br);
1898 				win_pcie_cr_write(base, j, cr);
1899 				break;
1900 			}
1901 		}
1902 	}
1903 
1904 	/*
1905 	 * Upper 16 bits in BAR register is interpreted as BAR size
1906 	 * (in 64 kB units) plus 64kB, so subtract 0x10000
1907 	 * form value passed to register to get correct value.
1908 	 */
1909 	size -= 0x10000;
1910 	pcie_bar_cr_write(base, 1, size | 1);
1911 	pcie_bar_br_write(base, 1, ddrbase |
1912 	    MV_PCIE_BAR_64BIT | MV_PCIE_BAR_PREFETCH_EN);
1913 	pcie_bar_br_write(base, 0, fdt_immr_pa |
1914 	    MV_PCIE_BAR_64BIT | MV_PCIE_BAR_PREFETCH_EN);
1915 }
1916 
1917 static int
1918 decode_win_pcie_valid(void)
1919 {
1920 
1921 	return (decode_win_can_cover_ddr(MV_WIN_PCIE_MAX));
1922 }
1923 
1924 /**************************************************************************
1925  * IDMA windows routines
1926  **************************************************************************/
1927 #if defined(SOC_MV_ORION) || defined(SOC_MV_DISCOVERY)
1928 static int
1929 idma_bare_read(u_long base, int i)
1930 {
1931 	uint32_t v;
1932 
1933 	v = win_idma_bare_read(base);
1934 	v &= (1 << i);
1935 
1936 	return (v >> i);
1937 }
1938 
1939 static void
1940 idma_bare_write(u_long base, int i, int val)
1941 {
1942 	uint32_t v;
1943 
1944 	v = win_idma_bare_read(base);
1945 	v &= ~(1 << i);
1946 	v |= (val << i);
1947 	win_idma_bare_write(base, v);
1948 }
1949 
1950 /*
1951  * Sets channel protection 'val' for window 'w' on channel 'c'
1952  */
1953 static void
1954 idma_cap_write(u_long base, int c, int w, int val)
1955 {
1956 	uint32_t v;
1957 
1958 	v = win_idma_cap_read(base, c);
1959 	v &= ~(0x3 << (w * 2));
1960 	v |= (val << (w * 2));
1961 	win_idma_cap_write(base, c, v);
1962 }
1963 
1964 /*
1965  * Set protection 'val' on all channels for window 'w'
1966  */
1967 static void
1968 idma_set_prot(u_long base, int w, int val)
1969 {
1970 	int c;
1971 
1972 	for (c = 0; c < MV_IDMA_CHAN_MAX; c++)
1973 		idma_cap_write(base, c, w, val);
1974 }
1975 
1976 static int
1977 win_idma_can_remap(int i)
1978 {
1979 
1980 	/* IDMA decode windows 0-3 have remap capability */
1981 	if (i < 4)
1982 		return (1);
1983 
1984 	return (0);
1985 }
1986 
1987 void
1988 decode_win_idma_setup(u_long base)
1989 {
1990 	uint32_t br, sz;
1991 	int i, j;
1992 
1993 	if (pm_is_disabled(CPU_PM_CTRL_IDMA))
1994 		return;
1995 	/*
1996 	 * Disable and clear all IDMA windows, revoke protection for all channels
1997 	 */
1998 	for (i = 0; i < MV_WIN_IDMA_MAX; i++) {
1999 		idma_bare_write(base, i, 1);
2000 		win_idma_br_write(base, i, 0);
2001 		win_idma_sz_write(base, i, 0);
2002 		if (win_idma_can_remap(i) == 1)
2003 			win_idma_har_write(base, i, 0);
2004 	}
2005 	for (i = 0; i < MV_IDMA_CHAN_MAX; i++)
2006 		win_idma_cap_write(base, i, 0);
2007 
2008 	/*
2009 	 * Set up access to all active DRAM banks
2010 	 */
2011 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
2012 		if (ddr_is_active(i)) {
2013 			br = ddr_base(i) | (ddr_attr(i) << 8) | ddr_target(i);
2014 			sz = ((ddr_size(i) - 1) & 0xffff0000);
2015 
2016 			/* Place DDR entries in non-remapped windows */
2017 			for (j = 0; j < MV_WIN_IDMA_MAX; j++)
2018 				if (win_idma_can_remap(j) != 1 &&
2019 				    idma_bare_read(base, j) == 1) {
2020 					/* Configure window */
2021 					win_idma_br_write(base, j, br);
2022 					win_idma_sz_write(base, j, sz);
2023 
2024 					/* Set protection RW on all channels */
2025 					idma_set_prot(base, j, 0x3);
2026 
2027 					/* Enable window */
2028 					idma_bare_write(base, j, 0);
2029 					break;
2030 				}
2031 		}
2032 
2033 	/*
2034 	 * Remaining targets -- from statically defined table
2035 	 */
2036 	for (i = 0; i < idma_wins_no; i++)
2037 		if (idma_wins[i].target > 0) {
2038 			br = (idma_wins[i].base & 0xffff0000) |
2039 			    (idma_wins[i].attr << 8) | idma_wins[i].target;
2040 			sz = ((idma_wins[i].size - 1) & 0xffff0000);
2041 
2042 			/* Set the first free IDMA window */
2043 			for (j = 0; j < MV_WIN_IDMA_MAX; j++) {
2044 				if (idma_bare_read(base, j) == 0)
2045 					continue;
2046 
2047 				/* Configure window */
2048 				win_idma_br_write(base, j, br);
2049 				win_idma_sz_write(base, j, sz);
2050 				if (win_idma_can_remap(j) &&
2051 				    idma_wins[j].remap >= 0)
2052 					win_idma_har_write(base, j,
2053 					    idma_wins[j].remap);
2054 
2055 				/* Set protection RW on all channels */
2056 				idma_set_prot(base, j, 0x3);
2057 
2058 				/* Enable window */
2059 				idma_bare_write(base, j, 0);
2060 				break;
2061 			}
2062 		}
2063 }
2064 
2065 int
2066 decode_win_idma_valid(void)
2067 {
2068 	const struct decode_win *wintab;
2069 	int c, i, j, rv;
2070 	uint32_t b, e, s;
2071 
2072 	if (idma_wins_no > MV_WIN_IDMA_MAX) {
2073 		printf("IDMA windows: too many entries: %d\n", idma_wins_no);
2074 		return (0);
2075 	}
2076 	for (i = 0, c = 0; i < MV_WIN_DDR_MAX; i++)
2077 		if (ddr_is_active(i))
2078 			c++;
2079 
2080 	if (idma_wins_no > (MV_WIN_IDMA_MAX - c)) {
2081 		printf("IDMA windows: too many entries: %d, available: %d\n",
2082 		    idma_wins_no, MV_WIN_IDMA_MAX - c);
2083 		return (0);
2084 	}
2085 
2086 	wintab = idma_wins;
2087 	rv = 1;
2088 	for (i = 0; i < idma_wins_no; i++, wintab++) {
2089 		if (wintab->target == 0) {
2090 			printf("IDMA window#%d: DDR target window is not "
2091 			    "supposed to be reprogrammed!\n", i);
2092 			rv = 0;
2093 		}
2094 
2095 		if (wintab->remap >= 0 && win_cpu_can_remap(i) != 1) {
2096 			printf("IDMA window#%d: not capable of remapping, but "
2097 			    "val 0x%08x defined\n", i, wintab->remap);
2098 			rv = 0;
2099 		}
2100 
2101 		s = wintab->size;
2102 		b = wintab->base;
2103 		e = b + s - 1;
2104 		if (s > (0xFFFFFFFF - b + 1)) {
2105 			/* XXX this boundary check should account for 64bit and
2106 			 * remapping.. */
2107 			printf("IDMA window#%d: no space for size 0x%08x at "
2108 			    "0x%08x\n", i, s, b);
2109 			rv = 0;
2110 			continue;
2111 		}
2112 
2113 		j = decode_win_overlap(i, idma_wins_no, &idma_wins[0]);
2114 		if (j >= 0) {
2115 			printf("IDMA window#%d: (0x%08x - 0x%08x) overlaps "
2116 			    "with #%d (0x%08x - 0x%08x)\n", i, b, e, j,
2117 			    idma_wins[j].base,
2118 			    idma_wins[j].base + idma_wins[j].size - 1);
2119 			rv = 0;
2120 		}
2121 	}
2122 
2123 	return (rv);
2124 }
2125 
2126 void
2127 decode_win_idma_dump(u_long base)
2128 {
2129 	int i;
2130 
2131 	if (pm_is_disabled(CPU_PM_CTRL_IDMA))
2132 		return;
2133 
2134 	for (i = 0; i < MV_WIN_IDMA_MAX; i++) {
2135 		printf("IDMA window#%d: b 0x%08x, s 0x%08x", i,
2136 		    win_idma_br_read(base, i), win_idma_sz_read(base, i));
2137 
2138 		if (win_idma_can_remap(i))
2139 			printf(", ha 0x%08x", win_idma_har_read(base, i));
2140 
2141 		printf("\n");
2142 	}
2143 	for (i = 0; i < MV_IDMA_CHAN_MAX; i++)
2144 		printf("IDMA channel#%d: ap 0x%08x\n", i,
2145 		    win_idma_cap_read(base, i));
2146 	printf("IDMA windows: bare 0x%08x\n", win_idma_bare_read(base));
2147 }
2148 #else
2149 
2150 /* Provide dummy functions to satisfy the build for SoCs not equipped with IDMA */
2151 int
2152 decode_win_idma_valid(void)
2153 {
2154 
2155 	return (1);
2156 }
2157 
2158 void
2159 decode_win_idma_setup(u_long base)
2160 {
2161 }
2162 
2163 void
2164 decode_win_idma_dump(u_long base)
2165 {
2166 }
2167 #endif
2168 
2169 /**************************************************************************
2170  * XOR windows routines
2171  **************************************************************************/
2172 #if defined(SOC_MV_KIRKWOOD) || defined(SOC_MV_DISCOVERY)
2173 static int
2174 xor_ctrl_read(u_long base, int i, int c, int e)
2175 {
2176 	uint32_t v;
2177 	v = win_xor_ctrl_read(base, c, e);
2178 	v &= (1 << i);
2179 
2180 	return (v >> i);
2181 }
2182 
2183 static void
2184 xor_ctrl_write(u_long base, int i, int c, int e, int val)
2185 {
2186 	uint32_t v;
2187 
2188 	v = win_xor_ctrl_read(base, c, e);
2189 	v &= ~(1 << i);
2190 	v |= (val << i);
2191 	win_xor_ctrl_write(base, c, e, v);
2192 }
2193 
2194 /*
2195  * Set channel protection 'val' for window 'w' on channel 'c'
2196  */
2197 static void
2198 xor_chan_write(u_long base, int c, int e, int w, int val)
2199 {
2200 	uint32_t v;
2201 
2202 	v = win_xor_ctrl_read(base, c, e);
2203 	v &= ~(0x3 << (w * 2 + 16));
2204 	v |= (val << (w * 2 + 16));
2205 	win_xor_ctrl_write(base, c, e, v);
2206 }
2207 
2208 /*
2209  * Set protection 'val' on all channels for window 'w' on engine 'e'
2210  */
2211 static void
2212 xor_set_prot(u_long base, int w, int e, int val)
2213 {
2214 	int c;
2215 
2216 	for (c = 0; c < MV_XOR_CHAN_MAX; c++)
2217 		xor_chan_write(base, c, e, w, val);
2218 }
2219 
2220 static int
2221 win_xor_can_remap(int i)
2222 {
2223 
2224 	/* XOR decode windows 0-3 have remap capability */
2225 	if (i < 4)
2226 		return (1);
2227 
2228 	return (0);
2229 }
2230 
2231 static int
2232 xor_max_eng(void)
2233 {
2234 	uint32_t dev, rev;
2235 
2236 	soc_id(&dev, &rev);
2237 	switch (dev) {
2238 	case MV_DEV_88F6281:
2239 	case MV_DEV_88F6282:
2240 	case MV_DEV_MV78130:
2241 	case MV_DEV_MV78160:
2242 	case MV_DEV_MV78230:
2243 	case MV_DEV_MV78260:
2244 	case MV_DEV_MV78460:
2245 		return (2);
2246 	case MV_DEV_MV78100:
2247 	case MV_DEV_MV78100_Z0:
2248 		return (1);
2249 	default:
2250 		return (0);
2251 	}
2252 }
2253 
2254 static void
2255 xor_active_dram(u_long base, int c, int e, int *window)
2256 {
2257 	uint32_t br, sz;
2258 	int i, m, w;
2259 
2260 	/*
2261 	 * Set up access to all active DRAM banks
2262 	 */
2263 	m = xor_max_eng();
2264 	for (i = 0; i < m; i++)
2265 		if (ddr_is_active(i)) {
2266 			br = ddr_base(i) | (ddr_attr(i) << 8) |
2267 			    ddr_target(i);
2268 			sz = ((ddr_size(i) - 1) & 0xffff0000);
2269 
2270 			/* Place DDR entries in non-remapped windows */
2271 			for (w = 0; w < MV_WIN_XOR_MAX; w++)
2272 				if (win_xor_can_remap(w) != 1 &&
2273 				    (xor_ctrl_read(base, w, c, e) == 0) &&
2274 				    w > *window) {
2275 					/* Configure window */
2276 					win_xor_br_write(base, w, e, br);
2277 					win_xor_sz_write(base, w, e, sz);
2278 
2279 					/* Set protection RW on all channels */
2280 					xor_set_prot(base, w, e, 0x3);
2281 
2282 					/* Enable window */
2283 					xor_ctrl_write(base, w, c, e, 1);
2284 					(*window)++;
2285 					break;
2286 				}
2287 		}
2288 }
2289 
2290 void
2291 decode_win_xor_setup(u_long base)
2292 {
2293 	uint32_t br, sz;
2294 	int i, j, z, e = 1, m, window;
2295 
2296 	if (pm_is_disabled(CPU_PM_CTRL_XOR))
2297 		return;
2298 
2299 	/*
2300 	 * Disable and clear all XOR windows, revoke protection for all
2301 	 * channels
2302 	 */
2303 	m = xor_max_eng();
2304 	for (j = 0; j < m; j++, e--) {
2305 		/* Number of non-remaped windows */
2306 		window = MV_XOR_NON_REMAP - 1;
2307 
2308 		for (i = 0; i < MV_WIN_XOR_MAX; i++) {
2309 			win_xor_br_write(base, i, e, 0);
2310 			win_xor_sz_write(base, i, e, 0);
2311 		}
2312 
2313 		if (win_xor_can_remap(i) == 1)
2314 			win_xor_har_write(base, i, e, 0);
2315 
2316 		for (i = 0; i < MV_XOR_CHAN_MAX; i++) {
2317 			win_xor_ctrl_write(base, i, e, 0);
2318 			xor_active_dram(base, i, e, &window);
2319 		}
2320 
2321 		/*
2322 		 * Remaining targets -- from a statically defined table
2323 		 */
2324 		for (i = 0; i < xor_wins_no; i++)
2325 			if (xor_wins[i].target > 0) {
2326 				br = (xor_wins[i].base & 0xffff0000) |
2327 				    (xor_wins[i].attr << 8) |
2328 				    xor_wins[i].target;
2329 				sz = ((xor_wins[i].size - 1) & 0xffff0000);
2330 
2331 				/* Set the first free XOR window */
2332 				for (z = 0; z < MV_WIN_XOR_MAX; z++) {
2333 					if (xor_ctrl_read(base, z, 0, e) &&
2334 					    xor_ctrl_read(base, z, 1, e))
2335 						continue;
2336 
2337 					/* Configure window */
2338 					win_xor_br_write(base, z, e, br);
2339 					win_xor_sz_write(base, z, e, sz);
2340 					if (win_xor_can_remap(z) &&
2341 					    xor_wins[z].remap >= 0)
2342 						win_xor_har_write(base, z, e,
2343 						    xor_wins[z].remap);
2344 
2345 					/* Set protection RW on all channels */
2346 					xor_set_prot(base, z, e, 0x3);
2347 
2348 					/* Enable window */
2349 					xor_ctrl_write(base, z, 0, e, 1);
2350 					xor_ctrl_write(base, z, 1, e, 1);
2351 					break;
2352 				}
2353 			}
2354 	}
2355 }
2356 
2357 int
2358 decode_win_xor_valid(void)
2359 {
2360 	const struct decode_win *wintab;
2361 	int c, i, j, rv;
2362 	uint32_t b, e, s;
2363 
2364 	if (xor_wins_no > MV_WIN_XOR_MAX) {
2365 		printf("XOR windows: too many entries: %d\n", xor_wins_no);
2366 		return (0);
2367 	}
2368 	for (i = 0, c = 0; i < MV_WIN_DDR_MAX; i++)
2369 		if (ddr_is_active(i))
2370 			c++;
2371 
2372 	if (xor_wins_no > (MV_WIN_XOR_MAX - c)) {
2373 		printf("XOR windows: too many entries: %d, available: %d\n",
2374 		    xor_wins_no, MV_WIN_IDMA_MAX - c);
2375 		return (0);
2376 	}
2377 
2378 	wintab = xor_wins;
2379 	rv = 1;
2380 	for (i = 0; i < xor_wins_no; i++, wintab++) {
2381 		if (wintab->target == 0) {
2382 			printf("XOR window#%d: DDR target window is not "
2383 			    "supposed to be reprogrammed!\n", i);
2384 			rv = 0;
2385 		}
2386 
2387 		if (wintab->remap >= 0 && win_cpu_can_remap(i) != 1) {
2388 			printf("XOR window#%d: not capable of remapping, but "
2389 			    "val 0x%08x defined\n", i, wintab->remap);
2390 			rv = 0;
2391 		}
2392 
2393 		s = wintab->size;
2394 		b = wintab->base;
2395 		e = b + s - 1;
2396 		if (s > (0xFFFFFFFF - b + 1)) {
2397 			/*
2398 			 * XXX this boundary check should account for 64bit
2399 			 * and remapping..
2400 			 */
2401 			printf("XOR window#%d: no space for size 0x%08x at "
2402 			    "0x%08x\n", i, s, b);
2403 			rv = 0;
2404 			continue;
2405 		}
2406 
2407 		j = decode_win_overlap(i, xor_wins_no, &xor_wins[0]);
2408 		if (j >= 0) {
2409 			printf("XOR window#%d: (0x%08x - 0x%08x) overlaps "
2410 			    "with #%d (0x%08x - 0x%08x)\n", i, b, e, j,
2411 			    xor_wins[j].base,
2412 			    xor_wins[j].base + xor_wins[j].size - 1);
2413 			rv = 0;
2414 		}
2415 	}
2416 
2417 	return (rv);
2418 }
2419 
2420 void
2421 decode_win_xor_dump(u_long base)
2422 {
2423 	int i, j;
2424 	int e = 1;
2425 
2426 	if (pm_is_disabled(CPU_PM_CTRL_XOR))
2427 		return;
2428 
2429 	for (j = 0; j < xor_max_eng(); j++, e--) {
2430 		for (i = 0; i < MV_WIN_XOR_MAX; i++) {
2431 			printf("XOR window#%d: b 0x%08x, s 0x%08x", i,
2432 			    win_xor_br_read(base, i, e), win_xor_sz_read(base, i, e));
2433 
2434 			if (win_xor_can_remap(i))
2435 				printf(", ha 0x%08x", win_xor_har_read(base, i, e));
2436 
2437 			printf("\n");
2438 		}
2439 		for (i = 0; i < MV_XOR_CHAN_MAX; i++)
2440 			printf("XOR control#%d: 0x%08x\n", i,
2441 			    win_xor_ctrl_read(base, i, e));
2442 	}
2443 }
2444 
2445 #else
2446 /* Provide dummy functions to satisfy the build for SoCs not equipped with XOR */
2447 static int
2448 decode_win_xor_valid(void)
2449 {
2450 
2451 	return (1);
2452 }
2453 
2454 static void
2455 decode_win_xor_setup(u_long base)
2456 {
2457 }
2458 
2459 static void
2460 decode_win_xor_dump(u_long base)
2461 {
2462 }
2463 #endif
2464 
2465 /**************************************************************************
2466  * SATA windows routines
2467  **************************************************************************/
2468 static void
2469 decode_win_sata_setup(u_long base)
2470 {
2471 	uint32_t cr, br;
2472 	int i, j;
2473 
2474 	if (pm_is_disabled(CPU_PM_CTRL_SATA))
2475 		return;
2476 
2477 	for (i = 0; i < MV_WIN_SATA_MAX; i++) {
2478 		win_sata_cr_write(base, i, 0);
2479 		win_sata_br_write(base, i, 0);
2480 	}
2481 
2482 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
2483 		if (ddr_is_active(i)) {
2484 			cr = ((ddr_size(i) - 1) & 0xffff0000) |
2485 			    (ddr_attr(i) << 8) | (ddr_target(i) << 4) | 1;
2486 			br = ddr_base(i);
2487 
2488 			/* Use the first available SATA window */
2489 			for (j = 0; j < MV_WIN_SATA_MAX; j++) {
2490 				if ((win_sata_cr_read(base, j) & 1) != 0)
2491 					continue;
2492 
2493 				win_sata_br_write(base, j, br);
2494 				win_sata_cr_write(base, j, cr);
2495 				break;
2496 			}
2497 		}
2498 }
2499 
2500 /*
2501  * Configure AHCI decoding windows
2502  */
2503 static void
2504 decode_win_ahci_setup(u_long base)
2505 {
2506 	uint32_t br, cr, sz;
2507 	int i, j;
2508 
2509 	for (i = 0; i < MV_WIN_SATA_MAX_ARMADA38X; i++) {
2510 		win_sata_armada38x_cr_write(base, i, 0);
2511 		win_sata_armada38x_br_write(base, i, 0);
2512 		win_sata_armada38x_sz_write(base, i, 0);
2513 	}
2514 
2515 	for (i = 0; i < MV_WIN_DDR_MAX; i++) {
2516 		if (ddr_is_active(i)) {
2517 			cr = (ddr_attr(i) << IO_WIN_ATTR_SHIFT) |
2518 			    (ddr_target(i) << IO_WIN_TGT_SHIFT) |
2519 			    IO_WIN_ENA_MASK;
2520 			br = ddr_base(i);
2521 			sz = (ddr_size(i) - 1) &
2522 			    (IO_WIN_SIZE_MASK << IO_WIN_SIZE_SHIFT);
2523 
2524 			/* Use first available SATA window */
2525 			for (j = 0; j < MV_WIN_SATA_MAX_ARMADA38X; j++) {
2526 				if (win_sata_armada38x_cr_read(base, j) & IO_WIN_ENA_MASK)
2527 					continue;
2528 
2529 				/* BASE is set to DRAM base (0x00000000) */
2530 				win_sata_armada38x_br_write(base, j, br);
2531 				/* CTRL targets DRAM ctrl with 0x0E or 0x0D */
2532 				win_sata_armada38x_cr_write(base, j, cr);
2533 				/* SIZE is set to 16MB - max value */
2534 				win_sata_armada38x_sz_write(base, j, sz);
2535 				break;
2536 			}
2537 		}
2538 	}
2539 }
2540 
2541 static void
2542 decode_win_ahci_dump(u_long base)
2543 {
2544 	int i;
2545 
2546 	for (i = 0; i < MV_WIN_SATA_MAX_ARMADA38X; i++)
2547 		printf("SATA window#%d: cr 0x%08x, br 0x%08x, sz 0x%08x\n", i,
2548 		    win_sata_armada38x_cr_read(base, i), win_sata_br_read(base, i),
2549 		    win_sata_armada38x_sz_read(base,i));
2550 }
2551 
2552 static int
2553 decode_win_sata_valid(void)
2554 {
2555 	uint32_t dev, rev;
2556 
2557 	soc_id(&dev, &rev);
2558 	if (dev == MV_DEV_88F5281)
2559 		return (1);
2560 
2561 	return (decode_win_can_cover_ddr(MV_WIN_SATA_MAX));
2562 }
2563 
2564 static void
2565 decode_win_sdhci_setup(u_long base)
2566 {
2567 	uint32_t cr, br;
2568 	int i, j;
2569 
2570 	for (i = 0; i < MV_WIN_SDHCI_MAX; i++) {
2571 		win_sdhci_cr_write(base, i, 0);
2572 		win_sdhci_br_write(base, i, 0);
2573 	}
2574 
2575 	for (i = 0; i < MV_WIN_DDR_MAX; i++)
2576 		if (ddr_is_active(i)) {
2577 			br = ddr_base(i);
2578 			cr = (((ddr_size(i) - 1) &
2579 			    (IO_WIN_SIZE_MASK << IO_WIN_SIZE_SHIFT)) |
2580 			    (ddr_attr(i) << IO_WIN_ATTR_SHIFT) |
2581 			    (ddr_target(i) << IO_WIN_TGT_SHIFT) |
2582 			    IO_WIN_ENA_MASK);
2583 
2584 			/* Use the first available SDHCI window */
2585 			for (j = 0; j < MV_WIN_SDHCI_MAX; j++) {
2586 				if (win_sdhci_cr_read(base, j) & IO_WIN_ENA_MASK)
2587 					continue;
2588 
2589 				win_sdhci_cr_write(base, j, cr);
2590 				win_sdhci_br_write(base, j, br);
2591 				break;
2592 			}
2593 		}
2594 }
2595 
2596 static void
2597 decode_win_sdhci_dump(u_long base)
2598 {
2599 	int i;
2600 
2601 	for (i = 0; i < MV_WIN_SDHCI_MAX; i++)
2602 		printf("SDHCI window#%d: c 0x%08x, b 0x%08x\n", i,
2603 		    win_sdhci_cr_read(base, i), win_sdhci_br_read(base, i));
2604 }
2605 
2606 static int
2607 decode_win_sdhci_valid(void)
2608 {
2609 
2610 	return (decode_win_can_cover_ddr(MV_WIN_SDHCI_MAX));
2611 }
2612 
2613 /**************************************************************************
2614  * FDT parsing routines.
2615  **************************************************************************/
2616 
2617 static int
2618 fdt_get_ranges(const char *nodename, void *buf, int size, int *tuples,
2619     int *tuplesize)
2620 {
2621 	phandle_t node;
2622 	pcell_t addr_cells, par_addr_cells, size_cells;
2623 	int len, tuple_size, tuples_count;
2624 
2625 	node = OF_finddevice(nodename);
2626 	if (node == -1)
2627 		return (EINVAL);
2628 
2629 	if ((fdt_addrsize_cells(node, &addr_cells, &size_cells)) != 0)
2630 		return (ENXIO);
2631 
2632 	par_addr_cells = fdt_parent_addr_cells(node);
2633 	if (par_addr_cells > 2)
2634 		return (ERANGE);
2635 
2636 	tuple_size = sizeof(pcell_t) * (addr_cells + par_addr_cells +
2637 	    size_cells);
2638 
2639 	/* Note the OF_getprop_alloc() cannot be used at this early stage. */
2640 	len = OF_getprop(node, "ranges", buf, size);
2641 
2642 	/*
2643 	 * XXX this does not handle the empty 'ranges;' case, which is
2644 	 * legitimate and should be allowed.
2645 	 */
2646 	tuples_count = len / tuple_size;
2647 	if (tuples_count <= 0)
2648 		return (ERANGE);
2649 
2650 	if (par_addr_cells > 2 || addr_cells > 2 || size_cells > 2)
2651 		return (ERANGE);
2652 
2653 	*tuples = tuples_count;
2654 	*tuplesize = tuple_size;
2655 	return (0);
2656 }
2657 
2658 static int
2659 win_cpu_from_dt(void)
2660 {
2661 	pcell_t ranges[48];
2662 	phandle_t node;
2663 	int i, entry_size, err, t, tuple_size, tuples;
2664 	u_long sram_base, sram_size;
2665 
2666 	t = 0;
2667 	/* Retrieve 'ranges' property of '/localbus' node. */
2668 	if ((err = fdt_get_ranges("/localbus", ranges, sizeof(ranges),
2669 	    &tuples, &tuple_size)) == 0) {
2670 		/*
2671 		 * Fill CPU decode windows table.
2672 		 */
2673 		bzero((void *)&cpu_win_tbl, sizeof(cpu_win_tbl));
2674 
2675 		entry_size = tuple_size / sizeof(pcell_t);
2676 		cpu_wins_no = tuples;
2677 
2678 		/* Check range */
2679 		if (tuples > nitems(cpu_win_tbl)) {
2680 			debugf("too many tuples to fit into cpu_win_tbl\n");
2681 			return (ENOMEM);
2682 		}
2683 
2684 		for (i = 0, t = 0; t < tuples; i += entry_size, t++) {
2685 			cpu_win_tbl[t].target = 1;
2686 			cpu_win_tbl[t].attr = fdt32_to_cpu(ranges[i + 1]);
2687 			cpu_win_tbl[t].base = fdt32_to_cpu(ranges[i + 2]);
2688 			cpu_win_tbl[t].size = fdt32_to_cpu(ranges[i + 3]);
2689 			cpu_win_tbl[t].remap = ~0;
2690 			debugf("target = 0x%0x attr = 0x%0x base = 0x%0x "
2691 			    "size = 0x%0x remap = 0x%0x\n",
2692 			    cpu_win_tbl[t].target,
2693 			    cpu_win_tbl[t].attr, cpu_win_tbl[t].base,
2694 			    cpu_win_tbl[t].size, cpu_win_tbl[t].remap);
2695 		}
2696 	}
2697 
2698 	/*
2699 	 * Retrieve CESA SRAM data.
2700 	 */
2701 	if ((node = OF_finddevice("sram")) != -1)
2702 		if (ofw_bus_node_is_compatible(node, "mrvl,cesa-sram"))
2703 			goto moveon;
2704 
2705 	if ((node = OF_finddevice("/")) == -1)
2706 		return (ENXIO);
2707 
2708 	if ((node = fdt_find_compatible(node, "mrvl,cesa-sram", 0)) == 0)
2709 		/* SRAM block is not always present. */
2710 		return (0);
2711 moveon:
2712 	sram_base = sram_size = 0;
2713 	if (fdt_regsize(node, &sram_base, &sram_size) != 0)
2714 		return (EINVAL);
2715 
2716 	/* Check range */
2717 	if (t >= nitems(cpu_win_tbl)) {
2718 		debugf("cannot fit CESA tuple into cpu_win_tbl\n");
2719 		return (ENOMEM);
2720 	}
2721 
2722 	cpu_win_tbl[t].target = soc_decode_win_spec->win_cesa_target;
2723 	if (soc_family == MV_SOC_ARMADA_38X)
2724 		cpu_win_tbl[t].attr = soc_decode_win_spec->win_cesa_attr(0);
2725 	else
2726 		cpu_win_tbl[t].attr = soc_decode_win_spec->win_cesa_attr(1);
2727 	cpu_win_tbl[t].base = sram_base;
2728 	cpu_win_tbl[t].size = sram_size;
2729 	cpu_win_tbl[t].remap = ~0;
2730 	cpu_wins_no++;
2731 	debugf("sram: base = 0x%0lx size = 0x%0lx\n", sram_base, sram_size);
2732 
2733 	/* Check if there is a second CESA node */
2734 	while ((node = OF_peer(node)) != 0) {
2735 		if (ofw_bus_node_is_compatible(node, "mrvl,cesa-sram")) {
2736 			if (fdt_regsize(node, &sram_base, &sram_size) != 0)
2737 				return (EINVAL);
2738 			break;
2739 		}
2740 	}
2741 
2742 	if (node == 0)
2743 		return (0);
2744 
2745 	t++;
2746 	if (t >= nitems(cpu_win_tbl)) {
2747 		debugf("cannot fit CESA tuple into cpu_win_tbl\n");
2748 		return (ENOMEM);
2749 	}
2750 
2751 	/* Configure window for CESA1 */
2752 	cpu_win_tbl[t].target = soc_decode_win_spec->win_cesa_target;
2753 	cpu_win_tbl[t].attr = soc_decode_win_spec->win_cesa_attr(1);
2754 	cpu_win_tbl[t].base = sram_base;
2755 	cpu_win_tbl[t].size = sram_size;
2756 	cpu_win_tbl[t].remap = ~0;
2757 	cpu_wins_no++;
2758 	debugf("sram: base = 0x%0lx size = 0x%0lx\n", sram_base, sram_size);
2759 
2760 	return (0);
2761 }
2762 
2763 static int
2764 fdt_win_process(phandle_t child)
2765 {
2766 	int i, ret;
2767 
2768 	for (i = 0; soc_nodes[i].compat != NULL; i++) {
2769 		/* Setup only for enabled devices */
2770 		if (ofw_bus_node_status_okay(child) == 0)
2771 			continue;
2772 
2773 		if (!ofw_bus_node_is_compatible(child, soc_nodes[i].compat))
2774 			continue;
2775 
2776 		ret = fdt_win_process_child(child, &soc_nodes[i], "reg");
2777 		if (ret != 0)
2778 			return (ret);
2779 	}
2780 
2781 	return (0);
2782 }
2783 
2784 static int
2785 fdt_win_process_child(phandle_t child, struct soc_node_spec *soc_node,
2786     const char* mimo_reg_source)
2787 {
2788 	int addr_cells, size_cells;
2789 	pcell_t reg[8];
2790 	u_long size, base;
2791 
2792 	if (fdt_addrsize_cells(OF_parent(child), &addr_cells,
2793 	    &size_cells))
2794 		return (ENXIO);
2795 
2796 	if ((sizeof(pcell_t) * (addr_cells + size_cells)) > sizeof(reg))
2797 		return (ENOMEM);
2798 	if (OF_getprop(child, mimo_reg_source, &reg, sizeof(reg)) <= 0)
2799 		return (EINVAL);
2800 
2801 	if (addr_cells <= 2)
2802 		base = fdt_data_get(&reg[0], addr_cells);
2803 	else
2804 		base = fdt_data_get(&reg[addr_cells - 2], 2);
2805 	size = fdt_data_get(&reg[addr_cells], size_cells);
2806 
2807 	if (soc_node->valid_handler != NULL)
2808 		if (!soc_node->valid_handler())
2809 			return (EINVAL);
2810 
2811 	base = (base & 0x000fffff) | fdt_immr_va;
2812 	if (soc_node->decode_handler != NULL)
2813 		soc_node->decode_handler(base);
2814 	else
2815 		return (ENXIO);
2816 
2817 	if (MV_DUMP_WIN && (soc_node->dump_handler != NULL))
2818 		soc_node->dump_handler(base);
2819 
2820 	return (0);
2821 }
2822 
2823 static int
2824 fdt_win_setup(void)
2825 {
2826 	phandle_t node, child, sb;
2827 	phandle_t child_pci;
2828 	int err;
2829 
2830 	sb = 0;
2831 	node = OF_finddevice("/");
2832 	if (node == -1)
2833 		panic("fdt_win_setup: no root node");
2834 
2835 	/* Allow for coherent transactions on the A38x MBUS */
2836 	if (ofw_bus_node_is_compatible(node, "marvell,armada380"))
2837 		platform_io_coherent = true;
2838 
2839 	/*
2840 	 * Traverse through all children of root and simple-bus nodes.
2841 	 * For each found device retrieve decode windows data (if applicable).
2842 	 */
2843 	child = OF_child(node);
2844 	while (child != 0) {
2845 		/* Lookup for callback and run */
2846 		err = fdt_win_process(child);
2847 		if (err != 0)
2848 			return (err);
2849 
2850 		/* Process Marvell Armada-XP/38x PCIe controllers */
2851 		if (ofw_bus_node_is_compatible(child, "marvell,armada-370-pcie")) {
2852 			child_pci = OF_child(child);
2853 			while (child_pci != 0) {
2854 				err = fdt_win_process_child(child_pci,
2855 				    &soc_nodes[SOC_NODE_PCIE_ENTRY_IDX],
2856 				    "assigned-addresses");
2857 				if (err != 0)
2858 					return (err);
2859 
2860 				child_pci = OF_peer(child_pci);
2861 			}
2862 		}
2863 
2864 		/*
2865 		 * Once done with root-level children let's move down to
2866 		 * simple-bus and its children.
2867 		 */
2868 		child = OF_peer(child);
2869 		if ((child == 0) && (node == OF_finddevice("/"))) {
2870 			sb = node = fdt_find_compatible(node, "simple-bus", 0);
2871 			if (node == 0)
2872 				return (ENXIO);
2873 			child = OF_child(node);
2874 		}
2875 		/*
2876 		 * Next, move one more level down to internal-regs node (if
2877 		 * it is present) and its children. This node also have
2878 		 * "simple-bus" compatible.
2879 		 */
2880 		if ((child == 0) && (node == sb)) {
2881 			node = fdt_find_compatible(node, "simple-bus", 0);
2882 			if (node == 0)
2883 				return (0);
2884 			child = OF_child(node);
2885 		}
2886 	}
2887 
2888 	return (0);
2889 }
2890 
2891 static void
2892 fdt_fixup_busfreq(phandle_t root)
2893 {
2894 	phandle_t sb;
2895 	pcell_t freq;
2896 
2897 	freq = cpu_to_fdt32(get_tclk());
2898 
2899 	/*
2900 	 * Fix bus speed in cpu node
2901 	 */
2902 	if ((sb = OF_finddevice("cpu")) != -1)
2903 		if (fdt_is_compatible_strict(sb, "ARM,88VS584"))
2904 			OF_setprop(sb, "bus-frequency", (void *)&freq,
2905 			    sizeof(freq));
2906 
2907 	/*
2908 	 * This fixup sets the simple-bus bus-frequency property.
2909 	 */
2910 	if ((sb = fdt_find_compatible(root, "simple-bus", 1)) != 0)
2911 		OF_setprop(sb, "bus-frequency", (void *)&freq, sizeof(freq));
2912 }
2913 
2914 static void
2915 fdt_fixup_ranges(phandle_t root)
2916 {
2917 	phandle_t node;
2918 	pcell_t par_addr_cells, addr_cells, size_cells;
2919 	pcell_t ranges[3], reg[2], *rangesptr;
2920 	int len, tuple_size, tuples_count;
2921 	uint32_t base;
2922 
2923 	/* Fix-up SoC ranges according to real fdt_immr_pa */
2924 	if ((node = fdt_find_compatible(root, "simple-bus", 1)) != 0) {
2925 		if (fdt_addrsize_cells(node, &addr_cells, &size_cells) == 0 &&
2926 		    ((par_addr_cells = fdt_parent_addr_cells(node)) <= 2)) {
2927 			tuple_size = sizeof(pcell_t) * (par_addr_cells +
2928 			   addr_cells + size_cells);
2929 			len = OF_getprop(node, "ranges", ranges,
2930 			    sizeof(ranges));
2931 			tuples_count = len / tuple_size;
2932 			/* Unexpected settings are not supported */
2933 			if (tuples_count != 1)
2934 				goto fixup_failed;
2935 
2936 			rangesptr = &ranges[0];
2937 			rangesptr += par_addr_cells;
2938 			base = fdt_data_get((void *)rangesptr, addr_cells);
2939 			*rangesptr = cpu_to_fdt32(fdt_immr_pa);
2940 			if (OF_setprop(node, "ranges", (void *)&ranges[0],
2941 			    sizeof(ranges)) < 0)
2942 				goto fixup_failed;
2943 		}
2944 	}
2945 
2946 	/* Fix-up PCIe reg according to real PCIe registers' PA */
2947 	if ((node = fdt_find_compatible(root, "mrvl,pcie", 1)) != 0) {
2948 		if (fdt_addrsize_cells(OF_parent(node), &par_addr_cells,
2949 		    &size_cells) == 0) {
2950 			tuple_size = sizeof(pcell_t) * (par_addr_cells +
2951 			    size_cells);
2952 			len = OF_getprop(node, "reg", reg, sizeof(reg));
2953 			tuples_count = len / tuple_size;
2954 			/* Unexpected settings are not supported */
2955 			if (tuples_count != 1)
2956 				goto fixup_failed;
2957 
2958 			base = fdt_data_get((void *)&reg[0], par_addr_cells);
2959 			base &= ~0xFF000000;
2960 			base |= fdt_immr_pa;
2961 			reg[0] = cpu_to_fdt32(base);
2962 			if (OF_setprop(node, "reg", (void *)&reg[0],
2963 			    sizeof(reg)) < 0)
2964 				goto fixup_failed;
2965 		}
2966 	}
2967 	/* Fix-up succeeded. May return and continue */
2968 	return;
2969 
2970 fixup_failed:
2971 	while (1) {
2972 		/*
2973 		 * In case of any error while fixing ranges just hang.
2974 		 *	1. No message can be displayed yet since console
2975 		 *	   is not initialized.
2976 		 *	2. Going further will cause failure on bus_space_map()
2977 		 *	   relying on the wrong ranges or data abort when
2978 		 *	   accessing PCIe registers.
2979 		 */
2980 	}
2981 }
2982 
2983 struct fdt_fixup_entry fdt_fixup_table[] = {
2984 	{ "mrvl,DB-88F6281", &fdt_fixup_busfreq },
2985 	{ "mrvl,DB-78460", &fdt_fixup_busfreq },
2986 	{ "mrvl,DB-78460", &fdt_fixup_ranges },
2987 	{ NULL, NULL }
2988 };
2989 
2990 #if __ARM_ARCH >= 6
2991 uint32_t
2992 get_tclk(void)
2993 {
2994 
2995 	if (soc_decode_win_spec->get_tclk != NULL)
2996 		return soc_decode_win_spec->get_tclk();
2997 	else
2998 		return -1;
2999 }
3000 
3001 uint32_t
3002 get_cpu_freq(void)
3003 {
3004 
3005 	if (soc_decode_win_spec->get_cpu_freq != NULL)
3006 		return soc_decode_win_spec->get_cpu_freq();
3007 	else
3008 		return -1;
3009 }
3010 #endif
3011 
3012 #ifndef INTRNG
3013 static int
3014 fdt_pic_decode_ic(phandle_t node, pcell_t *intr, int *interrupt, int *trig,
3015     int *pol)
3016 {
3017 
3018 	if (!ofw_bus_node_is_compatible(node, "mrvl,pic") &&
3019 	    !ofw_bus_node_is_compatible(node, "mrvl,mpic"))
3020 		return (ENXIO);
3021 
3022 	*interrupt = fdt32_to_cpu(intr[0]);
3023 	*trig = INTR_TRIGGER_CONFORM;
3024 	*pol = INTR_POLARITY_CONFORM;
3025 
3026 	return (0);
3027 }
3028 
3029 fdt_pic_decode_t fdt_pic_table[] = {
3030 	&fdt_pic_decode_ic,
3031 	NULL
3032 };
3033 #endif
3034