Merge branch 'msm-core' of git://codeaurora.org/quic/kernel/dwalker/linux-msm
[pandora-kernel.git] / arch / sh / kernel / cpu / sh4a / setup-shx3.c
1 /*
2  * SH-X3 Prototype Setup
3  *
4  *  Copyright (C) 2007 - 2009  Paul Mundt
5  *
6  * This file is subject to the terms and conditions of the GNU General Public
7  * License.  See the file "COPYING" in the main directory of this archive
8  * for more details.
9  */
10 #include <linux/platform_device.h>
11 #include <linux/init.h>
12 #include <linux/serial.h>
13 #include <linux/serial_sci.h>
14 #include <linux/io.h>
15 #include <linux/sh_timer.h>
16 #include <asm/mmzone.h>
17
18 /*
19  * This intentionally only registers SCIF ports 0, 1, and 3. SCIF 2
20  * INTEVT values overlap with the FPU EXPEVT ones, requiring special
21  * demuxing in the exception dispatch path.
22  *
23  * As this overlap is something that never should have made it in to
24  * silicon in the first place, we just refuse to deal with the port at
25  * all rather than adding infrastructure to hack around it.
26  */
27 static struct plat_sci_port scif0_platform_data = {
28         .mapbase        = 0xffc30000,
29         .flags          = UPF_BOOT_AUTOCONF,
30         .type           = PORT_SCIF,
31         .irqs           = { 40, 41, 43, 42 },
32 };
33
34 static struct platform_device scif0_device = {
35         .name           = "sh-sci",
36         .id             = 0,
37         .dev            = {
38                 .platform_data  = &scif0_platform_data,
39         },
40 };
41
42 static struct plat_sci_port scif1_platform_data = {
43         .mapbase        = 0xffc40000,
44         .flags          = UPF_BOOT_AUTOCONF,
45         .type           = PORT_SCIF,
46         .irqs           = { 44, 45, 47, 46 },
47 };
48
49 static struct platform_device scif1_device = {
50         .name           = "sh-sci",
51         .id             = 1,
52         .dev            = {
53                 .platform_data  = &scif1_platform_data,
54         },
55 };
56
57 static struct plat_sci_port scif2_platform_data = {
58         .mapbase        = 0xffc60000,
59         .flags          = UPF_BOOT_AUTOCONF,
60         .type           = PORT_SCIF,
61         .irqs           = { 52, 53, 55, 54 },
62 };
63
64 static struct platform_device scif2_device = {
65         .name           = "sh-sci",
66         .id             = 2,
67         .dev            = {
68                 .platform_data  = &scif2_platform_data,
69         },
70 };
71
72 static struct sh_timer_config tmu0_platform_data = {
73         .channel_offset = 0x04,
74         .timer_bit = 0,
75         .clockevent_rating = 200,
76 };
77
78 static struct resource tmu0_resources[] = {
79         [0] = {
80                 .start  = 0xffc10008,
81                 .end    = 0xffc10013,
82                 .flags  = IORESOURCE_MEM,
83         },
84         [1] = {
85                 .start  = 16,
86                 .flags  = IORESOURCE_IRQ,
87         },
88 };
89
90 static struct platform_device tmu0_device = {
91         .name           = "sh_tmu",
92         .id             = 0,
93         .dev = {
94                 .platform_data  = &tmu0_platform_data,
95         },
96         .resource       = tmu0_resources,
97         .num_resources  = ARRAY_SIZE(tmu0_resources),
98 };
99
100 static struct sh_timer_config tmu1_platform_data = {
101         .channel_offset = 0x10,
102         .timer_bit = 1,
103         .clocksource_rating = 200,
104 };
105
106 static struct resource tmu1_resources[] = {
107         [0] = {
108                 .start  = 0xffc10014,
109                 .end    = 0xffc1001f,
110                 .flags  = IORESOURCE_MEM,
111         },
112         [1] = {
113                 .start  = 17,
114                 .flags  = IORESOURCE_IRQ,
115         },
116 };
117
118 static struct platform_device tmu1_device = {
119         .name           = "sh_tmu",
120         .id             = 1,
121         .dev = {
122                 .platform_data  = &tmu1_platform_data,
123         },
124         .resource       = tmu1_resources,
125         .num_resources  = ARRAY_SIZE(tmu1_resources),
126 };
127
128 static struct sh_timer_config tmu2_platform_data = {
129         .channel_offset = 0x1c,
130         .timer_bit = 2,
131 };
132
133 static struct resource tmu2_resources[] = {
134         [0] = {
135                 .start  = 0xffc10020,
136                 .end    = 0xffc1002f,
137                 .flags  = IORESOURCE_MEM,
138         },
139         [1] = {
140                 .start  = 18,
141                 .flags  = IORESOURCE_IRQ,
142         },
143 };
144
145 static struct platform_device tmu2_device = {
146         .name           = "sh_tmu",
147         .id             = 2,
148         .dev = {
149                 .platform_data  = &tmu2_platform_data,
150         },
151         .resource       = tmu2_resources,
152         .num_resources  = ARRAY_SIZE(tmu2_resources),
153 };
154
155 static struct sh_timer_config tmu3_platform_data = {
156         .channel_offset = 0x04,
157         .timer_bit = 0,
158 };
159
160 static struct resource tmu3_resources[] = {
161         [0] = {
162                 .start  = 0xffc20008,
163                 .end    = 0xffc20013,
164                 .flags  = IORESOURCE_MEM,
165         },
166         [1] = {
167                 .start  = 19,
168                 .flags  = IORESOURCE_IRQ,
169         },
170 };
171
172 static struct platform_device tmu3_device = {
173         .name           = "sh_tmu",
174         .id             = 3,
175         .dev = {
176                 .platform_data  = &tmu3_platform_data,
177         },
178         .resource       = tmu3_resources,
179         .num_resources  = ARRAY_SIZE(tmu3_resources),
180 };
181
182 static struct sh_timer_config tmu4_platform_data = {
183         .channel_offset = 0x10,
184         .timer_bit = 1,
185 };
186
187 static struct resource tmu4_resources[] = {
188         [0] = {
189                 .start  = 0xffc20014,
190                 .end    = 0xffc2001f,
191                 .flags  = IORESOURCE_MEM,
192         },
193         [1] = {
194                 .start  = 20,
195                 .flags  = IORESOURCE_IRQ,
196         },
197 };
198
199 static struct platform_device tmu4_device = {
200         .name           = "sh_tmu",
201         .id             = 4,
202         .dev = {
203                 .platform_data  = &tmu4_platform_data,
204         },
205         .resource       = tmu4_resources,
206         .num_resources  = ARRAY_SIZE(tmu4_resources),
207 };
208
209 static struct sh_timer_config tmu5_platform_data = {
210         .channel_offset = 0x1c,
211         .timer_bit = 2,
212 };
213
214 static struct resource tmu5_resources[] = {
215         [0] = {
216                 .start  = 0xffc20020,
217                 .end    = 0xffc2002b,
218                 .flags  = IORESOURCE_MEM,
219         },
220         [1] = {
221                 .start  = 21,
222                 .flags  = IORESOURCE_IRQ,
223         },
224 };
225
226 static struct platform_device tmu5_device = {
227         .name           = "sh_tmu",
228         .id             = 5,
229         .dev = {
230                 .platform_data  = &tmu5_platform_data,
231         },
232         .resource       = tmu5_resources,
233         .num_resources  = ARRAY_SIZE(tmu5_resources),
234 };
235
236 static struct platform_device *shx3_early_devices[] __initdata = {
237         &scif0_device,
238         &scif1_device,
239         &scif2_device,
240         &tmu0_device,
241         &tmu1_device,
242         &tmu2_device,
243         &tmu3_device,
244         &tmu4_device,
245         &tmu5_device,
246 };
247
248 static int __init shx3_devices_setup(void)
249 {
250         return platform_add_devices(shx3_early_devices,
251                                    ARRAY_SIZE(shx3_early_devices));
252 }
253 arch_initcall(shx3_devices_setup);
254
255 void __init plat_early_device_setup(void)
256 {
257         early_platform_add_devices(shx3_early_devices,
258                                    ARRAY_SIZE(shx3_early_devices));
259 }
260
261 enum {
262         UNUSED = 0,
263
264         /* interrupt sources */
265         IRL_LLLL, IRL_LLLH, IRL_LLHL, IRL_LLHH,
266         IRL_LHLL, IRL_LHLH, IRL_LHHL, IRL_LHHH,
267         IRL_HLLL, IRL_HLLH, IRL_HLHL, IRL_HLHH,
268         IRL_HHLL, IRL_HHLH, IRL_HHHL,
269         IRQ0, IRQ1, IRQ2, IRQ3,
270         HUDII,
271         TMU0, TMU1, TMU2, TMU3, TMU4, TMU5,
272         PCII0, PCII1, PCII2, PCII3, PCII4,
273         PCII5, PCII6, PCII7, PCII8, PCII9,
274         SCIF0_ERI, SCIF0_RXI, SCIF0_BRI, SCIF0_TXI,
275         SCIF1_ERI, SCIF1_RXI, SCIF1_BRI, SCIF1_TXI,
276         SCIF2_ERI, SCIF2_RXI, SCIF2_BRI, SCIF2_TXI,
277         SCIF3_ERI, SCIF3_RXI, SCIF3_BRI, SCIF3_TXI,
278         DMAC0_DMINT0, DMAC0_DMINT1, DMAC0_DMINT2, DMAC0_DMINT3,
279         DMAC0_DMINT4, DMAC0_DMINT5, DMAC0_DMAE,
280         DU,
281         DMAC1_DMINT6, DMAC1_DMINT7, DMAC1_DMINT8, DMAC1_DMINT9,
282         DMAC1_DMINT10, DMAC1_DMINT11, DMAC1_DMAE,
283         IIC, VIN0, VIN1, VCORE0, ATAPI,
284         DTU0, DTU1, DTU2, DTU3,
285         FE0, FE1,
286         GPIO0, GPIO1, GPIO2, GPIO3,
287         PAM, IRM,
288         INTICI0, INTICI1, INTICI2, INTICI3,
289         INTICI4, INTICI5, INTICI6, INTICI7,
290
291         /* interrupt groups */
292         IRL, PCII56789, SCIF0, SCIF1, SCIF2, SCIF3,
293         DMAC0, DMAC1,
294 };
295
296 static struct intc_vect vectors[] __initdata = {
297         INTC_VECT(HUDII, 0x3e0),
298         INTC_VECT(TMU0, 0x400), INTC_VECT(TMU1, 0x420),
299         INTC_VECT(TMU2, 0x440), INTC_VECT(TMU3, 0x460),
300         INTC_VECT(TMU4, 0x480), INTC_VECT(TMU5, 0x4a0),
301         INTC_VECT(PCII0, 0x500), INTC_VECT(PCII1, 0x520),
302         INTC_VECT(PCII2, 0x540), INTC_VECT(PCII3, 0x560),
303         INTC_VECT(PCII4, 0x580), INTC_VECT(PCII5, 0x5a0),
304         INTC_VECT(PCII6, 0x5c0), INTC_VECT(PCII7, 0x5e0),
305         INTC_VECT(PCII8, 0x600), INTC_VECT(PCII9, 0x620),
306         INTC_VECT(SCIF0_ERI, 0x700), INTC_VECT(SCIF0_RXI, 0x720),
307         INTC_VECT(SCIF0_BRI, 0x740), INTC_VECT(SCIF0_TXI, 0x760),
308         INTC_VECT(SCIF1_ERI, 0x780), INTC_VECT(SCIF1_RXI, 0x7a0),
309         INTC_VECT(SCIF1_BRI, 0x7c0), INTC_VECT(SCIF1_TXI, 0x7e0),
310         INTC_VECT(SCIF3_ERI, 0x880), INTC_VECT(SCIF3_RXI, 0x8a0),
311         INTC_VECT(SCIF3_BRI, 0x8c0), INTC_VECT(SCIF3_TXI, 0x8e0),
312         INTC_VECT(DMAC0_DMINT0, 0x900), INTC_VECT(DMAC0_DMINT1, 0x920),
313         INTC_VECT(DMAC0_DMINT2, 0x940), INTC_VECT(DMAC0_DMINT3, 0x960),
314         INTC_VECT(DMAC0_DMINT4, 0x980), INTC_VECT(DMAC0_DMINT5, 0x9a0),
315         INTC_VECT(DMAC0_DMAE, 0x9c0),
316         INTC_VECT(DU, 0x9e0),
317         INTC_VECT(DMAC1_DMINT6, 0xa00), INTC_VECT(DMAC1_DMINT7, 0xa20),
318         INTC_VECT(DMAC1_DMINT8, 0xa40), INTC_VECT(DMAC1_DMINT9, 0xa60),
319         INTC_VECT(DMAC1_DMINT10, 0xa80), INTC_VECT(DMAC1_DMINT11, 0xaa0),
320         INTC_VECT(DMAC1_DMAE, 0xac0),
321         INTC_VECT(IIC, 0xae0),
322         INTC_VECT(VIN0, 0xb00), INTC_VECT(VIN1, 0xb20),
323         INTC_VECT(VCORE0, 0xb00), INTC_VECT(ATAPI, 0xb60),
324         INTC_VECT(DTU0, 0xc00), INTC_VECT(DTU0, 0xc20),
325         INTC_VECT(DTU0, 0xc40),
326         INTC_VECT(DTU1, 0xc60), INTC_VECT(DTU1, 0xc80),
327         INTC_VECT(DTU1, 0xca0),
328         INTC_VECT(DTU2, 0xcc0), INTC_VECT(DTU2, 0xce0),
329         INTC_VECT(DTU2, 0xd00),
330         INTC_VECT(DTU3, 0xd20), INTC_VECT(DTU3, 0xd40),
331         INTC_VECT(DTU3, 0xd60),
332         INTC_VECT(FE0, 0xe00), INTC_VECT(FE1, 0xe20),
333         INTC_VECT(GPIO0, 0xe40), INTC_VECT(GPIO1, 0xe60),
334         INTC_VECT(GPIO2, 0xe80), INTC_VECT(GPIO3, 0xea0),
335         INTC_VECT(PAM, 0xec0), INTC_VECT(IRM, 0xee0),
336         INTC_VECT(INTICI0, 0xf00), INTC_VECT(INTICI1, 0xf20),
337         INTC_VECT(INTICI2, 0xf40), INTC_VECT(INTICI3, 0xf60),
338         INTC_VECT(INTICI4, 0xf80), INTC_VECT(INTICI5, 0xfa0),
339         INTC_VECT(INTICI6, 0xfc0), INTC_VECT(INTICI7, 0xfe0),
340 };
341
342 static struct intc_group groups[] __initdata = {
343         INTC_GROUP(IRL, IRL_LLLL, IRL_LLLH, IRL_LLHL, IRL_LLHH,
344                    IRL_LHLL, IRL_LHLH, IRL_LHHL, IRL_LHHH,
345                    IRL_HLLL, IRL_HLLH, IRL_HLHL, IRL_HLHH,
346                    IRL_HHLL, IRL_HHLH, IRL_HHHL),
347         INTC_GROUP(PCII56789, PCII5, PCII6, PCII7, PCII8, PCII9),
348         INTC_GROUP(SCIF0, SCIF0_ERI, SCIF0_RXI, SCIF0_BRI, SCIF0_TXI),
349         INTC_GROUP(SCIF1, SCIF1_ERI, SCIF1_RXI, SCIF1_BRI, SCIF1_TXI),
350         INTC_GROUP(SCIF3, SCIF3_ERI, SCIF3_RXI, SCIF3_BRI, SCIF3_TXI),
351         INTC_GROUP(DMAC0, DMAC0_DMINT0, DMAC0_DMINT1, DMAC0_DMINT2,
352                    DMAC0_DMINT3, DMAC0_DMINT4, DMAC0_DMINT5, DMAC0_DMAE),
353         INTC_GROUP(DMAC1, DMAC1_DMINT6, DMAC1_DMINT7, DMAC1_DMINT8,
354                    DMAC1_DMINT9, DMAC1_DMINT10, DMAC1_DMINT11),
355 };
356
357 static struct intc_mask_reg mask_registers[] __initdata = {
358         { 0xfe410030, 0xfe410050, 32, /* CnINTMSK0 / CnINTMSKCLR0 */
359           { IRQ0, IRQ1, IRQ2, IRQ3 } },
360         { 0xfe410040, 0xfe410060, 32, /* CnINTMSK1 / CnINTMSKCLR1 */
361           { IRL } },
362         { 0xfe410820, 0xfe410850, 32, /* CnINT2MSK0 / CnINT2MSKCLR0 */
363           { FE1, FE0, 0, ATAPI, VCORE0, VIN1, VIN0, IIC,
364             DU, GPIO3, GPIO2, GPIO1, GPIO0, PAM, 0, 0,
365             0, 0, 0, 0, 0, 0, 0, 0, /* HUDI bits ignored */
366             0, TMU5, TMU4, TMU3, TMU2, TMU1, TMU0, 0, } },
367         { 0xfe410830, 0xfe410860, 32, /* CnINT2MSK1 / CnINT2MSKCLR1 */
368           { 0, 0, 0, 0, DTU3, DTU2, DTU1, DTU0, /* IRM bits ignored */
369             PCII9, PCII8, PCII7, PCII6, PCII5, PCII4, PCII3, PCII2,
370             PCII1, PCII0, DMAC1_DMAE, DMAC1_DMINT11,
371             DMAC1_DMINT10, DMAC1_DMINT9, DMAC1_DMINT8, DMAC1_DMINT7,
372             DMAC1_DMINT6, DMAC0_DMAE, DMAC0_DMINT5, DMAC0_DMINT4,
373             DMAC0_DMINT3, DMAC0_DMINT2, DMAC0_DMINT1, DMAC0_DMINT0 } },
374         { 0xfe410840, 0xfe410870, 32, /* CnINT2MSK2 / CnINT2MSKCLR2 */
375           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
376             SCIF3_TXI, SCIF3_BRI, SCIF3_RXI, SCIF3_ERI,
377             SCIF2_TXI, SCIF2_BRI, SCIF2_RXI, SCIF2_ERI,
378             SCIF1_TXI, SCIF1_BRI, SCIF1_RXI, SCIF1_ERI,
379             SCIF0_TXI, SCIF0_BRI, SCIF0_RXI, SCIF0_ERI } },
380 };
381
382 static struct intc_prio_reg prio_registers[] __initdata = {
383         { 0xfe410010, 0, 32, 4, /* INTPRI */ { IRQ0, IRQ1, IRQ2, IRQ3 } },
384
385         { 0xfe410800, 0, 32, 4, /* INT2PRI0 */ { 0, HUDII, TMU5, TMU4,
386                                                  TMU3, TMU2, TMU1, TMU0 } },
387         { 0xfe410804, 0, 32, 4, /* INT2PRI1 */ { DTU3, DTU2, DTU1, DTU0,
388                                                  SCIF3, SCIF2,
389                                                  SCIF1, SCIF0 } },
390         { 0xfe410808, 0, 32, 4, /* INT2PRI2 */ { DMAC1, DMAC0,
391                                                  PCII56789, PCII4,
392                                                  PCII3, PCII2,
393                                                  PCII1, PCII0 } },
394         { 0xfe41080c, 0, 32, 4, /* INT2PRI3 */ { FE1, FE0, ATAPI, VCORE0,
395                                                  VIN1, VIN0, IIC, DU} },
396         { 0xfe410810, 0, 32, 4, /* INT2PRI4 */ { 0, 0, PAM, GPIO3,
397                                                  GPIO2, GPIO1, GPIO0, IRM } },
398         { 0xfe410090, 0xfe4100a0, 32, 4, /* CnICIPRI / CnICIPRICLR */
399           { INTICI7, INTICI6, INTICI5, INTICI4,
400             INTICI3, INTICI2, INTICI1, INTICI0 }, INTC_SMP(4, 4) },
401 };
402
403 static DECLARE_INTC_DESC(intc_desc, "shx3", vectors, groups,
404                          mask_registers, prio_registers, NULL);
405
406 /* Support for external interrupt pins in IRQ mode */
407 static struct intc_vect vectors_irq[] __initdata = {
408         INTC_VECT(IRQ0, 0x240), INTC_VECT(IRQ1, 0x280),
409         INTC_VECT(IRQ2, 0x2c0), INTC_VECT(IRQ3, 0x300),
410 };
411
412 static struct intc_sense_reg sense_registers[] __initdata = {
413         { 0xfe41001c, 32, 2, /* ICR1 */   { IRQ0, IRQ1, IRQ2, IRQ3 } },
414 };
415
416 static DECLARE_INTC_DESC(intc_desc_irq, "shx3-irq", vectors_irq, groups,
417                          mask_registers, prio_registers, sense_registers);
418
419 /* External interrupt pins in IRL mode */
420 static struct intc_vect vectors_irl[] __initdata = {
421         INTC_VECT(IRL_LLLL, 0x200), INTC_VECT(IRL_LLLH, 0x220),
422         INTC_VECT(IRL_LLHL, 0x240), INTC_VECT(IRL_LLHH, 0x260),
423         INTC_VECT(IRL_LHLL, 0x280), INTC_VECT(IRL_LHLH, 0x2a0),
424         INTC_VECT(IRL_LHHL, 0x2c0), INTC_VECT(IRL_LHHH, 0x2e0),
425         INTC_VECT(IRL_HLLL, 0x300), INTC_VECT(IRL_HLLH, 0x320),
426         INTC_VECT(IRL_HLHL, 0x340), INTC_VECT(IRL_HLHH, 0x360),
427         INTC_VECT(IRL_HHLL, 0x380), INTC_VECT(IRL_HHLH, 0x3a0),
428         INTC_VECT(IRL_HHHL, 0x3c0),
429 };
430
431 static DECLARE_INTC_DESC(intc_desc_irl, "shx3-irl", vectors_irl, groups,
432                          mask_registers, prio_registers, NULL);
433
434 void __init plat_irq_setup_pins(int mode)
435 {
436         switch (mode) {
437         case IRQ_MODE_IRQ:
438                 register_intc_controller(&intc_desc_irq);
439                 break;
440         case IRQ_MODE_IRL3210:
441                 register_intc_controller(&intc_desc_irl);
442                 break;
443         default:
444                 BUG();
445         }
446 }
447
448 void __init plat_irq_setup(void)
449 {
450         register_intc_controller(&intc_desc);
451 }
452
453 void __init plat_mem_setup(void)
454 {
455         unsigned int nid = 1;
456
457         /* Register CPU#0 URAM space as Node 1 */
458         setup_bootmem_node(nid++, 0x145f0000, 0x14610000);      /* CPU0 */
459
460 #if 0
461         /* XXX: Not yet.. */
462         setup_bootmem_node(nid++, 0x14df0000, 0x14e10000);      /* CPU1 */
463         setup_bootmem_node(nid++, 0x155f0000, 0x15610000);      /* CPU2 */
464         setup_bootmem_node(nid++, 0x15df0000, 0x15e10000);      /* CPU3 */
465 #endif
466
467         setup_bootmem_node(nid++, 0x16000000, 0x16020000);      /* CSM */
468 }