Changeset 103404 in vbox for trunk/src/VBox/VMM/include/IEMN8veRecompilerEmit.h
- Timestamp:
- Feb 17, 2024 1:53:09 AM (13 months ago)
- svn:sync-xref-src-repo-rev:
- 161725
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/VMM/include/IEMN8veRecompilerEmit.h ¶
r102876 r103404 1036 1036 1037 1037 /** 1038 * Emits code for incrementing an unsigned 32-bit statistics counter in VMCPU. 1039 * 1040 * @note The two temp registers are not required for AMD64. ARM64 always 1041 * requires the first, and the 2nd is needed if the offset cannot be 1042 * encoded as an immediate. 1043 */ 1044 DECL_FORCE_INLINE(uint32_t) 1045 iemNativeEmitIncU32CounterInVCpuEx(PIEMNATIVEINSTR pCodeBuf, uint32_t off, uint8_t idxTmp1, uint8_t idxTmp2, uint32_t offVCpu) 1046 { 1047 Assert(!(offVCpu & 3)); /* ASSUME correctly aligned member. */ 1048 #ifdef RT_ARCH_AMD64 1049 /* inc dword [pVCpu + offVCpu] */ 1050 pCodeBuf[off++] = 0xff; 1051 off = iemNativeEmitGprByVCpuDisp(pCodeBuf, off, 0, offVCpu); 1052 RT_NOREF(idxTmp1, idxTmp2); 1053 1054 #elif defined(RT_ARCH_ARM64) 1055 /* Determine how we're to access pVCpu first. */ 1056 uint32_t const cbData = sizeof(uint32_t); 1057 if (offVCpu < (unsigned)(_4K * cbData)) 1058 { 1059 /* Use the unsigned variant of ldr Wt, [<Xn|SP>, #off]. */ 1060 pCodeBuf[off++] = Armv8A64MkInstrStLdRUOff(kArmv8A64InstrLdStType_Ld_Dword, idxTmp1, 1061 IEMNATIVE_REG_FIXED_PVMCPU, offVCpu / cbData); 1062 pCodeBuf[off++] = Armv8A64MkInstrAddUImm12(idxTmp1, idxTmp1, 1); 1063 pCodeBuf[off++] = Armv8A64MkInstrStLdRUOff(kArmv8A64InstrLdStType_St_Dword, idxTmp1, 1064 IEMNATIVE_REG_FIXED_PVMCPU, offVCpu / cbData); 1065 } 1066 else if (offVCpu - RT_UOFFSETOF(VMCPU, cpum.GstCtx) < (unsigned)(_4K * cbData)) 1067 { 1068 pCodeBuf[off++] = Armv8A64MkInstrStLdRUOff(kArmv8A64InstrLdStType_Ld_Dword, idxTmp1, IEMNATIVE_REG_FIXED_PCPUMCTX, 1069 (offVCpu - RT_UOFFSETOF(VMCPU, cpum.GstCtx)) / cbData); 1070 pCodeBuf[off++] = Armv8A64MkInstrAddUImm12(idxTmp1, idxTmp1, 1); 1071 pCodeBuf[off++] = Armv8A64MkInstrStLdRUOff(kArmv8A64InstrLdStType_St_Dword, idxTmp1, IEMNATIVE_REG_FIXED_PCPUMCTX, 1072 (offVCpu - RT_UOFFSETOF(VMCPU, cpum.GstCtx)) / cbData); 1073 } 1074 else 1075 { 1076 /* The offset is too large, so we must load it into a register and use 1077 ldr Wt, [<Xn|SP>, (<Wm>|<Xm>)]. We'll try use the 'LSL, #2' feature 1078 of the instruction if that'll reduce the constant to 16-bits. */ 1079 if (offVCpu / cbData < (unsigned)UINT16_MAX) 1080 { 1081 pCodeBuf[off++] = Armv8A64MkInstrMovZ(idxTmp2, offVCpu / cbData); 1082 pCodeBuf[off++] = Armv8A64MkInstrStLdRegIdx(kArmv8A64InstrLdStType_Ld_Word, idxTmp1, IEMNATIVE_REG_FIXED_PVMCPU, 1083 idxTmp2, kArmv8A64InstrLdStExtend_Lsl, true /*fShifted(2)*/); 1084 pCodeBuf[off++] = Armv8A64MkInstrAddUImm12(idxTmp1, idxTmp1, 1); 1085 pCodeBuf[off++] = Armv8A64MkInstrStLdRegIdx(kArmv8A64InstrLdStType_St_Word, idxTmp1, IEMNATIVE_REG_FIXED_PVMCPU, 1086 idxTmp2, kArmv8A64InstrLdStExtend_Lsl, true /*fShifted(2)*/); 1087 } 1088 else 1089 { 1090 off = iemNativeEmitLoadGprImmEx(pCodeBuf, off, idxTmp2, offVCpu); 1091 pCodeBuf[off++] = Armv8A64MkInstrStLdRegIdx(kArmv8A64InstrLdStType_Ld_Word, idxTmp1, IEMNATIVE_REG_FIXED_PVMCPU, idxTmp2); 1092 pCodeBuf[off++] = Armv8A64MkInstrAddUImm12(idxTmp1, idxTmp1, 1); 1093 pCodeBuf[off++] = Armv8A64MkInstrStLdRegIdx(kArmv8A64InstrLdStType_St_Word, idxTmp1, IEMNATIVE_REG_FIXED_PVMCPU, idxTmp2); 1094 } 1095 } 1096 1097 #else 1098 # error "port me" 1099 #endif 1100 return off; 1101 } 1102 1103 1104 /** 1105 * Emits code for incrementing an unsigned 32-bit statistics counter in VMCPU. 1106 * 1107 * @note The two temp registers are not required for AMD64. ARM64 always 1108 * requires the first, and the 2nd is needed if the offset cannot be 1109 * encoded as an immediate. 1110 */ 1111 DECL_FORCE_INLINE(uint32_t) 1112 iemNativeEmitIncU32CounterInVCpu(PIEMRECOMPILERSTATE pReNative, uint32_t off, uint8_t idxTmp1, uint8_t idxTmp2, uint32_t offVCpu) 1113 { 1114 #ifdef RT_ARCH_AMD64 1115 off = iemNativeEmitIncU32CounterInVCpuEx(iemNativeInstrBufEnsure(pReNative, off, 6), off, idxTmp1, idxTmp2, offVCpu); 1116 #elif defined(RT_ARCH_ARM64) 1117 off = iemNativeEmitIncU32CounterInVCpuEx(iemNativeInstrBufEnsure(pReNative, off, 4+3), off, idxTmp1, idxTmp2, offVCpu); 1118 #else 1119 # error "port me" 1120 #endif 1121 IEMNATIVE_ASSERT_INSTR_BUF_ENSURE(pReNative, off); 1122 return off; 1123 } 1124 1125 1126 /** 1038 1127 * Emits a gprdst = gprsrc load. 1039 1128 */
Note:
See TracChangeset
for help on using the changeset viewer.