2 * This file is part of the Palacios Virtual Machine Monitor developed
3 * by the V3VEE Project with funding from the United States National
4 * Science Foundation and the Department of Energy.
6 * The V3VEE Project is a joint project between Northwestern University
7 * and the University of New Mexico. You can find out more at
10 * Copyright (c) 2013, Peter Dinda <pdinda@northwestern.edu>
11 * Copyright (c) 2013, The V3VEE Project <http://www.v3vee.org>
12 * All rights reserved.
14 * Author: Peter Dinda <pdinda@northwestern.edu>
16 * This is free software. You are permitted to use,
17 * redistribute, and modify it as specified in the file "V3VEE_LICENSE".
20 #include <palacios/vmm.h>
21 #include <palacios/vmm_fp.h>
22 #include <palacios/vm_guest.h>
23 #include <palacios/vmm_lowlevel.h>
25 #ifdef V3_CONFIG_CHECKPOINT
26 #include <palacios/vmm_checkpoint.h>
30 static int can_do_fp=-1;
32 // assumes identical on all cores...
33 int v3_can_handle_fp_state()
38 uint32_t eax=0, ebx=0, ecx=0, edx=0;
40 v3_cpuid(CPUID_FEATURE_IDS,&eax,&ebx,&ecx,&edx);
42 can_do_fp= !!(edx & (1<<25)); // do we have SSE?
50 if (v3_can_handle_fp_state()) {
51 V3_Print(VM_NONE,VCORE_NONE,"Floating point save/restore init: available on this hardware\n");
53 V3_Print(VM_NONE,VCORE_NONE,"Floating point save/restore init: UNAVAILABLE ON THIS HARDWARE\n");
60 V3_Print(VM_NONE,VCORE_NONE,"Floating point save/restore deinited\n");
64 #define EFER_MSR 0xc0000080
67 int v3_get_fp_state(struct guest_info *core)
69 if (v3_can_handle_fp_state()) {
71 If the fast-FXSAVE/FXRSTOR (FFXSR) feature is enabled in EFER, FXSAVE and FXRSTOR do not save or restore the XMM0–15 registers when executed in 64-bit mode at CPL 0. The x87 environment and MXCSR are saved whether fast-FXSAVE/FXRSTOR is enabled or not. Software can use the CPUID instruction to determine whether the fast-FXSAVE/FXRSTOR feature is available
72 (CPUID Fn8000_0001h_EDX[FFXSR]). The fast-FXSAVE/FXRSTOR feature has no effect on FXSAVE/FXRSTOR in non 64-bit mode or when CPL > 0.
76 // We need to assure that the fast-FXSAVE/FXRSTOR are not on
77 // otherwise we will NOT have the XMM regs since we running at CPL 0
83 v3_get_msr(EFER_MSR,&high,&low);
85 if (low & (0x1<<14)) {
86 // fast save is in effect
89 v3_set_msr(EFER_MSR, high, low);
92 __asm__ __volatile__(" rex64/fxsave %0 ; "
93 : "=m"(core->fp_state.state)); /* no input, no clobber */
96 v3_set_msr(EFER_MSR, high, low);
99 // this is a giant guess
100 // we really need to capture the state type as seen in the guest, not here...
101 core->fp_state.state_type=V3_FP_MODE_64;
111 // Restore FP state from this structure to this core
112 int v3_put_fp_state(struct guest_info *core)
114 if (v3_can_handle_fp_state()) {
115 // We need to assure that the fast-FXSAVE/FXRSTOR are not on
116 // otherwise we will NOT have the XMM regs since we running at CPL 0
122 v3_get_msr(EFER_MSR,&high,&low);
124 if (low & (0x1<<14)) {
125 // fast restore is in effect
128 v3_set_msr(EFER_MSR, high, low);
131 __asm__ __volatile__(" rex64/fxrstor %0; "
133 : "m"((core->fp_state.state)) ); /* no clobber*/
138 v3_set_msr(EFER_MSR, high, low);
147 #ifdef V3_CONFIG_CHECKPOINT
150 int v3_save_fp_state(struct v3_chkpt_ctx *ctx, struct guest_info *core)
152 V3_CHKPT_SAVE(ctx, "FP_STATE_TYPE", core->fp_state.state_type, savefailout);
153 if (v3_chkpt_save(ctx,"FP_STATE_BLOB",sizeof(core->fp_state.state),&(core->fp_state.state))) {
160 PrintError(core->vm_info,core,"Unable to save floating point state\n");
165 int v3_load_fp_state(struct v3_chkpt_ctx *ctx, struct guest_info *core)
167 V3_CHKPT_LOAD(ctx, "FP_STATE_TYPE", core->fp_state.state_type, loadfailout);
168 if (v3_chkpt_load(ctx,"FP_STATE_BLOB",sizeof(core->fp_state.state),&(core->fp_state.state))) {
175 PrintError(core->vm_info,core,"Unable to load floating point state\n");