Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/arch/sh/kernel/cpu/sh4a/setup-sh7763.c
26498 views
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
457