[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [PATCH 2/6] x86/xsaves: enable xsaves/xrstors in xen
This patch uses xsaves/xrstors instead of xsaveopt/xrstor when perform task switch in xen if the feature is supported in hardware. Please note that xsaves/xrstors only use compact format. Signed-off-by: Shuai Ruan <shuai.ruan@xxxxxxxxx> --- xen/arch/x86/xstate.c | 83 ++++++++++++++++++++++++++++---------------- xen/include/asm-x86/xstate.h | 3 +- 2 files changed, 55 insertions(+), 31 deletions(-) diff --git a/xen/arch/x86/xstate.c b/xen/arch/x86/xstate.c index e34eda3..ff67986 100644 --- a/xen/arch/x86/xstate.c +++ b/xen/arch/x86/xstate.c @@ -14,6 +14,7 @@ #include <asm/xstate.h> #include <asm/asm_defns.h> +#define XSTATE_COMPACTION_ENABLED (1ULL << 63) static bool_t __read_mostly cpu_has_xsaveopt; static bool_t __read_mostly cpu_has_xsavec; bool_t __read_mostly cpu_has_xgetbv1; @@ -102,7 +103,9 @@ void xsave(struct vcpu *v, uint64_t mask) typeof(ptr->fpu_sse.fip.sel) fcs = ptr->fpu_sse.fip.sel; typeof(ptr->fpu_sse.fdp.sel) fds = ptr->fpu_sse.fdp.sel; - if ( cpu_has_xsaveopt ) + if ( cpu_has_xsaves ) + xsaves(lmask, hmask, ptr); + else if ( cpu_has_xsaveopt ) { /* * xsaveopt may not write the FPU portion even when the respective @@ -155,7 +158,9 @@ void xsave(struct vcpu *v, uint64_t mask) } else { - if ( cpu_has_xsaveopt ) + if ( cpu_has_xsaves ) + xsaves(lmask, hmask, ptr); + else if ( cpu_has_xsaveopt ) asm volatile ( ".byte 0x0f,0xae,0x37" : "=m" (*ptr) : "a" (lmask), "d" (hmask), "D" (ptr) ); @@ -198,36 +203,54 @@ void xrstor(struct vcpu *v, uint64_t mask) switch ( __builtin_expect(ptr->fpu_sse.x[FPU_WORD_SIZE_OFFSET], 8) ) { default: - asm volatile ( "1: .byte 0x48,0x0f,0xae,0x2f\n" - ".section .fixup,\"ax\" \n" - "2: mov %5,%%ecx \n" - " xor %1,%1 \n" - " rep stosb \n" - " lea %2,%0 \n" - " mov %3,%1 \n" - " jmp 1b \n" - ".previous \n" - _ASM_EXTABLE(1b, 2b) - : "+&D" (ptr), "+&a" (lmask) - : "m" (*ptr), "g" (lmask), "d" (hmask), - "m" (xsave_cntxt_size) - : "ecx" ); + if ( cpu_has_xsaves ) + { + if ( !(v->arch.xsave_area->xsave_hdr.xcomp_bv & + XSTATE_COMPACTION_ENABLED) ) + v->arch.xsave_area->xsave_hdr.xcomp_bv = get_xcr0() | + XSTATE_COMPACTION_ENABLED; + xrstors(lmask, hmask, ptr); + } + else + asm volatile ( "1: .byte 0x48,0x0f,0xae,0x2f\n" + ".section .fixup,\"ax\" \n" + "2: mov %5,%%ecx \n" + " xor %1,%1 \n" + " rep stosb \n" + " lea %2,%0 \n" + " mov %3,%1 \n" + " jmp 1b \n" + ".previous \n" + _ASM_EXTABLE(1b, 2b) + : "+&D" (ptr), "+&a" (lmask) + : "m" (*ptr), "g" (lmask), "d" (hmask), + "m" (xsave_cntxt_size) + : "ecx" ); break; case 4: case 2: - asm volatile ( "1: .byte 0x0f,0xae,0x2f\n" - ".section .fixup,\"ax\" \n" - "2: mov %5,%%ecx \n" - " xor %1,%1 \n" - " rep stosb \n" - " lea %2,%0 \n" - " mov %3,%1 \n" - " jmp 1b \n" - ".previous \n" - _ASM_EXTABLE(1b, 2b) - : "+&D" (ptr), "+&a" (lmask) - : "m" (*ptr), "g" (lmask), "d" (hmask), - "m" (xsave_cntxt_size) - : "ecx" ); + if ( cpu_has_xsaves ) + { + if ( !(v->arch.xsave_area->xsave_hdr.xcomp_bv & + XSTATE_COMPACTION_ENABLED) ) + v->arch.xsave_area->xsave_hdr.xcomp_bv = get_xcr0() | + XSTATE_COMPACTION_ENABLED; + xrstors(lmask, hmask, ptr); + } + else + asm volatile ( "1: .byte 0x48,0x0f,0xae,0x2f\n" + ".section .fixup,\"ax\" \n" + "2: mov %5,%%ecx \n" + " xor %1,%1 \n" + " rep stosb \n" + " lea %2,%0 \n" + " mov %3,%1 \n" + " jmp 1b \n" + ".previous \n" + _ASM_EXTABLE(1b, 2b) + : "+&D" (ptr), "+&a" (lmask) + : "m" (*ptr), "g" (lmask), "d" (hmask), + "m" (xsave_cntxt_size) + : "ecx" ); break; } } diff --git a/xen/include/asm-x86/xstate.h b/xen/include/asm-x86/xstate.h index 59c7156..d03d824 100644 --- a/xen/include/asm-x86/xstate.h +++ b/xen/include/asm-x86/xstate.h @@ -72,7 +72,8 @@ struct __packed __attribute__((aligned (64))) xsave_struct struct { u64 xstate_bv; - u64 reserved[7]; + u64 xcomp_bv; + u64 reserved[6]; } xsave_hdr; /* The 64-byte header */ struct { char x[XSTATE_YMM_SIZE]; } ymm; /* YMM */ -- 1.9.1 _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxx http://lists.xen.org/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |