summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/cinput.cpp58
-rw-r--r--src/hl2h.cpp3
2 files changed, 58 insertions, 3 deletions
diff --git a/src/cinput.cpp b/src/cinput.cpp
index f4ba322..a75cc4f 100644
--- a/src/cinput.cpp
+++ b/src/cinput.cpp
@@ -74,6 +74,63 @@ void fix_verified_crc(int seq, uint32_t crc) {
74} 74}
75 75
76// --------------------------------------------------------------------------- 76// ---------------------------------------------------------------------------
77// CInput::CreateMove hook
78// ---------------------------------------------------------------------------
79//
80// The CHLClient::CreateMove hook runs *inside* CInput::CreateMove. After it
81// returns, CInput::CreateMove overwrites cmd->random_seed with
82// MD5_PseudoRandom(sequence_number), then copies the command into the verified
83// command table. To choose the bullet-spread seed we must hook CInput itself
84// and run after that assignment.
85
86using InputCreateMoveFn = void (*)(void *, int, float, bool);
87static InputCreateMoveFn oInputCreateMove = nullptr;
88
89static void hkdInputCreateMove(void *self, int seq, float frametime,
90 bool active) {
91 if (oInputCreateMove)
92 oInputCreateMove(self, seq, frametime, active);
93
94 CUserCmd *cmd = get_usercmd(seq);
95 if (!cmd)
96 return;
97 int local = engine_get_local_player();
98 if (local <= 0)
99 return;
100 void *ent = entitylist_get(local);
101 if (!ent)
102 return;
103 if (!spread_control_apply(cmd, ent))
104 return;
105
106 // Keep the verified command copy and its CRC in sync with the modified
107 // random_seed. CInput::CreateMove already copied all other (aim/move) fields.
108 uintptr_t verified = *(uintptr_t *)(g_input + CMDOFF_M_PVERIFIED);
109 if (verified) {
110 CUserCmd *vc =
111 (CUserCmd *)(verified + (size_t)(seq % 90) * VERIFIED_STRIDE);
112 vc->random_seed = cmd->random_seed;
113 }
114 fix_verified_crc(seq, usercmd_checksum(cmd));
115}
116
117static bool install_input_hook() {
118 if (!g_input)
119 return false;
120 void **vt = VTABLE((void *)g_input);
121 if (!vt)
122 return false;
123 constexpr size_t N = 64;
124 void **nvt = new void *[N];
125 memcpy(nvt, vt, N * sizeof(void *));
126 oInputCreateMove = (InputCreateMoveFn)vt[3];
127 nvt[3] = (void *)&hkdInputCreateMove;
128 VTABLE((void *)g_input) = nvt;
129 logf("CInput CreateMove hooked: slot 3 orig=%p", (void *)oInputCreateMove);
130 return true;
131}
132
133// ---------------------------------------------------------------------------
77// CInput discovery: byte-scan of CHLClient::CreateMove prologue 134// CInput discovery: byte-scan of CHLClient::CreateMove prologue
78// --------------------------------------------------------------------------- 135// ---------------------------------------------------------------------------
79 136
@@ -135,6 +192,7 @@ bool find_input_global() {
135 logf("CInput* = %#lx (ptr var %#lx, vfunc[3] %#lx)", (unsigned long)input, 192 logf("CInput* = %#lx (ptr var %#lx, vfunc[3] %#lx)", (unsigned long)input,
136 (unsigned long)var, (unsigned long)f3); 193 (unsigned long)var, (unsigned long)f3);
137 g_input = input; 194 g_input = input;
195 install_input_hook();
138 return true; 196 return true;
139 } 197 }
140 } 198 }
diff --git a/src/hl2h.cpp b/src/hl2h.cpp
index dddcbdc..ee2e990 100644
--- a/src/hl2h.cpp
+++ b/src/hl2h.cpp
@@ -532,9 +532,6 @@ static void do_move(int seq, float frametime) {
532 note_modified(cmd, flags, vel); 532 note_modified(cmd, flags, vel);
533 } 533 }
534 } 534 }
535
536 if (spread_control_apply(cmd, ent))
537 note_modified(cmd, flags, vel);
538} 535}
539 536
540// --------------------------------------------------------------------------- 537// ---------------------------------------------------------------------------