summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorsalmonik <salmonik@tuta.io>2026-10-27 15:40:52 +0100
committersalmonik <salmonik@tuta.io>2026-10-27 15:40:52 +0100
commita029f2e25586533eb3feebab64864a69919f93b9 (patch)
tree233df88dac02f64cf83beede1a913ab5dcd70bbe
parentSpread control: set random_seed after CInput::CreateMove (diff)
downloadhl2h-a029f2e25586533eb3feebab64864a69919f93b9.tar.gz
hl2h-a029f2e25586533eb3feebab64864a69919f93b9.zip
Spread control: add server RandomSeed GOT diagnostic/override
Diffstat (limited to '')
-rw-r--r--src/hl2h.cpp61
1 files changed, 61 insertions, 0 deletions
diff --git a/src/hl2h.cpp b/src/hl2h.cpp
index ee2e990..90e0990 100644
--- a/src/hl2h.cpp
+++ b/src/hl2h.cpp
@@ -2,6 +2,8 @@
2#include "hl2h.h" 2#include "hl2h.h"
3#include <cmath> 3#include <cmath>
4#include <cstdarg> 4#include <cstdarg>
5#include <cstdlib>
6#include <sys/mman.h>
5 7
6// --------------------------------------------------------------------------- 8// ---------------------------------------------------------------------------
7// logging 9// logging
@@ -403,7 +405,66 @@ static bool jumpbug_apply(CUserCmd *cmd, int local, void *ent, int flags,
403 return cmd->buttons != before; 405 return cmd->buttons != before;
404} 406}
405 407
408// ---------------------------------------------------------------------------
409// server RandomSeed diagnostic / override
410// ---------------------------------------------------------------------------
411//
412// The installed 2024 server build is stripped and its usercmd/server-random-seed
413// handling differs from the 2013 SDK source. This hook is installed on the
414// server.so GOT slot for RandomSeed (R_386_JUMP_SLOT at vaddr 0xce1348) so we
415// can see which seed FireBullets actually uses and optionally force the chosen
416// spread seed. Disabled unless HL2H_SEED_TRACE / HL2H_SEED_FORCE are set.
417
418static void (*g_real_random_seed)(int) = nullptr;
419static uintptr_t g_srv_base = 0;
420static bool g_seed_hook_installed = false;
421
422static void hkdSrvRandomSeed(int seed) {
423 uintptr_t ret = (uintptr_t)__builtin_return_address(0);
424 long off = (long)(ret - g_srv_base);
425 static bool trace = getenv("HL2H_SEED_TRACE") != nullptr;
426 static bool force = getenv("HL2H_SEED_FORCE") != nullptr;
427 static int logs = 0;
428 bool bullet_site = (off >= 0x216900 && off <= 0x216930);
429 if (trace && (bullet_site || logs < 12)) {
430 if (logs < 200) {
431 logs++;
432 logf("srvseed: seed=%d off=0x%lx bullet=%d", seed, off,
433 (int)bullet_site);
434 }
435 }
436 if (force && bullet_site)
437 seed = 33;
438 if (g_real_random_seed)
439 g_real_random_seed(seed);
440}
441
442static void install_seed_hook() {
443 if (g_seed_hook_installed || !g_server.valid())
444 return;
445 g_srv_base = g_server.ranges[0].lo;
446 uintptr_t slot = g_srv_base + 0xce1348; // R_386_JUMP_SLOT RandomSeed
447 if (!g_server.contains(slot))
448 return;
449 g_real_random_seed =
450 (void (*)(int))dlsym(RTLD_NEXT, "RandomSeed");
451 if (!g_real_random_seed)
452 g_real_random_seed = (void (*)(int))dlsym(RTLD_DEFAULT, "RandomSeed");
453 if (!g_real_random_seed) {
454 logf("seed hook: real RandomSeed not found");
455 return;
456 }
457 mprotect((void *)(slot & ~(uintptr_t)0xFFF), 0x1000,
458 PROT_READ | PROT_WRITE | PROT_EXEC);
459 *(uint32_t *)slot = (uint32_t)(uintptr_t)&hkdSrvRandomSeed;
460 g_seed_hook_installed = true;
461 logf("seed hook: server GOT %#lx -> %p (real %p)",
462 (unsigned long)slot, (void *)&hkdSrvRandomSeed,
463 (void *)g_real_random_seed);
464}
465
406static void do_move(int seq, float frametime) { 466static void do_move(int seq, float frametime) {
467 install_seed_hook();
407 static bool g_echo_sent = false; 468 static bool g_echo_sent = false;
408 if (!g_input || !g_net.ok()) 469 if (!g_input || !g_net.ok())
409 return; 470 return;