VirtualBox

Changeset 103739 in vbox for trunk/src/VBox/VMM


Ignore:
Timestamp:
Mar 9, 2024 12:03:05 AM (12 months ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
162108
Message:

VMM/IEM: Implemented native emitter for ADD instructions taking immediates. bugref:10376

Location:
trunk/src/VBox/VMM
Files:
8 edited

Legend:

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

    r103731 r103739  
    823823 * a byte immediate.
    824824 */
    825 #define IEMOP_BODY_BINARY_AL_Ib(a_fnNormalU8) \
     825#define IEMOP_BODY_BINARY_AL_Ib(a_InsNm, a_fNativeArchs) \
     826    IEM_MC_BEGIN(3, 3, 0, 0); \
    826827    uint8_t u8Imm; IEM_OPCODE_GET_NEXT_U8(&u8Imm); \
    827     \
    828     IEM_MC_BEGIN(3, 0, 0, 0); \
    829828    IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    830     IEM_MC_ARG(uint8_t *,       pu8Dst,             0); \
    831     IEM_MC_ARG_CONST(uint8_t,   u8Src,/*=*/ u8Imm,  1); \
    832     IEM_MC_ARG(uint32_t *,      pEFlags,            2); \
    833     \
    834     IEM_MC_REF_GREG_U8(pu8Dst, X86_GREG_xAX); \
    835     IEM_MC_REF_EFLAGS(pEFlags); \
    836     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU8, pu8Dst, u8Src, pEFlags); \
    837     \
     829    IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     830        IEM_MC_LOCAL(uint8_t,       u8Dst); \
     831        IEM_MC_FETCH_GREG_U8(u8Dst, X86_GREG_xAX); \
     832        IEM_MC_LOCAL(uint32_t,      uEFlags); \
     833        IEM_MC_FETCH_EFLAGS(uEFlags); \
     834        IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u8Dst, u8Imm, uEFlags, 8, 8); \
     835        IEM_MC_COMMIT_EFLAGS(uEFlags); \
     836        IEM_MC_STORE_GREG_U8(X86_GREG_xAX, u8Dst); \
     837    } IEM_MC_NATIVE_ELSE() { \
     838        IEM_MC_ARG_CONST(uint8_t,   u8Src,/*=*/ u8Imm,  1); \
     839        IEM_MC_ARG(uint8_t *,       pu8Dst,             0); \
     840        IEM_MC_REF_GREG_U8(pu8Dst, X86_GREG_xAX); \
     841        IEM_MC_ARG(uint32_t *,      pEFlags,            2); \
     842        IEM_MC_REF_EFLAGS(pEFlags); \
     843        IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u8), pu8Dst, u8Src, pEFlags); \
     844    } IEM_MC_NATIVE_ENDIF(); \
    838845    IEM_MC_ADVANCE_RIP_AND_FINISH();  \
    839846    IEM_MC_END()
     
    843850 * AX/EAX/RAX with a word/dword immediate.
    844851 */
    845 #define IEMOP_BODY_BINARY_rAX_Iz(a_fnNormalU16, a_fnNormalU32, a_fnNormalU64, a_fModifiesDstReg) \
     852#define IEMOP_BODY_BINARY_rAX_Iz_RW(a_InsNm, a_fNativeArchs) \
    846853    switch (pVCpu->iem.s.enmEffOpSize) \
    847854    { \
    848855        case IEMMODE_16BIT: \
    849856        { \
     857            IEM_MC_BEGIN(3, 2, 0, 0); \
    850858            uint16_t u16Imm; IEM_OPCODE_GET_NEXT_U16(&u16Imm); \
    851             \
    852             IEM_MC_BEGIN(3, 0, 0, 0); \
    853859            IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    854             IEM_MC_ARG(uint16_t *,      pu16Dst,                0); \
    855             IEM_MC_ARG_CONST(uint16_t,  u16Src,/*=*/ u16Imm,    1); \
    856             IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    857             \
    858             IEM_MC_REF_GREG_U16(pu16Dst, X86_GREG_xAX); \
    859             IEM_MC_REF_EFLAGS(pEFlags); \
    860             IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU16, pu16Dst, u16Src, pEFlags); \
    861             \
     860            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     861                IEM_MC_LOCAL(uint16_t,       u16Dst); \
     862                IEM_MC_FETCH_GREG_U16(u16Dst, X86_GREG_xAX); \
     863                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     864                IEM_MC_FETCH_EFLAGS(uEFlags); \
     865                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u16Dst, u16Imm, uEFlags, 16, 16); \
     866                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     867                IEM_MC_STORE_GREG_U16(X86_GREG_xAX, u16Dst); \
     868            } IEM_MC_NATIVE_ELSE() { \
     869                IEM_MC_ARG_CONST(uint16_t,  u16Src,/*=*/ u16Imm,    1); \
     870                IEM_MC_ARG(uint16_t *,      pu16Dst,                0); \
     871                IEM_MC_REF_GREG_U16(pu16Dst, X86_GREG_xAX); \
     872                IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     873                IEM_MC_REF_EFLAGS(pEFlags); \
     874                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16), pu16Dst, u16Src, pEFlags); \
     875            } IEM_MC_NATIVE_ENDIF(); \
    862876            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    863877            IEM_MC_END(); \
     
    866880        case IEMMODE_32BIT: \
    867881        { \
     882            IEM_MC_BEGIN(3, 2, IEM_MC_F_MIN_386, 0); \
    868883            uint32_t u32Imm; IEM_OPCODE_GET_NEXT_U32(&u32Imm); \
    869             \
    870             IEM_MC_BEGIN(3, 0, IEM_MC_F_MIN_386, 0); \
    871884            IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    872             IEM_MC_ARG(uint32_t *,      pu32Dst,                0); \
    873             IEM_MC_ARG_CONST(uint32_t,  u32Src,/*=*/ u32Imm,    1); \
    874             IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    875             \
    876             IEM_MC_REF_GREG_U32(pu32Dst, X86_GREG_xAX); \
    877             IEM_MC_REF_EFLAGS(pEFlags); \
    878             IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU32, pu32Dst, u32Src, pEFlags); \
    879             \
    880             if (a_fModifiesDstReg) \
     885            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     886                IEM_MC_LOCAL(uint32_t,      u32Dst); \
     887                IEM_MC_FETCH_GREG_U32(u32Dst, X86_GREG_xAX); \
     888                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     889                IEM_MC_FETCH_EFLAGS(uEFlags); \
     890                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u32Dst, u32Imm, uEFlags, 32, 32); \
     891                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     892                IEM_MC_STORE_GREG_U32(X86_GREG_xAX, u32Dst); \
     893            } IEM_MC_NATIVE_ELSE() { \
     894                IEM_MC_ARG_CONST(uint32_t,  u32Src,/*=*/ u32Imm,    1); \
     895                IEM_MC_ARG(uint32_t *,      pu32Dst,                0); \
     896                IEM_MC_REF_GREG_U32(pu32Dst, X86_GREG_xAX); \
     897                IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     898                IEM_MC_REF_EFLAGS(pEFlags); \
     899                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32), pu32Dst, u32Src, pEFlags); \
    881900                IEM_MC_CLEAR_HIGH_GREG_U64(X86_GREG_xAX); \
     901            } IEM_MC_NATIVE_ENDIF(); \
    882902            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    883903            IEM_MC_END(); \
     
    886906        case IEMMODE_64BIT: \
    887907        { \
     908            IEM_MC_BEGIN(3, 2, IEM_MC_F_64BIT, 0); \
    888909            uint64_t u64Imm; IEM_OPCODE_GET_NEXT_S32_SX_U64(&u64Imm); \
    889             \
    890             IEM_MC_BEGIN(3, 0, IEM_MC_F_64BIT, 0); \
    891910            IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    892             IEM_MC_ARG(uint64_t *,      pu64Dst,                0); \
    893             IEM_MC_ARG_CONST(uint64_t,  u64Src,/*=*/ u64Imm,    1); \
    894             IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    895             \
    896             IEM_MC_REF_GREG_U64(pu64Dst, X86_GREG_xAX); \
    897             IEM_MC_REF_EFLAGS(pEFlags); \
    898             IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU64, pu64Dst, u64Src, pEFlags); \
    899             \
     911            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     912                IEM_MC_LOCAL(uint64_t,       u64Dst); \
     913                IEM_MC_FETCH_GREG_U64(u64Dst, X86_GREG_xAX); \
     914                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     915                IEM_MC_FETCH_EFLAGS(uEFlags); \
     916                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u64Dst, u64Imm, uEFlags, 64, 32); \
     917                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     918                IEM_MC_STORE_GREG_U64(X86_GREG_xAX, u64Dst); \
     919            } IEM_MC_NATIVE_ELSE() { \
     920                IEM_MC_ARG_CONST(uint64_t,  u64Src,/*=*/ u64Imm,    1); \
     921                IEM_MC_ARG(uint64_t *,      pu64Dst,                0); \
     922                IEM_MC_REF_GREG_U64(pu64Dst, X86_GREG_xAX); \
     923                IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     924                IEM_MC_REF_EFLAGS(pEFlags); \
     925                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64), pu64Dst, u64Src, pEFlags); \
     926            } IEM_MC_NATIVE_ENDIF(); \
     927            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
     928            IEM_MC_END(); \
     929        } \
     930        \
     931        IEM_NOT_REACHED_DEFAULT_CASE_RET(); \
     932    } \
     933    (void)0
     934
     935/**
     936 * Body for the instructions CMP and TEST working on AX/EAX/RAX with a
     937 * word/dword immediate.
     938 */
     939#define IEMOP_BODY_BINARY_rAX_Iz_RO(a_InsNm, a_fNativeArchs) \
     940    switch (pVCpu->iem.s.enmEffOpSize) \
     941    { \
     942        case IEMMODE_16BIT: \
     943        { \
     944            IEM_MC_BEGIN(3, 2, 0, 0); \
     945            uint16_t u16Imm; IEM_OPCODE_GET_NEXT_U16(&u16Imm); \
     946            IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
     947            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     948                IEM_MC_LOCAL(uint16_t,       u16Dst); \
     949                IEM_MC_FETCH_GREG_U16(u16Dst, X86_GREG_xAX); \
     950                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     951                IEM_MC_FETCH_EFLAGS(uEFlags); \
     952                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u16Dst, u16Imm, uEFlags, 16, 16); \
     953                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     954            } IEM_MC_NATIVE_ELSE() { \
     955                IEM_MC_ARG_CONST(uint16_t,  u16Src,/*=*/ u16Imm,    1); \
     956                IEM_MC_ARG(uint16_t const *,pu16Dst,                0); \
     957                IEM_MC_REF_GREG_U16_CONST(pu16Dst, X86_GREG_xAX); \
     958                IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     959                IEM_MC_REF_EFLAGS(pEFlags); \
     960                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16), pu16Dst, u16Src, pEFlags); \
     961            } IEM_MC_NATIVE_ENDIF(); \
     962            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
     963            IEM_MC_END(); \
     964        } \
     965        \
     966        case IEMMODE_32BIT: \
     967        { \
     968            IEM_MC_BEGIN(3, 2, IEM_MC_F_MIN_386, 0); \
     969            uint32_t u32Imm; IEM_OPCODE_GET_NEXT_U32(&u32Imm); \
     970            IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
     971            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     972                IEM_MC_LOCAL(uint32_t,      u32Dst); \
     973                IEM_MC_FETCH_GREG_U32(u32Dst, X86_GREG_xAX); \
     974                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     975                IEM_MC_FETCH_EFLAGS(uEFlags); \
     976                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u32Dst, u32Imm, uEFlags, 32, 32); \
     977                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     978            } IEM_MC_NATIVE_ELSE() { \
     979                IEM_MC_ARG_CONST(uint32_t,  u32Src,/*=*/ u32Imm,    1); \
     980                IEM_MC_ARG(uint32_t const *,pu32Dst,                0); \
     981                IEM_MC_REF_GREG_U32_CONST(pu32Dst, X86_GREG_xAX); \
     982                IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     983                IEM_MC_REF_EFLAGS(pEFlags); \
     984                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32), pu32Dst, u32Src, pEFlags); \
     985            } IEM_MC_NATIVE_ENDIF(); \
     986            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
     987            IEM_MC_END(); \
     988        } \
     989        \
     990        case IEMMODE_64BIT: \
     991        { \
     992            IEM_MC_BEGIN(3, 2, IEM_MC_F_64BIT, 0); \
     993            uint64_t u64Imm; IEM_OPCODE_GET_NEXT_S32_SX_U64(&u64Imm); \
     994            IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
     995            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     996                IEM_MC_LOCAL(uint64_t,       u64Dst); \
     997                IEM_MC_FETCH_GREG_U64(u64Dst, X86_GREG_xAX); \
     998                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     999                IEM_MC_FETCH_EFLAGS(uEFlags); \
     1000                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u64Dst, u64Imm, uEFlags, 64, 32); \
     1001                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     1002            } IEM_MC_NATIVE_ELSE() { \
     1003                IEM_MC_ARG_CONST(uint64_t,  u64Src,/*=*/ u64Imm,    1); \
     1004                IEM_MC_ARG(uint64_t const *,pu64Dst,                0); \
     1005                IEM_MC_REF_GREG_U64_CONST(pu64Dst, X86_GREG_xAX); \
     1006                IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     1007                IEM_MC_REF_EFLAGS(pEFlags); \
     1008                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64), pu64Dst, u64Src, pEFlags); \
     1009            } IEM_MC_NATIVE_ENDIF(); \
    9001010            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    9011011            IEM_MC_END(); \
     
    9891099{
    9901100    IEMOP_MNEMONIC2(FIXED, ADD, add, AL, Ib, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    991     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_add_u8);
     1101    IEMOP_BODY_BINARY_AL_Ib(add, RT_ARCH_VAL_AMD64 | RT_ARCH_VAL_ARM64);
    9921102}
    9931103
     
    10051115{
    10061116    IEMOP_MNEMONIC2(FIXED, ADD, add, rAX, Iz, DISOPTYPE_HARMLESS, 0);
    1007     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_add_u16, iemAImpl_add_u32, iemAImpl_add_u64, 1);
     1117    IEMOP_BODY_BINARY_rAX_Iz_RW(add, RT_ARCH_VAL_AMD64 | RT_ARCH_VAL_ARM64);
    10081118}
    10091119
     
    11201230    IEMOP_MNEMONIC2(FIXED, OR, or, AL, Ib, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    11211231    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    1122     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_or_u8);
     1232    IEMOP_BODY_BINARY_AL_Ib(or, 0);
    11231233}
    11241234
     
    11401250    IEMOP_MNEMONIC2(FIXED, OR, or, rAX, Iz, DISOPTYPE_HARMLESS, 0);
    11411251    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    1142     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_or_u16, iemAImpl_or_u32, iemAImpl_or_u64, 1);
     1252    IEMOP_BODY_BINARY_rAX_Iz_RW(or, 0);
    11431253}
    11441254
     
    12761386{
    12771387    IEMOP_MNEMONIC2(FIXED, ADC, adc, AL, Ib, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    1278     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_adc_u8);
     1388    IEMOP_BODY_BINARY_AL_Ib(adc, 0);
    12791389}
    12801390
     
    12891399{
    12901400    IEMOP_MNEMONIC2(FIXED, ADC, adc, rAX, Iz, DISOPTYPE_HARMLESS, 0);
    1291     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_adc_u16, iemAImpl_adc_u32, iemAImpl_adc_u64, 1);
     1401    IEMOP_BODY_BINARY_rAX_Iz_RW(adc, 0);
    12921402}
    12931403
     
    13831493{
    13841494    IEMOP_MNEMONIC2(FIXED, SBB, sbb, AL, Ib, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    1385     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_sbb_u8);
     1495    IEMOP_BODY_BINARY_AL_Ib(sbb, 0);
    13861496}
    13871497
     
    13951505{
    13961506    IEMOP_MNEMONIC2(FIXED, SBB, sbb, rAX, Iz, DISOPTYPE_HARMLESS, 0);
    1397     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_sbb_u16, iemAImpl_sbb_u32, iemAImpl_sbb_u64, 1);
     1507    IEMOP_BODY_BINARY_rAX_Iz_RW(sbb, 0);
    13981508}
    13991509
     
    14961606    IEMOP_MNEMONIC2(FIXED, AND, and, AL, Ib, DISOPTYPE_HARMLESS, 0);
    14971607    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    1498     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_and_u8);
     1608    IEMOP_BODY_BINARY_AL_Ib(and, 0);
    14991609}
    15001610
     
    15091619    IEMOP_MNEMONIC2(FIXED, AND, and, rAX, Iz, DISOPTYPE_HARMLESS, 0);
    15101620    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    1511     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_and_u16, iemAImpl_and_u32, iemAImpl_and_u64, 1);
     1621    IEMOP_BODY_BINARY_rAX_Iz_RW(and, 0);
    15121622}
    15131623
     
    16141724{
    16151725    IEMOP_MNEMONIC2(FIXED, SUB, sub, AL, Ib, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    1616     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_sub_u8);
     1726    IEMOP_BODY_BINARY_AL_Ib(sub, 0);
    16171727}
    16181728
     
    16261736{
    16271737    IEMOP_MNEMONIC2(FIXED, SUB, sub, rAX, Iz, DISOPTYPE_HARMLESS, 0);
    1628     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_sub_u16, iemAImpl_sub_u32, iemAImpl_sub_u64, 1);
     1738    IEMOP_BODY_BINARY_rAX_Iz_RW(sub, 0);
    16291739}
    16301740
     
    17361846    IEMOP_MNEMONIC2(FIXED, XOR, xor, AL, Ib, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    17371847    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    1738     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_xor_u8);
     1848    IEMOP_BODY_BINARY_AL_Ib(xor, 0);
    17391849}
    17401850
     
    17491859    IEMOP_MNEMONIC2(FIXED, XOR, xor, rAX, Iz, DISOPTYPE_HARMLESS, IEMOPHINT_IGNORES_OP_SIZES);
    17501860    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    1751     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_xor_u16, iemAImpl_xor_u32, iemAImpl_xor_u64, 1);
     1861    IEMOP_BODY_BINARY_rAX_Iz_RW(xor, 0);
    17521862}
    17531863
     
    18771987{
    18781988    IEMOP_MNEMONIC(cmp_al_Ib, "cmp al,Ib");
    1879     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_cmp_u8);
     1989    IEMOP_BODY_BINARY_AL_Ib(cmp, 0);
    18801990}
    18811991
     
    18881998{
    18891999    IEMOP_MNEMONIC(cmp_rAX_Iz, "cmp rAX,Iz");
    1890     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_cmp_u16, iemAImpl_cmp_u32, iemAImpl_cmp_u64, 0);
     2000    IEMOP_BODY_BINARY_rAX_Iz_RO(cmp, 0);
    18912001}
    18922002
     
    41204230 * iemOp_Grp1_Eb_Ib_80.
    41214231 */
    4122 #define IEMOP_BODY_BINARY_Eb_Ib_RW(a_fnNormalU8) \
     4232#define IEMOP_BODY_BINARY_Eb_Ib_RW(a_InsNm, a_fRegNativeArchs, a_fMemNativeArchs) \
    41234233    if (IEM_IS_MODRM_REG_MODE(bRm)) \
    41244234    { \
    41254235        /* register target */ \
     4236        IEM_MC_BEGIN(3, 2, 0, 0); \
    41264237        uint8_t u8Imm; IEM_OPCODE_GET_NEXT_U8(&u8Imm); \
    4127         IEM_MC_BEGIN(3, 0, 0, 0); \
    41284238        IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4129         IEM_MC_ARG(uint8_t *,       pu8Dst,                 0); \
    4130         IEM_MC_ARG_CONST(uint8_t,   u8Src, /*=*/ u8Imm,     1); \
    4131         IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4132         \
    4133         IEM_MC_REF_GREG_U8(pu8Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4134         IEM_MC_REF_EFLAGS(pEFlags); \
    4135         IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU8, pu8Dst, u8Src, pEFlags); \
    4136         \
     4239        IEM_MC_NATIVE_IF(a_fRegNativeArchs) { \
     4240            IEM_MC_LOCAL(uint8_t,       u8Dst); \
     4241            IEM_MC_FETCH_GREG_U8(u8Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4242            IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4243            IEM_MC_FETCH_EFLAGS(uEFlags); \
     4244            IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u8Dst, u8Imm, uEFlags, 8, 8); \
     4245            IEM_MC_STORE_GREG_U8(IEM_GET_MODRM_RM(pVCpu, bRm), u8Dst); \
     4246            IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4247        } IEM_MC_NATIVE_ELSE() { \
     4248            IEM_MC_ARG_CONST(uint8_t,   u8Src, /*=*/ u8Imm,     1); \
     4249            IEM_MC_ARG(uint8_t *,       pu8Dst,                 0); \
     4250            IEM_MC_REF_GREG_U8(pu8Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4251            IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4252            IEM_MC_REF_EFLAGS(pEFlags); \
     4253            IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u8), pu8Dst, u8Src, pEFlags); \
     4254        } IEM_MC_NATIVE_ENDIF(); \
    41374255        IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    41384256        IEM_MC_END(); \
     
    41564274            IEM_MC_MEM_MAP_U8_RW(pu8Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
    41574275            IEM_MC_FETCH_EFLAGS(EFlags); \
    4158             IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU8, pu8Dst, u8Src, pEFlags); \
     4276            IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u8), pu8Dst, u8Src, pEFlags); \
    41594277            \
    41604278            IEM_MC_MEM_COMMIT_AND_UNMAP_RW(bUnmapInfo); \
     
    41654283        else \
    41664284        { \
    4167             (void)0
    4168 
    4169 #define IEMOP_BODY_BINARY_Eb_Ib_LOCKED(a_fnLockedU8) \
    41704285            IEM_MC_BEGIN(3, 3, 0, 0); \
    41714286            IEM_MC_ARG(uint8_t *,       pu8Dst,                 0); \
     
    41814296            IEM_MC_MEM_MAP_U8_ATOMIC(pu8Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
    41824297            IEM_MC_FETCH_EFLAGS(EFlags); \
    4183             IEM_MC_CALL_VOID_AIMPL_3(a_fnLockedU8, pu8Dst, u8Src, pEFlags); \
     4298            IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u8_locked), pu8Dst, u8Src, pEFlags); \
    41844299            \
    41854300            IEM_MC_MEM_COMMIT_AND_UNMAP_ATOMIC(bUnmapInfo); \
     
    41914306    (void)0
    41924307
    4193 #define IEMOP_BODY_BINARY_Eb_Ib_RO(a_fnNormalU8) \
     4308#define IEMOP_BODY_BINARY_Eb_Ib_RO(a_InsNm, a_fNativeArchs) \
    41944309    if (IEM_IS_MODRM_REG_MODE(bRm)) \
    41954310    { \
    41964311        /* register target */ \
     4312        IEM_MC_BEGIN(3, 2, 0, 0); \
    41974313        uint8_t u8Imm; IEM_OPCODE_GET_NEXT_U8(&u8Imm); \
    4198         IEM_MC_BEGIN(3, 0, 0, 0); \
    41994314        IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4200         IEM_MC_ARG(uint8_t *,       pu8Dst,                 0); \
    4201         IEM_MC_ARG_CONST(uint8_t,   u8Src, /*=*/ u8Imm,     1); \
    4202         IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4203         \
    4204         IEM_MC_REF_GREG_U8(pu8Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4205         IEM_MC_REF_EFLAGS(pEFlags); \
    4206         IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU8, pu8Dst, u8Src, pEFlags); \
    4207         \
     4315        IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4316            IEM_MC_LOCAL(uint8_t,       u8Dst); \
     4317            IEM_MC_FETCH_GREG_U8(u8Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4318            IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4319            IEM_MC_FETCH_EFLAGS(uEFlags); \
     4320            IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u8Dst, u8Imm, uEFlags, 8, 8); \
     4321            IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4322        } IEM_MC_NATIVE_ELSE() { \
     4323            IEM_MC_ARG_CONST(uint8_t,   u8Src, /*=*/ u8Imm,     1); \
     4324            IEM_MC_ARG(uint8_t const *, pu8Dst,                 0); \
     4325            IEM_MC_REF_GREG_U8_CONST(pu8Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4326            IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4327            IEM_MC_REF_EFLAGS(pEFlags); \
     4328            IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u8), pu8Dst, u8Src, pEFlags); \
     4329        } IEM_MC_NATIVE_ENDIF(); \
    42084330        IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    42094331        IEM_MC_END(); \
     
    42154337        { \
    42164338            IEM_MC_BEGIN(3, 3, 0, 0); \
    4217             IEM_MC_ARG(uint8_t const *, pu8Dst,                 0); \
    4218             IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
    42194339            IEM_MC_LOCAL(RTGCPTR, GCPtrEffDst); \
    4220             IEM_MC_LOCAL(uint8_t, bUnmapInfo); \
    4221             \
    42224340            IEM_MC_CALC_RM_EFF_ADDR(GCPtrEffDst, bRm, 1); \
    42234341            uint8_t u8Imm; IEM_OPCODE_GET_NEXT_U8(&u8Imm); \
    4224             IEM_MC_ARG_CONST(uint8_t,   u8Src, /*=*/ u8Imm,     1); \
    42254342            IEMOP_HLP_DONE_DECODING(); \
    4226             \
    4227             IEM_MC_MEM_MAP_U8_RO(pu8Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
    4228             IEM_MC_FETCH_EFLAGS(EFlags); \
    4229             IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU8, pu8Dst, u8Src, pEFlags); \
    4230             \
    4231             IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
    4232             IEM_MC_COMMIT_EFLAGS(EFlags); \
     4343            IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4344                IEM_MC_LOCAL(uint8_t,       u8Dst); \
     4345                IEM_MC_FETCH_MEM_U8(u8Dst, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4346                IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4347                IEM_MC_FETCH_EFLAGS(uEFlags); \
     4348                IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u8Dst, u8Imm, uEFlags, 8, 8); \
     4349                IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4350            } IEM_MC_NATIVE_ELSE() { \
     4351                IEM_MC_LOCAL(uint8_t,       bUnmapInfo); \
     4352                IEM_MC_ARG(uint8_t const *, pu8Dst,                 0); \
     4353                IEM_MC_MEM_MAP_U8_RO(pu8Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4354                IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
     4355                IEM_MC_FETCH_EFLAGS(EFlags); \
     4356                IEM_MC_ARG_CONST(uint8_t,   u8Src, /*=*/ u8Imm,     1); \
     4357                IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u8), pu8Dst, u8Src, pEFlags); \
     4358                IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
     4359                IEM_MC_COMMIT_EFLAGS(EFlags); \
     4360            } IEM_MC_NATIVE_ENDIF(); \
    42334361            IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    42344362            IEM_MC_END(); \
     
    42364364        else \
    42374365        { \
    4238             (void)0
    4239 
    4240 #define IEMOP_BODY_BINARY_Eb_Ib_NO_LOCK() \
    42414366            IEMOP_HLP_DONE_DECODING(); \
    42424367            IEMOP_RAISE_INVALID_LOCK_PREFIX_RET(); \
     
    42554380{
    42564381    IEMOP_MNEMONIC(add_Eb_Ib, "add Eb,Ib");
    4257     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_add_u8);
    4258     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_add_u8_locked);
     4382    IEMOP_BODY_BINARY_Eb_Ib_RW(add, RT_ARCH_VAL_AMD64 | RT_ARCH_VAL_ARM64, 0);
    42594383}
    42604384
     
    42684392{
    42694393    IEMOP_MNEMONIC(or_Eb_Ib, "or Eb,Ib");
    4270     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_or_u8);
    4271     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_or_u8_locked);
     4394    IEMOP_BODY_BINARY_Eb_Ib_RW(or, 0, 0);
    42724395}
    42734396
     
    42814404{
    42824405    IEMOP_MNEMONIC(adc_Eb_Ib, "adc Eb,Ib");
    4283     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_adc_u8);
    4284     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_adc_u8_locked);
     4406    IEMOP_BODY_BINARY_Eb_Ib_RW(adc, 0, 0);
    42854407}
    42864408
     
    42944416{
    42954417    IEMOP_MNEMONIC(sbb_Eb_Ib, "sbb Eb,Ib");
    4296     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_sbb_u8);
    4297     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_sbb_u8_locked);
     4418    IEMOP_BODY_BINARY_Eb_Ib_RW(sbb, 0, 0);
    42984419}
    42994420
     
    43074428{
    43084429    IEMOP_MNEMONIC(and_Eb_Ib, "and Eb,Ib");
    4309     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_and_u8);
    4310     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_and_u8_locked);
     4430    IEMOP_BODY_BINARY_Eb_Ib_RW(and, 0, 0);
    43114431}
    43124432
     
    43204440{
    43214441    IEMOP_MNEMONIC(sub_Eb_Ib, "sub Eb,Ib");
    4322     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_sub_u8);
    4323     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_sub_u8_locked);
     4442    IEMOP_BODY_BINARY_Eb_Ib_RW(sub, 0, 0);
    43244443}
    43254444
     
    43334452{
    43344453    IEMOP_MNEMONIC(xor_Eb_Ib, "xor Eb,Ib");
    4335     IEMOP_BODY_BINARY_Eb_Ib_RW(    iemAImpl_xor_u8);
    4336     IEMOP_BODY_BINARY_Eb_Ib_LOCKED(iemAImpl_xor_u8_locked);
     4454    IEMOP_BODY_BINARY_Eb_Ib_RW(xor, 0, 0);
    43374455}
    43384456
     
    43464464{
    43474465    IEMOP_MNEMONIC(cmp_Eb_Ib, "cmp Eb,Ib");
    4348     IEMOP_BODY_BINARY_Eb_Ib_RO(iemAImpl_cmp_u8);
    4349     IEMOP_BODY_BINARY_Eb_Ib_NO_LOCK();
     4466    IEMOP_BODY_BINARY_Eb_Ib_RO(cmp, 0);
    43504467}
    43514468
     
    43754492 * Body for a group 1 binary operator.
    43764493 */
    4377 #define IEMOP_BODY_BINARY_Ev_Iz_RW(a_fnNormalU16, a_fnNormalU32, a_fnNormalU64) \
     4494#define IEMOP_BODY_BINARY_Ev_Iz_RW(a_InsNm, a_fRegNativeArchs, a_fMemNativeArchs) \
    43784495    if (IEM_IS_MODRM_REG_MODE(bRm)) \
    43794496    { \
     
    43834500            case IEMMODE_16BIT: \
    43844501            { \
     4502                IEM_MC_BEGIN(3, 2, 0, 0); \
    43854503                uint16_t u16Imm; IEM_OPCODE_GET_NEXT_U16(&u16Imm); \
    4386                 IEM_MC_BEGIN(3, 0, 0, 0); \
    43874504                IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4388                 IEM_MC_ARG(uint16_t *,      pu16Dst,                0); \
    4389                 IEM_MC_ARG_CONST(uint16_t,  u16Src, /*=*/ u16Imm,   1); \
    4390                 IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4391                 \
    4392                 IEM_MC_REF_GREG_U16(pu16Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4393                 IEM_MC_REF_EFLAGS(pEFlags); \
    4394                 IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU16, pu16Dst, u16Src, pEFlags); \
    4395                 \
     4505                IEM_MC_NATIVE_IF(a_fRegNativeArchs) { \
     4506                    IEM_MC_LOCAL(uint16_t,      u16Dst); \
     4507                    IEM_MC_FETCH_GREG_U16(u16Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4508                    IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4509                    IEM_MC_FETCH_EFLAGS(uEFlags); \
     4510                    IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u16Dst, u16Imm, uEFlags, 16, 16); \
     4511                    IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4512                    IEM_MC_STORE_GREG_U16(IEM_GET_MODRM_RM(pVCpu, bRm), u16Dst); \
     4513                } IEM_MC_NATIVE_ELSE() { \
     4514                    IEM_MC_ARG(uint16_t *,      pu16Dst,                0); \
     4515                    IEM_MC_REF_GREG_U16(pu16Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4516                    IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4517                    IEM_MC_REF_EFLAGS(pEFlags); \
     4518                    IEM_MC_ARG_CONST(uint16_t,  u16Src, /*=*/ u16Imm,   1); \
     4519                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16), pu16Dst, u16Src, pEFlags); \
     4520                } IEM_MC_NATIVE_ENDIF(); \
    43964521                IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    43974522                IEM_MC_END(); \
     
    44014526            case IEMMODE_32BIT: \
    44024527            { \
     4528                IEM_MC_BEGIN(3, 2, IEM_MC_F_MIN_386, 0); \
    44034529                uint32_t u32Imm; IEM_OPCODE_GET_NEXT_U32(&u32Imm); \
    4404                 IEM_MC_BEGIN(3, 0, IEM_MC_F_MIN_386, 0); \
    44054530                IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4406                 IEM_MC_ARG(uint32_t *,      pu32Dst,                0); \
    4407                 IEM_MC_ARG_CONST(uint32_t,  u32Src, /*=*/ u32Imm,   1); \
    4408                 IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4409                 \
    4410                 IEM_MC_REF_GREG_U32(pu32Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4411                 IEM_MC_REF_EFLAGS(pEFlags); \
    4412                 IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU32, pu32Dst, u32Src, pEFlags); \
    4413                 IEM_MC_CLEAR_HIGH_GREG_U64(IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4414                 \
     4531                IEM_MC_NATIVE_IF(a_fRegNativeArchs) { \
     4532                    IEM_MC_LOCAL(uint32_t,      u32Dst); \
     4533                    IEM_MC_FETCH_GREG_U32(u32Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4534                    IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4535                    IEM_MC_FETCH_EFLAGS(uEFlags); \
     4536                    IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u32Dst, u32Imm, uEFlags, 32, 32); \
     4537                    IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4538                    IEM_MC_STORE_GREG_U32(IEM_GET_MODRM_RM(pVCpu, bRm), u32Dst); \
     4539                } IEM_MC_NATIVE_ELSE() { \
     4540                    IEM_MC_ARG(uint32_t *,      pu32Dst,                0); \
     4541                    IEM_MC_REF_GREG_U32(pu32Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4542                    IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4543                    IEM_MC_REF_EFLAGS(pEFlags); \
     4544                    IEM_MC_ARG_CONST(uint32_t,  u32Src, /*=*/ u32Imm,   1); \
     4545                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32), pu32Dst, u32Src, pEFlags); \
     4546                    IEM_MC_CLEAR_HIGH_GREG_U64(IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4547                } IEM_MC_NATIVE_ENDIF(); \
    44154548                IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    44164549                IEM_MC_END(); \
     
    44204553            case IEMMODE_64BIT: \
    44214554            { \
     4555                IEM_MC_BEGIN(3, 2, IEM_MC_F_64BIT, 0); \
    44224556                uint64_t u64Imm; IEM_OPCODE_GET_NEXT_S32_SX_U64(&u64Imm); \
    4423                 IEM_MC_BEGIN(3, 0, IEM_MC_F_64BIT, 0); \
    44244557                IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4425                 IEM_MC_ARG(uint64_t *,      pu64Dst,                0); \
    4426                 IEM_MC_ARG_CONST(uint64_t,  u64Src, /*=*/ u64Imm,   1); \
    4427                 IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4428                 \
    4429                 IEM_MC_REF_GREG_U64(pu64Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4430                 IEM_MC_REF_EFLAGS(pEFlags); \
    4431                 IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU64, pu64Dst, u64Src, pEFlags); \
    4432                 \
     4558                IEM_MC_NATIVE_IF(a_fRegNativeArchs) { \
     4559                    IEM_MC_LOCAL(uint64_t,      u64Dst); \
     4560                    IEM_MC_FETCH_GREG_U64(u64Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4561                    IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4562                    IEM_MC_FETCH_EFLAGS(uEFlags); \
     4563                    IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u64Dst, u64Imm, uEFlags, 64, 32); \
     4564                    IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4565                    IEM_MC_STORE_GREG_U64(IEM_GET_MODRM_RM(pVCpu, bRm), u64Dst); \
     4566                } IEM_MC_NATIVE_ELSE() { \
     4567                    IEM_MC_ARG(uint64_t *,      pu64Dst,                0); \
     4568                    IEM_MC_REF_GREG_U64(pu64Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4569                    IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4570                    IEM_MC_REF_EFLAGS(pEFlags); \
     4571                    IEM_MC_ARG_CONST(uint64_t,  u64Src, /*=*/ u64Imm,   1); \
     4572                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64), pu64Dst, u64Src, pEFlags); \
     4573                } IEM_MC_NATIVE_ENDIF(); \
    44334574                IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    44344575                IEM_MC_END(); \
     
    44624603                    IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
    44634604                    IEM_MC_FETCH_EFLAGS(EFlags); \
    4464                     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU16, pu16Dst, u16Src, pEFlags); \
     4605                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16), pu16Dst, u16Src, pEFlags); \
    44654606                    \
    44664607                    IEM_MC_MEM_COMMIT_AND_UNMAP_RW(bUnmapInfo); \
     
    44874628                    IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags,    EFlags,     2); \
    44884629                    IEM_MC_FETCH_EFLAGS(EFlags); \
    4489                     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU32, pu32Dst, u32Src, pEFlags); \
     4630                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32), pu32Dst, u32Src, pEFlags); \
    44904631                    \
    44914632                    IEM_MC_MEM_COMMIT_AND_UNMAP_RW(bUnmapInfo); \
     
    45134654                    IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
    45144655                    IEM_MC_FETCH_EFLAGS(EFlags); \
    4515                     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU64, pu64Dst, u64Src, pEFlags); \
     4656                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64), pu64Dst, u64Src, pEFlags); \
    45164657                    \
    45174658                    IEM_MC_MEM_COMMIT_AND_UNMAP_RW(bUnmapInfo); \
     
    45274668        else \
    45284669        { \
    4529             (void)0
    4530 /* This must be a separate macro due to parsing restrictions in IEMAllInstPython.py. */
    4531 #define IEMOP_BODY_BINARY_Ev_Iz_LOCKED(a_fnLockedU16, a_fnLockedU32, a_fnLockedU64) \
    45324670            switch (pVCpu->iem.s.enmEffOpSize) \
    45334671            { \
     
    45484686                    IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
    45494687                    IEM_MC_FETCH_EFLAGS(EFlags); \
    4550                     IEM_MC_CALL_VOID_AIMPL_3(a_fnLockedU16, pu16Dst, u16Src, pEFlags); \
     4688                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16_locked), pu16Dst, u16Src, pEFlags); \
    45514689                    \
    45524690                    IEM_MC_MEM_COMMIT_AND_UNMAP_ATOMIC(bUnmapInfo); \
     
    45734711                    IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
    45744712                    IEM_MC_FETCH_EFLAGS(EFlags); \
    4575                     IEM_MC_CALL_VOID_AIMPL_3(a_fnLockedU32, pu32Dst, u32Src, pEFlags); \
     4713                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32_locked), pu32Dst, u32Src, pEFlags); \
    45764714                    \
    45774715                    IEM_MC_MEM_COMMIT_AND_UNMAP_ATOMIC(bUnmapInfo); \
     
    45984736                    IEM_MC_ARG_LOCAL_EFLAGS(    pEFlags, EFlags,        2); \
    45994737                    IEM_MC_FETCH_EFLAGS(EFlags); \
    4600                     IEM_MC_CALL_VOID_AIMPL_3(a_fnLockedU64, pu64Dst, u64Src, pEFlags); \
     4738                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64_locked), pu64Dst, u64Src, pEFlags); \
    46014739                    \
    46024740                    IEM_MC_MEM_COMMIT_AND_UNMAP_ATOMIC(bUnmapInfo); \
     
    46144752
    46154753/* read-only version */
    4616 #define IEMOP_BODY_BINARY_Ev_Iz_RO(a_fnNormalU16, a_fnNormalU32, a_fnNormalU64) \
     4754#define IEMOP_BODY_BINARY_Ev_Iz_RO(a_InsNm, a_fNativeArchs) \
    46174755    if (IEM_IS_MODRM_REG_MODE(bRm)) \
    46184756    { \
     
    46224760            case IEMMODE_16BIT: \
    46234761            { \
     4762                IEM_MC_BEGIN(3, 2, 0, 0); \
    46244763                uint16_t u16Imm; IEM_OPCODE_GET_NEXT_U16(&u16Imm); \
    4625                 IEM_MC_BEGIN(3, 0, 0, 0); \
    46264764                IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4627                 IEM_MC_ARG(uint16_t *,      pu16Dst,                0); \
    4628                 IEM_MC_ARG_CONST(uint16_t,  u16Src, /*=*/ u16Imm,   1); \
    4629                 IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4630                 \
    4631                 IEM_MC_REF_GREG_U16(pu16Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4632                 IEM_MC_REF_EFLAGS(pEFlags); \
    4633                 IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU16, pu16Dst, u16Src, pEFlags); \
    4634                 \
     4765                IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4766                    IEM_MC_LOCAL(uint16_t,      u16Dst); \
     4767                    IEM_MC_FETCH_GREG_U16(u16Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4768                    IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4769                    IEM_MC_FETCH_EFLAGS(uEFlags); \
     4770                    IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u16Dst, u16Imm, uEFlags, 16, 16); \
     4771                    IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4772                } IEM_MC_NATIVE_ELSE() { \
     4773                    IEM_MC_ARG(uint16_t const *,pu16Dst,                0); \
     4774                    IEM_MC_REF_GREG_U16_CONST(pu16Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4775                    IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4776                    IEM_MC_REF_EFLAGS(pEFlags); \
     4777                    IEM_MC_ARG_CONST(uint16_t,  u16Src, /*=*/ u16Imm,   1); \
     4778                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16), pu16Dst, u16Src, pEFlags); \
     4779                } IEM_MC_NATIVE_ENDIF(); \
    46354780                IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    46364781                IEM_MC_END(); \
     
    46404785            case IEMMODE_32BIT: \
    46414786            { \
     4787                IEM_MC_BEGIN(3, 2, IEM_MC_F_MIN_386, 0); \
    46424788                uint32_t u32Imm; IEM_OPCODE_GET_NEXT_U32(&u32Imm); \
    4643                 IEM_MC_BEGIN(3, 0, IEM_MC_F_MIN_386, 0); \
    46444789                IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4645                 IEM_MC_ARG(uint32_t *,      pu32Dst,                0); \
    4646                 IEM_MC_ARG_CONST(uint32_t,  u32Src, /*=*/ u32Imm,   1); \
    4647                 IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4648                 \
    4649                 IEM_MC_REF_GREG_U32(pu32Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4650                 IEM_MC_REF_EFLAGS(pEFlags); \
    4651                 IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU32, pu32Dst, u32Src, pEFlags); \
    4652                 \
     4790                IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4791                    IEM_MC_LOCAL(uint32_t,      u32Dst); \
     4792                    IEM_MC_FETCH_GREG_U32(u32Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4793                    IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4794                    IEM_MC_FETCH_EFLAGS(uEFlags); \
     4795                    IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u32Dst, u32Imm, uEFlags, 32, 32); \
     4796                    IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4797                } IEM_MC_NATIVE_ELSE() { \
     4798                    IEM_MC_ARG(uint32_t const *,pu32Dst,                0); \
     4799                    IEM_MC_REF_GREG_U32_CONST (pu32Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4800                    IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4801                    IEM_MC_REF_EFLAGS(pEFlags); \
     4802                    IEM_MC_ARG_CONST(uint32_t,  u32Src, /*=*/ u32Imm,   1); \
     4803                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32), pu32Dst, u32Src, pEFlags); \
     4804                } IEM_MC_NATIVE_ENDIF(); \
    46534805                IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    46544806                IEM_MC_END(); \
     
    46584810            case IEMMODE_64BIT: \
    46594811            { \
     4812                IEM_MC_BEGIN(3, 2, IEM_MC_F_64BIT, 0); \
    46604813                uint64_t u64Imm; IEM_OPCODE_GET_NEXT_S32_SX_U64(&u64Imm); \
    4661                 IEM_MC_BEGIN(3, 0, IEM_MC_F_64BIT, 0); \
    46624814                IEMOP_HLP_DONE_DECODING_NO_LOCK_PREFIX(); \
    4663                 IEM_MC_ARG(uint64_t *,      pu64Dst,                0); \
    4664                 IEM_MC_ARG_CONST(uint64_t,  u64Src, /*=*/ u64Imm,   1); \
    4665                 IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
    4666                 \
    4667                 IEM_MC_REF_GREG_U64(pu64Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
    4668                 IEM_MC_REF_EFLAGS(pEFlags); \
    4669                 IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU64, pu64Dst, u64Src, pEFlags); \
    4670                 \
     4815                IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4816                    IEM_MC_LOCAL(uint64_t,      u64Dst); \
     4817                    IEM_MC_FETCH_GREG_U64(u64Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4818                    IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4819                    IEM_MC_FETCH_EFLAGS(uEFlags); \
     4820                    IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u64Dst, u64Imm, uEFlags, 64, 32); \
     4821                    IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4822                } IEM_MC_NATIVE_ELSE() { \
     4823                    IEM_MC_ARG(uint64_t const *,pu64Dst,                0); \
     4824                    IEM_MC_REF_GREG_U64_CONST(pu64Dst, IEM_GET_MODRM_RM(pVCpu, bRm)); \
     4825                    IEM_MC_ARG(uint32_t *,      pEFlags,                2); \
     4826                    IEM_MC_REF_EFLAGS(pEFlags); \
     4827                    IEM_MC_ARG_CONST(uint64_t,  u64Src, /*=*/ u64Imm,   1); \
     4828                    IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64), pu64Dst, u64Src, pEFlags); \
     4829                } IEM_MC_NATIVE_ENDIF(); \
    46714830                IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    46724831                IEM_MC_END(); \
     
    46894848                    IEM_MC_LOCAL(RTGCPTR, GCPtrEffDst); \
    46904849                    IEM_MC_CALC_RM_EFF_ADDR(GCPtrEffDst, bRm, 2); \
    4691                     \
    46924850                    uint16_t u16Imm; IEM_OPCODE_GET_NEXT_U16(&u16Imm); \
    46934851                    IEMOP_HLP_DONE_DECODING(); \
    4694                     \
    4695                     IEM_MC_LOCAL(uint8_t, bUnmapInfo); \
    4696                     IEM_MC_ARG(uint16_t const *, pu16Dst,               0); \
    4697                     IEM_MC_MEM_MAP_U16_RO(pu16Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
    4698                     \
    4699                     IEM_MC_ARG_CONST(uint16_t,   u16Src,  u16Imm,       1); \
    4700                     IEM_MC_ARG_LOCAL_EFLAGS(     pEFlags, EFlags,       2); \
    4701                     IEM_MC_FETCH_EFLAGS(EFlags); \
    4702                     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU16, pu16Dst, u16Src, pEFlags); \
    4703                     \
    4704                     IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
    4705                     IEM_MC_COMMIT_EFLAGS(EFlags); \
     4852                    IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4853                        IEM_MC_LOCAL(uint16_t,      u16Dst); \
     4854                        IEM_MC_FETCH_MEM_U16(u16Dst, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4855                        IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4856                        IEM_MC_FETCH_EFLAGS(uEFlags); \
     4857                        IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u16Dst, u16Imm, uEFlags, 16, 16); \
     4858                        IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4859                    } IEM_MC_NATIVE_ELSE() { \
     4860                        IEM_MC_LOCAL(uint8_t,        bUnmapInfo); \
     4861                        IEM_MC_ARG(uint16_t const *, pu16Dst,               0); \
     4862                        IEM_MC_MEM_MAP_U16_RO(pu16Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4863                        IEM_MC_ARG_LOCAL_EFLAGS(     pEFlags, EFlags,       2); \
     4864                        IEM_MC_FETCH_EFLAGS(EFlags); \
     4865                        IEM_MC_ARG_CONST(uint16_t,   u16Src,  u16Imm,       1); \
     4866                        IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u16), pu16Dst, u16Src, pEFlags); \
     4867                        IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
     4868                        IEM_MC_COMMIT_EFLAGS(EFlags); \
     4869                    } IEM_MC_NATIVE_ENDIF(); \
    47064870                    IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    47074871                    IEM_MC_END(); \
     
    47144878                    IEM_MC_LOCAL(RTGCPTR, GCPtrEffDst); \
    47154879                    IEM_MC_CALC_RM_EFF_ADDR(GCPtrEffDst, bRm, 4); \
    4716                     \
    47174880                    uint32_t u32Imm; IEM_OPCODE_GET_NEXT_U32(&u32Imm); \
    47184881                    IEMOP_HLP_DONE_DECODING(); \
    4719                     \
    4720                     IEM_MC_LOCAL(uint8_t,        bUnmapInfo); \
    4721                     IEM_MC_ARG(uint32_t const *, pu32Dst,               0); \
    4722                     IEM_MC_MEM_MAP_U32_RO(pu32Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
    4723                     \
    4724                     IEM_MC_ARG_CONST(uint32_t,   u32Src,  u32Imm,       1); \
    4725                     IEM_MC_ARG_LOCAL_EFLAGS(     pEFlags, EFlags,       2); \
    4726                     IEM_MC_FETCH_EFLAGS(EFlags); \
    4727                     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU32, pu32Dst, u32Src, pEFlags); \
    4728                     \
    4729                     IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
    4730                     IEM_MC_COMMIT_EFLAGS(EFlags); \
     4882                    IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4883                        IEM_MC_LOCAL(uint32_t,      u32Dst); \
     4884                        IEM_MC_FETCH_MEM_U32(u32Dst, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4885                        IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4886                        IEM_MC_FETCH_EFLAGS(uEFlags); \
     4887                        IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u32Dst, u32Imm, uEFlags, 32, 32); \
     4888                        IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4889                    } IEM_MC_NATIVE_ELSE() { \
     4890                        IEM_MC_LOCAL(uint8_t,        bUnmapInfo); \
     4891                        IEM_MC_ARG(uint32_t const *, pu32Dst,               0); \
     4892                        IEM_MC_MEM_MAP_U32_RO(pu32Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4893                        IEM_MC_ARG_LOCAL_EFLAGS(     pEFlags, EFlags,       2); \
     4894                        IEM_MC_FETCH_EFLAGS(EFlags); \
     4895                        IEM_MC_ARG_CONST(uint32_t,   u32Src,  u32Imm,       1); \
     4896                        IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u32), pu32Dst, u32Src, pEFlags); \
     4897                        IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
     4898                        IEM_MC_COMMIT_EFLAGS(EFlags); \
     4899                    } IEM_MC_NATIVE_ENDIF(); \
    47314900                    IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    47324901                    IEM_MC_END(); \
     
    47394908                    IEM_MC_LOCAL(RTGCPTR, GCPtrEffDst); \
    47404909                    IEM_MC_CALC_RM_EFF_ADDR(GCPtrEffDst, bRm, 4); \
    4741                     \
    47424910                    uint64_t u64Imm; IEM_OPCODE_GET_NEXT_S32_SX_U64(&u64Imm); \
    47434911                    IEMOP_HLP_DONE_DECODING(); \
    4744                     \
    4745                     IEM_MC_LOCAL(uint8_t,        bUnmapInfo); \
    4746                     IEM_MC_ARG(uint64_t const *, pu64Dst,               0); \
    4747                     IEM_MC_MEM_MAP_U64_RO(pu64Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
    4748                     \
    4749                     IEM_MC_ARG_CONST(uint64_t,   u64Src,  u64Imm,       1); \
    4750                     IEM_MC_ARG_LOCAL_EFLAGS(     pEFlags, EFlags,       2); \
    4751                     IEM_MC_FETCH_EFLAGS(EFlags); \
    4752                     IEM_MC_CALL_VOID_AIMPL_3(a_fnNormalU64, pu64Dst, u64Src, pEFlags); \
    4753                     \
    4754                     IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
    4755                     IEM_MC_COMMIT_EFLAGS(EFlags); \
     4912                    IEM_MC_NATIVE_IF(a_fNativeArchs) { \
     4913                        IEM_MC_LOCAL(uint64_t,      u64Dst); \
     4914                        IEM_MC_FETCH_MEM_U64(u64Dst, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4915                        IEM_MC_LOCAL(uint32_t,      uEFlags); \
     4916                        IEM_MC_FETCH_EFLAGS(uEFlags); \
     4917                        IEM_MC_NATIVE_EMIT_5(RT_CONCAT3(iemNativeEmit_,a_InsNm,_r_i_efl), u64Dst, u64Imm, uEFlags, 64, 32); \
     4918                        IEM_MC_COMMIT_EFLAGS(uEFlags); \
     4919                    } IEM_MC_NATIVE_ELSE() { \
     4920                        IEM_MC_LOCAL(uint8_t,        bUnmapInfo); \
     4921                        IEM_MC_ARG(uint64_t const *, pu64Dst,               0); \
     4922                        IEM_MC_MEM_MAP_U64_RO(pu64Dst, bUnmapInfo, pVCpu->iem.s.iEffSeg, GCPtrEffDst); \
     4923                        IEM_MC_ARG_LOCAL_EFLAGS(     pEFlags, EFlags,       2); \
     4924                        IEM_MC_FETCH_EFLAGS(EFlags); \
     4925                        IEM_MC_ARG_CONST(uint64_t,   u64Src,  u64Imm,       1); \
     4926                        IEM_MC_CALL_VOID_AIMPL_3(RT_CONCAT3(iemAImpl_,a_InsNm,_u64), pu64Dst, u64Src, pEFlags); \
     4927                        IEM_MC_MEM_COMMIT_AND_UNMAP_RO(bUnmapInfo); \
     4928                        IEM_MC_COMMIT_EFLAGS(EFlags); \
     4929                    } IEM_MC_NATIVE_ENDIF(); \
    47564930                    IEM_MC_ADVANCE_RIP_AND_FINISH(); \
    47574931                    IEM_MC_END(); \
     
    47794953{
    47804954    IEMOP_MNEMONIC(add_Ev_Iz, "add Ev,Iz");
    4781     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_add_u16,        iemAImpl_add_u32,        iemAImpl_add_u64);
    4782     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_add_u16_locked, iemAImpl_add_u32_locked, iemAImpl_add_u64_locked);
     4955    IEMOP_BODY_BINARY_Ev_Iz_RW(add, RT_ARCH_VAL_AMD64 | RT_ARCH_VAL_ARM64, 0);
    47834956}
    47844957
     
    47924965{
    47934966    IEMOP_MNEMONIC(or_Ev_Iz, "or Ev,Iz");
    4794     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_or_u16,        iemAImpl_or_u32,        iemAImpl_or_u64);
    4795     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_or_u16_locked, iemAImpl_or_u32_locked, iemAImpl_or_u64_locked);
     4967    IEMOP_BODY_BINARY_Ev_Iz_RW(or, 0, 0);
    47964968}
    47974969
     
    48054977{
    48064978    IEMOP_MNEMONIC(adc_Ev_Iz, "adc Ev,Iz");
    4807     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_adc_u16,        iemAImpl_adc_u32,        iemAImpl_adc_u64);
    4808     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_adc_u16_locked, iemAImpl_adc_u32_locked, iemAImpl_adc_u64_locked);
     4979    IEMOP_BODY_BINARY_Ev_Iz_RW(adc, 0, 0);
    48094980}
    48104981
     
    48184989{
    48194990    IEMOP_MNEMONIC(sbb_Ev_Iz, "sbb Ev,Iz");
    4820     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_sbb_u16,        iemAImpl_sbb_u32,        iemAImpl_sbb_u64);
    4821     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_sbb_u16_locked, iemAImpl_sbb_u32_locked, iemAImpl_sbb_u64_locked);
     4991    IEMOP_BODY_BINARY_Ev_Iz_RW(sbb, 0, 0);
    48224992}
    48234993
     
    48315001{
    48325002    IEMOP_MNEMONIC(and_Ev_Iz, "and Ev,Iz");
    4833     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_and_u16,        iemAImpl_and_u32,        iemAImpl_and_u64);
    4834     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_and_u16_locked, iemAImpl_and_u32_locked, iemAImpl_and_u64_locked);
     5003    IEMOP_BODY_BINARY_Ev_Iz_RW(and, 0, 0);
    48355004}
    48365005
     
    48445013{
    48455014    IEMOP_MNEMONIC(sub_Ev_Iz, "sub Ev,Iz");
    4846     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_sub_u16,        iemAImpl_sub_u32,        iemAImpl_sub_u64);
    4847     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_sub_u16_locked, iemAImpl_sub_u32_locked, iemAImpl_sub_u64_locked);
     5015    IEMOP_BODY_BINARY_Ev_Iz_RW(sub, 0, 0);
    48485016}
    48495017
     
    48575025{
    48585026    IEMOP_MNEMONIC(xor_Ev_Iz, "xor Ev,Iz");
    4859     IEMOP_BODY_BINARY_Ev_Iz_RW(    iemAImpl_xor_u16,        iemAImpl_xor_u32,        iemAImpl_xor_u64);
    4860     IEMOP_BODY_BINARY_Ev_Iz_LOCKED(iemAImpl_xor_u16_locked, iemAImpl_xor_u32_locked, iemAImpl_xor_u64_locked);
     5027    IEMOP_BODY_BINARY_Ev_Iz_RW(xor, 0, 0);
    48615028}
    48625029
     
    48705037{
    48715038    IEMOP_MNEMONIC(cmp_Ev_Iz, "cmp Ev,Iz");
    4872     IEMOP_BODY_BINARY_Ev_Iz_RO(iemAImpl_cmp_u16, iemAImpl_cmp_u32, iemAImpl_cmp_u64);
     5039    IEMOP_BODY_BINARY_Ev_Iz_RO(cmp, 0);
    48735040}
    48745041
     
    75707737    IEMOP_MNEMONIC(test_al_Ib, "test al,Ib");
    75717738    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    7572     IEMOP_BODY_BINARY_AL_Ib(iemAImpl_test_u8);
     7739    IEMOP_BODY_BINARY_AL_Ib(test, 0);
    75737740}
    75747741
     
    75827749    IEMOP_MNEMONIC(test_rAX_Iz, "test rAX,Iz");
    75837750    IEMOP_VERIFICATION_UNDEFINED_EFLAGS(X86_EFL_AF);
    7584     IEMOP_BODY_BINARY_rAX_Iz(iemAImpl_test_u16, iemAImpl_test_u32, iemAImpl_test_u64, 0);
     7751    IEMOP_BODY_BINARY_rAX_Iz_RO(test, 0);
    75857752}
    75867753
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8veLiveness.cpp

    r103667 r103739  
    439439#define IEM_MC_STORE_GREG_U8_CONST_THREADED(a_iGRegEx, a_u8Value)   IEM_LIVENESS_GPR_MODIFY(a_iGRegEx & 15)
    440440#define IEM_MC_REF_GREG_U8_THREADED(a_pu8Dst, a_iGRegEx)            IEM_LIVENESS_GPR_MODIFY(a_iGRegEx & 15)
     441#define IEM_MC_REF_GREG_U8_CONST_THREADED(a_pu8Dst, a_iGRegEx)      IEM_LIVENESS_GPR_INPUT(a_iGRegEx & 15)
    441442#define IEM_MC_ADD_GREG_U8_TO_LOCAL_THREADED(a_u8Value, a_iGRegEx)  IEM_LIVENESS_GPR_INPUT(a_iGRegEx & 15)
    442443#define IEM_MC_AND_GREG_U8_THREADED(a_iGRegEx, a_u8Value)           IEM_LIVENESS_GPR_MODIFY(a_iGRegEx & 15)
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8vePython.py

    r103613 r103739  
    118118    'IEM_MC_FETCH_GREG_U8_ZX_U64_THREADED':                              (None, False, False, True,  ),
    119119    'IEM_MC_REF_GREG_U8_THREADED':                                       (None, True,  True,  True,  ),
     120    'IEM_MC_REF_GREG_U8_CONST_THREADED':                                 (None, True,  True,  True,  ),
    120121
    121122    'IEM_MC_REF_EFLAGS_EX':                                              (None, False, False, True,  ),
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8veRecompiler.cpp

    r103729 r103739  
    1185511855    off = iemNativeEmitRefGregU8(pReNative, off, a_pu8Dst, a_iGRegEx, false /*fConst*/)
    1185611856
    11857 #define IEM_MC_REF_GREG_U8_CONST_THREADED(a_pu8Dst, a_iGReg) \
     11857#define IEM_MC_REF_GREG_U8_CONST_THREADED(a_pu8Dst, a_iGRegEx) \
    1185811858    off = iemNativeEmitRefGregU8(pReNative, off, a_pu8Dst, a_iGRegEx, true /*fConst*/)
    1185911859
  • trunk/src/VBox/VMM/VMMAll/IEMAllThrdFuncs.cpp

    r103233 r103739  
    418418/** Variant of IEM_MC_REF_GREG_U8 with extended (20) register index. */
    419419#define IEM_MC_REF_GREG_U8_THREADED(a_pu8Dst, a_iGRegEx) \
     420    (a_pu8Dst) = iemGRegRefU8Ex(pVCpu, (a_iGRegEx))
     421#undef IEM_MC_REF_GREG_U8
     422
     423/** Variant of IEM_MC_REF_GREG_U8_CONST with extended (20) register index. */
     424#define IEM_MC_REF_GREG_U8_CONST_THREADED(a_pu8Dst, a_iGRegEx) \
    420425    (a_pu8Dst) = iemGRegRefU8Ex(pVCpu, (a_iGRegEx))
    421426#undef IEM_MC_REF_GREG_U8
  • trunk/src/VBox/VMM/VMMAll/target-x86/IEMAllN8veEmit-x86.h

    r103693 r103739  
    114114}
    115115
     116
     117/**
     118 * Emits one of three opcodes with an immediate.
     119 *
     120 * These are expected to be a /idxRegReg form.
     121 */
     122DECL_FORCE_INLINE(uint32_t)
     123iemNativeEmitAmd64OneByteModRmInstrRIEx(PIEMNATIVEINSTR pCodeBuf, uint32_t off, uint8_t bOpcode8, uint8_t bOpcodeOtherImm8,
     124                                        uint8_t bOpcodeOther, uint8_t cOpBits, uint8_t cImmBits, uint8_t idxRegReg,
     125                                        uint8_t idxRegRm, uint64_t uImmOp)
     126{
     127    Assert(idxRegReg < 8); Assert(idxRegRm < 16);
     128    if (cImmBits == 8 || uImmOp <= (uint64_t)0x7f)
     129    {
     130        switch (cOpBits)
     131        {
     132            case 16:
     133                pCodeBuf[off++] = X86_OP_PRF_SIZE_OP;
     134                RT_FALL_THRU();
     135            case 32:
     136                if (idxRegRm >= 8)
     137                    pCodeBuf[off++] = X86_OP_REX_B;
     138                pCodeBuf[off++] = bOpcodeOtherImm8;
     139                break;
     140
     141            default: AssertFailed(); RT_FALL_THRU();
     142            case 64:
     143                pCodeBuf[off++] = X86_OP_REX_W | (idxRegRm >= 8 ? X86_OP_REX_B : 0);
     144                pCodeBuf[off++] = bOpcodeOtherImm8;
     145                break;
     146
     147            case 8:
     148                if (idxRegRm >= 8)
     149                    pCodeBuf[off++] = X86_OP_REX_B;
     150                else if (idxRegRm >= 4)
     151                    pCodeBuf[off++] = X86_OP_REX;
     152                pCodeBuf[off++] = bOpcode8;
     153                break;
     154        }
     155        pCodeBuf[off++] = X86_MODRM_MAKE(X86_MOD_REG, idxRegReg, idxRegRm & 7);
     156        pCodeBuf[off++] = (uint8_t)uImmOp;
     157    }
     158    else
     159    {
     160        switch (cOpBits)
     161        {
     162            case 32:
     163                if (idxRegRm >= 8)
     164                    pCodeBuf[off++] = X86_OP_REX_B;
     165                break;
     166
     167            default: AssertFailed(); RT_FALL_THRU();
     168            case 64:
     169                pCodeBuf[off++] = X86_OP_REX_W | (idxRegRm >= 8 ? X86_OP_REX_B : 0);
     170                break;
     171
     172            case 16:
     173                pCodeBuf[off++] = X86_OP_PRF_SIZE_OP;
     174                if (idxRegRm >= 8)
     175                    pCodeBuf[off++] = X86_OP_REX_B;
     176                pCodeBuf[off++] = bOpcodeOther;
     177                pCodeBuf[off++] = X86_MODRM_MAKE(X86_MOD_REG, idxRegReg, idxRegRm & 7);
     178                pCodeBuf[off++] = RT_BYTE1(uImmOp);
     179                pCodeBuf[off++] = RT_BYTE2(uImmOp);
     180                Assert(cImmBits == 16);
     181                return off;
     182        }
     183        pCodeBuf[off++] = bOpcodeOther;
     184        pCodeBuf[off++] = X86_MODRM_MAKE(X86_MOD_REG, idxRegReg, idxRegRm & 7);
     185        pCodeBuf[off++] = RT_BYTE1(uImmOp);
     186        pCodeBuf[off++] = RT_BYTE2(uImmOp);
     187        pCodeBuf[off++] = RT_BYTE3(uImmOp);
     188        pCodeBuf[off++] = RT_BYTE4(uImmOp);
     189        Assert(cImmBits == 32);
     190    }
     191    return off;
     192}
     193
    116194#endif /* RT_ARCH_AMD64 */
    117195
     
    215293#ifndef RT_ARCH_AMD64
    216294                                 , uint8_t cOpBits, uint8_t idxRegResult, uint8_t idxRegDstIn, uint8_t idxRegSrc
    217                                  , bool fInvertCarry
     295                                 , bool fInvertCarry, uint64_t uImmSrc
    218296#endif
    219297                                 )
     
    286364            pCodeBuf[off++] = Armv8A64MkInstrBfxil(idxRegEfl, idxRegResult, cOpBits, 1, false /*f64Bit*/);
    287365
    288             /* The overflow flag is more work. See IEM_EFL_UPDATE_STATUS_BITS_FOR_ARITHMETIC. */
    289             if (fInvertCarry) /* sbb:  ~((a_uDst) ^ ~(a_uSrcOf)) ->  (a_uDst) ^  (a_uSrcOf); HACK ALERT: fInvertCarry == sbb */
    290                 pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg,  idxRegDstIn, idxRegSrc,  false);
    291             else              /* adc:  ~((a_uDst) ^ (a_uSrcOf))  ->  (a_uDst) ^ ~(a_uSrcOf) */
    292                 pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg,  idxRegDstIn, idxRegSrc,  false);
    293             pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg2,   idxRegDstIn, idxRegResult, false); /*  (a_uDst) ^ (a_uResult) */
    294             pCodeBuf[off++] = Armv8A64MkInstrAnd(idxTmpReg,    idxTmpReg,   idxTmpReg2,   false /*f64Bit*/);
     366            /* The overflow flag is more work. See IEM_EFL_UPDATE_STATUS_BITS_FOR_ARITHMETIC.
     367               It is a bit simpler when the right side is constant. */
     368            if (idxRegSrc != UINT8_MAX)
     369            {
     370                if (fInvertCarry) /* sbb:  ~((a_uDst) ^ ~(a_uSrcOf)) ->  (a_uDst) ^  (a_uSrcOf); HACK ALERT: fInvertCarry == sbb */
     371                    pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg,  idxRegDstIn, idxRegSrc,  false);
     372                else              /* adc:  ~((a_uDst) ^ (a_uSrcOf))  ->  (a_uDst) ^ ~(a_uSrcOf) */
     373                    pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg,  idxRegDstIn, idxRegSrc,  false);
     374                pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg2,   idxRegDstIn, idxRegResult, false); /* (a_uDst) ^ (a_uResult) */
     375                pCodeBuf[off++] = Armv8A64MkInstrAnd(idxTmpReg,    idxTmpReg,   idxTmpReg2,   false /*f64Bit*/);
     376            }
     377            else if (uImmSrc & RT_BIT_32(cOpBits - 1))
     378            {
     379                if (fInvertCarry) /* sbb w/ top right 1: ~a_uDst & a_uResult ; HACK ALERT: fInvertCarry == sbb */
     380                    pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg, idxRegResult, idxRegDstIn, false);
     381                else              /* adc w/ top right 1: a_uDst & ~a_uResult */
     382                    pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg, idxRegDstIn, idxRegResult, false);
     383            }
     384            else
     385            {
     386                if (fInvertCarry) /* sbb w/ top right 0: a_uDst & ~a_uResult ; HACK ALERT: fInvertCarry == sbb */
     387                    pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg, idxRegDstIn, idxRegResult, false);
     388                else              /* adc w/ top right 0: ~a_uDst & a_uResult */
     389                    pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg, idxRegResult, idxRegDstIn, false);
     390            }
    295391            pCodeBuf[off++] = Armv8A64MkInstrLsrImm(idxTmpReg, idxTmpReg,   cOpBits - 1,  false /*f64Bit*/);
    296392            pCodeBuf[off++] = Armv8A64MkInstrBfi(idxRegEfl,    idxTmpReg,   X86_EFL_OF_BIT, 1);
     
    309405        pCodeBuf[off++] = Armv8A64MkInstrBfi(idxRegEfl, idxTmpReg, X86_EFL_PF_BIT, 1,  false /*f64Bit*/);
    310406
    311         /* Calculate auxilary carry/borrow.  This is related to 8-bit BCD.*/
    312         pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg, idxRegDstIn, idxRegSrc, false /*f64Bit*/);
    313         pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg, idxTmpReg, idxRegResult, false /*f64Bit*/);
     407        /* Calculate auxilary carry/borrow.  This is related to 8-bit BCD.
     408           General formula: ((uint32_t)(a_uResult)  ^ (uint32_t)(a_uSrc) ^ (uint32_t)(a_uDst)) & X86_EFL_AF;
     409               S D R
     410               0 0 0 -> 0;  \
     411               0 0 1 -> 1;   \  regular
     412               0 1 0 -> 1;   /    xor R, D
     413               0 1 1 -> 0;  /
     414               1 0 0 -> 1;  \
     415               1 0 1 -> 0;   \  invert one of the two
     416               1 1 0 -> 0;   /    xor not(R), D
     417               1 1 1 -> 1;  /
     418           a_uSrc[bit 4]=0: ((uint32_t)(a_uResult)  ^ (uint32_t)(a_uDst)) & X86_EFL_AF;
     419           a_uSrc[bit 4]=1: ((uint32_t)~(a_uResult) ^ (uint32_t)(a_uDst)) & X86_EFL_AF;
     420           */
     421
     422        if (idxRegSrc != UINT8_MAX)
     423        {
     424            pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg, idxRegDstIn, idxRegSrc, false /*f64Bit*/);
     425            pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg, idxTmpReg, idxRegResult, false /*f64Bit*/);
     426        }
     427        else if (uImmSrc & X86_EFL_AF)
     428            pCodeBuf[off++] = Armv8A64MkInstrEon(idxTmpReg, idxRegDstIn, idxRegResult, false /*f64Bit*/);
     429        else
     430            pCodeBuf[off++] = Armv8A64MkInstrEor(idxTmpReg, idxRegDstIn, idxRegResult, false /*f64Bit*/);
    314431        pCodeBuf[off++] = Armv8A64MkInstrLsrImm(idxTmpReg, idxTmpReg, X86_EFL_AF_BIT, false /*f64Bit*/);
    315432        pCodeBuf[off++] = Armv8A64MkInstrBfi(idxRegEfl, idxTmpReg, X86_EFL_AF_BIT, 1,  false /*f64Bit*/);
     
    359476    off = iemNativeEmitEFlagsForLogical(pReNative, off, idxVarEfl, cOpBits, idxRegDst);
    360477    iemNativeVarRegisterRelease(pReNative, idxVarDst);
     478    return off;
     479}
     480
     481
     482/**
     483 * The AND instruction with immediate value as right operand.
     484 */
     485DECL_INLINE_THROW(uint32_t)
     486iemNativeEmit_and_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     487                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     488{
     489    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
    361490    return off;
    362491}
     
    408537
    409538/**
     539 * The TEST instruction with immediate value as right operand.
     540 */
     541DECL_INLINE_THROW(uint32_t)
     542iemNativeEmit_test_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     543                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     544{
     545    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
     546    return off;
     547}
     548
     549
     550/**
    410551 * The OR instruction will clear OF, CF and AF (latter is undefined) and
    411552 * set the other flags according to the result.
     
    441582
    442583/**
     584 * The OR instruction with immediate value as right operand.
     585 */
     586DECL_INLINE_THROW(uint32_t)
     587iemNativeEmit_or_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     588                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     589{
     590    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
     591    return off;
     592}
     593
     594
     595/**
    443596 * The XOR instruction will clear OF, CF and AF (latter is undefined) and
    444597 * set the other flags according to the result.
     
    469622    off = iemNativeEmitEFlagsForLogical(pReNative, off, idxVarEfl, cOpBits, idxRegDst);
    470623    iemNativeVarRegisterRelease(pReNative, idxVarDst);
     624    return off;
     625}
     626
     627
     628/**
     629 * The XOR instruction with immediate value as right operand.
     630 */
     631DECL_INLINE_THROW(uint32_t)
     632iemNativeEmit_xor_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     633                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     634{
     635    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
    471636    return off;
    472637}
     
    519684
    520685    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, idxVarEfl, UINT8_MAX, cOpBits, idxRegDst,
    521                                            idxRegDstIn, idxRegSrc, false /*fInvertCarry*/);
     686                                           idxRegDstIn, idxRegSrc, false /*fInvertCarry*/, 0);
    522687
    523688    iemNativeRegFreeTmp(pReNative, idxRegDstIn);
    524689    iemNativeVarRegisterRelease(pReNative, idxVarSrc);
    525690    iemNativeVarRegisterRelease(pReNative, idxVarDst);
     691
     692#else
     693# error "port me"
     694#endif
     695    return off;
     696}
     697
     698
     699/**
     700 * The ADD instruction with immediate value as right operand.
     701 */
     702DECL_INLINE_THROW(uint32_t)
     703iemNativeEmit_add_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     704                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     705{
     706    uint8_t const idxRegDst = iemNativeVarRegisterAcquire(pReNative, idxVarDst, &off, true /*fInitialized*/);
     707
     708#ifdef RT_ARCH_AMD64
     709    /* On AMD64 we just use the correctly sized ADD instruction to get the right EFLAGS.SF value. */
     710    PIEMNATIVEINSTR const pCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 8);
     711    off = iemNativeEmitAmd64OneByteModRmInstrRIEx(pCodeBuf, off, 0x80, 0x83, 0x81, cOpBits, cImmBits, 0, idxRegDst, uImmOp);
     712    IEMNATIVE_ASSERT_INSTR_BUF_ENSURE(pReNative, off);
     713
     714    iemNativeVarRegisterRelease(pReNative, idxVarDst);
     715
     716    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, idxVarEfl, UINT8_MAX);
     717
     718#elif defined(RT_ARCH_ARM64)
     719    /* On ARM64 we'll need the two input operands as well as the result in order
     720       to calculate the right flags, even if we use ADDS and translates NZCV into
     721       OF, CF, ZF and SF. */
     722    uint8_t const   idxRegDstIn  = iemNativeRegAllocTmp(pReNative, &off);
     723    PIEMNATIVEINSTR pCodeBuf     = iemNativeInstrBufEnsure(pReNative, off, 8);
     724    off = iemNativeEmitLoadGprFromGprEx(pCodeBuf, off, idxRegDstIn, idxRegDst);
     725    if (cOpBits >= 32)
     726    {
     727        if (uImmOp <= 0xfffU)
     728            pCodeBuf[off++] = Armv8A64MkInstrAddUImm12(idxRegDst, idxRegDst, uImmOp, cOpBits > 32 /*f64Bit*/, true /*fSetFlags*/);
     729        else if (uImmOp <= 0xfff000U && !(uImmOp & 0xfff))
     730            pCodeBuf[off++] = Armv8A64MkInstrAddUImm12(idxRegDst, idxRegDst, uImmOp, cOpBits > 32 /*f64Bit*/, true /*fSetFlags*/,
     731                                                       true /*fShift12*/);
     732        else
     733        {
     734            uint8_t const idxTmpImmReg = iemNativeRegAllocTmpImm(pReNative, &off, uImmOp);
     735            pCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 1);
     736            pCodeBuf[off++] = Armv8A64MkInstrAddReg(idxRegDst, idxRegDst, idxTmpImmReg, cOpBits > 32 /*f64Bit*/, true /*fSetFlags*/);
     737            iemNativeRegFreeTmpImm(pReNative, idxTmpImmReg);
     738        }
     739    }
     740    else
     741    {
     742        /* Shift the operands up so we can perform a 32-bit operation and get all four flags. */
     743        uint32_t const cShift = 32 - cOpBits;
     744        uint8_t const idxTmpImmReg = iemNativeRegAllocTmpImm(pReNative, &off, uImmOp << cShift);
     745        pCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 2);
     746        pCodeBuf[off++] = Armv8A64MkInstrAddReg(idxRegDst, idxTmpImmReg, idxRegDstIn, false /*f64Bit*/, true /*fSetFlags*/, cShift);
     747        pCodeBuf[off++] = Armv8A64MkInstrLsrImm(idxRegDst, idxRegDst, cShift, false /*f64Bit*/);
     748        cOpBits = 32;
     749        iemNativeRegFreeTmpImm(pReNative, idxTmpImmReg);
     750    }
     751    IEMNATIVE_ASSERT_INSTR_BUF_ENSURE(pReNative, off);
     752
     753    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, idxVarEfl, UINT8_MAX, cOpBits, idxRegDst,
     754                                           idxRegDstIn, UINT8_MAX, false /*fInvertCarry*/, uImmOp);
     755
     756    iemNativeRegFreeTmp(pReNative, idxRegDstIn);
     757    iemNativeVarRegisterRelease(pReNative, idxVarDst);
     758    RT_NOREF(cImmBits);
    526759
    527760#else
     
    581814
    582815    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, UINT8_MAX, idxRegEfl, cOpBits, idxRegDst,
    583                                            idxRegDstIn, idxRegSrc, false /*fInvertCarry*/);
     816                                           idxRegDstIn, idxRegSrc, false /*fInvertCarry*/, 0);
    584817
    585818    iemNativeRegFreeTmp(pReNative, idxRegDstIn);
     
    593826#endif
    594827    iemNativeVarRegisterRelease(pReNative, idxVarEfl);
     828    return off;
     829}
     830
     831
     832/**
     833 * The ADC instruction with immediate value as right operand.
     834 */
     835DECL_INLINE_THROW(uint32_t)
     836iemNativeEmit_adc_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     837                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     838{
     839    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
    595840    return off;
    596841}
     
    643888
    644889    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, idxVarEfl, UINT8_MAX, cOpBits, idxRegDst,
    645                                            idxRegDstIn, idxRegSrc, true /*fInvertCarry*/);
     890                                           idxRegDstIn, idxRegSrc, true /*fInvertCarry*/, 0);
    646891
    647892    iemNativeRegFreeTmp(pReNative, idxRegDstIn);
     
    652897# error "port me"
    653898#endif
     899    return off;
     900}
     901
     902
     903/**
     904 * The SUB instruction with immediate value as right operand.
     905 */
     906DECL_INLINE_THROW(uint32_t)
     907iemNativeEmit_sub_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     908                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     909{
     910    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
    654911    return off;
    655912}
     
    698955
    699956    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, idxVarEfl, UINT8_MAX, cOpBits, idxRegResult,
    700                                            idxRegDst, idxRegSrc, true /*fInvertCarry*/);
     957                                           idxRegDst, idxRegSrc, true /*fInvertCarry*/, 0);
    701958
    702959    iemNativeRegFreeTmp(pReNative, idxRegResult);
     
    707964# error "port me"
    708965#endif
     966    return off;
     967}
     968
     969
     970/**
     971 * The CMP instruction with immediate value as right operand.
     972 */
     973DECL_INLINE_THROW(uint32_t)
     974iemNativeEmit_cmp_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     975                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     976{
     977    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
    709978    return off;
    710979}
     
    7621031
    7631032    off = iemNativeEmitEFlagsForArithmetic(pReNative, off, UINT8_MAX, idxRegEfl, cOpBits, idxRegDst,
    764                                            idxRegDstIn, idxRegSrc, true /*fInvertCarry*/);
     1033                                           idxRegDstIn, idxRegSrc, true /*fInvertCarry*/, 0);
    7651034
    7661035    iemNativeRegFreeTmp(pReNative, idxRegDstIn);
     
    7741043#endif
    7751044    iemNativeVarRegisterRelease(pReNative, idxVarEfl);
     1045    return off;
     1046}
     1047
     1048
     1049/**
     1050 * The SBB instruction with immediate value as right operand.
     1051 */
     1052DECL_INLINE_THROW(uint32_t)
     1053iemNativeEmit_sbb_r_i_efl(PIEMRECOMPILERSTATE pReNative, uint32_t off,
     1054                          uint8_t idxVarDst, uint64_t uImmOp, uint8_t idxVarEfl, uint8_t cOpBits, uint8_t cImmBits)
     1055{
     1056    RT_NOREF(pReNative, off, idxVarDst, uImmOp, idxVarEfl, cOpBits, cImmBits);
    7761057    return off;
    7771058}
  • trunk/src/VBox/VMM/VMMR3/IEMR3.cpp

    r103737 r103739  
    918918#if defined(VBOX_WITH_IEM_RECOMPILER) && !defined(VBOX_VMM_TARGET_ARMV8)
    919919/**
    920  * @callback_method_impl{FNDBGFINFOARGVINT, dtlb}
     920 * @callback_method_impl{FNDBGFINFOARGVINT, tb}
    921921 */
    922922static DECLCALLBACK(void) iemR3InfoTb(PVM pVM, PCDBGFINFOHLP pHlp, int cArgs, char **papszArgs)
  • trunk/src/VBox/VMM/include/IEMN8veRecompiler.h

    r103728 r103739  
    4040/** @def IEMNATIVE_WITH_TB_DEBUG_INFO
    4141 * Enables generating internal debug info for better TB disassembly dumping. */
    42 #if defined(DEBUG) || defined(DOXYGEN_RUNNING)
     42#if defined(DEBUG) || defined(DOXYGEN_RUNNING) || 1
    4343# define IEMNATIVE_WITH_TB_DEBUG_INFO
    4444#endif
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