Logfile + scripting
This commit is contained in:
parent
a1d2252f6c
commit
a88f117c6e
@ -6,6 +6,7 @@
|
|||||||
#include "game_console.hpp"
|
#include "game_console.hpp"
|
||||||
#include "fastfiles.hpp"
|
#include "fastfiles.hpp"
|
||||||
#include "scheduler.hpp"
|
#include "scheduler.hpp"
|
||||||
|
#include "logfile.hpp"
|
||||||
|
|
||||||
#include "game/game.hpp"
|
#include "game/game.hpp"
|
||||||
#include "game/dvars.hpp"
|
#include "game/dvars.hpp"
|
||||||
@ -40,6 +41,11 @@ namespace command
|
|||||||
|
|
||||||
void client_command(const int client_num)
|
void client_command(const int client_num)
|
||||||
{
|
{
|
||||||
|
if (!logfile::client_command_stub(client_num))
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
params_sv params = {};
|
params_sv params = {};
|
||||||
|
|
||||||
const auto command = utils::string::to_lower(params[0]);
|
const auto command = utils::string::to_lower(params[0]);
|
||||||
|
@ -270,7 +270,15 @@ namespace console
|
|||||||
|
|
||||||
void post_unpack() override
|
void post_unpack() override
|
||||||
{
|
{
|
||||||
ShowWindow(GetConsoleWindow(), SW_SHOW);
|
if (game::environment::is_dedi())
|
||||||
|
{
|
||||||
|
ShowWindow(GetConsoleWindow(), SW_HIDE);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ShowWindow(GetConsoleWindow(), SW_SHOW);
|
||||||
|
}
|
||||||
|
|
||||||
SetConsoleTitle("H1-Mod");
|
SetConsoleTitle("H1-Mod");
|
||||||
|
|
||||||
con.kill_event = CreateEvent(NULL, TRUE, FALSE, NULL);
|
con.kill_event = CreateEvent(NULL, TRUE, FALSE, NULL);
|
||||||
|
@ -12,36 +12,6 @@
|
|||||||
|
|
||||||
namespace filesystem
|
namespace filesystem
|
||||||
{
|
{
|
||||||
namespace
|
|
||||||
{
|
|
||||||
bool custom_path_registered = false;
|
|
||||||
|
|
||||||
std::string get_binary_directory()
|
|
||||||
{
|
|
||||||
const auto dir = game_module::get_host_module().get_folder();
|
|
||||||
return utils::string::replace(dir, "/", "\\");
|
|
||||||
}
|
|
||||||
|
|
||||||
void register_custom_path_stub(const char* path, const char* dir)
|
|
||||||
{
|
|
||||||
if (!custom_path_registered)
|
|
||||||
{
|
|
||||||
custom_path_registered = true;
|
|
||||||
|
|
||||||
const auto launcher_dir = get_binary_directory();
|
|
||||||
game::FS_AddLocalizedGameDirectory(launcher_dir.data(), "data");
|
|
||||||
}
|
|
||||||
|
|
||||||
game::FS_AddLocalizedGameDirectory(path, dir);
|
|
||||||
}
|
|
||||||
|
|
||||||
void fs_startup_stub(const char* gamename)
|
|
||||||
{
|
|
||||||
custom_path_registered = false;
|
|
||||||
game::FS_Startup(gamename);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
file::file(std::string name)
|
file::file(std::string name)
|
||||||
: name_(std::move(name))
|
: name_(std::move(name))
|
||||||
{
|
{
|
||||||
@ -110,19 +80,6 @@ namespace filesystem
|
|||||||
public:
|
public:
|
||||||
void post_unpack() override
|
void post_unpack() override
|
||||||
{
|
{
|
||||||
// Set fs_basegame
|
|
||||||
dvars::override::register_string("fs_basegame", "h1-mod", game::DVAR_FLAG_WRITE);
|
|
||||||
|
|
||||||
utils::hook::call(SELECT_VALUE(0x1403B76E2, 0x1404ED3E2), fs_startup_stub);
|
|
||||||
if (game::environment::is_mp())
|
|
||||||
{
|
|
||||||
utils::hook::call(0x1404ED823, fs_startup_stub);
|
|
||||||
}
|
|
||||||
|
|
||||||
utils::hook::call(SELECT_VALUE(0x1403B8D31, 0x1404EE3D0), register_custom_path_stub);
|
|
||||||
utils::hook::call(SELECT_VALUE(0x1403B8D51, 0x1404EE3F0), register_custom_path_stub);
|
|
||||||
utils::hook::call(SELECT_VALUE(0x1403B8D90, 0x1404EE42F), register_custom_path_stub);
|
|
||||||
|
|
||||||
get_search_paths().insert(".");
|
get_search_paths().insert(".");
|
||||||
get_search_paths().insert("h1-mod");
|
get_search_paths().insert("h1-mod");
|
||||||
get_search_paths().insert("data");
|
get_search_paths().insert("data");
|
||||||
@ -130,4 +87,4 @@ namespace filesystem
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
//REGISTER_COMPONENT(filesystem::component)
|
REGISTER_COMPONENT(filesystem::component)
|
@ -2,15 +2,10 @@
|
|||||||
#include "loader/component_loader.hpp"
|
#include "loader/component_loader.hpp"
|
||||||
#include "scheduler.hpp"
|
#include "scheduler.hpp"
|
||||||
|
|
||||||
#include "game/scripting/entity.hpp"
|
#include "logfile.hpp"
|
||||||
#include "game/scripting/execution.hpp"
|
|
||||||
#include "game/scripting/lua/value_conversion.hpp"
|
|
||||||
#include "game/scripting/lua/error.hpp"
|
|
||||||
|
|
||||||
#include <utils/hook.hpp>
|
#include <utils/hook.hpp>
|
||||||
|
|
||||||
#include "logfile.hpp"
|
|
||||||
|
|
||||||
namespace logfile
|
namespace logfile
|
||||||
{
|
{
|
||||||
std::unordered_map<const char*, sol::protected_function> vm_execute_hooks;
|
std::unordered_map<const char*, sol::protected_function> vm_execute_hooks;
|
||||||
@ -20,6 +15,9 @@ namespace logfile
|
|||||||
utils::hook::detour scr_player_killed_hook;
|
utils::hook::detour scr_player_killed_hook;
|
||||||
utils::hook::detour scr_player_damage_hook;
|
utils::hook::detour scr_player_damage_hook;
|
||||||
|
|
||||||
|
utils::hook::detour client_command_hook;
|
||||||
|
utils::hook::detour g_shutdown_game_hook;
|
||||||
|
|
||||||
std::vector<sol::protected_function> player_killed_callbacks;
|
std::vector<sol::protected_function> player_killed_callbacks;
|
||||||
std::vector<sol::protected_function> player_damage_callbacks;
|
std::vector<sol::protected_function> player_damage_callbacks;
|
||||||
|
|
||||||
@ -147,51 +145,6 @@ namespace logfile
|
|||||||
meansOfDeath, weapon, isAlternate, vPoint, vDir, hitLoc, timeOffset);
|
meansOfDeath, weapon, isAlternate, vPoint, vDir, hitLoc, timeOffset);
|
||||||
}
|
}
|
||||||
|
|
||||||
void client_command_stub(const int clientNum)
|
|
||||||
{
|
|
||||||
auto self = &game::mp::g_entities[clientNum];
|
|
||||||
char cmd[1024] = {0};
|
|
||||||
|
|
||||||
game::SV_Cmd_ArgvBuffer(0, cmd, 1024);
|
|
||||||
|
|
||||||
if (cmd == "say"s || cmd == "say_team"s)
|
|
||||||
{
|
|
||||||
auto hidden = false;
|
|
||||||
std::string message(game::ConcatArgs(1));
|
|
||||||
|
|
||||||
hidden = message[1] == '/';
|
|
||||||
message.erase(0, hidden ? 2 : 1);
|
|
||||||
|
|
||||||
scheduler::once([cmd, message, self]()
|
|
||||||
{
|
|
||||||
const scripting::entity level{*game::levelEntityId};
|
|
||||||
const scripting::entity player{game::Scr_GetEntityId(self->s.entityNum, 0)};
|
|
||||||
|
|
||||||
scripting::notify(level, cmd, {player, message});
|
|
||||||
scripting::notify(player, cmd, {message});
|
|
||||||
}, scheduler::pipeline::server);
|
|
||||||
|
|
||||||
if (hidden)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// ClientCommand
|
|
||||||
return utils::hook::invoke<void>(0x4132E0_b, clientNum);
|
|
||||||
}
|
|
||||||
|
|
||||||
void g_shutdown_game_stub(const int freeScripts)
|
|
||||||
{
|
|
||||||
{
|
|
||||||
const scripting::entity level{*game::levelEntityId};
|
|
||||||
scripting::notify(level, "shutdownGame_called", {1});
|
|
||||||
}
|
|
||||||
|
|
||||||
// G_ShutdownGame
|
|
||||||
return utils::hook::invoke<void>(0x422F30_b, freeScripts);
|
|
||||||
}
|
|
||||||
|
|
||||||
unsigned int local_id_to_entity(unsigned int local_id)
|
unsigned int local_id_to_entity(unsigned int local_id)
|
||||||
{
|
{
|
||||||
const auto variable = game::scr_VarGlob->objectVariableValue[local_id];
|
const auto variable = game::scr_VarGlob->objectVariableValue[local_id];
|
||||||
@ -291,27 +244,55 @@ namespace logfile
|
|||||||
hook_enabled = false;
|
hook_enabled = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool client_command_stub(const int client_num)
|
||||||
|
{
|
||||||
|
auto self = &game::mp::g_entities[client_num];
|
||||||
|
char cmd[1024] = {0};
|
||||||
|
|
||||||
|
game::SV_Cmd_ArgvBuffer(0, cmd, 1024);
|
||||||
|
|
||||||
|
if (cmd == "say"s || cmd == "say_team"s)
|
||||||
|
{
|
||||||
|
auto hidden = false;
|
||||||
|
std::string message(game::ConcatArgs(1));
|
||||||
|
|
||||||
|
hidden = message[1] == '/';
|
||||||
|
message.erase(0, hidden ? 2 : 1);
|
||||||
|
|
||||||
|
scheduler::once([cmd, message, self, hidden]()
|
||||||
|
{
|
||||||
|
const scripting::entity level{*game::levelEntityId};
|
||||||
|
const scripting::entity player{game::Scr_GetEntityId(self->s.entityNum, 0)};
|
||||||
|
|
||||||
|
scripting::notify(level, cmd, {player, message, hidden});
|
||||||
|
scripting::notify(player, cmd, {message, hidden});
|
||||||
|
}, scheduler::pipeline::server);
|
||||||
|
|
||||||
|
if (hidden)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
class component final : public component_interface
|
class component final : public component_interface
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
void post_unpack() override
|
void post_unpack() override
|
||||||
{
|
{
|
||||||
utils::hook::jump(SELECT_VALUE(0x0, 0x444645_b), utils::hook::assemble(vm_execute_stub), true);
|
utils::hook::jump(SELECT_VALUE(0x0, 0x5111A5_b), utils::hook::assemble(vm_execute_stub), true);
|
||||||
|
|
||||||
if (game::environment::is_sp())
|
if (game::environment::is_sp())
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
utils::hook::call(0x54EB46_b, client_command_stub);
|
|
||||||
|
|
||||||
scr_player_damage_hook.create(0x1CE780_b, scr_player_damage_stub);
|
scr_player_damage_hook.create(0x1CE780_b, scr_player_damage_stub);
|
||||||
scr_player_killed_hook.create(0x1CEA60_b, scr_player_killed_stub);
|
scr_player_killed_hook.create(0x1CEA60_b, scr_player_killed_stub);
|
||||||
|
|
||||||
utils::hook::call(0x5520E0_b, g_shutdown_game_stub);
|
|
||||||
utils::hook::call(0x5525E1_b, g_shutdown_game_stub);
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
//REGISTER_COMPONENT(logfile::component)
|
REGISTER_COMPONENT(logfile::component)
|
@ -1,5 +1,10 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include "game/scripting/entity.hpp"
|
||||||
|
#include "game/scripting/execution.hpp"
|
||||||
|
#include "game/scripting/lua/value_conversion.hpp"
|
||||||
|
#include "game/scripting/lua/error.hpp"
|
||||||
|
|
||||||
namespace logfile
|
namespace logfile
|
||||||
{
|
{
|
||||||
extern std::unordered_map<const char*, sol::protected_function> vm_execute_hooks;
|
extern std::unordered_map<const char*, sol::protected_function> vm_execute_hooks;
|
||||||
@ -10,4 +15,6 @@ namespace logfile
|
|||||||
|
|
||||||
void enable_vm_execute_hook();
|
void enable_vm_execute_hook();
|
||||||
void disable_vm_execute_hook();
|
void disable_vm_execute_hook();
|
||||||
|
|
||||||
|
bool client_command_stub(const int client_num);
|
||||||
}
|
}
|
@ -94,6 +94,7 @@ namespace scripting
|
|||||||
script_function_table.clear();
|
script_function_table.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
scripting::notify(*game::levelEntityId, "shutdownGame_called", {1});
|
||||||
lua::engine::stop();
|
lua::engine::stop();
|
||||||
return g_shutdown_game_hook.invoke<void>(free_scripts);
|
return g_shutdown_game_hook.invoke<void>(free_scripts);
|
||||||
}
|
}
|
||||||
@ -159,26 +160,6 @@ namespace scripting
|
|||||||
scripting::token_map[str] = result;
|
scripting::token_map[str] = result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
game::XAssetHeader db_find_xasset_header_stub(game::XAssetType type, const char* name, int allow_create_default)
|
|
||||||
{
|
|
||||||
const auto result = db_find_xasset_header_hook.invoke<game::XAssetHeader>(type, name, allow_create_default);
|
|
||||||
if (!g_dump_scripts->current.enabled || type != game::XAssetType::ASSET_TYPE_SCRIPTFILE)
|
|
||||||
{
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string buffer;
|
|
||||||
buffer.append(result.scriptfile->name, strlen(result.scriptfile->name) + 1);
|
|
||||||
buffer.append(reinterpret_cast<char*>(&result.scriptfile->compressedLen), 4);
|
|
||||||
buffer.append(reinterpret_cast<char*>(&result.scriptfile->len), 4);
|
|
||||||
buffer.append(reinterpret_cast<char*>(&result.scriptfile->bytecodeLen), 4);
|
|
||||||
buffer.append(result.scriptfile->buffer, result.scriptfile->compressedLen);
|
|
||||||
buffer.append(result.scriptfile->bytecode, result.scriptfile->bytecodeLen);
|
|
||||||
utils::io::write_file(utils::string::va("gsc_dump/%s.gscbin", name), buffer);
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class component final : public component_interface
|
class component final : public component_interface
|
||||||
@ -205,9 +186,6 @@ namespace scripting
|
|||||||
|
|
||||||
g_shutdown_game_hook.create(SELECT_VALUE(0x0, 0x422F30_b), g_shutdown_game_stub);
|
g_shutdown_game_hook.create(SELECT_VALUE(0x0, 0x422F30_b), g_shutdown_game_stub);
|
||||||
|
|
||||||
db_find_xasset_header_hook.create(game::DB_FindXAssetHeader, db_find_xasset_header_stub);
|
|
||||||
g_dump_scripts = dvars::register_bool("g_dumpScripts", false, game::DVAR_FLAG_NONE, "Dump GSC scripts");
|
|
||||||
|
|
||||||
scheduler::loop([]()
|
scheduler::loop([]()
|
||||||
{
|
{
|
||||||
lua::engine::run_frame();
|
lua::engine::run_frame();
|
||||||
@ -216,4 +194,4 @@ namespace scripting
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
//REGISTER_COMPONENT(scripting::component)
|
REGISTER_COMPONENT(scripting::component)
|
||||||
|
@ -12,6 +12,7 @@
|
|||||||
#include "game_module.hpp"
|
#include "game_module.hpp"
|
||||||
#include "fps.hpp"
|
#include "fps.hpp"
|
||||||
#include "server_list.hpp"
|
#include "server_list.hpp"
|
||||||
|
#include "filesystem.hpp"
|
||||||
|
|
||||||
#include "game/ui_scripting/execution.hpp"
|
#include "game/ui_scripting/execution.hpp"
|
||||||
#include "game/scripting/execution.hpp"
|
#include "game/scripting/execution.hpp"
|
||||||
@ -223,8 +224,19 @@ namespace ui_scripting
|
|||||||
|
|
||||||
load_script("lui_common", lui_common);
|
load_script("lui_common", lui_common);
|
||||||
|
|
||||||
load_scripts("h1-mod/ui_scripts/");
|
for (const auto& path : filesystem::get_search_paths())
|
||||||
load_scripts("data/ui_scripts/");
|
{
|
||||||
|
load_scripts(path + "/ui_scripts/");
|
||||||
|
if (game::environment::is_sp())
|
||||||
|
{
|
||||||
|
load_scripts(path + "/ui_scripts/sp/");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
load_scripts(path + "/ui_scripts/mp/");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void try_start()
|
void try_start()
|
||||||
|
@ -59,10 +59,10 @@ namespace scripting
|
|||||||
|
|
||||||
script_function get_function_by_index(const unsigned index)
|
script_function get_function_by_index(const unsigned index)
|
||||||
{
|
{
|
||||||
static const auto function_table = SELECT_VALUE(0x14B1D1B90, 0xAC85070_b);
|
static const auto function_table = SELECT_VALUE(0x14B1D1B90, 0xAC83820_b);
|
||||||
static const auto method_table = SELECT_VALUE(0x14B1D33A0, 0xAC85070_b);
|
static const auto method_table = SELECT_VALUE(0x14B1D33A0, 0xAC85070_b);
|
||||||
|
|
||||||
if (index < 0x301)
|
if (index < 0x30A)
|
||||||
{
|
{
|
||||||
return reinterpret_cast<script_function*>(function_table)[index - 1];
|
return reinterpret_cast<script_function*>(function_table)[index - 1];
|
||||||
}
|
}
|
||||||
|
@ -74,7 +74,7 @@ namespace game
|
|||||||
float w, float min, float max, unsigned int flags)> Dvar_RegisterVec4{0x0, 0x183010};
|
float w, float min, float max, unsigned int flags)> Dvar_RegisterVec4{0x0, 0x183010};
|
||||||
|
|
||||||
WEAK symbol<long long(const char* qpath, char** buffer)> FS_ReadFile{0x0, 0x1EC690};
|
WEAK symbol<long long(const char* qpath, char** buffer)> FS_ReadFile{0x0, 0x1EC690};
|
||||||
WEAK symbol<void(void* buffer)> FS_FreeFile{0x0, 0x0};
|
WEAK symbol<void(void* buffer)> FS_FreeFile{0x0, 0x59E2F0};
|
||||||
WEAK symbol<void(const char* gameName)> FS_Startup{0x0, 0x0};
|
WEAK symbol<void(const char* gameName)> FS_Startup{0x0, 0x0};
|
||||||
WEAK symbol<void(const char* path, const char* dir)> FS_AddLocalizedGameDirectory{0x0, 0x1878F0};
|
WEAK symbol<void(const char* path, const char* dir)> FS_AddLocalizedGameDirectory{0x0, 0x1878F0};
|
||||||
|
|
||||||
@ -204,8 +204,8 @@ namespace game
|
|||||||
|
|
||||||
WEAK symbol<const char*(const char* string)> UI_SafeTranslateString{0x0, 0x4E8BC0};
|
WEAK symbol<const char*(const char* string)> UI_SafeTranslateString{0x0, 0x4E8BC0};
|
||||||
|
|
||||||
WEAK symbol<void*(jmp_buf* Buf, int Value)> longjmp{0x0, 0x0};
|
WEAK symbol<void*(jmp_buf* Buf, int Value)> longjmp{0x0, 0x826710};
|
||||||
WEAK symbol<int(jmp_buf* Buf)> _setjmp{0x0, 0x0};
|
WEAK symbol<int(jmp_buf* Buf)> _setjmp{0x0, 0x8A3190};
|
||||||
|
|
||||||
/***************************************************************
|
/***************************************************************
|
||||||
* Variables
|
* Variables
|
||||||
|
Loading…
Reference in New Issue
Block a user