From: Jan Beulich Date: Tue, 29 Mar 2016 12:24:26 +0000 (+0200) Subject: x86: fix information leak on AMD CPUs X-Git-Tag: archive/raspbian/4.8.0-1+rpi1~1^2~1485 X-Git-Url: https://dgit.raspbian.org/?a=commitdiff_plain;h=7bd9dc3adfbb014c55f0928ebb3b20950ca9c019;p=xen.git x86: fix information leak on AMD CPUs The fix for XSA-52 was wrong, and so was the change synchronizing that new behavior to the FXRSTOR logic: AMD's manuals explictly state that writes to the ES bit are ignored, and it instead gets calculated from the exception and mask bits (it gets set whenever there is an unmasked exception, and cleared otherwise). Hence we need to follow that model in our workaround. This is CVE-2016-3158 / CVE-2016-3159 / XSA-172. [xen/arch/x86/xstate.c:xrstor: CVE-2016-3158] [xen/arch/x86/i387.c:fpu_fxrstor: CVE-2016-3159] Signed-off-by: Jan Beulich Reviewed-by: Andrew Cooper --- diff --git a/xen/arch/x86/i387.c b/xen/arch/x86/i387.c index c29d0fa7b5..1a3e2771bd 100644 --- a/xen/arch/x86/i387.c +++ b/xen/arch/x86/i387.c @@ -49,7 +49,7 @@ static inline void fpu_fxrstor(struct vcpu *v) * sometimes new user value. Both should be ok. Use the FPU saved * data block as a safe address because it should be in L1. */ - if ( !(fpu_ctxt->fsw & 0x0080) && + if ( !(fpu_ctxt->fsw & ~fpu_ctxt->fcw & 0x003f) && boot_cpu_data.x86_vendor == X86_VENDOR_AMD ) { asm volatile ( "fnclex\n\t" diff --git a/xen/arch/x86/xstate.c b/xen/arch/x86/xstate.c index f64940538e..78cbfbb745 100644 --- a/xen/arch/x86/xstate.c +++ b/xen/arch/x86/xstate.c @@ -333,7 +333,7 @@ void xrstor(struct vcpu *v, uint64_t mask) * data block as a safe address because it should be in L1. */ if ( (mask & ptr->xsave_hdr.xstate_bv & XSTATE_FP) && - !(ptr->fpu_sse.fsw & 0x0080) && + !(ptr->fpu_sse.fsw & ~ptr->fpu_sse.fcw & 0x003f) && boot_cpu_data.x86_vendor == X86_VENDOR_AMD ) asm volatile ( "fnclex\n\t" /* clear exceptions */ "ffree %%st(7)\n\t" /* clear stack tag */