aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/mach-kirkwood
diff options
context:
space:
mode:
authorSaeed Bishara <saeed@marvell.com>2008-06-22 16:45:06 -0400
committerLennert Buytenhek <buytenh@marvell.com>2008-06-22 16:45:06 -0400
commit651c74c74bf84ba966b52588ba3329606f3fd8d4 (patch)
tree7cb446c1da925bf1f4ca9c3a74dfe478748ec515 /arch/arm/mach-kirkwood
parent9c2af6c57c4a253b595b5eef1b665989b5f15de5 (diff)
[ARM] add Marvell Kirkwood (88F6000) SoC support
The Marvell Kirkwood (88F6000) is a family of ARM SoCs based on a Shiva CPU core, and features a DDR2 controller, a x1 PCIe interface, a USB 2.0 interface, a SPI controller, a crypto accelerator, a TS interface, and IDMA/XOR engines, and depending on the model, also features one or two Gigabit Ethernet interfaces, two SATA II interfaces, one or two TWSI interfaces, one or two UARTs, a TDM/SLIC interface, a NAND controller, an I2S/SPDIF interface, and an SDIO interface. This patch adds supports for the Marvell DB-88F6281-BP Development Board and the RD-88F6192-NAS and the RD-88F6281 Reference Designs, enabling support for the PCIe interface, the USB interface, the ethernet interfaces, the SATA interfaces, the TWSI interfaces, the UARTs, and the NAND controller. Signed-off-by: Saeed Bishara <saeed@marvell.com> Signed-off-by: Lennert Buytenhek <buytenh@marvell.com>
Diffstat (limited to 'arch/arm/mach-kirkwood')
-rw-r--r--arch/arm/mach-kirkwood/Kconfig25
-rw-r--r--arch/arm/mach-kirkwood/Makefile5
-rw-r--r--arch/arm/mach-kirkwood/Makefile.boot3
-rw-r--r--arch/arm/mach-kirkwood/addr-map.c139
-rw-r--r--arch/arm/mach-kirkwood/common.c326
-rw-r--r--arch/arm/mach-kirkwood/common.h42
-rw-r--r--arch/arm/mach-kirkwood/db88f6281-bp-setup.c68
-rw-r--r--arch/arm/mach-kirkwood/irq.c22
-rw-r--r--arch/arm/mach-kirkwood/pcie.c180
-rw-r--r--arch/arm/mach-kirkwood/rd88f6192-nas-setup.c69
-rw-r--r--arch/arm/mach-kirkwood/rd88f6281-setup.c112
11 files changed, 991 insertions, 0 deletions
diff --git a/arch/arm/mach-kirkwood/Kconfig b/arch/arm/mach-kirkwood/Kconfig
new file mode 100644
index 000000000000..3600cd9f0519
--- /dev/null
+++ b/arch/arm/mach-kirkwood/Kconfig
@@ -0,0 +1,25 @@
1if ARCH_KIRKWOOD
2
3menu "Marvell Kirkwood Implementations"
4
5config MACH_DB88F6281_BP
6 bool "Marvell DB-88F6281-BP Development Board"
7 help
8 Say 'Y' here if you want your kernel to support the
9 Marvell DB-88F6281-BP Development Board.
10
11config MACH_RD88F6192_NAS
12 bool "Marvell RD-88F6192-NAS Reference Board"
13 help
14 Say 'Y' here if you want your kernel to support the
15 Marvell RD-88F6192-NAS Reference Board.
16
17config MACH_RD88F6281
18 bool "Marvell RD-88F6281 Reference Board"
19 help
20 Say 'Y' here if you want your kernel to support the
21 Marvell RD-88F6281 Reference Board.
22
23endmenu
24
25endif
diff --git a/arch/arm/mach-kirkwood/Makefile b/arch/arm/mach-kirkwood/Makefile
new file mode 100644
index 000000000000..e14bf40bfb07
--- /dev/null
+++ b/arch/arm/mach-kirkwood/Makefile
@@ -0,0 +1,5 @@
1obj-y += common.o addr-map.o irq.o pcie.o
2
3obj-$(CONFIG_MACH_DB88F6281_BP) += db88f6281-bp-setup.o
4obj-$(CONFIG_MACH_RD88F6192_NAS) += rd88f6192-nas-setup.o
5obj-$(CONFIG_MACH_RD88F6192_NAS) += rd88f6281-setup.o
diff --git a/arch/arm/mach-kirkwood/Makefile.boot b/arch/arm/mach-kirkwood/Makefile.boot
new file mode 100644
index 000000000000..67039c3e0c48
--- /dev/null
+++ b/arch/arm/mach-kirkwood/Makefile.boot
@@ -0,0 +1,3 @@
1 zreladdr-y := 0x00008000
2params_phys-y := 0x00000100
3initrd_phys-y := 0x00800000
diff --git a/arch/arm/mach-kirkwood/addr-map.c b/arch/arm/mach-kirkwood/addr-map.c
new file mode 100644
index 000000000000..a39f0f3c4730
--- /dev/null
+++ b/arch/arm/mach-kirkwood/addr-map.c
@@ -0,0 +1,139 @@
1/*
2 * arch/arm/mach-kirkwood/addr-map.c
3 *
4 * Address map functions for Marvell Kirkwood SoCs
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/init.h>
13#include <linux/mbus.h>
14#include <linux/io.h>
15#include <asm/hardware.h>
16#include "common.h"
17
18/*
19 * Generic Address Decode Windows bit settings
20 */
21#define TARGET_DDR 0
22#define TARGET_DEV_BUS 1
23#define TARGET_PCIE 4
24#define ATTR_DEV_SPI_ROM 0x1e
25#define ATTR_DEV_BOOT 0x1d
26#define ATTR_DEV_NAND 0x2f
27#define ATTR_DEV_CS3 0x37
28#define ATTR_DEV_CS2 0x3b
29#define ATTR_DEV_CS1 0x3d
30#define ATTR_DEV_CS0 0x3e
31#define ATTR_PCIE_IO 0xe0
32#define ATTR_PCIE_MEM 0xe8
33
34/*
35 * Helpers to get DDR bank info
36 */
37#define DDR_BASE_CS_OFF(n) (0x0000 + ((n) << 3))
38#define DDR_SIZE_CS_OFF(n) (0x0004 + ((n) << 3))
39
40/*
41 * CPU Address Decode Windows registers
42 */
43#define WIN_OFF(n) (BRIDGE_VIRT_BASE + 0x0000 + ((n) << 4))
44#define WIN_CTRL_OFF 0x0000
45#define WIN_BASE_OFF 0x0004
46#define WIN_REMAP_LO_OFF 0x0008
47#define WIN_REMAP_HI_OFF 0x000c
48
49
50struct mbus_dram_target_info kirkwood_mbus_dram_info;
51
52static int __init cpu_win_can_remap(int win)
53{
54 if (win < 4)
55 return 1;
56
57 return 0;
58}
59
60static void __init setup_cpu_win(int win, u32 base, u32 size,
61 u8 target, u8 attr, int remap)
62{
63 void __iomem *addr = (void __iomem *)WIN_OFF(win);
64 u32 ctrl;
65
66 base &= 0xffff0000;
67 ctrl = ((size - 1) & 0xffff0000) | (attr << 8) | (target << 4) | 1;
68
69 writel(base, addr + WIN_BASE_OFF);
70 writel(ctrl, addr + WIN_CTRL_OFF);
71 if (cpu_win_can_remap(win)) {
72 if (remap < 0)
73 remap = base;
74
75 writel(remap & 0xffff0000, addr + WIN_REMAP_LO_OFF);
76 writel(0, addr + WIN_REMAP_HI_OFF);
77 }
78}
79
80void __init kirkwood_setup_cpu_mbus(void)
81{
82 void __iomem *addr;
83 int i;
84 int cs;
85
86 /*
87 * First, disable and clear windows.
88 */
89 for (i = 0; i < 8; i++) {
90 addr = (void __iomem *)WIN_OFF(i);
91
92 writel(0, addr + WIN_BASE_OFF);
93 writel(0, addr + WIN_CTRL_OFF);
94 if (cpu_win_can_remap(i)) {
95 writel(0, addr + WIN_REMAP_LO_OFF);
96 writel(0, addr + WIN_REMAP_HI_OFF);
97 }
98 }
99
100 /*
101 * Setup windows for PCIe IO+MEM space.
102 */
103 setup_cpu_win(0, KIRKWOOD_PCIE_IO_PHYS_BASE, KIRKWOOD_PCIE_IO_SIZE,
104 TARGET_PCIE, ATTR_PCIE_IO, KIRKWOOD_PCIE_IO_BUS_BASE);
105 setup_cpu_win(1, KIRKWOOD_PCIE_MEM_PHYS_BASE, KIRKWOOD_PCIE_MEM_SIZE,
106 TARGET_PCIE, ATTR_PCIE_MEM, -1);
107
108 /*
109 * Setup window for NAND controller.
110 */
111 setup_cpu_win(2, KIRKWOOD_NAND_MEM_PHYS_BASE, KIRKWOOD_NAND_MEM_SIZE,
112 TARGET_DEV_BUS, ATTR_DEV_NAND, -1);
113
114 /*
115 * Setup MBUS dram target info.
116 */
117 kirkwood_mbus_dram_info.mbus_dram_target_id = TARGET_DDR;
118
119 addr = (void __iomem *)DDR_WINDOW_CPU_BASE;
120
121 for (i = 0, cs = 0; i < 4; i++) {
122 u32 base = readl(addr + DDR_BASE_CS_OFF(i));
123 u32 size = readl(addr + DDR_SIZE_CS_OFF(i));
124
125 /*
126 * Chip select enabled?
127 */
128 if (size & 1) {
129 struct mbus_dram_window *w;
130
131 w = &kirkwood_mbus_dram_info.cs[cs++];
132 w->cs_index = i;
133 w->mbus_attr = 0xf & ~(1 << i);
134 w->base = base & 0xffff0000;
135 w->size = (size | 0x0000ffff) + 1;
136 }
137 }
138 kirkwood_mbus_dram_info.num_cs = cs;
139}
diff --git a/arch/arm/mach-kirkwood/common.c b/arch/arm/mach-kirkwood/common.c
new file mode 100644
index 000000000000..e73384fbbba8
--- /dev/null
+++ b/arch/arm/mach-kirkwood/common.c
@@ -0,0 +1,326 @@
1/*
2 * arch/arm/mach-kirkwood/common.c
3 *
4 * Core functions for Marvell Kirkwood SoCs
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/init.h>
13#include <linux/platform_device.h>
14#include <linux/serial_8250.h>
15#include <linux/mbus.h>
16#include <linux/mv643xx_eth.h>
17#include <linux/ata_platform.h>
18#include <asm/page.h>
19#include <asm/timex.h>
20#include <asm/mach/map.h>
21#include <asm/mach/time.h>
22#include <asm/arch/kirkwood.h>
23#include <asm/plat-orion/cache-feroceon-l2.h>
24#include <asm/plat-orion/ehci-orion.h>
25#include <asm/plat-orion/orion_nand.h>
26#include <asm/plat-orion/time.h>
27#include "common.h"
28
29/*****************************************************************************
30 * I/O Address Mapping
31 ****************************************************************************/
32static struct map_desc kirkwood_io_desc[] __initdata = {
33 {
34 .virtual = KIRKWOOD_PCIE_IO_VIRT_BASE,
35 .pfn = __phys_to_pfn(KIRKWOOD_PCIE_IO_PHYS_BASE),
36 .length = KIRKWOOD_PCIE_IO_SIZE,
37 .type = MT_DEVICE,
38 }, {
39 .virtual = KIRKWOOD_REGS_VIRT_BASE,
40 .pfn = __phys_to_pfn(KIRKWOOD_REGS_PHYS_BASE),
41 .length = KIRKWOOD_REGS_SIZE,
42 .type = MT_DEVICE,
43 },
44};
45
46void __init kirkwood_map_io(void)
47{
48 iotable_init(kirkwood_io_desc, ARRAY_SIZE(kirkwood_io_desc));
49}
50
51
52/*****************************************************************************
53 * EHCI
54 ****************************************************************************/
55static struct orion_ehci_data kirkwood_ehci_data = {
56 .dram = &kirkwood_mbus_dram_info,
57};
58
59static u64 ehci_dmamask = 0xffffffffUL;
60
61
62/*****************************************************************************
63 * EHCI0
64 ****************************************************************************/
65static struct resource kirkwood_ehci_resources[] = {
66 {
67 .start = USB_PHYS_BASE,
68 .end = USB_PHYS_BASE + 0x0fff,
69 .flags = IORESOURCE_MEM,
70 }, {
71 .start = IRQ_KIRKWOOD_USB,
72 .end = IRQ_KIRKWOOD_USB,
73 .flags = IORESOURCE_IRQ,
74 },
75};
76
77static struct platform_device kirkwood_ehci = {
78 .name = "orion-ehci",
79 .id = 0,
80 .dev = {
81 .dma_mask = &ehci_dmamask,
82 .coherent_dma_mask = 0xffffffff,
83 .platform_data = &kirkwood_ehci_data,
84 },
85 .resource = kirkwood_ehci_resources,
86 .num_resources = ARRAY_SIZE(kirkwood_ehci_resources),
87};
88
89void __init kirkwood_ehci_init(void)
90{
91 platform_device_register(&kirkwood_ehci);
92}
93
94
95/*****************************************************************************
96 * GE00
97 ****************************************************************************/
98struct mv643xx_eth_shared_platform_data kirkwood_ge00_shared_data = {
99 .t_clk = KIRKWOOD_TCLK,
100 .dram = &kirkwood_mbus_dram_info,
101};
102
103static struct resource kirkwood_ge00_shared_resources[] = {
104 {
105 .name = "ge00 base",
106 .start = GE00_PHYS_BASE + 0x2000,
107 .end = GE00_PHYS_BASE + 0x3fff,
108 .flags = IORESOURCE_MEM,
109 },
110};
111
112static struct platform_device kirkwood_ge00_shared = {
113 .name = MV643XX_ETH_SHARED_NAME,
114 .id = 0,
115 .dev = {
116 .platform_data = &kirkwood_ge00_shared_data,
117 },
118 .num_resources = 1,
119 .resource = kirkwood_ge00_shared_resources,
120};
121
122static struct resource kirkwood_ge00_resources[] = {
123 {
124 .name = "ge00 irq",
125 .start = IRQ_KIRKWOOD_GE00_SUM,
126 .end = IRQ_KIRKWOOD_GE00_SUM,
127 .flags = IORESOURCE_IRQ,
128 },
129};
130
131static struct platform_device kirkwood_ge00 = {
132 .name = MV643XX_ETH_NAME,
133 .id = 0,
134 .num_resources = 1,
135 .resource = kirkwood_ge00_resources,
136};
137
138void __init kirkwood_ge00_init(struct mv643xx_eth_platform_data *eth_data)
139{
140 eth_data->shared = &kirkwood_ge00_shared;
141 kirkwood_ge00.dev.platform_data = eth_data;
142
143 platform_device_register(&kirkwood_ge00_shared);
144 platform_device_register(&kirkwood_ge00);
145}
146
147
148/*****************************************************************************
149 * SoC RTC
150 ****************************************************************************/
151static struct resource kirkwood_rtc_resource = {
152 .start = RTC_PHYS_BASE,
153 .end = RTC_PHYS_BASE + SZ_16 - 1,
154 .flags = IORESOURCE_MEM,
155};
156
157void __init kirkwood_rtc_init(void)
158{
159 platform_device_register_simple("rtc-mv", -1, &kirkwood_rtc_resource, 1);
160}
161
162
163/*****************************************************************************
164 * SATA
165 ****************************************************************************/
166static struct resource kirkwood_sata_resources[] = {
167 {
168 .name = "sata base",
169 .start = SATA_PHYS_BASE,
170 .end = SATA_PHYS_BASE + 0x5000 - 1,
171 .flags = IORESOURCE_MEM,
172 }, {
173 .name = "sata irq",
174 .start = IRQ_KIRKWOOD_SATA,
175 .end = IRQ_KIRKWOOD_SATA,
176 .flags = IORESOURCE_IRQ,
177 },
178};
179
180static struct platform_device kirkwood_sata = {
181 .name = "sata_mv",
182 .id = 0,
183 .dev = {
184 .coherent_dma_mask = 0xffffffff,
185 },
186 .num_resources = ARRAY_SIZE(kirkwood_sata_resources),
187 .resource = kirkwood_sata_resources,
188};
189
190void __init kirkwood_sata_init(struct mv_sata_platform_data *sata_data)
191{
192 sata_data->dram = &kirkwood_mbus_dram_info;
193 kirkwood_sata.dev.platform_data = sata_data;
194 platform_device_register(&kirkwood_sata);
195}
196
197
198/*****************************************************************************
199 * UART0
200 ****************************************************************************/
201static struct plat_serial8250_port kirkwood_uart0_data[] = {
202 {
203 .mapbase = UART0_PHYS_BASE,
204 .membase = (char *)UART0_VIRT_BASE,
205 .irq = IRQ_KIRKWOOD_UART_0,
206 .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
207 .iotype = UPIO_MEM,
208 .regshift = 2,
209 .uartclk = KIRKWOOD_TCLK,
210 }, {
211 },
212};
213
214static struct resource kirkwood_uart0_resources[] = {
215 {
216 .start = UART0_PHYS_BASE,
217 .end = UART0_PHYS_BASE + 0xff,
218 .flags = IORESOURCE_MEM,
219 }, {
220 .start = IRQ_KIRKWOOD_UART_0,
221 .end = IRQ_KIRKWOOD_UART_0,
222 .flags = IORESOURCE_IRQ,
223 },
224};
225
226static struct platform_device kirkwood_uart0 = {
227 .name = "serial8250",
228 .id = 0,
229 .dev = {
230 .platform_data = kirkwood_uart0_data,
231 },
232 .resource = kirkwood_uart0_resources,
233 .num_resources = ARRAY_SIZE(kirkwood_uart0_resources),
234};
235
236void __init kirkwood_uart0_init(void)
237{
238 platform_device_register(&kirkwood_uart0);
239}
240
241
242/*****************************************************************************
243 * UART1
244 ****************************************************************************/
245static struct plat_serial8250_port kirkwood_uart1_data[] = {
246 {
247 .mapbase = UART1_PHYS_BASE,
248 .membase = (char *)UART1_VIRT_BASE,
249 .irq = IRQ_KIRKWOOD_UART_1,
250 .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
251 .iotype = UPIO_MEM,
252 .regshift = 2,
253 .uartclk = KIRKWOOD_TCLK,
254 }, {
255 },
256};
257
258static struct resource kirkwood_uart1_resources[] = {
259 {
260 .start = UART1_PHYS_BASE,
261 .end = UART1_PHYS_BASE + 0xff,
262 .flags = IORESOURCE_MEM,
263 }, {
264 .start = IRQ_KIRKWOOD_UART_1,
265 .end = IRQ_KIRKWOOD_UART_1,
266 .flags = IORESOURCE_IRQ,
267 },
268};
269
270static struct platform_device kirkwood_uart1 = {
271 .name = "serial8250",
272 .id = 1,
273 .dev = {
274 .platform_data = kirkwood_uart1_data,
275 },
276 .resource = kirkwood_uart1_resources,
277 .num_resources = ARRAY_SIZE(kirkwood_uart1_resources),
278};
279
280void __init kirkwood_uart1_init(void)
281{
282 platform_device_register(&kirkwood_uart1);
283}
284
285
286/*****************************************************************************
287 * Time handling
288 ****************************************************************************/
289static void kirkwood_timer_init(void)
290{
291 orion_time_init(IRQ_KIRKWOOD_BRIDGE, KIRKWOOD_TCLK);
292}
293
294struct sys_timer kirkwood_timer = {
295 .init = kirkwood_timer_init,
296};
297
298
299/*****************************************************************************
300 * General
301 ****************************************************************************/
302static char * __init kirkwood_id(void)
303{
304 switch (readl(DEVICE_ID) & 0x3) {
305 case 0:
306 return "88F6180";
307 case 1:
308 return "88F6192";
309 case 2:
310 return "88F6281";
311 }
312
313 return "unknown 88F6000 variant";
314}
315
316void __init kirkwood_init(void)
317{
318 printk(KERN_INFO "Kirkwood: %s, TCLK=%d.\n",
319 kirkwood_id(), KIRKWOOD_TCLK);
320
321 kirkwood_setup_cpu_mbus();
322
323#ifdef CONFIG_CACHE_FEROCEON_L2
324 feroceon_l2_init(1);
325#endif
326}
diff --git a/arch/arm/mach-kirkwood/common.h b/arch/arm/mach-kirkwood/common.h
new file mode 100644
index 000000000000..5dee2f6b40a5
--- /dev/null
+++ b/arch/arm/mach-kirkwood/common.h
@@ -0,0 +1,42 @@
1/*
2 * arch/arm/mach-kirkwood/common.h
3 *
4 * Core functions for Marvell Kirkwood SoCs
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#ifndef __ARCH_KIRKWOOD_COMMON_H
12#define __ARCH_KIRKWOOD_COMMON_H
13
14struct mv643xx_eth_platform_data;
15struct mv_sata_platform_data;
16
17/*
18 * Basic Kirkwood init functions used early by machine-setup.
19 */
20void kirkwood_map_io(void);
21void kirkwood_init(void);
22void kirkwood_init_irq(void);
23
24extern struct mbus_dram_target_info kirkwood_mbus_dram_info;
25void kirkwood_setup_cpu_mbus(void);
26void kirkwood_setup_pcie_io_win(int window, u32 base, u32 size,
27 int maj, int min);
28void kirkwood_setup_pcie_mem_win(int window, u32 base, u32 size,
29 int maj, int min);
30
31void kirkwood_ehci_init(void);
32void kirkwood_ge00_init(struct mv643xx_eth_platform_data *eth_data);
33void kirkwood_pcie_init(void);
34void kirkwood_rtc_init(void);
35void kirkwood_sata_init(struct mv_sata_platform_data *sata_data);
36void kirkwood_uart0_init(void);
37void kirkwood_uart1_init(void);
38
39extern struct sys_timer kirkwood_timer;
40
41
42#endif
diff --git a/arch/arm/mach-kirkwood/db88f6281-bp-setup.c b/arch/arm/mach-kirkwood/db88f6281-bp-setup.c
new file mode 100644
index 000000000000..d5c482c628e3
--- /dev/null
+++ b/arch/arm/mach-kirkwood/db88f6281-bp-setup.c
@@ -0,0 +1,68 @@
1/*
2 * arch/arm/mach-kirkwood/db88f6281-bp-setup.c
3 *
4 * Marvell DB-88F6281-BP Development Board Setup
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/init.h>
13#include <linux/platform_device.h>
14#include <linux/pci.h>
15#include <linux/irq.h>
16#include <linux/mtd/physmap.h>
17#include <linux/mtd/nand.h>
18#include <linux/timer.h>
19#include <linux/ata_platform.h>
20#include <linux/mv643xx_eth.h>
21#include <asm/mach-types.h>
22#include <asm/mach/arch.h>
23#include <asm/mach/pci.h>
24#include <asm/arch/kirkwood.h>
25#include "common.h"
26
27static struct mv643xx_eth_platform_data db88f6281_ge00_data = {
28 .phy_addr = 8,
29};
30
31static struct mv_sata_platform_data db88f6281_sata_data = {
32 .n_ports = 2,
33};
34
35static void __init db88f6281_init(void)
36{
37 /*
38 * Basic setup. Needs to be called early.
39 */
40 kirkwood_init();
41
42 kirkwood_ehci_init();
43 kirkwood_ge00_init(&db88f6281_ge00_data);
44 kirkwood_rtc_init();
45 kirkwood_sata_init(&db88f6281_sata_data);
46 kirkwood_uart0_init();
47 kirkwood_uart1_init();
48}
49
50static int __init db88f6281_pci_init(void)
51{
52 if (machine_is_db88f6281_bp())
53 kirkwood_pcie_init();
54
55 return 0;
56}
57subsys_initcall(db88f6281_pci_init);
58
59MACHINE_START(DB88F6281_BP, "Marvell DB-88F6281-BP Development Board")
60 /* Maintainer: Saeed Bishara <saeed@marvell.com> */
61 .phys_io = KIRKWOOD_REGS_PHYS_BASE,
62 .io_pg_offst = ((KIRKWOOD_REGS_VIRT_BASE) >> 18) & 0xfffc,
63 .boot_params = 0x00000100,
64 .init_machine = db88f6281_init,
65 .map_io = kirkwood_map_io,
66 .init_irq = kirkwood_init_irq,
67 .timer = &kirkwood_timer,
68MACHINE_END
diff --git a/arch/arm/mach-kirkwood/irq.c b/arch/arm/mach-kirkwood/irq.c
new file mode 100644
index 000000000000..302bb2cf6669
--- /dev/null
+++ b/arch/arm/mach-kirkwood/irq.c
@@ -0,0 +1,22 @@
1/*
2 * arch/arm/mach-kirkwood/irq.c
3 *
4 * Kirkwood IRQ handling.
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/init.h>
13#include <linux/irq.h>
14#include <linux/io.h>
15#include <asm/plat-orion/irq.h>
16#include "common.h"
17
18void __init kirkwood_init_irq(void)
19{
20 orion_irq_init(0, (void __iomem *)(IRQ_VIRT_BASE + IRQ_MASK_LOW_OFF));
21 orion_irq_init(32, (void __iomem *)(IRQ_VIRT_BASE + IRQ_MASK_HIGH_OFF));
22}
diff --git a/arch/arm/mach-kirkwood/pcie.c b/arch/arm/mach-kirkwood/pcie.c
new file mode 100644
index 000000000000..8282d0ff84bf
--- /dev/null
+++ b/arch/arm/mach-kirkwood/pcie.c
@@ -0,0 +1,180 @@
1/*
2 * arch/arm/mach-kirkwood/pcie.c
3 *
4 * PCIe functions for Marvell Kirkwood SoCs
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/pci.h>
13#include <linux/mbus.h>
14#include <asm/mach/pci.h>
15#include <asm/plat-orion/pcie.h>
16#include "common.h"
17
18
19#define PCIE_BASE ((void __iomem *)PCIE_VIRT_BASE)
20
21static int pcie_valid_config(int bus, int dev)
22{
23 /*
24 * Don't go out when trying to access --
25 * 1. nonexisting device on local bus
26 * 2. where there's no device connected (no link)
27 */
28 if (bus == 0 && dev == 0)
29 return 1;
30
31 if (!orion_pcie_link_up(PCIE_BASE))
32 return 0;
33
34 if (bus == 0 && dev != 1)
35 return 0;
36
37 return 1;
38}
39
40
41/*
42 * PCIe config cycles are done by programming the PCIE_CONF_ADDR register
43 * and then reading the PCIE_CONF_DATA register. Need to make sure these
44 * transactions are atomic.
45 */
46static DEFINE_SPINLOCK(kirkwood_pcie_lock);
47
48static int pcie_rd_conf(struct pci_bus *bus, u32 devfn, int where,
49 int size, u32 *val)
50{
51 unsigned long flags;
52 int ret;
53
54 if (pcie_valid_config(bus->number, PCI_SLOT(devfn)) == 0) {
55 *val = 0xffffffff;
56 return PCIBIOS_DEVICE_NOT_FOUND;
57 }
58
59 spin_lock_irqsave(&kirkwood_pcie_lock, flags);
60 ret = orion_pcie_rd_conf(PCIE_BASE, bus, devfn, where, size, val);
61 spin_unlock_irqrestore(&kirkwood_pcie_lock, flags);
62
63 return ret;
64}
65
66static int pcie_wr_conf(struct pci_bus *bus, u32 devfn,
67 int where, int size, u32 val)
68{
69 unsigned long flags;
70 int ret;
71
72 if (pcie_valid_config(bus->number, PCI_SLOT(devfn)) == 0)
73 return PCIBIOS_DEVICE_NOT_FOUND;
74
75 spin_lock_irqsave(&kirkwood_pcie_lock, flags);
76 ret = orion_pcie_wr_conf(PCIE_BASE, bus, devfn, where, size, val);
77 spin_unlock_irqrestore(&kirkwood_pcie_lock, flags);
78
79 return ret;
80}
81
82static struct pci_ops pcie_ops = {
83 .read = pcie_rd_conf,
84 .write = pcie_wr_conf,
85};
86
87
88static int kirkwood_pcie_setup(int nr, struct pci_sys_data *sys)
89{
90 struct resource *res;
91
92 /*
93 * Generic PCIe unit setup.
94 */
95 orion_pcie_setup(PCIE_BASE, &kirkwood_mbus_dram_info);
96
97 /*
98 * Request resources.
99 */
100 res = kzalloc(sizeof(struct resource) * 2, GFP_KERNEL);
101 if (!res)
102 panic("pcie_setup unable to alloc resources");
103
104 /*
105 * IORESOURCE_IO
106 */
107 res[0].name = "PCIe I/O Space";
108 res[0].flags = IORESOURCE_IO;
109 res[0].start = KIRKWOOD_PCIE_IO_PHYS_BASE;
110 res[0].end = res[0].start + KIRKWOOD_PCIE_IO_SIZE - 1;
111 if (request_resource(&ioport_resource, &res[0]))
112 panic("Request PCIe IO resource failed\n");
113 sys->resource[0] = &res[0];
114
115 /*
116 * IORESOURCE_MEM
117 */
118 res[1].name = "PCIe Memory Space";
119 res[1].flags = IORESOURCE_MEM;
120 res[1].start = KIRKWOOD_PCIE_MEM_PHYS_BASE;
121 res[1].end = res[1].start + KIRKWOOD_PCIE_MEM_SIZE - 1;
122 if (request_resource(&iomem_resource, &res[1]))
123 panic("Request PCIe Memory resource failed\n");
124 sys->resource[1] = &res[1];
125
126 sys->resource[2] = NULL;
127 sys->io_offset = 0;
128
129 return 1;
130}
131
132static void __devinit rc_pci_fixup(struct pci_dev *dev)
133{
134 /*
135 * Prevent enumeration of root complex.
136 */
137 if (dev->bus->parent == NULL && dev->devfn == 0) {
138 int i;
139
140 for (i = 0; i < DEVICE_COUNT_RESOURCE; i++) {
141 dev->resource[i].start = 0;
142 dev->resource[i].end = 0;
143 dev->resource[i].flags = 0;
144 }
145 }
146}
147DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_MARVELL, PCI_ANY_ID, rc_pci_fixup);
148
149static struct pci_bus __init *
150kirkwood_pcie_scan_bus(int nr, struct pci_sys_data *sys)
151{
152 struct pci_bus *bus;
153
154 if (nr == 0) {
155 bus = pci_scan_bus(sys->busnr, &pcie_ops, sys);
156 } else {
157 bus = NULL;
158 BUG();
159 }
160
161 return bus;
162}
163
164static int __init kirkwood_pcie_map_irq(struct pci_dev *dev, u8 slot, u8 pin)
165{
166 return IRQ_KIRKWOOD_PCIE;
167}
168
169static struct hw_pci kirkwood_pci __initdata = {
170 .nr_controllers = 1,
171 .swizzle = pci_std_swizzle,
172 .setup = kirkwood_pcie_setup,
173 .scan = kirkwood_pcie_scan_bus,
174 .map_irq = kirkwood_pcie_map_irq,
175};
176
177void __init kirkwood_pcie_init(void)
178{
179 pci_common_init(&kirkwood_pci);
180}
diff --git a/arch/arm/mach-kirkwood/rd88f6192-nas-setup.c b/arch/arm/mach-kirkwood/rd88f6192-nas-setup.c
new file mode 100644
index 000000000000..6cf642c504d3
--- /dev/null
+++ b/arch/arm/mach-kirkwood/rd88f6192-nas-setup.c
@@ -0,0 +1,69 @@
1/*
2 * arch/arm/mach-kirkwood/rd88f6192-nas-setup.c
3 *
4 * Marvell RD-88F6192-NAS Reference Board Setup
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/init.h>
13#include <linux/platform_device.h>
14#include <linux/pci.h>
15#include <linux/irq.h>
16#include <linux/mtd/physmap.h>
17#include <linux/mtd/nand.h>
18#include <linux/timer.h>
19#include <linux/ata_platform.h>
20#include <linux/mv643xx_eth.h>
21#include <asm/mach-types.h>
22#include <asm/mach/arch.h>
23#include <asm/mach/pci.h>
24#include <asm/arch/kirkwood.h>
25#include "common.h"
26
27#define RD88F6192_GPIO_USB_VBUS 10
28
29static struct mv643xx_eth_platform_data rd88f6192_ge00_data = {
30 .phy_addr = 8,
31};
32
33static struct mv_sata_platform_data rd88f6192_sata_data = {
34 .n_ports = 2,
35};
36
37static void __init rd88f6192_init(void)
38{
39 /*
40 * Basic setup. Needs to be called early.
41 */
42 kirkwood_init();
43
44 kirkwood_ehci_init();
45 kirkwood_ge00_init(&rd88f6192_ge00_data);
46 kirkwood_rtc_init();
47 kirkwood_sata_init(&rd88f6192_sata_data);
48 kirkwood_uart0_init();
49}
50
51static int __init rd88f6192_pci_init(void)
52{
53 if (machine_is_rd88f6192_nas())
54 kirkwood_pcie_init();
55
56 return 0;
57}
58subsys_initcall(rd88f6192_pci_init);
59
60MACHINE_START(RD88F6192_NAS, "Marvell RD-88F6192-NAS Development Board")
61 /* Maintainer: Saeed Bishara <saeed@marvell.com> */
62 .phys_io = KIRKWOOD_REGS_PHYS_BASE,
63 .io_pg_offst = ((KIRKWOOD_REGS_VIRT_BASE) >> 18) & 0xfffc,
64 .boot_params = 0x00000100,
65 .init_machine = rd88f6192_init,
66 .map_io = kirkwood_map_io,
67 .init_irq = kirkwood_init_irq,
68 .timer = &kirkwood_timer,
69MACHINE_END
diff --git a/arch/arm/mach-kirkwood/rd88f6281-setup.c b/arch/arm/mach-kirkwood/rd88f6281-setup.c
new file mode 100644
index 000000000000..fe8b242d2060
--- /dev/null
+++ b/arch/arm/mach-kirkwood/rd88f6281-setup.c
@@ -0,0 +1,112 @@
1/*
2 * arch/arm/mach-kirkwood/rd88f6281-setup.c
3 *
4 * Marvell RD-88F6281 Reference Board Setup
5 *
6 * This file is licensed under the terms of the GNU General Public
7 * License version 2. This program is licensed "as is" without any
8 * warranty of any kind, whether express or implied.
9 */
10
11#include <linux/kernel.h>
12#include <linux/init.h>
13#include <linux/platform_device.h>
14#include <linux/pci.h>
15#include <linux/irq.h>
16#include <linux/mtd/physmap.h>
17#include <linux/mtd/nand.h>
18#include <linux/timer.h>
19#include <linux/ata_platform.h>
20#include <linux/mv643xx_eth.h>
21#include <asm/mach-types.h>
22#include <asm/mach/arch.h>
23#include <asm/mach/pci.h>
24#include <asm/arch/kirkwood.h>
25#include <asm/plat-orion/orion_nand.h>
26#include "common.h"
27
28static struct mtd_partition rd88f6281_nand_parts[] = {
29 {
30 .name = "u-boot",
31 .offset = 0,
32 .size = SZ_1M
33 }, {
34 .name = "uImage",
35 .offset = MTDPART_OFS_NXTBLK,
36 .size = SZ_2M
37 }, {
38 .name = "root",
39 .offset = MTDPART_OFS_NXTBLK,
40 .size = MTDPART_SIZ_FULL
41 },
42};
43
44static struct resource rd88f6281_nand_resource = {
45 .flags = IORESOURCE_MEM,
46 .start = KIRKWOOD_NAND_MEM_PHYS_BASE,
47 .end = KIRKWOOD_NAND_MEM_PHYS_BASE +
48 KIRKWOOD_NAND_MEM_SIZE - 1,
49};
50
51static struct orion_nand_data rd88f6281_nand_data = {
52 .parts = rd88f6281_nand_parts,
53 .nr_parts = ARRAY_SIZE(rd88f6281_nand_parts),
54 .cle = 0,
55 .ale = 1,
56 .width = 8,
57};
58
59static struct platform_device rd88f6281_nand_flash = {
60 .name = "orion_nand",
61 .id = -1,
62 .dev = {
63 .platform_data = &rd88f6281_nand_data,
64 },
65 .resource = &rd88f6281_nand_resource,
66 .num_resources = 1,
67};
68
69static struct mv643xx_eth_platform_data rd88f6281_ge00_data = {
70 .phy_addr = -1,
71};
72
73static struct mv_sata_platform_data rd88f6281_sata_data = {
74 .n_ports = 2,
75};
76
77static void __init rd88f6281_init(void)
78{
79 /*
80 * Basic setup. Needs to be called early.
81 */
82 kirkwood_init();
83
84 kirkwood_ehci_init();
85 kirkwood_ge00_init(&rd88f6281_ge00_data);
86 kirkwood_rtc_init();
87 kirkwood_sata_init(&rd88f6281_sata_data);
88 kirkwood_uart0_init();
89 kirkwood_uart1_init();
90
91 platform_device_register(&rd88f6281_nand_flash);
92}
93
94static int __init rd88f6281_pci_init(void)
95{
96 if (machine_is_rd88f6281())
97 kirkwood_pcie_init();
98
99 return 0;
100}
101subsys_initcall(rd88f6281_pci_init);
102
103MACHINE_START(RD88F6281, "Marvell RD-88F6281 Reference Board")
104 /* Maintainer: Saeed Bishara <saeed@marvell.com> */
105 .phys_io = KIRKWOOD_REGS_PHYS_BASE,
106 .io_pg_offst = ((KIRKWOOD_REGS_VIRT_BASE) >> 18) & 0xfffc,
107 .boot_params = 0x00000100,
108 .init_machine = rd88f6281_init,
109 .map_io = kirkwood_map_io,
110 .init_irq = kirkwood_init_irq,
111 .timer = &kirkwood_timer,
112MACHINE_END