diff options
author | Ralf Baechle <ralf@linux-mips.org> | 2006-04-03 08:17:41 -0400 |
---|---|---|
committer | Ralf Baechle <ralf@linux-mips.org> | 2006-04-18 22:14:21 -0400 |
commit | d35d473c25d43d7db3e5e18b66d558d2a631cca8 (patch) | |
tree | 2351622ad74bb5f09ee2faf0daf6581e7b9e47c5 | |
parent | fde3505c695e0de8ae7504b58d373db2d0ba498a (diff) |
[MIPS] Fix the crime against humanity that mipsIRQ.S is.
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
-rw-r--r-- | arch/mips/mips-boards/atlas/Makefile | 2 | ||||
-rw-r--r-- | arch/mips/mips-boards/atlas/atlas-irq.S (renamed from arch/mips/mips-boards/generic/mipsIRQ.S) | 47 | ||||
-rw-r--r-- | arch/mips/mips-boards/generic/Makefile | 4 | ||||
-rw-r--r-- | arch/mips/mips-boards/malta/Makefile | 2 | ||||
-rw-r--r-- | arch/mips/mips-boards/malta/malta-irq.S | 122 | ||||
-rw-r--r-- | arch/mips/mips-boards/sead/Makefile | 2 | ||||
-rw-r--r-- | arch/mips/mips-boards/sead/sead-irq.S | 111 | ||||
-rw-r--r-- | include/asm-mips/mips-boards/atlas.h | 18 | ||||
-rw-r--r-- | include/asm-mips/mips-boards/atlasint.h | 19 |
9 files changed, 260 insertions, 67 deletions
diff --git a/arch/mips/mips-boards/atlas/Makefile b/arch/mips/mips-boards/atlas/Makefile index d8dab75906bf..50fec2a5aee6 100644 --- a/arch/mips/mips-boards/atlas/Makefile +++ b/arch/mips/mips-boards/atlas/Makefile | |||
@@ -16,5 +16,5 @@ | |||
16 | # 59 Temple Place - Suite 330, Boston MA 02111-1307, USA. | 16 | # 59 Temple Place - Suite 330, Boston MA 02111-1307, USA. |
17 | # | 17 | # |
18 | 18 | ||
19 | obj-y := atlas_int.o atlas_setup.o | 19 | obj-y := atlas_int.o atlas-irq.o atlas_setup.o |
20 | obj-$(CONFIG_KGDB) += atlas_gdb.o | 20 | obj-$(CONFIG_KGDB) += atlas_gdb.o |
diff --git a/arch/mips/mips-boards/generic/mipsIRQ.S b/arch/mips/mips-boards/atlas/atlas-irq.S index 973e10aaacd5..31bc99a52383 100644 --- a/arch/mips/mips-boards/generic/mipsIRQ.S +++ b/arch/mips/mips-boards/atlas/atlas-irq.S | |||
@@ -2,8 +2,6 @@ | |||
2 | * Carsten Langgaard, carstenl@mips.com | 2 | * Carsten Langgaard, carstenl@mips.com |
3 | * Copyright (C) 1999, 2000 MIPS Technologies, Inc. All rights reserved. | 3 | * Copyright (C) 1999, 2000 MIPS Technologies, Inc. All rights reserved. |
4 | * | 4 | * |
5 | * ######################################################################## | ||
6 | * | ||
7 | * This program is free software; you can distribute it and/or modify it | 5 | * This program is free software; you can distribute it and/or modify it |
8 | * under the terms of the GNU General Public License (Version 2) as | 6 | * under the terms of the GNU General Public License (Version 2) as |
9 | * published by the Free Software Foundation. | 7 | * published by the Free Software Foundation. |
@@ -17,10 +15,7 @@ | |||
17 | * with this program; if not, write to the Free Software Foundation, Inc., | 15 | * with this program; if not, write to the Free Software Foundation, Inc., |
18 | * 59 Temple Place - Suite 330, Boston MA 02111-1307, USA. | 16 | * 59 Temple Place - Suite 330, Boston MA 02111-1307, USA. |
19 | * | 17 | * |
20 | * ######################################################################## | ||
21 | * | ||
22 | * Interrupt exception dispatch code. | 18 | * Interrupt exception dispatch code. |
23 | * | ||
24 | */ | 19 | */ |
25 | #include <linux/config.h> | 20 | #include <linux/config.h> |
26 | 21 | ||
@@ -28,33 +23,9 @@ | |||
28 | #include <asm/mipsregs.h> | 23 | #include <asm/mipsregs.h> |
29 | #include <asm/regdef.h> | 24 | #include <asm/regdef.h> |
30 | #include <asm/stackframe.h> | 25 | #include <asm/stackframe.h> |
31 | |||
32 | #ifdef CONFIG_MIPS_ATLAS | ||
33 | #include <asm/mips-boards/atlasint.h> | 26 | #include <asm/mips-boards/atlasint.h> |
34 | #define CASCADE_IRQ MIPSCPU_INT_ATLAS | ||
35 | #define CASCADE_DISPATCH atlas_hw0_irqdispatch | ||
36 | #endif | ||
37 | #ifdef CONFIG_MIPS_MALTA | ||
38 | #include <asm/mips-boards/maltaint.h> | ||
39 | #define CASCADE_IRQ MIPSCPU_INT_I8259A | ||
40 | #define CASCADE_DISPATCH malta_hw0_irqdispatch | ||
41 | #endif | ||
42 | #ifdef CONFIG_MIPS_SEAD | ||
43 | #include <asm/mips-boards/seadint.h> | ||
44 | #endif | ||
45 | 27 | ||
46 | /* A lot of complication here is taken away because: | 28 | /* |
47 | * | ||
48 | * 1) We handle one interrupt and return, sitting in a loop and moving across | ||
49 | * all the pending IRQ bits in the cause register is _NOT_ the answer, the | ||
50 | * common case is one pending IRQ so optimize in that direction. | ||
51 | * | ||
52 | * 2) We need not check against bits in the status register IRQ mask, that | ||
53 | * would make this routine slow as hell. | ||
54 | * | ||
55 | * 3) Linux only thinks in terms of all IRQs on or all IRQs off, nothing in | ||
56 | * between like BSD spl() brain-damage. | ||
57 | * | ||
58 | * Furthermore, the IRQs on the MIPS board look basically (barring software | 29 | * Furthermore, the IRQs on the MIPS board look basically (barring software |
59 | * IRQs which we don't use at all and all external interrupt sources are | 30 | * IRQs which we don't use at all and all external interrupt sources are |
60 | * combined together on hardware interrupt 0 (MIPS IRQ 2)) like: | 31 | * combined together on hardware interrupt 0 (MIPS IRQ 2)) like: |
@@ -127,31 +98,23 @@ | |||
127 | # sll s0, t0 | 98 | # sll s0, t0 |
128 | #endif | 99 | #endif |
129 | 100 | ||
130 | #ifdef CASCADE_IRQ | 101 | li a1, MIPSCPU_INT_ATLAS |
131 | li a1, CASCADE_IRQ | ||
132 | bne a0, a1, 1f | 102 | bne a0, a1, 1f |
133 | addu a0, MIPSCPU_INT_BASE | 103 | addu a0, MIPSCPU_INT_BASE |
134 | 104 | ||
135 | jal CASCADE_DISPATCH | 105 | jal atlas_hw0_irqdispatch |
136 | move a0, sp | 106 | move a0, sp |
137 | 107 | ||
138 | j ret_from_irq | 108 | j ret_from_irq |
139 | nop | 109 | nop |
140 | 1: | ||
141 | #else | ||
142 | addu a0, MIPSCPU_INT_BASE | ||
143 | #endif | ||
144 | 110 | ||
145 | jal do_IRQ | 111 | 1: jal do_IRQ |
146 | move a1, sp | 112 | move a1, sp |
147 | 113 | ||
148 | j ret_from_irq | 114 | j ret_from_irq |
149 | nop | 115 | nop |
150 | 116 | ||
151 | |||
152 | spurious: | 117 | spurious: |
153 | jal spurious_interrupt | 118 | j spurious_interrupt |
154 | nop | ||
155 | j ret_from_irq | ||
156 | nop | 119 | nop |
157 | END(mipsIRQ) | 120 | END(mipsIRQ) |
diff --git a/arch/mips/mips-boards/generic/Makefile b/arch/mips/mips-boards/generic/Makefile index b21bc6887fa8..be47c1c2bc80 100644 --- a/arch/mips/mips-boards/generic/Makefile +++ b/arch/mips/mips-boards/generic/Makefile | |||
@@ -18,8 +18,8 @@ | |||
18 | # Makefile for the MIPS boards generic routines under Linux. | 18 | # Makefile for the MIPS boards generic routines under Linux. |
19 | # | 19 | # |
20 | 20 | ||
21 | obj-y := mipsIRQ.o reset.o display.o init.o memory.o \ | 21 | obj-y := reset.o display.o init.o memory.o printf.o \ |
22 | printf.o cmdline.o time.o | 22 | cmdline.o time.o |
23 | obj-$(CONFIG_PCI) += pci.o | 23 | obj-$(CONFIG_PCI) += pci.o |
24 | obj-$(CONFIG_KGDB) += gdb_hook.o | 24 | obj-$(CONFIG_KGDB) += gdb_hook.o |
25 | 25 | ||
diff --git a/arch/mips/mips-boards/malta/Makefile b/arch/mips/mips-boards/malta/Makefile index fd4c143c0e2f..3ae8fe6c0070 100644 --- a/arch/mips/mips-boards/malta/Makefile +++ b/arch/mips/mips-boards/malta/Makefile | |||
@@ -19,4 +19,4 @@ | |||
19 | # under Linux. | 19 | # under Linux. |
20 | # | 20 | # |
21 | 21 | ||
22 | obj-y := malta_int.o malta_setup.o | 22 | obj-y := malta_int.o malta-irq.o malta_setup.o |
diff --git a/arch/mips/mips-boards/malta/malta-irq.S b/arch/mips/mips-boards/malta/malta-irq.S new file mode 100644 index 000000000000..6217aff3be03 --- /dev/null +++ b/arch/mips/mips-boards/malta/malta-irq.S | |||
@@ -0,0 +1,122 @@ | |||
1 | /* | ||
2 | * Carsten Langgaard, carstenl@mips.com | ||
3 | * Copyright (C) 1999, 2000 MIPS Technologies, Inc. All rights reserved. | ||
4 | * | ||
5 | * ######################################################################## | ||
6 | * | ||
7 | * This program is free software; you can distribute it and/or modify it | ||
8 | * under the terms of the GNU General Public License (Version 2) as | ||
9 | * published by the Free Software Foundation. | ||
10 | * | ||
11 | * This program is distributed in the hope it will be useful, but WITHOUT | ||
12 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
13 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | ||
14 | * for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License along | ||
17 | * with this program; if not, write to the Free Software Foundation, Inc., | ||
18 | * 59 Temple Place - Suite 330, Boston MA 02111-1307, USA. | ||
19 | * | ||
20 | * ######################################################################## | ||
21 | * | ||
22 | * Interrupt exception dispatch code. | ||
23 | * | ||
24 | */ | ||
25 | #include <linux/config.h> | ||
26 | |||
27 | #include <asm/asm.h> | ||
28 | #include <asm/mipsregs.h> | ||
29 | #include <asm/regdef.h> | ||
30 | #include <asm/stackframe.h> | ||
31 | #include <asm/mips-boards/maltaint.h> | ||
32 | |||
33 | /* | ||
34 | * IRQs on the Malta board look basically (barring software IRQs which we | ||
35 | * don't use at all and all external interrupt sources are combined together | ||
36 | * on hardware interrupt 0 (MIPS IRQ 2)) like: | ||
37 | * | ||
38 | * MIPS IRQ Source | ||
39 | * -------- ------ | ||
40 | * 0 Software (ignored) | ||
41 | * 1 Software (ignored) | ||
42 | * 2 Combined hardware interrupt (hw0) | ||
43 | * 3 Hardware (ignored) | ||
44 | * 4 Hardware (ignored) | ||
45 | * 5 Hardware (ignored) | ||
46 | * 6 Hardware (ignored) | ||
47 | * 7 R4k timer (what we use) | ||
48 | * | ||
49 | * We handle the IRQ according to _our_ priority which is: | ||
50 | * | ||
51 | * Highest ---- R4k Timer | ||
52 | * Lowest ---- Combined hardware interrupt | ||
53 | * | ||
54 | * then we just return, if multiple IRQs are pending then we will just take | ||
55 | * another exception, big deal. | ||
56 | */ | ||
57 | |||
58 | .text | ||
59 | .set noreorder | ||
60 | .set noat | ||
61 | .align 5 | ||
62 | NESTED(mipsIRQ, PT_SIZE, sp) | ||
63 | SAVE_ALL | ||
64 | CLI | ||
65 | .set at | ||
66 | |||
67 | mfc0 s0, CP0_CAUSE # get irq bits | ||
68 | mfc0 s1, CP0_STATUS # get irq mask | ||
69 | andi s0, ST0_IM # CAUSE.CE may be non-zero! | ||
70 | and s0, s1 | ||
71 | |||
72 | #if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64) | ||
73 | .set mips32 | ||
74 | clz a0, s0 | ||
75 | .set mips0 | ||
76 | negu a0 | ||
77 | addu a0, 31-CAUSEB_IP | ||
78 | bltz a0, spurious | ||
79 | #else | ||
80 | beqz s0, spurious | ||
81 | li a0, 7 | ||
82 | |||
83 | and t0, s0, 0xf000 | ||
84 | sltiu t0, t0, 1 | ||
85 | sll t0, 2 | ||
86 | subu a0, t0 | ||
87 | sll s0, t0 | ||
88 | |||
89 | and t0, s0, 0xc000 | ||
90 | sltiu t0, t0, 1 | ||
91 | sll t0, 1 | ||
92 | subu a0, t0 | ||
93 | sll s0, t0 | ||
94 | |||
95 | and t0, s0, 0x8000 | ||
96 | sltiu t0, t0, 1 | ||
97 | # sll t0, 0 | ||
98 | subu a0, t0 | ||
99 | # sll s0, t0 | ||
100 | #endif | ||
101 | |||
102 | li a1, MIPSCPU_INT_I8259A | ||
103 | bne a0, a1, 1f | ||
104 | addu a0, MIPSCPU_INT_BASE | ||
105 | |||
106 | jal malta_hw0_irqdispatch | ||
107 | move a0, sp | ||
108 | |||
109 | j ret_from_irq | ||
110 | nop | ||
111 | 1: | ||
112 | |||
113 | jal do_IRQ | ||
114 | move a1, sp | ||
115 | |||
116 | j ret_from_irq | ||
117 | nop | ||
118 | |||
119 | spurious: | ||
120 | j spurious_interrupt | ||
121 | nop | ||
122 | END(mipsIRQ) | ||
diff --git a/arch/mips/mips-boards/sead/Makefile b/arch/mips/mips-boards/sead/Makefile index 224bb848f16b..01780b605346 100644 --- a/arch/mips/mips-boards/sead/Makefile +++ b/arch/mips/mips-boards/sead/Makefile | |||
@@ -23,4 +23,4 @@ | |||
23 | # under Linux. | 23 | # under Linux. |
24 | # | 24 | # |
25 | 25 | ||
26 | obj-y := sead_int.o sead_setup.o | 26 | obj-y := sead_int.o sead-irq.o sead_setup.o |
diff --git a/arch/mips/mips-boards/sead/sead-irq.S b/arch/mips/mips-boards/sead/sead-irq.S new file mode 100644 index 000000000000..d5dea1d2e220 --- /dev/null +++ b/arch/mips/mips-boards/sead/sead-irq.S | |||
@@ -0,0 +1,111 @@ | |||
1 | /* | ||
2 | * Carsten Langgaard, carstenl@mips.com | ||
3 | * Copyright (C) 1999, 2000 MIPS Technologies, Inc. All rights reserved. | ||
4 | * | ||
5 | * ######################################################################## | ||
6 | * | ||
7 | * This program is free software; you can distribute it and/or modify it | ||
8 | * under the terms of the GNU General Public License (Version 2) as | ||
9 | * published by the Free Software Foundation. | ||
10 | * | ||
11 | * This program is distributed in the hope it will be useful, but WITHOUT | ||
12 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
13 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | ||
14 | * for more details. | ||
15 | * | ||
16 | * You should have received a copy of the GNU General Public License along | ||
17 | * with this program; if not, write to the Free Software Foundation, Inc., | ||
18 | * 59 Temple Place - Suite 330, Boston MA 02111-1307, USA. | ||
19 | * | ||
20 | * ######################################################################## | ||
21 | * | ||
22 | * Interrupt exception dispatch code. | ||
23 | * | ||
24 | */ | ||
25 | #include <linux/config.h> | ||
26 | |||
27 | #include <asm/asm.h> | ||
28 | #include <asm/mipsregs.h> | ||
29 | #include <asm/regdef.h> | ||
30 | #include <asm/stackframe.h> | ||
31 | #include <asm/mips-boards/seadint.h> | ||
32 | |||
33 | /* | ||
34 | * IRQs on the SEAD board look basically are combined together on hardware | ||
35 | * interrupt 0 (MIPS IRQ 2)) like: | ||
36 | * | ||
37 | * MIPS IRQ Source | ||
38 | * -------- ------ | ||
39 | * 0 Software (ignored) | ||
40 | * 1 Software (ignored) | ||
41 | * 2 UART0 (hw0) | ||
42 | * 3 UART1 (hw1) | ||
43 | * 4 Hardware (ignored) | ||
44 | * 5 Hardware (ignored) | ||
45 | * 6 Hardware (ignored) | ||
46 | * 7 R4k timer (what we use) | ||
47 | * | ||
48 | * We handle the IRQ according to _our_ priority which is: | ||
49 | * | ||
50 | * Highest ---- R4k Timer | ||
51 | * Lowest ---- Combined hardware interrupt | ||
52 | * | ||
53 | * then we just return, if multiple IRQs are pending then we will just take | ||
54 | * another exception, big deal. | ||
55 | */ | ||
56 | |||
57 | .text | ||
58 | .set noreorder | ||
59 | .set noat | ||
60 | .align 5 | ||
61 | NESTED(mipsIRQ, PT_SIZE, sp) | ||
62 | SAVE_ALL | ||
63 | CLI | ||
64 | .set at | ||
65 | |||
66 | mfc0 s0, CP0_CAUSE # get irq bits | ||
67 | mfc0 s1, CP0_STATUS # get irq mask | ||
68 | andi s0, ST0_IM # CAUSE.CE may be non-zero! | ||
69 | and s0, s1 | ||
70 | |||
71 | #if defined(CONFIG_CPU_MIPS32) || defined(CONFIG_CPU_MIPS64) | ||
72 | .set mips32 | ||
73 | clz a0, s0 | ||
74 | .set mips0 | ||
75 | negu a0 | ||
76 | addu a0, 31-CAUSEB_IP | ||
77 | bltz a0, spurious | ||
78 | #else | ||
79 | beqz s0, spurious | ||
80 | li a0, 7 | ||
81 | |||
82 | and t0, s0, 0xf000 | ||
83 | sltiu t0, t0, 1 | ||
84 | sll t0, 2 | ||
85 | subu a0, t0 | ||
86 | sll s0, t0 | ||
87 | |||
88 | and t0, s0, 0xc000 | ||
89 | sltiu t0, t0, 1 | ||
90 | sll t0, 1 | ||
91 | subu a0, t0 | ||
92 | sll s0, t0 | ||
93 | |||
94 | and t0, s0, 0x8000 | ||
95 | sltiu t0, t0, 1 | ||
96 | # sll t0, 0 | ||
97 | subu a0, t0 | ||
98 | # sll s0, t0 | ||
99 | #endif | ||
100 | |||
101 | addu a0, MIPSCPU_INT_BASE | ||
102 | jal do_IRQ | ||
103 | move a1, sp | ||
104 | |||
105 | j ret_from_irq | ||
106 | nop | ||
107 | |||
108 | spurious: | ||
109 | j spurious_interrupt | ||
110 | nop | ||
111 | END(mipsIRQ) | ||
diff --git a/include/asm-mips/mips-boards/atlas.h b/include/asm-mips/mips-boards/atlas.h index 0998151fb3a1..a8ae12d120ee 100644 --- a/include/asm-mips/mips-boards/atlas.h +++ b/include/asm-mips/mips-boards/atlas.h | |||
@@ -33,13 +33,29 @@ | |||
33 | #define ATLAS_RTC_ADR_REG 0x1f000800 | 33 | #define ATLAS_RTC_ADR_REG 0x1f000800 |
34 | #define ATLAS_RTC_DAT_REG 0x1f000808 | 34 | #define ATLAS_RTC_DAT_REG 0x1f000808 |
35 | 35 | ||
36 | |||
37 | /* | 36 | /* |
38 | * Atlas interrupt controller register base. | 37 | * Atlas interrupt controller register base. |
39 | */ | 38 | */ |
40 | #define ATLAS_ICTRL_REGS_BASE 0x1f000000 | 39 | #define ATLAS_ICTRL_REGS_BASE 0x1f000000 |
41 | 40 | ||
42 | /* | 41 | /* |
42 | * Atlas registers are memory mapped on 64-bit aligned boundaries and | ||
43 | * only word access are allowed. | ||
44 | */ | ||
45 | struct atlas_ictrl_regs { | ||
46 | volatile unsigned int intraw; | ||
47 | int dummy1; | ||
48 | volatile unsigned int intseten; | ||
49 | int dummy2; | ||
50 | volatile unsigned int intrsten; | ||
51 | int dummy3; | ||
52 | volatile unsigned int intenable; | ||
53 | int dummy4; | ||
54 | volatile unsigned int intstatus; | ||
55 | int dummy5; | ||
56 | }; | ||
57 | |||
58 | /* | ||
43 | * Atlas UART register base. | 59 | * Atlas UART register base. |
44 | */ | 60 | */ |
45 | #define ATLAS_UART_REGS_BASE 0x1f000900 | 61 | #define ATLAS_UART_REGS_BASE 0x1f000900 |
diff --git a/include/asm-mips/mips-boards/atlasint.h b/include/asm-mips/mips-boards/atlasint.h index bba35c183d08..fd7ebc54fa90 100644 --- a/include/asm-mips/mips-boards/atlasint.h +++ b/include/asm-mips/mips-boards/atlasint.h | |||
@@ -62,23 +62,4 @@ | |||
62 | #define ATLASINT_RES31 (ATLASINT_BASE+31) | 62 | #define ATLASINT_RES31 (ATLASINT_BASE+31) |
63 | #define ATLASINT_END (ATLASINT_BASE+31) | 63 | #define ATLASINT_END (ATLASINT_BASE+31) |
64 | 64 | ||
65 | /* | ||
66 | * Atlas registers are memory mapped on 64-bit aligned boundaries and | ||
67 | * only word access are allowed. | ||
68 | */ | ||
69 | struct atlas_ictrl_regs { | ||
70 | volatile unsigned int intraw; | ||
71 | int dummy1; | ||
72 | volatile unsigned int intseten; | ||
73 | int dummy2; | ||
74 | volatile unsigned int intrsten; | ||
75 | int dummy3; | ||
76 | volatile unsigned int intenable; | ||
77 | int dummy4; | ||
78 | volatile unsigned int intstatus; | ||
79 | int dummy5; | ||
80 | }; | ||
81 | |||
82 | extern void atlasint_init(void); | ||
83 | |||
84 | #endif /* !(_MIPS_ATLASINT_H) */ | 65 | #endif /* !(_MIPS_ATLASINT_H) */ |