xref: /linux/arch/sh/kernel/cpu/sh4a/setup-sh7763.c (revision e5a52fd2b8cdb700b3c07b030e050a49ef3156b9)
1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * SH7763 Setup
4  *
5  *  Copyright (C) 2006  Paul Mundt
6  *  Copyright (C) 2007  Yoshihiro Shimoda
7  *  Copyright (C) 2008, 2009  Nobuhiro Iwamatsu
8  */
9 #include <linux/platform_device.h>
10 #include <linux/init.h>
11 #include <linux/serial.h>
12 #include <linux/sh_timer.h>
13 #include <linux/sh_intc.h>
14 #include <linux/io.h>
15 #include <linux/serial_sci.h>
16 #include <linux/usb/ohci_pdriver.h>
17 #include <asm/platform_early.h>
18 
19 static struct plat_sci_port scif0_platform_data = {
20 	.scscr		= SCSCR_REIE,
21 	.type		= PORT_SCIF,
22 	.regtype	= SCIx_SH4_SCIF_FIFODATA_REGTYPE,
23 };
24 
25 static struct resource scif0_resources[] = {
26 	DEFINE_RES_MEM(0xffe00000, 0x100),
27 	DEFINE_RES_IRQ(evt2irq(0x700)),
28 };
29 
30 static struct platform_device scif0_device = {
31 	.name		= "sh-sci",
32 	.id		= 0,
33 	.resource	= scif0_resources,
34 	.num_resources	= ARRAY_SIZE(scif0_resources),
35 	.dev		= {
36 		.platform_data	= &scif0_platform_data,
37 	},
38 };
39 
40 static struct plat_sci_port scif1_platform_data = {
41 	.scscr		= SCSCR_REIE,
42 	.type		= PORT_SCIF,
43 	.regtype	= SCIx_SH4_SCIF_FIFODATA_REGTYPE,
44 };
45 
46 static struct resource scif1_resources[] = {
47 	DEFINE_RES_MEM(0xffe08000, 0x100),
48 	DEFINE_RES_IRQ(evt2irq(0xb80)),
49 };
50 
51 static struct platform_device scif1_device = {
52 	.name		= "sh-sci",
53 	.id		= 1,
54 	.resource	= scif1_resources,
55 	.num_resources	= ARRAY_SIZE(scif1_resources),
56 	.dev		= {
57 		.platform_data	= &scif1_platform_data,
58 	},
59 };
60 
61 static struct plat_sci_port scif2_platform_data = {
62 	.scscr		= SCSCR_REIE,
63 	.type		= PORT_SCIF,
64 	.regtype	= SCIx_SH4_SCIF_FIFODATA_REGTYPE,
65 };
66 
67 static struct resource scif2_resources[] = {
68 	DEFINE_RES_MEM(0xffe10000, 0x100),
69 	DEFINE_RES_IRQ(evt2irq(0xf00)),
70 };
71 
72 static struct platform_device scif2_device = {
73 	.name		= "sh-sci",
74 	.id		= 2,
75 	.resource	= scif2_resources,
76 	.num_resources	= ARRAY_SIZE(scif2_resources),
77 	.dev		= {
78 		.platform_data	= &scif2_platform_data,
79 	},
80 };
81 
82 static struct resource rtc_resources[] = {
83 	[0] = {
84 		.start	= 0xffe80000,
85 		.end	= 0xffe80000 + 0x58 - 1,
86 		.flags	= IORESOURCE_IO,
87 	},
88 	[1] = {
89 		/* Shared Period/Carry/Alarm IRQ */
90 		.start  = evt2irq(0x480),
91 		.flags	= IORESOURCE_IRQ,
92 	},
93 };
94 
95 static struct platform_device rtc_device = {
96 	.name		= "sh-rtc",
97 	.id		= -1,
98 	.num_resources	= ARRAY_SIZE(rtc_resources),
99 	.resource	= rtc_resources,
100 };
101 
102 static struct resource usb_ohci_resources[] = {
103 	[0] = {
104 		.start	= 0xffec8000,
105 		.end	= 0xffec80ff,
106 		.flags	= IORESOURCE_MEM,
107 	},
108 	[1] = {
109 		.start	= evt2irq(0xc60),
110 		.end	= evt2irq(0xc60),
111 		.flags	= IORESOURCE_IRQ,
112 	},
113 };
114 
115 static u64 usb_ohci_dma_mask = 0xffffffffUL;
116 
117 static struct usb_ohci_pdata usb_ohci_pdata;
118 
119 static struct platform_device usb_ohci_device = {
120 	.name		= "ohci-platform",
121 	.id		= -1,
122 	.dev = {
123 		.dma_mask		= &usb_ohci_dma_mask,
124 		.coherent_dma_mask	= 0xffffffff,
125 		.platform_data		= &usb_ohci_pdata,
126 	},
127 	.num_resources	= ARRAY_SIZE(usb_ohci_resources),
128 	.resource	= usb_ohci_resources,
129 };
130 
131 static struct resource usbf_resources[] = {
132 	[0] = {
133 		.start	= 0xffec0000,
134 		.end	= 0xffec00ff,
135 		.flags	= IORESOURCE_MEM,
136 	},
137 	[1] = {
138 		.start	= evt2irq(0xc80),
139 		.end	= evt2irq(0xc80),
140 		.flags	= IORESOURCE_IRQ,
141 	},
142 };
143 
144 static struct platform_device usbf_device = {
145 	.name		= "sh_udc",
146 	.id		= -1,
147 	.dev = {
148 		.dma_mask		= NULL,
149 		.coherent_dma_mask	= 0xffffffff,
150 	},
151 	.num_resources	= ARRAY_SIZE(usbf_resources),
152 	.resource	= usbf_resources,
153 };
154 
155 static struct sh_timer_config tmu0_platform_data = {
156 	.channels_mask = 7,
157 };
158 
159 static struct resource tmu0_resources[] = {
160 	DEFINE_RES_MEM(0xffd80000, 0x30),
161 	DEFINE_RES_IRQ(evt2irq(0x580)),
162 	DEFINE_RES_IRQ(evt2irq(0x5a0)),
163 	DEFINE_RES_IRQ(evt2irq(0x5c0)),
164 };
165 
166 static struct platform_device tmu0_device = {
167 	.name		= "sh-tmu",
168 	.id		= 0,
169 	.dev = {
170 		.platform_data	= &tmu0_platform_data,
171 	},
172 	.resource	= tmu0_resources,
173 	.num_resources	= ARRAY_SIZE(tmu0_resources),
174 };
175 
176 static struct sh_timer_config tmu1_platform_data = {
177 	.channels_mask = 7,
178 };
179 
180 static struct resource tmu1_resources[] = {
181 	DEFINE_RES_MEM(0xffd88000, 0x2c),
182 	DEFINE_RES_IRQ(evt2irq(0xe00)),
183 	DEFINE_RES_IRQ(evt2irq(0xe20)),
184 	DEFINE_RES_IRQ(evt2irq(0xe40)),
185 };
186 
187 static struct platform_device tmu1_device = {
188 	.name		= "sh-tmu",
189 	.id		= 1,
190 	.dev = {
191 		.platform_data	= &tmu1_platform_data,
192 	},
193 	.resource	= tmu1_resources,
194 	.num_resources	= ARRAY_SIZE(tmu1_resources),
195 };
196 
197 static struct platform_device *sh7763_devices[] __initdata = {
198 	&scif0_device,
199 	&scif1_device,
200 	&scif2_device,
201 	&tmu0_device,
202 	&tmu1_device,
203 	&rtc_device,
204 	&usb_ohci_device,
205 	&usbf_device,
206 };
207 
208 static int __init sh7763_devices_setup(void)
209 {
210 	return platform_add_devices(sh7763_devices,
211 				    ARRAY_SIZE(sh7763_devices));
212 }
213 arch_initcall(sh7763_devices_setup);
214 
215 static struct platform_device *sh7763_early_devices[] __initdata = {
216 	&scif0_device,
217 	&scif1_device,
218 	&scif2_device,
219 	&tmu0_device,
220 	&tmu1_device,
221 };
222 
223 void __init plat_early_device_setup(void)
224 {
225 	sh_early_platform_add_devices(sh7763_early_devices,
226 				   ARRAY_SIZE(sh7763_early_devices));
227 }
228 
229 enum {
230 	UNUSED = 0,
231 
232 	/* interrupt sources */
233 
234 	IRL_LLLL, IRL_LLLH, IRL_LLHL, IRL_LLHH,
235 	IRL_LHLL, IRL_LHLH, IRL_LHHL, IRL_LHHH,
236 	IRL_HLLL, IRL_HLLH, IRL_HLHL, IRL_HLHH,
237 	IRL_HHLL, IRL_HHLH, IRL_HHHL,
238 
239 	IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7,
240 	RTC, WDT, TMU0, TMU1, TMU2, TMU2_TICPI,
241 	HUDI, LCDC, DMAC, SCIF0, IIC0, IIC1, CMT, GETHER, HAC,
242 	PCISERR, PCIINTA, PCIINTB, PCIINTC, PCIINTD, PCIC5,
243 	STIF0, STIF1, SCIF1, SIOF0, SIOF1, SIOF2,
244 	USBH, USBF, TPU, PCC, MMCIF, SIM,
245 	TMU3, TMU4, TMU5, ADC, SSI0, SSI1, SSI2, SSI3,
246 	SCIF2, GPIO,
247 
248 	/* interrupt groups */
249 
250 	TMU012, TMU345,
251 };
252 
253 static struct intc_vect vectors[] __initdata = {
254 	INTC_VECT(RTC, 0x480), INTC_VECT(RTC, 0x4a0),
255 	INTC_VECT(RTC, 0x4c0),
256 	INTC_VECT(WDT, 0x560), INTC_VECT(TMU0, 0x580),
257 	INTC_VECT(TMU1, 0x5a0), INTC_VECT(TMU2, 0x5c0),
258 	INTC_VECT(TMU2_TICPI, 0x5e0), INTC_VECT(HUDI, 0x600),
259 	INTC_VECT(LCDC, 0x620),
260 	INTC_VECT(DMAC, 0x640), INTC_VECT(DMAC, 0x660),
261 	INTC_VECT(DMAC, 0x680), INTC_VECT(DMAC, 0x6a0),
262 	INTC_VECT(DMAC, 0x6c0),
263 	INTC_VECT(SCIF0, 0x700), INTC_VECT(SCIF0, 0x720),
264 	INTC_VECT(SCIF0, 0x740), INTC_VECT(SCIF0, 0x760),
265 	INTC_VECT(DMAC, 0x780), INTC_VECT(DMAC, 0x7a0),
266 	INTC_VECT(IIC0, 0x8A0), INTC_VECT(IIC1, 0x8C0),
267 	INTC_VECT(CMT, 0x900), INTC_VECT(GETHER, 0x920),
268 	INTC_VECT(GETHER, 0x940), INTC_VECT(GETHER, 0x960),
269 	INTC_VECT(HAC, 0x980),
270 	INTC_VECT(PCISERR, 0xa00), INTC_VECT(PCIINTA, 0xa20),
271 	INTC_VECT(PCIINTB, 0xa40), INTC_VECT(PCIINTC, 0xa60),
272 	INTC_VECT(PCIINTD, 0xa80), INTC_VECT(PCIC5, 0xaa0),
273 	INTC_VECT(PCIC5, 0xac0), INTC_VECT(PCIC5, 0xae0),
274 	INTC_VECT(PCIC5, 0xb00), INTC_VECT(PCIC5, 0xb20),
275 	INTC_VECT(STIF0, 0xb40), INTC_VECT(STIF1, 0xb60),
276 	INTC_VECT(SCIF1, 0xb80), INTC_VECT(SCIF1, 0xba0),
277 	INTC_VECT(SCIF1, 0xbc0), INTC_VECT(SCIF1, 0xbe0),
278 	INTC_VECT(SIOF0, 0xc00), INTC_VECT(SIOF1, 0xc20),
279 	INTC_VECT(USBH, 0xc60), INTC_VECT(USBF, 0xc80),
280 	INTC_VECT(USBF, 0xca0),
281 	INTC_VECT(TPU, 0xcc0), INTC_VECT(PCC, 0xce0),
282 	INTC_VECT(MMCIF, 0xd00), INTC_VECT(MMCIF, 0xd20),
283 	INTC_VECT(MMCIF, 0xd40), INTC_VECT(MMCIF, 0xd60),
284 	INTC_VECT(SIM, 0xd80), INTC_VECT(SIM, 0xda0),
285 	INTC_VECT(SIM, 0xdc0), INTC_VECT(SIM, 0xde0),
286 	INTC_VECT(TMU3, 0xe00), INTC_VECT(TMU4, 0xe20),
287 	INTC_VECT(TMU5, 0xe40), INTC_VECT(ADC, 0xe60),
288 	INTC_VECT(SSI0, 0xe80), INTC_VECT(SSI1, 0xea0),
289 	INTC_VECT(SSI2, 0xec0), INTC_VECT(SSI3, 0xee0),
290 	INTC_VECT(SCIF2, 0xf00), INTC_VECT(SCIF2, 0xf20),
291 	INTC_VECT(SCIF2, 0xf40), INTC_VECT(SCIF2, 0xf60),
292 	INTC_VECT(GPIO, 0xf80), INTC_VECT(GPIO, 0xfa0),
293 	INTC_VECT(GPIO, 0xfc0), INTC_VECT(GPIO, 0xfe0),
294 };
295 
296 static struct intc_group groups[] __initdata = {
297 	INTC_GROUP(TMU012, TMU0, TMU1, TMU2, TMU2_TICPI),
298 	INTC_GROUP(TMU345, TMU3, TMU4, TMU5),
299 };
300 
301 static struct intc_mask_reg mask_registers[] __initdata = {
302 	{ 0xffd40038, 0xffd4003c, 32, /* INT2MSKR / INT2MSKCR */
303 	  { 0, 0, 0, 0, 0, 0, GPIO, 0,
304 	    SSI0, MMCIF, 0, SIOF0, PCIC5, PCIINTD, PCIINTC, PCIINTB,
305 	    PCIINTA, PCISERR, HAC, CMT, 0, 0, 0, DMAC,
306 	    HUDI, 0, WDT, SCIF1, SCIF0, RTC, TMU345, TMU012 } },
307 	{ 0xffd400d0, 0xffd400d4, 32, /* INT2MSKR1 / INT2MSKCR1 */
308 	  { 0, 0, 0, 0, 0, 0, SCIF2, USBF,
309 	    0, 0, STIF1, STIF0, 0, 0, USBH, GETHER,
310 	    PCC, 0, 0, ADC, TPU, SIM, SIOF2, SIOF1,
311 	    LCDC, 0, IIC1, IIC0, SSI3, SSI2, SSI1, 0 } },
312 };
313 
314 static struct intc_prio_reg prio_registers[] __initdata = {
315 	{ 0xffd40000, 0, 32, 8, /* INT2PRI0 */ { TMU0, TMU1,
316 						 TMU2, TMU2_TICPI } },
317 	{ 0xffd40004, 0, 32, 8, /* INT2PRI1 */ { TMU3, TMU4, TMU5, RTC } },
318 	{ 0xffd40008, 0, 32, 8, /* INT2PRI2 */ { SCIF0, SCIF1, WDT } },
319 	{ 0xffd4000c, 0, 32, 8, /* INT2PRI3 */ { HUDI, DMAC, ADC } },
320 	{ 0xffd40010, 0, 32, 8, /* INT2PRI4 */ { CMT, HAC,
321 						 PCISERR, PCIINTA } },
322 	{ 0xffd40014, 0, 32, 8, /* INT2PRI5 */ { PCIINTB, PCIINTC,
323 						 PCIINTD, PCIC5 } },
324 	{ 0xffd40018, 0, 32, 8, /* INT2PRI6 */ { SIOF0, USBF, MMCIF, SSI0 } },
325 	{ 0xffd4001c, 0, 32, 8, /* INT2PRI7 */ { SCIF2, GPIO } },
326 	{ 0xffd400a0, 0, 32, 8, /* INT2PRI8 */ { SSI3, SSI2, SSI1, 0 } },
327 	{ 0xffd400a4, 0, 32, 8, /* INT2PRI9 */ { LCDC, 0, IIC1, IIC0 } },
328 	{ 0xffd400a8, 0, 32, 8, /* INT2PRI10 */ { TPU, SIM, SIOF2, SIOF1 } },
329 	{ 0xffd400ac, 0, 32, 8, /* INT2PRI11 */ { PCC } },
330 	{ 0xffd400b0, 0, 32, 8, /* INT2PRI12 */ { 0, 0, USBH, GETHER } },
331 	{ 0xffd400b4, 0, 32, 8, /* INT2PRI13 */ { 0, 0, STIF1, STIF0 } },
332 };
333 
334 static DECLARE_INTC_DESC(intc_desc, "sh7763", vectors, groups,
335 			 mask_registers, prio_registers, NULL);
336 
337 /* Support for external interrupt pins in IRQ mode */
338 static struct intc_vect irq_vectors[] __initdata = {
339 	INTC_VECT(IRQ0, 0x240), INTC_VECT(IRQ1, 0x280),
340 	INTC_VECT(IRQ2, 0x2c0), INTC_VECT(IRQ3, 0x300),
341 	INTC_VECT(IRQ4, 0x340), INTC_VECT(IRQ5, 0x380),
342 	INTC_VECT(IRQ6, 0x3c0), INTC_VECT(IRQ7, 0x200),
343 };
344 
345 static struct intc_mask_reg irq_mask_registers[] __initdata = {
346 	{ 0xffd00044, 0xffd00064, 32, /* INTMSK0 / INTMSKCLR0 */
347 	  { IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7 } },
348 };
349 
350 static struct intc_prio_reg irq_prio_registers[] __initdata = {
351 	{ 0xffd00010, 0, 32, 4, /* INTPRI */ { IRQ0, IRQ1, IRQ2, IRQ3,
352 					       IRQ4, IRQ5, IRQ6, IRQ7 } },
353 };
354 
355 static struct intc_sense_reg irq_sense_registers[] __initdata = {
356 	{ 0xffd0001c, 32, 2, /* ICR1 */   { IRQ0, IRQ1, IRQ2, IRQ3,
357 					    IRQ4, IRQ5, IRQ6, IRQ7 } },
358 };
359 
360 static struct intc_mask_reg irq_ack_registers[] __initdata = {
361 	{ 0xffd00024, 0, 32, /* INTREQ */
362 	  { IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5, IRQ6, IRQ7 } },
363 };
364 
365 static DECLARE_INTC_DESC_ACK(intc_irq_desc, "sh7763-irq", irq_vectors,
366 			     NULL, irq_mask_registers, irq_prio_registers,
367 			     irq_sense_registers, irq_ack_registers);
368 
369 
370 /* External interrupt pins in IRL mode */
371 static struct intc_vect irl_vectors[] __initdata = {
372 	INTC_VECT(IRL_LLLL, 0x200), INTC_VECT(IRL_LLLH, 0x220),
373 	INTC_VECT(IRL_LLHL, 0x240), INTC_VECT(IRL_LLHH, 0x260),
374 	INTC_VECT(IRL_LHLL, 0x280), INTC_VECT(IRL_LHLH, 0x2a0),
375 	INTC_VECT(IRL_LHHL, 0x2c0), INTC_VECT(IRL_LHHH, 0x2e0),
376 	INTC_VECT(IRL_HLLL, 0x300), INTC_VECT(IRL_HLLH, 0x320),
377 	INTC_VECT(IRL_HLHL, 0x340), INTC_VECT(IRL_HLHH, 0x360),
378 	INTC_VECT(IRL_HHLL, 0x380), INTC_VECT(IRL_HHLH, 0x3a0),
379 	INTC_VECT(IRL_HHHL, 0x3c0),
380 };
381 
382 static struct intc_mask_reg irl3210_mask_registers[] __initdata = {
383 	{ 0xffd40080, 0xffd40084, 32, /* INTMSK2 / INTMSKCLR2 */
384 	  { IRL_LLLL, IRL_LLLH, IRL_LLHL, IRL_LLHH,
385 	    IRL_LHLL, IRL_LHLH, IRL_LHHL, IRL_LHHH,
386 	    IRL_HLLL, IRL_HLLH, IRL_HLHL, IRL_HLHH,
387 	    IRL_HHLL, IRL_HHLH, IRL_HHHL, } },
388 };
389 
390 static struct intc_mask_reg irl7654_mask_registers[] __initdata = {
391 	{ 0xffd40080, 0xffd40084, 32, /* INTMSK2 / INTMSKCLR2 */
392 	  { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
393 	    IRL_LLLL, IRL_LLLH, IRL_LLHL, IRL_LLHH,
394 	    IRL_LHLL, IRL_LHLH, IRL_LHHL, IRL_LHHH,
395 	    IRL_HLLL, IRL_HLLH, IRL_HLHL, IRL_HLHH,
396 	    IRL_HHLL, IRL_HHLH, IRL_HHHL, } },
397 };
398 
399 static DECLARE_INTC_DESC(intc_irl7654_desc, "sh7763-irl7654", irl_vectors,
400 			NULL, irl7654_mask_registers, NULL, NULL);
401 
402 static DECLARE_INTC_DESC(intc_irl3210_desc, "sh7763-irl3210", irl_vectors,
403 			NULL, irl3210_mask_registers, NULL, NULL);
404 
405 #define INTC_ICR0	0xffd00000
406 #define INTC_INTMSK0	0xffd00044
407 #define INTC_INTMSK1	0xffd00048
408 #define INTC_INTMSK2	0xffd40080
409 #define INTC_INTMSKCLR1	0xffd00068
410 #define INTC_INTMSKCLR2	0xffd40084
411 
412 void __init plat_irq_setup(void)
413 {
414 	/* disable IRQ7-0 */
415 	__raw_writel(0xff000000, INTC_INTMSK0);
416 
417 	/* disable IRL3-0 + IRL7-4 */
418 	__raw_writel(0xc0000000, INTC_INTMSK1);
419 	__raw_writel(0xfffefffe, INTC_INTMSK2);
420 
421 	register_intc_controller(&intc_desc);
422 }
423 
424 void __init plat_irq_setup_pins(int mode)
425 {
426 	switch (mode) {
427 	case IRQ_MODE_IRQ:
428 		/* select IRQ mode for IRL3-0 + IRL7-4 */
429 		__raw_writel(__raw_readl(INTC_ICR0) | 0x00c00000, INTC_ICR0);
430 		register_intc_controller(&intc_irq_desc);
431 		break;
432 	case IRQ_MODE_IRL7654:
433 		/* enable IRL7-4 but don't provide any masking */
434 		__raw_writel(0x40000000, INTC_INTMSKCLR1);
435 		__raw_writel(0x0000fffe, INTC_INTMSKCLR2);
436 		break;
437 	case IRQ_MODE_IRL3210:
438 		/* enable IRL0-3 but don't provide any masking */
439 		__raw_writel(0x80000000, INTC_INTMSKCLR1);
440 		__raw_writel(0xfffe0000, INTC_INTMSKCLR2);
441 		break;
442 	case IRQ_MODE_IRL7654_MASK:
443 		/* enable IRL7-4 and mask using cpu intc controller */
444 		__raw_writel(0x40000000, INTC_INTMSKCLR1);
445 		register_intc_controller(&intc_irl7654_desc);
446 		break;
447 	case IRQ_MODE_IRL3210_MASK:
448 		/* enable IRL0-3 and mask using cpu intc controller */
449 		__raw_writel(0x80000000, INTC_INTMSKCLR1);
450 		register_intc_controller(&intc_irl3210_desc);
451 		break;
452 	default:
453 		BUG();
454 	}
455 }
456