]> xenbits.xensource.com Git - xen.git/commitdiff
x86/EFI: further correct FPU state handling around runtime calls
authorJan Beulich <jbeulich@suse.com>
Thu, 28 Jun 2018 10:27:56 +0000 (12:27 +0200)
committerJan Beulich <jbeulich@suse.com>
Thu, 28 Jun 2018 10:27:56 +0000 (12:27 +0200)
We must not leave a vCPU with CR0.TS clear when it is not in fully eager
mode and has not touched non-lazy state. Instead of adding a 3rd
invocation of stts() to vcpu_restore_fpu_eager(), consolidate all of
them into a single one done at the end of the function.

Rename the function at the same time to better reflect its purpose, as
the patches touches all of its occurences anyway.

The new function parameter is not really well named, but
"need_stts_if_not_fully_eager" seemed excessive to me.

Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Paul Durrant <paul.durrant@citrix.com>
xen/arch/x86/domain.c
xen/arch/x86/i387.c
xen/common/efi/runtime.c
xen/include/asm-x86/i387.h

index 0eb377a2f288258751194603ed7e7226e02da770..2b798bb1d0fe852f9c0013c2586fbe9f5f92f467 100644 (file)
@@ -1703,7 +1703,7 @@ static void __context_switch(void)
             if ( xcr0 != get_xcr0() && !set_xcr0(xcr0) )
                 BUG();
         }
-        vcpu_restore_fpu_eager(n);
+        vcpu_restore_fpu_nonlazy(n, 0);
         n->arch.ctxt_switch_to(n);
     }
 
index 28edfce67f941c46bf8129effa42976d8118ec74..e2f5cca4409cda552bee3ebfb1a49c830996d26d 100644 (file)
@@ -212,7 +212,7 @@ static inline void fpu_fsave(struct vcpu *v)
 /*       VCPU FPU Functions    */
 /*******************************/
 /* Restore FPU state whenever VCPU is schduled in. */
-void vcpu_restore_fpu_eager(struct vcpu *v)
+void vcpu_restore_fpu_nonlazy(struct vcpu *v, bool_t need_stts)
 {
     if ( v->arch.fully_eager_fpu )
     {
@@ -230,8 +230,7 @@ void vcpu_restore_fpu_eager(struct vcpu *v)
         v->fpu_dirtied = 1;
 
         /* Xen doesn't need TS set, but the guest might. */
-        if ( is_pv_vcpu(v) && (v->arch.pv_vcpu.ctrlreg[0] & X86_CR0_TS) )
-            stts();
+        need_stts = is_pv_vcpu(v) && (v->arch.pv_vcpu.ctrlreg[0] & X86_CR0_TS);
     }
     /* save the nonlazy extended state which is not tracked by CR0.TS bit */
     else if ( v->arch.nonlazy_xstate_used )
@@ -241,8 +240,11 @@ void vcpu_restore_fpu_eager(struct vcpu *v)
         /* Avoid recursion */
         clts();        
         fpu_xrstor(v, XSTATE_NONLAZY);
-        stts();
+        need_stts = 1;
     }
+
+    if ( need_stts )
+        stts();
 }
 
 /* 
index 309b13a70fde22e7649e43279ccd695e555cd3a6..75f119315a09b10e236b0064d5588163caf44cfa 100644 (file)
@@ -128,7 +128,7 @@ void efi_rs_leave(struct efi_rs_state *state)
     irq_exit();
     efi_rs_on_cpu = NR_CPUS;
     spin_unlock(&efi_rs_lock);
-    vcpu_restore_fpu_eager(curr);
+    vcpu_restore_fpu_nonlazy(curr, 1);
 }
 
 bool_t efi_rs_using_pgtables(void)
index 150a09e41f150ccf5509dd972af967122515e06f..64e277e656037300f89da5a9c78e8acbc2f8eea2 100644 (file)
@@ -35,7 +35,7 @@ struct ix87_state {
     } r[8];
 };
 
-void vcpu_restore_fpu_eager(struct vcpu *v);
+void vcpu_restore_fpu_nonlazy(struct vcpu *v, bool_t need_stts);
 void vcpu_restore_fpu_lazy(struct vcpu *v);
 void vcpu_save_fpu(struct vcpu *v);
 void save_fpu_enable(void);