More robust RPak loading/unloading system

This is currently the most robust way to perform this.
However it might fail still as the locks don't seem valid for the second loads (we currently load more paks from the same queue..).

We need to push the strings to the queue list and let the engine load these too so a new lock is acquired for that job.
This commit is contained in:
Kawe Mazidjatari 2022-05-15 12:20:21 +02:00
parent 107a516f9e
commit 596682c483
8 changed files with 415 additions and 107 deletions

View File

@ -8,19 +8,293 @@
#include "core/stdafx.h" #include "core/stdafx.h"
#include "tier0/jobthread.h" #include "tier0/jobthread.h"
#include "engine/host_cmd.h" #include "engine/host_cmd.h"
#include "engine/host_state.h"
#include "engine/sys_utils.h" #include "engine/sys_utils.h"
#include "engine/cmodel_bsp.h" #include "engine/cmodel_bsp.h"
#include "rtech/rtech_utils.h"
#include "rtech/rtech_game.h" #include "rtech/rtech_game.h"
#include "datacache/mdlcache.h"
string g_svLevelName;
bool s_bLevelResourceInitialized = false;
bool s_bBasePaksInitialized = false;
//-----------------------------------------------------------------------------
// Purpose: checks if level has changed
// Input : &svLevelName -
// Output : true if level name deviates from previous level
//-----------------------------------------------------------------------------
bool MOD_LevelHasChanged(const string& svLevelName)
{
return (strcmp(svLevelName.c_str(), g_svLevelName.c_str()) != 0);
}
//-----------------------------------------------------------------------------
// Purpose: gets the queued pak handles
// Input : *a1 -
// *a2 -
// a3 -
// Output : __int64
//-----------------------------------------------------------------------------
__int64 __fastcall MOD_GetQueuedPakHandle(char* a1, char* a2, __int64 a3)
{
char v3; // al
signed int v4; // er11
__int64 v5; // r10
char* v6; // r9
signed __int64 v7; // rdx
char v8; // al
char* v10; // r8
char* v11; // r8
v3 = *a2;
v4 = 0;
*a1 = *a2;
v5 = 0i64;
if (v3)
{
v6 = a1;
v7 = a2 - a1;
while (1)
{
++v5;
++v6;
if (v5 == a3)
break;
v8 = v6[v7];
*v6 = v8;
if (!v8)
return v5;
}
*(v6 - 1) = 0;
if (--v5)
{
v10 = &a1[v5 - 1];
if ((*v10 & 0xC0) == 0x80)
{
do
++v4;
while ((v10[-v4] & 0xC0) == 0x80);
}
v11 = &v10[-v4];
if (v4 != ((0xE5000000 >> (((unsigned __int8)*v11 >> 3) & 0x1E)) & 3))
{
*v11 = 0;
v5 -= v4;
}
}
}
return v5;
}
//-----------------------------------------------------------------------------
// Purpose: processes queued pak files
//-----------------------------------------------------------------------------
void MOD_ProcessPakQueue()
{
char v0; // bl
char** v1; // r10
int i; // er9
char* v3; // rcx
signed __int64 v4; // r8
int v5; // eax
int v6; // edx
int v7; // eax
__int64 v8; // rbp
__int64 v9; // rsi
char* v10; // rbx
unsigned int v11; // ecx
__int64 v12; // rax
int v13; // edi
char v14; // al
char* v15; // rbx
int v16; // edi
char* v17; // rsi
char* v18; // rax
int v19; // ecx
int v20; // er8
int v21; // ecx
__int64 v22; // rdx
__int64 v23; // rbx
__int64 v24{}; // rdx
__int64 v25{}; // rcx
v0 = 0;
if (*(float*)&*dword_14B383420 == 1.0 && *qword_167ED7BB8 && *((int*)&*qword_14180A098/* + 36*/) < 2)
{
*byte_16709DDDF = 0;
v0 = 1;
}
else if (*byte_16709DDDF)
{
return;
}
if ((*(unsigned __int8(__fastcall**)(__int64))(*(_QWORD*)*g_FileSystem + 696i64))(*g_FileSystem) && !*dword_1634F445C)
{
v1 = &*off_141874660;
for (i = 0; i < 5; ++i)
{
if (*((_BYTE*)v1 - 268))
break;
v3 = (char*)&*unk_141874555 + 280 * i;
v4 = *v1 - v3;
do
{
v5 = (unsigned __int8)v3[v4];
v6 = (unsigned __int8)*v3 - v5;
if (v6)
break;
++v3;
} while (v5);
if (v6)
break;
v1 += 35;
}
v7 = 0;
if (!v0)
v7 = i;
v8 = v7;
if (v7 <= 4i64)
{
v9 = 4i64;
v10 = (char*)&*unk_1418749B0;
do
{
if (v10[5])
{
v11 = *(_DWORD*)v10;
v12 = *(_DWORD*)v10 & 0x1FF;
v10[4] = 1;
if (*((_DWORD*)&*unk_167D40B70 + 46 * v12) == v11)
{
v13 = *((_DWORD*)&*unk_167D40B70 + 46 * v12 + 1);
v14 = v10[4];
}
else
{
v13 = 14;
v14 = 1;
}
if (!v14 || v13 == 9)
{
g_pakLoadApi->Unload(*(_DWORD*)v10);
MOD_UnloadPakFile();
}
if (v13 && (unsigned int)(v13 - 13) > 1)
return;
*((_WORD*)v10 + 2) = 0;
*(_DWORD*)v10 = -1;
}
--v9;
v10 -= 280;
} while (v9 >= v8);
}
*byte_16709DDDF = 1;
v15 = (char*)&*unk_141874550;
v16 = 0;
while (1)
{
v17 = (char*)&*unk_141874550 + 280 * v16 + 5;
v18 = v17;
do
{
v19 = (unsigned __int8)v18[*((_QWORD*)v15 + 34) - (_QWORD)v17];
v20 = (unsigned __int8)*v18 - v19;
if (v20)
break;
++v18;
} while (v19);
if (!v20)
goto LABEL_37;
sub_1401F9C10(v17, *((char**)v15 + 34), 260i64);
if (v15[5])
break;
*(_DWORD*)v15 = -1;
LABEL_40:
++v16;
v15 += 280;
if (v16 >= 5)
{
if (*byte_16709DDDF)
{
v23 = *qword_1671061C8;
if (*qword_1671061C8)
{
if (!*(_BYTE*)(*qword_1671061C8 + 4))
{
if (*qword_167ED7BC0 || WORD2(*qword_167ED7C68) != HIWORD(*qword_167ED7C68))
{
if (!JT_AcquireFifoLock((JobFifoLock_s*)&*qword_167ED7BE0)
&& !(unsigned __int8)sub_14045BAC0((__int64(__fastcall*)(__int64, _DWORD*, __int64, _QWORD*))qword_14045C070, (__int64)&*qword_167ED7BE0, -1i64, 0i64))
{
sub_14045A1D0((unsigned __int8(__fastcall*)(_QWORD))qword_14045C070, (__int64)&*qword_167ED7BE0, -1i64, 0i64, 0i64, 1);
}
sub_140441220(v25, v24);
if (GetCurrentThreadId() == *dword_1641E443C)
{
if (*byte_167208B0C)
{
*byte_167208B0C = 0;
JT_ReleaseFifoLock((JobFifoLock_s*)&*qword_167ED7BE0);
}
}
JT_ReleaseFifoLock((JobFifoLock_s*)&*qword_167ED7BE0);
v23 = *qword_1671061C8;
}
(*(void(__fastcall**)(__int64, __int64))(*(_QWORD*)*g_FileSystem + 656i64))(*g_FileSystem, 256i64);
(*(void(__fastcall**)(__int64, __int64))(*(_QWORD*)*g_FileSystem + 648i64))(*g_FileSystem, v23);
}
}
}
return;
}
}
if (strcmp(v17, "mp_lobby.rpak") == 0)
s_bBasePaksInitialized = true;
if (s_bBasePaksInitialized && !s_bLevelResourceInitialized)
{
s_bLevelResourceInitialized = true;
MOD_PreloadPakFile(g_svLevelName);
}
*(_DWORD*)v15 = g_pakLoadApi->AsyncLoad(v17, g_pMallocPool.GetPtr(), 4, 0);
LABEL_37:
v21 = *(_DWORD*)v15;
if (*(_DWORD*)v15 != -1)
{
v22 = 184i64 * (v21 & 0x1FF);
if (*(_DWORD*)((char*)&*unk_167D40B70 + v22) != v21 || ((*(_DWORD*)((char*)&*unk_167D40B70 + v22 + 4) - 9) & 0xFFFFFFFB) != 0)
{
*byte_16709DDDF = 0; return;
}
}
goto LABEL_40;
}
}
//-----------------------------------------------------------------------------
// Purpose: load assets for level with fifolock (still not reliable enough).
// Input : *szLevelName -
// Output : true on success, false on failure
//-----------------------------------------------------------------------------
bool MOD_LoadPakForMap(const char* szLevelName)
{
if (MOD_LevelHasChanged(szLevelName))
s_bLevelResourceInitialized = false;
g_svLevelName = szLevelName;
return v_MOD_LoadPakForMap(szLevelName);
}
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Purpose: loads required pakfile assets for specified BSP // Purpose: loads required pakfile assets for specified BSP
// Input : svSetFile - // Input : &svSetFile -
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
void MOD_PreloadPak() void MOD_PreloadPakFile(const string& svLevelName)
{ {
ostringstream ostream; ostringstream ostream;
ostream << "platform\\scripts\\levels\\settings\\" << g_pHostState->m_levelName << ".json"; ostream << "platform\\scripts\\levels\\settings\\" << svLevelName << ".json";
fs::path fsPath = std::filesystem::current_path() /= ostream.str(); fs::path fsPath = std::filesystem::current_path() /= ostream.str();
if (FileExists(fsPath.string().c_str())) if (FileExists(fsPath.string().c_str()))
@ -62,38 +336,29 @@ void MOD_PreloadPak()
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Purpose: load assets for level with fifolock (still not reliable enough). // Purpose: unloads all pakfiles loaded by the SDK
// Input : svSetFile -
// TODO : Rebuild '0x140341D40' and load paks from there, this should always work.
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
#if defined (GAMEDLL_S0) || defined (GAMEDLL_S1) void MOD_UnloadPakFile(void)
bool MOD_LoadPakForMap()
#elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3)
bool MOD_LoadPakForMap(void* pBuffer)
#endif
{ {
if (!g_bLevelResourceInitialized && for (auto& it : g_LoadedPakHandle)
g_bBasePaksInitialized)
{ {
g_bLevelResourceInitialized = true; if (it >= 0)
if (g_pHostState->LevelHasChanged())
{ {
JT_AcquireFifoLock(); g_pakLoadApi->Unload(it);
MOD_PreloadPak();
} }
} }
g_LoadedPakHandle.clear();
return v_MOD_LoadPakForMap(pBuffer); g_BadMDLHandles.clear();
} }
void CModelBsp_Attach() void CModelBsp_Attach()
{ {
DetourAttach((LPVOID*)&v_MOD_LoadPakForMap, &MOD_LoadPakForMap); DetourAttach((LPVOID*)&v_MOD_LoadPakForMap, &MOD_LoadPakForMap);
DetourAttach((LPVOID*)&v_MOD_ProcessPakQueue, &MOD_ProcessPakQueue);
} }
void CModelBsp_Detach() void CModelBsp_Detach()
{ {
DetourDetach((LPVOID*)&v_MOD_LoadPakForMap, &MOD_LoadPakForMap); DetourDetach((LPVOID*)&v_MOD_LoadPakForMap, &MOD_LoadPakForMap);
DetourDetach((LPVOID*)&v_MOD_ProcessPakQueue, &MOD_ProcessPakQueue);
} }

View File

@ -4,13 +4,41 @@ inline CMemory p_CollisionBSPData_LinkPhysics;
inline auto CollisionBSPData_LinkPhysics = p_CollisionBSPData_LinkPhysics.RCast<uint64_t(*)(void* thisptr)>(); inline auto CollisionBSPData_LinkPhysics = p_CollisionBSPData_LinkPhysics.RCast<uint64_t(*)(void* thisptr)>();
inline CMemory p_MOD_LoadPakForMap; inline CMemory p_MOD_LoadPakForMap;
#if defined (GAMEDLL_S0) || defined (GAMEDLL_S1) inline auto v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(const char* szLevelName)>();
inline auto v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(void)>();
#elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3)
inline auto v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(void* pBuffer)>();
#endif
void MOD_PreloadPak(); inline CMemory p_MOD_ProcessPakQueue;
inline auto v_MOD_ProcessPakQueue = p_MOD_ProcessPakQueue.RCast<void(*)(void)>();
inline float* dword_14B383420;
inline int32_t * dword_1634F445C;
inline void** qword_167ED7BB8;
inline void** qword_14180A098;
inline bool* byte_16709DDDF;
inline int64_t * g_FileSystem;
inline char** off_141874660;
inline void** unk_141874555;
inline void** unk_167D40B70;
inline void** unk_1418749B0;
inline void** unk_141874550;
inline int64_t* qword_1671061C8;
inline int64_t* qword_167ED7BC0;
inline int64_t* qword_167ED7C68;
inline int64_t* qword_167ED7BE0;
inline int64_t* qword_14045C070;
inline int32_t* dword_1641E443C;
inline bool* byte_167208B0C;
inline auto sub_1401F9C10 = p_MOD_ProcessPakQueue.RCast<__int64(*)(char* a1, char* a2, __int64 a3)>();
inline auto sub_14045BAC0 = p_MOD_ProcessPakQueue.RCast<__int64(*)(__int64(__fastcall* a1)(__int64, _DWORD*, __int64, _QWORD*), __int64 a2, __int64 a3, __int64 a4)>();
inline auto sub_14045A1D0 = p_MOD_ProcessPakQueue.RCast<__int64(*)(unsigned __int8(__fastcall* a1)(_QWORD), __int64 a2, __int64 a3, __int64 a4, volatile signed __int64* a5, char a6)>();
inline auto sub_140441220 = p_MOD_ProcessPakQueue.RCast<void(*)(__int64 a1, __int64 a2)>();
extern bool s_bBasePaksInitialized;
extern string g_svLevelName;
bool MOD_LevelHasChanged(const string& svLevelName);
void MOD_PreloadPakFile(const string& svLevelName);
void MOD_UnloadPakFile(void);
void CModelBsp_Attach(); void CModelBsp_Attach();
void CModelBsp_Detach(); void CModelBsp_Detach();
@ -21,6 +49,30 @@ class VModel_BSP : public IDetour
{ {
spdlog::debug("| FUN: CollisionBSPData_LinkPhysics : {:#18x} |\n", p_CollisionBSPData_LinkPhysics.GetPtr()); spdlog::debug("| FUN: CollisionBSPData_LinkPhysics : {:#18x} |\n", p_CollisionBSPData_LinkPhysics.GetPtr());
spdlog::debug("| FUN: MOD_LoadPakForMap : {:#18x} |\n", p_MOD_LoadPakForMap.GetPtr()); spdlog::debug("| FUN: MOD_LoadPakForMap : {:#18x} |\n", p_MOD_LoadPakForMap.GetPtr());
spdlog::debug("| FUN: MOD_ProcessPakQueue : {:#18x} |\n", p_MOD_ProcessPakQueue.GetPtr());
spdlog::debug("+----------------------------------------------------------------+\n");
spdlog::debug("| FUN: sub_1401F9C10 : {:#18x} |\n", reinterpret_cast<uintptr_t>(sub_1401F9C10));
spdlog::debug("| FUN: sub_14045BAC0 : {:#18x} |\n", reinterpret_cast<uintptr_t>(sub_14045BAC0));
spdlog::debug("| FUN: sub_14045A1D0 : {:#18x} |\n", reinterpret_cast<uintptr_t>(sub_14045A1D0));
spdlog::debug("| FUN: sub_140441220 : {:#18x} |\n", reinterpret_cast<uintptr_t>(sub_140441220));
spdlog::debug("| VAR: dword_14B383420 : {:#18x} |\n", reinterpret_cast<uintptr_t>(dword_14B383420));
spdlog::debug("| VAR: dword_1634F445C : {:#18x} |\n", reinterpret_cast<uintptr_t>(dword_1634F445C));
spdlog::debug("| VAR: qword_167ED7BB8 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_167ED7BB8));
spdlog::debug("| VAR: qword_14180A098 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_14180A098));
spdlog::debug("| VAR: byte_16709DDDF : {:#18x} |\n", reinterpret_cast<uintptr_t>(byte_16709DDDF));
spdlog::debug("| VAR: g_FileSystem : {:#18x} |\n", reinterpret_cast<uintptr_t>(g_FileSystem));
spdlog::debug("| VAR: off_141874660 : {:#18x} |\n", reinterpret_cast<uintptr_t>(off_141874660));
spdlog::debug("| VAR: unk_141874555 : {:#18x} |\n", reinterpret_cast<uintptr_t>(unk_141874555));
spdlog::debug("| VAR: unk_167D40B70 : {:#18x} |\n", reinterpret_cast<uintptr_t>(unk_167D40B70));
spdlog::debug("| VAR: unk_1418749B0 : {:#18x} |\n", reinterpret_cast<uintptr_t>(unk_1418749B0));
spdlog::debug("| VAR: unk_141874550 : {:#18x} |\n", reinterpret_cast<uintptr_t>(unk_141874550));
spdlog::debug("| VAR: qword_1671061C8 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_1671061C8));
spdlog::debug("| VAR: qword_167ED7BC0 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_167ED7BC0));
spdlog::debug("| VAR: qword_167ED7C68 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_167ED7C68));
spdlog::debug("| VAR: qword_167ED7BE0 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_167ED7BE0));
spdlog::debug("| VAR: qword_14045C070 : {:#18x} |\n", reinterpret_cast<uintptr_t>(qword_14045C070));
spdlog::debug("| VAR: dword_1641E443C : {:#18x} |\n", reinterpret_cast<uintptr_t>(dword_1641E443C));
spdlog::debug("| VAR: byte_167208B0C : {:#18x} |\n", reinterpret_cast<uintptr_t>(byte_167208B0C));
spdlog::debug("+----------------------------------------------------------------+\n"); spdlog::debug("+----------------------------------------------------------------+\n");
} }
virtual void GetFun(void) const virtual void GetFun(void) const
@ -30,16 +82,45 @@ class VModel_BSP : public IDetour
CollisionBSPData_LinkPhysics = p_CollisionBSPData_LinkPhysics.RCast<uint64_t(*)(void*)>(); /*48 89 5C 24 ?? 48 89 6C 24 ?? 57 48 81 EC ?? ?? ?? ?? 48 8B F9 33 ED*/ CollisionBSPData_LinkPhysics = p_CollisionBSPData_LinkPhysics.RCast<uint64_t(*)(void*)>(); /*48 89 5C 24 ?? 48 89 6C 24 ?? 57 48 81 EC ?? ?? ?? ?? 48 8B F9 33 ED*/
p_MOD_LoadPakForMap = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x81\xEC\x00\x00\x00\x00\x4C\x8B\xC1\x48\x8D\x15\x00\x00\x00\x00\x48\x8D\x4C\x24\x00\xE8\x00\x00\x00\x00\x4C\x8D\x0D\x00\x00\x00\x00"), "xxx????xxxxxx????xxxx?x????xxx????"); p_MOD_LoadPakForMap = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x81\xEC\x00\x00\x00\x00\x4C\x8B\xC1\x48\x8D\x15\x00\x00\x00\x00\x48\x8D\x4C\x24\x00\xE8\x00\x00\x00\x00\x4C\x8D\x0D\x00\x00\x00\x00"), "xxx????xxxxxx????xxxx?x????xxx????");
v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(void)>(); /*48 81 EC ? ? ? ? 4C 8B C1 48 8D 15 ? ? ? ? 48 8D 4C 24 ? E8 ? ? ? ? 4C 8D 0D ? ? ? ?*/ v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(const char*)>(); /*48 81 EC ? ? ? ? 4C 8B C1 48 8D 15 ? ? ? ? 48 8D 4C 24 ? E8 ? ? ? ? 4C 8D 0D ? ? ? ?*/
#elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3) #elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3)
p_CollisionBSPData_LinkPhysics = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x6C\x24\x00\x57\x48\x81\xEC\x00\x00\x00\x00\x48\x8B\xF9\x33\xED"), "xxxx?xxxx?xxxx????xxxxx"); p_CollisionBSPData_LinkPhysics = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x6C\x24\x00\x57\x48\x81\xEC\x00\x00\x00\x00\x48\x8B\xF9\x33\xED"), "xxxx?xxxx?xxxx????xxxxx");
CollisionBSPData_LinkPhysics = p_CollisionBSPData_LinkPhysics.RCast<uint64_t(*)(void*)>(); /*48 89 5C 24 ?? 48 89 6C 24 ?? 57 48 81 EC ?? ?? ?? ?? 48 8B F9 33 ED*/ CollisionBSPData_LinkPhysics = p_CollisionBSPData_LinkPhysics.RCast<uint64_t(*)(void*)>(); /*48 89 5C 24 ?? 48 89 6C 24 ?? 57 48 81 EC ?? ?? ?? ?? 48 8B F9 33 ED*/
p_MOD_LoadPakForMap = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x81\xEC\x00\x00\x00\x00\x0F\xB6\x05\x00\x00\x00\x00\x4C\x8D\x05\x00\x00\x00\x00\x84\xC0"), "xxx????xxx????xxx????xx"); p_MOD_LoadPakForMap = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x81\xEC\x00\x00\x00\x00\x0F\xB6\x05\x00\x00\x00\x00\x4C\x8D\x05\x00\x00\x00\x00\x84\xC0"), "xxx????xxx????xxx????xx");
v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(void* pBuffer)>(); /*48 81 EC ? ? ? ? 0F B6 05 ? ? ? ? 4C 8D 05 ? ? ? ? 84 C0*/ v_MOD_LoadPakForMap = p_MOD_LoadPakForMap.RCast<bool(*)(const char*)>(); /*48 81 EC ? ? ? ? 0F B6 05 ? ? ? ? 4C 8D 05 ? ? ? ? 84 C0*/
#endif #endif
p_MOD_ProcessPakQueue = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x40\x53\x48\x83\xEC\x00\xF3\x0F\x10\x05\x00\x00\x00\x00\x32\xDB"), "xxxxx?xxxx????xx");
v_MOD_ProcessPakQueue = p_MOD_ProcessPakQueue.RCast<void(*)(void)>(); /*40 53 48 83 EC ?? F3 0F 10 05 ? ? ? ? 32 DB*/
sub_1401F9C10 = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x0F\xB6\x02\x45\x33\xDB"), "xxxxxx").RCast<__int64(*)(char* a1, char* a2, __int64 a3)>();
sub_14045BAC0 = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x4C\x89\x4C\x24\x00\x4C\x89\x44\x24\x00\x55\x56\x57\x41\x54\x41\x55\x41\x56\x41\x57\x48\x83\xEC\x60"), "xxxx?xxxx?xxxx?xxxxxxxxxxxxxxx").RCast<__int64(*)(__int64(__fastcall* a1)(__int64, _DWORD*, __int64, _QWORD*), __int64 a2, __int64 a3, __int64 a4)>();
sub_14045A1D0 = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x4C\x89\x4C\x24\x00\x4C\x89\x44\x24\x00\x48\x89\x54\x24\x00\x48\x89\x4C\x24\x00\x55\x53\x56\x57\x41\x54\x41\x55\x41\x56\x41\x57\x48\x8D\x6C\x24\x00"), "xxxx?xxxx?xxxx?xxxx?xxxxxxxxxxxxxxxx?").RCast<__int64(*)(unsigned __int8(__fastcall* a1)(_QWORD), __int64 a2, __int64 a3, __int64 a4, volatile signed __int64* a5, char a6)>();
sub_140441220 = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x6C\x24\x00\x48\x89\x74\x24\x00\x57\x48\x83\xEC\x20\x33\xED\x48\x8D\x35\x00\x00\x00\x00\x48\x39\x2D\x00\x00\x00\x00"), "xxxx?xxxx?xxxx?xxxxxxxxxx????xxx????").RCast<void(*)(__int64 a1, __int64 a2)>();
}
virtual void GetVar(void) const
{
dword_14B383420 = p_MOD_ProcessPakQueue.FindPattern("F3 0F 10").ResolveRelativeAddressSelf(0x4, 0x8).RCast<float*>();
dword_1634F445C = p_MOD_ProcessPakQueue.FindPattern("8B 05").ResolveRelativeAddressSelf(0x2, 0x6).RCast<int32_t*>();
qword_167ED7BB8 = p_MOD_ProcessPakQueue.Offset(0x10).FindPattern("48 83").ResolveRelativeAddressSelf(0x3, 0x8).RCast<void**>();
qword_14180A098 = p_MOD_ProcessPakQueue.Offset(0x20).FindPattern("83 3D").ResolveRelativeAddressSelf(0x2, 0x7).RCast<void**>();
byte_16709DDDF = p_MOD_ProcessPakQueue.Offset(0x20).FindPattern("88 1D").ResolveRelativeAddressSelf(0x2, 0x6).RCast<bool*>();
g_FileSystem = p_MOD_ProcessPakQueue.Offset(0x20).FindPattern("48 8B").ResolveRelativeAddressSelf(0x3, 0x7).RCast<int64_t*>();
off_141874660 = p_MOD_ProcessPakQueue.Offset(0x40).FindPattern("4C 8D 15").ResolveRelativeAddressSelf(0x3, 0x7).RCast<char**>();
unk_141874555 = p_MOD_ProcessPakQueue.Offset(0x40).FindPattern("4C 8D 1D").ResolveRelativeAddressSelf(0x3, 0x7).RCast<void**>();
unk_167D40B70 = p_MOD_ProcessPakQueue.Offset(0xA0).FindPattern("4C 8D 35").ResolveRelativeAddressSelf(0x3, 0x7).RCast<void**>();
unk_1418749B0 = p_MOD_ProcessPakQueue.Offset(0xA0).FindPattern("48 8D 1D").ResolveRelativeAddressSelf(0x3, 0x7).RCast<void**>();
unk_141874550 = p_MOD_ProcessPakQueue.Offset(0x150).FindPattern("48 8D 2D").ResolveRelativeAddressSelf(0x3, 0x7).RCast<void**>();
qword_1671061C8 = p_MOD_ProcessPakQueue.Offset(0x200).FindPattern("48 8B 1D").ResolveRelativeAddressSelf(0x3, 0x7).RCast<int64_t*>();
qword_167ED7BC0 = p_MOD_ProcessPakQueue.Offset(0x200).FindPattern("48 83 3D").ResolveRelativeAddressSelf(0x3, 0x8).RCast<int64_t*>();
qword_167ED7C68 = p_MOD_ProcessPakQueue.Offset(0x200).FindPattern("0F B7 05").ResolveRelativeAddressSelf(0x3, 0x7).RCast<int64_t*>();
qword_167ED7BE0 = p_MOD_ProcessPakQueue.Offset(0x250).FindPattern("48 8D 0D").ResolveRelativeAddressSelf(0x3, 0x7).RCast<int64_t*>();
qword_14045C070 = p_MOD_ProcessPakQueue.Offset(0x2A0).FindPattern("48 8D 0D").ResolveRelativeAddressSelf(0x3, 0x7).RCast<int64_t*>();
dword_1641E443C = p_MOD_ProcessPakQueue.Offset(0x2A0).FindPattern("3B 05").ResolveRelativeAddressSelf(0x2, 0x6).RCast<int32_t*>();
byte_167208B0C = p_MOD_ProcessPakQueue.Offset(0x2A0).FindPattern("C6 05").ResolveRelativeAddressSelf(0x2, 0x7).RCast<bool*>();
(*((char**)(&qword_167ED7C68))) -= 6;
} }
virtual void GetVar(void) const { }
virtual void GetCon(void) const { } virtual void GetCon(void) const { }
virtual void Attach(void) const { } virtual void Attach(void) const { }
virtual void Detach(void) const { } virtual void Detach(void) const { }

View File

@ -46,9 +46,6 @@
#include "game/server/gameinterface.h" #include "game/server/gameinterface.h"
#endif // !CLIENT_DLL #endif // !CLIENT_DLL
bool g_bLevelResourceInitialized = false;
bool g_bBasePaksInitialized = false;
string g_svPrevLevelName;
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Purpose: state machine's main processing loop // Purpose: state machine's main processing loop
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -93,13 +90,11 @@ FORCEINLINE void CHostState::FrameUpdate(CHostState* rcx, void* rdx, float time)
case HostStates_t::HS_CHANGE_LEVEL_SP: case HostStates_t::HS_CHANGE_LEVEL_SP:
{ {
g_pHostState->State_ChangeLevelSP(); g_pHostState->State_ChangeLevelSP();
g_pHostState->UnloadPakFile(); // Unload our loaded rpaks. Calling this before the actual level change happens kills the game.
break; break;
} }
case HostStates_t::HS_CHANGE_LEVEL_MP: case HostStates_t::HS_CHANGE_LEVEL_MP:
{ {
g_pHostState->State_ChangeLevelMP(); g_pHostState->State_ChangeLevelMP();
g_pHostState->UnloadPakFile();
break; break;
} }
case HostStates_t::HS_RUN: case HostStates_t::HS_RUN:
@ -113,14 +108,12 @@ FORCEINLINE void CHostState::FrameUpdate(CHostState* rcx, void* rdx, float time)
if (g_pHostState->m_bActiveGame) { if (g_pHostState->m_bActiveGame) {
g_pHostState->ResetLevelName(); g_pHostState->ResetLevelName();
} }
g_bLevelResourceInitialized = false;
CHostState_State_GameShutDown(g_pHostState); CHostState_State_GameShutDown(g_pHostState);
break; break;
} }
case HostStates_t::HS_RESTART: case HostStates_t::HS_RESTART:
{ {
DevMsg(eDLL_T::ENGINE, "%s - Restarting state machine\n", "CHostState::FrameUpdate"); DevMsg(eDLL_T::ENGINE, "%s - Restarting state machine\n", "CHostState::FrameUpdate");
g_bLevelResourceInitialized = false;
#ifndef DEDICATED #ifndef DEDICATED
CL_EndMovie(); CL_EndMovie();
#endif // !DEDICATED #endif // !DEDICATED
@ -131,7 +124,6 @@ FORCEINLINE void CHostState::FrameUpdate(CHostState* rcx, void* rdx, float time)
case HostStates_t::HS_SHUTDOWN: case HostStates_t::HS_SHUTDOWN:
{ {
DevMsg(eDLL_T::ENGINE, "%s - Shutdown state machine\n", "CHostState::FrameUpdate"); DevMsg(eDLL_T::ENGINE, "%s - Shutdown state machine\n", "CHostState::FrameUpdate");
g_bLevelResourceInitialized = false;
#ifndef DEDICATED #ifndef DEDICATED
CL_EndMovie(); CL_EndMovie();
#endif // !DEDICATED #endif // !DEDICATED
@ -177,7 +169,6 @@ FORCEINLINE void CHostState::Init(void)
m_vecLocation.Init(); m_vecLocation.Init();
m_angLocation.Init(); m_angLocation.Init();
m_iCurrentState = HostStates_t::HS_NEW_GAME; m_iCurrentState = HostStates_t::HS_NEW_GAME;
g_svPrevLevelName = m_levelName;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -291,7 +282,6 @@ FORCEINLINE void CHostState::LoadConfig(void) const
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
FORCEINLINE void CHostState::GameShutDown(void) FORCEINLINE void CHostState::GameShutDown(void)
{ {
g_bLevelResourceInitialized = false;
if (m_bActiveGame) if (m_bActiveGame)
{ {
#ifndef CLIENT_DLL #ifndef CLIENT_DLL
@ -303,32 +293,6 @@ FORCEINLINE void CHostState::GameShutDown(void)
} }
} }
//-----------------------------------------------------------------------------
// Purpose: unloads all pakfiles loaded by the SDK
//-----------------------------------------------------------------------------
FORCEINLINE void CHostState::UnloadPakFile(void) const
{
if (g_pHostState->m_iCurrentState != HostStates_t::HS_SHUTDOWN && !LevelHasChanged())
return; // Do not issue unload if we reload the same level.
for (auto& it : g_LoadedPakHandle)
{
if (it >= 0)
{
#ifdef GAMEDLL_S3
RPakLoadedInfo_t pakInfo = g_pRTech->GetPakLoadedInfo(it);
if (pakInfo.m_pszFileName)
{
DevMsg(eDLL_T::RTECH, "%s - Unloading PakFile '%s'\n", "CHostState::UnloadPakFile", pakInfo.m_pszFileName);
}
#endif // GAMEDLL_S3
CPakFile_UnloadPak(it);
}
}
g_LoadedPakHandle.clear();
g_BadMDLHandles.clear();
}
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
// Purpose: initialize new game // Purpose: initialize new game
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -336,7 +300,6 @@ FORCEINLINE void CHostState::State_NewGame(void)
{ {
LARGE_INTEGER time{}; LARGE_INTEGER time{};
g_bLevelResourceInitialized = false;
m_bSplitScreenConnect = false; m_bSplitScreenConnect = false;
#ifndef CLIENT_DLL #ifndef CLIENT_DLL
if (!g_pServerGameClients) // Init Game if it ain't valid. if (!g_pServerGameClients) // Init Game if it ain't valid.
@ -364,7 +327,6 @@ FORCEINLINE void CHostState::State_NewGame(void)
{ {
m_iNextState = HostStates_t::HS_RUN; m_iNextState = HostStates_t::HS_RUN;
} }
g_svPrevLevelName = m_levelName;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -374,7 +336,6 @@ FORCEINLINE void CHostState::State_ChangeLevelSP(void)
{ {
DevMsg(eDLL_T::ENGINE, "%s - Changing singleplayer level to: '%s'\n", "CHostState::State_ChangeLevelSP", m_levelName); DevMsg(eDLL_T::ENGINE, "%s - Changing singleplayer level to: '%s'\n", "CHostState::State_ChangeLevelSP", m_levelName);
m_flShortFrameTime = 1.5; // Set frame time. m_flShortFrameTime = 1.5; // Set frame time.
g_bLevelResourceInitialized = false;
if (CModelLoader__Map_IsValid(g_pModelLoader, m_levelName)) // Check if map is valid and if we can start a new game. if (CModelLoader__Map_IsValid(g_pModelLoader, m_levelName)) // Check if map is valid and if we can start a new game.
{ {
@ -392,7 +353,6 @@ FORCEINLINE void CHostState::State_ChangeLevelSP(void)
{ {
m_iNextState = HostStates_t::HS_RUN; m_iNextState = HostStates_t::HS_RUN;
} }
g_svPrevLevelName = m_levelName;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -402,7 +362,6 @@ FORCEINLINE void CHostState::State_ChangeLevelMP(void)
{ {
DevMsg(eDLL_T::ENGINE, "%s - Changing multiplayer level to: '%s'\n", "CHostState::State_ChangeLevelMP", m_levelName); DevMsg(eDLL_T::ENGINE, "%s - Changing multiplayer level to: '%s'\n", "CHostState::State_ChangeLevelMP", m_levelName);
m_flShortFrameTime = 0.5; // Set frame time. m_flShortFrameTime = 0.5; // Set frame time.
g_bLevelResourceInitialized = false;
#ifndef CLIENT_DLL #ifndef CLIENT_DLL
g_pServerGameDLL->LevelShutdown(); g_pServerGameDLL->LevelShutdown();
@ -426,7 +385,6 @@ FORCEINLINE void CHostState::State_ChangeLevelMP(void)
{ {
m_iNextState = HostStates_t::HS_RUN; m_iNextState = HostStates_t::HS_RUN;
} }
g_svPrevLevelName = m_levelName;
} }
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
@ -442,15 +400,6 @@ FORCEINLINE void CHostState::ResetLevelName(void)
snprintf(const_cast<char*>(m_levelName), sizeof(m_levelName), szNoMap); snprintf(const_cast<char*>(m_levelName), sizeof(m_levelName), szNoMap);
} }
//-----------------------------------------------------------------------------
// Purpose: checks if level has changed
// Output : true if level name deviates from previous level
//-----------------------------------------------------------------------------
FORCEINLINE bool CHostState::LevelHasChanged(void) const
{
return (strcmp(m_levelName, g_svPrevLevelName.c_str()) != 0);
}
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void CHostState_Attach() void CHostState_Attach()
{ {

View File

@ -25,14 +25,12 @@ public:
FORCEINLINE void Think(void) const; FORCEINLINE void Think(void) const;
FORCEINLINE void GameShutDown(void); FORCEINLINE void GameShutDown(void);
FORCEINLINE void UnloadPakFile(void) const;
FORCEINLINE void State_NewGame(void); FORCEINLINE void State_NewGame(void);
FORCEINLINE void State_ChangeLevelSP(void); FORCEINLINE void State_ChangeLevelSP(void);
FORCEINLINE void State_ChangeLevelMP(void); FORCEINLINE void State_ChangeLevelMP(void);
FORCEINLINE void ResetLevelName(void); FORCEINLINE void ResetLevelName(void);
FORCEINLINE bool LevelHasChanged(void) const;
public: public:
HostStates_t m_iCurrentState; //0x0000 HostStates_t m_iCurrentState; //0x0000
@ -62,8 +60,6 @@ inline auto CHostState_State_Run = p_CHostState_State_Run.RCast<void(*)(HostStat
inline CMemory p_CHostState_State_GameShutDown; inline CMemory p_CHostState_State_GameShutDown;
inline auto CHostState_State_GameShutDown = p_CHostState_State_GameShutDown.RCast<void(*)(CHostState* thisptr)>(); inline auto CHostState_State_GameShutDown = p_CHostState_State_GameShutDown.RCast<void(*)(CHostState* thisptr)>();
extern bool g_bLevelResourceInitialized;
extern bool g_bBasePaksInitialized;
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
void CHostState_Attach(); void CHostState_Attach();
void CHostState_Detach(); void CHostState_Detach();

View File

@ -9,6 +9,7 @@
#include "engine/host_state.h" #include "engine/host_state.h"
#include "engine/cmodel_bsp.h" #include "engine/cmodel_bsp.h"
#include "rtech/rtech_game.h" #include "rtech/rtech_game.h"
#include "rtech/rtech_utils.h"
vector<RPakHandle_t> g_LoadedPakHandle{ }; vector<RPakHandle_t> g_LoadedPakHandle{ };
@ -41,20 +42,6 @@ RPakHandle_t CPakFile::AsyncLoad(const char* szPakFileName, uintptr_t pMalloc, i
} }
#endif // DEDICATED #endif // DEDICATED
if (strcmp(szPakFileName, "mp_lobby.rpak") == 0)
g_bBasePaksInitialized = true;
static bool bOnce = false;
if (g_bBasePaksInitialized && !g_bLevelResourceInitialized
&& !bOnce)
{
g_bLevelResourceInitialized = true;
bOnce = true;
if (g_pHostState->LevelHasChanged())
MOD_PreloadPak();
}
string svPakFilePathMod = "paks\\Win32\\" + string(szPakFileName); string svPakFilePathMod = "paks\\Win32\\" + string(szPakFileName);
string svPakFilePathBase = "paks\\Win64\\" + string(szPakFileName); string svPakFilePathBase = "paks\\Win64\\" + string(szPakFileName);
@ -75,6 +62,25 @@ RPakHandle_t CPakFile::AsyncLoad(const char* szPakFileName, uintptr_t pMalloc, i
return pakHandle; return pakHandle;
} }
//-----------------------------------------------------------------------------
// Purpose: unloads loaded pak files
// Input : handle -
//-----------------------------------------------------------------------------
void CPakFile::Unload(RPakHandle_t handle)
{
RPakLoadedInfo_t pakInfo = g_pRTech->GetPakLoadedInfo(handle);
if (pakInfo.m_pszFileName)
{
DevMsg(eDLL_T::RTECH, "%s - Unloading PakFile '%s'\n", __FUNCTION__, pakInfo.m_pszFileName);
if (strcmp(pakInfo.m_pszFileName, "mp_lobby.rpak") == 0)
s_bBasePaksInitialized = false;
}
CPakFile_UnloadPak(handle);
}
void RTech_Game_Attach() void RTech_Game_Attach()
{ {
DetourAttach((LPVOID*)&CPakFile_AsyncLoad, &CPakFile::AsyncLoad); DetourAttach((LPVOID*)&CPakFile_AsyncLoad, &CPakFile::AsyncLoad);

View File

@ -36,12 +36,13 @@ inline CMemory p_CPakFile_AsyncLoad;
inline auto CPakFile_AsyncLoad = p_CPakFile_AsyncLoad.RCast<RPakHandle_t(*)(const char* svPakFileName, uintptr_t pMalloc, int nIdx, bool bUnk)>(); inline auto CPakFile_AsyncLoad = p_CPakFile_AsyncLoad.RCast<RPakHandle_t(*)(const char* svPakFileName, uintptr_t pMalloc, int nIdx, bool bUnk)>();
inline CMemory p_CPakFile_UnloadPak; inline CMemory p_CPakFile_UnloadPak;
inline auto CPakFile_UnloadPak = p_CPakFile_UnloadPak.RCast<void* (*)(RPakHandle_t handle)>(); inline auto CPakFile_UnloadPak = p_CPakFile_UnloadPak.RCast<void (*)(RPakHandle_t handle)>();
class CPakFile class CPakFile
{ {
public: public:
static RPakHandle_t AsyncLoad(const char* szPakFileName, uintptr_t pMalloc = g_pMallocPool.GetPtr(), int nIdx = NULL, bool bUnk = false); static RPakHandle_t AsyncLoad(const char* szPakFileName, uintptr_t pMalloc = g_pMallocPool.GetPtr(), int nIdx = NULL, bool bUnk = false);
static void Unload(RPakHandle_t handle);
}; };
extern CPakFile* g_pakLoadApi; extern CPakFile* g_pakLoadApi;
@ -80,7 +81,7 @@ class VRTechGame : public IDetour
CPakFile_AsyncLoad = p_CPakFile_AsyncLoad.RCast<RPakHandle_t(*)(const char*, uintptr_t, int, bool)>(); /*40 53 48 83 EC 40 48 89 6C 24 ? 41 0F B6 E9*/ CPakFile_AsyncLoad = p_CPakFile_AsyncLoad.RCast<RPakHandle_t(*)(const char*, uintptr_t, int, bool)>(); /*40 53 48 83 EC 40 48 89 6C 24 ? 41 0F B6 E9*/
#endif #endif
p_CPakFile_UnloadPak = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x74\x24\x00\x57\x48\x83\xEC\x30\x8B\xC1"), "xxxx?xxxx?xxxxxxx"); p_CPakFile_UnloadPak = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x74\x24\x00\x57\x48\x83\xEC\x30\x8B\xC1"), "xxxx?xxxx?xxxxxxx");
CPakFile_UnloadPak = p_CPakFile_UnloadPak.RCast<void* (*)(RPakHandle_t)>(); /*48 89 5C 24 ? 48 89 74 24 ? 57 48 83 EC 30 8B C1*/ CPakFile_UnloadPak = p_CPakFile_UnloadPak.RCast<void (*)(RPakHandle_t)>(); /*48 89 5C 24 ? 48 89 74 24 ? 57 48 83 EC 30 8B C1*/
} }
virtual void GetVar(void) const { } virtual void GetVar(void) const { }
virtual void GetCon(void) const { } virtual void GetCon(void) const { }

View File

@ -1,11 +1,18 @@
#ifndef JOBTHREAD_H #ifndef JOBTHREAD_H
#define JOBTHREAD_H #define JOBTHREAD_H
struct JobFifoLock_s
{
};
inline CMemory p_JT_HelpWithAnything; inline CMemory p_JT_HelpWithAnything;
inline auto JT_HelpWithAnything = p_JT_HelpWithAnything.RCast<void* (*)(bool bShouldLoadPak)>(); inline auto JT_HelpWithAnything = p_JT_HelpWithAnything.RCast<void* (*)(bool bShouldLoadPak)>();
inline CMemory p_JT_AcquireFifoLock; inline CMemory p_JT_AcquireFifoLock;
inline auto JT_AcquireFifoLock = p_JT_AcquireFifoLock.RCast<void* (*)(void)>(); inline auto JT_AcquireFifoLock = p_JT_AcquireFifoLock.RCast<bool (*)(struct JobFifoLock_s* pFifo)>();
inline CMemory p_JT_ReleaseFifoLock;
inline auto JT_ReleaseFifoLock = p_JT_ReleaseFifoLock.RCast<void (*)(struct JobFifoLock_s* pFifo)>();
void JT_Attach(); void JT_Attach();
void JT_Detach(); void JT_Detach();
@ -16,6 +23,7 @@ class VJobThread : public IDetour
{ {
spdlog::debug("| FUN: JT_HelpWithAnything : {:#18x} |\n", p_JT_HelpWithAnything.GetPtr()); spdlog::debug("| FUN: JT_HelpWithAnything : {:#18x} |\n", p_JT_HelpWithAnything.GetPtr());
spdlog::debug("| FUN: JT_AcquireFifoLock : {:#18x} |\n", p_JT_AcquireFifoLock.GetPtr()); spdlog::debug("| FUN: JT_AcquireFifoLock : {:#18x} |\n", p_JT_AcquireFifoLock.GetPtr());
spdlog::debug("| FUN: JT_ReleaseFifoLock : {:#18x} |\n", p_JT_ReleaseFifoLock.GetPtr());
spdlog::debug("+----------------------------------------------------------------+\n"); spdlog::debug("+----------------------------------------------------------------+\n");
} }
virtual void GetFun(void) const virtual void GetFun(void) const
@ -25,10 +33,12 @@ class VJobThread : public IDetour
#elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3) #elif defined (GAMEDLL_S2) || defined (GAMEDLL_S3)
p_JT_HelpWithAnything = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x74\x24\x00\x57\x48\x83\xEC\x30\x80\x3D\x00\x00\x00\x00\x00"), "xxxx?xxxx?xxxxxxx?????"); p_JT_HelpWithAnything = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x89\x5C\x24\x00\x48\x89\x74\x24\x00\x57\x48\x83\xEC\x30\x80\x3D\x00\x00\x00\x00\x00"), "xxxx?xxxx?xxxxxxx?????");
#endif #endif
p_JT_AcquireFifoLock = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x40\x55\x48\x83\xEC\x30\x33\xED"), "xxxxxxxx"); p_JT_AcquireFifoLock = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x83\xEC\x08\x65\x48\x8B\x04\x25\x00\x00\x00\x00\x4C\x8B\xC1"), "xxxxxxxxx????xxx");
p_JT_ReleaseFifoLock = g_mGameDll.FindPatternSIMD(reinterpret_cast<rsig_t>("\x48\x83\xEC\x28\x44\x8B\x11"), "xxxxxxx");
JT_HelpWithAnything = p_JT_HelpWithAnything.RCast<void* (*)(bool bShouldLoadPak)>(); /*48 89 5C 24 ?? 48 89 74 24 ?? 57 48 83 EC 30 80 3D ?? ?? ?? ?? ??*/ JT_HelpWithAnything = p_JT_HelpWithAnything.RCast<void* (*)(bool bShouldLoadPak)>(); /*48 89 5C 24 ?? 48 89 74 24 ?? 57 48 83 EC 30 80 3D ?? ?? ?? ?? ??*/
JT_AcquireFifoLock = p_JT_AcquireFifoLock.RCast<void* (*)(void)>(); /*40 55 48 83 EC 30 33 ED*/ JT_AcquireFifoLock = p_JT_AcquireFifoLock.RCast<bool (*)(struct JobFifoLock_s*)>(); /*48 83 EC 08 65 48 8B 04 25 ?? ?? ?? ?? 4C 8B C1*/
JT_ReleaseFifoLock = p_JT_ReleaseFifoLock.RCast<void (*)(struct JobFifoLock_s*)>(); /*48 83 EC 28 44 8B 11*/
} }
virtual void GetVar(void) const { } virtual void GetVar(void) const { }
virtual void GetCon(void) const { } virtual void GetCon(void) const { }

View File

@ -369,7 +369,7 @@ void _Pak_RequestUnload_f_CompletionFunc(const CCommand& args)
int nPakId = std::stoi(args.Arg(1)); int nPakId = std::stoi(args.Arg(1));
RPakLoadedInfo_t pakInfo = g_pRTech->GetPakLoadedInfo(nPakId); RPakLoadedInfo_t pakInfo = g_pRTech->GetPakLoadedInfo(nPakId);
pakInfo.m_pszFileName ? DevMsg(eDLL_T::RTECH, "Requested Pak Unload for '%s'\n", pakInfo.m_pszFileName) : DevMsg(eDLL_T::RTECH, "Requested Pak Unload for '%d'\n", nPakId); pakInfo.m_pszFileName ? DevMsg(eDLL_T::RTECH, "Requested Pak Unload for '%s'\n", pakInfo.m_pszFileName) : DevMsg(eDLL_T::RTECH, "Requested Pak Unload for '%d'\n", nPakId);
CPakFile_UnloadPak(nPakId); g_pakLoadApi->Unload(nPakId);
} }
else else
{ {