diff options
| -rw-r--r-- | arch/mips/kernel/traps.c | 21 |
1 files changed, 18 insertions, 3 deletions
diff --git a/arch/mips/kernel/traps.c b/arch/mips/kernel/traps.c index d6103e510899..6379003f9d8d 100644 --- a/arch/mips/kernel/traps.c +++ b/arch/mips/kernel/traps.c | |||
| @@ -606,6 +606,8 @@ asmlinkage void do_ov(struct pt_regs *regs) | |||
| 606 | */ | 606 | */ |
| 607 | asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31) | 607 | asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31) |
| 608 | { | 608 | { |
| 609 | siginfo_t info; | ||
| 610 | |||
| 609 | die_if_kernel("FP exception in kernel code", regs); | 611 | die_if_kernel("FP exception in kernel code", regs); |
| 610 | 612 | ||
| 611 | if (fcr31 & FPU_CSR_UNI_X) { | 613 | if (fcr31 & FPU_CSR_UNI_X) { |
| @@ -641,9 +643,22 @@ asmlinkage void do_fpe(struct pt_regs *regs, unsigned long fcr31) | |||
| 641 | force_sig(sig, current); | 643 | force_sig(sig, current); |
| 642 | 644 | ||
| 643 | return; | 645 | return; |
| 644 | } | 646 | } else if (fcr31 & FPU_CSR_INV_X) |
| 645 | 647 | info.si_code = FPE_FLTINV; | |
| 646 | force_sig(SIGFPE, current); | 648 | else if (fcr31 & FPU_CSR_DIV_X) |
| 649 | info.si_code = FPE_FLTDIV; | ||
| 650 | else if (fcr31 & FPU_CSR_OVF_X) | ||
| 651 | info.si_code = FPE_FLTOVF; | ||
| 652 | else if (fcr31 & FPU_CSR_UDF_X) | ||
| 653 | info.si_code = FPE_FLTUND; | ||
| 654 | else if (fcr31 & FPU_CSR_INE_X) | ||
| 655 | info.si_code = FPE_FLTRES; | ||
| 656 | else | ||
| 657 | info.si_code = __SI_FAULT; | ||
| 658 | info.si_signo = SIGFPE; | ||
| 659 | info.si_errno = 0; | ||
| 660 | info.si_addr = (void __user *) regs->cp0_epc; | ||
| 661 | force_sig_info(SIGFPE, &info, current); | ||
| 647 | } | 662 | } |
| 648 | 663 | ||
| 649 | asmlinkage void do_bp(struct pt_regs *regs) | 664 | asmlinkage void do_bp(struct pt_regs *regs) |
