aboutsummaryrefslogtreecommitdiffstats
path: root/arch/mips/kernel
diff options
context:
space:
mode:
Diffstat (limited to 'arch/mips/kernel')
-rw-r--r--arch/mips/kernel/asm-offsets.c3
-rw-r--r--arch/mips/kernel/branch.c1
-rw-r--r--arch/mips/kernel/cpu-bugs64.c5
-rw-r--r--arch/mips/kernel/cpu-probe.c12
-rw-r--r--arch/mips/kernel/head.S39
-rw-r--r--arch/mips/kernel/irq-gic.c15
-rw-r--r--arch/mips/kernel/mcount.S4
-rw-r--r--arch/mips/kernel/octeon_switch.S34
-rw-r--r--arch/mips/kernel/proc.c4
-rw-r--r--arch/mips/kernel/process.c9
-rw-r--r--arch/mips/kernel/prom.c2
-rw-r--r--arch/mips/kernel/ptrace.c12
-rw-r--r--arch/mips/kernel/r2300_switch.S7
-rw-r--r--arch/mips/kernel/r4k_switch.S6
-rw-r--r--arch/mips/kernel/rtlx.c1
-rw-r--r--arch/mips/kernel/scall32-o32.S2
-rw-r--r--arch/mips/kernel/scall64-64.S2
-rw-r--r--arch/mips/kernel/scall64-n32.S2
-rw-r--r--arch/mips/kernel/scall64-o32.S2
-rw-r--r--arch/mips/kernel/signal.c5
-rw-r--r--arch/mips/kernel/smp-bmips.c29
-rw-r--r--arch/mips/kernel/traps.c104
-rw-r--r--arch/mips/kernel/unaligned.c8
-rw-r--r--arch/mips/kernel/watch.c8
24 files changed, 180 insertions, 136 deletions
diff --git a/arch/mips/kernel/asm-offsets.c b/arch/mips/kernel/asm-offsets.c
index 0845091ba480..0c2e853c3db4 100644
--- a/arch/mips/kernel/asm-offsets.c
+++ b/arch/mips/kernel/asm-offsets.c
@@ -82,6 +82,9 @@ void output_task_defines(void)
82 OFFSET(TASK_FLAGS, task_struct, flags); 82 OFFSET(TASK_FLAGS, task_struct, flags);
83 OFFSET(TASK_MM, task_struct, mm); 83 OFFSET(TASK_MM, task_struct, mm);
84 OFFSET(TASK_PID, task_struct, pid); 84 OFFSET(TASK_PID, task_struct, pid);
85#if defined(CONFIG_CC_STACKPROTECTOR)
86 OFFSET(TASK_STACK_CANARY, task_struct, stack_canary);
87#endif
85 DEFINE(TASK_STRUCT_SIZE, sizeof(struct task_struct)); 88 DEFINE(TASK_STRUCT_SIZE, sizeof(struct task_struct));
86 BLANK(); 89 BLANK();
87} 90}
diff --git a/arch/mips/kernel/branch.c b/arch/mips/kernel/branch.c
index 46c2ad0703a0..4d78bf445a9c 100644
--- a/arch/mips/kernel/branch.c
+++ b/arch/mips/kernel/branch.c
@@ -467,5 +467,4 @@ unaligned:
467 printk("%s: unaligned epc - sending SIGBUS.\n", current->comm); 467 printk("%s: unaligned epc - sending SIGBUS.\n", current->comm);
468 force_sig(SIGBUS, current); 468 force_sig(SIGBUS, current);
469 return -EFAULT; 469 return -EFAULT;
470
471} 470}
diff --git a/arch/mips/kernel/cpu-bugs64.c b/arch/mips/kernel/cpu-bugs64.c
index de3c25ffd9f9..0c61df281ce6 100644
--- a/arch/mips/kernel/cpu-bugs64.c
+++ b/arch/mips/kernel/cpu-bugs64.c
@@ -6,6 +6,7 @@
6 * as published by the Free Software Foundation; either version 6 * as published by the Free Software Foundation; either version
7 * 2 of the License, or (at your option) any later version. 7 * 2 of the License, or (at your option) any later version.
8 */ 8 */
9#include <linux/context_tracking.h>
9#include <linux/init.h> 10#include <linux/init.h>
10#include <linux/kernel.h> 11#include <linux/kernel.h>
11#include <linux/ptrace.h> 12#include <linux/ptrace.h>
@@ -171,8 +172,12 @@ static volatile int daddi_ov __cpuinitdata;
171 172
172asmlinkage void __init do_daddi_ov(struct pt_regs *regs) 173asmlinkage void __init do_daddi_ov(struct pt_regs *regs)
173{ 174{
175 enum ctx_state prev_state;
176
177 prev_state = exception_enter();
174 daddi_ov = 1; 178 daddi_ov = 1;
175 regs->cp0_epc += 4; 179 regs->cp0_epc += 4;
180 exception_exit(prev_state);
176} 181}
177 182
178static inline void check_daddi(void) 183static inline void check_daddi(void)
diff --git a/arch/mips/kernel/cpu-probe.c b/arch/mips/kernel/cpu-probe.c
index c6568bf4b1b0..c7b1b3c5a761 100644
--- a/arch/mips/kernel/cpu-probe.c
+++ b/arch/mips/kernel/cpu-probe.c
@@ -146,8 +146,7 @@ static void __cpuinit set_isa(struct cpuinfo_mips *c, unsigned int isa)
146 case MIPS_CPU_ISA_IV: 146 case MIPS_CPU_ISA_IV:
147 c->isa_level |= MIPS_CPU_ISA_IV; 147 c->isa_level |= MIPS_CPU_ISA_IV;
148 case MIPS_CPU_ISA_III: 148 case MIPS_CPU_ISA_III:
149 c->isa_level |= MIPS_CPU_ISA_I | MIPS_CPU_ISA_II | 149 c->isa_level |= MIPS_CPU_ISA_II | MIPS_CPU_ISA_III;
150 MIPS_CPU_ISA_III;
151 break; 150 break;
152 151
153 case MIPS_CPU_ISA_M32R2: 152 case MIPS_CPU_ISA_M32R2:
@@ -156,8 +155,6 @@ static void __cpuinit set_isa(struct cpuinfo_mips *c, unsigned int isa)
156 c->isa_level |= MIPS_CPU_ISA_M32R1; 155 c->isa_level |= MIPS_CPU_ISA_M32R1;
157 case MIPS_CPU_ISA_II: 156 case MIPS_CPU_ISA_II:
158 c->isa_level |= MIPS_CPU_ISA_II; 157 c->isa_level |= MIPS_CPU_ISA_II;
159 case MIPS_CPU_ISA_I:
160 c->isa_level |= MIPS_CPU_ISA_I;
161 break; 158 break;
162 } 159 }
163} 160}
@@ -272,9 +269,6 @@ static inline unsigned int decode_config3(struct cpuinfo_mips *c)
272 c->options |= MIPS_CPU_ULRI; 269 c->options |= MIPS_CPU_ULRI;
273 if (config3 & MIPS_CONF3_ISA) 270 if (config3 & MIPS_CONF3_ISA)
274 c->options |= MIPS_CPU_MICROMIPS; 271 c->options |= MIPS_CPU_MICROMIPS;
275#ifdef CONFIG_CPU_MICROMIPS
276 write_c0_config3(read_c0_config3() | MIPS_CONF3_ISA_OE);
277#endif
278 if (config3 & MIPS_CONF3_VZ) 272 if (config3 & MIPS_CONF3_VZ)
279 c->ases |= MIPS_ASE_VZ; 273 c->ases |= MIPS_ASE_VZ;
280 274
@@ -332,7 +326,6 @@ static inline void cpu_probe_legacy(struct cpuinfo_mips *c, unsigned int cpu)
332 case PRID_IMP_R2000: 326 case PRID_IMP_R2000:
333 c->cputype = CPU_R2000; 327 c->cputype = CPU_R2000;
334 __cpu_name[cpu] = "R2000"; 328 __cpu_name[cpu] = "R2000";
335 set_isa(c, MIPS_CPU_ISA_I);
336 c->options = MIPS_CPU_TLB | MIPS_CPU_3K_CACHE | 329 c->options = MIPS_CPU_TLB | MIPS_CPU_3K_CACHE |
337 MIPS_CPU_NOFPUEX; 330 MIPS_CPU_NOFPUEX;
338 if (__cpu_has_fpu()) 331 if (__cpu_has_fpu())
@@ -352,7 +345,6 @@ static inline void cpu_probe_legacy(struct cpuinfo_mips *c, unsigned int cpu)
352 c->cputype = CPU_R3000; 345 c->cputype = CPU_R3000;
353 __cpu_name[cpu] = "R3000"; 346 __cpu_name[cpu] = "R3000";
354 } 347 }
355 set_isa(c, MIPS_CPU_ISA_I);
356 c->options = MIPS_CPU_TLB | MIPS_CPU_3K_CACHE | 348 c->options = MIPS_CPU_TLB | MIPS_CPU_3K_CACHE |
357 MIPS_CPU_NOFPUEX; 349 MIPS_CPU_NOFPUEX;
358 if (__cpu_has_fpu()) 350 if (__cpu_has_fpu())
@@ -455,7 +447,6 @@ static inline void cpu_probe_legacy(struct cpuinfo_mips *c, unsigned int cpu)
455 break; 447 break;
456 #endif 448 #endif
457 case PRID_IMP_TX39: 449 case PRID_IMP_TX39:
458 set_isa(c, MIPS_CPU_ISA_I);
459 c->options = MIPS_CPU_TLB | MIPS_CPU_TX39_CACHE; 450 c->options = MIPS_CPU_TLB | MIPS_CPU_TX39_CACHE;
460 451
461 if ((c->processor_id & 0xf0) == (PRID_REV_TX3927 & 0xf0)) { 452 if ((c->processor_id & 0xf0) == (PRID_REV_TX3927 & 0xf0)) {
@@ -959,6 +950,7 @@ static inline void cpu_probe_netlogic(struct cpuinfo_mips *c, int cpu)
959 set_isa(c, MIPS_CPU_ISA_M64R1); 950 set_isa(c, MIPS_CPU_ISA_M64R1);
960 c->tlbsize = ((read_c0_config1() >> 25) & 0x3f) + 1; 951 c->tlbsize = ((read_c0_config1() >> 25) & 0x3f) + 1;
961 } 952 }
953 c->kscratch_mask = 0xf;
962} 954}
963 955
964#ifdef CONFIG_64BIT 956#ifdef CONFIG_64BIT
diff --git a/arch/mips/kernel/head.S b/arch/mips/kernel/head.S
index c61cdaed2b1d..099912324423 100644
--- a/arch/mips/kernel/head.S
+++ b/arch/mips/kernel/head.S
@@ -28,45 +28,6 @@
28#include <kernel-entry-init.h> 28#include <kernel-entry-init.h>
29 29
30 /* 30 /*
31 * inputs are the text nasid in t1, data nasid in t2.
32 */
33 .macro MAPPED_KERNEL_SETUP_TLB
34#ifdef CONFIG_MAPPED_KERNEL
35 /*
36 * This needs to read the nasid - assume 0 for now.
37 * Drop in 0xffffffffc0000000 in tlbhi, 0+VG in tlblo_0,
38 * 0+DVG in tlblo_1.
39 */
40 dli t0, 0xffffffffc0000000
41 dmtc0 t0, CP0_ENTRYHI
42 li t0, 0x1c000 # Offset of text into node memory
43 dsll t1, NASID_SHFT # Shift text nasid into place
44 dsll t2, NASID_SHFT # Same for data nasid
45 or t1, t1, t0 # Physical load address of kernel text
46 or t2, t2, t0 # Physical load address of kernel data
47 dsrl t1, 12 # 4K pfn
48 dsrl t2, 12 # 4K pfn
49 dsll t1, 6 # Get pfn into place
50 dsll t2, 6 # Get pfn into place
51 li t0, ((_PAGE_GLOBAL|_PAGE_VALID| _CACHE_CACHABLE_COW) >> 6)
52 or t0, t0, t1
53 mtc0 t0, CP0_ENTRYLO0 # physaddr, VG, cach exlwr
54 li t0, ((_PAGE_GLOBAL|_PAGE_VALID| _PAGE_DIRTY|_CACHE_CACHABLE_COW) >> 6)
55 or t0, t0, t2
56 mtc0 t0, CP0_ENTRYLO1 # physaddr, DVG, cach exlwr
57 li t0, 0x1ffe000 # MAPPED_KERN_TLBMASK, TLBPGMASK_16M
58 mtc0 t0, CP0_PAGEMASK
59 li t0, 0 # KMAP_INX
60 mtc0 t0, CP0_INDEX
61 li t0, 1
62 mtc0 t0, CP0_WIRED
63 tlbwi
64#else
65 mtc0 zero, CP0_WIRED
66#endif
67 .endm
68
69 /*
70 * For the moment disable interrupts, mark the kernel mode and 31 * For the moment disable interrupts, mark the kernel mode and
71 * set ST0_KX so that the CPU does not spit fire when using 32 * set ST0_KX so that the CPU does not spit fire when using
72 * 64-bit addresses. A full initialization of the CPU's status 33 * 64-bit addresses. A full initialization of the CPU's status
diff --git a/arch/mips/kernel/irq-gic.c b/arch/mips/kernel/irq-gic.c
index c01b307317a9..5b5ddb231f26 100644
--- a/arch/mips/kernel/irq-gic.c
+++ b/arch/mips/kernel/irq-gic.c
@@ -219,16 +219,15 @@ static int gic_set_affinity(struct irq_data *d, const struct cpumask *cpumask,
219 219
220 /* Assumption : cpumask refers to a single CPU */ 220 /* Assumption : cpumask refers to a single CPU */
221 spin_lock_irqsave(&gic_lock, flags); 221 spin_lock_irqsave(&gic_lock, flags);
222 for (;;) {
223 /* Re-route this IRQ */
224 GIC_SH_MAP_TO_VPE_SMASK(irq, first_cpu(tmp));
225 222
226 /* Update the pcpu_masks */ 223 /* Re-route this IRQ */
227 for (i = 0; i < NR_CPUS; i++) 224 GIC_SH_MAP_TO_VPE_SMASK(irq, first_cpu(tmp));
228 clear_bit(irq, pcpu_masks[i].pcpu_mask); 225
229 set_bit(irq, pcpu_masks[first_cpu(tmp)].pcpu_mask); 226 /* Update the pcpu_masks */
227 for (i = 0; i < NR_CPUS; i++)
228 clear_bit(irq, pcpu_masks[i].pcpu_mask);
229 set_bit(irq, pcpu_masks[first_cpu(tmp)].pcpu_mask);
230 230
231 }
232 cpumask_copy(d->affinity, cpumask); 231 cpumask_copy(d->affinity, cpumask);
233 spin_unlock_irqrestore(&gic_lock, flags); 232 spin_unlock_irqrestore(&gic_lock, flags);
234 233
diff --git a/arch/mips/kernel/mcount.S b/arch/mips/kernel/mcount.S
index 33d067148e61..a03e93c4a946 100644
--- a/arch/mips/kernel/mcount.S
+++ b/arch/mips/kernel/mcount.S
@@ -168,15 +168,11 @@ NESTED(ftrace_graph_caller, PT_SIZE, ra)
168#endif 168#endif
169 169
170 /* arg3: Get frame pointer of current stack */ 170 /* arg3: Get frame pointer of current stack */
171#ifdef CONFIG_FRAME_POINTER
172 move a2, fp
173#else /* ! CONFIG_FRAME_POINTER */
174#ifdef CONFIG_64BIT 171#ifdef CONFIG_64BIT
175 PTR_LA a2, PT_SIZE(sp) 172 PTR_LA a2, PT_SIZE(sp)
176#else 173#else
177 PTR_LA a2, (PT_SIZE+8)(sp) 174 PTR_LA a2, (PT_SIZE+8)(sp)
178#endif 175#endif
179#endif
180 176
181 jal prepare_ftrace_return 177 jal prepare_ftrace_return
182 nop 178 nop
diff --git a/arch/mips/kernel/octeon_switch.S b/arch/mips/kernel/octeon_switch.S
index 0e23343eb0a9..4204d76af854 100644
--- a/arch/mips/kernel/octeon_switch.S
+++ b/arch/mips/kernel/octeon_switch.S
@@ -40,33 +40,6 @@
40 cpu_save_nonscratch a0 40 cpu_save_nonscratch a0
41 LONG_S ra, THREAD_REG31(a0) 41 LONG_S ra, THREAD_REG31(a0)
42 42
43 /* check if we need to save COP2 registers */
44 PTR_L t2, TASK_THREAD_INFO(a0)
45 LONG_L t0, ST_OFF(t2)
46 bbit0 t0, 30, 1f
47
48 /* Disable COP2 in the stored process state */
49 li t1, ST0_CU2
50 xor t0, t1
51 LONG_S t0, ST_OFF(t2)
52
53 /* Enable COP2 so we can save it */
54 mfc0 t0, CP0_STATUS
55 or t0, t1
56 mtc0 t0, CP0_STATUS
57
58 /* Save COP2 */
59 daddu a0, THREAD_CP2
60 jal octeon_cop2_save
61 dsubu a0, THREAD_CP2
62
63 /* Disable COP2 now that we are done */
64 mfc0 t0, CP0_STATUS
65 li t1, ST0_CU2
66 xor t0, t1
67 mtc0 t0, CP0_STATUS
68
691:
70#if CONFIG_CAVIUM_OCTEON_CVMSEG_SIZE > 0 43#if CONFIG_CAVIUM_OCTEON_CVMSEG_SIZE > 0
71 /* Check if we need to store CVMSEG state */ 44 /* Check if we need to store CVMSEG state */
72 mfc0 t0, $11,7 /* CvmMemCtl */ 45 mfc0 t0, $11,7 /* CvmMemCtl */
@@ -98,6 +71,13 @@
98 mtc0 t0, $11,7 /* CvmMemCtl */ 71 mtc0 t0, $11,7 /* CvmMemCtl */
99#endif 72#endif
1003: 733:
74
75#if defined(CONFIG_CC_STACKPROTECTOR) && !defined(CONFIG_SMP)
76 PTR_L t8, __stack_chk_guard
77 LONG_L t9, TASK_STACK_CANARY(a1)
78 LONG_S t9, 0(t8)
79#endif
80
101 /* 81 /*
102 * The order of restoring the registers takes care of the race 82 * The order of restoring the registers takes care of the race
103 * updating $28, $29 and kernelsp without disabling ints. 83 * updating $28, $29 and kernelsp without disabling ints.
diff --git a/arch/mips/kernel/proc.c b/arch/mips/kernel/proc.c
index acb34373679e..8c58d8a84bf3 100644
--- a/arch/mips/kernel/proc.c
+++ b/arch/mips/kernel/proc.c
@@ -66,9 +66,7 @@ static int show_cpuinfo(struct seq_file *m, void *v)
66 seq_printf(m, "]\n"); 66 seq_printf(m, "]\n");
67 } 67 }
68 if (cpu_has_mips_r) { 68 if (cpu_has_mips_r) {
69 seq_printf(m, "isa\t\t\t:"); 69 seq_printf(m, "isa\t\t\t: mips1");
70 if (cpu_has_mips_1)
71 seq_printf(m, "%s", " mips1");
72 if (cpu_has_mips_2) 70 if (cpu_has_mips_2)
73 seq_printf(m, "%s", " mips2"); 71 seq_printf(m, "%s", " mips2");
74 if (cpu_has_mips_3) 72 if (cpu_has_mips_3)
diff --git a/arch/mips/kernel/process.c b/arch/mips/kernel/process.c
index c6a041d9d05d..ddc76103e78c 100644
--- a/arch/mips/kernel/process.c
+++ b/arch/mips/kernel/process.c
@@ -201,9 +201,12 @@ int dump_task_fpu(struct task_struct *t, elf_fpregset_t *fpr)
201 return 1; 201 return 1;
202} 202}
203 203
204/* 204#ifdef CONFIG_CC_STACKPROTECTOR
205 * 205#include <linux/stackprotector.h>
206 */ 206unsigned long __stack_chk_guard __read_mostly;
207EXPORT_SYMBOL(__stack_chk_guard);
208#endif
209
207struct mips_frame_info { 210struct mips_frame_info {
208 void *func; 211 void *func;
209 unsigned long func_size; 212 unsigned long func_size;
diff --git a/arch/mips/kernel/prom.c b/arch/mips/kernel/prom.c
index 5712bb532245..7e954042f252 100644
--- a/arch/mips/kernel/prom.c
+++ b/arch/mips/kernel/prom.c
@@ -30,7 +30,7 @@ __init void mips_set_machine_name(const char *name)
30 if (name == NULL) 30 if (name == NULL)
31 return; 31 return;
32 32
33 strncpy(mips_machine_name, name, sizeof(mips_machine_name)); 33 strlcpy(mips_machine_name, name, sizeof(mips_machine_name));
34 pr_info("MIPS: machine is %s\n", mips_get_machine_name()); 34 pr_info("MIPS: machine is %s\n", mips_get_machine_name());
35} 35}
36 36
diff --git a/arch/mips/kernel/ptrace.c b/arch/mips/kernel/ptrace.c
index 9c6299c733a3..8ae1ebef8b71 100644
--- a/arch/mips/kernel/ptrace.c
+++ b/arch/mips/kernel/ptrace.c
@@ -15,6 +15,7 @@
15 * binaries. 15 * binaries.
16 */ 16 */
17#include <linux/compiler.h> 17#include <linux/compiler.h>
18#include <linux/context_tracking.h>
18#include <linux/kernel.h> 19#include <linux/kernel.h>
19#include <linux/sched.h> 20#include <linux/sched.h>
20#include <linux/mm.h> 21#include <linux/mm.h>
@@ -534,6 +535,8 @@ static inline int audit_arch(void)
534 */ 535 */
535asmlinkage void syscall_trace_enter(struct pt_regs *regs) 536asmlinkage void syscall_trace_enter(struct pt_regs *regs)
536{ 537{
538 user_exit();
539
537 /* do the secure computing check first */ 540 /* do the secure computing check first */
538 secure_computing_strict(regs->regs[2]); 541 secure_computing_strict(regs->regs[2]);
539 542
@@ -570,6 +573,13 @@ out:
570 */ 573 */
571asmlinkage void syscall_trace_leave(struct pt_regs *regs) 574asmlinkage void syscall_trace_leave(struct pt_regs *regs)
572{ 575{
576 /*
577 * We may come here right after calling schedule_user()
578 * or do_notify_resume(), in which case we can be in RCU
579 * user mode.
580 */
581 user_exit();
582
573 audit_syscall_exit(regs); 583 audit_syscall_exit(regs);
574 584
575 if (!(current->ptrace & PT_PTRACED)) 585 if (!(current->ptrace & PT_PTRACED))
@@ -592,4 +602,6 @@ asmlinkage void syscall_trace_leave(struct pt_regs *regs)
592 send_sig(current->exit_code, current, 1); 602 send_sig(current->exit_code, current, 1);
593 current->exit_code = 0; 603 current->exit_code = 0;
594 } 604 }
605
606 user_enter();
595} 607}
diff --git a/arch/mips/kernel/r2300_switch.S b/arch/mips/kernel/r2300_switch.S
index 5266c6ee2b35..38af83f84c4a 100644
--- a/arch/mips/kernel/r2300_switch.S
+++ b/arch/mips/kernel/r2300_switch.S
@@ -65,6 +65,13 @@ LEAF(resume)
65 fpu_save_single a0, t0 # clobbers t0 65 fpu_save_single a0, t0 # clobbers t0
66 66
671: 671:
68
69#if defined(CONFIG_CC_STACKPROTECTOR) && !defined(CONFIG_SMP)
70 PTR_L t8, __stack_chk_guard
71 LONG_L t9, TASK_STACK_CANARY(a1)
72 LONG_S t9, 0(t8)
73#endif
74
68 /* 75 /*
69 * The order of restoring the registers takes care of the race 76 * The order of restoring the registers takes care of the race
70 * updating $28, $29 and kernelsp without disabling ints. 77 * updating $28, $29 and kernelsp without disabling ints.
diff --git a/arch/mips/kernel/r4k_switch.S b/arch/mips/kernel/r4k_switch.S
index 5e51219990aa..921238a6bd26 100644
--- a/arch/mips/kernel/r4k_switch.S
+++ b/arch/mips/kernel/r4k_switch.S
@@ -68,6 +68,12 @@
68 # clobbers t1 68 # clobbers t1
691: 691:
70 70
71#if defined(CONFIG_CC_STACKPROTECTOR) && !defined(CONFIG_SMP)
72 PTR_L t8, __stack_chk_guard
73 LONG_L t9, TASK_STACK_CANARY(a1)
74 LONG_S t9, 0(t8)
75#endif
76
71 /* 77 /*
72 * The order of restoring the registers takes care of the race 78 * The order of restoring the registers takes care of the race
73 * updating $28, $29 and kernelsp without disabling ints. 79 * updating $28, $29 and kernelsp without disabling ints.
diff --git a/arch/mips/kernel/rtlx.c b/arch/mips/kernel/rtlx.c
index 6fa198db8999..d763f11e35e2 100644
--- a/arch/mips/kernel/rtlx.c
+++ b/arch/mips/kernel/rtlx.c
@@ -437,7 +437,6 @@ static ssize_t file_write(struct file *file, const char __user * buffer,
437 size_t count, loff_t * ppos) 437 size_t count, loff_t * ppos)
438{ 438{
439 int minor = iminor(file_inode(file)); 439 int minor = iminor(file_inode(file));
440 struct rtlx_channel *rt = &rtlx->channel[minor];
441 440
442 /* any space left... */ 441 /* any space left... */
443 if (!rtlx_write_poll(minor)) { 442 if (!rtlx_write_poll(minor)) {
diff --git a/arch/mips/kernel/scall32-o32.S b/arch/mips/kernel/scall32-o32.S
index e9127ec612ef..e774bb1088b5 100644
--- a/arch/mips/kernel/scall32-o32.S
+++ b/arch/mips/kernel/scall32-o32.S
@@ -52,7 +52,7 @@ NESTED(handle_sys, PT_SIZE, sp)
52 52
53stack_done: 53stack_done:
54 lw t0, TI_FLAGS($28) # syscall tracing enabled? 54 lw t0, TI_FLAGS($28) # syscall tracing enabled?
55 li t1, _TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT 55 li t1, _TIF_WORK_SYSCALL_ENTRY
56 and t0, t1 56 and t0, t1
57 bnez t0, syscall_trace_entry # -> yes 57 bnez t0, syscall_trace_entry # -> yes
58 58
diff --git a/arch/mips/kernel/scall64-64.S b/arch/mips/kernel/scall64-64.S
index 97a5909a61cf..be6627ead619 100644
--- a/arch/mips/kernel/scall64-64.S
+++ b/arch/mips/kernel/scall64-64.S
@@ -54,7 +54,7 @@ NESTED(handle_sys64, PT_SIZE, sp)
54 54
55 sd a3, PT_R26(sp) # save a3 for syscall restarting 55 sd a3, PT_R26(sp) # save a3 for syscall restarting
56 56
57 li t1, _TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT 57 li t1, _TIF_WORK_SYSCALL_ENTRY
58 LONG_L t0, TI_FLAGS($28) # syscall tracing enabled? 58 LONG_L t0, TI_FLAGS($28) # syscall tracing enabled?
59 and t0, t1, t0 59 and t0, t1, t0
60 bnez t0, syscall_trace_entry 60 bnez t0, syscall_trace_entry
diff --git a/arch/mips/kernel/scall64-n32.S b/arch/mips/kernel/scall64-n32.S
index edcb6594e7b5..cab150789c8d 100644
--- a/arch/mips/kernel/scall64-n32.S
+++ b/arch/mips/kernel/scall64-n32.S
@@ -47,7 +47,7 @@ NESTED(handle_sysn32, PT_SIZE, sp)
47 47
48 sd a3, PT_R26(sp) # save a3 for syscall restarting 48 sd a3, PT_R26(sp) # save a3 for syscall restarting
49 49
50 li t1, _TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT 50 li t1, _TIF_WORK_SYSCALL_ENTRY
51 LONG_L t0, TI_FLAGS($28) # syscall tracing enabled? 51 LONG_L t0, TI_FLAGS($28) # syscall tracing enabled?
52 and t0, t1, t0 52 and t0, t1, t0
53 bnez t0, n32_syscall_trace_entry 53 bnez t0, n32_syscall_trace_entry
diff --git a/arch/mips/kernel/scall64-o32.S b/arch/mips/kernel/scall64-o32.S
index 74f485d3c0ef..37605dc8eef7 100644
--- a/arch/mips/kernel/scall64-o32.S
+++ b/arch/mips/kernel/scall64-o32.S
@@ -81,7 +81,7 @@ NESTED(handle_sys, PT_SIZE, sp)
81 PTR 4b, bad_stack 81 PTR 4b, bad_stack
82 .previous 82 .previous
83 83
84 li t1, _TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT 84 li t1, _TIF_WORK_SYSCALL_ENTRY
85 LONG_L t0, TI_FLAGS($28) # syscall tracing enabled? 85 LONG_L t0, TI_FLAGS($28) # syscall tracing enabled?
86 and t0, t1, t0 86 and t0, t1, t0
87 bnez t0, trace_a_syscall 87 bnez t0, trace_a_syscall
diff --git a/arch/mips/kernel/signal.c b/arch/mips/kernel/signal.c
index fd3ef2c2afbc..2f285abc76d5 100644
--- a/arch/mips/kernel/signal.c
+++ b/arch/mips/kernel/signal.c
@@ -8,6 +8,7 @@
8 * Copyright (C) 1999, 2000 Silicon Graphics, Inc. 8 * Copyright (C) 1999, 2000 Silicon Graphics, Inc.
9 */ 9 */
10#include <linux/cache.h> 10#include <linux/cache.h>
11#include <linux/context_tracking.h>
11#include <linux/irqflags.h> 12#include <linux/irqflags.h>
12#include <linux/sched.h> 13#include <linux/sched.h>
13#include <linux/mm.h> 14#include <linux/mm.h>
@@ -573,6 +574,8 @@ asmlinkage void do_notify_resume(struct pt_regs *regs, void *unused,
573{ 574{
574 local_irq_enable(); 575 local_irq_enable();
575 576
577 user_exit();
578
576 /* deal with pending signal delivery */ 579 /* deal with pending signal delivery */
577 if (thread_info_flags & _TIF_SIGPENDING) 580 if (thread_info_flags & _TIF_SIGPENDING)
578 do_signal(regs); 581 do_signal(regs);
@@ -581,6 +584,8 @@ asmlinkage void do_notify_resume(struct pt_regs *regs, void *unused,
581 clear_thread_flag(TIF_NOTIFY_RESUME); 584 clear_thread_flag(TIF_NOTIFY_RESUME);
582 tracehook_notify_resume(regs); 585 tracehook_notify_resume(regs);
583 } 586 }
587
588 user_enter();
584} 589}
585 590
586#ifdef CONFIG_SMP 591#ifdef CONFIG_SMP
diff --git a/arch/mips/kernel/smp-bmips.c b/arch/mips/kernel/smp-bmips.c
index 8e393b8443f7..aea6c0885838 100644
--- a/arch/mips/kernel/smp-bmips.c
+++ b/arch/mips/kernel/smp-bmips.c
@@ -63,7 +63,7 @@ static irqreturn_t bmips_ipi_interrupt(int irq, void *dev_id);
63 63
64static void __init bmips_smp_setup(void) 64static void __init bmips_smp_setup(void)
65{ 65{
66 int i; 66 int i, cpu = 1, boot_cpu = 0;
67 67
68#if defined(CONFIG_CPU_BMIPS4350) || defined(CONFIG_CPU_BMIPS4380) 68#if defined(CONFIG_CPU_BMIPS4350) || defined(CONFIG_CPU_BMIPS4380)
69 /* arbitration priority */ 69 /* arbitration priority */
@@ -72,13 +72,22 @@ static void __init bmips_smp_setup(void)
72 /* NBK and weak order flags */ 72 /* NBK and weak order flags */
73 set_c0_brcm_config_0(0x30000); 73 set_c0_brcm_config_0(0x30000);
74 74
75 /* Find out if we are running on TP0 or TP1 */
76 boot_cpu = !!(read_c0_brcm_cmt_local() & (1 << 31));
77
75 /* 78 /*
76 * MIPS interrupts 0,1 (SW INT 0,1) cross over to the other thread 79 * MIPS interrupts 0,1 (SW INT 0,1) cross over to the other thread
77 * MIPS interrupt 2 (HW INT 0) is the CPU0 L1 controller output 80 * MIPS interrupt 2 (HW INT 0) is the CPU0 L1 controller output
78 * MIPS interrupt 3 (HW INT 1) is the CPU1 L1 controller output 81 * MIPS interrupt 3 (HW INT 1) is the CPU1 L1 controller output
82 *
83 * If booting from TP1, leave the existing CMT interrupt routing
84 * such that TP0 responds to SW1 and TP1 responds to SW0.
79 */ 85 */
80 change_c0_brcm_cmt_intr(0xf8018000, 86 if (boot_cpu == 0)
81 (0x02 << 27) | (0x03 << 15)); 87 change_c0_brcm_cmt_intr(0xf8018000,
88 (0x02 << 27) | (0x03 << 15));
89 else
90 change_c0_brcm_cmt_intr(0xf8018000, (0x1d << 27));
82 91
83 /* single core, 2 threads (2 pipelines) */ 92 /* single core, 2 threads (2 pipelines) */
84 max_cpus = 2; 93 max_cpus = 2;
@@ -106,9 +115,15 @@ static void __init bmips_smp_setup(void)
106 if (!board_ebase_setup) 115 if (!board_ebase_setup)
107 board_ebase_setup = &bmips_ebase_setup; 116 board_ebase_setup = &bmips_ebase_setup;
108 117
118 __cpu_number_map[boot_cpu] = 0;
119 __cpu_logical_map[0] = boot_cpu;
120
109 for (i = 0; i < max_cpus; i++) { 121 for (i = 0; i < max_cpus; i++) {
110 __cpu_number_map[i] = 1; 122 if (i != boot_cpu) {
111 __cpu_logical_map[i] = 1; 123 __cpu_number_map[i] = cpu;
124 __cpu_logical_map[cpu] = i;
125 cpu++;
126 }
112 set_cpu_possible(i, 1); 127 set_cpu_possible(i, 1);
113 set_cpu_present(i, 1); 128 set_cpu_present(i, 1);
114 } 129 }
@@ -157,7 +172,9 @@ static void bmips_boot_secondary(int cpu, struct task_struct *idle)
157 bmips_send_ipi_single(cpu, 0); 172 bmips_send_ipi_single(cpu, 0);
158 else { 173 else {
159#if defined(CONFIG_CPU_BMIPS4350) || defined(CONFIG_CPU_BMIPS4380) 174#if defined(CONFIG_CPU_BMIPS4350) || defined(CONFIG_CPU_BMIPS4380)
160 set_c0_brcm_cmt_ctrl(0x01); 175 /* Reset slave TP1 if booting from TP0 */
176 if (cpu_logical_map(cpu) == 0)
177 set_c0_brcm_cmt_ctrl(0x01);
161#elif defined(CONFIG_CPU_BMIPS5000) 178#elif defined(CONFIG_CPU_BMIPS5000)
162 if (cpu & 0x01) 179 if (cpu & 0x01)
163 write_c0_brcm_action(ACTION_BOOT_THREAD(cpu)); 180 write_c0_brcm_action(ACTION_BOOT_THREAD(cpu));
diff --git a/arch/mips/kernel/traps.c b/arch/mips/kernel/traps.c
index a75ae40184aa..0903d70b2cfe 100644
--- a/arch/mips/kernel/traps.c
+++ b/arch/mips/kernel/traps.c
@@ -13,6 +13,7 @@
13 */ 13 */
14#include <linux/bug.h> 14#include <linux/bug.h>
15#include <linux/compiler.h> 15#include <linux/compiler.h>
16#include <linux/context_tracking.h>
16#include <linux/kexec.h> 17#include <linux/kexec.h>
17#include <linux/init.h> 18#include <linux/init.h>
18#include <linux/kernel.h> 19#include <linux/kernel.h>
@@ -264,7 +265,7 @@ static void __show_regs(const struct pt_regs *regs)
264 265
265 printk("Status: %08x ", (uint32_t) regs->cp0_status); 266 printk("Status: %08x ", (uint32_t) regs->cp0_status);
266 267
267 if (current_cpu_data.isa_level == MIPS_CPU_ISA_I) { 268 if (cpu_has_3kex) {
268 if (regs->cp0_status & ST0_KUO) 269 if (regs->cp0_status & ST0_KUO)
269 printk("KUo "); 270 printk("KUo ");
270 if (regs->cp0_status & ST0_IEO) 271 if (regs->cp0_status & ST0_IEO)
@@ -277,7 +278,7 @@ static void __show_regs(const struct pt_regs *regs)
277 printk("KUc "); 278 printk("KUc ");
278 if (regs->cp0_status & ST0_IEC) 279 if (regs->cp0_status & ST0_IEC)
279 printk("IEc "); 280 printk("IEc ");
280 } else { 281 } else if (cpu_has_4kex) {
281 if (regs->cp0_status & ST0_KX) 282 if (regs->cp0_status & ST0_KX)
282 printk("KX "); 283 printk("KX ");
283 if (regs->cp0_status & ST0_SX) 284 if (regs->cp0_status & ST0_SX)
@@ -423,7 +424,9 @@ asmlinkage void do_be(struct pt_regs *regs)
423 const struct exception_table_entry *fixup = NULL; 424 const struct exception_table_entry *fixup = NULL;
424 int data = regs->cp0_cause & 4; 425 int data = regs->cp0_cause & 4;
425 int action = MIPS_BE_FATAL; 426 int action = MIPS_BE_FATAL;
427 enum ctx_state prev_state;
426 428
429 prev_state = exception_enter();
427 /* XXX For now. Fixme, this searches the wrong table ... */ 430 /* XXX For now. Fixme, this searches the wrong table ... */
428 if (data && !user_mode(regs)) 431 if (data && !user_mode(regs))
429 fixup = search_dbe_tables(exception_epc(regs)); 432 fixup = search_dbe_tables(exception_epc(regs));
@@ -436,11 +439,11 @@ asmlinkage void do_be(struct pt_regs *regs)
436 439
437 switch (action) { 440 switch (action) {
438 case MIPS_BE_DISCARD: 441 case MIPS_BE_DISCARD:
439 return; 442 goto out;
440 case MIPS_BE_FIXUP: 443 case MIPS_BE_FIXUP:
441 if (fixup) { 444 if (fixup) {
442 regs->cp0_epc = fixup->nextinsn; 445 regs->cp0_epc = fixup->nextinsn;
443 return; 446 goto out;
444 } 447 }
445 break; 448 break;
446 default: 449 default:
@@ -455,10 +458,13 @@ asmlinkage void do_be(struct pt_regs *regs)
455 field, regs->cp0_epc, field, regs->regs[31]); 458 field, regs->cp0_epc, field, regs->regs[31]);
456 if (notify_die(DIE_OOPS, "bus error", regs, 0, regs_to_trapnr(regs), SIGBUS) 459 if (notify_die(DIE_OOPS, "bus error", regs, 0, regs_to_trapnr(regs), SIGBUS)
457 == NOTIFY_STOP) 460 == NOTIFY_STOP)
458 return; 461 goto out;
459 462
460 die_if_kernel("Oops", regs); 463 die_if_kernel("Oops", regs);
461 force_sig(SIGBUS, current); 464 force_sig(SIGBUS, current);
465
466out:
467 exception_exit(prev_state);
462} 468}
463 469
464/* 470/*
@@ -673,8 +679,10 @@ static int simulate_sync(struct pt_regs *regs, unsigned int opcode)
673 679
674asmlinkage void do_ov(struct pt_regs *regs) 680asmlinkage void do_ov(struct pt_regs *regs)
675{ 681{
682 enum ctx_state prev_state;
676 siginfo_t info; 683 siginfo_t info;
677 684
685 prev_state = exception_enter();
678 die_if_kernel("Integer overflow", regs); 686 die_if_kernel("Integer overflow", regs);
679 687
680 info.si_code = FPE_INTOVF; 688 info.si_code = FPE_INTOVF;
@@ -682,6 +690,7 @@ asmlinkage void do_ov(struct pt_regs *regs)
682 info.si_errno = 0; 690 info.si_errno = 0;
683 info.si_addr = (void __user *) regs->cp0_epc; 691 info.si_addr = (void __user *) regs->cp0_epc;
684 force_sig_info(SIGFPE, &info, current); 692 force_sig_info(SIGFPE, &info, current);
693 exception_exit(prev_state);
685} 694}
686 695
687int process_fpemu_return(int sig, void __user *fault_addr) 696int process_fpemu_return(int sig, void __user *fault_addr)
@@ -713,11 +722,13 @@ int process_fpemu_return(int sig, void __user *fault_addr)
713 */ 722 */
714asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31) 723asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31)
715{ 724{
725 enum ctx_state prev_state;
716 siginfo_t info = {0}; 726 siginfo_t info = {0};
717 727
728 prev_state = exception_enter();
718 if (notify_die(DIE_FP, "FP exception", regs, 0, regs_to_trapnr(regs), SIGFPE) 729 if (notify_die(DIE_FP, "FP exception", regs, 0, regs_to_trapnr(regs), SIGFPE)
719 == NOTIFY_STOP) 730 == NOTIFY_STOP)
720 return; 731 goto out;
721 die_if_kernel("FP exception in kernel code", regs); 732 die_if_kernel("FP exception in kernel code", regs);
722 733
723 if (fcr31 & FPU_CSR_UNI_X) { 734 if (fcr31 & FPU_CSR_UNI_X) {
@@ -753,7 +764,7 @@ asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31)
753 /* If something went wrong, signal */ 764 /* If something went wrong, signal */
754 process_fpemu_return(sig, fault_addr); 765 process_fpemu_return(sig, fault_addr);
755 766
756 return; 767 goto out;
757 } else if (fcr31 & FPU_CSR_INV_X) 768 } else if (fcr31 & FPU_CSR_INV_X)
758 info.si_code = FPE_FLTINV; 769 info.si_code = FPE_FLTINV;
759 else if (fcr31 & FPU_CSR_DIV_X) 770 else if (fcr31 & FPU_CSR_DIV_X)
@@ -770,6 +781,9 @@ asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31)
770 info.si_errno = 0; 781 info.si_errno = 0;
771 info.si_addr = (void __user *) regs->cp0_epc; 782 info.si_addr = (void __user *) regs->cp0_epc;
772 force_sig_info(SIGFPE, &info, current); 783 force_sig_info(SIGFPE, &info, current);
784
785out:
786 exception_exit(prev_state);
773} 787}
774 788
775static void do_trap_or_bp(struct pt_regs *regs, unsigned int code, 789static void do_trap_or_bp(struct pt_regs *regs, unsigned int code,
@@ -835,9 +849,11 @@ static void do_trap_or_bp(struct pt_regs *regs, unsigned int code,
835asmlinkage void do_bp(struct pt_regs *regs) 849asmlinkage void do_bp(struct pt_regs *regs)
836{ 850{
837 unsigned int opcode, bcode; 851 unsigned int opcode, bcode;
852 enum ctx_state prev_state;
838 unsigned long epc; 853 unsigned long epc;
839 u16 instr[2]; 854 u16 instr[2];
840 855
856 prev_state = exception_enter();
841 if (get_isa16_mode(regs->cp0_epc)) { 857 if (get_isa16_mode(regs->cp0_epc)) {
842 /* Calculate EPC. */ 858 /* Calculate EPC. */
843 epc = exception_epc(regs); 859 epc = exception_epc(regs);
@@ -852,7 +868,7 @@ asmlinkage void do_bp(struct pt_regs *regs)
852 goto out_sigsegv; 868 goto out_sigsegv;
853 bcode = (instr[0] >> 6) & 0x3f; 869 bcode = (instr[0] >> 6) & 0x3f;
854 do_trap_or_bp(regs, bcode, "Break"); 870 do_trap_or_bp(regs, bcode, "Break");
855 return; 871 goto out;
856 } 872 }
857 } else { 873 } else {
858 if (__get_user(opcode, (unsigned int __user *) exception_epc(regs))) 874 if (__get_user(opcode, (unsigned int __user *) exception_epc(regs)))
@@ -876,12 +892,12 @@ asmlinkage void do_bp(struct pt_regs *regs)
876 switch (bcode) { 892 switch (bcode) {
877 case BRK_KPROBE_BP: 893 case BRK_KPROBE_BP:
878 if (notify_die(DIE_BREAK, "debug", regs, bcode, regs_to_trapnr(regs), SIGTRAP) == NOTIFY_STOP) 894 if (notify_die(DIE_BREAK, "debug", regs, bcode, regs_to_trapnr(regs), SIGTRAP) == NOTIFY_STOP)
879 return; 895 goto out;
880 else 896 else
881 break; 897 break;
882 case BRK_KPROBE_SSTEPBP: 898 case BRK_KPROBE_SSTEPBP:
883 if (notify_die(DIE_SSTEPBP, "single_step", regs, bcode, regs_to_trapnr(regs), SIGTRAP) == NOTIFY_STOP) 899 if (notify_die(DIE_SSTEPBP, "single_step", regs, bcode, regs_to_trapnr(regs), SIGTRAP) == NOTIFY_STOP)
884 return; 900 goto out;
885 else 901 else
886 break; 902 break;
887 default: 903 default:
@@ -889,18 +905,24 @@ asmlinkage void do_bp(struct pt_regs *regs)
889 } 905 }
890 906
891 do_trap_or_bp(regs, bcode, "Break"); 907 do_trap_or_bp(regs, bcode, "Break");
908
909out:
910 exception_exit(prev_state);
892 return; 911 return;
893 912
894out_sigsegv: 913out_sigsegv:
895 force_sig(SIGSEGV, current); 914 force_sig(SIGSEGV, current);
915 goto out;
896} 916}
897 917
898asmlinkage void do_tr(struct pt_regs *regs) 918asmlinkage void do_tr(struct pt_regs *regs)
899{ 919{
900 u32 opcode, tcode = 0; 920 u32 opcode, tcode = 0;
921 enum ctx_state prev_state;
901 u16 instr[2]; 922 u16 instr[2];
902 unsigned long epc = msk_isa16_mode(exception_epc(regs)); 923 unsigned long epc = msk_isa16_mode(exception_epc(regs));
903 924
925 prev_state = exception_enter();
904 if (get_isa16_mode(regs->cp0_epc)) { 926 if (get_isa16_mode(regs->cp0_epc)) {
905 if (__get_user(instr[0], (u16 __user *)(epc + 0)) || 927 if (__get_user(instr[0], (u16 __user *)(epc + 0)) ||
906 __get_user(instr[1], (u16 __user *)(epc + 2))) 928 __get_user(instr[1], (u16 __user *)(epc + 2)))
@@ -918,10 +940,14 @@ asmlinkage void do_tr(struct pt_regs *regs)
918 } 940 }
919 941
920 do_trap_or_bp(regs, tcode, "Trap"); 942 do_trap_or_bp(regs, tcode, "Trap");
943
944out:
945 exception_exit(prev_state);
921 return; 946 return;
922 947
923out_sigsegv: 948out_sigsegv:
924 force_sig(SIGSEGV, current); 949 force_sig(SIGSEGV, current);
950 goto out;
925} 951}
926 952
927asmlinkage void do_ri(struct pt_regs *regs) 953asmlinkage void do_ri(struct pt_regs *regs)
@@ -929,17 +955,19 @@ asmlinkage void do_ri(struct pt_regs *regs)
929 unsigned int __user *epc = (unsigned int __user *)exception_epc(regs); 955 unsigned int __user *epc = (unsigned int __user *)exception_epc(regs);
930 unsigned long old_epc = regs->cp0_epc; 956 unsigned long old_epc = regs->cp0_epc;
931 unsigned long old31 = regs->regs[31]; 957 unsigned long old31 = regs->regs[31];
958 enum ctx_state prev_state;
932 unsigned int opcode = 0; 959 unsigned int opcode = 0;
933 int status = -1; 960 int status = -1;
934 961
962 prev_state = exception_enter();
935 if (notify_die(DIE_RI, "RI Fault", regs, 0, regs_to_trapnr(regs), SIGILL) 963 if (notify_die(DIE_RI, "RI Fault", regs, 0, regs_to_trapnr(regs), SIGILL)
936 == NOTIFY_STOP) 964 == NOTIFY_STOP)
937 return; 965 goto out;
938 966
939 die_if_kernel("Reserved instruction in kernel code", regs); 967 die_if_kernel("Reserved instruction in kernel code", regs);
940 968
941 if (unlikely(compute_return_epc(regs) < 0)) 969 if (unlikely(compute_return_epc(regs) < 0))
942 return; 970 goto out;
943 971
944 if (get_isa16_mode(regs->cp0_epc)) { 972 if (get_isa16_mode(regs->cp0_epc)) {
945 unsigned short mmop[2] = { 0 }; 973 unsigned short mmop[2] = { 0 };
@@ -974,6 +1002,9 @@ asmlinkage void do_ri(struct pt_regs *regs)
974 regs->regs[31] = old31; 1002 regs->regs[31] = old31;
975 force_sig(status, current); 1003 force_sig(status, current);
976 } 1004 }
1005
1006out:
1007 exception_exit(prev_state);
977} 1008}
978 1009
979/* 1010/*
@@ -1025,21 +1056,16 @@ static int default_cu2_call(struct notifier_block *nfb, unsigned long action,
1025{ 1056{
1026 struct pt_regs *regs = data; 1057 struct pt_regs *regs = data;
1027 1058
1028 switch (action) { 1059 die_if_kernel("COP2: Unhandled kernel unaligned access or invalid "
1029 default:
1030 die_if_kernel("Unhandled kernel unaligned access or invalid "
1031 "instruction", regs); 1060 "instruction", regs);
1032 /* Fall through */ 1061 force_sig(SIGILL, current);
1033
1034 case CU2_EXCEPTION:
1035 force_sig(SIGILL, current);
1036 }
1037 1062
1038 return NOTIFY_OK; 1063 return NOTIFY_OK;
1039} 1064}
1040 1065
1041asmlinkage void do_cpu(struct pt_regs *regs) 1066asmlinkage void do_cpu(struct pt_regs *regs)
1042{ 1067{
1068 enum ctx_state prev_state;
1043 unsigned int __user *epc; 1069 unsigned int __user *epc;
1044 unsigned long old_epc, old31; 1070 unsigned long old_epc, old31;
1045 unsigned int opcode; 1071 unsigned int opcode;
@@ -1047,10 +1073,12 @@ asmlinkage void do_cpu(struct pt_regs *regs)
1047 int status; 1073 int status;
1048 unsigned long __maybe_unused flags; 1074 unsigned long __maybe_unused flags;
1049 1075
1050 die_if_kernel("do_cpu invoked from kernel context!", regs); 1076 prev_state = exception_enter();
1051
1052 cpid = (regs->cp0_cause >> CAUSEB_CE) & 3; 1077 cpid = (regs->cp0_cause >> CAUSEB_CE) & 3;
1053 1078
1079 if (cpid != 2)
1080 die_if_kernel("do_cpu invoked from kernel context!", regs);
1081
1054 switch (cpid) { 1082 switch (cpid) {
1055 case 0: 1083 case 0:
1056 epc = (unsigned int __user *)exception_epc(regs); 1084 epc = (unsigned int __user *)exception_epc(regs);
@@ -1060,7 +1088,7 @@ asmlinkage void do_cpu(struct pt_regs *regs)
1060 status = -1; 1088 status = -1;
1061 1089
1062 if (unlikely(compute_return_epc(regs) < 0)) 1090 if (unlikely(compute_return_epc(regs) < 0))
1063 return; 1091 goto out;
1064 1092
1065 if (get_isa16_mode(regs->cp0_epc)) { 1093 if (get_isa16_mode(regs->cp0_epc)) {
1066 unsigned short mmop[2] = { 0 }; 1094 unsigned short mmop[2] = { 0 };
@@ -1093,7 +1121,7 @@ asmlinkage void do_cpu(struct pt_regs *regs)
1093 force_sig(status, current); 1121 force_sig(status, current);
1094 } 1122 }
1095 1123
1096 return; 1124 goto out;
1097 1125
1098 case 3: 1126 case 3:
1099 /* 1127 /*
@@ -1131,19 +1159,26 @@ asmlinkage void do_cpu(struct pt_regs *regs)
1131 mt_ase_fp_affinity(); 1159 mt_ase_fp_affinity();
1132 } 1160 }
1133 1161
1134 return; 1162 goto out;
1135 1163
1136 case 2: 1164 case 2:
1137 raw_notifier_call_chain(&cu2_chain, CU2_EXCEPTION, regs); 1165 raw_notifier_call_chain(&cu2_chain, CU2_EXCEPTION, regs);
1138 return; 1166 goto out;
1139 } 1167 }
1140 1168
1141 force_sig(SIGILL, current); 1169 force_sig(SIGILL, current);
1170
1171out:
1172 exception_exit(prev_state);
1142} 1173}
1143 1174
1144asmlinkage void do_mdmx(struct pt_regs *regs) 1175asmlinkage void do_mdmx(struct pt_regs *regs)
1145{ 1176{
1177 enum ctx_state prev_state;
1178
1179 prev_state = exception_enter();
1146 force_sig(SIGILL, current); 1180 force_sig(SIGILL, current);
1181 exception_exit(prev_state);
1147} 1182}
1148 1183
1149/* 1184/*
@@ -1151,8 +1186,10 @@ asmlinkage void do_mdmx(struct pt_regs *regs)
1151 */ 1186 */
1152asmlinkage void do_watch(struct pt_regs *regs) 1187asmlinkage void do_watch(struct pt_regs *regs)
1153{ 1188{
1189 enum ctx_state prev_state;
1154 u32 cause; 1190 u32 cause;
1155 1191
1192 prev_state = exception_enter();
1156 /* 1193 /*
1157 * Clear WP (bit 22) bit of cause register so we don't loop 1194 * Clear WP (bit 22) bit of cause register so we don't loop
1158 * forever. 1195 * forever.
@@ -1174,13 +1211,16 @@ asmlinkage void do_watch(struct pt_regs *regs)
1174 mips_clear_watch_registers(); 1211 mips_clear_watch_registers();
1175 local_irq_enable(); 1212 local_irq_enable();
1176 } 1213 }
1214 exception_exit(prev_state);
1177} 1215}
1178 1216
1179asmlinkage void do_mcheck(struct pt_regs *regs) 1217asmlinkage void do_mcheck(struct pt_regs *regs)
1180{ 1218{
1181 const int field = 2 * sizeof(unsigned long); 1219 const int field = 2 * sizeof(unsigned long);
1182 int multi_match = regs->cp0_status & ST0_TS; 1220 int multi_match = regs->cp0_status & ST0_TS;
1221 enum ctx_state prev_state;
1183 1222
1223 prev_state = exception_enter();
1184 show_regs(regs); 1224 show_regs(regs);
1185 1225
1186 if (multi_match) { 1226 if (multi_match) {
@@ -1202,6 +1242,7 @@ asmlinkage void do_mcheck(struct pt_regs *regs)
1202 panic("Caught Machine Check exception - %scaused by multiple " 1242 panic("Caught Machine Check exception - %scaused by multiple "
1203 "matching entries in the TLB.", 1243 "matching entries in the TLB.",
1204 (multi_match) ? "" : "not "); 1244 (multi_match) ? "" : "not ");
1245 exception_exit(prev_state);
1205} 1246}
1206 1247
1207asmlinkage void do_mt(struct pt_regs *regs) 1248asmlinkage void do_mt(struct pt_regs *regs)
@@ -1627,7 +1668,6 @@ void *set_vi_handler(int n, vi_handler_t addr)
1627} 1668}
1628 1669
1629extern void tlb_init(void); 1670extern void tlb_init(void);
1630extern void flush_tlb_handlers(void);
1631 1671
1632/* 1672/*
1633 * Timer interrupt 1673 * Timer interrupt
@@ -1837,6 +1877,15 @@ void __init trap_init(void)
1837 ebase += (read_c0_ebase() & 0x3ffff000); 1877 ebase += (read_c0_ebase() & 0x3ffff000);
1838 } 1878 }
1839 1879
1880 if (cpu_has_mmips) {
1881 unsigned int config3 = read_c0_config3();
1882
1883 if (IS_ENABLED(CONFIG_CPU_MICROMIPS))
1884 write_c0_config3(config3 | MIPS_CONF3_ISA_OE);
1885 else
1886 write_c0_config3(config3 & ~MIPS_CONF3_ISA_OE);
1887 }
1888
1840 if (board_ebase_setup) 1889 if (board_ebase_setup)
1841 board_ebase_setup(); 1890 board_ebase_setup();
1842 per_cpu_trap_init(true); 1891 per_cpu_trap_init(true);
@@ -1956,7 +2005,6 @@ void __init trap_init(void)
1956 set_handler(0x080, &except_vec3_generic, 0x80); 2005 set_handler(0x080, &except_vec3_generic, 0x80);
1957 2006
1958 local_flush_icache_range(ebase, ebase + 0x400); 2007 local_flush_icache_range(ebase, ebase + 0x400);
1959 flush_tlb_handlers();
1960 2008
1961 sort_extable(__start___dbe_table, __stop___dbe_table); 2009 sort_extable(__start___dbe_table, __stop___dbe_table);
1962 2010
diff --git a/arch/mips/kernel/unaligned.c b/arch/mips/kernel/unaligned.c
index 203d8857070d..c369a5d35527 100644
--- a/arch/mips/kernel/unaligned.c
+++ b/arch/mips/kernel/unaligned.c
@@ -72,6 +72,7 @@
72 * A store crossing a page boundary might be executed only partially. 72 * A store crossing a page boundary might be executed only partially.
73 * Undo the partial store in this case. 73 * Undo the partial store in this case.
74 */ 74 */
75#include <linux/context_tracking.h>
75#include <linux/mm.h> 76#include <linux/mm.h>
76#include <linux/signal.h> 77#include <linux/signal.h>
77#include <linux/smp.h> 78#include <linux/smp.h>
@@ -684,7 +685,8 @@ const int reg16to32[] = { 16, 17, 2, 3, 4, 5, 6, 7 };
684/* Recode table from 16-bit STORE register notation to 32-bit GPR. */ 685/* Recode table from 16-bit STORE register notation to 32-bit GPR. */
685const int reg16to32st[] = { 0, 17, 2, 3, 4, 5, 6, 7 }; 686const int reg16to32st[] = { 0, 17, 2, 3, 4, 5, 6, 7 };
686 687
687void emulate_load_store_microMIPS(struct pt_regs *regs, void __user * addr) 688static void emulate_load_store_microMIPS(struct pt_regs *regs,
689 void __user *addr)
688{ 690{
689 unsigned long value; 691 unsigned long value;
690 unsigned int res; 692 unsigned int res;
@@ -1548,11 +1550,14 @@ sigill:
1548 ("Unhandled kernel unaligned access or invalid instruction", regs); 1550 ("Unhandled kernel unaligned access or invalid instruction", regs);
1549 force_sig(SIGILL, current); 1551 force_sig(SIGILL, current);
1550} 1552}
1553
1551asmlinkage void do_ade(struct pt_regs *regs) 1554asmlinkage void do_ade(struct pt_regs *regs)
1552{ 1555{
1556 enum ctx_state prev_state;
1553 unsigned int __user *pc; 1557 unsigned int __user *pc;
1554 mm_segment_t seg; 1558 mm_segment_t seg;
1555 1559
1560 prev_state = exception_enter();
1556 perf_sw_event(PERF_COUNT_SW_ALIGNMENT_FAULTS, 1561 perf_sw_event(PERF_COUNT_SW_ALIGNMENT_FAULTS,
1557 1, regs, regs->cp0_badvaddr); 1562 1, regs, regs->cp0_badvaddr);
1558 /* 1563 /*
@@ -1628,6 +1633,7 @@ sigbus:
1628 /* 1633 /*
1629 * XXX On return from the signal handler we should advance the epc 1634 * XXX On return from the signal handler we should advance the epc
1630 */ 1635 */
1636 exception_exit(prev_state);
1631} 1637}
1632 1638
1633#ifdef CONFIG_DEBUG_FS 1639#ifdef CONFIG_DEBUG_FS
diff --git a/arch/mips/kernel/watch.c b/arch/mips/kernel/watch.c
index 7726f6157d9e..cbdc4de85bb4 100644
--- a/arch/mips/kernel/watch.c
+++ b/arch/mips/kernel/watch.c
@@ -111,6 +111,7 @@ __cpuinit void mips_probe_watch_registers(struct cpuinfo_mips *c)
111 * disable the register. 111 * disable the register.
112 */ 112 */
113 write_c0_watchlo0(7); 113 write_c0_watchlo0(7);
114 back_to_back_c0_hazard();
114 t = read_c0_watchlo0(); 115 t = read_c0_watchlo0();
115 write_c0_watchlo0(0); 116 write_c0_watchlo0(0);
116 c->watch_reg_masks[0] = t & 7; 117 c->watch_reg_masks[0] = t & 7;
@@ -121,12 +122,14 @@ __cpuinit void mips_probe_watch_registers(struct cpuinfo_mips *c)
121 c->watch_reg_use_cnt = 1; 122 c->watch_reg_use_cnt = 1;
122 t = read_c0_watchhi0(); 123 t = read_c0_watchhi0();
123 write_c0_watchhi0(t | 0xff8); 124 write_c0_watchhi0(t | 0xff8);
125 back_to_back_c0_hazard();
124 t = read_c0_watchhi0(); 126 t = read_c0_watchhi0();
125 c->watch_reg_masks[0] |= (t & 0xff8); 127 c->watch_reg_masks[0] |= (t & 0xff8);
126 if ((t & 0x80000000) == 0) 128 if ((t & 0x80000000) == 0)
127 return; 129 return;
128 130
129 write_c0_watchlo1(7); 131 write_c0_watchlo1(7);
132 back_to_back_c0_hazard();
130 t = read_c0_watchlo1(); 133 t = read_c0_watchlo1();
131 write_c0_watchlo1(0); 134 write_c0_watchlo1(0);
132 c->watch_reg_masks[1] = t & 7; 135 c->watch_reg_masks[1] = t & 7;
@@ -135,12 +138,14 @@ __cpuinit void mips_probe_watch_registers(struct cpuinfo_mips *c)
135 c->watch_reg_use_cnt = 2; 138 c->watch_reg_use_cnt = 2;
136 t = read_c0_watchhi1(); 139 t = read_c0_watchhi1();
137 write_c0_watchhi1(t | 0xff8); 140 write_c0_watchhi1(t | 0xff8);
141 back_to_back_c0_hazard();
138 t = read_c0_watchhi1(); 142 t = read_c0_watchhi1();
139 c->watch_reg_masks[1] |= (t & 0xff8); 143 c->watch_reg_masks[1] |= (t & 0xff8);
140 if ((t & 0x80000000) == 0) 144 if ((t & 0x80000000) == 0)
141 return; 145 return;
142 146
143 write_c0_watchlo2(7); 147 write_c0_watchlo2(7);
148 back_to_back_c0_hazard();
144 t = read_c0_watchlo2(); 149 t = read_c0_watchlo2();
145 write_c0_watchlo2(0); 150 write_c0_watchlo2(0);
146 c->watch_reg_masks[2] = t & 7; 151 c->watch_reg_masks[2] = t & 7;
@@ -149,12 +154,14 @@ __cpuinit void mips_probe_watch_registers(struct cpuinfo_mips *c)
149 c->watch_reg_use_cnt = 3; 154 c->watch_reg_use_cnt = 3;
150 t = read_c0_watchhi2(); 155 t = read_c0_watchhi2();
151 write_c0_watchhi2(t | 0xff8); 156 write_c0_watchhi2(t | 0xff8);
157 back_to_back_c0_hazard();
152 t = read_c0_watchhi2(); 158 t = read_c0_watchhi2();
153 c->watch_reg_masks[2] |= (t & 0xff8); 159 c->watch_reg_masks[2] |= (t & 0xff8);
154 if ((t & 0x80000000) == 0) 160 if ((t & 0x80000000) == 0)
155 return; 161 return;
156 162
157 write_c0_watchlo3(7); 163 write_c0_watchlo3(7);
164 back_to_back_c0_hazard();
158 t = read_c0_watchlo3(); 165 t = read_c0_watchlo3();
159 write_c0_watchlo3(0); 166 write_c0_watchlo3(0);
160 c->watch_reg_masks[3] = t & 7; 167 c->watch_reg_masks[3] = t & 7;
@@ -163,6 +170,7 @@ __cpuinit void mips_probe_watch_registers(struct cpuinfo_mips *c)
163 c->watch_reg_use_cnt = 4; 170 c->watch_reg_use_cnt = 4;
164 t = read_c0_watchhi3(); 171 t = read_c0_watchhi3();
165 write_c0_watchhi3(t | 0xff8); 172 write_c0_watchhi3(t | 0xff8);
173 back_to_back_c0_hazard();
166 t = read_c0_watchhi3(); 174 t = read_c0_watchhi3();
167 c->watch_reg_masks[3] |= (t & 0xff8); 175 c->watch_reg_masks[3] |= (t & 0xff8);
168 if ((t & 0x80000000) == 0) 176 if ((t & 0x80000000) == 0)