aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/mm
diff options
context:
space:
mode:
Diffstat (limited to 'arch/x86/mm')
-rw-r--r--arch/x86/mm/fault.c14
1 files changed, 13 insertions, 1 deletions
diff --git a/arch/x86/mm/fault.c b/arch/x86/mm/fault.c
index 4d09df054e39..247aae3dc008 100644
--- a/arch/x86/mm/fault.c
+++ b/arch/x86/mm/fault.c
@@ -105,7 +105,7 @@ check_prefetch_opcode(struct pt_regs *regs, unsigned char *instr,
105 * but for now it's good enough to assume that long 105 * but for now it's good enough to assume that long
106 * mode only uses well known segments or kernel. 106 * mode only uses well known segments or kernel.
107 */ 107 */
108 return (!user_mode(regs)) || (regs->cs == __USER_CS); 108 return (!user_mode(regs) || user_64bit_mode(regs));
109#endif 109#endif
110 case 0x60: 110 case 0x60:
111 /* 0x64 thru 0x67 are valid prefixes in all modes. */ 111 /* 0x64 thru 0x67 are valid prefixes in all modes. */
@@ -720,6 +720,18 @@ __bad_area_nosemaphore(struct pt_regs *regs, unsigned long error_code,
720 if (is_errata100(regs, address)) 720 if (is_errata100(regs, address))
721 return; 721 return;
722 722
723#ifdef CONFIG_X86_64
724 /*
725 * Instruction fetch faults in the vsyscall page might need
726 * emulation.
727 */
728 if (unlikely((error_code & PF_INSTR) &&
729 ((address & ~0xfff) == VSYSCALL_START))) {
730 if (emulate_vsyscall(regs, address))
731 return;
732 }
733#endif
734
723 if (unlikely(show_unhandled_signals)) 735 if (unlikely(show_unhandled_signals))
724 show_signal_msg(regs, error_code, address, tsk); 736 show_signal_msg(regs, error_code, address, tsk);
725 737