diff options
-rw-r--r-- | xen/include/asm-x86/asm_defns.h | 24 | ||||
-rw-r--r-- | xen/include/asm-x86/hvm/vmx/vmx.h | 25 |
2 files changed, 43 insertions, 6 deletions
diff --git a/xen/include/asm-x86/asm_defns.h b/xen/include/asm-x86/asm_defns.h index 81d490559c..8fc1a2c4c5 100644 --- a/xen/include/asm-x86/asm_defns.h +++ b/xen/include/asm-x86/asm_defns.h @@ -67,6 +67,30 @@ void ret_from_intr(void); #define ASSERT_NOT_IN_ATOMIC #endif +#else + +#ifdef __clang__ /* clang's builtin assember can't do .subsection */ + +#define UNLIKELY_START_SECTION ".pushsection .fixup,\"ax\"" +#define UNLIKELY_END_SECTION ".popsection" + +#else + +#define UNLIKELY_START_SECTION ".subsection 1" +#define UNLIKELY_END_SECTION ".subsection 0" + +#endif + +#define UNLIKELY_START(cond, tag) \ + "j" #cond " .Lunlikely%=.tag;\n\t" \ + UNLIKELY_START_SECTION "\n" \ + ".Lunlikely%=.tag:" + +#define UNLIKELY_END(tag) \ + "jmp .Llikely%=.tag;\n\t" \ + UNLIKELY_END_SECTION "\n" \ + ".Llikely%=.tag:" + #endif #endif /* __X86_ASM_DEFNS_H__ */ diff --git a/xen/include/asm-x86/hvm/vmx/vmx.h b/xen/include/asm-x86/hvm/vmx/vmx.h index f4d759bd5a..a7b667e31e 100644 --- a/xen/include/asm-x86/hvm/vmx/vmx.h +++ b/xen/include/asm-x86/hvm/vmx/vmx.h @@ -285,7 +285,9 @@ static inline void __vmptrld(u64 addr) asm volatile ( VMPTRLD_OPCODE MODRM_EAX_06 /* CF==1 or ZF==1 --> crash (ud2) */ - "ja 1f ; ud2 ; 1:\n" + UNLIKELY_START(be, vmptrld) + "\tud2\n" + UNLIKELY_END_SECTION : : "a" (&addr) : "memory"); @@ -296,7 +298,9 @@ static inline void __vmpclear(u64 addr) asm volatile ( VMCLEAR_OPCODE MODRM_EAX_06 /* CF==1 or ZF==1 --> crash (ud2) */ - "ja 1f ; ud2 ; 1:\n" + UNLIKELY_START(be, vmclear) + "\tud2\n" + UNLIKELY_END_SECTION : : "a" (&addr) : "memory"); @@ -309,7 +313,9 @@ static inline unsigned long __vmread(unsigned long field) asm volatile ( VMREAD_OPCODE MODRM_EAX_ECX /* CF==1 or ZF==1 --> crash (ud2) */ - "ja 1f ; ud2 ; 1:\n" + UNLIKELY_START(be, vmread) + "\tud2\n" + UNLIKELY_END_SECTION : "=c" (ecx) : "a" (field) : "memory"); @@ -322,7 +328,9 @@ static inline void __vmwrite(unsigned long field, unsigned long value) asm volatile ( VMWRITE_OPCODE MODRM_EAX_ECX /* CF==1 or ZF==1 --> crash (ud2) */ - "ja 1f ; ud2 ; 1:\n" + UNLIKELY_START(be, vmwrite) + "\tud2\n" + UNLIKELY_END_SECTION : : "a" (field) , "c" (value) : "memory"); @@ -360,7 +368,9 @@ static inline void __invept(int type, u64 eptp, u64 gpa) asm volatile ( INVEPT_OPCODE MODRM_EAX_08 /* CF==1 or ZF==1 --> crash (ud2) */ - "ja 1f ; ud2 ; 1:\n" + UNLIKELY_START(be, invept) + "\tud2\n" + UNLIKELY_END_SECTION : : "a" (&operand), "c" (type) : "memory" ); @@ -377,7 +387,10 @@ static inline void __invvpid(int type, u16 vpid, u64 gva) /* Fix up #UD exceptions which occur when TLBs are flushed before VMXON. */ asm volatile ( "1: " INVVPID_OPCODE MODRM_EAX_08 /* CF==1 or ZF==1 --> crash (ud2) */ - "ja 2f ; ud2 ; 2:\n" + UNLIKELY_START(be, invvpid) + "\tud2\n" + UNLIKELY_END_SECTION "\n" + "2:" _ASM_EXTABLE(1b, 2b) : : "a" (&operand), "c" (type) |