aboutsummaryrefslogtreecommitdiffstats
path: root/arch/sparc/kernel
diff options
context:
space:
mode:
authorSam Ravnborg <sam@ravnborg.org>2012-05-11 07:35:04 -0400
committerDavid S. Miller <davem@davemloft.net>2012-05-11 22:27:44 -0400
commit2c1cfb2db61474040a394962872f4cde613f89fb (patch)
treed8100472f04af9b17f75135c3190221d5920d856 /arch/sparc/kernel
parentaa6f079075d3396d4ac8a5d84ad724bfe8fc1ba9 (diff)
sparc32: drop sun4c support
Machines with sun4c support are very rare these days, and noone is using them for any practical purposes. The sun4c support has been know broken for quite some time too. So rather than trying to keep it up-to-date, lets get rid of it. This allows us to do some very welcome cleanup of sparc32 support. Updated the former sun4c specifc nmi (which was also used for sun4m UP) to be a generic UP NMI. Signed-off-by: Sam Ravnborg <sam@ravnborg.org> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'arch/sparc/kernel')
-rw-r--r--arch/sparc/kernel/Makefile2
-rw-r--r--arch/sparc/kernel/entry.S20
-rw-r--r--arch/sparc/kernel/head_32.S7
-rw-r--r--arch/sparc/kernel/irq_32.c5
-rw-r--r--arch/sparc/kernel/kernel.h3
-rw-r--r--arch/sparc/kernel/process_32.c2
-rw-r--r--arch/sparc/kernel/sun4c_irq.c269
7 files changed, 11 insertions, 297 deletions
diff --git a/arch/sparc/kernel/Makefile b/arch/sparc/kernel/Makefile
index cb85458f89d2..bfb93c37313c 100644
--- a/arch/sparc/kernel/Makefile
+++ b/arch/sparc/kernel/Makefile
@@ -28,7 +28,7 @@ obj-y += traps_$(BITS).o
28 28
29# IRQ 29# IRQ
30obj-y += irq_$(BITS).o 30obj-y += irq_$(BITS).o
31obj-$(CONFIG_SPARC32) += sun4m_irq.o sun4c_irq.o sun4d_irq.o 31obj-$(CONFIG_SPARC32) += sun4m_irq.o sun4d_irq.o
32 32
33obj-y += process_$(BITS).o 33obj-y += process_$(BITS).o
34obj-y += signal_$(BITS).o 34obj-y += signal_$(BITS).o
diff --git a/arch/sparc/kernel/entry.S b/arch/sparc/kernel/entry.S
index f445e98463e6..e0e0b8109225 100644
--- a/arch/sparc/kernel/entry.S
+++ b/arch/sparc/kernel/entry.S
@@ -317,8 +317,8 @@ maybe_smp4m_msg_out:
317 RESTORE_ALL 317 RESTORE_ALL
318 318
319 .align 4 319 .align 4
320 .globl linux_trap_ipi15_sun4m 320 .globl linux_trap_ipi15
321linux_trap_ipi15_sun4m: 321linux_trap_ipi15:
322 SAVE_ALL 322 SAVE_ALL
323 sethi %hi(0x80000000), %o2 323 sethi %hi(0x80000000), %o2
324 GET_PROCESSOR4M_ID(o0) 324 GET_PROCESSOR4M_ID(o0)
@@ -760,20 +760,12 @@ setcc_trap_handler:
760 jmp %l2 ! advance over trap instruction 760 jmp %l2 ! advance over trap instruction
761 rett %l2 + 0x4 ! like this... 761 rett %l2 + 0x4 ! like this...
762 762
763#ifndef CONFIG_SMP
763 .align 4 764 .align 4
764 .globl linux_trap_nmi_sun4c 765 .globl linux_trap_ipi15
765linux_trap_nmi_sun4c: 766linux_trap_ipi15:
766 SAVE_ALL 767 SAVE_ALL
767 768
768 /* Ugh, we need to clear the IRQ line. This is now
769 * a very sun4c specific trap handler...
770 */
771 sethi %hi(interrupt_enable), %l5
772 ld [%l5 + %lo(interrupt_enable)], %l5
773 ldub [%l5], %l6
774 andn %l6, INTS_ENAB, %l6
775 stb %l6, [%l5]
776
777 /* Now it is safe to re-enable traps without recursion. */ 769 /* Now it is safe to re-enable traps without recursion. */
778 or %l0, PSR_PIL, %l0 770 or %l0, PSR_PIL, %l0
779 wr %l0, PSR_ET, %psr 771 wr %l0, PSR_ET, %psr
@@ -797,6 +789,8 @@ linux_trap_nmi_sun4c:
797 789
798 RESTORE_ALL 790 RESTORE_ALL
799 791
792#endif /* CONFIG_SMP */
793
800 .align 4 794 .align 4
801 .globl invalid_segment_patch1_ff 795 .globl invalid_segment_patch1_ff
802 .globl invalid_segment_patch2_ff 796 .globl invalid_segment_patch2_ff
diff --git a/arch/sparc/kernel/head_32.S b/arch/sparc/kernel/head_32.S
index 587785759838..054a49f3044c 100644
--- a/arch/sparc/kernel/head_32.S
+++ b/arch/sparc/kernel/head_32.S
@@ -111,11 +111,8 @@ t_irq12:TRAP_ENTRY_INTERRUPT(12) /* IRQ Zilog serial chip */
111t_irq13:TRAP_ENTRY_INTERRUPT(13) /* IRQ Audio Intr. */ 111t_irq13:TRAP_ENTRY_INTERRUPT(13) /* IRQ Audio Intr. */
112t_irq14:TRAP_ENTRY_INTERRUPT(14) /* IRQ Timer #2 */ 112t_irq14:TRAP_ENTRY_INTERRUPT(14) /* IRQ Timer #2 */
113 .globl t_nmi 113 .globl t_nmi
114#ifndef CONFIG_SMP 114t_nmi: TRAP_ENTRY(0x1f, linux_trap_ipi15)
115t_nmi: NMI_TRAP /* Level 15 (NMI) */ 115
116#else
117t_nmi: TRAP_ENTRY(0x1f, linux_trap_ipi15_sun4m)
118#endif
119t_racc: TRAP_ENTRY(0x20, do_reg_access) /* General Register Access Error */ 116t_racc: TRAP_ENTRY(0x20, do_reg_access) /* General Register Access Error */
120t_iacce:BAD_TRAP(0x21) /* Instr Access Error */ 117t_iacce:BAD_TRAP(0x21) /* Instr Access Error */
121t_bad22:BAD_TRAP(0x22) BAD_TRAP(0x23) 118t_bad22:BAD_TRAP(0x22) BAD_TRAP(0x23)
diff --git a/arch/sparc/kernel/irq_32.c b/arch/sparc/kernel/irq_32.c
index 4a2b8018ac97..998d90cb5439 100644
--- a/arch/sparc/kernel/irq_32.c
+++ b/arch/sparc/kernel/irq_32.c
@@ -346,11 +346,6 @@ void sparc_floppy_irq(int irq, void *dev_id, struct pt_regs *regs)
346void __init init_IRQ(void) 346void __init init_IRQ(void)
347{ 347{
348 switch (sparc_cpu_model) { 348 switch (sparc_cpu_model) {
349 case sun4c:
350 case sun4:
351 sun4c_init_IRQ();
352 break;
353
354 case sun4m: 349 case sun4m:
355 pcic_probe(); 350 pcic_probe();
356 if (pcic_present()) 351 if (pcic_present())
diff --git a/arch/sparc/kernel/kernel.h b/arch/sparc/kernel/kernel.h
index 8abbad38e34e..8278df5d4ce7 100644
--- a/arch/sparc/kernel/kernel.h
+++ b/arch/sparc/kernel/kernel.h
@@ -43,9 +43,6 @@ extern spinlock_t irq_action_lock;
43extern void unexpected_irq(int irq, void *dev_id, struct pt_regs * regs); 43extern void unexpected_irq(int irq, void *dev_id, struct pt_regs * regs);
44extern void init_IRQ(void); 44extern void init_IRQ(void);
45 45
46/* sun4c_irq.c */
47extern void sun4c_init_IRQ(void);
48
49/* sun4m_irq.c */ 46/* sun4m_irq.c */
50extern void sun4m_init_IRQ(void); 47extern void sun4m_init_IRQ(void);
51extern void sun4m_unmask_profile_irq(void); 48extern void sun4m_unmask_profile_irq(void);
diff --git a/arch/sparc/kernel/process_32.c b/arch/sparc/kernel/process_32.c
index efa07542e85f..de81e21cbf68 100644
--- a/arch/sparc/kernel/process_32.c
+++ b/arch/sparc/kernel/process_32.c
@@ -100,7 +100,7 @@ void cpu_idle(void)
100 printk("kernel faults / second = %ld\n", fps); 100 printk("kernel faults / second = %ld\n", fps);
101#endif 101#endif
102 if (fps >= SUN4C_FAULT_HIGH) { 102 if (fps >= SUN4C_FAULT_HIGH) {
103 sun4c_grow_kernel_ring(); 103 /*sun4c_grow_kernel_ring();*/
104 } 104 }
105 } 105 }
106 local_irq_enable(); 106 local_irq_enable();
diff --git a/arch/sparc/kernel/sun4c_irq.c b/arch/sparc/kernel/sun4c_irq.c
deleted file mode 100644
index 39c64211b1b6..000000000000
--- a/arch/sparc/kernel/sun4c_irq.c
+++ /dev/null
@@ -1,269 +0,0 @@
1/*
2 * sun4c irq support
3 *
4 * djhr: Hacked out of irq.c into a CPU dependent version.
5 *
6 * Copyright (C) 1995 David S. Miller (davem@caip.rutgers.edu)
7 * Copyright (C) 1995 Miguel de Icaza (miguel@nuclecu.unam.mx)
8 * Copyright (C) 1995 Pete A. Zaitcev (zaitcev@yahoo.com)
9 * Copyright (C) 1996 Dave Redman (djhr@tadpole.co.uk)
10 */
11
12#include <linux/init.h>
13
14#include <asm/oplib.h>
15#include <asm/timer.h>
16#include <asm/irq.h>
17#include <asm/io.h>
18
19#include "irq.h"
20
21/* Sun4c interrupts are typically laid out as follows:
22 *
23 * 1 - Software interrupt, SBUS level 1
24 * 2 - SBUS level 2
25 * 3 - ESP SCSI, SBUS level 3
26 * 4 - Software interrupt
27 * 5 - Lance ethernet, SBUS level 4
28 * 6 - Software interrupt
29 * 7 - Graphics card, SBUS level 5
30 * 8 - SBUS level 6
31 * 9 - SBUS level 7
32 * 10 - Counter timer
33 * 11 - Floppy
34 * 12 - Zilog uart
35 * 13 - CS4231 audio
36 * 14 - Profiling timer
37 * 15 - NMI
38 *
39 * The interrupt enable bits in the interrupt mask register are
40 * really only used to enable/disable the timer interrupts, and
41 * for signalling software interrupts. There is also a master
42 * interrupt enable bit in this register.
43 *
44 * Interrupts are enabled by setting the SUN4C_INT_* bits, they
45 * are disabled by clearing those bits.
46 */
47
48/*
49 * Bit field defines for the interrupt registers on various
50 * Sparc machines.
51 */
52
53/* The sun4c interrupt register. */
54#define SUN4C_INT_ENABLE 0x01 /* Allow interrupts. */
55#define SUN4C_INT_E14 0x80 /* Enable level 14 IRQ. */
56#define SUN4C_INT_E10 0x20 /* Enable level 10 IRQ. */
57#define SUN4C_INT_E8 0x10 /* Enable level 8 IRQ. */
58#define SUN4C_INT_E6 0x08 /* Enable level 6 IRQ. */
59#define SUN4C_INT_E4 0x04 /* Enable level 4 IRQ. */
60#define SUN4C_INT_E1 0x02 /* Enable level 1 IRQ. */
61
62/*
63 * Pointer to the interrupt enable byte
64 * Used by entry.S
65 */
66unsigned char __iomem *interrupt_enable;
67
68static void sun4c_mask_irq(struct irq_data *data)
69{
70 unsigned long mask = (unsigned long)data->chip_data;
71
72 if (mask) {
73 unsigned long flags;
74
75 local_irq_save(flags);
76 mask = sbus_readb(interrupt_enable) & ~mask;
77 sbus_writeb(mask, interrupt_enable);
78 local_irq_restore(flags);
79 }
80}
81
82static void sun4c_unmask_irq(struct irq_data *data)
83{
84 unsigned long mask = (unsigned long)data->chip_data;
85
86 if (mask) {
87 unsigned long flags;
88
89 local_irq_save(flags);
90 mask = sbus_readb(interrupt_enable) | mask;
91 sbus_writeb(mask, interrupt_enable);
92 local_irq_restore(flags);
93 }
94}
95
96static unsigned int sun4c_startup_irq(struct irq_data *data)
97{
98 irq_link(data->irq);
99 sun4c_unmask_irq(data);
100
101 return 0;
102}
103
104static void sun4c_shutdown_irq(struct irq_data *data)
105{
106 sun4c_mask_irq(data);
107 irq_unlink(data->irq);
108}
109
110static struct irq_chip sun4c_irq = {
111 .name = "sun4c",
112 .irq_startup = sun4c_startup_irq,
113 .irq_shutdown = sun4c_shutdown_irq,
114 .irq_mask = sun4c_mask_irq,
115 .irq_unmask = sun4c_unmask_irq,
116};
117
118static unsigned int sun4c_build_device_irq(struct platform_device *op,
119 unsigned int real_irq)
120{
121 unsigned int irq;
122
123 if (real_irq >= 16) {
124 prom_printf("Bogus sun4c IRQ %u\n", real_irq);
125 prom_halt();
126 }
127
128 irq = irq_alloc(real_irq, real_irq);
129 if (irq) {
130 unsigned long mask = 0UL;
131
132 switch (real_irq) {
133 case 1:
134 mask = SUN4C_INT_E1;
135 break;
136 case 8:
137 mask = SUN4C_INT_E8;
138 break;
139 case 10:
140 mask = SUN4C_INT_E10;
141 break;
142 case 14:
143 mask = SUN4C_INT_E14;
144 break;
145 default:
146 /* All the rest are either always enabled,
147 * or are for signalling software interrupts.
148 */
149 break;
150 }
151 irq_set_chip_and_handler_name(irq, &sun4c_irq,
152 handle_level_irq, "level");
153 irq_set_chip_data(irq, (void *)mask);
154 }
155 return irq;
156}
157
158struct sun4c_timer_info {
159 u32 l10_count;
160 u32 l10_limit;
161 u32 l14_count;
162 u32 l14_limit;
163};
164
165static struct sun4c_timer_info __iomem *sun4c_timers;
166
167static void sun4c_clear_clock_irq(void)
168{
169 sbus_readl(&sun4c_timers->l10_limit);
170}
171
172static void sun4c_load_profile_irq(int cpu, unsigned int limit)
173{
174 /* Errm.. not sure how to do this.. */
175}
176
177static void __init sun4c_init_timers(void)
178{
179 const struct linux_prom_irqs *prom_irqs;
180 struct device_node *dp;
181 unsigned int irq;
182 const u32 *addr;
183 int err;
184
185 dp = of_find_node_by_name(NULL, "counter-timer");
186 if (!dp) {
187 prom_printf("sun4c_init_timers: Unable to find counter-timer\n");
188 prom_halt();
189 }
190
191 addr = of_get_property(dp, "address", NULL);
192 if (!addr) {
193 prom_printf("sun4c_init_timers: No address property\n");
194 prom_halt();
195 }
196
197 sun4c_timers = (void __iomem *) (unsigned long) addr[0];
198
199 prom_irqs = of_get_property(dp, "intr", NULL);
200 of_node_put(dp);
201 if (!prom_irqs) {
202 prom_printf("sun4c_init_timers: No intr property\n");
203 prom_halt();
204 }
205
206 /* Have the level 10 timer tick at 100HZ. We don't touch the
207 * level 14 timer limit since we are letting the prom handle
208 * them until we have a real console driver so L1-A works.
209 */
210 sparc_config.cs_period = SBUS_CLOCK_RATE / HZ;
211 sparc_config.features |=
212 FEAT_L10_CLOCKSOURCE | FEAT_L10_CLOCKEVENT;
213 sbus_writel(timer_value(sparc_config.cs_period),
214 &sun4c_timers->l10_limit);
215
216 master_l10_counter = &sun4c_timers->l10_count;
217
218 irq = sun4c_build_device_irq(NULL, prom_irqs[0].pri);
219 err = request_irq(irq, timer_interrupt, IRQF_TIMER, "timer", NULL);
220 if (err) {
221 prom_printf("sun4c_init_timers: request_irq() fails with %d\n", err);
222 prom_halt();
223 }
224
225 /* disable timer interrupt */
226 sun4c_mask_irq(irq_get_irq_data(irq));
227}
228
229#ifdef CONFIG_SMP
230static void sun4c_nop(void)
231{
232}
233#endif
234
235void __init sun4c_init_IRQ(void)
236{
237 struct device_node *dp;
238 const u32 *addr;
239
240 dp = of_find_node_by_name(NULL, "interrupt-enable");
241 if (!dp) {
242 prom_printf("sun4c_init_IRQ: Unable to find interrupt-enable\n");
243 prom_halt();
244 }
245
246 addr = of_get_property(dp, "address", NULL);
247 of_node_put(dp);
248 if (!addr) {
249 prom_printf("sun4c_init_IRQ: No address property\n");
250 prom_halt();
251 }
252
253 interrupt_enable = (void __iomem *) (unsigned long) addr[0];
254
255 BTFIXUPSET_CALL(clear_clock_irq, sun4c_clear_clock_irq, BTFIXUPCALL_NORM);
256 BTFIXUPSET_CALL(load_profile_irq, sun4c_load_profile_irq, BTFIXUPCALL_NOP);
257
258 sparc_config.init_timers = sun4c_init_timers;
259 sparc_config.build_device_irq = sun4c_build_device_irq;
260 sparc_config.clock_rate = SBUS_CLOCK_RATE;
261
262#ifdef CONFIG_SMP
263 BTFIXUPSET_CALL(set_cpu_int, sun4c_nop, BTFIXUPCALL_NOP);
264 BTFIXUPSET_CALL(clear_cpu_int, sun4c_nop, BTFIXUPCALL_NOP);
265 BTFIXUPSET_CALL(set_irq_udt, sun4c_nop, BTFIXUPCALL_NOP);
266#endif
267 sbus_writeb(SUN4C_INT_ENABLE, interrupt_enable);
268 /* Cannot enable interrupts until OBP ticker is disabled. */
269}