Vulnerability Development mailing list archives

Win32: Using SEH to search memory


From: "Bob Askew" <bdaskew () hotmail com>
Date: Wed, 24 Sep 2003 23:06:34 +0000

I'm trying to search through memory using structured exception handling to avoid crashing when accessing bad memory. Various buffer overflow exploits have used this technique for locating the address of GetProcAdd() or for locating shellcode planted in memory.

I have an example written in inline assembly and compiled with Visual Studio on XP. It implements seh and searches through memory just fine. My handler handles the memory access violations. (Example 1 code below) However, if I stick my handler on the stack, then Windows doesn't send the exception to my handler. (Example 2 code below)

Does anyone have any suggestions as to what I might be doing wrong? Does Windows care where a handler lives in memory? Can anyone recommend a good reference for implementing seh in shellcode?


Example 1:
*****************************************

#include<stdio.h>

//simple test for SEH with handler

void main()
{
        unsigned int cint = 0;

        __asm{

                jmp gethandler
start:
                xor ebx,ebx
                xor ecx,ecx
                push dword ptr fs:[ecx]
                mov dword ptr fs:[ecx],esp
search:
                inc ebx
                cmp dword ptr[ebx],0x00000000   ;//causes exception

//exception cleanup
                xor     ecx,ecx         ;
                mov     eax,[ESP]               ; // Get pointer to previous record
                mov     FS:[ecx], eax           ; // Install previous record
                add     esp, 8          ; //clean handler & fs[0] off stack
                jmp printit

gethandler:
                call start
handler:
                push ebp
                        mov ebp,esp
                push ebx
                mov ebx,[ebp+10h]
                add ebx,0xa4
                inc dword ptr[ebx]  ;//increment ebx
                xor eax,eax
                pop ebx
                mov esp,ebp
                pop ebp
                ret
printit:
                mov [cint],ebx
        }
        printf("Last ebx = %x\n",cint);

}

Example 2:
*****************************************

#include<stdio.h>

//simple test for SEH with handler located on stack

void main()
{
        unsigned int cint = 0;

        char unsigned bytes[] =
                "\xEB\x1B"             // jmp         gethandler
//start:
                "\x33\xDB"             // xor         ebx,ebx
                "\x33\xC9"             // xor         ecx,ecx
                "\x64\xFF\x31"         // push        dword ptr fs:[ecx]
                "\x64\x89\x21"         // mov         dword ptr fs:[ecx],esp
//search:
                "\x43"                 // inc         ebx
                "\x83\x3B\x00"         // cmp         dword ptr [ebx],0
//SEH cleanup
                "\x33\xC9"             // xor         ecx,ecx
                "\x8B\x04\x24"         // mov         eax,dword ptr [esp]
                "\x64\x89\x01"         // mov         dword ptr fs:[ecx],eax
                "\x83\xC4\x08"         // add         esp,8
                "\xEB\x1B"             // jmp         printit
//gethandler:
                "\xE8\xE0\xFF\xFF\xFF" // call        start
//handler:
                "\x55"                 // push        ebp
                "\x8B\xEC"             // mov         ebp,esp
                "\x53"                 // push        ebx
                "\x8B\x5D\x10"                 // mov         ebx,dword ptr [ebp+10h]
                "\x81\xC3\xA4\x00\x00\x00"//add         ebx,0A4h
                "\xFF\x03"                     // inc         dword ptr [ebx]
                "\x33\xC0"             // xor         eax,eax
                "\x5B"                 // pop         ebx
                "\x8B\xE5"             // mov         esp,ebp
                "\x5D"                 // pop         ebp
                "\xC3"                 // ret
//printit: (clean exit?)
                "\xff\xd2";              //jump edx

        __asm{
                lea eax,bytes
                lea edx,printit
                jmp eax
printit:
                mov [cint],ebx
        }

        printf("Last ebx = %x\n",cint);       //probably will never make it here.

}

_________________________________________________________________
High-speed Internet access as low as $29.95/month (depending on the local service providers in your area). Click here. https://broadband.msn.com


Current thread: