Changeset 103894 in vbox for trunk/src/VBox/VMM/include/IEMN8veRecompilerEmit.h
- Timestamp:
- Mar 18, 2024 1:48:31 PM (11 months ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/VMM/include/IEMN8veRecompilerEmit.h
r103892 r103894 2106 2106 2107 2107 2108 #ifdef IEMNATIVE_WITH_SIMD_REG_ALLOCATOR 2109 /** 2110 * Emits a 128-bit vector register load instruction with an BP relative source address. 2111 */ 2112 DECL_FORCE_INLINE_THROW(uint32_t) 2113 iemNativeEmitLoadVecRegByBpU128(PIEMRECOMPILERSTATE pReNative, uint32_t off, uint8_t iVecRegDst, int32_t offDisp) 2114 { 2115 #ifdef RT_ARCH_AMD64 2116 uint8_t *pbCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 9); 2117 2118 /* movdqu reg128, mem128 */ 2119 pbCodeBuf[off++] = 0xf3; 2120 if (iVecRegDst >= 8) 2121 pbCodeBuf[off++] = X86_OP_REX_R; 2122 pbCodeBuf[off++] = 0x0f; 2123 pbCodeBuf[off++] = 0x6f; 2124 return iemNativeEmitGprByBpDisp(pbCodeBuf, off, iVecRegDst, offDisp, pReNative); 2125 #elif defined(RT_ARCH_ARM64) 2126 return iemNativeEmitGprByBpLdSt(pReNative, off, iVecRegDst, offDisp, kArmv8A64InstrLdStType_Ld_Vr_128, sizeof(RTUINT128U)); 2127 #else 2128 # error "port me" 2129 #endif 2130 } 2131 2132 2133 /** 2134 * Emits a 256-bit vector register load instruction with an BP relative source address. 2135 */ 2136 DECL_FORCE_INLINE_THROW(uint32_t) 2137 iemNativeEmitLoadVecRegByBpU256(PIEMRECOMPILERSTATE pReNative, uint32_t off, uint8_t iVecRegDst, int32_t offDisp) 2138 { 2139 #ifdef RT_ARCH_AMD64 2140 uint8_t *pbCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 8); 2141 2142 /* vmovdqu reg256, mem256 */ 2143 pbCodeBuf[off++] = X86_OP_VEX2; 2144 pbCodeBuf[off++] = X86_OP_VEX2_BYTE1_MAKE_NO_VVVV(iVecRegDst >= 8, true /*f256BitAvx*/, X86_OP_VEX2_BYTE1_P_0F3H); 2145 pbCodeBuf[off++] = 0x6f; 2146 return iemNativeEmitGprByBpDisp(pbCodeBuf, off, iVecRegDst, offDisp, pReNative); 2147 #elif defined(RT_ARCH_ARM64) 2148 /* ASSUMES two consecutive vector registers for the 256-bit value. */ 2149 Assert(!(iVecRegDst & 0x1)); 2150 off = iemNativeEmitGprByBpLdSt(pReNative, off, iVecRegDst, offDisp, kArmv8A64InstrLdStType_Ld_Vr_128, sizeof(RTUINT128U)); 2151 return iemNativeEmitGprByBpLdSt(pReNative, off, iVecRegDst + 1, offDisp + sizeof(RTUINT128U), kArmv8A64InstrLdStType_Ld_Vr_128, sizeof(RTUINT128U)); 2152 #else 2153 # error "port me" 2154 #endif 2155 } 2156 2157 #endif 2158 2159 2108 2160 /** 2109 2161 * Emits a load effective address to a GRP with an BP relative source address. … … 2251 2303 return iemNativeEmitStoreGprByBp(pReNative, off, offDisp, IEMNATIVE_REG_FIXED_TMP0); 2252 2304 } 2305 2306 2307 #ifdef IEMNATIVE_WITH_SIMD_REG_ALLOCATOR 2308 /** 2309 * Emits a 128-bit vector register store with an BP relative destination address. 2310 * 2311 * @note May trash IEMNATIVE_REG_FIXED_TMP0. 2312 */ 2313 DECL_INLINE_THROW(uint32_t) 2314 iemNativeEmitStoreVecRegByBpU128(PIEMRECOMPILERSTATE pReNative, uint32_t off, int32_t offDisp, uint8_t iVecRegSrc) 2315 { 2316 #ifdef RT_ARCH_AMD64 2317 /* movdqu [rbp + offDisp], vecsrc */ 2318 uint8_t *pbCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 7); 2319 pbCodeBuf[off++] = 0xf3; 2320 if (iVecRegSrc >= 8) 2321 pbCodeBuf[off++] = X86_OP_REX_R; 2322 pbCodeBuf[off++] = 0x0f; 2323 pbCodeBuf[off++] = 0x7f; 2324 return iemNativeEmitGprByBpDisp(pbCodeBuf, off, iVecRegSrc, offDisp, pReNative); 2325 2326 #elif defined(RT_ARCH_ARM64) 2327 if (offDisp >= 0 && offDisp < 4096 * 8 && !((uint32_t)offDisp & 7)) 2328 { 2329 /* str w/ unsigned imm12 (scaled) */ 2330 uint32_t *pu32CodeBuf = iemNativeInstrBufEnsure(pReNative, off, 1); 2331 pu32CodeBuf[off++] = Armv8A64MkInstrStLdRUOff(kArmv8A64InstrLdStType_St_Vr_128, iVecRegSrc, 2332 ARMV8_A64_REG_BP, (uint32_t)offDisp / 8); 2333 } 2334 else if (offDisp >= -256 && offDisp <= 256) 2335 { 2336 /* stur w/ signed imm9 (unscaled) */ 2337 uint32_t *pu32CodeBuf = iemNativeInstrBufEnsure(pReNative, off, 1); 2338 pu32CodeBuf[off++] = Armv8A64MkInstrSturLdur(kArmv8A64InstrLdStType_St_Vr_128, iVecRegSrc, ARMV8_A64_REG_BP, offDisp); 2339 } 2340 else if ((uint32_t)-offDisp < (unsigned)_4K) 2341 { 2342 /* Use temporary indexing register w/ sub uimm12. */ 2343 uint32_t *pu32CodeBuf = iemNativeInstrBufEnsure(pReNative, off, 2); 2344 pu32CodeBuf[off++] = Armv8A64MkInstrAddSubUImm12(true /*fSub*/, IEMNATIVE_REG_FIXED_TMP0, 2345 ARMV8_A64_REG_BP, (uint32_t)-offDisp); 2346 pu32CodeBuf[off++] = Armv8A64MkInstrStLdRUOff(kArmv8A64InstrLdStType_St_Vr_128, iVecRegSrc, IEMNATIVE_REG_FIXED_TMP0, 0); 2347 } 2348 else 2349 { 2350 /* Use temporary indexing register. */ 2351 off = iemNativeEmitLoadGprImm64(pReNative, off, IEMNATIVE_REG_FIXED_TMP0, (uint32_t)offDisp); 2352 uint32_t *pu32CodeBuf = iemNativeInstrBufEnsure(pReNative, off, 1); 2353 pu32CodeBuf[off++] = Armv8A64MkInstrStLdRegIdx(kArmv8A64InstrLdStType_St_Vr_128, iVecRegSrc, ARMV8_A64_REG_BP, 2354 IEMNATIVE_REG_FIXED_TMP0, kArmv8A64InstrLdStExtend_Sxtw); 2355 } 2356 IEMNATIVE_ASSERT_INSTR_BUF_ENSURE(pReNative, off); 2357 return off; 2358 2359 #else 2360 # error "Port me!" 2361 #endif 2362 } 2363 2364 2365 /** 2366 * Emits a 256-bit vector register store with an BP relative destination address. 2367 * 2368 * @note May trash IEMNATIVE_REG_FIXED_TMP0. 2369 */ 2370 DECL_INLINE_THROW(uint32_t) 2371 iemNativeEmitStoreVecRegByBpU256(PIEMRECOMPILERSTATE pReNative, uint32_t off, int32_t offDisp, uint8_t iVecRegSrc) 2372 { 2373 #ifdef RT_ARCH_AMD64 2374 uint8_t *pbCodeBuf = iemNativeInstrBufEnsure(pReNative, off, 8); 2375 2376 /* vmovdqu mem256, reg256 */ 2377 pbCodeBuf[off++] = X86_OP_VEX2; 2378 pbCodeBuf[off++] = X86_OP_VEX2_BYTE1_MAKE_NO_VVVV(iVecRegSrc >= 8, true /*f256BitAvx*/, X86_OP_VEX2_BYTE1_P_0F3H); 2379 pbCodeBuf[off++] = 0x7f; 2380 return iemNativeEmitGprByBpDisp(pbCodeBuf, off, iVecRegSrc, offDisp, pReNative); 2381 #elif defined(RT_ARCH_ARM64) 2382 Assert(!(iVecRegSrc & 0x1)); 2383 off = iemNativeEmitStoreVecRegByBpU128(pReNative, off, offDisp, iVecRegSrc); 2384 return iemNativeEmitStoreVecRegByBpU128(pReNative, off, offDisp + sizeof(RTUINT128U), iVecRegSrc + 1); 2385 #else 2386 # error "Port me!" 2387 #endif 2388 } 2389 #endif 2253 2390 2254 2391 #if defined(RT_ARCH_ARM64) … … 7155 7292 7156 7293 /** 7157 * Emits code to load the variable address into an argument G RP.7294 * Emits code to load the variable address into an argument GPR. 7158 7295 * 7159 7296 * This only works for uninitialized and stack variables. … … 7173 7310 7174 7311 uint8_t const idxRegVar = pVar->idxReg; 7312 #ifdef IEMNATIVE_WITH_SIMD_REG_ALLOCATOR 7313 if ( idxRegVar != UINT8_MAX 7314 && pVar->fSimdReg) 7315 { 7316 Assert(idxRegVar < RT_ELEMENTS(pReNative->Core.aHstSimdRegs)); 7317 Assert(pVar->cbVar == sizeof(RTUINT128U) || pVar->cbVar == sizeof(RTUINT256U)); 7318 7319 if (pVar->cbVar == sizeof(RTUINT128U)) 7320 off = iemNativeEmitStoreVecRegByBpU128(pReNative, off, offBpDisp, idxRegVar); 7321 else 7322 off = iemNativeEmitStoreVecRegByBpU256(pReNative, off, offBpDisp, idxRegVar); 7323 7324 iemNativeSimdRegFreeVar(pReNative, idxRegVar, fFlushShadows); 7325 Assert(pVar->idxReg == UINT8_MAX); 7326 } 7327 else 7328 #endif 7175 7329 if (idxRegVar < RT_ELEMENTS(pReNative->Core.aHstRegs)) 7176 7330 { … … 7400 7554 { 7401 7555 #ifdef RT_ARCH_AMD64 7402 off = iemNativeEmitSimdLoadVecRegFromVCpu LowU128Ex(iemNativeInstrBufEnsure(pReNative, off, 10), off, iVecReg, offVCpu);7556 off = iemNativeEmitSimdLoadVecRegFromVCpuHighU128Ex(iemNativeInstrBufEnsure(pReNative, off, 10), off, iVecReg, offVCpu); 7403 7557 #elif defined(RT_ARCH_ARM64) 7404 7558 /* ASSUMES that there are two adjacent 128-bit registers available for the 256-bit value. */ 7405 7559 Assert(!(iVecReg & 0x1)); 7406 off = iemNativeEmitSimdLoadVecRegFromVCpu LowU128Ex(iemNativeInstrBufEnsure(pReNative, off, 1), off, iVecReg + 1, offVCpu);7560 off = iemNativeEmitSimdLoadVecRegFromVCpuHighU128Ex(iemNativeInstrBufEnsure(pReNative, off, 1), off, iVecReg + 1, offVCpu); 7407 7561 #else 7408 7562 # error "port me"
Note:
See TracChangeset
for help on using the changeset viewer.