Changeset 106319 in vbox for trunk/src/VBox/VMM
- Timestamp:
- Oct 15, 2024 8:50:24 AM (6 weeks ago)
- Location:
- trunk/src/VBox/VMM
- Files:
-
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/VMM/VMMAll/IEMAllN8veRecompFuncs.h
r106315 r106319 2057 2057 uint8_t const idxPcRegOld = iemNativeRegAllocTmpForGuestReg(pReNative, &off, kIemNativeGstReg_Pc, 2058 2058 kIemNativeGstRegUse_Calculation, true /*fNoVolatileRegs*/); 2059 uint8_t const idxPcRegNew = iemNativeRegAllocTmp (pReNative, &off, false /*fPreferVolatile*/);2059 uint8_t const idxPcRegNew = iemNativeRegAllocTmpPreferNonVolatile(pReNative, &off); 2060 2060 2061 2061 /* Calculate the new RIP. */ … … 2127 2127 uint8_t const idxPcRegOld = iemNativeRegAllocTmpForGuestReg(pReNative, &off, kIemNativeGstReg_Pc, 2128 2128 kIemNativeGstRegUse_ReadOnly, true /*fNoVolatileRegs*/); 2129 uint8_t const idxPcRegNew = iemNativeRegAllocTmp (pReNative, &off, false /*fPreferVolatile*/);2129 uint8_t const idxPcRegNew = iemNativeRegAllocTmpPreferNonVolatile(pReNative, &off); 2130 2130 2131 2131 /* Update the EIP to get the return address. */ … … 2194 2194 uint8_t const idxPcRegOld = iemNativeRegAllocTmpForGuestReg(pReNative, &off, kIemNativeGstReg_Pc, 2195 2195 kIemNativeGstRegUse_ReadOnly, true /*fNoVolatileRegs*/); 2196 uint8_t const idxPcRegNew = iemNativeRegAllocTmp (pReNative, &off, false /*fPreferVolatile*/);2196 uint8_t const idxPcRegNew = iemNativeRegAllocTmpPreferNonVolatile(pReNative, &off); 2197 2197 2198 2198 /* Update the RIP to get the return address. */ … … 9797 9797 } 9798 9798 9799 uint8_t const idxRegTmp = iemNativeRegAllocTmp (pReNative, &off, false /*fPreferVolatile*/);9799 uint8_t const idxRegTmp = iemNativeRegAllocTmpPreferNonVolatile(pReNative, &off); 9800 9800 uint8_t const idxRegMxCsr = iemNativeRegAllocTmpForGuestReg(pReNative, &off, kIemNativeGstReg_MxCsr, 9801 9801 kIemNativeGstRegUse_ReadOnly); … … 9829 9829 9830 9830 # elif defined(RT_ARCH_ARM64) 9831 uint8_t const idxRegTmp = iemNativeRegAllocTmp (pReNative, &off, false /*fPreferVolatile*/);9831 uint8_t const idxRegTmp = iemNativeRegAllocTmpPreferNonVolatile(pReNative, &off); 9832 9832 9833 9833 /* Need to save the host floating point control register the first time, clear FPSR. */ -
trunk/src/VBox/VMM/VMMAll/IEMAllN8veRecompiler.cpp
r106315 r106319 3472 3472 * This will be update if we need to move a variable from 3473 3473 * register to stack in order to satisfy the request. 3474 * @param fPreferVolatile Whether to prefer volatile over non-volatile3474 * @param a_fPreferVolatile Whether to prefer volatile over non-volatile 3475 3475 * registers (@c true, default) or the other way around 3476 3476 * (@c false, for iemNativeRegAllocTmpForGuestReg()). … … 3478 3478 * @note Must not modify the host status flags! 3479 3479 */ 3480 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmp(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, bool fPreferVolatile /*= true*/) 3480 template<bool const a_fPreferVolatile> 3481 DECL_FORCE_INLINE_THROW(uint8_t) iemNativeRegAllocTmpInt(PIEMRECOMPILERSTATE pReNative, uint32_t *poff) 3481 3482 { 3482 3483 /* … … 3489 3490 if (fRegs) 3490 3491 { 3491 if ( fPreferVolatile)3492 if (a_fPreferVolatile) 3492 3493 idxReg = (uint8_t)ASMBitFirstSetU32( fRegs & IEMNATIVE_CALL_VOLATILE_GREG_MASK 3493 3494 ? fRegs & IEMNATIVE_CALL_VOLATILE_GREG_MASK : fRegs) - 1; … … 3501 3502 else 3502 3503 { 3503 idxReg = iemNativeRegAllocFindFree(pReNative, poff, fPreferVolatile);3504 idxReg = iemNativeRegAllocFindFree(pReNative, poff, a_fPreferVolatile); 3504 3505 AssertStmt(idxReg != UINT8_MAX, IEMNATIVE_DO_LONGJMP(pReNative, VERR_IEM_REG_ALLOCATOR_NO_FREE_TMP)); 3505 3506 Log12(("iemNativeRegAllocTmp: %s (slow)\n", g_apszIemNativeHstRegNames[idxReg])); 3506 3507 } 3507 3508 return iemNativeRegMarkAllocated(pReNative, idxReg, kIemNativeWhat_Tmp); 3509 } 3510 3511 3512 /** See iemNativeRegAllocTmpInt for details. */ 3513 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmp(PIEMRECOMPILERSTATE pReNative, uint32_t *poff) 3514 { 3515 return iemNativeRegAllocTmpInt<true>(pReNative, poff); 3516 } 3517 3518 3519 /** See iemNativeRegAllocTmpInt for details. */ 3520 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpPreferNonVolatile(PIEMRECOMPILERSTATE pReNative, uint32_t *poff) 3521 { 3522 return iemNativeRegAllocTmpInt<false>(pReNative, poff); 3508 3523 } 3509 3524 … … 3524 3539 * (@c false, for iemNativeRegAllocTmpForGuestReg()). 3525 3540 */ 3526 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpEx(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask, 3527 bool fPreferVolatile /*= true*/)3541 template<bool const a_fPreferVolatile> 3542 DECL_FORCE_INLINE_THROW(uint8_t) iemNativeRegAllocTmpExInt(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask) 3528 3543 { 3529 3544 Assert(!(fRegMask & ~IEMNATIVE_HST_GREG_MASK)); … … 3540 3555 if (fRegs) 3541 3556 { 3542 if (fPreferVolatile)3557 if RT_CONSTEXPR_IF(a_fPreferVolatile) 3543 3558 idxReg = (uint8_t)ASMBitFirstSetU32( fRegs & IEMNATIVE_CALL_VOLATILE_GREG_MASK 3544 3559 ? fRegs & IEMNATIVE_CALL_VOLATILE_GREG_MASK : fRegs) - 1; … … 3548 3563 Assert(pReNative->Core.aHstRegs[idxReg].fGstRegShadows == 0); 3549 3564 Assert(!(pReNative->Core.bmHstRegsWithGstShadow & RT_BIT_32(idxReg))); 3550 Log12(("iemNativeRegAllocTmpEx : %s\n", g_apszIemNativeHstRegNames[idxReg]));3565 Log12(("iemNativeRegAllocTmpExInt: %s\n", g_apszIemNativeHstRegNames[idxReg])); 3551 3566 } 3552 3567 else 3553 3568 { 3554 idxReg = iemNativeRegAllocFindFree(pReNative, poff, fPreferVolatile, fRegMask);3569 idxReg = iemNativeRegAllocFindFree(pReNative, poff, a_fPreferVolatile, fRegMask); 3555 3570 AssertStmt(idxReg != UINT8_MAX, IEMNATIVE_DO_LONGJMP(pReNative, VERR_IEM_REG_ALLOCATOR_NO_FREE_TMP)); 3556 Log12(("iemNativeRegAllocTmpEx: %s (slow)\n", g_apszIemNativeHstRegNames[idxReg])); 3571 Log12(("iemNativeRegAllocTmpExInt: %s (slow)\n", g_apszIemNativeHstRegNames[idxReg])); 3572 } 3573 return iemNativeRegMarkAllocated(pReNative, idxReg, kIemNativeWhat_Tmp); 3574 } 3575 3576 3577 /** See iemNativeRegAllocTmpExInt for details. */ 3578 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpEx(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask) 3579 { 3580 return iemNativeRegAllocTmpExInt<true>(pReNative, poff, fRegMask); 3581 } 3582 3583 3584 /** See iemNativeRegAllocTmpExInt for details. */ 3585 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpExPreferNonVolatile(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask) 3586 { 3587 return iemNativeRegAllocTmpExInt<false>(pReNative, poff, fRegMask); 3588 } 3589 3590 3591 /** Internal templated variation of iemNativeRegAllocTmpEx. */ 3592 template<uint32_t const a_fRegMask, bool const a_fPreferVolatile> 3593 DECL_FORCE_INLINE_THROW(uint8_t) iemNativeRegAllocTmpExInt(PIEMRECOMPILERSTATE pReNative, uint32_t *poff) 3594 { 3595 AssertCompile(!(a_fRegMask & ~IEMNATIVE_HST_GREG_MASK)); 3596 AssertCompile(!(a_fRegMask & IEMNATIVE_REG_FIXED_MASK)); 3597 3598 /* 3599 * Try find a completely unused register, preferably a call-volatile one. 3600 */ 3601 uint8_t idxReg; 3602 uint32_t fRegs = ~pReNative->Core.bmHstRegs 3603 & ~pReNative->Core.bmHstRegsWithGstShadow 3604 & (~IEMNATIVE_REG_FIXED_MASK & IEMNATIVE_HST_GREG_MASK) 3605 & a_fRegMask; 3606 if (fRegs) 3607 { 3608 if RT_CONSTEXPR_IF(a_fPreferVolatile) 3609 idxReg = (uint8_t)ASMBitFirstSetU32( fRegs & IEMNATIVE_CALL_VOLATILE_GREG_MASK 3610 ? fRegs & IEMNATIVE_CALL_VOLATILE_GREG_MASK : fRegs) - 1; 3611 else 3612 idxReg = (uint8_t)ASMBitFirstSetU32( fRegs & ~IEMNATIVE_CALL_VOLATILE_GREG_MASK 3613 ? fRegs & ~IEMNATIVE_CALL_VOLATILE_GREG_MASK : fRegs) - 1; 3614 Assert(pReNative->Core.aHstRegs[idxReg].fGstRegShadows == 0); 3615 Assert(!(pReNative->Core.bmHstRegsWithGstShadow & RT_BIT_32(idxReg))); 3616 Log12(("iemNativeRegAllocTmpExInt: %s\n", g_apszIemNativeHstRegNames[idxReg])); 3617 } 3618 else 3619 { 3620 idxReg = iemNativeRegAllocFindFree(pReNative, poff, a_fPreferVolatile, a_fRegMask); 3621 AssertStmt(idxReg != UINT8_MAX, IEMNATIVE_DO_LONGJMP(pReNative, VERR_IEM_REG_ALLOCATOR_NO_FREE_TMP)); 3622 Log12(("iemNativeRegAllocTmpExInt: %s (slow)\n", g_apszIemNativeHstRegNames[idxReg])); 3557 3623 } 3558 3624 return iemNativeRegMarkAllocated(pReNative, idxReg, kIemNativeWhat_Tmp); … … 3575 3641 * @param uImm The immediate value that the register must hold upon 3576 3642 * return. 3577 * @param fPreferVolatile Whether to prefer volatile over non-volatile 3578 * registers (@c true, default) or the other way around 3579 * (@c false). 3580 * 3643 * @note Prefers volatile registers. 3581 3644 * @note Reusing immediate values has not been implemented yet. 3582 3645 */ 3583 3646 DECL_HIDDEN_THROW(uint8_t) 3584 iemNativeRegAllocTmpImm(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint64_t uImm , bool fPreferVolatile /*= true*/)3585 { 3586 uint8_t const idxReg = iemNativeRegAllocTmp(pReNative, poff , fPreferVolatile);3647 iemNativeRegAllocTmpImm(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint64_t uImm) 3648 { 3649 uint8_t const idxReg = iemNativeRegAllocTmp(pReNative, poff); 3587 3650 *poff = iemNativeEmitLoadGprImm64(pReNative, *poff, idxReg, uImm); 3588 3651 return idxReg; … … 3630 3693 & (~IEMNATIVE_REG_FIXED_MASK & IEMNATIVE_HST_GREG_MASK))) 3631 3694 { 3632 uint8_t const idxRegNew = iemNativeRegAllocTmpEx (pReNative, poff, a_fRegMask);3695 uint8_t const idxRegNew = iemNativeRegAllocTmpExInt<a_fRegMask, true>(pReNative, poff); 3633 3696 3634 3697 *poff = iemNativeEmitLoadGprFromGpr(pReNative, *poff, idxRegNew, idxReg); … … 3662 3725 { 3663 3726 Assert(!(a_fRegMask & IEMNATIVE_CALL_VOLATILE_GREG_MASK)); 3664 uint8_t const idxRegNew = iemNativeRegAllocTmpEx(pReNative, poff, a_fRegMask & ~RT_BIT_32(idxReg), 3665 (a_fRegMask & IEMNATIVE_CALL_VOLATILE_GREG_MASK) 3666 && a_enmIntendedUse == kIemNativeGstRegUse_Calculation); 3727 uint8_t const idxRegNew = (a_fRegMask & IEMNATIVE_CALL_VOLATILE_GREG_MASK) 3728 && a_enmIntendedUse == kIemNativeGstRegUse_Calculation 3729 ? iemNativeRegAllocTmpEx(pReNative, poff, a_fRegMask & ~RT_BIT_32(idxReg)) 3730 : iemNativeRegAllocTmpExPreferNonVolatile(pReNative, poff, a_fRegMask & ~RT_BIT_32(idxReg)); 3667 3731 *poff = iemNativeEmitLoadGprFromGpr(pReNative, *poff, idxRegNew, idxReg); 3668 3732 if RT_CONSTEXPR_IF(a_enmIntendedUse != kIemNativeGstRegUse_Calculation) … … 3694 3758 3695 3759 /** @todo share register for readonly access. */ 3696 uint8_t const idxRegNew = iemNativeRegAllocTmpEx(pReNative, poff, a_fRegMask, 3697 a_enmIntendedUse == kIemNativeGstRegUse_Calculation); 3760 uint8_t const idxRegNew = a_enmIntendedUse == kIemNativeGstRegUse_Calculation 3761 ? iemNativeRegAllocTmpExInt<a_fRegMask, true>(pReNative, poff) 3762 : iemNativeRegAllocTmpExInt<a_fRegMask, false>(pReNative, poff); 3698 3763 3699 3764 if RT_CONSTEXPR_IF(a_enmIntendedUse != kIemNativeGstRegUse_ForFullWrite) … … 3743 3808 * Allocate a new register, load it with the guest value and designate it as a copy of the 3744 3809 */ 3745 uint8_t const idxRegNew = iemNativeRegAllocTmpEx(pReNative, poff, a_fRegMask, 3746 a_enmIntendedUse == kIemNativeGstRegUse_Calculation); 3810 uint8_t const idxRegNew = a_enmIntendedUse != kIemNativeGstRegUse_Calculation 3811 ? iemNativeRegAllocTmpExInt<a_fRegMask, false>(pReNative, poff) 3812 : iemNativeRegAllocTmpExInt<a_fRegMask, true>(pReNative, poff); 3747 3813 3748 3814 if RT_CONSTEXPR_IF(a_enmIntendedUse != kIemNativeGstRegUse_ForFullWrite) -
trunk/src/VBox/VMM/VMMAll/target-x86/IEMAllN8veEmit-x86.h
r106201 r106319 599 599 pReNative->PostponedEfl.enmOp = kIemNativePostponedEflOp_Logical; 600 600 pReNative->PostponedEfl.cOpBits = cOpBits; 601 pReNative->PostponedEfl.idxReg1 = iemNativeRegAllocTmpEx (pReNative, &off, IEMNATIVE_POSTPONING_REG_MASK, false);601 pReNative->PostponedEfl.idxReg1 = iemNativeRegAllocTmpExPreferNonVolatile(pReNative, &off, IEMNATIVE_POSTPONING_REG_MASK); 602 602 /** @todo it would normally be possible to use idxRegResult, iff it is 603 603 * already a non-volatile register and we can be user the caller -
trunk/src/VBox/VMM/include/IEMN8veRecompiler.h
r106315 r106319 2225 2225 DECL_HIDDEN_THROW(PIEMNATIVEINSTR) iemNativeInstrBufEnsureSlow(PIEMRECOMPILERSTATE pReNative, uint32_t off, uint32_t cInstrReq); 2226 2226 2227 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmp(PIEMRECOMPILERSTATE pReNative, uint32_t *poff , bool fPreferVolatile = true);2228 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmp Ex(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask,2229 bool fPreferVolatile = true);2230 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmp Imm(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint64_t uImm,2231 bool fPreferVolatile = true);2227 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmp(PIEMRECOMPILERSTATE pReNative, uint32_t *poff); 2228 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpPreferNonVolatile(PIEMRECOMPILERSTATE pReNative, uint32_t *poff); 2229 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpEx(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask); 2230 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpExPreferNonVolatile(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint32_t fRegMask); 2231 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpImm(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, uint64_t uImm); 2232 2232 2233 2233 DECL_HIDDEN_THROW(uint8_t) iemNativeRegAllocTmpForGuestRegReadOnly(PIEMRECOMPILERSTATE pReNative, uint32_t *poff, IEMNATIVEGSTREG enmGstReg);
Note:
See TracChangeset
for help on using the changeset viewer.