Skip to content

Commit 782358f

Browse files
committed
Convert engineLoadTXD textures to D3DPOOL_DEFAULT (#4062)
GTA SA's RenderWare loader (D3DResourceSystem::CreateTexture @ 0x730510) hardcodes D3DPOOL_MANAGED for every texture in a TXD. MANAGED textures are mirrored 1:1 in system memory so D3D9 can auto-restore them on a device reset, which is exactly what makes a 10 MB DXT TXD count as ~20 MB of working set in MTA's process. After RW finishes decoding a script-loaded TXD in CRenderWareSA::ReadTXD we now walk every raster, allocate a fresh IDirect3DTexture9 in D3DPOOL_DEFAULT, copy each mip through a transient SYSTEMMEM scratch + UpdateTexture, release the original MANAGED texture, and swap the pointer in rasterExt->texture. The release deliberately bypasses D3DResourceSystem::DestroyTexture so the gD3DTextureBuffer cache (MANAGED-only, keyed by w/h/format) never sees DEFAULT-pool entries; the destroy intercept in CRenderWareSA::DestroyTexture NULLs rasterExt->texture before RwTextureDestroy so _rwD3D9RasterDestroy hits its existing early-out. Conversion happens before ScriptAddedTxd so the shader-matching map (m_D3DDataTexInfoMap) is keyed against the new IDirect3DTexture9 pointer the renderer will see. Cube maps, palettised rasters, and unrecognised D3DFORMATs are skipped and stay MANAGED; per-texture failures (out of vram, lock failure) silently leave the original MANAGED texture in place. Because DEFAULT-pool resources are auto-destroyed on a D3D9 cooperative loss, CRenderWareSA gains OnDeviceLost / OnDeviceReset hooks called from CGraphics around the existing CRenderItemManager handling. CClientTXD implements a new CRwReplacementOwner interface and re-decodes on Reset: file-path TXDs re-read from disk, raw-data TXDs use the m_FileData buffer that LoadFromBuffer already keeps for the clothes system. Memory impact for a 10 MB TXD: - file path (the common case for vehicle/skin packs): ~10 MB sysmem dropped, VRAM usage unchanged. ~50% total saving. - raw-data path (rare; engineLoadTXD with a buffer): m_FileData was already kept by master for clothes compatibility, so the MANAGED shadow is replaced by that buffer at no net memory cost.
1 parent 7f23f61 commit 782358f

8 files changed

Lines changed: 595 additions & 7 deletions

File tree

Client/core/Graphics/CGraphics.cpp

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@
1111

1212
#include "StdInc.h"
1313
#include <game/CSettings.h>
14+
#include <game/CGame.h>
15+
#include <game/CRenderWare.h>
1416
#include <memory>
1517
#include "DXHook/CProxyDirect3DDevice9.h"
1618
#include "CTileBatcher.h"
@@ -1727,6 +1729,13 @@ void CGraphics::OnDeviceInvalidate(IDirect3DDevice9* pDevice)
17271729
SAFE_RELEASE(m_pSavedFrontBufferData);
17281730
SAFE_RELEASE(m_pTempBackBufferData);
17291731

1732+
// Release D3DPOOL_DEFAULT replacement textures owned by engineLoadTXD before
1733+
// IDirect3DDevice9::Reset is attempted; per the D3D9 contract, every DEFAULT-pool
1734+
// resource must be gone first. The game module rebuilds these in OnDeviceRestore.
1735+
if (CGame* pGame = g_pCore->GetGame())
1736+
if (CRenderWare* pRenderWare = pGame->GetRenderWare())
1737+
pRenderWare->OnDeviceLost();
1738+
17301739
// Reset render zone tracking on device loss
17311740
m_MTARenderZone = MTA_RZONE_NONE;
17321741
m_iOutsideZoneCount = 0;
@@ -1757,6 +1766,13 @@ void CGraphics::OnDeviceRestore(IDirect3DDevice9* pDevice)
17571766
m_pRenderItemManager->OnResetDevice();
17581767
m_pScreenGrabber->OnResetDevice();
17591768

1769+
// Re-create the D3DPOOL_DEFAULT replacement textures we released in OnDeviceInvalidate.
1770+
// File-path TXDs re-read from disk; raw-data TXDs use the m_FileData buffer kept by
1771+
// CClientTXD since LoadFromBuffer.
1772+
if (CGame* pGame = g_pCore->GetGame())
1773+
if (CRenderWare* pRenderWare = pGame->GetRenderWare())
1774+
pRenderWare->OnDeviceReset();
1775+
17601776
const uint uiViewportWidth = GetViewportWidth();
17611777
const uint uiViewportHeight = GetViewportHeight();
17621778
if (uiViewportWidth > 0 && uiViewportHeight > 0)

0 commit comments

Comments
 (0)