From 67b5b302f5319f70288587dc98ab505c4deada1e Mon Sep 17 00:00:00 2001 From: Jan Beulich Date: Thu, 10 Nov 2016 09:06:30 -0700 Subject: [PATCH] x86/EFI: meet further spec requirements for runtime calls So far we didn't guarantee 16-byte alignment of the stack: While (so far) we don't tell the compiler to use smaller alignment, we also don't guarantee 16-byte alignment when establishing stack pointers for new vCPU-s. Runtime service functions using SSE instructions may end with Note that -mpreferred-stack-boundary=3 is can be used only from gcc 4.8 onwards, and -mincoming-stack-boundary=3 only from 5.3 onwards. It is for that reason that an alternative approach (using higher than necessary alignment) is being used when building with such older compilers. Furthermore we should avoid #MF to be raised on the FLDCW we do. Signed-off-by: Jan Beulich Acked-by: Andrew Cooper Acked-by: Wei Liu Release-acked-by: Wei Liu --- xen/arch/x86/efi/Makefile | 5 +++++ xen/common/efi/runtime.c | 16 +++++++++++++++- 2 files changed, 20 insertions(+), 1 deletion(-) diff --git a/xen/arch/x86/efi/Makefile b/xen/arch/x86/efi/Makefile index ad3fdf7ff7..7a743f8888 100644 --- a/xen/arch/x86/efi/Makefile +++ b/xen/arch/x86/efi/Makefile @@ -14,5 +14,10 @@ extra-$(efi) += boot.init.o relocs-dummy.o runtime.o compat.o buildid.o %.o: %.ihex $(OBJCOPY) -I ihex -O binary $< $@ +cc-runtime.o := $(CC) -mno-sse +$(call cc-option-add,cflags-runtime.o,cc-runtime.o,-mpreferred-stack-boundary=3) +$(call cc-option-add,cflags-runtime.o,cc-runtime.o,-mincoming-stack-boundary=3) +runtime.o: CFLAGS += $(cflags-runtime.o) + stub.o: $(extra-y) nogcov-$(efi) += stub.o diff --git a/xen/common/efi/runtime.c b/xen/common/efi/runtime.c index c256814967..926dae69d5 100644 --- a/xen/common/efi/runtime.c +++ b/xen/common/efi/runtime.c @@ -59,12 +59,26 @@ unsigned long efi_rs_enter(void) static const u16 fcw = FCW_DEFAULT; static const u32 mxcsr = MXCSR_DEFAULT; unsigned long cr3 = read_cr3(); +#if __GNUC__ < 5 || (__GNUC__ == 5 && __GNUC_MINOR__ < 3) +/* + * -mpreferred-stack-boundary=3 is can be used only from gcc 4.8 onwards, + * and -mincoming-stack-boundary=3 only from 5.3 onwards. Therefore higher + * than necessary alignment is being forced here in that case. + */ +# define FORCE_ALIGN 32 +#else +# define FORCE_ALIGN 16 +#endif + unsigned long __aligned(FORCE_ALIGN) placeholder[0]; +#undef FORCE_ALIGN + + asm volatile("" : "+m" (placeholder)); if ( !efi_l4_pgtable ) return 0; save_fpu_enable(); - asm volatile ( "fldcw %0" :: "m" (fcw) ); + asm volatile ( "fnclex; fldcw %0" :: "m" (fcw) ); asm volatile ( "ldmxcsr %0" :: "m" (mxcsr) ); spin_lock(&efi_rs_lock); -- 2.30.2