2 * arch/arm/mach-kirkwood/common.c
4 * Core functions for Marvell Kirkwood SoCs
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.
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 <linux/spi/orion_spi.h>
21 #include <asm/timex.h>
22 #include <asm/mach/map.h>
23 #include <asm/mach/time.h>
24 #include <mach/kirkwood.h>
25 #include <plat/cache-feroceon-l2.h>
26 #include <plat/ehci-orion.h>
27 #include <plat/mv_xor.h>
28 #include <plat/orion_nand.h>
29 #include <plat/time.h>
32 /*****************************************************************************
34 ****************************************************************************/
35 static struct map_desc kirkwood_io_desc
[] __initdata
= {
37 .virtual = KIRKWOOD_PCIE_IO_VIRT_BASE
,
38 .pfn
= __phys_to_pfn(KIRKWOOD_PCIE_IO_PHYS_BASE
),
39 .length
= KIRKWOOD_PCIE_IO_SIZE
,
42 .virtual = KIRKWOOD_REGS_VIRT_BASE
,
43 .pfn
= __phys_to_pfn(KIRKWOOD_REGS_PHYS_BASE
),
44 .length
= KIRKWOOD_REGS_SIZE
,
49 void __init
kirkwood_map_io(void)
51 iotable_init(kirkwood_io_desc
, ARRAY_SIZE(kirkwood_io_desc
));
55 /*****************************************************************************
57 ****************************************************************************/
58 static struct orion_ehci_data kirkwood_ehci_data
= {
59 .dram
= &kirkwood_mbus_dram_info
,
60 .phy_version
= EHCI_PHY_NA
,
63 static u64 ehci_dmamask
= 0xffffffffUL
;
66 /*****************************************************************************
68 ****************************************************************************/
69 static struct resource kirkwood_ehci_resources
[] = {
71 .start
= USB_PHYS_BASE
,
72 .end
= USB_PHYS_BASE
+ 0x0fff,
73 .flags
= IORESOURCE_MEM
,
75 .start
= IRQ_KIRKWOOD_USB
,
76 .end
= IRQ_KIRKWOOD_USB
,
77 .flags
= IORESOURCE_IRQ
,
81 static struct platform_device kirkwood_ehci
= {
85 .dma_mask
= &ehci_dmamask
,
86 .coherent_dma_mask
= 0xffffffff,
87 .platform_data
= &kirkwood_ehci_data
,
89 .resource
= kirkwood_ehci_resources
,
90 .num_resources
= ARRAY_SIZE(kirkwood_ehci_resources
),
93 void __init
kirkwood_ehci_init(void)
95 platform_device_register(&kirkwood_ehci
);
99 /*****************************************************************************
101 ****************************************************************************/
102 struct mv643xx_eth_shared_platform_data kirkwood_ge00_shared_data
= {
103 .dram
= &kirkwood_mbus_dram_info
,
106 static struct resource kirkwood_ge00_shared_resources
[] = {
109 .start
= GE00_PHYS_BASE
+ 0x2000,
110 .end
= GE00_PHYS_BASE
+ 0x3fff,
111 .flags
= IORESOURCE_MEM
,
113 .name
= "ge00 err irq",
114 .start
= IRQ_KIRKWOOD_GE00_ERR
,
115 .end
= IRQ_KIRKWOOD_GE00_ERR
,
116 .flags
= IORESOURCE_IRQ
,
120 static struct platform_device kirkwood_ge00_shared
= {
121 .name
= MV643XX_ETH_SHARED_NAME
,
124 .platform_data
= &kirkwood_ge00_shared_data
,
126 .num_resources
= ARRAY_SIZE(kirkwood_ge00_shared_resources
),
127 .resource
= kirkwood_ge00_shared_resources
,
130 static struct resource kirkwood_ge00_resources
[] = {
133 .start
= IRQ_KIRKWOOD_GE00_SUM
,
134 .end
= IRQ_KIRKWOOD_GE00_SUM
,
135 .flags
= IORESOURCE_IRQ
,
139 static struct platform_device kirkwood_ge00
= {
140 .name
= MV643XX_ETH_NAME
,
143 .resource
= kirkwood_ge00_resources
,
146 void __init
kirkwood_ge00_init(struct mv643xx_eth_platform_data
*eth_data
)
148 eth_data
->shared
= &kirkwood_ge00_shared
;
149 kirkwood_ge00
.dev
.platform_data
= eth_data
;
151 platform_device_register(&kirkwood_ge00_shared
);
152 platform_device_register(&kirkwood_ge00
);
156 /*****************************************************************************
158 ****************************************************************************/
159 struct mv643xx_eth_shared_platform_data kirkwood_ge01_shared_data
= {
160 .dram
= &kirkwood_mbus_dram_info
,
161 .shared_smi
= &kirkwood_ge00_shared
,
164 static struct resource kirkwood_ge01_shared_resources
[] = {
167 .start
= GE01_PHYS_BASE
+ 0x2000,
168 .end
= GE01_PHYS_BASE
+ 0x3fff,
169 .flags
= IORESOURCE_MEM
,
171 .name
= "ge01 err irq",
172 .start
= IRQ_KIRKWOOD_GE01_ERR
,
173 .end
= IRQ_KIRKWOOD_GE01_ERR
,
174 .flags
= IORESOURCE_IRQ
,
178 static struct platform_device kirkwood_ge01_shared
= {
179 .name
= MV643XX_ETH_SHARED_NAME
,
182 .platform_data
= &kirkwood_ge01_shared_data
,
184 .num_resources
= ARRAY_SIZE(kirkwood_ge01_shared_resources
),
185 .resource
= kirkwood_ge01_shared_resources
,
188 static struct resource kirkwood_ge01_resources
[] = {
191 .start
= IRQ_KIRKWOOD_GE01_SUM
,
192 .end
= IRQ_KIRKWOOD_GE01_SUM
,
193 .flags
= IORESOURCE_IRQ
,
197 static struct platform_device kirkwood_ge01
= {
198 .name
= MV643XX_ETH_NAME
,
201 .resource
= kirkwood_ge01_resources
,
204 void __init
kirkwood_ge01_init(struct mv643xx_eth_platform_data
*eth_data
)
206 eth_data
->shared
= &kirkwood_ge01_shared
;
207 kirkwood_ge01
.dev
.platform_data
= eth_data
;
209 platform_device_register(&kirkwood_ge01_shared
);
210 platform_device_register(&kirkwood_ge01
);
214 /*****************************************************************************
216 ****************************************************************************/
217 static struct resource kirkwood_switch_resources
[] = {
221 .flags
= IORESOURCE_IRQ
,
225 static struct platform_device kirkwood_switch_device
= {
229 .resource
= kirkwood_switch_resources
,
232 void __init
kirkwood_ge00_switch_init(struct dsa_platform_data
*d
, int irq
)
235 kirkwood_switch_resources
[0].start
= irq
;
236 kirkwood_switch_resources
[0].end
= irq
;
237 kirkwood_switch_device
.num_resources
= 1;
240 d
->mii_bus
= &kirkwood_ge00_shared
.dev
;
241 d
->netdev
= &kirkwood_ge00
.dev
;
242 kirkwood_switch_device
.dev
.platform_data
= d
;
244 platform_device_register(&kirkwood_switch_device
);
248 /*****************************************************************************
250 ****************************************************************************/
251 static struct resource kirkwood_rtc_resource
= {
252 .start
= RTC_PHYS_BASE
,
253 .end
= RTC_PHYS_BASE
+ SZ_16
- 1,
254 .flags
= IORESOURCE_MEM
,
257 void __init
kirkwood_rtc_init(void)
259 platform_device_register_simple("rtc-mv", -1, &kirkwood_rtc_resource
, 1);
263 /*****************************************************************************
265 ****************************************************************************/
266 static struct resource kirkwood_sata_resources
[] = {
269 .start
= SATA_PHYS_BASE
,
270 .end
= SATA_PHYS_BASE
+ 0x5000 - 1,
271 .flags
= IORESOURCE_MEM
,
274 .start
= IRQ_KIRKWOOD_SATA
,
275 .end
= IRQ_KIRKWOOD_SATA
,
276 .flags
= IORESOURCE_IRQ
,
280 static struct platform_device kirkwood_sata
= {
284 .coherent_dma_mask
= 0xffffffff,
286 .num_resources
= ARRAY_SIZE(kirkwood_sata_resources
),
287 .resource
= kirkwood_sata_resources
,
290 void __init
kirkwood_sata_init(struct mv_sata_platform_data
*sata_data
)
292 sata_data
->dram
= &kirkwood_mbus_dram_info
;
293 kirkwood_sata
.dev
.platform_data
= sata_data
;
294 platform_device_register(&kirkwood_sata
);
298 /*****************************************************************************
300 ****************************************************************************/
301 static struct orion_spi_info kirkwood_spi_plat_data
= {
304 static struct resource kirkwood_spi_resources
[] = {
306 .start
= SPI_PHYS_BASE
,
307 .end
= SPI_PHYS_BASE
+ SZ_512
- 1,
308 .flags
= IORESOURCE_MEM
,
312 static struct platform_device kirkwood_spi
= {
315 .resource
= kirkwood_spi_resources
,
317 .platform_data
= &kirkwood_spi_plat_data
,
319 .num_resources
= ARRAY_SIZE(kirkwood_spi_resources
),
322 void __init
kirkwood_spi_init()
324 platform_device_register(&kirkwood_spi
);
328 /*****************************************************************************
330 ****************************************************************************/
331 static struct plat_serial8250_port kirkwood_uart0_data
[] = {
333 .mapbase
= UART0_PHYS_BASE
,
334 .membase
= (char *)UART0_VIRT_BASE
,
335 .irq
= IRQ_KIRKWOOD_UART_0
,
336 .flags
= UPF_SKIP_TEST
| UPF_BOOT_AUTOCONF
,
344 static struct resource kirkwood_uart0_resources
[] = {
346 .start
= UART0_PHYS_BASE
,
347 .end
= UART0_PHYS_BASE
+ 0xff,
348 .flags
= IORESOURCE_MEM
,
350 .start
= IRQ_KIRKWOOD_UART_0
,
351 .end
= IRQ_KIRKWOOD_UART_0
,
352 .flags
= IORESOURCE_IRQ
,
356 static struct platform_device kirkwood_uart0
= {
357 .name
= "serial8250",
360 .platform_data
= kirkwood_uart0_data
,
362 .resource
= kirkwood_uart0_resources
,
363 .num_resources
= ARRAY_SIZE(kirkwood_uart0_resources
),
366 void __init
kirkwood_uart0_init(void)
368 platform_device_register(&kirkwood_uart0
);
372 /*****************************************************************************
374 ****************************************************************************/
375 static struct plat_serial8250_port kirkwood_uart1_data
[] = {
377 .mapbase
= UART1_PHYS_BASE
,
378 .membase
= (char *)UART1_VIRT_BASE
,
379 .irq
= IRQ_KIRKWOOD_UART_1
,
380 .flags
= UPF_SKIP_TEST
| UPF_BOOT_AUTOCONF
,
388 static struct resource kirkwood_uart1_resources
[] = {
390 .start
= UART1_PHYS_BASE
,
391 .end
= UART1_PHYS_BASE
+ 0xff,
392 .flags
= IORESOURCE_MEM
,
394 .start
= IRQ_KIRKWOOD_UART_1
,
395 .end
= IRQ_KIRKWOOD_UART_1
,
396 .flags
= IORESOURCE_IRQ
,
400 static struct platform_device kirkwood_uart1
= {
401 .name
= "serial8250",
404 .platform_data
= kirkwood_uart1_data
,
406 .resource
= kirkwood_uart1_resources
,
407 .num_resources
= ARRAY_SIZE(kirkwood_uart1_resources
),
410 void __init
kirkwood_uart1_init(void)
412 platform_device_register(&kirkwood_uart1
);
416 /*****************************************************************************
418 ****************************************************************************/
419 static struct mv_xor_platform_shared_data kirkwood_xor_shared_data
= {
420 .dram
= &kirkwood_mbus_dram_info
,
423 static u64 kirkwood_xor_dmamask
= DMA_32BIT_MASK
;
426 /*****************************************************************************
428 ****************************************************************************/
429 static struct resource kirkwood_xor0_shared_resources
[] = {
432 .start
= XOR0_PHYS_BASE
,
433 .end
= XOR0_PHYS_BASE
+ 0xff,
434 .flags
= IORESOURCE_MEM
,
436 .name
= "xor 0 high",
437 .start
= XOR0_HIGH_PHYS_BASE
,
438 .end
= XOR0_HIGH_PHYS_BASE
+ 0xff,
439 .flags
= IORESOURCE_MEM
,
443 static struct platform_device kirkwood_xor0_shared
= {
444 .name
= MV_XOR_SHARED_NAME
,
447 .platform_data
= &kirkwood_xor_shared_data
,
449 .num_resources
= ARRAY_SIZE(kirkwood_xor0_shared_resources
),
450 .resource
= kirkwood_xor0_shared_resources
,
453 static struct resource kirkwood_xor00_resources
[] = {
455 .start
= IRQ_KIRKWOOD_XOR_00
,
456 .end
= IRQ_KIRKWOOD_XOR_00
,
457 .flags
= IORESOURCE_IRQ
,
461 static struct mv_xor_platform_data kirkwood_xor00_data
= {
462 .shared
= &kirkwood_xor0_shared
,
464 .pool_size
= PAGE_SIZE
,
467 static struct platform_device kirkwood_xor00_channel
= {
470 .num_resources
= ARRAY_SIZE(kirkwood_xor00_resources
),
471 .resource
= kirkwood_xor00_resources
,
473 .dma_mask
= &kirkwood_xor_dmamask
,
474 .coherent_dma_mask
= DMA_64BIT_MASK
,
475 .platform_data
= (void *)&kirkwood_xor00_data
,
479 static struct resource kirkwood_xor01_resources
[] = {
481 .start
= IRQ_KIRKWOOD_XOR_01
,
482 .end
= IRQ_KIRKWOOD_XOR_01
,
483 .flags
= IORESOURCE_IRQ
,
487 static struct mv_xor_platform_data kirkwood_xor01_data
= {
488 .shared
= &kirkwood_xor0_shared
,
490 .pool_size
= PAGE_SIZE
,
493 static struct platform_device kirkwood_xor01_channel
= {
496 .num_resources
= ARRAY_SIZE(kirkwood_xor01_resources
),
497 .resource
= kirkwood_xor01_resources
,
499 .dma_mask
= &kirkwood_xor_dmamask
,
500 .coherent_dma_mask
= DMA_64BIT_MASK
,
501 .platform_data
= (void *)&kirkwood_xor01_data
,
505 void __init
kirkwood_xor0_init(void)
507 platform_device_register(&kirkwood_xor0_shared
);
510 * two engines can't do memset simultaneously, this limitation
511 * satisfied by removing memset support from one of the engines.
513 dma_cap_set(DMA_MEMCPY
, kirkwood_xor00_data
.cap_mask
);
514 dma_cap_set(DMA_XOR
, kirkwood_xor00_data
.cap_mask
);
515 platform_device_register(&kirkwood_xor00_channel
);
517 dma_cap_set(DMA_MEMCPY
, kirkwood_xor01_data
.cap_mask
);
518 dma_cap_set(DMA_MEMSET
, kirkwood_xor01_data
.cap_mask
);
519 dma_cap_set(DMA_XOR
, kirkwood_xor01_data
.cap_mask
);
520 platform_device_register(&kirkwood_xor01_channel
);
524 /*****************************************************************************
526 ****************************************************************************/
527 static struct resource kirkwood_xor1_shared_resources
[] = {
530 .start
= XOR1_PHYS_BASE
,
531 .end
= XOR1_PHYS_BASE
+ 0xff,
532 .flags
= IORESOURCE_MEM
,
534 .name
= "xor 1 high",
535 .start
= XOR1_HIGH_PHYS_BASE
,
536 .end
= XOR1_HIGH_PHYS_BASE
+ 0xff,
537 .flags
= IORESOURCE_MEM
,
541 static struct platform_device kirkwood_xor1_shared
= {
542 .name
= MV_XOR_SHARED_NAME
,
545 .platform_data
= &kirkwood_xor_shared_data
,
547 .num_resources
= ARRAY_SIZE(kirkwood_xor1_shared_resources
),
548 .resource
= kirkwood_xor1_shared_resources
,
551 static struct resource kirkwood_xor10_resources
[] = {
553 .start
= IRQ_KIRKWOOD_XOR_10
,
554 .end
= IRQ_KIRKWOOD_XOR_10
,
555 .flags
= IORESOURCE_IRQ
,
559 static struct mv_xor_platform_data kirkwood_xor10_data
= {
560 .shared
= &kirkwood_xor1_shared
,
562 .pool_size
= PAGE_SIZE
,
565 static struct platform_device kirkwood_xor10_channel
= {
568 .num_resources
= ARRAY_SIZE(kirkwood_xor10_resources
),
569 .resource
= kirkwood_xor10_resources
,
571 .dma_mask
= &kirkwood_xor_dmamask
,
572 .coherent_dma_mask
= DMA_64BIT_MASK
,
573 .platform_data
= (void *)&kirkwood_xor10_data
,
577 static struct resource kirkwood_xor11_resources
[] = {
579 .start
= IRQ_KIRKWOOD_XOR_11
,
580 .end
= IRQ_KIRKWOOD_XOR_11
,
581 .flags
= IORESOURCE_IRQ
,
585 static struct mv_xor_platform_data kirkwood_xor11_data
= {
586 .shared
= &kirkwood_xor1_shared
,
588 .pool_size
= PAGE_SIZE
,
591 static struct platform_device kirkwood_xor11_channel
= {
594 .num_resources
= ARRAY_SIZE(kirkwood_xor11_resources
),
595 .resource
= kirkwood_xor11_resources
,
597 .dma_mask
= &kirkwood_xor_dmamask
,
598 .coherent_dma_mask
= DMA_64BIT_MASK
,
599 .platform_data
= (void *)&kirkwood_xor11_data
,
603 void __init
kirkwood_xor1_init(void)
605 platform_device_register(&kirkwood_xor1_shared
);
608 * two engines can't do memset simultaneously, this limitation
609 * satisfied by removing memset support from one of the engines.
611 dma_cap_set(DMA_MEMCPY
, kirkwood_xor10_data
.cap_mask
);
612 dma_cap_set(DMA_XOR
, kirkwood_xor10_data
.cap_mask
);
613 platform_device_register(&kirkwood_xor10_channel
);
615 dma_cap_set(DMA_MEMCPY
, kirkwood_xor11_data
.cap_mask
);
616 dma_cap_set(DMA_MEMSET
, kirkwood_xor11_data
.cap_mask
);
617 dma_cap_set(DMA_XOR
, kirkwood_xor11_data
.cap_mask
);
618 platform_device_register(&kirkwood_xor11_channel
);
622 /*****************************************************************************
624 ****************************************************************************/
627 int __init
kirkwood_find_tclk(void)
631 kirkwood_pcie_id(&dev
, &rev
);
632 if (dev
== MV88F6281_DEV_ID
&& rev
== MV88F6281_REV_A0
)
638 static void kirkwood_timer_init(void)
640 kirkwood_tclk
= kirkwood_find_tclk();
641 orion_time_init(IRQ_KIRKWOOD_BRIDGE
, kirkwood_tclk
);
644 struct sys_timer kirkwood_timer
= {
645 .init
= kirkwood_timer_init
,
649 /*****************************************************************************
651 ****************************************************************************/
653 * Identify device ID and revision.
655 static char * __init
kirkwood_id(void)
659 kirkwood_pcie_id(&dev
, &rev
);
661 if (dev
== MV88F6281_DEV_ID
) {
662 if (rev
== MV88F6281_REV_Z0
)
663 return "MV88F6281-Z0";
664 else if (rev
== MV88F6281_REV_A0
)
665 return "MV88F6281-A0";
667 return "MV88F6281-Rev-Unsupported";
668 } else if (dev
== MV88F6192_DEV_ID
) {
669 if (rev
== MV88F6192_REV_Z0
)
670 return "MV88F6192-Z0";
671 else if (rev
== MV88F6192_REV_A0
)
672 return "MV88F6192-A0";
674 return "MV88F6192-Rev-Unsupported";
675 } else if (dev
== MV88F6180_DEV_ID
) {
676 if (rev
== MV88F6180_REV_A0
)
677 return "MV88F6180-Rev-A0";
679 return "MV88F6180-Rev-Unsupported";
681 return "Device-Unknown";
685 static void __init
kirkwood_l2_init(void)
687 #ifdef CONFIG_CACHE_FEROCEON_L2_WRITETHROUGH
688 writel(readl(L2_CONFIG_REG
) | L2_WRITETHROUGH
, L2_CONFIG_REG
);
691 writel(readl(L2_CONFIG_REG
) & ~L2_WRITETHROUGH
, L2_CONFIG_REG
);
696 void __init
kirkwood_init(void)
698 printk(KERN_INFO
"Kirkwood: %s, TCLK=%d.\n",
699 kirkwood_id(), kirkwood_tclk
);
700 kirkwood_ge00_shared_data
.t_clk
= kirkwood_tclk
;
701 kirkwood_ge01_shared_data
.t_clk
= kirkwood_tclk
;
702 kirkwood_spi_plat_data
.tclk
= kirkwood_tclk
;
703 kirkwood_uart0_data
[0].uartclk
= kirkwood_tclk
;
704 kirkwood_uart1_data
[0].uartclk
= kirkwood_tclk
;
706 kirkwood_setup_cpu_mbus();
708 #ifdef CONFIG_CACHE_FEROCEON_L2