VirtualBox

Changeset 10473 in vbox


Ignore:
Timestamp:
Jul 10, 2008 3:02:53 PM (17 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
33146
Message:

MMIO instruction emulation for OR, BT and XOR added.

Location:
trunk
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/include/VBox/em.h

    r9984 r10473  
    7878} EMSTATE;
    7979
     80/*
     81 * Callback handlers for instruction emulation functions.
     82 */
     83typedef DECLCALLBACK(uint32_t) PFN_EMULATE_PARAM2_UINT32(void *pvParam1, uint64_t val2);
     84typedef DECLCALLBACK(uint32_t) PFN_EMULATE_PARAM2(void *pvParam1, size_t val2);
     85typedef DECLCALLBACK(uint32_t) PFN_EMULATE_PARAM3(void *pvParam1, uint64_t val2, size_t val3);
     86typedef DECLCALLBACK(int)      FNEMULATELOCKPARAM2(void *pvParam1, uint64_t val2, RTGCUINTREG32 *pf);
     87typedef FNEMULATELOCKPARAM2 *PFNEMULATELOCKPARAM2;
     88typedef DECLCALLBACK(int)      FNEMULATELOCKPARAM3(void *pvParam1, uint64_t val2, size_t cb, RTGCUINTREG32 *pf);
     89typedef FNEMULATELOCKPARAM3 *PFNEMULATELOCKPARAM3;
    8090
    8191/**
  • trunk/src/VBox/VMM/IOM.cpp

    r9776 r10473  
    132132        STAM_REG(pVM, &pVM->iom.s.StatGCInstCmp,          STAMTYPE_PROFILE, "/IOM/GC/Inst/CMP",            STAMUNIT_TICKS_PER_CALL, "Profiling of the CMP instruction emulation.");
    133133        STAM_REG(pVM, &pVM->iom.s.StatGCInstAnd,          STAMTYPE_PROFILE, "/IOM/GC/Inst/AND",            STAMUNIT_TICKS_PER_CALL, "Profiling of the AND instruction emulation.");
     134        STAM_REG(pVM, &pVM->iom.s.StatGCInstOr,           STAMTYPE_PROFILE, "/IOM/GC/Inst/OR",             STAMUNIT_TICKS_PER_CALL, "Profiling of the OR instruction emulation.");
     135        STAM_REG(pVM, &pVM->iom.s.StatGCInstXor,          STAMTYPE_PROFILE, "/IOM/GC/Inst/XOR",            STAMUNIT_TICKS_PER_CALL, "Profiling of the XOR instruction emulation.");
     136        STAM_REG(pVM, &pVM->iom.s.StatGCInstBt,           STAMTYPE_PROFILE, "/IOM/GC/Inst/BT",             STAMUNIT_TICKS_PER_CALL, "Profiling of the BT instruction emulation.");
    134137        STAM_REG(pVM, &pVM->iom.s.StatGCInstTest,         STAMTYPE_PROFILE, "/IOM/GC/Inst/TEST",           STAMUNIT_TICKS_PER_CALL, "Profiling of the TEST instruction emulation.");
    135138        STAM_REG(pVM, &pVM->iom.s.StatGCInstXchg,         STAMTYPE_PROFILE, "/IOM/GC/Inst/XCHG",           STAMUNIT_TICKS_PER_CALL, "Profiling of the XCHG instruction emulation.");
  • trunk/src/VBox/VMM/IOMInternal.h

    r9776 r10473  
    390390    STAMPROFILE             StatGCInstCmp;
    391391    STAMPROFILE             StatGCInstAnd;
     392    STAMPROFILE             StatGCInstOr;
     393    STAMPROFILE             StatGCInstXor;
     394    STAMPROFILE             StatGCInstBt;
    392395    STAMPROFILE             StatGCInstTest;
    393396    STAMPROFILE             StatGCInstXchg;
  • trunk/src/VBox/VMM/VMMAll/EMAll.cpp

    r10362 r10473  
    5151*   Structures and Typedefs                                                    *
    5252*******************************************************************************/
    53 typedef DECLCALLBACK(uint32_t) PFN_EMULATE_PARAM2_UINT32(void *pvParam1, uint64_t val2);
    54 typedef DECLCALLBACK(uint32_t) PFN_EMULATE_PARAM2(void *pvParam1, size_t val2);
    55 typedef DECLCALLBACK(uint32_t) PFN_EMULATE_PARAM3(void *pvParam1, uint64_t val2, size_t val3);
    56 typedef DECLCALLBACK(int)      FNEMULATELOCKPARAM2(void *pvParam1, uint64_t val2, RTGCUINTREG32 *pf);
    57 typedef FNEMULATELOCKPARAM2 *PFNEMULATELOCKPARAM2;
    58 typedef DECLCALLBACK(int)      FNEMULATELOCKPARAM3(void *pvParam1, uint64_t val2, size_t cb, RTGCUINTREG32 *pf);
    59 typedef FNEMULATELOCKPARAM3 *PFNEMULATELOCKPARAM3;
    6053
    6154
  • trunk/src/VBox/VMM/VMMAll/IOMAllMMIO.cpp

    r10382 r10473  
    748748 * AND [MMIO], reg|imm
    749749 * AND reg, [MMIO]
     750 * OR [MMIO], reg|imm
     751 * OR reg, [MMIO]
    750752 *
    751753 * Restricted implementation.
     
    759761 * @param   pCpu        Disassembler CPU state.
    760762 * @param   pRange      Pointer MMIO range.
    761  */
    762 static int iomInterpretAND(PVM pVM, PCPUMCTXCORE pRegFrame, RTGCPHYS GCPhysFault, PDISCPUSTATE pCpu, PIOMMMIORANGE pRange)
     763 * @param   pfnEmulate  Instruction emulation function.
     764 */
     765static int iomInterpretOrXorAnd(PVM pVM, PCPUMCTXCORE pRegFrame, RTGCPHYS GCPhysFault, PDISCPUSTATE pCpu, PIOMMMIORANGE pRange, PFN_EMULATE_PARAM3 pfnEmulate)
    763766{
    764767    unsigned    cb = 0;
     
    767770    bool        fAndWrite;
    768771    int         rc;
     772
     773#ifdef LOG_ENABLED
     774    const char *pszInstr;
     775
     776    if (pCpu->pCurInstr->opcode == OP_XOR)
     777        pszInstr = "Xor";
     778    else if (pCpu->pCurInstr->opcode == OP_OR)
     779        pszInstr = "Or";
     780    else if (pCpu->pCurInstr->opcode == OP_AND)
     781        pszInstr = "And";
     782    else
     783        pszInstr = "OrXorAnd??";
     784#endif
     785
    769786    if (iomGetRegImmData(pCpu, &pCpu->param1, pRegFrame, &uData1, &cb))
    770787    {
     
    793810    {
    794811        /* Emulate AND and update guest flags. */
    795         uint32_t eflags = EMEmulateAnd((uint32_t *)&uData1, uData2, cb);
     812        uint32_t eflags = pfnEmulate((uint32_t *)&uData1, uData2, cb);
     813
     814        LogFlow(("iomInterpretOrXorAnd %s result %RX64\n", pszInstr, uData1));
     815
    796816        if (fAndWrite)
    797817            /* Store result to MMIO. */
     
    815835}
    816836
    817 
    818 
    819837/**
    820838 * TEST [MMIO], reg|imm
     
    863881        pRegFrame->eflags.u32 = (pRegFrame->eflags.u32 & ~(X86_EFL_CF | X86_EFL_PF | X86_EFL_AF | X86_EFL_ZF | X86_EFL_SF | X86_EFL_OF))
    864882                              | (eflags                &  (X86_EFL_CF | X86_EFL_PF | X86_EFL_AF | X86_EFL_ZF | X86_EFL_SF | X86_EFL_OF));
     883        iomMMIOStatLength(pVM, cb);
     884    }
     885
     886    return rc;
     887}
     888
     889/**
     890 * BT [MMIO], reg|imm
     891 *
     892 * Restricted implementation.
     893 *
     894 *
     895 * @returns VBox status code.
     896 *
     897 * @param   pVM         The virtual machine (GC pointer ofcourse).
     898 * @param   pRegFrame   Trap register frame.
     899 * @param   GCPhysFault The GC physical address corresponding to pvFault.
     900 * @param   pCpu        Disassembler CPU state.
     901 * @param   pRange      Pointer MMIO range.
     902 */
     903static int iomInterpretBT(PVM pVM, PCPUMCTXCORE pRegFrame, RTGCPHYS GCPhysFault, PDISCPUSTATE pCpu, PIOMMMIORANGE pRange)
     904{
     905    Assert(pRange->CTXALLSUFF(pfnReadCallback) || !pRange->pfnReadCallbackR3);
     906
     907    uint64_t    uBit;
     908    uint64_t    uData1;
     909    int         rc;
     910    unsigned    cb;
     911
     912    if (iomGetRegImmData(pCpu, &pCpu->param2, pRegFrame, &uBit, &cb))
     913    {
     914        /* bt [MMIO], reg|imm. */
     915        rc = iomMMIODoRead(pVM, pRange, GCPhysFault, &uData1, cb);
     916    }
     917    else
     918    {
     919        AssertMsgFailed(("Disassember BT problem..\n"));
     920        return VERR_IOM_MMIO_HANDLER_DISASM_ERROR;
     921    }
     922
     923    if (rc == VINF_SUCCESS)
     924    {
     925        /* The size of the memory operand only matters here. */
     926        cb = DISGetParamSize(pCpu, &pCpu->param1);
     927
     928        /* Find the bit inside the faulting address */
     929        uBit &= (cb*8 - 1);
     930
     931        pRegFrame->eflags.Bits.u1CF = (uData1 >> uBit);
    865932        iomMMIOStatLength(pVM, cb);
    866933    }
     
    10621129        case OP_AND:
    10631130            STAM_PROFILE_START(&pVM->iom.s.StatGCInstAnd, g);
    1064             rc = iomInterpretAND(pVM, pCtxCore, GCPhysFault, &Cpu, pRange);
     1131            rc = iomInterpretOrXorAnd(pVM, pCtxCore, GCPhysFault, &Cpu, pRange, EMEmulateAnd);
    10651132            STAM_PROFILE_STOP(&pVM->iom.s.StatGCInstAnd, g);
     1133            break;
     1134
     1135        case OP_OR:
     1136            STAM_PROFILE_START(&pVM->iom.s.StatGCInstOr, k);
     1137            rc = iomInterpretOrXorAnd(pVM, pCtxCore, GCPhysFault, &Cpu, pRange, EMEmulateOr);
     1138            STAM_PROFILE_STOP(&pVM->iom.s.StatGCInstOr, k);
     1139            break;
     1140
     1141        case OP_XOR:
     1142            STAM_PROFILE_START(&pVM->iom.s.StatGCInstXor, m);
     1143            rc = iomInterpretOrXorAnd(pVM, pCtxCore, GCPhysFault, &Cpu, pRange, EMEmulateXor);
     1144            STAM_PROFILE_STOP(&pVM->iom.s.StatGCInstXor, m);
    10661145            break;
    10671146
     
    10711150            rc = iomInterpretTEST(pVM, pCtxCore, GCPhysFault, &Cpu, pRange);
    10721151            STAM_PROFILE_STOP(&pVM->iom.s.StatGCInstTest, h);
     1152            break;
     1153
     1154        case OP_BT:
     1155            Assert(!(uErrorCode & X86_TRAP_PF_RW));
     1156            STAM_PROFILE_START(&pVM->iom.s.StatGCInstBt, l);
     1157            rc = iomInterpretBT(pVM, pCtxCore, GCPhysFault, &Cpu, pRange);
     1158            STAM_PROFILE_STOP(&pVM->iom.s.StatGCInstBt, l);
    10731159            break;
    10741160
  • trunk/src/VBox/VMM/VMMR0/HWVMXR0.cpp

    r10466 r10473  
    11861186    /* Note the 32 bits exception for AMD (X86_CPUID_AMD_FEATURE_ECX_CR8L), but that appears missing in Intel CPUs */
    11871187    /* Note: we can't do this in LoadGuestState as PDMApicGetTPR can jump back to ring 3 (lock). */
     1188    /*
     1189     * @todo reduce overhead
     1190     */
    11881191    if (    pCtx->msrEFER & MSR_K6_EFER_LMA
    11891192        &&  pVM->hwaccm.s.vmx.pAPIC)
     
    14101413    pCtx->eflags.u32        = val;
    14111414
    1412     /* Update the APIC with the cached TPR value. */
     1415    /* Update the APIC with the cached TPR value.
     1416     * @todo reduce overhead
     1417     */
    14131418    if (    pCtx->msrEFER & MSR_K6_EFER_LMA
    14141419        &&  pVM->hwaccm.s.vmx.pAPIC)
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette