aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86/kernel
diff options
context:
space:
mode:
authorTony Luck <tony.luck@intel.com>2016-02-17 13:20:12 -0500
committerIngo Molnar <mingo@kernel.org>2016-02-18 03:21:46 -0500
commit548acf19234dbda5a52d5a8e7e205af46e9da840 (patch)
tree4dabffd6070e082620a47de718bbab508f928440 /arch/x86/kernel
parent061f817eb6a6f97a7e34b73e5e80baa3a20b7663 (diff)
x86/mm: Expand the exception table logic to allow new handling options
Huge amounts of help from Andy Lutomirski and Borislav Petkov to produce this. Andy provided the inspiration to add classes to the exception table with a clever bit-squeezing trick, Boris pointed out how much cleaner it would all be if we just had a new field. Linus Torvalds blessed the expansion with: ' I'd rather not be clever in order to save just a tiny amount of space in the exception table, which isn't really criticial for anybody. ' The third field is another relative function pointer, this one to a handler that executes the actions. We start out with three handlers: 1: Legacy - just jumps the to fixup IP 2: Fault - provide the trap number in %ax to the fixup code 3: Cleaned up legacy for the uaccess error hack Signed-off-by: Tony Luck <tony.luck@intel.com> Reviewed-by: Borislav Petkov <bp@suse.de> Cc: Linus Torvalds <torvalds@linux-foundation.org> Cc: Peter Zijlstra <peterz@infradead.org> Cc: Thomas Gleixner <tglx@linutronix.de> Link: http://lkml.kernel.org/r/f6af78fcbd348cf4939875cfda9c19689b5e50b8.1455732970.git.tony.luck@intel.com Signed-off-by: Ingo Molnar <mingo@kernel.org>
Diffstat (limited to 'arch/x86/kernel')
-rw-r--r--arch/x86/kernel/kprobes/core.c2
-rw-r--r--arch/x86/kernel/traps.c6
2 files changed, 4 insertions, 4 deletions
diff --git a/arch/x86/kernel/kprobes/core.c b/arch/x86/kernel/kprobes/core.c
index 1deffe6cc873..0f05deeff5ce 100644
--- a/arch/x86/kernel/kprobes/core.c
+++ b/arch/x86/kernel/kprobes/core.c
@@ -988,7 +988,7 @@ int kprobe_fault_handler(struct pt_regs *regs, int trapnr)
988 * In case the user-specified fault handler returned 988 * In case the user-specified fault handler returned
989 * zero, try to fix up. 989 * zero, try to fix up.
990 */ 990 */
991 if (fixup_exception(regs)) 991 if (fixup_exception(regs, trapnr))
992 return 1; 992 return 1;
993 993
994 /* 994 /*
diff --git a/arch/x86/kernel/traps.c b/arch/x86/kernel/traps.c
index ade185a46b1d..211c11c7bba4 100644
--- a/arch/x86/kernel/traps.c
+++ b/arch/x86/kernel/traps.c
@@ -199,7 +199,7 @@ do_trap_no_signal(struct task_struct *tsk, int trapnr, char *str,
199 } 199 }
200 200
201 if (!user_mode(regs)) { 201 if (!user_mode(regs)) {
202 if (!fixup_exception(regs)) { 202 if (!fixup_exception(regs, trapnr)) {
203 tsk->thread.error_code = error_code; 203 tsk->thread.error_code = error_code;
204 tsk->thread.trap_nr = trapnr; 204 tsk->thread.trap_nr = trapnr;
205 die(str, regs, error_code); 205 die(str, regs, error_code);
@@ -453,7 +453,7 @@ do_general_protection(struct pt_regs *regs, long error_code)
453 453
454 tsk = current; 454 tsk = current;
455 if (!user_mode(regs)) { 455 if (!user_mode(regs)) {
456 if (fixup_exception(regs)) 456 if (fixup_exception(regs, X86_TRAP_GP))
457 return; 457 return;
458 458
459 tsk->thread.error_code = error_code; 459 tsk->thread.error_code = error_code;
@@ -699,7 +699,7 @@ static void math_error(struct pt_regs *regs, int error_code, int trapnr)
699 conditional_sti(regs); 699 conditional_sti(regs);
700 700
701 if (!user_mode(regs)) { 701 if (!user_mode(regs)) {
702 if (!fixup_exception(regs)) { 702 if (!fixup_exception(regs, trapnr)) {
703 task->thread.error_code = error_code; 703 task->thread.error_code = error_code;
704 task->thread.trap_nr = trapnr; 704 task->thread.trap_nr = trapnr;
705 die(str, regs, error_code); 705 die(str, regs, error_code);