mirror of
https://github.com/JezuzLizard/T4SP-Server-Plugin.git
synced 2025-04-19 21:22:54 +00:00
Some debug stuff
This commit is contained in:
parent
5e51712a02
commit
601a661fe0
@ -1,2 +1,100 @@
|
|||||||
#include <stdinc.hpp>
|
#include <stdinc.hpp>
|
||||||
#include "clientscript_public.hpp"
|
#include "clientscript_public.hpp"
|
||||||
|
#include <dbghelp.h>
|
||||||
|
|
||||||
|
namespace game
|
||||||
|
{
|
||||||
|
#define QUICK_TO_JSON_FIELD(j, v, membername) j[#membername] = v.membername
|
||||||
|
|
||||||
|
#define QUICK_TO_JSON_FIELD_SAFE_CSTR(j, v, membername) \
|
||||||
|
if (v.membername) \
|
||||||
|
j[#membername] = v.membername; \
|
||||||
|
else \
|
||||||
|
j[#membername] = "(NULL)"
|
||||||
|
|
||||||
|
#define QUICK_TO_JSON_FIELD_PTR_ADDR(j, v, membername) j[#membername] = reinterpret_cast<size_t>(&v.membername)
|
||||||
|
|
||||||
|
#define QUICK_TO_JSON_FIELD_ARRAY(j, v, membername) \
|
||||||
|
for (auto i = 0; i < ARRAY_COUNT(v.membername); i++) \
|
||||||
|
{ \
|
||||||
|
j[#membername][i] = v.membername[i]; \
|
||||||
|
}
|
||||||
|
|
||||||
|
#define QUICK_TO_JSON_FIELD_SL_STRING(j, v, membername) j[#membername "Str"] = SL_ConvertToStringSafe(v.membername, *gInst)
|
||||||
|
|
||||||
|
void to_json(nlohmann::json& j, const scrVarPub_t& v)
|
||||||
|
{
|
||||||
|
QUICK_TO_JSON_FIELD_SAFE_CSTR(j, v, fieldBuffer);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, canonicalStrCount);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, developer);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, developer_script);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, evaluate);
|
||||||
|
QUICK_TO_JSON_FIELD_SAFE_CSTR(j, v, error_message);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, error_index);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, time);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, timeArrayId);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, pauseArrayId);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, levelId);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, gameId);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, animId);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, freeEntList);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, tempVariable);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, bInited);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, savecount);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, checksum);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, entId);
|
||||||
|
QUICK_TO_JSON_FIELD(j, v, entFieldName);
|
||||||
|
QUICK_TO_JSON_FIELD_SL_STRING(j, v, entFieldName);
|
||||||
|
QUICK_TO_JSON_FIELD_PTR_ADDR(j, v, programHunkUser);
|
||||||
|
QUICK_TO_JSON_FIELD_PTR_ADDR(j, v, programBuffer);
|
||||||
|
QUICK_TO_JSON_FIELD_PTR_ADDR(j, v, endScriptBuffer);
|
||||||
|
QUICK_TO_JSON_FIELD_ARRAY(j, v, saveIdMap);
|
||||||
|
QUICK_TO_JSON_FIELD_ARRAY(j, v, saveIdMapRev);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// https://stackoverflow.com/questions/5693192/win32-backtrace-from-c-code
|
||||||
|
std::string printStack()
|
||||||
|
{
|
||||||
|
unsigned int i;
|
||||||
|
void * stack[ 100 ];
|
||||||
|
unsigned short frames;
|
||||||
|
SYMBOL_INFO * symbol;
|
||||||
|
HANDLE process;
|
||||||
|
std::string answer;
|
||||||
|
|
||||||
|
process = GetCurrentProcess();
|
||||||
|
|
||||||
|
SymInitialize( process, NULL, TRUE );
|
||||||
|
|
||||||
|
frames = CaptureStackBackTrace( 0, 100, stack, NULL );
|
||||||
|
symbol = ( SYMBOL_INFO * )calloc( sizeof( SYMBOL_INFO ) + 256 * sizeof( char ), 1 );
|
||||||
|
symbol->MaxNameLen = 255;
|
||||||
|
symbol->SizeOfStruct = sizeof( SYMBOL_INFO );
|
||||||
|
|
||||||
|
for( i = 0; i < frames; i++ )
|
||||||
|
{
|
||||||
|
SymFromAddr( process, ( DWORD64 )( stack[ i ] ), 0, symbol );
|
||||||
|
|
||||||
|
answer += std::format("{}: {} - {:06x}\n", frames - i - 1, symbol->Name, symbol->Address);
|
||||||
|
}
|
||||||
|
|
||||||
|
free( symbol );
|
||||||
|
|
||||||
|
return answer;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string get_full_gsc_state_str(game::scriptInstance_t inst)
|
||||||
|
{
|
||||||
|
nlohmann::json answer;
|
||||||
|
auto t = *game::gInst;
|
||||||
|
*game::gInst = inst;
|
||||||
|
|
||||||
|
answer["inst"] = inst;
|
||||||
|
answer["gScrVarPub"] = game::gScrVarPub[inst];
|
||||||
|
answer["stack"] = printStack();
|
||||||
|
|
||||||
|
*game::gInst = t;
|
||||||
|
|
||||||
|
return answer.dump(2);
|
||||||
|
}
|
||||||
|
@ -39,4 +39,5 @@ namespace codsrc
|
|||||||
int SL_ConvertFromRefString(game::scriptInstance_t inst, game::RefString* refString);
|
int SL_ConvertFromRefString(game::scriptInstance_t inst, game::RefString* refString);
|
||||||
game::RefString* GetRefString_0(game::scriptInstance_t inst, const char* str);
|
game::RefString* GetRefString_0(game::scriptInstance_t inst, const char* str);
|
||||||
const char* SL_DebugConvertToString(unsigned int stringValue, game::scriptInstance_t inst);
|
const char* SL_DebugConvertToString(unsigned int stringValue, game::scriptInstance_t inst);
|
||||||
|
const char* SL_ConvertToStringSafe(unsigned int id, game::scriptInstance_t inst);
|
||||||
}
|
}
|
||||||
|
@ -47,6 +47,17 @@ namespace codsrc
|
|||||||
game::DVAR_FLAG_NONE,
|
game::DVAR_FLAG_NONE,
|
||||||
"Used to toggle systems in script on and off on the server.");
|
"Used to toggle systems in script on and off on the server.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// our additions
|
||||||
|
if (!game::Cmd_FindCommand("dump_gsc_state"))
|
||||||
|
{
|
||||||
|
game::Cmd_AddCommand("dump_gsc_state", []()
|
||||||
|
{
|
||||||
|
game::scriptInstance_t inst = game::SCRIPTINSTANCE_SERVER;
|
||||||
|
utils::io::write_file("t4sp-server-plugin/gsc_state.json", get_full_gsc_state_str(inst));
|
||||||
|
});
|
||||||
|
}
|
||||||
|
//
|
||||||
}
|
}
|
||||||
|
|
||||||
// Completed
|
// Completed
|
||||||
|
@ -70,6 +70,10 @@ namespace exception
|
|||||||
line(utils::string::va("Exception: 0x%08X", exceptioninfo->ExceptionRecord->ExceptionCode));
|
line(utils::string::va("Exception: 0x%08X", exceptioninfo->ExceptionRecord->ExceptionCode));
|
||||||
line(utils::string::va("Address: 0x%lX", exceptioninfo->ExceptionRecord->ExceptionAddress));
|
line(utils::string::va("Address: 0x%lX", exceptioninfo->ExceptionRecord->ExceptionAddress));
|
||||||
|
|
||||||
|
line("");
|
||||||
|
line(get_full_gsc_state_str(game::SCRIPTINSTANCE_SERVER));
|
||||||
|
line("");
|
||||||
|
|
||||||
#pragma warning(push)
|
#pragma warning(push)
|
||||||
#pragma warning(disable: 4996)
|
#pragma warning(disable: 4996)
|
||||||
OSVERSIONINFOEXA version_info;
|
OSVERSIONINFOEXA version_info;
|
||||||
@ -85,7 +89,7 @@ namespace exception
|
|||||||
|
|
||||||
void write_minidump(const LPEXCEPTION_POINTERS exceptioninfo)
|
void write_minidump(const LPEXCEPTION_POINTERS exceptioninfo)
|
||||||
{
|
{
|
||||||
const std::string crash_name = utils::string::va("minidumps/plutonium-t4-crash-%s.zip",
|
const std::string crash_name = utils::string::va("t4sp-server-plugin/minidumps/plutonium-t4-crash-%s.zip",
|
||||||
utils::string::get_timestamp().data());
|
utils::string::get_timestamp().data());
|
||||||
|
|
||||||
utils::compression::zip::archive zip_file{};
|
utils::compression::zip::archive zip_file{};
|
||||||
|
@ -61,4 +61,5 @@ namespace game
|
|||||||
int SL_ConvertFromString(scriptInstance_t inst, const char* str);
|
int SL_ConvertFromString(scriptInstance_t inst, const char* str);
|
||||||
int SL_ConvertFromRefString(scriptInstance_t inst, RefString* refString);
|
int SL_ConvertFromRefString(scriptInstance_t inst, RefString* refString);
|
||||||
RefString* GetRefString_0(scriptInstance_t inst, const char* str);
|
RefString* GetRefString_0(scriptInstance_t inst, const char* str);
|
||||||
|
const char* SL_ConvertToStringSafe(unsigned int id, game::scriptInstance_t inst);
|
||||||
}
|
}
|
@ -362,4 +362,9 @@ namespace game
|
|||||||
{
|
{
|
||||||
return codsrc::GetRefString_0(inst, str);
|
return codsrc::GetRefString_0(inst, str);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const char* SL_ConvertToStringSafe(unsigned int id, game::scriptInstance_t inst)
|
||||||
|
{
|
||||||
|
return codsrc::SL_ConvertToStringSafe(id, inst);
|
||||||
|
}
|
||||||
}
|
}
|
@ -188,6 +188,33 @@ namespace game
|
|||||||
return answer;
|
return answer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// cmd_function_s *__usercall Cmd_FindCommand@<eax>(const char *cmdName@<esi>)
|
||||||
|
cmd_function_s* Cmd_FindCommand(const char* cmdName, void* call_addr)
|
||||||
|
{
|
||||||
|
cmd_function_s* answer;
|
||||||
|
|
||||||
|
__asm
|
||||||
|
{
|
||||||
|
mov esi, cmdName;
|
||||||
|
call call_addr;
|
||||||
|
mov answer, eax;
|
||||||
|
}
|
||||||
|
|
||||||
|
return answer;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Cmd_AddCommand(const char* name, void (__cdecl *function)())
|
||||||
|
{
|
||||||
|
cmd_function_s* newCmd = utils::memory::allocate<cmd_function_s>();
|
||||||
|
|
||||||
|
*newCmd = {};
|
||||||
|
newCmd->next = *cmd_functions;
|
||||||
|
newCmd->function = function;
|
||||||
|
newCmd->name = utils::memory::duplicate_string(name);
|
||||||
|
|
||||||
|
*cmd_functions = newCmd;
|
||||||
|
}
|
||||||
|
|
||||||
// restored
|
// restored
|
||||||
void Sys_EnterCriticalSection(CriticalSection critSect)
|
void Sys_EnterCriticalSection(CriticalSection critSect)
|
||||||
{
|
{
|
||||||
|
@ -10,6 +10,16 @@
|
|||||||
#define ARRAY_COUNT(arrayn) \
|
#define ARRAY_COUNT(arrayn) \
|
||||||
((sizeof(arrayn)) / (sizeof(arrayn[0])))
|
((sizeof(arrayn)) / (sizeof(arrayn[0])))
|
||||||
|
|
||||||
|
#ifndef NDEBUG
|
||||||
|
#undef assert
|
||||||
|
#define assert(expr) \
|
||||||
|
if (!!!(expr)) \
|
||||||
|
{ \
|
||||||
|
utils::io::write_file("t4sp-server-plugin/gsc_state_assert.json", get_full_gsc_state_str(game::SCRIPTINSTANCE_SERVER)); \
|
||||||
|
_wassert(_CRT_WIDE(#expr), _CRT_WIDE(__FILE__), (unsigned)(__LINE__)); \
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
namespace game
|
namespace game
|
||||||
{
|
{
|
||||||
enum gamemode
|
enum gamemode
|
||||||
|
@ -55,6 +55,10 @@ namespace game
|
|||||||
inline void* XAnimGetAnimDebugName_ADDR() { return CALL_ADDR(0x0, 0x60F850); }
|
inline void* XAnimGetAnimDebugName_ADDR() { return CALL_ADDR(0x0, 0x60F850); }
|
||||||
const char * XAnimGetAnimDebugName(unsigned int animIndex, XAnim_s * anims, void* call_addr = XAnimGetAnimDebugName_ADDR());
|
const char * XAnimGetAnimDebugName(unsigned int animIndex, XAnim_s * anims, void* call_addr = XAnimGetAnimDebugName_ADDR());
|
||||||
|
|
||||||
|
inline void* Cmd_FindCommand_ADDR() { return CALL_ADDR(0x0, 0x594DB0); }
|
||||||
|
cmd_function_s* Cmd_FindCommand(const char* cmdName, void* call_addr = Cmd_FindCommand_ADDR());
|
||||||
|
void Cmd_AddCommand(const char* name, void(__cdecl* function)());
|
||||||
|
|
||||||
void Sys_EnterCriticalSection(CriticalSection critSect);
|
void Sys_EnterCriticalSection(CriticalSection critSect);
|
||||||
void Sys_LeaveCriticalSection(CriticalSection critSect);
|
void Sys_LeaveCriticalSection(CriticalSection critSect);
|
||||||
|
|
||||||
@ -69,6 +73,7 @@ namespace game
|
|||||||
WEAK symbol<HunkUser*> g_allocNodeUser{ 0x0, 0x3882B20 };
|
WEAK symbol<HunkUser*> g_allocNodeUser{ 0x0, 0x3882B20 };
|
||||||
WEAK symbol<struct HunkUser *> g_user{ 0x0, 0x3882B48 };
|
WEAK symbol<struct HunkUser *> g_user{ 0x0, 0x3882B48 };
|
||||||
WEAK symbol<searchpath_s*> fs_searchpaths{ 0x0, 0x46E5044 };
|
WEAK symbol<searchpath_s*> fs_searchpaths{ 0x0, 0x46E5044 };
|
||||||
|
WEAK symbol<cmd_function_s*> cmd_functions{ 0x0, 0x1F416F4 };
|
||||||
|
|
||||||
namespace plutonium
|
namespace plutonium
|
||||||
{
|
{
|
||||||
|
@ -61,6 +61,7 @@
|
|||||||
#pragma comment(lib, "Winmm.lib")
|
#pragma comment(lib, "Winmm.lib")
|
||||||
|
|
||||||
#include "utils/hexrays_defs.h"
|
#include "utils/hexrays_defs.h"
|
||||||
|
#include "utils/io.hpp"
|
||||||
|
|
||||||
#undef GetObject
|
#undef GetObject
|
||||||
|
|
||||||
@ -68,5 +69,6 @@
|
|||||||
#include "game/enums.hpp"
|
#include "game/enums.hpp"
|
||||||
#include "game/structs.hpp"
|
#include "game/structs.hpp"
|
||||||
#include "game/symbols.hpp"
|
#include "game/symbols.hpp"
|
||||||
|
std::string get_full_gsc_state_str(game::scriptInstance_t inst);
|
||||||
|
|
||||||
using namespace std::literals;
|
using namespace std::literals;
|
Loading…
x
Reference in New Issue
Block a user