Application error after calling Detoured function which I created @ Win7-x64

I'm new here and my first question was asked. I hope everything goes well here :) And for my question !:

I wrote the Detouring framework for x64 processor (normal intel x64)

The main interesting features are as follows:

typedef ULONG_PTR (WINAPI *MESSAGEBOX)(HWND, LPCSTR, LPCSTR, UINT);

    DWORD WINAPI DETOUR_MyMessageboxA(MESSAGEBOX OriginalFunction, HWND hWnd, LPCSTR lpText, LPCSTR lpCaption, UINT uType)
    {
        OutputDebugPrintA("Success.");
        return OriginalFunction(hWnd, lpText, lpCaption, uType);
    }

      

When I merge MessageBoxA, I wrote the following ASM code:

push rdi
push r9

sub rsp, 20
mov rdi, rsp

mov r9, r8
mov r8, rdx
mov rdx, ecx
mov ecx, [ORIGINAL_ADDRESS]

call DETOUR_MyMessageboxA

add rsp, 20

pop r9
pop rdi
ret

      

The idea is to basically "Shift right" the arguments and add another argument (My function source address) to the detour. I hope I figured out that the calling convention looks like this:

First Arg: RCX

Second Arg: RDX

Third Arg: R8

Fourth Arg: R9

Anything else in the rsp (under the "Shadow space" thingy)

Just make sure that on the same page with everyone .. the stack should look like this to call the function:

    GARBAGE.....
RSP RetAddress
    8BYTE-GARBAGE - [Shadow space]
    8BYTE-GARBAGE - [Shadow space]
    8BYTE-GARBAGE - [Shadow space]
    8BYTE-GARBAGE - [Shadow space]
    Arg5
    Arg6
    ...

      

Now, after I start to connect and my Assembly code is called instead of the original function, I get an exception:

0:000> g
(624.17b4): Access violation - code c0000005 (first chance)
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
ntdll!RtlCaptureContext+0x86:
00000000`76d508c5 0fae8100010000  fxsave  [rcx+100h]    ds:00000000`0026ead8=50
0:000> k
Child-SP          RetAddr           Call Site
00000000`0026e998 00000000`76d195c8 ntdll!RtlCaptureContext+0x86
00000000`0026e9a8 000007fe`fccc940d ntdll!RtlRaiseException+0x48
00000000`0026efe8 000007fe`fccdaa0d KERNELBASE!RaiseException+0x39
00000000`0026f0b8 000007fe`f6ec2c7a KERNELBASE!OutputDebugStringA+0x6d
00000000`0026f388 00000000`0014002f Detour_RekSai!DETOUR_MyMessageboxA+0x3a [c:\projects\test.c @ 14]
00000000`0026f3b8 00000000`00130000 0x14002f
00000000`0026f3c0 00000000`00000000 0x130000
0:000> !vprot 00000000`0026ead8
BaseAddress:       000000000026e000
AllocationBase:    00000000001f0000
AllocationProtect: 00000004  PAGE_READWRITE
RegionSize:        0000000000002000
State:             00001000  MEM_COMMIT
Protect:           00000004  PAGE_READWRITE
Type:              00020000  MEM_PRIVATE
0:000> db rcx+100 L20
00000000`0026ead8  50 f0 26 00 00 00 00 00-58 f9 26 00 00 00 00 00  P.&.....X.&.....
00000000`0026eae8  00 00 00 00 00 00 00 00-e9 c9 ec f6 fe 07 00 00  ................
0:000> !gle
LastErrorValue: (NTSTATUS) 0xc0000008 (3221225480) - An invalid HANDLE was specified.
LastStatusValue: (NTSTATUS) 0xc0000005 - The instruction at 0x%08lx referenced memory at 0x%08lx. The memory could not be %s.

      

Now I have no idea what is causing this. I think I have all the variables and looped correctly ... right? I don't know what this memory location is or why this is happening.

Thanks for any help ..

EDIT : If I remove "OutputDebugPrint" in my function:

DWORD WINAPI DETOUR_MyMessageboxA(MESSAGEBOX OriginalFunction, HWND hWnd, LPCSTR lpText, LPCSTR lpCaption, UINT uType)
{
    return OriginalFunction(hWnd, lpText, lpCaption, uType);
}

      

I still get the exception (different, but something tells me that both of them are being called due to the same).

0:000> g
(1e3c.298c): Access violation - code c0000005 (first chance)
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
LPK!LpkCharsetDraw+0x78:
000007fe`fe811775 440f29842450010000 movaps xmmword ptr [rsp+150h],xmm8 ss:00000000`0026ebf8=000007fefe91a8e40000000002051320
0:000> k
Child-SP          RetAddr           Call Site
00000000`0026eaa8 000007fe`fe8114cc LPK!LpkCharsetDraw+0x78
00000000`0026ec68 00000000`76af85c5 LPK!LpkDrawTextEx+0x68
00000000`0026ecd8 00000000`76af87fc USER32!DT_DrawStr+0xa6
00000000`0026ed78 00000000`76af8216 USER32!DT_GetLineBreak+0x241
00000000`0026ee28 00000000`76b51e07 USER32!DrawTextExWorker+0x3f8
00000000`0026ef38 00000000`76b523e9 USER32!MB_CalcDialogSize+0x187
00000000`0026efd8 00000000`76b51c15 USER32!SoftModalMessageBox+0x47d
00000000`0026f108 00000000`76b5146b USER32!MessageBoxWorker+0x31d
00000000`0026f2c8 00000000`76b51362 USER32!MessageBoxTimeoutW+0xb3
00000000`0026f398 000007fe`ecfe2c85 USER32!MessageBoxW+0x4e
00000000`0026f3d8 00000000`0015002f Detour_RekSai!DETOUR_MyMessageboxA+0x45 [c:\users\ariel\documents\visual studio 2012\projects\detour_reksai\detour_reksai\test.c @ 19]
00000000`0026f408 00000000`00140000 0x15002f
00000000`0026f410 00000000`00000000 0x140000
0:000> !vprot [rsp+150h]
BaseAddress:       000000000026e000
AllocationBase:    00000000001f0000
AllocationProtect: 00000004  PAGE_READWRITE
RegionSize:        0000000000002000
State:             00001000  MEM_COMMIT
Protect:           00000004  PAGE_READWRITE
Type:              00020000  MEM_PRIVATE
0:000> db [rsp+150h] L20
00000000`0026ebf8  20 13 05 02 00 00 00 00-e4 a8 91 fe fe 07 00 00   ...............
00000000`0026ec08  01 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
0:000> !gle
LastErrorValue: (Win32) 0 (0) - The operation completed successfully.
LastStatusValue: (NTSTATUS) 0xc0000005 - The instruction at 0x%08lx referenced memory at 0x%08lx. The memory could not be %s.

      

+3


source to share


1 answer


You may have missed this line: The This exception may be expected and handled.

exception is reportedly coming from OutputDebugPrintA

and I doubt it has much to do with your traversal logic. Make sure this is a real unhandled exception.

PS: Not sure what you wanted to do with mov edi, esp

.


As per the comments, it seems your problem is inconsistency rsp

. You must support 16 byte alignment. In this case, you push 2 items (costs 16 bytes) and then set to 32, and finally you have call

, which pushes 8 bytes of the return address onto the stack. In general, you have 8x misalignment. Since you don't need it in this code rdi

, you can simply omit push

/ pop

for this and thereby eliminate the misalignment. Also, using mov

makes the situation clearer:



sub rsp, 28h

mov [rsp+20h], r9
mov r9, r8
mov r8, rdx
mov rdx, rcx
mov ecx, [ORIGINAL_ADDRESS]

call DETOUR_MyMessageboxA

add rsp, 28h
ret

      


How am I supposed to implement let, say 5 variable traversals?

mov rax, [rsp+28h] ; 5th arg
sub rsp, 38h       ; space for 6 args + alignment

mov [rsp+28h], rax
mov [rsp+20h], r9
mov r9, r8
mov r8, rdx
mov rdx, rcx
mov ecx, [ORIGINAL_ADDRESS]

call DETOUR

add rsp, 38h
ret

      

+1


source







All Articles