diff --git a/src/common/global.cpp b/src/common/global.cpp index 51b4cff3..850ba453 100644 --- a/src/common/global.cpp +++ b/src/common/global.cpp @@ -75,6 +75,7 @@ ConVar* r_visualizetraces_duration = nullptr; ConVar* gfx_nvnUseLowLatency = nullptr; ConVar* gfx_nvnUseLowLatencyBoost = nullptr; +ConVar* gfx_nvnUseMarkersToOptimize = nullptr; #endif // !DEDICATED ConVar* stream_overlay = nullptr; @@ -337,8 +338,9 @@ void ConVar_StaticInit(void) fps_max_rt_sleep_threshold = ConVar::StaticCreate("fps_max_rt_sleep_threshold", "0.016666667", FCVAR_RELEASE, "Frame limiter starts to sleep when frame time exceeds this threshold.", true, 0.f, false, 0.f, nullptr, nullptr); fps_max_gfx = ConVar::StaticCreate("fps_max_gfx", "0", FCVAR_RELEASE, "Frame rate limiter using NVIDIA Reflex Low Latency SDK. -1 indicates use the desktop refresh. 0 is disabled.", true, -1.f, true, 295.f, &GFX_NVN_Changed_f, nullptr); - gfx_nvnUseLowLatency = ConVar::StaticCreate("gfx_nvnUseLowLatency" , "1", FCVAR_RELEASE | FCVAR_ARCHIVE, "Enables NVIDIA Reflex Low Latency SDK." , false, 0.f, false, 0.f, &GFX_NVN_Changed_f, nullptr); - gfx_nvnUseLowLatencyBoost = ConVar::StaticCreate("gfx_nvnUseLowLatencyBoost", "0", FCVAR_RELEASE | FCVAR_ARCHIVE, "Enables NVIDIA Reflex Low Latency Boost.", false, 0.f, false, 0.f, &GFX_NVN_Changed_f, nullptr); + gfx_nvnUseLowLatency = ConVar::StaticCreate("gfx_nvnUseLowLatency" , "1", FCVAR_RELEASE | FCVAR_ARCHIVE, "Enables NVIDIA Reflex Low Latency SDK." , false, 0.f, false, 0.f, &GFX_NVN_Changed_f, nullptr); + gfx_nvnUseLowLatencyBoost = ConVar::StaticCreate("gfx_nvnUseLowLatencyBoost" , "0", FCVAR_RELEASE | FCVAR_ARCHIVE, "Enables NVIDIA Reflex Low Latency Boost.", false, 0.f, false, 0.f, &GFX_NVN_Changed_f, nullptr); + gfx_nvnUseMarkersToOptimize = ConVar::StaticCreate("gfx_nvnUseMarkersToOptimize", "0", FCVAR_RELEASE | FCVAR_ARCHIVE, "Use NVIDIA Reflex Low Latency markers to optimize (requires Low Latency Boost to be enabled).", false, 0.f, false, 0.f, &GFX_NVN_Changed_f, nullptr); #endif // !DEDICATED //------------------------------------------------------------------------- diff --git a/src/common/global.h b/src/common/global.h index 1c3a1ee3..3d546b56 100644 --- a/src/common/global.h +++ b/src/common/global.h @@ -66,6 +66,7 @@ extern ConVar* r_visualizetraces_duration; extern ConVar* gfx_nvnUseLowLatency; extern ConVar* gfx_nvnUseLowLatencyBoost; +extern ConVar* gfx_nvnUseMarkersToOptimize; #endif // !DEDICATED extern ConVar* stream_overlay; diff --git a/src/core/init.cpp b/src/core/init.cpp index f1be0083..61c80dee 100644 --- a/src/core/init.cpp +++ b/src/core/init.cpp @@ -100,6 +100,7 @@ #include "engine/sys_mainwind.h" #include "engine/matsys_interface.h" #include "engine/gl_matsysiface.h" +#include "engine/gl_drawlights.h" #include "engine/gl_screen.h" #include "engine/gl_rsurf.h" #include "engine/debugoverlay.h" @@ -581,6 +582,7 @@ void DetourRegister() // Register detour classes to be searched and hooked. REGISTER(VGL_RMain); REGISTER(VMatSys_Interface); REGISTER(VGL_MatSysIFace); + REGISTER(VGL_DrawLights); REGISTER(VGL_Screen); #endif // !DEDICATED diff --git a/src/engine/CMakeLists.txt b/src/engine/CMakeLists.txt index 4caac9d9..a27fa06f 100644 --- a/src/engine/CMakeLists.txt +++ b/src/engine/CMakeLists.txt @@ -29,6 +29,8 @@ add_sources( SOURCE_GROUP "Debug" add_sources( SOURCE_GROUP "Render" "framelimit.cpp" "framelimit.h" + "gl_drawlights.cpp" + "gl_drawlights.h" "gl_matsysiface.h" "gl_model_private.h" "gl_rmain.cpp" diff --git a/src/engine/client/cdll_engine_int.cpp b/src/engine/client/cdll_engine_int.cpp index 97f40254..c6acb0e4 100644 --- a/src/engine/client/cdll_engine_int.cpp +++ b/src/engine/client/cdll_engine_int.cpp @@ -18,12 +18,67 @@ /*****************************************************************************/ #ifndef DEDICATED +//----------------------------------------------------------------------------- +// Purpose: pre frame stage notify hook +//----------------------------------------------------------------------------- +void FrameStageNotify_Pre(const ClientFrameStage_t frameStage) +{ + switch (frameStage) + { + case ClientFrameStage_t::FRAME_START: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_START: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_POSTDATAUPDATE_START: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_POSTDATAUPDATE_END: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_END: + break; + case ClientFrameStage_t::FRAME_RENDER_START: + break; + case ClientFrameStage_t::FRAME_RENDER_END: + break; + case ClientFrameStage_t::FRAME_NET_FULL_FRAME_UPDATE_ON_REMOVE: + break; + } +} + +//----------------------------------------------------------------------------- +// Purpose: post frame stage notify hook +//----------------------------------------------------------------------------- +void FrameStageNotify_Post(const ClientFrameStage_t frameStage) +{ + switch (frameStage) + { + case ClientFrameStage_t::FRAME_START: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_START: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_POSTDATAUPDATE_START: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_POSTDATAUPDATE_END: + break; + case ClientFrameStage_t::FRAME_NET_UPDATE_END: + break; + case ClientFrameStage_t::FRAME_RENDER_START: + break; + case ClientFrameStage_t::FRAME_RENDER_END: + GFX_SetLatencyMarker(D3D11Device(), SIMULATION_END); + break; + case ClientFrameStage_t::FRAME_NET_FULL_FRAME_UPDATE_ON_REMOVE: + break; + } +} + //----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CHLClient::FrameStageNotify(CHLClient* pHLClient, ClientFrameStage_t frameStage) { + FrameStageNotify_Pre(frameStage); CHLClient_FrameStageNotify(pHLClient, frameStage); + FrameStageNotify_Post(frameStage); } //----------------------------------------------------------------------------- diff --git a/src/engine/gl_drawlights.cpp b/src/engine/gl_drawlights.cpp new file mode 100644 index 00000000..40b69635 --- /dev/null +++ b/src/engine/gl_drawlights.cpp @@ -0,0 +1,13 @@ +#include "gl_drawlights.h" + + +void DrawLightSprites(void* unkType) +{ + v_DrawLightSprites(unkType); +} + +void VGL_DrawLights::Detour(const bool bAttach) const +{ + // Enable if needed. + //DetourSetup(&v_DrawLightSprites, &DrawLightSprites, bAttach); +} diff --git a/src/engine/gl_drawlights.h b/src/engine/gl_drawlights.h new file mode 100644 index 00000000..6194bbc6 --- /dev/null +++ b/src/engine/gl_drawlights.h @@ -0,0 +1,23 @@ +#pragma once + +inline CMemory p_DrawLightSprites; +inline void(*v_DrawLightSprites)(void*); + + +/////////////////////////////////////////////////////////////////////////////// +class VGL_DrawLights : public IDetour +{ + virtual void GetAdr(void) const + { + LogFunAdr("DrawLightSprites", p_DrawLightSprites.GetPtr()); + } + virtual void GetFun(void) const + { + p_DrawLightSprites = g_GameDll.FindPatternSIMD("48 8B C4 55 57 48 8D 68 A1 48 81 EC ?? ?? ?? ?? 48 8B 15 ?? ?? ?? ??"); + v_DrawLightSprites = p_DrawLightSprites.RCast(); + } + virtual void GetVar(void) const { } + virtual void GetCon(void) const { } + virtual void Detour(const bool bAttach) const; +}; +/////////////////////////////////////////////////////////////////////////////// diff --git a/src/engine/gl_rsurf.cpp b/src/engine/gl_rsurf.cpp index 997a3ccc..695526b5 100644 --- a/src/engine/gl_rsurf.cpp +++ b/src/engine/gl_rsurf.cpp @@ -6,8 +6,16 @@ //===========================================================================// #include "core/stdafx.h" #include "tier1/cvar.h" +#include "windows/id3dx.h" +#include "geforce/reflex.h" #include "engine/gl_rsurf.h" +void* R_DrawDepthOfField(const float a1) +{ + GFX_SetLatencyMarker(D3D11Device(), RENDERSUBMIT_START); + return V_DrawDepthOfField(a1); +} + void* R_DrawWorldMeshes(void* baseEntity, void* renderContext, DrawWorldLists_t worldLists) { if (r_drawWorldMeshes->GetBool()) @@ -34,6 +42,7 @@ void* R_DrawWorldMeshesDepthAtTheEnd(void* ptr1, void* ptr2, void* ptr3, DrawWor void VGL_RSurf::Detour(const bool bAttach) const { + DetourSetup(&V_DrawDepthOfField, &R_DrawDepthOfField, bAttach); DetourSetup(&V_DrawWorldMeshes, &R_DrawWorldMeshes, bAttach); DetourSetup(&V_DrawWorldMeshesDepthOnly, &R_DrawWorldMeshesDepthOnly, bAttach); DetourSetup(&V_DrawWorldMeshesDepthAtTheEnd, &R_DrawWorldMeshesDepthAtTheEnd, bAttach); diff --git a/src/engine/gl_rsurf.h b/src/engine/gl_rsurf.h index ff793a41..902477e2 100644 --- a/src/engine/gl_rsurf.h +++ b/src/engine/gl_rsurf.h @@ -1,6 +1,9 @@ #pragma once #include "public/ivrenderview.h" +inline CMemory P_DrawDepthOfField; +inline void*(*V_DrawDepthOfField)(const float a1); + inline CMemory P_DrawWorldMeshes; inline void*(*V_DrawWorldMeshes)(void* baseEntity, void* renderContext, DrawWorldLists_t worldLists); @@ -15,12 +18,14 @@ class VGL_RSurf : public IDetour { virtual void GetAdr(void) const { + LogFunAdr("R_DrawDepthOfField", P_DrawDepthOfField.GetPtr()); LogFunAdr("R_DrawWorldMeshes", P_DrawWorldMeshes.GetPtr()); LogFunAdr("R_DrawWorldMeshesDepthOnly", P_DrawWorldMeshesDepthOnly.GetPtr()); LogFunAdr("R_DrawWorldMeshesDepthAtTheEnd", P_DrawWorldMeshesDepthAtTheEnd.GetPtr()); } virtual void GetFun(void) const { + P_DrawDepthOfField = g_GameDll.FindPatternSIMD("48 83 EC 48 0F 28 E8"); #if defined (GAMEDLL_S0) || defined (GAMEDLL_S1) P_DrawWorldMeshes = g_GameDll.FindPatternSIMD("48 8B C4 48 89 48 08 53 48 83 EC 70"); #elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3) @@ -29,6 +34,7 @@ class VGL_RSurf : public IDetour P_DrawWorldMeshesDepthOnly = g_GameDll.FindPatternSIMD("40 56 57 B8 ?? ?? ?? ??"); P_DrawWorldMeshesDepthAtTheEnd = g_GameDll.FindPatternSIMD("48 89 5C 24 ?? 48 89 74 24 ?? 57 48 83 EC 20 48 8B 0D ?? ?? ?? ?? 41 8B F9"); + V_DrawDepthOfField = P_DrawDepthOfField.RCast(); V_DrawWorldMeshes = P_DrawWorldMeshes.RCast(); /*48 8B C4 48 89 48 08 53 57 41 55*/ V_DrawWorldMeshesDepthOnly = P_DrawWorldMeshesDepthOnly.RCast(); /*40 56 57 B8 ?? ?? ?? ??*/ V_DrawWorldMeshesDepthAtTheEnd = P_DrawWorldMeshesDepthAtTheEnd.RCast(); /*48 89 5C 24 ?? 48 89 74 24 ? 57 48 83 EC 20 48 8B 0D ?? ?? ?? ?? 41 8B F9*/ diff --git a/src/engine/host.cpp b/src/engine/host.cpp index ae5a8715..f605ce81 100644 --- a/src/engine/host.cpp +++ b/src/engine/host.cpp @@ -9,6 +9,8 @@ #include "tier0/frametask.h" #include "engine/host.h" #ifndef DEDICATED +#include "windows/id3dx.h" +#include "geforce/reflex.h" #include "vgui/vgui_debugpanel.h" #endif // !DEDICATED @@ -30,6 +32,23 @@ void CCommonHostState::SetWorldModel(model_t* pModel) } } +/* +================== +Host_CountRealTimePackets + +Counts the number of +packets in non-prescaled +clock frames (does not +count for bots or Terminal +Services environments) +================== +*/ +void Host_CountRealTimePackets() +{ + v_Host_CountRealTimePackets(); + GFX_SetLatencyMarker(D3D11Device(), SIMULATION_START); +} + /* ================== _Host_RunFrame @@ -77,6 +96,7 @@ void _Host_Error(const char* error, ...) void VHost::Detour(const bool bAttach) const { DetourSetup(&v_Host_RunFrame, &_Host_RunFrame, bAttach); + DetourSetup(&v_Host_CountRealTimePackets, &Host_CountRealTimePackets, bAttach); #ifndef DEDICATED // Dedicated already logs this! DetourSetup(&v_Host_Error, &_Host_Error, bAttach); diff --git a/src/engine/host.h b/src/engine/host.h index 1dce0e30..ec649ddc 100644 --- a/src/engine/host.h +++ b/src/engine/host.h @@ -4,8 +4,11 @@ inline CMemory p_Host_RunFrame; inline void(*v_Host_RunFrame)(void* unused, float time); -//inline CMemory p_Host_RunFrame_Render; // DEDICATED PATCH! -//inline void(*v_Host_RunFrame_Render)(void); +inline CMemory p_Host_RunFrame_Render; +inline void(*v_Host_RunFrame_Render)(void); + +inline CMemory p_Host_CountRealTimePackets; +inline void(*v_Host_CountRealTimePackets)(void); inline CMemory p_Host_ShouldRun; inline bool(*v_Host_ShouldRun)(); @@ -54,7 +57,8 @@ class VHost : public IDetour virtual void GetAdr(void) const { LogFunAdr("_Host_RunFrame", p_Host_RunFrame.GetPtr()); - //LogFunAdr("_Host_RunFrame_Render", p_Host_RunFrame_Render.GetPtr()); + LogFunAdr("_Host_RunFrame_Render", p_Host_RunFrame_Render.GetPtr()); + LogFunAdr("Host_CountRealTimePackets", p_Host_CountRealTimePackets.GetPtr()); LogFunAdr("Host_ShouldRun", p_Host_ShouldRun.GetPtr()); LogFunAdr("Host_Error", p_Host_Error.GetPtr()); //LogFunAdr("VCR_EnterPausedState", p_VCR_EnterPausedState.GetPtr()); @@ -69,16 +73,18 @@ class VHost : public IDetour { p_Host_RunFrame = g_GameDll.FindPatternSIMD("48 8B C4 48 89 58 18 48 89 70 20 F3 0F 11 48 ??"); #if defined (GAMEDLL_S0) || defined (GAMEDLL_S1) - //p_Host_RunFrame_Render = g_GameDll.FindPatternSIMD("48 89 5C 24 ?? 57 48 83 EC 20 48 8B 1D ?? ?? ?? ?? 33 FF"); + p_Host_RunFrame_Render = g_GameDll.FindPatternSIMD("48 89 5C 24 ?? 57 48 83 EC 20 48 8B 1D ?? ?? ?? ?? 33 FF"); #elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3) - //p_Host_RunFrame_Render = g_GameDll.FindPatternSIMD("40 53 48 83 EC 20 48 8B 0D ?? ?? ?? ?? 48 85 C9 75 34"); + p_Host_RunFrame_Render = g_GameDll.FindPatternSIMD("40 53 48 83 EC 20 48 8B 0D ?? ?? ?? ?? 48 85 C9 75 34"); #endif + p_Host_CountRealTimePackets = g_GameDll.FindPatternSIMD("40 53 48 83 EC 30 65 48 8B 04 25 ?? ?? ?? ?? 33 DB"); p_Host_ShouldRun = g_GameDll.FindPatternSIMD("48 83 EC 28 48 8B 05 ?? ?? ?? ?? 83 78 6C 00 75 07 B0 01"); p_Host_Error = g_GameDll.FindPatternSIMD("48 89 4C 24 ?? 48 89 54 24 ?? 4C 89 44 24 ?? 4C 89 4C 24 ?? 53 57 48 81 EC ?? ?? ?? ??"); //p_VCR_EnterPausedState = g_GameDll.FindPatternSIMD("40 53 48 83 EC 20 65 48 8B 04 25 ?? ?? ?? ?? BB ?? ?? ?? ?? C6 05 ?? ?? ?? ?? ??"); v_Host_RunFrame = p_Host_RunFrame.RCast(); - //v_Host_RunFrame_Render = p_Host_Error.RCast(); + v_Host_RunFrame_Render = p_Host_RunFrame_Render.RCast(); + v_Host_CountRealTimePackets = p_Host_CountRealTimePackets.RCast(); v_Host_ShouldRun = p_Host_ShouldRun.RCast(); v_Host_Error = p_Host_Error.RCast(); //v_VCR_EnterPausedState = p_VCR_EnterPausedState.RCast(); diff --git a/src/engine/sys_dll2.cpp b/src/engine/sys_dll2.cpp index 46c583ee..d9dc35c2 100644 --- a/src/engine/sys_dll2.cpp +++ b/src/engine/sys_dll2.cpp @@ -190,6 +190,7 @@ bool CEngineAPI::MainLoop() { const bool bUseLowLatencyMode = gfx_nvnUseLowLatency->GetBool(); const bool bUseLowLatencyBoost = gfx_nvnUseLowLatencyBoost->GetBool(); + const bool bUseMarkersToOptimize = gfx_nvnUseMarkersToOptimize->GetBool(); float fpsMax = fps_max_gfx->GetFloat(); @@ -208,7 +209,7 @@ bool CEngineAPI::MainLoop() } GFX_UpdateLowLatencyParameters(D3D11Device(), bUseLowLatencyMode, - bUseLowLatencyBoost, false, fpsMax); + bUseLowLatencyBoost, bUseMarkersToOptimize, fpsMax); } GFX_RunLowLatencyFrame(D3D11Device()); diff --git a/src/materialsystem/cmaterialsystem.cpp b/src/materialsystem/cmaterialsystem.cpp index 671dae11..851fcd79 100644 --- a/src/materialsystem/cmaterialsystem.cpp +++ b/src/materialsystem/cmaterialsystem.cpp @@ -12,12 +12,13 @@ #include "engine/cmodel_bsp.h" #include "geforce/reflex.h" #ifndef MATERIALSYSTEM_NODX +#include "windows/id3dx.h" #include "materialsystem/cmaterialglue.h" #endif // !MATERIALSYSTEM_NODX #include "materialsystem/cmaterialsystem.h" #ifndef MATERIALSYSTEM_NODX -//PCLSTATS_DEFINE() +PCLSTATS_DEFINE() #endif // MATERIALSYSTEM_NODX //----------------------------------------------------------------------------- @@ -38,10 +39,10 @@ InitReturnVal_t CMaterialSystem::Init(CMaterialSystem* thisptr) // Initialize as usual. GFX_EnableLowLatencySDK(!CommandLine()->CheckParm("-gfx_nvnDisableLowLatency")); - //if (GFX_IsLowLatencySDKEnabled()) - //{ - // PCLSTATS_INIT(0); - //} + if (GFX_IsLowLatencySDKEnabled()) + { + PCLSTATS_INIT(0); + } return CMaterialSystem__Init(thisptr); #endif @@ -52,10 +53,10 @@ InitReturnVal_t CMaterialSystem::Init(CMaterialSystem* thisptr) //----------------------------------------------------------------------------- int CMaterialSystem::Shutdown(CMaterialSystem* thisptr) { - //if (GFX_IsLowLatencySDKEnabled()) - //{ - // PCLSTATS_SHUTDOWN(); - //} + if (GFX_IsLowLatencySDKEnabled()) + { + PCLSTATS_SHUTDOWN(); + } return CMaterialSystem__Shutdown(thisptr); } @@ -108,9 +109,21 @@ void* __fastcall DispatchDrawCall(int64_t a1, uint64_t a2, int a3, int a4, int64 return v_DispatchDrawCall(a1, a2, a3, a4, a5, a6, a7, a8, a9, a10, a11, a12, a13, a14); #endif } -#endif // !MATERIALSYSTEM_NODX -#ifndef MATERIALSYSTEM_NODX +//--------------------------------------------------------------------------------- +// Purpose: run IDXGISwapChain::Present +//--------------------------------------------------------------------------------- +ssize_t SpinPresent(void) +{ + GFX_SetLatencyMarker(D3D11Device(), RENDERSUBMIT_END); + + GFX_SetLatencyMarker(D3D11Device(), PRESENT_START); + const ssize_t val = v_SpinPresent(); + GFX_SetLatencyMarker(D3D11Device(), PRESENT_END); + + return val; +} + //----------------------------------------------------------------------------- // Purpose: finds a material // Input : *pMatSys - @@ -154,6 +167,7 @@ void VMaterialSystem::Detour(const bool bAttach) const #ifndef MATERIALSYSTEM_NODX DetourSetup(&v_StreamDB_Init, &StreamDB_Init, bAttach); DetourSetup(&v_DispatchDrawCall, &DispatchDrawCall, bAttach); + DetourSetup(&v_SpinPresent, &SpinPresent, bAttach); DetourSetup(&CMaterialSystem__FindMaterialEx, &CMaterialSystem::FindMaterialEx, bAttach); #endif // !MATERIALSYSTEM_NODX } diff --git a/src/materialsystem/cmaterialsystem.h b/src/materialsystem/cmaterialsystem.h index f2422631..1058ca96 100644 --- a/src/materialsystem/cmaterialsystem.h +++ b/src/materialsystem/cmaterialsystem.h @@ -75,6 +75,9 @@ inline void*(*v_DispatchDrawCall)(int64_t a1, uint64_t a2, int a3, int a4, char inline CMemory p_DispatchDrawCall; inline void*(*v_DispatchDrawCall)(int64_t a1, uint64_t a2, int a3, int a4, int64_t a5, int a6, uint8_t a7, int64_t a8, uint32_t a9, uint32_t a10, int a11, __m128* a12, int a13, int64_t a14); #endif +inline CMemory p_SpinPresent; +inline ssize_t(*v_SpinPresent)(void); + inline CMemory p_GetStreamOverlay; inline void(*v_GetStreamOverlay)(const char* mode, char* buf, size_t bufSize); @@ -100,9 +103,10 @@ class VMaterialSystem : public IDetour #ifndef MATERIALSYSTEM_NODX LogFunAdr("CMaterialSystem::FindMaterialEx", p_CMaterialSystem__FindMaterialEx.GetPtr()); LogFunAdr("CMaterialSystem::GetScreenSize", p_CMaterialSystem_GetScreenSize.GetPtr()); - LogFunAdr("CMaterialSystem::DispatchDrawCall", p_DispatchDrawCall.GetPtr()); LogFunAdr("CMaterialSystem::GetStreamOverlay", p_GetStreamOverlay.GetPtr()); LogFunAdr("CMaterialSystem::DrawStreamOverlay", p_DrawStreamOverlay.GetPtr()); + LogFunAdr("DispatchDrawCall", p_DispatchDrawCall.GetPtr()); + LogFunAdr("SpinPresent", p_SpinPresent.GetPtr()); LogVarAdr("g_nTotalStreamingTextureMemory", reinterpret_cast(g_nTotalStreamingTextureMemory)); LogVarAdr("g_nUnfreeStreamingTextureMemory", reinterpret_cast(g_nUnfreeStreamingTextureMemory)); LogVarAdr("g_nUnusableStreamingTextureMemory", reinterpret_cast(g_nUnusableStreamingTextureMemory)); @@ -134,6 +138,9 @@ class VMaterialSystem : public IDetour p_DispatchDrawCall = g_GameDll.FindPatternSIMD("44 89 4C 24 ?? 44 89 44 24 ?? 48 89 4C 24 ?? 55 53 56"); v_DispatchDrawCall = p_DispatchDrawCall.RCast(); #endif + p_SpinPresent = g_GameDll.FindPatternSIMD("48 89 5C 24 ?? 48 89 74 24 ?? 57 48 81 EC ?? ?? ?? ?? 8B 15 ?? ?? ?? ??"); + v_SpinPresent = p_SpinPresent.RCast(); + p_GetStreamOverlay = g_GameDll.FindPatternSIMD("E8 ?? ?? ?? ?? 80 7C 24 ?? ?? 0F 84 ?? ?? ?? ?? 48 89 9C 24 ?? ?? ?? ??").FollowNearCallSelf(); v_GetStreamOverlay = p_GetStreamOverlay.RCast(); /*E8 ? ? ? ? 80 7C 24 ? ? 0F 84 ? ? ? ? 48 89 9C 24 ? ? ? ?*/