blob: 65022094747a91dc1d9a1af1cf50eb32e46de197 [file] [log] [blame]
Andrew Lunn28a2b452011-05-15 13:32:41 +02001/*
2 * arch/arm/plat-orion/common.c
3 *
4 * Marvell Orion SoC common setup code used by multiple mach-/common.c
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>
Andrew Lunn7e3819d2011-05-15 13:32:44 +020014#include <linux/dma-mapping.h>
Andrew Lunn28a2b452011-05-15 13:32:41 +020015#include <linux/serial_8250.h>
Andrew Lunn7e3819d2011-05-15 13:32:44 +020016#include <linux/mbus.h>
17#include <linux/mv643xx_eth.h>
Andrew Lunnaac7ffa2011-05-15 13:32:45 +020018#include <linux/mv643xx_i2c.h>
Andrew Lunn7e3819d2011-05-15 13:32:44 +020019#include <net/dsa.h>
Andrew Lunn980f9f62011-05-15 13:32:46 +020020#include <linux/spi/orion_spi.h>
Andrew Lunn5e00d372011-05-15 13:32:47 +020021#include <plat/orion_wdt.h>
Andrew Lunn28a2b452011-05-15 13:32:41 +020022
23/* Fill in the resources structure and link it into the platform
24 device structure. There is always a memory region, and nearly
25 always an interrupt.*/
26static void fill_resources(struct platform_device *device,
27 struct resource *resources,
28 resource_size_t mapbase,
29 resource_size_t size,
30 unsigned int irq)
31{
32 device->resource = resources;
33 device->num_resources = 1;
34 resources[0].flags = IORESOURCE_MEM;
35 resources[0].start = mapbase;
36 resources[0].end = mapbase + size;
37
38 if (irq != NO_IRQ) {
39 device->num_resources++;
40 resources[1].flags = IORESOURCE_IRQ;
41 resources[1].start = irq;
42 resources[1].end = irq;
43 }
44}
45
46/*****************************************************************************
47 * UART
48 ****************************************************************************/
49static void __init uart_complete(
50 struct platform_device *orion_uart,
51 struct plat_serial8250_port *data,
52 struct resource *resources,
53 unsigned int membase,
54 resource_size_t mapbase,
55 unsigned int irq,
56 unsigned int uartclk)
57{
58 data->mapbase = mapbase;
59 data->membase = (void __iomem *)membase;
60 data->irq = irq;
61 data->uartclk = uartclk;
62 orion_uart->dev.platform_data = data;
63
64 fill_resources(orion_uart, resources, mapbase, 0xff, irq);
65 platform_device_register(orion_uart);
66}
67
68/*****************************************************************************
69 * UART0
70 ****************************************************************************/
71static struct plat_serial8250_port orion_uart0_data[] = {
72 {
73 .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
74 .iotype = UPIO_MEM,
75 .regshift = 2,
76 }, {
77 },
78};
79
80static struct resource orion_uart0_resources[2];
81
82static struct platform_device orion_uart0 = {
83 .name = "serial8250",
84 .id = PLAT8250_DEV_PLATFORM,
85};
86
87void __init orion_uart0_init(unsigned int membase,
88 resource_size_t mapbase,
89 unsigned int irq,
90 unsigned int uartclk)
91{
92 uart_complete(&orion_uart0, orion_uart0_data, orion_uart0_resources,
93 membase, mapbase, irq, uartclk);
94}
95
96/*****************************************************************************
97 * UART1
98 ****************************************************************************/
99static struct plat_serial8250_port orion_uart1_data[] = {
100 {
101 .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
102 .iotype = UPIO_MEM,
103 .regshift = 2,
104 }, {
105 },
106};
107
108static struct resource orion_uart1_resources[2];
109
110static struct platform_device orion_uart1 = {
111 .name = "serial8250",
112 .id = PLAT8250_DEV_PLATFORM1,
113};
114
115void __init orion_uart1_init(unsigned int membase,
116 resource_size_t mapbase,
117 unsigned int irq,
118 unsigned int uartclk)
119{
120 uart_complete(&orion_uart1, orion_uart1_data, orion_uart1_resources,
121 membase, mapbase, irq, uartclk);
122}
123
124/*****************************************************************************
125 * UART2
126 ****************************************************************************/
127static struct plat_serial8250_port orion_uart2_data[] = {
128 {
129 .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
130 .iotype = UPIO_MEM,
131 .regshift = 2,
132 }, {
133 },
134};
135
136static struct resource orion_uart2_resources[2];
137
138static struct platform_device orion_uart2 = {
139 .name = "serial8250",
140 .id = PLAT8250_DEV_PLATFORM2,
141};
142
143void __init orion_uart2_init(unsigned int membase,
144 resource_size_t mapbase,
145 unsigned int irq,
146 unsigned int uartclk)
147{
148 uart_complete(&orion_uart2, orion_uart2_data, orion_uart2_resources,
149 membase, mapbase, irq, uartclk);
150}
151
152/*****************************************************************************
153 * UART3
154 ****************************************************************************/
155static struct plat_serial8250_port orion_uart3_data[] = {
156 {
157 .flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF,
158 .iotype = UPIO_MEM,
159 .regshift = 2,
160 }, {
161 },
162};
163
164static struct resource orion_uart3_resources[2];
165
166static struct platform_device orion_uart3 = {
167 .name = "serial8250",
168 .id = 3,
169};
170
171void __init orion_uart3_init(unsigned int membase,
172 resource_size_t mapbase,
173 unsigned int irq,
174 unsigned int uartclk)
175{
176 uart_complete(&orion_uart3, orion_uart3_data, orion_uart3_resources,
177 membase, mapbase, irq, uartclk);
178}
Andrew Lunnf6eaccb2011-05-15 13:32:42 +0200179
180/*****************************************************************************
181 * SoC RTC
182 ****************************************************************************/
183static struct resource orion_rtc_resource[2];
184
185void __init orion_rtc_init(unsigned long mapbase,
186 unsigned long irq)
187{
188 orion_rtc_resource[0].start = mapbase;
189 orion_rtc_resource[0].end = mapbase + SZ_32 - 1;
190 orion_rtc_resource[0].flags = IORESOURCE_MEM;
191 orion_rtc_resource[1].start = irq;
192 orion_rtc_resource[1].end = irq;
193 orion_rtc_resource[1].flags = IORESOURCE_IRQ;
194
195 platform_device_register_simple("rtc-mv", -1, orion_rtc_resource, 2);
196}
Andrew Lunn7e3819d2011-05-15 13:32:44 +0200197
198/*****************************************************************************
199 * GE
200 ****************************************************************************/
201static __init void ge_complete(
202 struct mv643xx_eth_shared_platform_data *orion_ge_shared_data,
203 struct mbus_dram_target_info *mbus_dram_info, int tclk,
204 struct resource *orion_ge_resource, unsigned long irq,
205 struct platform_device *orion_ge_shared,
206 struct mv643xx_eth_platform_data *eth_data,
207 struct platform_device *orion_ge)
208{
209 orion_ge_shared_data->dram = mbus_dram_info;
210 orion_ge_shared_data->t_clk = tclk;
211 orion_ge_resource->start = irq;
212 orion_ge_resource->end = irq;
213 eth_data->shared = orion_ge_shared;
214 orion_ge->dev.platform_data = eth_data;
215
216 platform_device_register(orion_ge_shared);
217 platform_device_register(orion_ge);
218}
219
220/*****************************************************************************
221 * GE00
222 ****************************************************************************/
223struct mv643xx_eth_shared_platform_data orion_ge00_shared_data;
224
225static struct resource orion_ge00_shared_resources[] = {
226 {
227 .name = "ge00 base",
228 }, {
229 .name = "ge00 err irq",
230 },
231};
232
233static struct platform_device orion_ge00_shared = {
234 .name = MV643XX_ETH_SHARED_NAME,
235 .id = 0,
236 .dev = {
237 .platform_data = &orion_ge00_shared_data,
238 },
239};
240
241static struct resource orion_ge00_resources[] = {
242 {
243 .name = "ge00 irq",
244 .flags = IORESOURCE_IRQ,
245 },
246};
247
248static struct platform_device orion_ge00 = {
249 .name = MV643XX_ETH_NAME,
250 .id = 0,
251 .num_resources = 1,
252 .resource = orion_ge00_resources,
253 .dev = {
254 .coherent_dma_mask = DMA_BIT_MASK(32),
255 },
256};
257
258void __init orion_ge00_init(struct mv643xx_eth_platform_data *eth_data,
259 struct mbus_dram_target_info *mbus_dram_info,
260 unsigned long mapbase,
261 unsigned long irq,
262 unsigned long irq_err,
263 int tclk)
264{
265 fill_resources(&orion_ge00_shared, orion_ge00_shared_resources,
266 mapbase + 0x2000, SZ_16K - 1, irq_err);
267 ge_complete(&orion_ge00_shared_data, mbus_dram_info, tclk,
268 orion_ge00_resources, irq, &orion_ge00_shared,
269 eth_data, &orion_ge00);
270}
271
272/*****************************************************************************
273 * GE01
274 ****************************************************************************/
275struct mv643xx_eth_shared_platform_data orion_ge01_shared_data = {
276 .shared_smi = &orion_ge00_shared,
277};
278
279static struct resource orion_ge01_shared_resources[] = {
280 {
281 .name = "ge01 base",
282 }, {
283 .name = "ge01 err irq",
284 },
285};
286
287static struct platform_device orion_ge01_shared = {
288 .name = MV643XX_ETH_SHARED_NAME,
289 .id = 1,
290 .dev = {
291 .platform_data = &orion_ge01_shared_data,
292 },
293};
294
295static struct resource orion_ge01_resources[] = {
296 {
297 .name = "ge01 irq",
298 .flags = IORESOURCE_IRQ,
299 },
300};
301
302static struct platform_device orion_ge01 = {
303 .name = MV643XX_ETH_NAME,
304 .id = 1,
305 .num_resources = 1,
306 .resource = orion_ge01_resources,
307 .dev = {
308 .coherent_dma_mask = DMA_BIT_MASK(32),
309 },
310};
311
312void __init orion_ge01_init(struct mv643xx_eth_platform_data *eth_data,
313 struct mbus_dram_target_info *mbus_dram_info,
314 unsigned long mapbase,
315 unsigned long irq,
316 unsigned long irq_err,
317 int tclk)
318{
319 fill_resources(&orion_ge01_shared, orion_ge01_shared_resources,
320 mapbase + 0x2000, SZ_16K - 1, irq_err);
321 ge_complete(&orion_ge01_shared_data, mbus_dram_info, tclk,
322 orion_ge01_resources, irq, &orion_ge01_shared,
323 eth_data, &orion_ge01);
324}
325
326/*****************************************************************************
327 * GE10
328 ****************************************************************************/
329struct mv643xx_eth_shared_platform_data orion_ge10_shared_data = {
330 .shared_smi = &orion_ge00_shared,
331};
332
333static struct resource orion_ge10_shared_resources[] = {
334 {
335 .name = "ge10 base",
336 }, {
337 .name = "ge10 err irq",
338 },
339};
340
341static struct platform_device orion_ge10_shared = {
342 .name = MV643XX_ETH_SHARED_NAME,
343 .id = 1,
344 .dev = {
345 .platform_data = &orion_ge10_shared_data,
346 },
347};
348
349static struct resource orion_ge10_resources[] = {
350 {
351 .name = "ge10 irq",
352 .flags = IORESOURCE_IRQ,
353 },
354};
355
356static struct platform_device orion_ge10 = {
357 .name = MV643XX_ETH_NAME,
358 .id = 1,
359 .num_resources = 2,
360 .resource = orion_ge10_resources,
361 .dev = {
362 .coherent_dma_mask = DMA_BIT_MASK(32),
363 },
364};
365
366void __init orion_ge10_init(struct mv643xx_eth_platform_data *eth_data,
367 struct mbus_dram_target_info *mbus_dram_info,
368 unsigned long mapbase,
369 unsigned long irq,
370 unsigned long irq_err,
371 int tclk)
372{
373 fill_resources(&orion_ge10_shared, orion_ge10_shared_resources,
374 mapbase + 0x2000, SZ_16K - 1, irq_err);
375 ge_complete(&orion_ge10_shared_data, mbus_dram_info, tclk,
376 orion_ge10_resources, irq, &orion_ge10_shared,
377 eth_data, &orion_ge10);
378}
379
380/*****************************************************************************
381 * GE11
382 ****************************************************************************/
383struct mv643xx_eth_shared_platform_data orion_ge11_shared_data = {
384 .shared_smi = &orion_ge00_shared,
385};
386
387static struct resource orion_ge11_shared_resources[] = {
388 {
389 .name = "ge11 base",
390 }, {
391 .name = "ge11 err irq",
392 },
393};
394
395static struct platform_device orion_ge11_shared = {
396 .name = MV643XX_ETH_SHARED_NAME,
397 .id = 1,
398 .dev = {
399 .platform_data = &orion_ge11_shared_data,
400 },
401};
402
403static struct resource orion_ge11_resources[] = {
404 {
405 .name = "ge11 irq",
406 .flags = IORESOURCE_IRQ,
407 },
408};
409
410static struct platform_device orion_ge11 = {
411 .name = MV643XX_ETH_NAME,
412 .id = 1,
413 .num_resources = 2,
414 .resource = orion_ge11_resources,
415 .dev = {
416 .coherent_dma_mask = DMA_BIT_MASK(32),
417 },
418};
419
420void __init orion_ge11_init(struct mv643xx_eth_platform_data *eth_data,
421 struct mbus_dram_target_info *mbus_dram_info,
422 unsigned long mapbase,
423 unsigned long irq,
424 unsigned long irq_err,
425 int tclk)
426{
427 fill_resources(&orion_ge11_shared, orion_ge11_shared_resources,
428 mapbase + 0x2000, SZ_16K - 1, irq_err);
429 ge_complete(&orion_ge11_shared_data, mbus_dram_info, tclk,
430 orion_ge11_resources, irq, &orion_ge11_shared,
431 eth_data, &orion_ge11);
432}
433
434/*****************************************************************************
435 * Ethernet switch
436 ****************************************************************************/
437static struct resource orion_switch_resources[] = {
438 {
439 .start = 0,
440 .end = 0,
441 .flags = IORESOURCE_IRQ,
442 },
443};
444
445static struct platform_device orion_switch_device = {
446 .name = "dsa",
447 .id = 0,
448 .num_resources = 0,
449 .resource = orion_switch_resources,
450};
451
452void __init orion_ge00_switch_init(struct dsa_platform_data *d, int irq)
453{
454 int i;
455
456 if (irq != NO_IRQ) {
457 orion_switch_resources[0].start = irq;
458 orion_switch_resources[0].end = irq;
459 orion_switch_device.num_resources = 1;
460 }
461
462 d->netdev = &orion_ge00.dev;
463 for (i = 0; i < d->nr_chips; i++)
464 d->chip[i].mii_bus = &orion_ge00_shared.dev;
465 orion_switch_device.dev.platform_data = d;
466
467 platform_device_register(&orion_switch_device);
468}
Andrew Lunnaac7ffa2011-05-15 13:32:45 +0200469
470/*****************************************************************************
471 * I2C
472 ****************************************************************************/
473static struct mv64xxx_i2c_pdata orion_i2c_pdata = {
474 .freq_n = 3,
475 .timeout = 1000, /* Default timeout of 1 second */
476};
477
478static struct resource orion_i2c_resources[2];
479
480static struct platform_device orion_i2c = {
481 .name = MV64XXX_I2C_CTLR_NAME,
482 .id = 0,
483 .dev = {
484 .platform_data = &orion_i2c_pdata,
485 },
486};
487
488static struct mv64xxx_i2c_pdata orion_i2c_1_pdata = {
489 .freq_n = 3,
490 .timeout = 1000, /* Default timeout of 1 second */
491};
492
493static struct resource orion_i2c_1_resources[2];
494
495static struct platform_device orion_i2c_1 = {
496 .name = MV64XXX_I2C_CTLR_NAME,
497 .id = 1,
498 .dev = {
499 .platform_data = &orion_i2c_1_pdata,
500 },
501};
502
503void __init orion_i2c_init(unsigned long mapbase,
504 unsigned long irq,
505 unsigned long freq_m)
506{
507 orion_i2c_pdata.freq_m = freq_m;
508 fill_resources(&orion_i2c, orion_i2c_resources, mapbase,
509 SZ_32 - 1, irq);
510 platform_device_register(&orion_i2c);
511}
512
513void __init orion_i2c_1_init(unsigned long mapbase,
514 unsigned long irq,
515 unsigned long freq_m)
516{
517 orion_i2c_1_pdata.freq_m = freq_m;
518 fill_resources(&orion_i2c_1, orion_i2c_1_resources, mapbase,
519 SZ_32 - 1, irq);
520 platform_device_register(&orion_i2c_1);
521}
Andrew Lunn980f9f62011-05-15 13:32:46 +0200522
523/*****************************************************************************
524 * SPI
525 ****************************************************************************/
526static struct orion_spi_info orion_spi_plat_data;
527static struct resource orion_spi_resources;
528
529static struct platform_device orion_spi = {
530 .name = "orion_spi",
531 .id = 0,
532 .dev = {
533 .platform_data = &orion_spi_plat_data,
534 },
535};
536
537static struct orion_spi_info orion_spi_1_plat_data;
538static struct resource orion_spi_1_resources;
539
540static struct platform_device orion_spi_1 = {
541 .name = "orion_spi",
542 .id = 1,
543 .dev = {
544 .platform_data = &orion_spi_1_plat_data,
545 },
546};
547
548/* Note: The SPI silicon core does have interrupts. However the
549 * current Linux software driver does not use interrupts. */
550
551void __init orion_spi_init(unsigned long mapbase,
552 unsigned long tclk)
553{
554 orion_spi_plat_data.tclk = tclk;
555 fill_resources(&orion_spi, &orion_spi_resources,
556 mapbase, SZ_512 - 1, NO_IRQ);
557 platform_device_register(&orion_spi);
558}
559
560void __init orion_spi_1_init(unsigned long mapbase,
561 unsigned long tclk)
562{
563 orion_spi_1_plat_data.tclk = tclk;
564 fill_resources(&orion_spi_1, &orion_spi_1_resources,
565 mapbase, SZ_512 - 1, NO_IRQ);
566 platform_device_register(&orion_spi_1);
567}
Andrew Lunn5e00d372011-05-15 13:32:47 +0200568
569/*****************************************************************************
570 * Watchdog
571 ****************************************************************************/
572static struct orion_wdt_platform_data orion_wdt_data;
573
574static struct platform_device orion_wdt_device = {
575 .name = "orion_wdt",
576 .id = -1,
577 .dev = {
578 .platform_data = &orion_wdt_data,
579 },
580 .num_resources = 0,
581};
582
583void __init orion_wdt_init(unsigned long tclk)
584{
585 orion_wdt_data.tclk = tclk;
586 platform_device_register(&orion_wdt_device);
587}