VirtualBox

Changeset 10630

Show
Ignore:
Timestamp:
07/15/08 11:06:33 (4 months ago)
Author:
vboxsync
Message:

Newer functions for handling fpu save/restore in ring 0.

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/include/VBox/cpum.h

    r10353 r10630  
    10451045CPUMR0DECL(int) CPUMR0Init(PVM pVM); 
    10461046 
     1047/** 
     1048 * Lazily sync in the FPU/XMM state 
     1049 * 
     1050 * @returns VBox status code. 
     1051 * @param   pVM         VM handle. 
     1052 * @param   pCtx        CPU context 
     1053 */ 
     1054CPUMR0DECL(int) CPUMR0LoadGuestFPU(PVM pVM, PCPUMCTX pCtx); 
     1055 
     1056/** 
     1057 * Save guest FPU/XMM state 
     1058 * 
     1059 * @returns VBox status code. 
     1060 * @param   pVM         VM handle. 
     1061 * @param   pCtx        CPU context 
     1062 */ 
     1063CPUMR0DECL(int) CPUMR0SaveGuestFPU(PVM pVM, PCPUMCTX pCtx); 
     1064 
    10471065/** @} */ 
    10481066#endif 
  • trunk/src/VBox/VMM/CPUMInternal.h

    r10569 r10630  
    358358__BEGIN_DECLS 
    359359 
    360 DECLASM(int) CPUMHandleLazyFPUAsm(PCPUM pCPUM); 
    361 DECLASM(int) CPUMRestoreHostFPUStateAsm(PCPUM pCPUM); 
     360DECLASM(int)  CPUMHandleLazyFPUAsm(PCPUM pCPUM); 
     361DECLASM(int)  CPUMRestoreHostFPUStateAsm(PCPUM pCPUM); 
     362DECLASM(void) CPUMLoadFPUAsm(PCPUMCTX pCtx); 
     363DECLASM(void) CPUMSaveFPUAsm(PCPUMCTX pCtx); 
    362364 
    363365__END_DECLS 
  • trunk/src/VBox/VMM/VMMAll/CPUMAllA.asm

    r8155 r10630  
    245245ENDPROC   CPUMRestoreHostFPUStateAsm 
    246246 
     247 
     248;; 
     249; Restores the guest's FPU/XMM state 
     250; 
     251; @returns  0 
     252; @param    pCtx  x86:[esp+4] GCC:rdi MSC:rcx     CPUMCTX pointer 
     253; 
     254align 16 
     255BEGINPROC   CPUMLoadFPUAsm 
     256%ifdef RT_ARCH_AMD64 
     257 %ifdef RT_OS_WINDOWS 
     258    mov     xDX, rcx 
     259 %else 
     260    mov     xDX, rdi 
     261 %endif 
     262%else 
     263    mov     xDX, dword [esp + 4] 
     264%endif 
     265    fxrstor [xDX + CPUMCTX.fpu] 
     266    ret 
     267ENDPROC     CPUMLoadFPUAsm 
     268 
     269;; 
     270; Restores the host's FPU/XMM state 
     271; 
     272; @returns  0 
     273; @param    pCtx  x86:[esp+4] GCC:rdi MSC:rcx     CPUMCTX pointer 
     274; 
     275align 16 
     276BEGINPROC   CPUMSaveFPUAsm 
     277%ifdef RT_ARCH_AMD64 
     278 %ifdef RT_OS_WINDOWS 
     279    mov     xDX, rcx 
     280 %else 
     281    mov     xDX, rdi 
     282 %endif 
     283%else 
     284    mov     xDX, dword [esp + 4] 
     285%endif 
     286    fxsave  [xDX + CPUMCTX.fpu] 
     287    ret 
     288ENDPROC CPUMSaveFPUAsm 
  • trunk/src/VBox/VMM/VMMR0/CPUMR0.cpp

    r8155 r10630  
    109109 
    110110 
     111/** 
     112 * Lazily sync in the FPU/XMM state 
     113 * 
     114 * @returns VBox status code. 
     115 * @param   pVM         VM handle. 
     116 * @param   pCtx        CPU context 
     117 */ 
     118CPUMR0DECL(int) CPUMR0LoadGuestFPU(PVM pVM, PCPUMCTX pCtx) 
     119{ 
     120    Assert(pVM->cpum.s.CPUFeatures.edx.u1FXSR); 
     121 
     122    /* If the FPU state has already been loaded, then it's a guest trap. */ 
     123    if (pVM->cpum.s.fUseFlags & CPUM_USED_FPU) 
     124    { 
     125        Assert(    ((pCtx->cr0 & (X86_CR0_MP | X86_CR0_EM | X86_CR0_TS)) == (X86_CR0_MP | X86_CR0_EM | X86_CR0_TS)) 
     126               ||  ((pCtx->cr0 & (X86_CR0_MP | X86_CR0_EM | X86_CR0_TS)) == (X86_CR0_MP | X86_CR0_TS))); 
     127        return VINF_EM_RAW_GUEST_TRAP; 
     128    } 
     129 
     130    /* 
     131     * There are two basic actions: 
     132     *   1. Save host fpu and restore guest fpu. 
     133     *   2. Generate guest trap. 
     134     * 
     135     * When entering the hypervisor we'll always enable MP (for proper wait 
     136     * trapping) and TS (for intercepting all fpu/mmx/sse stuff). The EM flag 
     137     * is taken from the guest OS in order to get proper SSE handling. 
     138     * 
     139     * 
     140     * Actions taken depending on the guest CR0 flags: 
     141     * 
     142     *   3    2    1 
     143     *  TS | EM | MP | FPUInstr | WAIT :: VMM Action 
     144     * ------------------------------------------------------------------------ 
     145     *   0 |  0 |  0 | Exec     | Exec :: Clear TS & MP, Save HC, Load GC. 
     146     *   0 |  0 |  1 | Exec     | Exec :: Clear TS, Save HC, Load GC. 
     147     *   0 |  1 |  0 | #NM      | Exec :: Clear TS & MP, Save HC, Load GC. 
     148     *   0 |  1 |  1 | #NM      | Exec :: Clear TS, Save HC, Load GC. 
     149     *   1 |  0 |  0 | #NM      | Exec :: Clear MP, Save HC, Load GC. (EM is already cleared.) 
     150     *   1 |  0 |  1 | #NM      | #NM  :: Go to guest taking trap there. 
     151     *   1 |  1 |  0 | #NM      | Exec :: Clear MP, Save HC, Load GC. (EM is already set.) 
     152     *   1 |  1 |  1 | #NM      | #NM  :: Go to guest taking trap there. 
     153     */ 
     154 
     155    switch(pCtx->cr0 & (X86_CR0_MP | X86_CR0_EM | X86_CR0_TS)) 
     156    { 
     157    case X86_CR0_MP | X86_CR0_TS: 
     158    case X86_CR0_MP | X86_CR0_EM | X86_CR0_TS: 
     159        return VINF_EM_RAW_GUEST_TRAP; 
     160 
     161    default: 
     162        break; 
     163    } 
     164    CPUMLoadFPUAsm(pCtx); 
     165    pVM->cpum.s.fUseFlags |= CPUM_USED_FPU; 
     166    return VINF_SUCCESS; 
     167} 
     168 
     169 
     170/** 
     171 * Save guest FPU/XMM state 
     172 * 
     173 * @returns VBox status code. 
     174 * @param   pVM         VM handle. 
     175 * @param   pCtx        CPU context 
     176 */ 
     177CPUMR0DECL(int) CPUMR0SaveGuestFPU(PVM pVM, PCPUMCTX pCtx) 
     178{ 
     179    Assert(pVM->cpum.s.CPUFeatures.edx.u1FXSR); 
     180    AssertReturn((pVM->cpum.s.fUseFlags & CPUM_USED_FPU), VINF_SUCCESS); 
     181 
     182    CPUMSaveFPUAsm(pCtx); 
     183    pVM->cpum.s.fUseFlags &= ~CPUM_USED_FPU; 
     184    return VINF_SUCCESS; 
     185} 

© 2008 Sun Microsystems, Inc.
ContactPrivacy policy