summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authornavewindre <nw@moneybot.cc>2024-07-14 08:43:58 +0200
committernavewindre <nw@moneybot.cc>2024-07-14 08:43:58 +0200
commit320e7b14a5a29838ed2cb909cadfd7c448c6849b (patch)
tree3cbd09c2c09abb6263da01d41b9da5c37837e4c8
parent28f41cf689def99fb586bfca47b7e1786227a5a2 (diff)
schemas
-rw-r--r--src/cs2/cs2.cpp21
-rw-r--r--src/cs2/cs2.h22
-rw-r--r--src/cs2/hack.cpp2
-rw-r--r--src/cs2/iface.h7
-rw-r--r--src/cs2/schema.h166
-rw-r--r--src/cs2/sdk.h88
-rw-r--r--src/heavens-gate.vcxproj3
-rw-r--r--src/heavens-gate.vcxproj.filters9
-rw-r--r--src/source.cpp2
9 files changed, 300 insertions, 20 deletions
diff --git a/src/cs2/cs2.cpp b/src/cs2/cs2.cpp
new file mode 100644
index 0000000..224e445
--- /dev/null
+++ b/src/cs2/cs2.cpp
@@ -0,0 +1,21 @@
+#include "cs2.h"
+#include "schema.h"
+
+bool CS2::open() {
+ if( !PROCESS64::open() )
+ return false;
+
+ mod.client = get_module64( "client.dll"fnv );
+ mod.engine = get_module64( "engine.dll"fnv );
+ mod.schema = get_module64( "schemasystem.dll"fnv );
+
+ // todo: handle this using loader
+ iface.client = get_iface( "Source2Client0" );
+ iface.engine = get_iface( "Source2EngineToClient0" );
+ iface.schema = get_iface( "SchemaSystem_0" );
+
+ // also handle w/ loader
+ netvars = schema_get_all( this );
+
+ return true;
+}
diff --git a/src/cs2/cs2.h b/src/cs2/cs2.h
index 58eba14..db136b9 100644
--- a/src/cs2/cs2.h
+++ b/src/cs2/cs2.h
@@ -1,25 +1,14 @@
#pragma once
-
#include "../process64.h"
+#include "iface.h"
+
+#include "sdk.h"
class CS2 : public PROCESS64 {
public:
CS2() : PROCESS64( "cs2.exe" ) {};
- bool open() {
- if( !PROCESS64::open() )
- return false;
-
- mod.client = get_module64( "client.dll"fnv );
- mod.engine = get_module64( "engine.dll"fnv );
- mod.schema = get_module64( "schemasystem.dll"fnv );
-
- // todo: handle this using loader
- iface.client = get_iface( "Source2Client0" );
- iface.engine = get_iface( "Source2EngineToClient0" );
-
- return true;
- }
+ bool open();
IFACE_ENTRY get_iface( const char* name ) {
VECTOR<IFACE_ENTRY> entries = iface_get_all( this );
@@ -42,5 +31,8 @@ public:
struct {
IFACE_ENTRY client;
IFACE_ENTRY engine;
+ IFACE_ENTRY schema;
} iface;
+
+ VECTOR<NETVAR_ENTRY> netvars;
}; \ No newline at end of file
diff --git a/src/cs2/hack.cpp b/src/cs2/hack.cpp
index b5f0242..ef4008d 100644
--- a/src/cs2/hack.cpp
+++ b/src/cs2/hack.cpp
@@ -12,8 +12,6 @@ PROCESS64* hack_init() {
return nullptr;
}
- VECTOR<IFACE_ENTRY> entries = iface_get_all( p );
-
return p;
}
diff --git a/src/cs2/iface.h b/src/cs2/iface.h
index 6c3b34b..be2137d 100644
--- a/src/cs2/iface.h
+++ b/src/cs2/iface.h
@@ -42,6 +42,8 @@ inline U64 iface_get_address( PROCESS64* p, U64 create_fn ) {
U32 off = *(U32*)&data[3];
U64 addr = create_fn + off + 7;
+
+ return addr;
}
inline U64 iface_get_createinterface( PROCESS64* p, U64 module ) {
@@ -77,7 +79,10 @@ inline VECTOR<IFACE_ENTRY> iface_dump_module( PROCESS64* p, MODULE_ENTRY module
for( ;; ) {
IFACE_ENTRY entry;
p->read( reg.name, entry.name.data, 64 );
- entry.ptr = reg.create_fn;
+
+ U64 ptr = iface_get_address( p, reg.create_fn );
+
+ entry.ptr = ptr;
entry.module = module.base;
entry.module_name = module.name;
entries.push_back( entry );
diff --git a/src/cs2/schema.h b/src/cs2/schema.h
index e69de29..f99683d 100644
--- a/src/cs2/schema.h
+++ b/src/cs2/schema.h
@@ -0,0 +1,166 @@
+#pragma once
+#include "cs2.h"
+#include "../util.h"
+#include "sdk.h"
+
+
+inline CS2_SCHEMA_FIELD* schema_class_get_fields( CS2* p, CS2_SCHEMA_CLASS* schclass ) {
+ if( !schclass->fields || !schclass->num_fields )
+ return 0;
+
+ U32 c = schclass->num_fields;
+ CS2_SCHEMA_FIELD* fields = (CS2_SCHEMA_FIELD*)malloc( sizeof(CS2_SCHEMA_FIELD) * c );
+
+ p->read( schclass->fields, fields, sizeof(CS2_SCHEMA_FIELD) * c );
+
+ return fields;
+}
+
+inline CS2_SCHEMA_CLASS* schema_scope_get_classes( CS2* p, CS2_SCHEMA_SCOPE* scope ) {
+ U32 c = scope->num_classes;
+ CS2_SCHEMA_ENTRY* entries = (CS2_SCHEMA_ENTRY*)malloc( sizeof(CS2_SCHEMA_ENTRY) * (c) );
+ CS2_SCHEMA_CLASS* ret = (CS2_SCHEMA_CLASS*)malloc( sizeof(CS2_SCHEMA_CLASS) * (c) );
+
+ p->read( scope->declared_classes, entries, sizeof(CS2_SCHEMA_ENTRY) * (c) );
+
+ for( U32 i = 0; i < c; ++i ) {
+ CS2_SCHEMA_ENTRY* e = &entries[i];
+
+ CS2_SCHEMA_DECLARED_CLASS _class;
+ p->read( e->declared_class, &_class, sizeof( _class ) );
+ p->read( _class.class_ptr, &ret[i], sizeof(CS2_SCHEMA_CLASS) );
+ }
+
+ free( entries );
+ return ret;
+}
+
+inline CS2_SCHEMA_SCOPE* schema_get_scopes( CS2* p, CS2_SCHEMA schema ) {
+ U32 c = (U32)schema.scope_size;
+ U64* ptrarr = (U64*)malloc( sizeof(U64) * c );
+ CS2_SCHEMA_SCOPE* ret = (CS2_SCHEMA_SCOPE*)malloc( sizeof(CS2_SCHEMA_SCOPE) * c );
+
+ p->read( schema.scopes, ptrarr, sizeof(U64) * c );
+
+ for( U32 i = 0; i < c; ++i ) {
+ p->read( ptrarr[i], &ret[i], sizeof(CS2_SCHEMA_SCOPE) );
+ }
+
+ free( ptrarr );
+ return ret;
+}
+
+inline CS2_SCHEMA schema_read_iface( CS2* p, U64 schemasys ) {
+ CS2_SCHEMA ret;
+
+ p->read( schemasys, &ret, sizeof(CS2_SCHEMA) );
+
+ return ret;
+}
+
+// CAUTION: SLOW!!!!
+static VECTOR<NETVAR_ENTRY> schema_get_all( CS2* p ) {
+ VECTOR<NETVAR_ENTRY> entries;
+ CS2_SCHEMA schema = schema_read_iface( p, p->iface.schema.ptr );
+ CS2_SCHEMA_SCOPE* scopes = schema_get_scopes( p, schema );
+
+ for( U32 i = 0; i < schema.scope_size; ++i ) {
+ CS2_SCHEMA_SCOPE* scope = &scopes[i];
+
+ if( !scope->declared_classes )
+ continue;
+
+ CS2_SCHEMA_CLASS* classes = schema_scope_get_classes( p, scope );
+
+ for( U32 j = 0; j < scope->num_classes; ++j ) {
+ CS2_SCHEMA_CLASS* schclass = &classes[j];
+
+ STR<128> classname{};
+ p->read( schclass->name, classname.data, 128 );
+
+ if( classname.data[0] == 0 || !strlen( classname ) )
+ continue;
+
+ if( !schclass->fields || !schclass->num_fields )
+ continue;
+
+ CS2_SCHEMA_FIELD* fields = schema_class_get_fields( p, schclass );
+
+ for( U32 k = 0; k < schclass->num_fields; ++k ) {
+ CS2_SCHEMA_FIELD* field = &fields[k];
+ NETVAR_ENTRY entry{};
+
+ STR<256> buf;
+ p->read( field->name, buf.data, 256 );
+ entry.prop = buf;
+ entry.clientclass = buf;
+ entry.scope = scope->name;
+ entries.push_back( entry );
+ }
+
+ free( fields );
+ }
+
+ free( classes );
+ }
+
+ free( scopes );
+ return entries;
+}
+
+static void schema_dump_to_file( CS2* p ) {
+ CS2_SCHEMA schema = schema_read_iface( p, p->iface.schema.ptr );
+
+ static STR<9999999> output;
+ memset( output, 0, sizeof(output.data) );
+
+ sprintf( output.data, "schema: %llx %llx\n", schema.scopes, schema.scope_size );
+
+ CS2_SCHEMA_SCOPE* scopes = schema_get_scopes( p, schema );
+
+ for( U32 i = 0; i < schema.scope_size; ++i ) {
+ CS2_SCHEMA_SCOPE* scope = &scopes[i];
+
+ sprintf( output.data, "%s --scope %s: %d classes [%llx]\n", output.data, scope->name, scope->num_classes, scope->declared_classes );
+
+ if( !scope->declared_classes )
+ continue;
+
+ CS2_SCHEMA_CLASS* classes = schema_scope_get_classes( p, scope );
+
+ for( U32 j = 0; j < scope->num_classes; ++j ) {
+ CS2_SCHEMA_CLASS* schclass = &classes[j];
+
+ STR<128> classname{};
+ p->read( schclass->name, classname.data, 128 );
+
+ if( classname.data[0] == 0 || !strlen( classname ) )
+ continue;
+
+ sprintf( output.data, "%s ----class %s: %d fields\n", output.data, classname.data, schclass->num_fields );
+
+ if( !schclass->fields || !schclass->num_fields )
+ continue;
+
+ CS2_SCHEMA_FIELD* fields = schema_class_get_fields( p, schclass );
+
+ for( U32 k = 0; k < schclass->num_fields; ++k ) {
+ CS2_SCHEMA_FIELD* field = &fields[k];
+
+ STR<256> buf;
+ p->read( field->name, buf.data, 256 );
+ sprintf( output.data, "%s ------field %s 0x%x\n", output.data, buf.data, field->offset );
+ }
+
+ free( fields );
+ }
+
+ free( classes );
+ }
+
+ FILE* f = fopen( "schema.txt", "w" );
+ fwrite( output.data, 1, strlen(output.data), f );
+ fclose( f );
+
+ free( scopes );
+} \ No newline at end of file
diff --git a/src/cs2/sdk.h b/src/cs2/sdk.h
new file mode 100644
index 0000000..0751f94
--- /dev/null
+++ b/src/cs2/sdk.h
@@ -0,0 +1,88 @@
+#pragma once
+#include "../typedef.h"
+
+struct CS2_SCHEMA_FIELD {
+ U64 name;
+ U64 type;
+ U32 offset;
+ U32 size;
+ U64 metadata;
+};
+
+struct CS2_SCHEMA_CLASS {
+ U64 vft;
+ // const char*
+ U64 name;
+ // const char*
+ U64 module_name;
+ U32 size;
+ U16 num_fields;
+
+private:
+ U8 unk_01[2];
+
+public:
+ U16 static_size;
+ U16 metadata_size;
+
+private:
+ U8 unk_02[4];
+
+public:
+ // CS2_SCHEMA_FIELD
+ U64 fields;
+};
+
+struct CS2_SCHEMA_DECLARED_CLASS {
+ U64 vft;
+ // const char*
+ U64 name;
+ // const char*
+ U64 module_name;
+ // void*
+ U64 unk_ptr;
+ // CS2_SCHEMA_CLASS
+ U64 class_ptr;
+};
+
+struct CS2_SCHEMA_ENTRY {
+ U64 hash[2];
+ // CS2_SCHEMA_DECLARED_CLASS
+ U64 declared_class;
+};
+
+struct CS2_SCHEMA_SCOPE {
+ U64 vft;
+ char name[256];
+
+private:
+ U8 unk_01[0x338];
+
+public:
+ // CS2_SCHEMA_ENTRY*
+ U64 declared_classes;
+
+private:
+ U8 unk_02[0xe];
+
+public:
+ U16 num_classes;
+};
+
+struct CS2_SCHEMA {
+private:
+ U8 unk_01[0x188];
+public:
+ U64 scope_size;
+ // CS2_SCHEMA_SCOPE[]
+ U64 scopes;
+};
+
+// fuck you, they will forever be netvars to me.
+struct NETVAR_ENTRY {
+ STR<256> scope;
+ STR<256> clientclass;
+ STR<256> prop;
+
+ I32 offset;
+}; \ No newline at end of file
diff --git a/src/heavens-gate.vcxproj b/src/heavens-gate.vcxproj
index 23a1b96..0a41f0b 100644
--- a/src/heavens-gate.vcxproj
+++ b/src/heavens-gate.vcxproj
@@ -197,6 +197,7 @@
<ItemGroup>
<ClCompile Include="conout.cpp" />
<ClCompile Include="conin.cpp" />
+ <ClCompile Include="cs2\cs2.cpp" />
<ClCompile Include="cs2\hack.cpp" />
<ClCompile Include="menu.cpp" />
<ClCompile Include="ntutil.cpp" />
@@ -209,6 +210,8 @@
<ClInclude Include="cs2\cs2.h" />
<ClInclude Include="cs2\hack.h" />
<ClInclude Include="cs2\iface.h" />
+ <ClInclude Include="cs2\schema.h" />
+ <ClInclude Include="cs2\sdk.h" />
<ClInclude Include="disasm.h" />
<ClInclude Include="fnv.h" />
<ClInclude Include="inet.h" />
diff --git a/src/heavens-gate.vcxproj.filters b/src/heavens-gate.vcxproj.filters
index f6c97b7..643ec4f 100644
--- a/src/heavens-gate.vcxproj.filters
+++ b/src/heavens-gate.vcxproj.filters
@@ -17,6 +17,9 @@
<ClCompile Include="util.cpp">
<Filter>Util</Filter>
</ClCompile>
+ <ClCompile Include="cs2\cs2.cpp">
+ <Filter>Game</Filter>
+ </ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="typedef.h" />
@@ -72,6 +75,12 @@
<ClInclude Include="cs2\cs2.h">
<Filter>Game</Filter>
</ClInclude>
+ <ClInclude Include="cs2\schema.h">
+ <Filter>Game</Filter>
+ </ClInclude>
+ <ClInclude Include="cs2\sdk.h">
+ <Filter>Game</Filter>
+ </ClInclude>
</ItemGroup>
<ItemGroup>
<Filter Include="Console">
diff --git a/src/source.cpp b/src/source.cpp
index dd08e9e..1ce0754 100644
--- a/src/source.cpp
+++ b/src/source.cpp
@@ -26,8 +26,6 @@ bool run() {
}
I32 __cdecl main() {
- con_init();
-
u_set_debug_privilege();
u_thread_create( &con_hook_handler );
u_thread_create( &con_handler );