sha0coder / libscemu

SCEMU The crates.io lib, x86 cpu and systems emulator focused mainly for anti-malware
40 stars 8 forks source link

Still have a bug in PEB walking #68

Closed HongThatCong closed 13 minutes ago

HongThatCong commented 2 days ago

Hi @sha0coder

Please test again with this simple metasploit x64 shellcode. And VirtualAlloc can still failed.

21 Reading PEB 0x7fefff00320
22 0x3c0018: push  rsi ;0x1
23 0x3c0019: mov   rdx,[rdx+18h]
24 0x3c001d: mov   rdx,[rdx+20h]
25 0x3c0021: xor   r9,r9
26 0x3c0024: mov   rsi,[rdx+50h]
27 0x3c0028: movzx rcx,word ptr [rdx+4Ah]
28 0x3c002d: xor   rax,rax
29 0x3c0030: lodsb [rsi]
lodsb: memory read error
=>dt
structure=>PEB
address=>0x7fefff00320
thread 'main' panicked at C:\Rust\cargo\registry\src\index.crates.io-6f17d22bba15001f\libscemu-0.18.5\src\emu\structures.rs:363:53:
called `Option::unwrap()` on a `None` value
note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace

test.bin.gz

I use scemu/pyscemu and Speakeasy in parallel I highly appreciate the speed of scemu

Thank you very much

sha0coder commented 1 day ago

Hello, I fixed the structure offsets, but it is not matching well the metasploit hash for kernel32 + LoadLibraryA.

It Is accessing to the FullDllName, that should be “C:\Windows\System32\kernel32.dll” without quotes and in wide.

This python code calculates in same way the emulator does, and matches the hash with the emulator but not with metasploit:

# https://github.com/sha0coder/unsigned
from unsigned import Unsigned32 as u32
from unsigned import Unsigned64 as u64

lib = 'C\x00:\x00\\\x00W\x00i\x00n\x00d\x00o\x00w\x00s\x00\\\x00S\x00y\x00s\x00t\x00e\x00m\x003\x002\x00\\\x00k\x00e\x00r\x00n\x00e\x00l\x003\x002\x00.\x00d\x00l\x00l\x00'
api = 'LoadLibraryA\x00'

r9d = u32(0)
for al in lib:
    c = ord(al)
    if c >= 0x61:
        c -= 0x20
    r9d.ror(0x0d)
    r9d.add(u32(c))

libhash = r9d
print('libhash',libhash.hex())

r9d = u32(0)
for al in api:
    r9d.ror(0x0d)
    r9d.add(u32(ord(al)))
r9 = u64(r9d())
r9.add(u64(libhash()))

final = hex(r9() & 0xffffffff)
print('final:',final) # 0xb47e823c
print('metasploit looks for: 0x726774c’)

I’m creating the ldr entry in this way:

…
    ldr.dll_base = base;
    ldr.entry_point = entry_point;
    ldr.size_of_image = 0;
    ldr.full_dll_name.length = full_libname.len() as u16 * 2;
    ldr.full_dll_name.maximum_length = full_libname.len() as u16 * 2;
    ldr.full_dll_name.buffer = space_addr + LdrDataTableEntry64::size();
    ldr.base_dll_name.length = libname.len() as u16 * 2;
    ldr.base_dll_name.maximum_length = libname.len() as u16 * 2;
    ldr.base_dll_name.buffer = space_addr + LdrDataTableEntry64::size() + full_libname.len() as u64 * 2 + 10;
    ldr.flags = 0;
    ldr.load_count = 0;
    ldr.tls_index = 0;
    ldr.hash_links.flink = next_flink;
    ldr.hash_links.blink = prev_flink;
    mem.write_wide_string(space_addr + LdrDataTableEntry64::size(), &(full_libname.clone() + "\x00\x00"));
    mem.write_wide_string(space_addr + LdrDataTableEntry64::size() + full_libname.len() as u64 * 2 +10, &(libname.to_string() + "\x00"));
    ldr.save(space_addr, &mut emu.maps);

I have to do some window reversing to get how is the FullDllName, which is the input value of the hashing.

For now Im super busy and will continue on Sunday.

sha0coder commented 1 day ago
=>ldr
0x9a4 loader.exe flink:12e4 blink:6f64 base:7ff00aaa280 pe_hdr:f0 5045
0x12e4 ntdll.dll flink:1c24 blink:9a4 base:7ff000ee108 pe_hdr:e8 5045
0x1c24 kernel32.dll flink:2564 blink:12e4 base:7fefffbaa28 pe_hdr:f0 5045
0x2564 kernelbase.dll flink:2ea4 blink:1c24 base:7ff00492f30 pe_hdr:f0 5045
0x2ea4 iphlpapi.dll flink:37e4 blink:2564 base:7fefff38098 pe_hdr:f8 5045
0x37e4 ws2_32.dll flink:4124 blink:2ea4 base:7ff00311b80 pe_hdr:f0 5045
0x4124 advapi32.dll flink:4a64 blink:37e4 base:7ff003934c0 pe_hdr:100 5045
0x4a64 comctl64.dll flink:53a4 blink:4124 base:7ff007b68a8 pe_hdr:f8 5045
0x53a4 winhttp.dll flink:5ce4 blink:4a64 base:7ff0094f768 pe_hdr:f8 5045
0x5ce4 wininet.dll flink:6624 blink:53a4 base:7ff00b8aa00 pe_hdr:f0 5045
0x6624 dnsapi.dll flink:6f64 blink:5ce4 base:7ff0086a800 pe_hdr:f8 5045
0x6f64 shell32.dll flink:9a4 blink:6624 base:7ff788c0000 pe_hdr:f0 5045
=>dt
structure=>ldr_data_table_entry64
address=>0x1c24
LdrDataTableEntry64 {
    in_load_order_links: ListEntry64 {
        flink: 0x2564,
        blink: 0x12e4,
    },
    in_memory_order_links: ListEntry64 {
        flink: 0x2574,
        blink: 0x9b4,
    },
    in_initialization_order_links: ListEntry64 {
        flink: 0x2584,
        blink: 0x1304,
    },
    dll_base: 0x7fefffbaa28,
    entry_point: 0xf0,
    size_of_image: 0x0,
    full_dll_name: UnicodeString64 {
        length: 0x40,
        maximum_length: 0x40,
        padding: 0x0,
        buffer: 0x1d24,
    },
    base_dll_name: UnicodeString64 {
        length: 0x18,
        maximum_length: 0x18,
        padding: 0x0,
        buffer: 0x1d6e,
    },
    flags: 0x0,
    load_count: 0x0,
    tls_index: 0x0,
    hash_links: ListEntry64 {
        flink: 0x9a4,
        blink: 0x12e4,
    },
    time_date_stamp: 0x0,
}
=>md
address=>0x1d24
0x1d24: 43 00 3a 00 5c 00 57 00 69 00 6e 00 64 00 6f 00     C.:.\.W.i.n.d.o.
0x1d34: 77 00 73 00 5c 00 53 00 79 00 73 00 74 00 65 00     w.s.\.S.y.s.t.e.
0x1d44: 6d 00 33 00 32 00 5c 00 6b 00 65 00 72 00 6e 00     m.3.2.\.k.e.r.n.
0x1d54: 65 00 6c 00 33 00 32 00 2e 00 64 00 6c 00 6c 00     e.l.3.2...d.l.l.
0x1d64: 00 00 00 00 00 00 00 00 00 00 6b 00 65 00 72 00     ..........k.e.r.
0x1d74: 6e 00 65 00 6c 00 33 00 32 00 2e 00 64 00 6c 00     n.e.l.3.2...d.l.
0x1d84: 6c 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00     l……………
sha0coder commented 28 minutes ago

It’s fixed, I’m going to publish the latest changes

~/s/scemu ❯❯❯ cargo run --release -- -f shellcodes64/metasploit.bin -6                                                                   ✘ 130 main ✱ ◼
    Finished `release` profile [optimized] target(s) in 0.02s
     Running `target/release/scemu -f shellcodes64/metasploit.bin -6`
use -vv to see the assembly code emulated, and -v to see the messages
loading memory maps
loading pe64: shellcodes64/metasploit.bin
shellcode detected.
 ----- emulation -----
** 635367 kernel32!LoadLibraryA  'ws2_32' =0x7ff00311b80
calling unimplemented ws2_32 API 0x7ff00320690 WSAStartup
WSAStartup(257, 1372936, 0, 0) (unimplemented)
calling unimplemented ws2_32 API 0x7ff00325b90 WSASocketA
WSASocketA(3, 2, 0, 0) (unimplemented)
** 3837112 ws2_32!connect  family: 2 10.25.44.1:4444
    invalid socket.
** 4897337 ws2_32!connect  family: 2 10.25.44.1:4444
    invalid socket.
** 5957562 ws2_32!connect  family: 2 10.25.44.1:4444
    invalid socket.
** 7017787 ws2_32!connect  family: 2 10.25.44.1:4444
    invalid socket.
** 8078012 ws2_32!connect  family: 2 10.25.44.1:4444
    invalid socket.
** 9138237 ws2_32!connect  family: 2 10.25.44.1:4444
    invalid socket.
^CCtrl-C detected, spawning console
--- console —
sha0coder commented 23 minutes ago
 ----- emulation -----
** 635367 kernel32!LoadLibraryA  'ws2_32' =0x7ff00311b80
** 1706051 ws2_32!WsaStartup
** 2776890 ws2_32!WsaSocketA
** 3837112 ws2_32!connect  family: 2 10.25.44.1:4444
** 4895567 ws2_32!recv   buff: 0x14f260 sz: 4
sha0coder commented 13 minutes ago

I published the fix on crates.io pypi and the 3 gits