mirror of https://github.com/OpenIPC/firmware.git
138 lines
5.7 KiB
Diff
138 lines
5.7 KiB
Diff
diff -drupN a/arch/mips/kernel/traps.c b/arch/mips/kernel/traps.c
|
|
--- a/arch/mips/kernel/traps.c 2017-10-21 18:09:07.000000000 +0300
|
|
+++ b/arch/mips/kernel/traps.c 2022-06-09 05:02:27.000000000 +0300
|
|
@@ -64,6 +64,8 @@
|
|
#include <asm/types.h>
|
|
#include <asm/stacktrace.h>
|
|
#include <asm/uasm.h>
|
|
+#include <asm/smp.h>
|
|
+
|
|
|
|
extern void check_wait(void);
|
|
extern asmlinkage void rollback_handle_int(void);
|
|
@@ -85,7 +87,11 @@ extern asmlinkage void handle_ov(void);
|
|
extern asmlinkage void handle_tr(void);
|
|
extern asmlinkage void handle_msa_fpe(void);
|
|
extern asmlinkage void handle_fpe(void);
|
|
+#ifdef CONFIG_XBURST_MXUV2
|
|
+extern asmlinkage void handle_mfpe(void);
|
|
+#else
|
|
extern asmlinkage void handle_ftlb(void);
|
|
+#endif
|
|
extern asmlinkage void handle_msa(void);
|
|
extern asmlinkage void handle_mdmx(void);
|
|
extern asmlinkage void handle_watch(void);
|
|
@@ -873,6 +879,14 @@ out:
|
|
exception_exit(prev_state);
|
|
}
|
|
|
|
+#ifdef CONFIG_MACH_XBURST
|
|
+asmlinkage void do_mfpe(struct pt_regs * regs)
|
|
+{
|
|
+ die_if_kernel("Kernel bug detected", regs);
|
|
+ force_sig(SIGILL, current);
|
|
+}
|
|
+#endif
|
|
+
|
|
void do_trap_or_bp(struct pt_regs *regs, unsigned int code,
|
|
const char *str)
|
|
{
|
|
@@ -1077,6 +1091,21 @@ asmlinkage void do_ri(struct pt_regs *re
|
|
unsigned int opcode = 0;
|
|
int status = -1;
|
|
|
|
+ /* If Config1.CU2 is not set, the exc_code = 10 of cause reg */
|
|
+ if (cpu_has_mxuv3 && (1 == smp_processor_id())) {
|
|
+ printk("%s(%d):reschedule to cpu0 to smp_processor_id()=%d, read_c0_status()=0x%x, task_cpu(current)=%d, KSTK_STATUS(current)=0x%lx, current->tgid=%d, current->pid=%d\n", __func__, __LINE__, smp_processor_id(), read_c0_status(), task_cpu(current), KSTK_STATUS(current), current->tgid, current->pid);
|
|
+ //resched_cpu(0);
|
|
+ write_c0_cache(0x2000ff0f);
|
|
+ smp_send_reschedule(0);
|
|
+ if (0 == smp_processor_id()) {
|
|
+ printk("%s(%d):open cu2 field to cpu0 to smp_processor_id()=%d, read_c0_status()=0x%x, task_cpu(current)=%d, KSTK_STATUS(current)=0x%lx, current->tgid=%d, current->pid=%d\n", __func__, __LINE__, smp_processor_id(), read_c0_status(), task_cpu(current), KSTK_STATUS(current), current->tgid, current->pid);
|
|
+ set_c0_status(ST0_CU2);
|
|
+ KSTK_STATUS(current) |= ST0_CU2;
|
|
+ }
|
|
+ printk("%s(%d):no cu2 coprocessor to smp_processor_id()=%d, read_c0_status()=0x%x, task_cpu(current)=%d, KSTK_STATUS(current)=0x%lx, current->tgid=%d, current->pid=%d\n", __func__, __LINE__, smp_processor_id(), read_c0_status(), task_cpu(current), KSTK_STATUS(current), current->tgid, current->pid);
|
|
+ return;
|
|
+ }
|
|
+
|
|
/*
|
|
* Avoid any kernel code. Just emulate the R2 instruction
|
|
* as quickly as possible.
|
|
@@ -1445,10 +1474,38 @@ asmlinkage void do_cpu(struct pt_regs *r
|
|
break;
|
|
|
|
case 2:
|
|
+#ifdef CONFIG_MACH_XBURST2
|
|
+#if 0
|
|
+ /* Processing of MXA instructions needs setting MSA enable. */
|
|
+ if (cpu_has_mxuv3 && (KSTK_STATUS(current) & ST0_CU2)) {
|
|
+ err = enable_restore_fp_context(0);
|
|
+ if (err) {
|
|
+ printk("===debug CU2 exception, KSTK_STATUS(current) & ST0_CU2=0x%lx\n", KSTK_STATUS(current) & ST0_CU2);
|
|
+ force_sig(SIGILL, current);
|
|
+ }
|
|
+ }
|
|
+
|
|
+#else
|
|
+
|
|
+ /* To Xburst2 T40, If Status.CU2 is not set and Config1.CU2 is set, the exc_code is 10 and CE field is 2 to Cause Reg
|
|
+ * So here only need to open the Status.CU2 field */
|
|
+ if (cpu_has_mxuv3 && (0 == smp_processor_id())) {
|
|
+ set_c0_status(ST0_CU2);
|
|
+ KSTK_STATUS(current) |= ST0_CU2;
|
|
+// printk("%s(%d):open cu2 field to cpu0 to smp_processor_id()=%d, read_c0_status()=0x%x, task_cpu(current)=%d, KSTK_STATUS(current)=0x%lx, current->tgid=%d, current->pid=%d\n", __func__, __LINE__, smp_processor_id(), read_c0_status(), task_cpu(current), KSTK_STATUS(current), current->tgid, current->pid);
|
|
+ goto out;
|
|
+ } else if (1 == smp_processor_id()) {
|
|
+ printk("%s(%d):no cu2 coprocessor to smp_processor_id()=%d, read_c0_status()=0x%x, task_cpu(current)=%d, KSTK_STATUS(current)=0x%lx, current->tgid=%d, current->pid=%d\n", __func__, __LINE__, smp_processor_id(), read_c0_status(), task_cpu(current), KSTK_STATUS(current), current->tgid, current->pid);
|
|
+ force_sig(SIGILL, current);
|
|
+ goto out;
|
|
+ }
|
|
+#endif
|
|
+#else
|
|
raw_notifier_call_chain(&cu2_chain, CU2_EXCEPTION, regs);
|
|
- break;
|
|
+#endif
|
|
+ goto out;
|
|
}
|
|
-
|
|
+out:
|
|
exception_exit(prev_state);
|
|
}
|
|
|
|
@@ -2070,6 +2127,9 @@ static void configure_status(void)
|
|
status_set |= ST0_XX;
|
|
if (cpu_has_dsp)
|
|
status_set |= ST0_MX;
|
|
+ if (cpu_has_mxuv3 && (KSTK_STATUS(current) & ST0_CU2)) {
|
|
+ status_set |= ST0_CU2;
|
|
+ }
|
|
|
|
change_c0_status(ST0_CU|ST0_MX|ST0_RE|ST0_FR|ST0_BEV|ST0_TS|ST0_KX|ST0_SX|ST0_UX,
|
|
status_set);
|
|
@@ -2087,7 +2147,7 @@ static void configure_hwrena(void)
|
|
hwrena |= (1 << 29);
|
|
|
|
if (hwrena)
|
|
- write_c0_hwrena(hwrena);
|
|
+ write_c0_hwrena(0x2000ff0f);
|
|
}
|
|
|
|
static void configure_exception_vector(void)
|
|
@@ -2321,8 +2381,14 @@ void __init trap_init(void)
|
|
if (cpu_has_fpu && !cpu_has_nofpuex)
|
|
set_except_vector(15, handle_fpe);
|
|
|
|
+#ifdef CONFIG_XBURST_MXUV2
|
|
+ if (cpu_has_mxu)
|
|
+ set_except_vector(16, handle_fpe);
|
|
+ if (cpu_has_mxuv3)
|
|
+ set_except_vector(16, handle_fpe);
|
|
+#else
|
|
set_except_vector(16, handle_ftlb);
|
|
-
|
|
+#endif
|
|
if (cpu_has_rixiex) {
|
|
set_except_vector(19, tlb_do_page_fault_0);
|
|
set_except_vector(20, tlb_do_page_fault_0);
|