Commit e407d620 authored by Alexander van Heukelum's avatar Alexander van Heukelum Committed by Ingo Molnar

x86, traps: introduce dotraplinkage

Mark the exception handlers with "dotraplinkage" to hide the
calling convention differences between i386 and x86_64.
Signed-off-by: default avatarAlexander van Heukelum <heukelum@fastmail.fm>
Signed-off-by: default avatarIngo Molnar <mingo@elte.hu>
parent ae82157b
...@@ -1243,7 +1243,7 @@ ENTRY(simd_coprocessor_error) ...@@ -1243,7 +1243,7 @@ ENTRY(simd_coprocessor_error)
END(simd_coprocessor_error) END(simd_coprocessor_error)
ENTRY(device_not_available) ENTRY(device_not_available)
zeroentry math_state_restore zeroentry do_device_not_available
END(device_not_available) END(device_not_available)
/* runs on exception stack */ /* runs on exception stack */
......
...@@ -190,7 +190,7 @@ do_trap(int trapnr, int signr, char *str, struct pt_regs *regs, ...@@ -190,7 +190,7 @@ do_trap(int trapnr, int signr, char *str, struct pt_regs *regs,
} }
#define DO_ERROR(trapnr, signr, str, name) \ #define DO_ERROR(trapnr, signr, str, name) \
void do_##name(struct pt_regs *regs, long error_code) \ dotraplinkage void do_##name(struct pt_regs *regs, long error_code) \
{ \ { \
if (notify_die(DIE_TRAP, str, regs, error_code, trapnr, signr) \ if (notify_die(DIE_TRAP, str, regs, error_code, trapnr, signr) \
== NOTIFY_STOP) \ == NOTIFY_STOP) \
...@@ -200,7 +200,7 @@ void do_##name(struct pt_regs *regs, long error_code) \ ...@@ -200,7 +200,7 @@ void do_##name(struct pt_regs *regs, long error_code) \
} }
#define DO_ERROR_INFO(trapnr, signr, str, name, sicode, siaddr) \ #define DO_ERROR_INFO(trapnr, signr, str, name, sicode, siaddr) \
void do_##name(struct pt_regs *regs, long error_code) \ dotraplinkage void do_##name(struct pt_regs *regs, long error_code) \
{ \ { \
siginfo_t info; \ siginfo_t info; \
info.si_signo = signr; \ info.si_signo = signr; \
...@@ -224,7 +224,7 @@ DO_ERROR(11, SIGBUS, "segment not present", segment_not_present) ...@@ -224,7 +224,7 @@ DO_ERROR(11, SIGBUS, "segment not present", segment_not_present)
DO_ERROR(12, SIGBUS, "stack segment", stack_segment) DO_ERROR(12, SIGBUS, "stack segment", stack_segment)
DO_ERROR_INFO(17, SIGBUS, "alignment check", alignment_check, BUS_ADRALN, 0) DO_ERROR_INFO(17, SIGBUS, "alignment check", alignment_check, BUS_ADRALN, 0)
void __kprobes dotraplinkage void __kprobes
do_general_protection(struct pt_regs *regs, long error_code) do_general_protection(struct pt_regs *regs, long error_code)
{ {
struct task_struct *tsk; struct task_struct *tsk;
...@@ -428,7 +428,8 @@ static notrace __kprobes void default_do_nmi(struct pt_regs *regs) ...@@ -428,7 +428,8 @@ static notrace __kprobes void default_do_nmi(struct pt_regs *regs)
reassert_nmi(); reassert_nmi();
} }
notrace __kprobes void do_nmi(struct pt_regs *regs, long error_code) dotraplinkage notrace __kprobes void
do_nmi(struct pt_regs *regs, long error_code)
{ {
int cpu; int cpu;
...@@ -456,7 +457,7 @@ void restart_nmi(void) ...@@ -456,7 +457,7 @@ void restart_nmi(void)
acpi_nmi_enable(); acpi_nmi_enable();
} }
void __kprobes do_int3(struct pt_regs *regs, long error_code) dotraplinkage void __kprobes do_int3(struct pt_regs *regs, long error_code)
{ {
#ifdef CONFIG_KPROBES #ifdef CONFIG_KPROBES
if (notify_die(DIE_INT3, "int3", regs, error_code, 3, SIGTRAP) if (notify_die(DIE_INT3, "int3", regs, error_code, 3, SIGTRAP)
...@@ -494,7 +495,7 @@ void __kprobes do_int3(struct pt_regs *regs, long error_code) ...@@ -494,7 +495,7 @@ void __kprobes do_int3(struct pt_regs *regs, long error_code)
* find every occurrence of the TF bit that could be saved away even * find every occurrence of the TF bit that could be saved away even
* by user code) * by user code)
*/ */
void __kprobes do_debug(struct pt_regs *regs, long error_code) dotraplinkage void __kprobes do_debug(struct pt_regs *regs, long error_code)
{ {
struct task_struct *tsk = current; struct task_struct *tsk = current;
unsigned int condition; unsigned int condition;
...@@ -627,7 +628,7 @@ void math_error(void __user *ip) ...@@ -627,7 +628,7 @@ void math_error(void __user *ip)
force_sig_info(SIGFPE, &info, task); force_sig_info(SIGFPE, &info, task);
} }
void do_coprocessor_error(struct pt_regs *regs, long error_code) dotraplinkage void do_coprocessor_error(struct pt_regs *regs, long error_code)
{ {
conditional_sti(regs); conditional_sti(regs);
ignore_fpu_irq = 1; ignore_fpu_irq = 1;
...@@ -682,7 +683,8 @@ static void simd_math_error(void __user *ip) ...@@ -682,7 +683,8 @@ static void simd_math_error(void __user *ip)
force_sig_info(SIGFPE, &info, task); force_sig_info(SIGFPE, &info, task);
} }
void do_simd_coprocessor_error(struct pt_regs *regs, long error_code) dotraplinkage void
do_simd_coprocessor_error(struct pt_regs *regs, long error_code)
{ {
conditional_sti(regs); conditional_sti(regs);
...@@ -706,7 +708,8 @@ void do_simd_coprocessor_error(struct pt_regs *regs, long error_code) ...@@ -706,7 +708,8 @@ void do_simd_coprocessor_error(struct pt_regs *regs, long error_code)
force_sig(SIGSEGV, current); force_sig(SIGSEGV, current);
} }
void do_spurious_interrupt_bug(struct pt_regs *regs, long error_code) dotraplinkage void
do_spurious_interrupt_bug(struct pt_regs *regs, long error_code)
{ {
conditional_sti(regs); conditional_sti(regs);
#if 0 #if 0
...@@ -784,7 +787,8 @@ asmlinkage void math_emulate(long arg) ...@@ -784,7 +787,8 @@ asmlinkage void math_emulate(long arg)
#endif /* CONFIG_MATH_EMULATION */ #endif /* CONFIG_MATH_EMULATION */
void __kprobes do_device_not_available(struct pt_regs *regs, long error) dotraplinkage void __kprobes
do_device_not_available(struct pt_regs *regs, long error)
{ {
if (read_cr0() & X86_CR0_EM) { if (read_cr0() & X86_CR0_EM) {
conditional_sti(regs); conditional_sti(regs);
...@@ -796,14 +800,14 @@ void __kprobes do_device_not_available(struct pt_regs *regs, long error) ...@@ -796,14 +800,14 @@ void __kprobes do_device_not_available(struct pt_regs *regs, long error)
} }
#ifdef CONFIG_X86_MCE #ifdef CONFIG_X86_MCE
void __kprobes do_machine_check(struct pt_regs *regs, long error) dotraplinkage void __kprobes do_machine_check(struct pt_regs *regs, long error)
{ {
conditional_sti(regs); conditional_sti(regs);
machine_check_vector(regs, error); machine_check_vector(regs, error);
} }
#endif #endif
void do_iret_error(struct pt_regs *regs, long error_code) dotraplinkage void do_iret_error(struct pt_regs *regs, long error_code)
{ {
siginfo_t info; siginfo_t info;
local_irq_enable(); local_irq_enable();
......
...@@ -125,7 +125,7 @@ do_trap(int trapnr, int signr, char *str, struct pt_regs *regs, ...@@ -125,7 +125,7 @@ do_trap(int trapnr, int signr, char *str, struct pt_regs *regs,
} }
#define DO_ERROR(trapnr, signr, str, name) \ #define DO_ERROR(trapnr, signr, str, name) \
asmlinkage void do_##name(struct pt_regs *regs, long error_code) \ dotraplinkage void do_##name(struct pt_regs *regs, long error_code) \
{ \ { \
if (notify_die(DIE_TRAP, str, regs, error_code, trapnr, signr) \ if (notify_die(DIE_TRAP, str, regs, error_code, trapnr, signr) \
== NOTIFY_STOP) \ == NOTIFY_STOP) \
...@@ -135,7 +135,7 @@ asmlinkage void do_##name(struct pt_regs *regs, long error_code) \ ...@@ -135,7 +135,7 @@ asmlinkage void do_##name(struct pt_regs *regs, long error_code) \
} }
#define DO_ERROR_INFO(trapnr, signr, str, name, sicode, siaddr) \ #define DO_ERROR_INFO(trapnr, signr, str, name, sicode, siaddr) \
asmlinkage void do_##name(struct pt_regs *regs, long error_code) \ dotraplinkage void do_##name(struct pt_regs *regs, long error_code) \
{ \ { \
siginfo_t info; \ siginfo_t info; \
info.si_signo = signr; \ info.si_signo = signr; \
...@@ -159,7 +159,7 @@ DO_ERROR(11, SIGBUS, "segment not present", segment_not_present) ...@@ -159,7 +159,7 @@ DO_ERROR(11, SIGBUS, "segment not present", segment_not_present)
DO_ERROR_INFO(17, SIGBUS, "alignment check", alignment_check, BUS_ADRALN, 0) DO_ERROR_INFO(17, SIGBUS, "alignment check", alignment_check, BUS_ADRALN, 0)
/* Runs on IST stack */ /* Runs on IST stack */
asmlinkage void do_stack_segment(struct pt_regs *regs, long error_code) dotraplinkage void do_stack_segment(struct pt_regs *regs, long error_code)
{ {
if (notify_die(DIE_TRAP, "stack segment", regs, error_code, if (notify_die(DIE_TRAP, "stack segment", regs, error_code,
12, SIGBUS) == NOTIFY_STOP) 12, SIGBUS) == NOTIFY_STOP)
...@@ -169,7 +169,7 @@ asmlinkage void do_stack_segment(struct pt_regs *regs, long error_code) ...@@ -169,7 +169,7 @@ asmlinkage void do_stack_segment(struct pt_regs *regs, long error_code)
preempt_conditional_cli(regs); preempt_conditional_cli(regs);
} }
asmlinkage void do_double_fault(struct pt_regs *regs, long error_code) dotraplinkage void do_double_fault(struct pt_regs *regs, long error_code)
{ {
static const char str[] = "double fault"; static const char str[] = "double fault";
struct task_struct *tsk = current; struct task_struct *tsk = current;
...@@ -186,7 +186,7 @@ asmlinkage void do_double_fault(struct pt_regs *regs, long error_code) ...@@ -186,7 +186,7 @@ asmlinkage void do_double_fault(struct pt_regs *regs, long error_code)
die(str, regs, error_code); die(str, regs, error_code);
} }
asmlinkage void __kprobes dotraplinkage void __kprobes
do_general_protection(struct pt_regs *regs, long error_code) do_general_protection(struct pt_regs *regs, long error_code)
{ {
struct task_struct *tsk; struct task_struct *tsk;
...@@ -317,7 +317,7 @@ asmlinkage notrace __kprobes void default_do_nmi(struct pt_regs *regs) ...@@ -317,7 +317,7 @@ asmlinkage notrace __kprobes void default_do_nmi(struct pt_regs *regs)
io_check_error(reason, regs); io_check_error(reason, regs);
} }
asmlinkage notrace __kprobes void dotraplinkage notrace __kprobes void
do_nmi(struct pt_regs *regs, long error_code) do_nmi(struct pt_regs *regs, long error_code)
{ {
nmi_enter(); nmi_enter();
...@@ -343,7 +343,7 @@ void restart_nmi(void) ...@@ -343,7 +343,7 @@ void restart_nmi(void)
} }
/* runs on IST stack. */ /* runs on IST stack. */
asmlinkage void __kprobes do_int3(struct pt_regs *regs, long error_code) dotraplinkage void __kprobes do_int3(struct pt_regs *regs, long error_code)
{ {
if (notify_die(DIE_INT3, "int3", regs, error_code, 3, SIGTRAP) if (notify_die(DIE_INT3, "int3", regs, error_code, 3, SIGTRAP)
== NOTIFY_STOP) == NOTIFY_STOP)
...@@ -376,8 +376,7 @@ asmlinkage __kprobes struct pt_regs *sync_regs(struct pt_regs *eregs) ...@@ -376,8 +376,7 @@ asmlinkage __kprobes struct pt_regs *sync_regs(struct pt_regs *eregs)
} }
/* runs on IST stack. */ /* runs on IST stack. */
asmlinkage void __kprobes do_debug(struct pt_regs *regs, dotraplinkage void __kprobes do_debug(struct pt_regs *regs, long error_code)
unsigned long error_code)
{ {
struct task_struct *tsk = current; struct task_struct *tsk = current;
unsigned long condition; unsigned long condition;
...@@ -510,7 +509,7 @@ void math_error(void __user *ip) ...@@ -510,7 +509,7 @@ void math_error(void __user *ip)
force_sig_info(SIGFPE, &info, task); force_sig_info(SIGFPE, &info, task);
} }
asmlinkage void do_coprocessor_error(struct pt_regs *regs, long error_code) dotraplinkage void do_coprocessor_error(struct pt_regs *regs, long error_code)
{ {
conditional_sti(regs); conditional_sti(regs);
if (!user_mode(regs) && if (!user_mode(regs) &&
...@@ -572,7 +571,8 @@ static void simd_math_error(void __user *ip) ...@@ -572,7 +571,8 @@ static void simd_math_error(void __user *ip)
force_sig_info(SIGFPE, &info, task); force_sig_info(SIGFPE, &info, task);
} }
asmlinkage void do_simd_coprocessor_error(struct pt_regs *regs, long error_code) dotraplinkage void
do_simd_coprocessor_error(struct pt_regs *regs, long error_code)
{ {
conditional_sti(regs); conditional_sti(regs);
if (!user_mode(regs) && if (!user_mode(regs) &&
...@@ -581,7 +581,8 @@ asmlinkage void do_simd_coprocessor_error(struct pt_regs *regs, long error_code) ...@@ -581,7 +581,8 @@ asmlinkage void do_simd_coprocessor_error(struct pt_regs *regs, long error_code)
simd_math_error((void __user *)regs->ip); simd_math_error((void __user *)regs->ip);
} }
asmlinkage void do_spurious_interrupt_bug(struct pt_regs *regs, long error_code) dotraplinkage void
do_spurious_interrupt_bug(struct pt_regs *regs, long error_code)
{ {
} }
...@@ -633,6 +634,12 @@ asmlinkage void math_state_restore(void) ...@@ -633,6 +634,12 @@ asmlinkage void math_state_restore(void)
} }
EXPORT_SYMBOL_GPL(math_state_restore); EXPORT_SYMBOL_GPL(math_state_restore);
dotraplinkage void __kprobes
do_device_not_available(struct pt_regs *regs, long error)
{
math_state_restore();
}
void __init trap_init(void) void __init trap_init(void)
{ {
set_intr_gate(0, &divide_error); set_intr_gate(0, &divide_error);
......
...@@ -3,7 +3,12 @@ ...@@ -3,7 +3,12 @@
#include <asm/debugreg.h> #include <asm/debugreg.h>
/* Common in X86_32 and X86_64 */ #ifdef CONFIG_X86_32
#define dotraplinkage
#else
#define dotraplinkage asmlinkage
#endif
asmlinkage void divide_error(void); asmlinkage void divide_error(void);
asmlinkage void debug(void); asmlinkage void debug(void);
asmlinkage void nmi(void); asmlinkage void nmi(void);
...@@ -12,31 +17,47 @@ asmlinkage void overflow(void); ...@@ -12,31 +17,47 @@ asmlinkage void overflow(void);
asmlinkage void bounds(void); asmlinkage void bounds(void);
asmlinkage void invalid_op(void); asmlinkage void invalid_op(void);
asmlinkage void device_not_available(void); asmlinkage void device_not_available(void);
#ifdef CONFIG_X86_64
asmlinkage void double_fault(void);
#endif
asmlinkage void coprocessor_segment_overrun(void); asmlinkage void coprocessor_segment_overrun(void);
asmlinkage void invalid_TSS(void); asmlinkage void invalid_TSS(void);
asmlinkage void segment_not_present(void); asmlinkage void segment_not_present(void);
asmlinkage void stack_segment(void); asmlinkage void stack_segment(void);
asmlinkage void general_protection(void); asmlinkage void general_protection(void);
asmlinkage void page_fault(void); asmlinkage void page_fault(void);
asmlinkage void spurious_interrupt_bug(void);
asmlinkage void coprocessor_error(void); asmlinkage void coprocessor_error(void);
asmlinkage void simd_coprocessor_error(void);
asmlinkage void alignment_check(void); asmlinkage void alignment_check(void);
asmlinkage void spurious_interrupt_bug(void);
#ifdef CONFIG_X86_MCE #ifdef CONFIG_X86_MCE
asmlinkage void machine_check(void); asmlinkage void machine_check(void);
#endif /* CONFIG_X86_MCE */ #endif /* CONFIG_X86_MCE */
asmlinkage void simd_coprocessor_error(void);
void do_divide_error(struct pt_regs *, long); dotraplinkage void do_divide_error(struct pt_regs *, long);
void do_overflow(struct pt_regs *, long); dotraplinkage void do_debug(struct pt_regs *, long);
void do_bounds(struct pt_regs *, long); dotraplinkage void do_nmi(struct pt_regs *, long);
void do_coprocessor_segment_overrun(struct pt_regs *, long); dotraplinkage void do_int3(struct pt_regs *, long);
void do_invalid_TSS(struct pt_regs *, long); dotraplinkage void do_overflow(struct pt_regs *, long);
void do_segment_not_present(struct pt_regs *, long); dotraplinkage void do_bounds(struct pt_regs *, long);
void do_stack_segment(struct pt_regs *, long); dotraplinkage void do_invalid_op(struct pt_regs *, long);
void do_alignment_check(struct pt_regs *, long); dotraplinkage void do_device_not_available(struct pt_regs *, long);
void do_invalid_op(struct pt_regs *, long); dotraplinkage void do_coprocessor_segment_overrun(struct pt_regs *, long);
void do_general_protection(struct pt_regs *, long); dotraplinkage void do_invalid_TSS(struct pt_regs *, long);
void do_nmi(struct pt_regs *, long); dotraplinkage void do_segment_not_present(struct pt_regs *, long);
dotraplinkage void do_stack_segment(struct pt_regs *, long);
dotraplinkage void do_general_protection(struct pt_regs *, long);
dotraplinkage void do_page_fault(struct pt_regs *, unsigned long);
dotraplinkage void do_spurious_interrupt_bug(struct pt_regs *, long);
dotraplinkage void do_coprocessor_error(struct pt_regs *, long);
dotraplinkage void do_alignment_check(struct pt_regs *, long);
#ifdef CONFIG_X86_MCE
dotraplinkage void do_machine_check(struct pt_regs *, long);
#endif
dotraplinkage void do_simd_coprocessor_error(struct pt_regs *, long);
#ifdef CONFIG_X86_32
dotraplinkage void do_iret_error(struct pt_regs *, long);
#endif
static inline int get_si_code(unsigned long condition) static inline int get_si_code(unsigned long condition)
{ {
...@@ -52,31 +73,9 @@ extern int panic_on_unrecovered_nmi; ...@@ -52,31 +73,9 @@ extern int panic_on_unrecovered_nmi;
extern int kstack_depth_to_print; extern int kstack_depth_to_print;
#ifdef CONFIG_X86_32 #ifdef CONFIG_X86_32
void do_iret_error(struct pt_regs *, long);
void do_int3(struct pt_regs *, long);
void do_debug(struct pt_regs *, long);
void math_error(void __user *); void math_error(void __user *);
void do_coprocessor_error(struct pt_regs *, long);
void do_simd_coprocessor_error(struct pt_regs *, long);
void do_spurious_interrupt_bug(struct pt_regs *, long);
unsigned long patch_espfix_desc(unsigned long, unsigned long); unsigned long patch_espfix_desc(unsigned long, unsigned long);
asmlinkage void math_emulate(long); asmlinkage void math_emulate(long);
#endif
void do_page_fault(struct pt_regs *regs, unsigned long error_code);
#else /* CONFIG_X86_32 */
asmlinkage void double_fault(void);
asmlinkage void do_int3(struct pt_regs *, long);
asmlinkage void do_stack_segment(struct pt_regs *, long);
asmlinkage void do_debug(struct pt_regs *, unsigned long);
asmlinkage void do_coprocessor_error(struct pt_regs *, long);
asmlinkage void do_simd_coprocessor_error(struct pt_regs *, long);
asmlinkage void do_spurious_interrupt_bug(struct pt_regs *, long);
asmlinkage void do_page_fault(struct pt_regs *regs, unsigned long error_code);
#endif /* CONFIG_X86_32 */
#endif /* ASM_X86__TRAPS_H */ #endif /* ASM_X86__TRAPS_H */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment