aboutsummaryrefslogtreecommitdiffstats
path: root/arch/sh/kernel/cpu
diff options
context:
space:
mode:
Diffstat (limited to 'arch/sh/kernel/cpu')
-rw-r--r--arch/sh/kernel/cpu/irq/intc-sh5.c73
-rw-r--r--arch/sh/kernel/cpu/irq/intc.c93
-rw-r--r--arch/sh/kernel/cpu/sh2a/fpu.c4
-rw-r--r--arch/sh/kernel/cpu/sh3/Makefile2
-rw-r--r--arch/sh/kernel/cpu/sh3/setup-sh3.c71
-rw-r--r--arch/sh/kernel/cpu/sh3/setup-sh7705.c22
-rw-r--r--arch/sh/kernel/cpu/sh3/setup-sh770x.c32
-rw-r--r--arch/sh/kernel/cpu/sh3/setup-sh7710.c25
-rw-r--r--arch/sh/kernel/cpu/sh3/setup-sh7720.c35
-rw-r--r--arch/sh/kernel/cpu/sh5/entry.S28
-rw-r--r--arch/sh/kernel/cpu/sh5/probe.c4
11 files changed, 246 insertions, 143 deletions
diff --git a/arch/sh/kernel/cpu/irq/intc-sh5.c b/arch/sh/kernel/cpu/irq/intc-sh5.c
index d6e0e2bdaad5..de45c6a3e33b 100644
--- a/arch/sh/kernel/cpu/irq/intc-sh5.c
+++ b/arch/sh/kernel/cpu/irq/intc-sh5.c
@@ -184,9 +184,8 @@ int intc_irq_describe(char* p, int irq)
184 184
185void __init plat_irq_setup(void) 185void __init plat_irq_setup(void)
186{ 186{
187 unsigned long long __dummy0, __dummy1=~0x00000000100000f0; 187 unsigned long long __dummy0, __dummy1=~0x00000000100000f0;
188 unsigned long reg; 188 unsigned long reg;
189 unsigned long data;
190 int i; 189 int i;
191 190
192 intc_virt = onchip_remap(INTC_BASE, 1024, "INTC"); 191 intc_virt = onchip_remap(INTC_BASE, 1024, "INTC");
@@ -196,11 +195,8 @@ void __init plat_irq_setup(void)
196 195
197 196
198 /* Set default: per-line enable/disable, priority driven ack/eoi */ 197 /* Set default: per-line enable/disable, priority driven ack/eoi */
199 for (i = 0; i < NR_INTC_IRQS; i++) { 198 for (i = 0; i < NR_INTC_IRQS; i++)
200 if (platform_int_priority[i] != NO_PRIORITY) { 199 irq_desc[i].chip = &intc_irq_type;
201 irq_desc[i].chip = &intc_irq_type;
202 }
203 }
204 200
205 201
206 /* Disable all interrupts and set all priorities to 0 to avoid trouble */ 202 /* Disable all interrupts and set all priorities to 0 to avoid trouble */
@@ -211,35 +207,42 @@ void __init plat_irq_setup(void)
211 ctrl_outl( NO_PRIORITY, reg); 207 ctrl_outl( NO_PRIORITY, reg);
212 208
213 209
214 /* Set IRLM */ 210#ifdef CONFIG_SH_CAYMAN
215 /* If all the priorities are set to 'no priority', then 211 {
216 * assume we are using encoded mode. 212 unsigned long data;
217 */ 213
218 irlm = platform_int_priority[IRQ_IRL0] + platform_int_priority[IRQ_IRL1] + \ 214 /* Set IRLM */
219 platform_int_priority[IRQ_IRL2] + platform_int_priority[IRQ_IRL3]; 215 /* If all the priorities are set to 'no priority', then
220 216 * assume we are using encoded mode.
221 if (irlm == NO_PRIORITY) { 217 */
222 /* IRLM = 0 */ 218 irlm = platform_int_priority[IRQ_IRL0] +
223 reg = INTC_ICR_CLEAR; 219 platform_int_priority[IRQ_IRL1] +
224 i = IRQ_INTA; 220 platform_int_priority[IRQ_IRL2] +
225 printk("Trying to use encoded IRL0-3. IRLs unsupported.\n"); 221 platform_int_priority[IRQ_IRL3];
226 } else { 222 if (irlm == NO_PRIORITY) {
227 /* IRLM = 1 */ 223 /* IRLM = 0 */
228 reg = INTC_ICR_SET; 224 reg = INTC_ICR_CLEAR;
229 i = IRQ_IRL0; 225 i = IRQ_INTA;
230 } 226 printk("Trying to use encoded IRL0-3. IRLs unsupported.\n");
231 ctrl_outl(INTC_ICR_IRLM, reg); 227 } else {
232 228 /* IRLM = 1 */
233 /* Set interrupt priorities according to platform description */ 229 reg = INTC_ICR_SET;
234 for (data = 0, reg = INTC_INTPRI_0; i < NR_INTC_IRQS; i++) { 230 i = IRQ_IRL0;
235 data |= platform_int_priority[i] << ((i % INTC_INTPRI_PPREG) * 4);
236 if ((i % INTC_INTPRI_PPREG) == (INTC_INTPRI_PPREG - 1)) {
237 /* Upon the 7th, set Priority Register */
238 ctrl_outl(data, reg);
239 data = 0;
240 reg += 8;
241 } 231 }
242 } 232 ctrl_outl(INTC_ICR_IRLM, reg);
233
234 /* Set interrupt priorities according to platform description */
235 for (data = 0, reg = INTC_INTPRI_0; i < NR_INTC_IRQS; i++) {
236 data |= platform_int_priority[i] <<
237 ((i % INTC_INTPRI_PPREG) * 4);
238 if ((i % INTC_INTPRI_PPREG) == (INTC_INTPRI_PPREG - 1)) {
239 /* Upon the 7th, set Priority Register */
240 ctrl_outl(data, reg);
241 data = 0;
242 reg += 8;
243 }
244 }
245#endif
243 246
244 /* 247 /*
245 * And now let interrupts come in. 248 * And now let interrupts come in.
diff --git a/arch/sh/kernel/cpu/irq/intc.c b/arch/sh/kernel/cpu/irq/intc.c
index 84806b2027f8..da5dae787888 100644
--- a/arch/sh/kernel/cpu/irq/intc.c
+++ b/arch/sh/kernel/cpu/irq/intc.c
@@ -1,7 +1,7 @@
1/* 1/*
2 * Shared interrupt handling code for IPR and INTC2 types of IRQs. 2 * Shared interrupt handling code for IPR and INTC2 types of IRQs.
3 * 3 *
4 * Copyright (C) 2007 Magnus Damm 4 * Copyright (C) 2007, 2008 Magnus Damm
5 * 5 *
6 * Based on intc2.c and ipr.c 6 * Based on intc2.c and ipr.c
7 * 7 *
@@ -62,6 +62,9 @@ struct intc_desc_int {
62#endif 62#endif
63 63
64static unsigned int intc_prio_level[NR_IRQS]; /* for now */ 64static unsigned int intc_prio_level[NR_IRQS]; /* for now */
65#ifdef CONFIG_CPU_SH3
66static unsigned long ack_handle[NR_IRQS];
67#endif
65 68
66static inline struct intc_desc_int *get_intc_desc(unsigned int irq) 69static inline struct intc_desc_int *get_intc_desc(unsigned int irq)
67{ 70{
@@ -98,17 +101,26 @@ static void write_32(unsigned long addr, unsigned long h, unsigned long data)
98 101
99static void modify_8(unsigned long addr, unsigned long h, unsigned long data) 102static void modify_8(unsigned long addr, unsigned long h, unsigned long data)
100{ 103{
104 unsigned long flags;
105 local_irq_save(flags);
101 ctrl_outb(set_field(ctrl_inb(addr), data, h), addr); 106 ctrl_outb(set_field(ctrl_inb(addr), data, h), addr);
107 local_irq_restore(flags);
102} 108}
103 109
104static void modify_16(unsigned long addr, unsigned long h, unsigned long data) 110static void modify_16(unsigned long addr, unsigned long h, unsigned long data)
105{ 111{
112 unsigned long flags;
113 local_irq_save(flags);
106 ctrl_outw(set_field(ctrl_inw(addr), data, h), addr); 114 ctrl_outw(set_field(ctrl_inw(addr), data, h), addr);
115 local_irq_restore(flags);
107} 116}
108 117
109static void modify_32(unsigned long addr, unsigned long h, unsigned long data) 118static void modify_32(unsigned long addr, unsigned long h, unsigned long data)
110{ 119{
120 unsigned long flags;
121 local_irq_save(flags);
111 ctrl_outl(set_field(ctrl_inl(addr), data, h), addr); 122 ctrl_outl(set_field(ctrl_inl(addr), data, h), addr);
123 local_irq_restore(flags);
112} 124}
113 125
114enum { REG_FN_ERR = 0, REG_FN_WRITE_BASE = 1, REG_FN_MODIFY_BASE = 5 }; 126enum { REG_FN_ERR = 0, REG_FN_WRITE_BASE = 1, REG_FN_MODIFY_BASE = 5 };
@@ -219,6 +231,25 @@ static void intc_disable(unsigned int irq)
219 } 231 }
220} 232}
221 233
234#ifdef CONFIG_CPU_SH3
235static void intc_mask_ack(unsigned int irq)
236{
237 struct intc_desc_int *d = get_intc_desc(irq);
238 unsigned long handle = ack_handle[irq];
239 unsigned long addr;
240
241 intc_disable(irq);
242
243 /* read register and write zero only to the assocaited bit */
244
245 if (handle) {
246 addr = INTC_REG(d, _INTC_ADDR_D(handle), 0);
247 ctrl_inb(addr);
248 ctrl_outb(0x3f ^ set_field(0, 1, handle), addr);
249 }
250}
251#endif
252
222static struct intc_handle_int *intc_find_irq(struct intc_handle_int *hp, 253static struct intc_handle_int *intc_find_irq(struct intc_handle_int *hp,
223 unsigned int nr_hp, 254 unsigned int nr_hp,
224 unsigned int irq) 255 unsigned int irq)
@@ -280,7 +311,12 @@ static unsigned char intc_irq_sense_table[IRQ_TYPE_SENSE_MASK + 1] = {
280 [IRQ_TYPE_EDGE_FALLING] = VALID(0), 311 [IRQ_TYPE_EDGE_FALLING] = VALID(0),
281 [IRQ_TYPE_EDGE_RISING] = VALID(1), 312 [IRQ_TYPE_EDGE_RISING] = VALID(1),
282 [IRQ_TYPE_LEVEL_LOW] = VALID(2), 313 [IRQ_TYPE_LEVEL_LOW] = VALID(2),
314 /* SH7706, SH7707 and SH7709 do not support high level triggered */
315#if !defined(CONFIG_CPU_SUBTYPE_SH7706) && \
316 !defined(CONFIG_CPU_SUBTYPE_SH7707) && \
317 !defined(CONFIG_CPU_SUBTYPE_SH7709)
283 [IRQ_TYPE_LEVEL_HIGH] = VALID(3), 318 [IRQ_TYPE_LEVEL_HIGH] = VALID(3),
319#endif
284}; 320};
285 321
286static int intc_set_sense(unsigned int irq, unsigned int type) 322static int intc_set_sense(unsigned int irq, unsigned int type)
@@ -430,6 +466,40 @@ static unsigned int __init intc_prio_data(struct intc_desc *desc,
430 return 0; 466 return 0;
431} 467}
432 468
469#ifdef CONFIG_CPU_SH3
470static unsigned int __init intc_ack_data(struct intc_desc *desc,
471 struct intc_desc_int *d,
472 intc_enum enum_id)
473{
474 struct intc_mask_reg *mr = desc->ack_regs;
475 unsigned int i, j, fn, mode;
476 unsigned long reg_e, reg_d;
477
478 for (i = 0; mr && enum_id && i < desc->nr_ack_regs; i++) {
479 mr = desc->ack_regs + i;
480
481 for (j = 0; j < ARRAY_SIZE(mr->enum_ids); j++) {
482 if (mr->enum_ids[j] != enum_id)
483 continue;
484
485 fn = REG_FN_MODIFY_BASE;
486 mode = MODE_ENABLE_REG;
487 reg_e = mr->set_reg;
488 reg_d = mr->set_reg;
489
490 fn += (mr->reg_width >> 3) - 1;
491 return _INTC_MK(fn, mode,
492 intc_get_reg(d, reg_e),
493 intc_get_reg(d, reg_d),
494 1,
495 (mr->reg_width - 1) - j);
496 }
497 }
498
499 return 0;
500}
501#endif
502
433static unsigned int __init intc_sense_data(struct intc_desc *desc, 503static unsigned int __init intc_sense_data(struct intc_desc *desc,
434 struct intc_desc_int *d, 504 struct intc_desc_int *d,
435 intc_enum enum_id) 505 intc_enum enum_id)
@@ -530,6 +600,11 @@ static void __init intc_register_irq(struct intc_desc *desc,
530 600
531 /* irq should be disabled by default */ 601 /* irq should be disabled by default */
532 d->chip.mask(irq); 602 d->chip.mask(irq);
603
604#ifdef CONFIG_CPU_SH3
605 if (desc->ack_regs)
606 ack_handle[irq] = intc_ack_data(desc, d, enum_id);
607#endif
533} 608}
534 609
535static unsigned int __init save_reg(struct intc_desc_int *d, 610static unsigned int __init save_reg(struct intc_desc_int *d,
@@ -560,6 +635,9 @@ void __init register_intc_controller(struct intc_desc *desc)
560 d->nr_reg += desc->prio_regs ? desc->nr_prio_regs * 2 : 0; 635 d->nr_reg += desc->prio_regs ? desc->nr_prio_regs * 2 : 0;
561 d->nr_reg += desc->sense_regs ? desc->nr_sense_regs : 0; 636 d->nr_reg += desc->sense_regs ? desc->nr_sense_regs : 0;
562 637
638#ifdef CONFIG_CPU_SH3
639 d->nr_reg += desc->ack_regs ? desc->nr_ack_regs : 0;
640#endif
563 d->reg = alloc_bootmem(d->nr_reg * sizeof(*d->reg)); 641 d->reg = alloc_bootmem(d->nr_reg * sizeof(*d->reg));
564#ifdef CONFIG_SMP 642#ifdef CONFIG_SMP
565 d->smp = alloc_bootmem(d->nr_reg * sizeof(*d->smp)); 643 d->smp = alloc_bootmem(d->nr_reg * sizeof(*d->smp));
@@ -592,14 +670,23 @@ void __init register_intc_controller(struct intc_desc *desc)
592 } 670 }
593 } 671 }
594 672
595 BUG_ON(k > 256); /* _INTC_ADDR_E() and _INTC_ADDR_D() are 8 bits */
596
597 d->chip.name = desc->name; 673 d->chip.name = desc->name;
598 d->chip.mask = intc_disable; 674 d->chip.mask = intc_disable;
599 d->chip.unmask = intc_enable; 675 d->chip.unmask = intc_enable;
600 d->chip.mask_ack = intc_disable; 676 d->chip.mask_ack = intc_disable;
601 d->chip.set_type = intc_set_sense; 677 d->chip.set_type = intc_set_sense;
602 678
679#ifdef CONFIG_CPU_SH3
680 if (desc->ack_regs) {
681 for (i = 0; i < desc->nr_ack_regs; i++)
682 k += save_reg(d, k, desc->ack_regs[i].set_reg, 0);
683
684 d->chip.mask_ack = intc_mask_ack;
685 }
686#endif
687
688 BUG_ON(k > 256); /* _INTC_ADDR_E() and _INTC_ADDR_D() are 8 bits */
689
603 for (i = 0; i < desc->nr_vectors; i++) { 690 for (i = 0; i < desc->nr_vectors; i++) {
604 struct intc_vect *vect = desc->vectors + i; 691 struct intc_vect *vect = desc->vectors + i;
605 692
diff --git a/arch/sh/kernel/cpu/sh2a/fpu.c b/arch/sh/kernel/cpu/sh2a/fpu.c
index 5627c0b3ffa8..6df2fb98eb30 100644
--- a/arch/sh/kernel/cpu/sh2a/fpu.c
+++ b/arch/sh/kernel/cpu/sh2a/fpu.c
@@ -300,7 +300,7 @@ static int denormal_addf(int hx, int hy)
300 iy = hy & 0x7fffffff; 300 iy = hy & 0x7fffffff;
301 if (iy < 0x00800000) { 301 if (iy < 0x00800000) {
302 ix = denormal_subf1(ix, iy); 302 ix = denormal_subf1(ix, iy);
303 if (ix < 0) { 303 if ((int) ix < 0) {
304 ix = -ix; 304 ix = -ix;
305 sign ^= 0x80000000; 305 sign ^= 0x80000000;
306 } 306 }
@@ -385,7 +385,7 @@ static long long denormal_addd(long long hx, long long hy)
385 iy = hy & 0x7fffffffffffffffLL; 385 iy = hy & 0x7fffffffffffffffLL;
386 if (iy < 0x0010000000000000LL) { 386 if (iy < 0x0010000000000000LL) {
387 ix = denormal_subd1(ix, iy); 387 ix = denormal_subd1(ix, iy);
388 if (ix < 0) { 388 if ((int) ix < 0) {
389 ix = -ix; 389 ix = -ix;
390 sign ^= 0x8000000000000000LL; 390 sign ^= 0x8000000000000000LL;
391 } 391 }
diff --git a/arch/sh/kernel/cpu/sh3/Makefile b/arch/sh/kernel/cpu/sh3/Makefile
index 3ae4d9111f19..511de55af832 100644
--- a/arch/sh/kernel/cpu/sh3/Makefile
+++ b/arch/sh/kernel/cpu/sh3/Makefile
@@ -2,7 +2,7 @@
2# Makefile for the Linux/SuperH SH-3 backends. 2# Makefile for the Linux/SuperH SH-3 backends.
3# 3#
4 4
5obj-y := ex.o probe.o entry.o 5obj-y := ex.o probe.o entry.o setup-sh3.o
6 6
7# CPU subtype setup 7# CPU subtype setup
8obj-$(CONFIG_CPU_SUBTYPE_SH7705) += setup-sh7705.o 8obj-$(CONFIG_CPU_SUBTYPE_SH7705) += setup-sh7705.o
diff --git a/arch/sh/kernel/cpu/sh3/setup-sh3.c b/arch/sh/kernel/cpu/sh3/setup-sh3.c
new file mode 100644
index 000000000000..c98846857855
--- /dev/null
+++ b/arch/sh/kernel/cpu/sh3/setup-sh3.c
@@ -0,0 +1,71 @@
1/*
2 * Shared SH3 Setup code
3 *
4 * Copyright (C) 2008 Magnus Damm
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
11#include <linux/init.h>
12#include <linux/irq.h>
13#include <linux/io.h>
14
15/* All SH3 devices are equipped with IRQ0->5 (except sh7708) */
16
17enum {
18 UNUSED = 0,
19
20 /* interrupt sources */
21 IRQ0, IRQ1, IRQ2, IRQ3, IRQ4, IRQ5,
22};
23
24static struct intc_vect vectors_irq0123[] __initdata = {
25 INTC_VECT(IRQ0, 0x600), INTC_VECT(IRQ1, 0x620),
26 INTC_VECT(IRQ2, 0x640), INTC_VECT(IRQ3, 0x660),
27};
28
29static struct intc_vect vectors_irq45[] __initdata = {
30 INTC_VECT(IRQ4, 0x680), INTC_VECT(IRQ5, 0x6a0),
31};
32
33static struct intc_prio_reg prio_registers[] __initdata = {
34 { 0xa4000016, 0, 16, 4, /* IPRC */ { IRQ3, IRQ2, IRQ1, IRQ0 } },
35 { 0xa4000018, 0, 16, 4, /* IPRD */ { 0, 0, IRQ5, IRQ4 } },
36};
37
38static struct intc_mask_reg ack_registers[] __initdata = {
39 { 0xa4000004, 0, 8, /* IRR0 */
40 { 0, 0, IRQ5, IRQ4, IRQ3, IRQ2, IRQ1, IRQ0 } },
41};
42
43static struct intc_sense_reg sense_registers[] __initdata = {
44 { 0xa4000010, 16, 2, { 0, 0, IRQ5, IRQ4, IRQ3, IRQ2, IRQ1, IRQ0 } },
45};
46
47static DECLARE_INTC_DESC_ACK(intc_desc_irq0123, "sh3-irq0123",
48 vectors_irq0123, NULL, NULL,
49 prio_registers, sense_registers, ack_registers);
50
51static DECLARE_INTC_DESC_ACK(intc_desc_irq45, "sh3-irq45",
52 vectors_irq45, NULL, NULL,
53 prio_registers, sense_registers, ack_registers);
54
55#define INTC_ICR1 0xa4000010UL
56#define INTC_ICR1_IRQLVL (1<<14)
57
58void __init plat_irq_setup_pins(int mode)
59{
60 if (mode == IRQ_MODE_IRQ) {
61 ctrl_outw(ctrl_inw(INTC_ICR1) & ~INTC_ICR1_IRQLVL, INTC_ICR1);
62 register_intc_controller(&intc_desc_irq0123);
63 return;
64 }
65 BUG();
66}
67
68void __init plat_irq_setup_sh3(void)
69{
70 register_intc_controller(&intc_desc_irq45);
71}
diff --git a/arch/sh/kernel/cpu/sh3/setup-sh7705.c b/arch/sh/kernel/cpu/sh3/setup-sh7705.c
index f581534cb732..6468ae86b944 100644
--- a/arch/sh/kernel/cpu/sh3/setup-sh7705.c
+++ b/arch/sh/kernel/cpu/sh3/setup-sh7705.c
@@ -37,7 +37,7 @@ enum {
37}; 37};
38 38
39static struct intc_vect vectors[] __initdata = { 39static struct intc_vect vectors[] __initdata = {
40 INTC_VECT(IRQ4, 0x680), INTC_VECT(IRQ5, 0x6a0), 40 /* IRQ0->5 are handled in setup-sh3.c */
41 INTC_VECT(PINT07, 0x700), INTC_VECT(PINT815, 0x720), 41 INTC_VECT(PINT07, 0x700), INTC_VECT(PINT815, 0x720),
42 INTC_VECT(DMAC_DEI0, 0x800), INTC_VECT(DMAC_DEI1, 0x820), 42 INTC_VECT(DMAC_DEI0, 0x800), INTC_VECT(DMAC_DEI1, 0x820),
43 INTC_VECT(DMAC_DEI2, 0x840), INTC_VECT(DMAC_DEI3, 0x860), 43 INTC_VECT(DMAC_DEI2, 0x840), INTC_VECT(DMAC_DEI3, 0x860),
@@ -48,7 +48,7 @@ static struct intc_vect vectors[] __initdata = {
48 INTC_VECT(ADC_ADI, 0x980), 48 INTC_VECT(ADC_ADI, 0x980),
49 INTC_VECT(USB_USI0, 0xa20), INTC_VECT(USB_USI1, 0xa40), 49 INTC_VECT(USB_USI0, 0xa20), INTC_VECT(USB_USI1, 0xa40),
50 INTC_VECT(TPU0, 0xc00), INTC_VECT(TPU1, 0xc20), 50 INTC_VECT(TPU0, 0xc00), INTC_VECT(TPU1, 0xc20),
51 INTC_VECT(TPU3, 0xc80), INTC_VECT(TPU1, 0xca0), 51 INTC_VECT(TPU2, 0xc80), INTC_VECT(TPU3, 0xca0),
52 INTC_VECT(TMU0, 0x400), INTC_VECT(TMU1, 0x420), 52 INTC_VECT(TMU0, 0x400), INTC_VECT(TMU1, 0x420),
53 INTC_VECT(TMU2_TUNI, 0x440), INTC_VECT(TMU2_TICPI, 0x460), 53 INTC_VECT(TMU2_TUNI, 0x440), INTC_VECT(TMU2_TICPI, 0x460),
54 INTC_VECT(RTC_ATI, 0x480), INTC_VECT(RTC_PRI, 0x4a0), 54 INTC_VECT(RTC_ATI, 0x480), INTC_VECT(RTC_PRI, 0x4a0),
@@ -81,14 +81,6 @@ static struct intc_prio_reg prio_registers[] __initdata = {
81static DECLARE_INTC_DESC(intc_desc, "sh7705", vectors, groups, 81static DECLARE_INTC_DESC(intc_desc, "sh7705", vectors, groups,
82 NULL, prio_registers, NULL); 82 NULL, prio_registers, NULL);
83 83
84static struct intc_vect vectors_irq[] __initdata = {
85 INTC_VECT(IRQ0, 0x600), INTC_VECT(IRQ1, 0x620),
86 INTC_VECT(IRQ2, 0x640), INTC_VECT(IRQ3, 0x660),
87};
88
89static DECLARE_INTC_DESC(intc_desc_irq, "sh7705-irq", vectors_irq, NULL,
90 NULL, prio_registers, NULL);
91
92static struct plat_sci_port sci_platform_data[] = { 84static struct plat_sci_port sci_platform_data[] = {
93 { 85 {
94 .mapbase = 0xa4410000, 86 .mapbase = 0xa4410000,
@@ -159,16 +151,8 @@ static int __init sh7705_devices_setup(void)
159} 151}
160__initcall(sh7705_devices_setup); 152__initcall(sh7705_devices_setup);
161 153
162void __init plat_irq_setup_pins(int mode)
163{
164 if (mode == IRQ_MODE_IRQ) {
165 register_intc_controller(&intc_desc_irq);
166 return;
167 }
168 BUG();
169}
170
171void __init plat_irq_setup(void) 154void __init plat_irq_setup(void)
172{ 155{
173 register_intc_controller(&intc_desc); 156 register_intc_controller(&intc_desc);
157 plat_irq_setup_sh3();
174} 158}
diff --git a/arch/sh/kernel/cpu/sh3/setup-sh770x.c b/arch/sh/kernel/cpu/sh3/setup-sh770x.c
index d3733b13ea52..93c55e2ed952 100644
--- a/arch/sh/kernel/cpu/sh3/setup-sh770x.c
+++ b/arch/sh/kernel/cpu/sh3/setup-sh770x.c
@@ -52,7 +52,7 @@ static struct intc_vect vectors[] __initdata = {
52#if defined(CONFIG_CPU_SUBTYPE_SH7706) || \ 52#if defined(CONFIG_CPU_SUBTYPE_SH7706) || \
53 defined(CONFIG_CPU_SUBTYPE_SH7707) || \ 53 defined(CONFIG_CPU_SUBTYPE_SH7707) || \
54 defined(CONFIG_CPU_SUBTYPE_SH7709) 54 defined(CONFIG_CPU_SUBTYPE_SH7709)
55 INTC_VECT(IRQ4, 0x680), INTC_VECT(IRQ5, 0x6a0), 55 /* IRQ0->5 are handled in setup-sh3.c */
56 INTC_VECT(DMAC_DEI0, 0x800), INTC_VECT(DMAC_DEI1, 0x820), 56 INTC_VECT(DMAC_DEI0, 0x800), INTC_VECT(DMAC_DEI1, 0x820),
57 INTC_VECT(DMAC_DEI2, 0x840), INTC_VECT(DMAC_DEI3, 0x860), 57 INTC_VECT(DMAC_DEI2, 0x840), INTC_VECT(DMAC_DEI3, 0x860),
58 INTC_VECT(ADC_ADI, 0x980), 58 INTC_VECT(ADC_ADI, 0x980),
@@ -104,18 +104,6 @@ static struct intc_prio_reg prio_registers[] __initdata = {
104static DECLARE_INTC_DESC(intc_desc, "sh770x", vectors, groups, 104static DECLARE_INTC_DESC(intc_desc, "sh770x", vectors, groups,
105 NULL, prio_registers, NULL); 105 NULL, prio_registers, NULL);
106 106
107#if defined(CONFIG_CPU_SUBTYPE_SH7706) || \
108 defined(CONFIG_CPU_SUBTYPE_SH7707) || \
109 defined(CONFIG_CPU_SUBTYPE_SH7709)
110static struct intc_vect vectors_irq[] __initdata = {
111 INTC_VECT(IRQ0, 0x600), INTC_VECT(IRQ1, 0x620),
112 INTC_VECT(IRQ2, 0x640), INTC_VECT(IRQ3, 0x660),
113};
114
115static DECLARE_INTC_DESC(intc_desc_irq, "sh770x-irq", vectors_irq, NULL,
116 NULL, prio_registers, NULL);
117#endif
118
119static struct resource rtc_resources[] = { 107static struct resource rtc_resources[] = {
120 [0] = { 108 [0] = {
121 .start = 0xfffffec0, 109 .start = 0xfffffec0,
@@ -194,24 +182,12 @@ static int __init sh770x_devices_setup(void)
194} 182}
195__initcall(sh770x_devices_setup); 183__initcall(sh770x_devices_setup);
196 184
197#define INTC_ICR1 0xa4000010UL 185void __init plat_irq_setup(void)
198#define INTC_ICR1_IRQLVL (1<<14)
199
200void __init plat_irq_setup_pins(int mode)
201{ 186{
202 if (mode == IRQ_MODE_IRQ) { 187 register_intc_controller(&intc_desc);
203#if defined(CONFIG_CPU_SUBTYPE_SH7706) || \ 188#if defined(CONFIG_CPU_SUBTYPE_SH7706) || \
204 defined(CONFIG_CPU_SUBTYPE_SH7707) || \ 189 defined(CONFIG_CPU_SUBTYPE_SH7707) || \
205 defined(CONFIG_CPU_SUBTYPE_SH7709) 190 defined(CONFIG_CPU_SUBTYPE_SH7709)
206 ctrl_outw(ctrl_inw(INTC_ICR1) & ~INTC_ICR1_IRQLVL, INTC_ICR1); 191 plat_irq_setup_sh3();
207 register_intc_controller(&intc_desc_irq);
208 return;
209#endif 192#endif
210 }
211 BUG();
212}
213
214void __init plat_irq_setup(void)
215{
216 register_intc_controller(&intc_desc);
217} 193}
diff --git a/arch/sh/kernel/cpu/sh3/setup-sh7710.c b/arch/sh/kernel/cpu/sh3/setup-sh7710.c
index 7406c9ad9259..77eee481de47 100644
--- a/arch/sh/kernel/cpu/sh3/setup-sh7710.c
+++ b/arch/sh/kernel/cpu/sh3/setup-sh7710.c
@@ -38,7 +38,7 @@ enum {
38}; 38};
39 39
40static struct intc_vect vectors[] __initdata = { 40static struct intc_vect vectors[] __initdata = {
41 INTC_VECT(IRQ4, 0x680), INTC_VECT(IRQ5, 0x6a0), 41 /* IRQ0->5 are handled in setup-sh3.c */
42 INTC_VECT(DMAC_DEI0, 0x800), INTC_VECT(DMAC_DEI1, 0x820), 42 INTC_VECT(DMAC_DEI0, 0x800), INTC_VECT(DMAC_DEI1, 0x820),
43 INTC_VECT(DMAC_DEI2, 0x840), INTC_VECT(DMAC_DEI3, 0x860), 43 INTC_VECT(DMAC_DEI2, 0x840), INTC_VECT(DMAC_DEI3, 0x860),
44 INTC_VECT(SCIF0_ERI, 0x880), INTC_VECT(SCIF0_RXI, 0x8a0), 44 INTC_VECT(SCIF0_ERI, 0x880), INTC_VECT(SCIF0_RXI, 0x8a0),
@@ -79,10 +79,7 @@ static struct intc_prio_reg prio_registers[] __initdata = {
79 { 0xa4000016, 0, 16, 4, /* IPRC */ { IRQ3, IRQ2, IRQ1, IRQ0 } }, 79 { 0xa4000016, 0, 16, 4, /* IPRC */ { IRQ3, IRQ2, IRQ1, IRQ0 } },
80 { 0xa4000018, 0, 16, 4, /* IPRD */ { 0, 0, IRQ5, IRQ4 } }, 80 { 0xa4000018, 0, 16, 4, /* IPRD */ { 0, 0, IRQ5, IRQ4 } },
81 { 0xa400001a, 0, 16, 4, /* IPRE */ { DMAC1, SCIF0, SCIF1 } }, 81 { 0xa400001a, 0, 16, 4, /* IPRE */ { DMAC1, SCIF0, SCIF1 } },
82 { 0xa4080000, 0, 16, 4, /* IPRF */ { 0, DMAC2 } }, 82 { 0xa4080000, 0, 16, 4, /* IPRF */ { IPSEC, DMAC2 } },
83#ifdef CONFIG_CPU_SUBTYPE_SH7710
84 { 0xa4080000, 0, 16, 4, /* IPRF */ { IPSEC } },
85#endif
86 { 0xa4080002, 0, 16, 4, /* IPRG */ { EDMAC0, EDMAC1, EDMAC2 } }, 83 { 0xa4080002, 0, 16, 4, /* IPRG */ { EDMAC0, EDMAC1, EDMAC2 } },
87 { 0xa4080004, 0, 16, 4, /* IPRH */ { 0, 0, 0, SIOF0 } }, 84 { 0xa4080004, 0, 16, 4, /* IPRH */ { 0, 0, 0, SIOF0 } },
88 { 0xa4080006, 0, 16, 4, /* IPRI */ { 0, 0, SIOF1 } }, 85 { 0xa4080006, 0, 16, 4, /* IPRI */ { 0, 0, SIOF1 } },
@@ -91,14 +88,6 @@ static struct intc_prio_reg prio_registers[] __initdata = {
91static DECLARE_INTC_DESC(intc_desc, "sh7710", vectors, groups, 88static DECLARE_INTC_DESC(intc_desc, "sh7710", vectors, groups,
92 NULL, prio_registers, NULL); 89 NULL, prio_registers, NULL);
93 90
94static struct intc_vect vectors_irq[] __initdata = {
95 INTC_VECT(IRQ0, 0x600), INTC_VECT(IRQ1, 0x620),
96 INTC_VECT(IRQ2, 0x640), INTC_VECT(IRQ3, 0x660),
97};
98
99static DECLARE_INTC_DESC(intc_desc_irq, "sh7710-irq", vectors_irq, NULL,
100 NULL, prio_registers, NULL);
101
102static struct resource rtc_resources[] = { 91static struct resource rtc_resources[] = {
103 [0] = { 92 [0] = {
104 .start = 0xa413fec0, 93 .start = 0xa413fec0,
@@ -170,16 +159,8 @@ static int __init sh7710_devices_setup(void)
170} 159}
171__initcall(sh7710_devices_setup); 160__initcall(sh7710_devices_setup);
172 161
173void __init plat_irq_setup_pins(int mode)
174{
175 if (mode == IRQ_MODE_IRQ) {
176 register_intc_controller(&intc_desc_irq);
177 return;
178 }
179 BUG();
180}
181
182void __init plat_irq_setup(void) 162void __init plat_irq_setup(void)
183{ 163{
184 register_intc_controller(&intc_desc); 164 register_intc_controller(&intc_desc);
165 plat_irq_setup_sh3();
185} 166}
diff --git a/arch/sh/kernel/cpu/sh3/setup-sh7720.c b/arch/sh/kernel/cpu/sh3/setup-sh7720.c
index 8028082527c5..f807a21b066c 100644
--- a/arch/sh/kernel/cpu/sh3/setup-sh7720.c
+++ b/arch/sh/kernel/cpu/sh3/setup-sh7720.c
@@ -19,10 +19,6 @@
19#include <linux/serial_sci.h> 19#include <linux/serial_sci.h>
20#include <asm/rtc.h> 20#include <asm/rtc.h>
21 21
22#define INTC_ICR1 0xA4140010UL
23#define INTC_ICR_IRLM 0x4000
24#define INTC_ICR_IRQ (~INTC_ICR_IRLM)
25
26static struct resource rtc_resources[] = { 22static struct resource rtc_resources[] = {
27 [0] = { 23 [0] = {
28 .start = 0xa413fec0, 24 .start = 0xa413fec0,
@@ -170,6 +166,7 @@ enum {
170}; 166};
171 167
172static struct intc_vect vectors[] __initdata = { 168static struct intc_vect vectors[] __initdata = {
169 /* IRQ0->5 are handled in setup-sh3.c */
173 INTC_VECT(TMU0, 0x400), INTC_VECT(TMU1, 0x420), 170 INTC_VECT(TMU0, 0x400), INTC_VECT(TMU1, 0x420),
174 INTC_VECT(TMU2, 0x440), INTC_VECT(RTC_ATI, 0x480), 171 INTC_VECT(TMU2, 0x440), INTC_VECT(RTC_ATI, 0x480),
175 INTC_VECT(RTC_PRI, 0x4a0), INTC_VECT(RTC_CUI, 0x4c0), 172 INTC_VECT(RTC_PRI, 0x4a0), INTC_VECT(RTC_CUI, 0x4c0),
@@ -214,11 +211,7 @@ static struct intc_prio_reg prio_registers[] __initdata = {
214 { 0xA414FEE4UL, 0, 16, 4, /* IPRB */ { WDT, REF_RCMI, SIM, 0 } }, 211 { 0xA414FEE4UL, 0, 16, 4, /* IPRB */ { WDT, REF_RCMI, SIM, 0 } },
215 { 0xA4140016UL, 0, 16, 4, /* IPRC */ { IRQ3, IRQ2, IRQ1, IRQ0 } }, 212 { 0xA4140016UL, 0, 16, 4, /* IPRC */ { IRQ3, IRQ2, IRQ1, IRQ0 } },
216 { 0xA4140018UL, 0, 16, 4, /* IPRD */ { USBF_SPD, TMU_SUNI, IRQ5, IRQ4 } }, 213 { 0xA4140018UL, 0, 16, 4, /* IPRD */ { USBF_SPD, TMU_SUNI, IRQ5, IRQ4 } },
217#if defined(CONFIG_CPU_SUBTYPE_SH7720)
218 { 0xA414001AUL, 0, 16, 4, /* IPRE */ { DMAC1, 0, LCDC, SSL } }, 214 { 0xA414001AUL, 0, 16, 4, /* IPRE */ { DMAC1, 0, LCDC, SSL } },
219#else
220 { 0xA414001AUL, 0, 16, 4, /* IPRE */ { DMAC1, 0, LCDC, 0 } },
221#endif
222 { 0xA4080000UL, 0, 16, 4, /* IPRF */ { ADC, DMAC2, USBFI, CMT } }, 215 { 0xA4080000UL, 0, 16, 4, /* IPRF */ { ADC, DMAC2, USBFI, CMT } },
223 { 0xA4080002UL, 0, 16, 4, /* IPRG */ { SCIF0, SCIF1, 0, 0 } }, 216 { 0xA4080002UL, 0, 16, 4, /* IPRG */ { SCIF0, SCIF1, 0, 0 } },
224 { 0xA4080004UL, 0, 16, 4, /* IPRH */ { PINT07, PINT815, TPU, IIC } }, 217 { 0xA4080004UL, 0, 16, 4, /* IPRH */ { PINT07, PINT815, TPU, IIC } },
@@ -229,32 +222,8 @@ static struct intc_prio_reg prio_registers[] __initdata = {
229static DECLARE_INTC_DESC(intc_desc, "sh7720", vectors, groups, 222static DECLARE_INTC_DESC(intc_desc, "sh7720", vectors, groups,
230 NULL, prio_registers, NULL); 223 NULL, prio_registers, NULL);
231 224
232static struct intc_sense_reg sense_registers[] __initdata = {
233 { INTC_ICR1, 16, 2, { 0, 0, IRQ5, IRQ4, IRQ3, IRQ2, IRQ1, IRQ0 } },
234};
235
236static struct intc_vect vectors_irq[] __initdata = {
237 INTC_VECT(IRQ0, 0x600), INTC_VECT(IRQ1, 0x620),
238 INTC_VECT(IRQ2, 0x640), INTC_VECT(IRQ3, 0x660),
239 INTC_VECT(IRQ4, 0x680), INTC_VECT(IRQ5, 0x6a0),
240};
241
242static DECLARE_INTC_DESC(intc_irq_desc, "sh7720-irq", vectors_irq,
243 NULL, NULL, prio_registers, sense_registers);
244
245void __init plat_irq_setup_pins(int mode)
246{
247 switch (mode) {
248 case IRQ_MODE_IRQ:
249 ctrl_outw(ctrl_inw(INTC_ICR1) & INTC_ICR_IRQ, INTC_ICR1);
250 register_intc_controller(&intc_irq_desc);
251 break;
252 default:
253 BUG();
254 }
255}
256
257void __init plat_irq_setup(void) 225void __init plat_irq_setup(void)
258{ 226{
259 register_intc_controller(&intc_desc); 227 register_intc_controller(&intc_desc);
228 plat_irq_setup_sh3();
260} 229}
diff --git a/arch/sh/kernel/cpu/sh5/entry.S b/arch/sh/kernel/cpu/sh5/entry.S
index ba8750176d91..05372ed6c568 100644
--- a/arch/sh/kernel/cpu/sh5/entry.S
+++ b/arch/sh/kernel/cpu/sh5/entry.S
@@ -143,12 +143,22 @@ resvec_save_area:
143trap_jtable: 143trap_jtable:
144 .long do_exception_error /* 0x000 */ 144 .long do_exception_error /* 0x000 */
145 .long do_exception_error /* 0x020 */ 145 .long do_exception_error /* 0x020 */
146#ifdef CONFIG_MMU
146 .long tlb_miss_load /* 0x040 */ 147 .long tlb_miss_load /* 0x040 */
147 .long tlb_miss_store /* 0x060 */ 148 .long tlb_miss_store /* 0x060 */
149#else
150 .long do_exception_error
151 .long do_exception_error
152#endif
148 ! ARTIFICIAL pseudo-EXPEVT setting 153 ! ARTIFICIAL pseudo-EXPEVT setting
149 .long do_debug_interrupt /* 0x080 */ 154 .long do_debug_interrupt /* 0x080 */
155#ifdef CONFIG_MMU
150 .long tlb_miss_load /* 0x0A0 */ 156 .long tlb_miss_load /* 0x0A0 */
151 .long tlb_miss_store /* 0x0C0 */ 157 .long tlb_miss_store /* 0x0C0 */
158#else
159 .long do_exception_error
160 .long do_exception_error
161#endif
152 .long do_address_error_load /* 0x0E0 */ 162 .long do_address_error_load /* 0x0E0 */
153 .long do_address_error_store /* 0x100 */ 163 .long do_address_error_store /* 0x100 */
154#ifdef CONFIG_SH_FPU 164#ifdef CONFIG_SH_FPU
@@ -185,10 +195,18 @@ trap_jtable:
185 .endr 195 .endr
186 .long do_IRQ /* 0xA00 */ 196 .long do_IRQ /* 0xA00 */
187 .long do_IRQ /* 0xA20 */ 197 .long do_IRQ /* 0xA20 */
198#ifdef CONFIG_MMU
188 .long itlb_miss_or_IRQ /* 0xA40 */ 199 .long itlb_miss_or_IRQ /* 0xA40 */
200#else
201 .long do_IRQ
202#endif
189 .long do_IRQ /* 0xA60 */ 203 .long do_IRQ /* 0xA60 */
190 .long do_IRQ /* 0xA80 */ 204 .long do_IRQ /* 0xA80 */
205#ifdef CONFIG_MMU
191 .long itlb_miss_or_IRQ /* 0xAA0 */ 206 .long itlb_miss_or_IRQ /* 0xAA0 */
207#else
208 .long do_IRQ
209#endif
192 .long do_exception_error /* 0xAC0 */ 210 .long do_exception_error /* 0xAC0 */
193 .long do_address_error_exec /* 0xAE0 */ 211 .long do_address_error_exec /* 0xAE0 */
194 .rept 8 212 .rept 8
@@ -274,6 +292,7 @@ not_a_tlb_miss:
274 * Instead of '.space 1024-TEXT_SIZE' place the RESVEC 292 * Instead of '.space 1024-TEXT_SIZE' place the RESVEC
275 * block making sure the final alignment is correct. 293 * block making sure the final alignment is correct.
276 */ 294 */
295#ifdef CONFIG_MMU
277tlb_miss: 296tlb_miss:
278 synco /* TAKum03020 (but probably a good idea anyway.) */ 297 synco /* TAKum03020 (but probably a good idea anyway.) */
279 putcon SP, KCR1 298 putcon SP, KCR1
@@ -377,6 +396,9 @@ fixup_to_invoke_general_handler:
377 getcon KCR1, SP 396 getcon KCR1, SP
378 pta handle_exception, tr0 397 pta handle_exception, tr0
379 blink tr0, ZERO 398 blink tr0, ZERO
399#else /* CONFIG_MMU */
400 .balign 256
401#endif
380 402
381/* NB TAKE GREAT CARE HERE TO ENSURE THAT THE INTERRUPT CODE 403/* NB TAKE GREAT CARE HERE TO ENSURE THAT THE INTERRUPT CODE
382 DOES END UP AT VBR+0x600 */ 404 DOES END UP AT VBR+0x600 */
@@ -1103,6 +1125,7 @@ restore_all:
1103 * fpu_error_or_IRQ? is a helper to deflect to the right cause. 1125 * fpu_error_or_IRQ? is a helper to deflect to the right cause.
1104 * 1126 *
1105 */ 1127 */
1128#ifdef CONFIG_MMU
1106tlb_miss_load: 1129tlb_miss_load:
1107 or SP, ZERO, r2 1130 or SP, ZERO, r2
1108 or ZERO, ZERO, r3 /* Read */ 1131 or ZERO, ZERO, r3 /* Read */
@@ -1132,6 +1155,7 @@ call_do_page_fault:
1132 movi do_page_fault, r6 1155 movi do_page_fault, r6
1133 ptabs r6, tr0 1156 ptabs r6, tr0
1134 blink tr0, ZERO 1157 blink tr0, ZERO
1158#endif /* CONFIG_MMU */
1135 1159
1136fpu_error_or_IRQA: 1160fpu_error_or_IRQA:
1137 pta its_IRQ, tr0 1161 pta its_IRQ, tr0
@@ -1481,6 +1505,7 @@ poke_real_address_q:
1481 ptabs LINK, tr0 1505 ptabs LINK, tr0
1482 blink tr0, r63 1506 blink tr0, r63
1483 1507
1508#ifdef CONFIG_MMU
1484/* 1509/*
1485 * --- User Access Handling Section 1510 * --- User Access Handling Section
1486 */ 1511 */
@@ -1604,6 +1629,7 @@ ___clear_user_exit:
1604 ptabs LINK, tr0 1629 ptabs LINK, tr0
1605 blink tr0, ZERO 1630 blink tr0, ZERO
1606 1631
1632#endif /* CONFIG_MMU */
1607 1633
1608/* 1634/*
1609 * int __strncpy_from_user(unsigned long __dest, unsigned long __src, 1635 * int __strncpy_from_user(unsigned long __dest, unsigned long __src,
@@ -2014,9 +2040,11 @@ sa_default_restorer:
2014 .global asm_uaccess_start /* Just a marker */ 2040 .global asm_uaccess_start /* Just a marker */
2015asm_uaccess_start: 2041asm_uaccess_start:
2016 2042
2043#ifdef CONFIG_MMU
2017 .long ___copy_user1, ___copy_user_exit 2044 .long ___copy_user1, ___copy_user_exit
2018 .long ___copy_user2, ___copy_user_exit 2045 .long ___copy_user2, ___copy_user_exit
2019 .long ___clear_user1, ___clear_user_exit 2046 .long ___clear_user1, ___clear_user_exit
2047#endif
2020 .long ___strncpy_from_user1, ___strncpy_from_user_exit 2048 .long ___strncpy_from_user1, ___strncpy_from_user_exit
2021 .long ___strnlen_user1, ___strnlen_user_exit 2049 .long ___strnlen_user1, ___strnlen_user_exit
2022 .long ___get_user_asm_b1, ___get_user_asm_b_exit 2050 .long ___get_user_asm_b1, ___get_user_asm_b_exit
diff --git a/arch/sh/kernel/cpu/sh5/probe.c b/arch/sh/kernel/cpu/sh5/probe.c
index 31f8cb0f6374..92ad844b5c12 100644
--- a/arch/sh/kernel/cpu/sh5/probe.c
+++ b/arch/sh/kernel/cpu/sh5/probe.c
@@ -15,6 +15,7 @@
15#include <linux/string.h> 15#include <linux/string.h>
16#include <asm/processor.h> 16#include <asm/processor.h>
17#include <asm/cache.h> 17#include <asm/cache.h>
18#include <asm/tlb.h>
18 19
19int __init detect_cpu_and_cache_system(void) 20int __init detect_cpu_and_cache_system(void)
20{ 21{
@@ -67,5 +68,8 @@ int __init detect_cpu_and_cache_system(void)
67 set_bit(SH_CACHE_MODE_WB, &(boot_cpu_data.dcache.flags)); 68 set_bit(SH_CACHE_MODE_WB, &(boot_cpu_data.dcache.flags));
68#endif 69#endif
69 70
71 /* Setup some I/D TLB defaults */
72 sh64_tlb_init();
73
70 return 0; 74 return 0;
71} 75}