ee7fa339fb
- use VA directly on interceptor instead of RVA
116 lines
4.2 KiB
Rust
116 lines
4.2 KiB
Rust
use std::cell::OnceCell;
|
|
|
|
use patternscan::scan_first_match;
|
|
use windows::{
|
|
Win32::System::{
|
|
LibraryLoader::GetModuleHandleA,
|
|
ProcessStatus::{GetModuleInformation, MODULEINFO},
|
|
Threading::GetCurrentProcess,
|
|
},
|
|
core::s,
|
|
};
|
|
|
|
use crate::addr::GAME_ASSEMBLY_BASE;
|
|
|
|
#[allow(static_mut_refs)]
|
|
unsafe fn game_assembly_slice() -> &'static [u8] {
|
|
static mut SLICE: OnceCell<&[u8]> = OnceCell::new();
|
|
unsafe {
|
|
SLICE.get_or_init(|| {
|
|
let module = GetModuleHandleA(s!("GameAssembly.dll")).unwrap();
|
|
let mut module_info = MODULEINFO {
|
|
lpBaseOfDll: std::ptr::null_mut(),
|
|
SizeOfImage: 0,
|
|
EntryPoint: std::ptr::null_mut(),
|
|
};
|
|
GetModuleInformation(
|
|
GetCurrentProcess(),
|
|
module,
|
|
&mut module_info,
|
|
std::mem::size_of::<MODULEINFO>() as u32,
|
|
)
|
|
.unwrap();
|
|
std::slice::from_raw_parts(
|
|
module.0 as *const u8,
|
|
module_info.SizeOfImage.try_into().unwrap(),
|
|
)
|
|
})
|
|
}
|
|
}
|
|
|
|
pub unsafe fn scan_il2cpp_section(pat: &str) -> Option<usize> {
|
|
let mut slice = unsafe { game_assembly_slice() };
|
|
scan_first_match(&mut slice, pat).unwrap().map(|address| {
|
|
let slice = unsafe { game_assembly_slice() };
|
|
match slice.get(address) {
|
|
// jmp sub_xxxxxxx
|
|
Some(&0xE8) => {
|
|
let offset =
|
|
i32::from_le_bytes(slice[address + 1..address + 5].try_into().unwrap());
|
|
GAME_ASSEMBLY_BASE.wrapping_add(address + 5 + offset as usize)
|
|
}
|
|
// mov rcx, [rip + offset] (0x48 0x8B 0x0D XXXXXXXX)
|
|
Some(&0x48)
|
|
if slice.get(address + 1) == Some(&0x8B)
|
|
&& slice.get(address + 2) == Some(&0x0D) =>
|
|
{
|
|
let offset =
|
|
i32::from_le_bytes(slice[address + 3..address + 7].try_into().unwrap());
|
|
GAME_ASSEMBLY_BASE.wrapping_add(address + 7 + offset as usize)
|
|
}
|
|
_ => GAME_ASSEMBLY_BASE.wrapping_add(address),
|
|
}
|
|
})
|
|
}
|
|
|
|
// #[allow(static_mut_refs)]
|
|
// unsafe fn unity_player_slice() -> &'static [u8] {
|
|
// static mut SLICE: OnceCell<&[u8]> = OnceCell::new();
|
|
// unsafe {
|
|
// SLICE.get_or_init(|| {
|
|
// let module = GetModuleHandleA(s!("UnityPlayer.dll")).unwrap();
|
|
// let mut module_info = MODULEINFO {
|
|
// lpBaseOfDll: std::ptr::null_mut(),
|
|
// SizeOfImage: 0,
|
|
// EntryPoint: std::ptr::null_mut(),
|
|
// };
|
|
// GetModuleInformation(
|
|
// GetCurrentProcess(),
|
|
// module,
|
|
// &mut module_info,
|
|
// std::mem::size_of::<MODULEINFO>() as u32,
|
|
// )
|
|
// .unwrap();
|
|
// std::slice::from_raw_parts(
|
|
// module.0 as *const u8,
|
|
// module_info.SizeOfImage.try_into().unwrap(),
|
|
// )
|
|
// })
|
|
// }
|
|
// }
|
|
|
|
// pub unsafe fn scan_unity_player_section(pat: &str) -> Option<usize> {
|
|
// let mut slice = unsafe { unity_player_slice() };
|
|
// scan_first_match(&mut slice, pat).unwrap().map(|address| {
|
|
// let slice = unsafe { unity_player_slice() };
|
|
// match slice.get(address) {
|
|
// // jmp sub_xxxxxxx
|
|
// Some(&0xE8) => {
|
|
// let offset =
|
|
// i32::from_le_bytes(slice[address + 1..address + 5].try_into().unwrap());
|
|
// UNITY_PLAYER_BASE.wrapping_add(address + 5 + offset as usize)
|
|
// }
|
|
// // mov rcx, [rip + offset] (0x48 0x8B 0x0D XXXXXXXX)
|
|
// Some(&0x48)
|
|
// if slice.get(address + 1) == Some(&0x8B)
|
|
// && slice.get(address + 2) == Some(&0x0D) =>
|
|
// {
|
|
// let offset =
|
|
// i32::from_le_bytes(slice[address + 3..address + 7].try_into().unwrap());
|
|
// UNITY_PLAYER_BASE.wrapping_add(address + 7 + offset as usize)
|
|
// }
|
|
// _ => UNITY_PLAYER_BASE.wrapping_add(address),
|
|
// }
|
|
// })
|
|
// }
|