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