From: Nadav Amit <namit@xxxxxxxxxx> Add a "mask" field to vDSO exception tables that says which exceptions should be handled. Add a "flags" field to vDSO as well to provide additional information about the exception. The existing preprocessor macro _ASM_VDSO_EXTABLE_HANDLE for assembly is not easy to use as it requires the user to stringify the expanded C macro. Remove _ASM_VDSO_EXTABLE_HANDLE and use a similar scheme to ALTERNATIVE, using assembly macros directly in assembly without wrapping them in C macros. Move the vsgx supported exceptions test out of the generic C code into vsgx-specific assembly by setting vsgx supported exceptions in the mask. Cc: Andy Lutomirski <luto@xxxxxxxxxx> Cc: Peter Zijlstra <peterz@xxxxxxxxxxxxx> Cc: Sean Christopherson <seanjc@xxxxxxxxxx> Cc: Thomas Gleixner <tglx@xxxxxxxxxxxxx> Cc: Ingo Molnar <mingo@xxxxxxxxxx> Cc: Borislav Petkov <bp@xxxxxxxxx> Cc: Andrew Morton <akpm@xxxxxxxxxxxxxxxxxxxx> Cc: x86@xxxxxxxxxx Signed-off-by: Nadav Amit <namit@xxxxxxxxxx> --- arch/x86/entry/vdso/extable.c | 9 +-------- arch/x86/entry/vdso/extable.h | 21 +++++++++++++-------- arch/x86/entry/vdso/vsgx.S | 9 +++++++-- 3 files changed, 21 insertions(+), 18 deletions(-) diff --git a/arch/x86/entry/vdso/extable.c b/arch/x86/entry/vdso/extable.c index c81e78636220..93fb37bd32ad 100644 --- a/arch/x86/entry/vdso/extable.c +++ b/arch/x86/entry/vdso/extable.c @@ -7,6 +7,7 @@ struct vdso_exception_table_entry { int insn, fixup; + unsigned int mask, flags; }; bool fixup_vdso_exception(struct pt_regs *regs, int trapnr, @@ -17,14 +18,6 @@ bool fixup_vdso_exception(struct pt_regs *regs, int trapnr, unsigned int nr_entries, i; unsigned long base; - /* - * Do not attempt to fixup #DB or #BP. It's impossible to identify - * whether or not a #DB/#BP originated from within an SGX enclave and - * SGX enclaves are currently the only use case for vDSO fixup. - */ - if (trapnr == X86_TRAP_DB || trapnr == X86_TRAP_BP) - return false; - if (!current->mm->context.vdso) return false; diff --git a/arch/x86/entry/vdso/extable.h b/arch/x86/entry/vdso/extable.h index b56f6b012941..7ca8a0776805 100644 --- a/arch/x86/entry/vdso/extable.h +++ b/arch/x86/entry/vdso/extable.h @@ -2,26 +2,31 @@ #ifndef __VDSO_EXTABLE_H #define __VDSO_EXTABLE_H +#include <asm/trapnr.h> + +#define ASM_VDSO_ASYNC_FLAGS (1 << 0) + /* * Inject exception fixup for vDSO code. Unlike normal exception fixup, * vDSO uses a dedicated handler the addresses are relative to the overall * exception table, not each individual entry. */ #ifdef __ASSEMBLY__ -#define _ASM_VDSO_EXTABLE_HANDLE(from, to) \ - ASM_VDSO_EXTABLE_HANDLE from to - -.macro ASM_VDSO_EXTABLE_HANDLE from:req to:req +.macro ASM_VDSO_EXTABLE_HANDLE from:req to:req mask:req flags:req .pushsection __ex_table, "a" .long (\from) - __ex_table .long (\to) - __ex_table + .long (\mask) + .long (\flags) .popsection .endm #else -#define _ASM_VDSO_EXTABLE_HANDLE(from, to) \ - ".pushsection __ex_table, \"a\"\n" \ - ".long (" #from ") - __ex_table\n" \ - ".long (" #to ") - __ex_table\n" \ +#define ASM_VDSO_EXTABLE_HANDLE(from, to, mask, flags) \ + ".pushsection __ex_table, \"a\"\n" \ + ".long (" #from ") - __ex_table\n" \ + ".long (" #to ") - __ex_table\n" \ + ".long (" #mask ")\n" \ + ".long (" #flags ")\n" \ ".popsection\n" #endif diff --git a/arch/x86/entry/vdso/vsgx.S b/arch/x86/entry/vdso/vsgx.S index 86a0e94f68df..c588255af480 100644 --- a/arch/x86/entry/vdso/vsgx.S +++ b/arch/x86/entry/vdso/vsgx.S @@ -4,6 +4,7 @@ #include <asm/export.h> #include <asm/errno.h> #include <asm/enclu.h> +#include <asm/trapnr.h> #include "extable.h" @@ -146,6 +147,10 @@ SYM_FUNC_START(__vdso_sgx_enter_enclave) .cfi_endproc -_ASM_VDSO_EXTABLE_HANDLE(.Lenclu_eenter_eresume, .Lhandle_exception) - +/* + * Do not attempt to fixup #DB or #BP. It's impossible to identify + * whether or not a #DB/#BP originated from within an SGX enclave. + */ +ASM_VDSO_EXTABLE_HANDLE .Lenclu_eenter_eresume, .Lhandle_exception, \ + ~((1<<X86_TRAP_DB)+(1<<X86_TRAP_BP)), 0 SYM_FUNC_END(__vdso_sgx_enter_enclave) -- 2.25.1