VirtualBox

Changeset 47288 in vbox for trunk/src/VBox/VMM/VMMAll


Ignore:
Timestamp:
Jul 20, 2013 10:52:31 PM (12 years ago)
Author:
vboxsync
Message:

64-bit segmentation fixes to string instr.

Location:
trunk/src/VBox/VMM/VMMAll
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMAll/IEMAll.cpp

    r47283 r47288  
    47794779 * @param   pHid                Pointer to the hidden register.
    47804780 * @param   iSegReg             The register number.
    4781  */
    4782 static VBOXSTRICTRC iemMemSegCheckWriteAccessEx(PIEMCPU pIemCpu, PCCPUMSELREGHID pHid, uint8_t iSegReg)
    4783 {
    4784     if (!pHid->Attr.n.u1Present)
    4785         return iemRaiseSelectorNotPresentBySegReg(pIemCpu, iSegReg);
    4786 
    4787     if (   (   (pHid->Attr.n.u4Type & X86_SEL_TYPE_CODE)
    4788             || !(pHid->Attr.n.u4Type & X86_SEL_TYPE_WRITE) )
    4789         &&  pIemCpu->enmCpuMode != IEMMODE_64BIT )
    4790         return iemRaiseSelectorInvalidAccess(pIemCpu, iSegReg, IEM_ACCESS_DATA_W);
    4791 
    4792     /** @todo DPL/RPL/CPL? */
    4793 
     4781 * @param   pu64BaseAddr        Where to return the base address to use for the
     4782 *                              segment. (In 64-bit code it may differ from the
     4783 *                              base in the hidden segment.)
     4784 */
     4785static VBOXSTRICTRC iemMemSegCheckWriteAccessEx(PIEMCPU pIemCpu, PCCPUMSELREGHID pHid, uint8_t iSegReg, uint64_t *pu64BaseAddr)
     4786{
     4787    if (pIemCpu->enmCpuMode == IEMMODE_64BIT)
     4788        *pu64BaseAddr = iSegReg < X86_SREG_FS ? 0 : pHid->u64Base;
     4789    else
     4790    {
     4791        if (!pHid->Attr.n.u1Present)
     4792            return iemRaiseSelectorNotPresentBySegReg(pIemCpu, iSegReg);
     4793
     4794        if (   (   (pHid->Attr.n.u4Type & X86_SEL_TYPE_CODE)
     4795                || !(pHid->Attr.n.u4Type & X86_SEL_TYPE_WRITE) )
     4796            &&  pIemCpu->enmCpuMode != IEMMODE_64BIT )
     4797            return iemRaiseSelectorInvalidAccess(pIemCpu, iSegReg, IEM_ACCESS_DATA_W);
     4798        *pu64BaseAddr = pHid->u64Base;
     4799    }
    47944800    return VINF_SUCCESS;
    47954801}
     
    48054811 * @param   pHid                Pointer to the hidden register.
    48064812 * @param   iSegReg             The register number.
    4807  */
    4808 static VBOXSTRICTRC iemMemSegCheckReadAccessEx(PIEMCPU pIemCpu, PCCPUMSELREGHID pHid, uint8_t iSegReg)
    4809 {
    4810     if (!pHid->Attr.n.u1Present)
    4811         return iemRaiseSelectorNotPresentBySegReg(pIemCpu, iSegReg);
    4812 
    4813     if (   (pHid->Attr.n.u4Type & (X86_SEL_TYPE_CODE | X86_SEL_TYPE_READ)) == X86_SEL_TYPE_CODE
    4814         &&  pIemCpu->enmCpuMode != IEMMODE_64BIT )
    4815         return iemRaiseSelectorInvalidAccess(pIemCpu, iSegReg, IEM_ACCESS_DATA_R);
    4816 
    4817     /** @todo DPL/RPL/CPL? */
    4818 
     4813 * @param   pu64BaseAddr        Where to return the base address to use for the
     4814 *                              segment. (In 64-bit code it may differ from the
     4815 *                              base in the hidden segment.)
     4816 */
     4817static VBOXSTRICTRC iemMemSegCheckReadAccessEx(PIEMCPU pIemCpu, PCCPUMSELREGHID pHid, uint8_t iSegReg, uint64_t *pu64BaseAddr)
     4818{
     4819    if (pIemCpu->enmCpuMode == IEMMODE_64BIT)
     4820        *pu64BaseAddr = iSegReg < X86_SREG_FS ? 0 : pHid->u64Base;
     4821    else
     4822    {
     4823        if (!pHid->Attr.n.u1Present)
     4824            return iemRaiseSelectorNotPresentBySegReg(pIemCpu, iSegReg);
     4825
     4826        if ((pHid->Attr.n.u4Type & (X86_SEL_TYPE_CODE | X86_SEL_TYPE_READ)) == X86_SEL_TYPE_CODE)
     4827            return iemRaiseSelectorInvalidAccess(pIemCpu, iSegReg, IEM_ACCESS_DATA_R);
     4828        *pu64BaseAddr = pHid->u64Base;
     4829    }
    48194830    return VINF_SUCCESS;
    48204831}
  • trunk/src/VBox/VMM/VMMAll/IEMAllCImplStrInstr.cpp.h

    r45305 r47288  
    4848# define ADDR_rCX   rcx
    4949# define ADDR2_TYPE uint64_t
     50# define IS_64_BIT_CODE(a_pIemCpu) (true)
    5051#else
    5152# error "Bad ADDR_SIZE."
    5253#endif
    5354#define ADDR_TYPE                   RT_CONCAT3(uint,ADDR_SIZE,_t)
     55
     56#if ADDR_SIZE == 64 || OP_SIZE == 64
     57# define IS_64_BIT_CODE(a_pIemCpu)  (true)
     58#elif ADDR_SIZE == 32
     59# define IS_64_BIT_CODE(a_pIemCpu)  ((a_pIemCpu)->enmCpuMode == IEMMODE_64BIT)
     60#else
     61# define IS_64_BIT_CODE(a_pIemCpu)  (false)
     62#endif
    5463
    5564
     
    7281
    7382    PCCPUMSELREGHID pSrc1Hid     = iemSRegGetHid(pIemCpu, iEffSeg);
    74     VBOXSTRICTRC    rcStrict     = iemMemSegCheckReadAccessEx(pIemCpu, pSrc1Hid, iEffSeg);
    75     if (rcStrict != VINF_SUCCESS)
    76         return rcStrict;
    77 
    78     rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     83    uint64_t        uSrc1Base;
     84    VBOXSTRICTRC    rcStrict     = iemMemSegCheckReadAccessEx(pIemCpu, pSrc1Hid, iEffSeg, &uSrc1Base);
     85    if (rcStrict != VINF_SUCCESS)
     86        return rcStrict;
     87
     88    uint64_t        uSrc2Base;
     89    rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uSrc2Base);
    7990    if (rcStrict != VINF_SUCCESS)
    8091        return rcStrict;
     
    93104         * Do segmentation and virtual page stuff.
    94105         */
    95 #if ADDR_SIZE != 64
    96         ADDR2_TYPE  uVirtSrc1Addr = (uint32_t)pSrc1Hid->u64Base + uSrc1AddrReg;
    97         ADDR2_TYPE  uVirtSrc2Addr = (uint32_t)pCtx->es.u64Base  + uSrc2AddrReg;
    98 #else
    99         uint64_t    uVirtSrc1Addr = uSrc1AddrReg;
    100         uint64_t    uVirtSrc2Addr = uSrc2AddrReg;
    101 #endif
     106        ADDR2_TYPE  uVirtSrc1Addr = uSrc1AddrReg + (ADDR2_TYPE)uSrc1Base;
     107        ADDR2_TYPE  uVirtSrc2Addr = uSrc2AddrReg + (ADDR2_TYPE)uSrc2Base;
    102108        uint32_t    cLeftSrc1Page = (PAGE_SIZE - (uVirtSrc1Addr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    103109        if (cLeftSrc1Page > uCounterReg)
     
    107113
    108114        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    109             && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    110 #if ADDR_SIZE != 64
    111             && uSrc1AddrReg < pSrc1Hid->u32Limit
    112             && uSrc1AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrc1Hid->u32Limit
    113             && uSrc2AddrReg < pCtx->es.u32Limit
    114             && uSrc2AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    115 #endif
     115            && cbIncr > 0    /** @todo Optimize reverse direction string ops. */
     116            && (   IS_64_BIT_CODE(pIemCpu)
     117                || (  uSrc1AddrReg < pSrc1Hid->u32Limit
     118                    && uSrc1AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrc1Hid->u32Limit
     119                    && uSrc2AddrReg < pCtx->es.u32Limit
     120                    && uSrc2AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     121               )
    116122           )
    117123        {
     
    231237
    232238    PCCPUMSELREGHID pSrc1Hid = iemSRegGetHid(pIemCpu, iEffSeg);
    233     VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pSrc1Hid, iEffSeg);
    234     if (rcStrict != VINF_SUCCESS)
    235         return rcStrict;
    236 
    237     rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     239    uint64_t        uSrc1Base;
     240    VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pSrc1Hid, iEffSeg, &uSrc1Base);
     241    if (rcStrict != VINF_SUCCESS)
     242        return rcStrict;
     243
     244    uint64_t        uSrc2Base;
     245    rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uSrc2Base);
    238246    if (rcStrict != VINF_SUCCESS)
    239247        return rcStrict;
     
    252260         * Do segmentation and virtual page stuff.
    253261         */
    254 #if ADDR_SIZE != 64
    255         ADDR2_TYPE  uVirtSrc1Addr = (uint32_t)pSrc1Hid->u64Base + uSrc1AddrReg;
    256         ADDR2_TYPE  uVirtSrc2Addr = (uint32_t)pCtx->es.u64Base  + uSrc2AddrReg;
    257 #else
    258         uint64_t    uVirtSrc1Addr = uSrc1AddrReg;
    259         uint64_t    uVirtSrc2Addr = uSrc2AddrReg;
    260 #endif
     262        ADDR2_TYPE  uVirtSrc1Addr = uSrc1AddrReg + (ADDR2_TYPE)uSrc1Base;
     263        ADDR2_TYPE  uVirtSrc2Addr = uSrc2AddrReg + (ADDR2_TYPE)uSrc2Base;
    261264        uint32_t    cLeftSrc1Page = (PAGE_SIZE - (uVirtSrc1Addr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    262265        if (cLeftSrc1Page > uCounterReg)
     
    266269
    267270        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    268             && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    269 #if ADDR_SIZE != 64
    270             && uSrc1AddrReg < pSrc1Hid->u32Limit
    271             && uSrc1AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrc1Hid->u32Limit
    272             && uSrc2AddrReg < pCtx->es.u32Limit
    273             && uSrc2AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    274 #endif
     271            && cbIncr > 0    /** @todo Optimize reverse direction string ops. */
     272            && (   IS_64_BIT_CODE(pIemCpu)
     273                || (  uSrc1AddrReg < pSrc1Hid->u32Limit
     274                    && uSrc1AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrc1Hid->u32Limit
     275                    && uSrc2AddrReg < pCtx->es.u32Limit
     276                    && uSrc2AddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     277                )
    275278           )
    276279        {
     
    389392    }
    390393
    391     VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     394    uint64_t        uBaseAddr;
     395    VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uBaseAddr);
    392396    if (rcStrict != VINF_SUCCESS)
    393397        return rcStrict;
     
    406410         * Do segmentation and virtual page stuff.
    407411         */
    408 #if ADDR_SIZE != 64
    409         ADDR2_TYPE  uVirtAddr = (uint32_t)pCtx->es.u64Base + uAddrReg;
    410 #else
    411         uint64_t    uVirtAddr = uAddrReg;
    412 #endif
     412        ADDR2_TYPE  uVirtAddr = uAddrReg + (ADDR2_TYPE)uBaseAddr;
    413413        uint32_t    cLeftPage = (PAGE_SIZE - (uVirtAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    414414        if (cLeftPage > uCounterReg)
     
    416416        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    417417            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    418 #if ADDR_SIZE != 64
    419             && uAddrReg < pCtx->es.u32Limit
    420             && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    421 #endif
     418            && (   IS_64_BIT_CODE(pIemCpu)
     419                || (  uAddrReg < pCtx->es.u32Limit
     420                    && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     421               )
    422422           )
    423423        {
     
    514514    }
    515515
    516     VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     516    uint64_t        uBaseAddr;
     517    VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uBaseAddr);
    517518    if (rcStrict != VINF_SUCCESS)
    518519        return rcStrict;
     
    531532         * Do segmentation and virtual page stuff.
    532533         */
    533 #if ADDR_SIZE != 64
    534         ADDR2_TYPE  uVirtAddr = (uint32_t)pCtx->es.u64Base + uAddrReg;
    535 #else
    536         uint64_t    uVirtAddr = uAddrReg;
    537 #endif
     534        ADDR2_TYPE  uVirtAddr = uAddrReg + (ADDR2_TYPE)uBaseAddr;
    538535        uint32_t    cLeftPage = (PAGE_SIZE - (uVirtAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    539536        if (cLeftPage > uCounterReg)
     
    541538        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    542539            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    543 #if ADDR_SIZE != 64
    544             && uAddrReg < pCtx->es.u32Limit
    545             && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    546 #endif
     540            && (   IS_64_BIT_CODE(pIemCpu)
     541                || (  uAddrReg < pCtx->es.u32Limit
     542                    && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     543               )
    547544           )
    548545        {
     
    641638
    642639    PCCPUMSELREGHID pSrcHid = iemSRegGetHid(pIemCpu, iEffSeg);
    643     VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pSrcHid, iEffSeg);
    644     if (rcStrict != VINF_SUCCESS)
    645         return rcStrict;
    646 
    647     rcStrict = iemMemSegCheckWriteAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     640    uint64_t        uSrcBase;
     641    VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pSrcHid, iEffSeg, &uSrcBase);
     642    if (rcStrict != VINF_SUCCESS)
     643        return rcStrict;
     644
     645    uint64_t        uDstBase;
     646    rcStrict = iemMemSegCheckWriteAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uDstBase);
    648647    if (rcStrict != VINF_SUCCESS)
    649648        return rcStrict;
     
    685684         * Do segmentation and virtual page stuff.
    686685         */
    687 #if ADDR_SIZE != 64
    688         ADDR2_TYPE  uVirtSrcAddr = (uint32_t)pSrcHid->u64Base + uSrcAddrReg;
    689         ADDR2_TYPE  uVirtDstAddr = (uint32_t)pCtx->es.u64Base + uDstAddrReg;
    690 #else
    691         uint64_t    uVirtSrcAddr = uSrcAddrReg;
    692         uint64_t    uVirtDstAddr = uDstAddrReg;
    693 #endif
     686        ADDR2_TYPE  uVirtSrcAddr = uSrcAddrReg + (ADDR2_TYPE)uSrcBase;
     687        ADDR2_TYPE  uVirtDstAddr = uDstAddrReg + (ADDR2_TYPE)uDstBase;
    694688        uint32_t    cLeftSrcPage = (PAGE_SIZE - (uVirtSrcAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    695689        if (cLeftSrcPage > uCounterReg)
     
    700694        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    701695            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    702 #if ADDR_SIZE != 64
    703             && uSrcAddrReg < pSrcHid->u32Limit
    704             && uSrcAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrcHid->u32Limit
    705             && uDstAddrReg < pCtx->es.u32Limit
    706             && uDstAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    707 #endif
     696            && (   IS_64_BIT_CODE(pIemCpu)
     697                || (  uSrcAddrReg < pSrcHid->u32Limit
     698                    && uSrcAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrcHid->u32Limit
     699                    && uDstAddrReg < pCtx->es.u32Limit
     700                    && uDstAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     701               )
    708702           )
    709703        {
     
    804798    }
    805799
    806     VBOXSTRICTRC rcStrict = iemMemSegCheckWriteAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     800    uint64_t        uBaseAddr;
     801    VBOXSTRICTRC rcStrict = iemMemSegCheckWriteAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uBaseAddr);
    807802    if (rcStrict != VINF_SUCCESS)
    808803        return rcStrict;
     
    830825         * Do segmentation and virtual page stuff.
    831826         */
    832 #if ADDR_SIZE != 64
    833         ADDR2_TYPE  uVirtAddr = (uint32_t)pCtx->es.u64Base + uAddrReg;
    834 #else
    835         uint64_t    uVirtAddr = uAddrReg;
    836 #endif
     827        ADDR2_TYPE  uVirtAddr = uAddrReg + (ADDR2_TYPE)uBaseAddr;
    837828        uint32_t    cLeftPage = (PAGE_SIZE - (uVirtAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    838829        if (cLeftPage > uCounterReg)
     
    840831        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    841832            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    842 #if ADDR_SIZE != 64
    843             && uAddrReg < pCtx->es.u32Limit
    844             && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    845 #endif
     833            && (   IS_64_BIT_CODE(pIemCpu)
     834                || (  uAddrReg < pCtx->es.u32Limit
     835                    && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     836               )
    846837           )
    847838        {
     
    928919
    929920    PCCPUMSELREGHID pSrcHid = iemSRegGetHid(pIemCpu, iEffSeg);
    930     VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pSrcHid, iEffSeg);
     921    uint64_t        uBaseAddr;
     922    VBOXSTRICTRC rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pSrcHid, iEffSeg, &uBaseAddr);
    931923    if (rcStrict != VINF_SUCCESS)
    932924        return rcStrict;
     
    943935         * Do segmentation and virtual page stuff.
    944936         */
    945 #if ADDR_SIZE != 64
    946         ADDR2_TYPE  uVirtAddr = (uint32_t)pSrcHid->u64Base + uAddrReg;
    947 #else
    948         uint64_t    uVirtAddr = uAddrReg;
    949 #endif
     937        ADDR2_TYPE  uVirtAddr = uAddrReg + (ADDR2_TYPE)uBaseAddr;
    950938        uint32_t    cLeftPage = (PAGE_SIZE - (uVirtAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    951939        if (cLeftPage > uCounterReg)
     
    953941        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    954942            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    955 #if ADDR_SIZE != 64
    956             && uAddrReg < pSrcHid->u32Limit
    957             && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrcHid->u32Limit
    958 #endif
     943            && (   IS_64_BIT_CODE(pIemCpu)
     944                || (  uAddrReg < pSrcHid->u32Limit
     945                    && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pSrcHid->u32Limit)
     946               )
    959947           )
    960948        {
     
    11101098    }
    11111099
    1112     rcStrict = iemMemSegCheckWriteAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES);
     1100    uint64_t        uBaseAddr;
     1101    rcStrict = iemMemSegCheckWriteAccessEx(pIemCpu, &pCtx->es, X86_SREG_ES, &uBaseAddr);
    11131102    if (rcStrict != VINF_SUCCESS)
    11141103        return rcStrict;
     
    11341123         * Do segmentation and virtual page stuff.
    11351124         */
    1136 #if ADDR_SIZE != 64
    1137         ADDR2_TYPE  uVirtAddr = (uint32_t)pCtx->es.u64Base + uAddrReg;
    1138 #else
    1139         uint64_t    uVirtAddr = uAddrReg;
    1140 #endif
     1125        ADDR2_TYPE  uVirtAddr = uAddrReg + (ADDR2_TYPE)uBaseAddr;
    11411126        uint32_t    cLeftPage = (PAGE_SIZE - (uVirtAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    11421127        if (cLeftPage > uCounterReg)
     
    11441129        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    11451130            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    1146 #if ADDR_SIZE != 64
    1147             && uAddrReg < pCtx->es.u32Limit
    1148             && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit
    1149 #endif
     1131            && (   IS_64_BIT_CODE(pIemCpu)
     1132                || (  uAddrReg < pCtx->es.u32Limit
     1133                    && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pCtx->es.u32Limit)
     1134               )
    11501135           )
    11511136        {
     
    13241309
    13251310    PCCPUMSELREGHID pHid = iemSRegGetHid(pIemCpu, iEffSeg);
    1326     rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pHid, iEffSeg);
     1311    uint64_t        uBaseAddr;
     1312    rcStrict = iemMemSegCheckReadAccessEx(pIemCpu, pHid, iEffSeg, &uBaseAddr);
    13271313    if (rcStrict != VINF_SUCCESS)
    13281314        return rcStrict;
     
    13391325         * Do segmentation and virtual page stuff.
    13401326         */
    1341 #if ADDR_SIZE != 64
    1342         ADDR2_TYPE  uVirtAddr = (uint32_t)pHid->u64Base + uAddrReg;
    1343 #else
    1344         uint64_t    uVirtAddr = uAddrReg;
    1345 #endif
     1327        ADDR2_TYPE  uVirtAddr = uAddrReg + (ADDR2_TYPE)uBaseAddr;
    13461328        uint32_t    cLeftPage = (PAGE_SIZE - (uVirtAddr & PAGE_OFFSET_MASK)) / (OP_SIZE / 8);
    13471329        if (cLeftPage > uCounterReg)
     
    13491331        if (   cLeftPage > 0 /* can be null if unaligned, do one fallback round. */
    13501332            && cbIncr > 0    /** @todo Implement reverse direction string ops. */
    1351 #if ADDR_SIZE != 64
    1352             && uAddrReg < pHid->u32Limit
    1353             && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pHid->u32Limit
    1354 #endif
     1333            && (   IS_64_BIT_CODE(pIemCpu)
     1334                || (  uAddrReg < pHid->u32Limit
     1335                    && uAddrReg + (cLeftPage * (OP_SIZE / 8)) <= pHid->u32Limit)
     1336               )
    13551337           )
    13561338        {
     
    14681450#undef ADDR_TYPE
    14691451#undef ADDR2_TYPE
    1470 
     1452#undef IS_64_BIT_CODE
Note: See TracChangeset for help on using the changeset viewer.

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