This commit is contained in:
2024-11-13 21:41:26 -05:00
commit 03066e2e55
29 changed files with 1549 additions and 0 deletions

92
sub/winu/src/modules.rs Normal file
View File

@@ -0,0 +1,92 @@
use sub_pe::imagebase::ImageBase;
#[inline(always)]
pub unsafe fn find_module(hash: u64) -> Option<&'static ImageBase> {
use sub_core::fnv1::hash_utf16;
loaded_modules()
.find(|(_, n)|hash_utf16(*n) == hash)
.map(|(i,_)|i)
}
#[inline(always)]
pub unsafe fn process_image() -> &'static ImageBase {
let mut process_exe: *const ImageBase;
core::arch::asm!(
"mov {x}, gs:[60h]", // TEB->PEB
"mov {x}, [{x} + 10h]", // PEB->ImageBaseAddress
x = out(reg) process_exe,
);
&*process_exe
}
#[inline(always)]
pub unsafe fn loaded_modules() -> ModuleIter {
let mut module_link: *const LDR_DATA_TABLE_ENTRY;
core::arch::asm!(
"mov {x}, gs:[60h]", // TEB->PEB
"mov {x}, [{x} + 18h]", // PEB->LDR
"mov {x}, [{x} + 10h]", // LDR->InLoadOrderModuleList
x = out(reg) module_link,
);
ModuleIter {
entry: (*module_link).prev,
head: (*module_link).prev,
}
}
pub struct ModuleIter {
entry: *const LDR_DATA_TABLE_ENTRY,
head: *const LDR_DATA_TABLE_ENTRY,
}
impl Iterator for ModuleIter {
type Item = (&'static ImageBase, &'static [u16]);
fn next(&mut self) -> Option<Self::Item> {
unsafe {
self.entry = (&*self.entry).next;
match self.entry == self.head {
true => { None }
false => {
let module = (*self.entry).module;
let name = (*self.entry).name.as_slice();
Some((&*module,name))
}
}
}
}
}
/*
FFI STRUCTS
*/
#[repr(C)]
#[derive(Copy, Clone)]
#[allow(non_camel_case_types)]
struct UNICODE_STRING {
pub length: u16,
pub capacity: u16,
pub buffer: *const u16,
}
#[repr(C)]
#[allow(non_camel_case_types)]
struct LDR_DATA_TABLE_ENTRY {
/* 0x00 */ pub next: *const LDR_DATA_TABLE_ENTRY,
/* 0x08 */ pub prev: *const LDR_DATA_TABLE_ENTRY,
/* 0x10 */ pub reserved2: [usize;4],
/* 0x30 */ pub module: *const ImageBase,
/* 0x38 */ pub entry_point: *const (),
/* 0x40 */ pub reserved3: usize,
/* 0x48 */ pub path: UNICODE_STRING,
/* 0x58 */ pub name: UNICODE_STRING,
}
impl UNICODE_STRING {
pub fn as_slice(&self) -> &'static [u16] {
unsafe { core::slice::from_raw_parts(self.buffer, (self.length / 2) as usize) }
}
}