1+
2+ use std:: ptr:: null_mut;
3+ use std:: thread;
4+ use ilhook:: x86:: { CallbackOption , Hooker , HookFlags , HookType , Registers } ;
5+
6+ use crate :: entity:: Entity ;
7+ use crate :: offsets:: offsets:: { AMMO_CARBINE , AMMO_IN_MAGAZINE_CARBINE , AMMO_IN_MAGAZINE_PISTOL , AMMO_IN_MAGAZINE_RIFLE , AMMO_IN_MAGAZINE_SHOTGUN , AMMO_IN_MAGAZINE_SNIPER , AMMO_IN_MAGAZINE_SUBMACHINEGUN , AMMO_PISTOL , AMMO_RIFLE , AMMO_SHOTGUN , AMMO_SNIPER , AMMO_SUBMACHINEGUN , ARMOR_OFFSET_FROM_LOCAL_PLAYER , CARBINE_COOLDOWN , GRENADES_COUNT , HEALTH_OFFSET_FROM_LOCAL_PLAYER , KNIFE_COOLDOWN , PISTOL_COOLDOWN , RIFLE_COOLDOWN , SHOTGUN_COOLDOWN , SNIPER_COOLDOWN , SUBMACHINEGUN_COOLDOWN } ;
8+ use crate :: pattern_mask:: PatternMask ;
9+ use crate :: utils:: find_pattern;
10+ use crate :: vars:: hooks:: { LOCAL_PLAYER_HOOK } ;
11+ use crate :: vars:: ui_vars:: { IS_GRENADES_INFINITE , IS_INFINITE_AMMO , IS_INVULNERABLE , IS_NO_RELOAD } ;
12+
13+ pub static mut LOCAL_PLAYER_FIELDS_ADDR : * mut usize = null_mut ( ) ;
14+
15+ // The function to be hooked
16+ #[ inline( never) ]
17+ pub ( crate ) unsafe extern "cdecl" fn get_local_player_health (
18+ reg : * mut Registers ,
19+ _: usize
20+ ) {
21+ LOCAL_PLAYER_FIELDS_ADDR = ( * reg) . ebx as * mut usize ;
22+ if LOCAL_PLAYER_FIELDS_ADDR != null_mut ( )
23+ {
24+ let local_player_ent = Entity :: from_addr ( LOCAL_PLAYER_FIELDS_ADDR as usize ) ;
25+ if IS_GRENADES_INFINITE
26+ {
27+ if * ( ( local_player_ent. entity_starts_at_addr + GRENADES_COUNT ) as * mut i32 ) == 0
28+ {
29+ * ( ( local_player_ent. entity_starts_at_addr + GRENADES_COUNT ) as * mut i32 ) = 1 ;
30+ }
31+ }
32+ if IS_NO_RELOAD
33+ {
34+ * ( ( local_player_ent. entity_starts_at_addr + KNIFE_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
35+ * ( ( local_player_ent. entity_starts_at_addr + PISTOL_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
36+ * ( ( local_player_ent. entity_starts_at_addr + CARBINE_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
37+ * ( ( local_player_ent. entity_starts_at_addr + SHOTGUN_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
38+ * ( ( local_player_ent. entity_starts_at_addr + SUBMACHINEGUN_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
39+ * ( ( local_player_ent. entity_starts_at_addr + SNIPER_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
40+ * ( ( local_player_ent. entity_starts_at_addr + RIFLE_COOLDOWN ) as * mut f32 ) = 0.0f32 ;
41+ }
42+ if IS_INVULNERABLE
43+ {
44+ * ( ( local_player_ent. entity_starts_at_addr + HEALTH_OFFSET_FROM_LOCAL_PLAYER ) as * mut i32 ) = 1337 ;
45+ * ( ( local_player_ent. entity_starts_at_addr + ARMOR_OFFSET_FROM_LOCAL_PLAYER ) as * mut i32 ) = 1337 ;
46+ }
47+ if IS_INFINITE_AMMO
48+ {
49+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_RIFLE ) as * mut i32 ) = 40 ;
50+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_IN_MAGAZINE_RIFLE ) as * mut i32 ) = 40 ;
51+
52+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_PISTOL ) as * mut i32 ) = 40 ;
53+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_IN_MAGAZINE_PISTOL ) as * mut i32 ) = 40 ;
54+
55+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_CARBINE ) as * mut i32 ) = 40 ;
56+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_IN_MAGAZINE_CARBINE ) as * mut i32 ) = 40 ;
57+
58+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_SHOTGUN ) as * mut i32 ) = 40 ;
59+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_IN_MAGAZINE_SHOTGUN ) as * mut i32 ) = 40 ;
60+
61+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_SUBMACHINEGUN ) as * mut i32 ) = 40 ;
62+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_IN_MAGAZINE_SUBMACHINEGUN ) as * mut i32 ) = 40 ;
63+
64+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_SNIPER ) as * mut i32 ) = 40 ;
65+ * ( ( local_player_ent. entity_starts_at_addr + AMMO_IN_MAGAZINE_SNIPER ) as * mut i32 ) = 40 ;
66+ }
67+ }
68+ }
69+
70+
71+
72+
73+ // Example of finding a pattern and setting up the hook
74+ pub fn setup_invul ( ) {
75+ unsafe {
76+ thread:: spawn ( ||
77+ {
78+ /*8B 8B EC 00 00 00 83 F9 19*/
79+ /*8B ? ? ? ? ? 83 F9 19*/
80+ /*x?????xxx*/
81+ let pattern_mask = PatternMask :: aob_to_pattern_mask (
82+ "8B ? ? ? ? ? 83 F9 19"
83+ ) ;
84+
85+ println ! ( "[GetLocalPlayerHealthHook] {:#x}" , & pattern_mask) ;
86+
87+ let get_local_player_health_aob = find_pattern ( "ac_client.exe" ,
88+ & * pattern_mask. aob_pattern ,
89+ & pattern_mask. mask_to_string ( ) ) ;
90+ /* &[0x8B, 0x8B, 0xEC, 0x00, 0x00, 0x00, 0x83, 0xF9, 0x19],
91+ "x?????xxx");*/
92+
93+ if let Some ( addr) = get_local_player_health_aob {
94+ println ! ( "[get_local_player_hook.rs->setup_invul] local player get current hp pattern found at: {:#x}" , addr) ;
95+ let hooker = Hooker :: new (
96+ addr,
97+ HookType :: JmpBack ( get_local_player_health) ,
98+ CallbackOption :: None ,
99+ 0 ,
100+ HookFlags :: empty ( ) ,
101+ ) ;
102+ let hook_res = hooker. hook ( ) ;
103+
104+ match hook_res {
105+ Ok ( trampoline_hook) => {
106+ * LOCAL_PLAYER_HOOK . lock ( ) . unwrap ( ) = Some ( trampoline_hook) ;
107+ println ! ( "[get_local_player_hook.rs->setup_invul] local player get current hp pattern hook succeeded!" ) ;
108+ }
109+ Err ( e) => {
110+ println ! ( "[get_local_player_hook.rs->setup_invul] local player get current hp pattern hook failed: {:?}" , e) ;
111+ }
112+ }
113+ } else {
114+ println ! ( "[get_local_player_hook.rs->setup_invul] local player get current hp pattern not found" ) ;
115+ }
116+ } ) ;
117+ }
118+ }
0 commit comments