Forcefully disable item schema update on beta branches

Remove signature for filesystem, fetch it from factory instead
This commit is contained in:
ficool2 2023-10-23 17:48:12 +01:00
parent d39ee5a0b3
commit cb1e6461c6
5 changed files with 88 additions and 28 deletions

View File

@ -1,6 +1,9 @@
# Custom Items Games plugin # Custom Items Games plugin
This client-side plugin bypasses integrity checks for items_games.txt and proto_defs.vpd in Team Fortress 2. The plugin will only work locally, and it is VAC-safe. Signature scanning is used which should make the plugin work consistently after updates. This client-side plugin bypasses integrity checks for items_games.txt and proto_defs.vpd in Team Fortress 2. The plugin will only work locally, and it is VAC-safe. Signature scanning is used which should make the plugin work consistently after updates.
## Beta branches
Beta branches `pre_07_25_23_demos` and `pre_smissmas_2022_demos` currently crash on boot due to the newer item schema. This plugin supports these branches and will also fix these crashes, by forcefully disabling item schema updating.
## Installation ## Installation
* Download the latest release and extract the "addons" folder to TF2's main folder (../common/Team Fortress 2/tf). * Download the latest release and extract the "addons" folder to TF2's main folder (../common/Team Fortress 2/tf).
* Go into tf/scripts/items, copy the items_game.txt and rename it to items_game_custom.txt. This file will be loaded instead of the original items_games.txt. proto_defs.vpd will still load the same file. * Go into tf/scripts/items, copy the items_game.txt and rename it to items_game_custom.txt. This file will be loaded instead of the original items_games.txt. proto_defs.vpd will still load the same file.

View File

@ -21,6 +21,7 @@
<ItemGroup> <ItemGroup>
<ClInclude Include="address.h" /> <ClInclude Include="address.h" />
<ClInclude Include="detours.h" /> <ClInclude Include="detours.h" />
<ClInclude Include="filesystem.h" />
<ClInclude Include="functions.h" /> <ClInclude Include="functions.h" />
<ClInclude Include="helpers.h" /> <ClInclude Include="helpers.h" />
<ClInclude Include="module.h" /> <ClInclude Include="module.h" />

29
filesystem.h Normal file
View File

@ -0,0 +1,29 @@
#pragma once
#include <stdio.h>
#define BASEFILESYSTEM_INTERFACE_VERSION "VBaseFileSystem011"
typedef void* FileHandle_t;
enum FileSystemSeek_t
{
FILESYSTEM_SEEK_HEAD = SEEK_SET,
FILESYSTEM_SEEK_CURRENT = SEEK_CUR,
FILESYSTEM_SEEK_TAIL = SEEK_END,
};
class IBaseFileSystem
{
public:
virtual int Read(void* pOutput, int size, FileHandle_t file) = 0;
virtual int Write(void const* pInput, int size, FileHandle_t file) = 0;
virtual FileHandle_t Open(const char* pFileName, const char* pOptions, const char* pathID = 0) = 0;
virtual void Close(FileHandle_t file) = 0;
virtual void Seek(FileHandle_t file, int pos, FileSystemSeek_t seekType) = 0;
virtual unsigned int Tell(FileHandle_t file) = 0;
virtual unsigned int Size(FileHandle_t file) = 0;
virtual unsigned int Size(const char* pFileName, const char* pPathID = 0) = 0;
virtual void Flush(FileHandle_t file) = 0;
virtual bool Precache(const char* pFileName, const char* pPathID = 0) = 0;
virtual bool FileExists(const char* pFileName, const char* pPathID = 0) = 0;
};

View File

@ -1,25 +1,7 @@
#pragma optimize("", off)
#define CUSTOM_ITEMS_GAME "scripts/items/items_game_custom.txt" #define CUSTOM_ITEMS_GAME "scripts/items/items_game_custom.txt"
#define CUSTOM_ITEMS_GAME_SIG CUSTOM_ITEMS_GAME ".sig" #define CUSTOM_ITEMS_GAME_SIG CUSTOM_ITEMS_GAME ".sig"
intptr_t server_fileSystem = 0; extern IBaseFileSystem* filesystem;
void gameStats_loadFromFile_resolve(AddressInfo<intptr_t>& addr, ModuleName mod)
{
server_fileSystem = Deref(addr[mod] + 42);
Log(Color(0, 255, 200, 255), "Filesystem found at 0x%X in %s.%s\n", server_fileSystem, modules[mod].name, "dll");
}
typedef intptr_t gameStats_loadFromFile;
ADDR_CALLBACK(
gameStats_loadFromFile,
"CBaseGameStats::LoadFromFile",
MOD_SERVER,
\x55\x8B\xEC\x81\xEC\x38\x02\x00\x00\xA1\x2A\x2A\x2A\x2A,
xxxxxxxxxx????,
gameStats_loadFromFile_resolve
);
typedef intptr_t (*econItemSystem)(); typedef intptr_t (*econItemSystem)();
ADDR( ADDR(
@ -32,22 +14,15 @@ ADDR(
bool customItemsGameFound = false; bool customItemsGameFound = false;
typedef bool (__thiscall** filesystem_fileExists)(intptr_t, const char*, const char*);
bool function_filesystem_fileExists(const char* filename)
{
intptr_t filesystem = Deref(server_fileSystem) + 4;
return (*(filesystem_fileExists)(Deref(filesystem) + 40))(filesystem, filename, nullptr);
}
bool helper_check_custom_itemsgame() bool helper_check_custom_itemsgame()
{ {
bool foundCustom = true; bool foundCustom = true;
if (!function_filesystem_fileExists(CUSTOM_ITEMS_GAME)) if (!filesystem->FileExists(CUSTOM_ITEMS_GAME))
{ {
Log(Color(255, 0, 127, 255), "Server: %s not found, loading default items_game.txt ...\n", CUSTOM_ITEMS_GAME); Log(Color(255, 0, 127, 255), "Server: %s not found, loading default items_game.txt ...\n", CUSTOM_ITEMS_GAME);
foundCustom = false; foundCustom = false;
} }
if (!function_filesystem_fileExists(CUSTOM_ITEMS_GAME_SIG)) if (!filesystem->FileExists(CUSTOM_ITEMS_GAME_SIG))
{ {
Log(Color(255, 0, 127, 255), "Server: %s not found, loading default items_game.txt ...\n", CUSTOM_ITEMS_GAME_SIG); Log(Color(255, 0, 127, 255), "Server: %s not found, loading default items_game.txt ...\n", CUSTOM_ITEMS_GAME_SIG);
foundCustom = false; foundCustom = false;
@ -96,6 +71,41 @@ void __fastcall hook_client_econItemSystem_parseItemSchemaFile(intptr_t thisptr,
address_econItemSystem_parseItemSchemaFile[MOD_CLIENT](thisptr, edx, filename); address_econItemSystem_parseItemSchemaFile[MOD_CLIENT](thisptr, edx, filename);
} }
bool is_demo_branch()
{
FileHandle_t f = filesystem->Open("steam.inf", "r");
if (!f)
{
Log(Color(255, 0, 0, 255), "Failed to open steam.inf\n");
return false;
}
bool demo_branch = false;
bool patch_version = false;
char buffer[256];
filesystem->Read(buffer, sizeof(buffer), f);
char* p = strtok(buffer, "=\r\n");
while (p)
{
if (patch_version)
{
if (atoi(p) <= 8207200)
demo_branch = true;
break;
}
if (!strcmp(p, "PatchVersion"))
patch_version = true;
p = strtok(NULL, "=\r\n");
}
filesystem->Close(f);
return demo_branch;
}
typedef bool (__fastcall* gcUpdateItemSchema_runJob)(intptr_t, void*, void*); typedef bool (__fastcall* gcUpdateItemSchema_runJob)(intptr_t, void*, void*);
ADDR_GAME( ADDR_GAME(
gcUpdateItemSchema_runJob, gcUpdateItemSchema_runJob,
@ -109,6 +119,10 @@ void __fastcall hook_gcUpdateItemSchema_runJob(intptr_t thisptr, void* edx, void
{ {
Log(Color(0, 255, 127, 255), "Blocked item schema update from GC\n"); Log(Color(0, 255, 127, 255), "Blocked item schema update from GC\n");
} }
else if (is_demo_branch())
{
Log(Color(0, 255, 127, 255), "Forcefully blocked item schema update from GC (demo branch detected)\n");
}
else else
{ {
address_gcUpdateItemSchema_runJob.Resolve(Deref(thisptr))(thisptr, edx, packet); address_gcUpdateItemSchema_runJob.Resolve(Deref(thisptr))(thisptr, edx, packet);

View File

@ -7,6 +7,7 @@
#include "detours.h" #include "detours.h"
#include "plugin.h" #include "plugin.h"
#include "filesystem.h"
#include "helpers.h" #include "helpers.h"
#include "module.h" #include "module.h"
@ -46,6 +47,8 @@ public:
CPlugin g_Plugin; CPlugin g_Plugin;
IBaseFileSystem* filesystem = nullptr;
extern "C" __declspec(dllexport) void* CreateInterface(const char* pName, int* pReturnCode) extern "C" __declspec(dllexport) void* CreateInterface(const char* pName, int* pReturnCode)
{ {
if (!strcmp(INTERFACEVERSION_IPLUGIN, pName)) if (!strcmp(INTERFACEVERSION_IPLUGIN, pName))
@ -68,7 +71,17 @@ BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
bool CPlugin::Load(CreateInterfaceFn interfaceFactory, CreateInterfaceFn gameServerFactory) bool CPlugin::Load(CreateInterfaceFn interfaceFactory, CreateInterfaceFn gameServerFactory)
{ {
if (!FindLog()) if (!FindLog())
{
Log(Color(255, 0, 0, 255), "Failed to find logging func\n");
return false; return false;
}
filesystem = (IBaseFileSystem*)interfaceFactory(BASEFILESYSTEM_INTERFACE_VERSION, NULL);
if (!filesystem)
{
Log(Color(255, 0, 0, 255), "Failed to find filesystem\n");
return false;
}
if (!FindModules()) if (!FindModules())
return false; return false;