flat assembler
Message board for the users of flat assembler.
Index
> Windows > Detours example crashes |
Author |
|
Adam Kachwalla 25 Aug 2007, 06:22
What OS are you running it under? If you are talking about the "Windows hooking example" on the Examples page, I can run that under Longhorn Server without a problem.
|
|||
25 Aug 2007, 06:22 |
|
StakFallT 25 Aug 2007, 08:29
Windows XP SP 2 and yeah, the windows hooking example
|
|||
25 Aug 2007, 08:29 |
|
StakFallT 25 Aug 2007, 18:18
ok I definitely found the spot I think, it wasn't my original belief of where the code-flow was always coming back to (upon a ret from ntdll). Ok lemme elaborate.
I ran the newly downloaded and compiled detours example, it crashes, so I loaded it up into OllyDbg and I found it to make some jumps (no phun intended) to ntdll, probably due to the various Heap Allocations the example does, anyhow, I had thought when control comes back from ntdll ollydbg was showing me that it lands here: Code: mov ecx, ebx add ecx, $5 ; +$5 for jmp + address back to original API call halloc test eax, eax jz .done it does't.. it lands here Code: @@: push ecx push $0 push dword [.heapaddr] call [HeapAlloc] pop edi esi ebx ret .hinit: ; get the process heap call [GetProcessHeap] ; .ProcessHeap is located at +$18 in the ; Process Environment Block test eax, eax jz .err mov dword [.heapaddr], eax ; <--- The line that OllyDbg shows flow ; always comes back to jmp @b It seems like it's having some kind of memory allocating problem. The error I get in my console window in ollydbg is: [/code] Log data, item 1 Address=0040233A Message=Access violation when writing to [00402345] Log data, item 0 Message=Debugged program was unable to process exception [/code] A problem allocating memory would certainly explain the memory access violation, er the other way around. An access violation would certainly explain why it can't allocate memory. I know the detours (The Windows Hooking) example does modify memory permissions, but I'm pretty sure that's only for writing opcodes to the particular Windows API call's memory. as I said I'm on Windows XP SP2.. It is somewhat of a botched sp2 upgrade though. I kind of downgraded when I heard from other techs about how bad the upgrade is (they said it's not so bad if it's an OEM install with sp2), but unfortunately for me it didn't downgrade all that well, it's kinda of a hybrid sp1/sp2. BUT... the specific DLLs can only be each either sp1 or sp2, it's not like you can have a DLL half sp1 and half-sp2, at least not without it not-working. My original thought is maybe the DLL that has the memory_alloc APIs are one sp and the api it's hooking is another, but again, if that were the case it would be seriously big time noticeable via lots and lots of windows crashes on other applications/games/etc <whatever else>. Now I do get lots of errors about anything odbc related, like checking event logs (I get permission errors which are actually in error, so I have to browse to the event log file and open it as a saved log file).. So it's kinda been proven that if there's a conflict between sp1 and sp2 files it would show itself. Especially on something as basic/generic as the MessageBoxA (Which the detours example latches into) API. I've kinda thought this through a bit and I don't think it's because this is a botched upgrade/downgrade that would affect it. The only reason I keep coming back to my install is because you said you downloaded it, compiled it and it ran fine ( I even tried running the exe that came with the zip). But then again you're on Server 2003, they might've improved memory handling slightly or something weird, but that can't really be the case because the example was made before 2003 I'm sure, but... unless nobody ever bothered to try it since it's making (the example that is) which is kinda hard to believe.. Hmm I dunno, too many coins with too many equal opposing sides. I guess the best way to figure this out is, go with what is fact: 1 - The problem exists on my dev setup. 2 - My Windows sp number is not known for certain. 3 - I've tried the exe inside the zip and that doesn't run without crashing. 4 - The ASM code compiles ok. 5 - The compiled code doesn't run without crashing. 6 - Loading it into Ollydbg on my dev setup and running reveals the code-flow constantly coming back to the above code to the above mentioned (in the asm code) line. I think we need someone with an actual known sp1 to run it and someone with an actual known sp2 to run it, and see if it works. (I wonder... It's kind of a bit of a stretch but I have seen online games crash due to things like the ATI control center is loaded in the systray. Now I've went as far as disabling my McAfee virus scanner, but I wonder if there's some kind of conflict with another program already running...) Edit: Just realized something, why would an application get an access violation just trying to allocate memory for itself, doesn't make sense... I wonder if the access violation is caused by the permission on the memory not successfully being modified. Though the violation does seem to come during the halloc business. |
|||
25 Aug 2007, 18:18 |
|
FrozenKnight 25 Aug 2007, 21:39
I have stated before i don't like the detour method of hooking. because of the way fASM handles data, hooks like this one are easy. as you can access the API memory location directly. but if you wanted to do this hte hard way then you can always walk through the PE and replace the API call location in the PE. both of these methods will work on all versions of windows and are much safer than trying to modify system dll's. Simple ms updates can destroy such hooks.
|
|||
25 Aug 2007, 21:39 |
|
StakFallT 26 Aug 2007, 15:48
Couple of questions:
1 - When you say "like this one are easy" are you referring to the detours example? And yeah I've tried the IAT route, somehow "not fun" just doesn't quite express it well enough 2 - What exactly do you mean by modifying system dll's? You mean open the dll in something like hiew and literally permanently change the data? yeesh! (sp?) Nah my idea of what I'm trying to do is someone can download the app, drop it into the location where they want and run it. (But still having problems getting the detours example to run :/ ) |
|||
26 Aug 2007, 15:48 |
|
FrozenKnight 27 Aug 2007, 09:36
Detours modify system or other dll's in memory, what i was referring to was
Code: mov [fun], hookedfun As for the IAT problem simply look over an example of manual imports they should help a little. And I should be able to help with any problems as i have used this method before. |
|||
27 Aug 2007, 09:36 |
|
StakFallT 27 Aug 2007, 23:34
Well the problem with something like:
Code: mov [fun], hookedfun is it doesn't preserve the original API code, the idea for my app is that it will spit out the parameters to the console passed to the API, call the API and then also spit out the result to the console, after which passing the API result back to the app that made the call. The IAT stuff could work, I mean it would just I dunno how difficult it would be for me. I did play around a bit with IAT modifying stuff in MASM and it was kind of a nightmare, the code was based off existing code and the resulting asm code was designed to be encapsulated into a DLL with an exported function called Install_hook, or something to that effect, which was then to be called by a VB program. The nice thing about the detours method was that it didn't seem like it would need to be made into a DLL.. Can the IAT method be done the same way (i.e. make it into an app and not a dll with exported functions called by an app to install the DLL's hook code) |
|||
27 Aug 2007, 23:34 |
|
FrozenKnight 28 Aug 2007, 17:01
Well, I'm not really fond of giving this code out this is only 2 of the 7 source files i used for this project. (i like separating by content and sections) but if you can follow it then you should have no problem with hooking the IAT
heres the most important part the PE inc. this has all of the structures you will need to find and hook the IAT provided you have the base addr of the modual. (sorry, about the C style comments I used struts form MSDN to create this file.) PE.INC Code: ;#define IMAGE_DOS_SIGNATURE 0x5A4D // MZ ;#define IMAGE_OS2_SIGNATURE 0x454E // NE ;#define IMAGE_OS2_SIGNATURE_LE 0x454C // LE ;#define IMAGE_VXD_SIGNATURE 0x454C // LE ;#define IMAGE_NT_SIGNATURE 0x00004550 // PE00 IMAGE_DOS_SIGNATURE = 0x5A4D IMAGE_OS2_SIGNATURE = 0x454E IMAGE_OS2_SIGNATURE_LE = 0x454C IMAGE_VXD_SIGNATURE = 0x454C IMAGE_NT_SIGNATURE = 0x00004550 ;typedef struct _IMAGE_DOS_HEADER { // DOS .EXE header ; WORD e_magic; // Magic number ; WORD e_cblp; // Bytes on last page of file ; WORD e_cp; // Pages in file ; WORD e_crlc; // Relocations ; WORD e_cparhdr; // Size of header in paragraphs ; WORD e_minalloc; // Minimum extra paragraphs needed ; WORD e_maxalloc; // Maximum extra paragraphs needed ; WORD e_ss; // Initial (relative) SS value ; WORD e_sp; // Initial SP value ; WORD e_csum; // Checksum ; WORD e_ip; // Initial IP value ; WORD e_cs; // Initial (relative) CS value ; WORD e_lfarlc; // File address of relocation table ; WORD e_ovno; // Overlay number ; WORD e_res[4]; // Reserved words ; WORD e_oemid; // OEM identifier (for e_oeminfo) ; WORD e_oeminfo; // OEM information; e_oemid specific ; WORD e_res2[10]; // Reserved words ; LONG e_lfanew; // File address of new exe header ; } IMAGE_DOS_HEADER, *PIMAGE_DOS_HEADER; struct IMAGE_DOS_HEADER e_magic dw ? e_cblp dw ? e_cp dw ? e_crlc dw ? e_cparhdr dw ? e_minalloc dw ? e_maxalloc dw ? e_ss dw ? e_sp dw ? e_csum dw ? e_ip dw ? e_cs dw ? e_lfarlc dw ? e_ovno dw ? e_res dw 4 dup (?) e_oemid dw ? e_oeminfo dw ? e_res2 dw 10 dup (?) e_lfanew dd ? ends ;typedef struct _IMAGE_FILE_HEADER { ; WORD Machine; ; WORD NumberOfSections; ; DWORD TimeDateStamp; ; DWORD PointerToSymbolTable; ; DWORD NumberOfSymbols; ; WORD SizeOfOptionalHeader; ; WORD Characteristics; ;} IMAGE_FILE_HEADER, *PIMAGE_FILE_HEADER; struct IMAGE_FILE_HEADER Machine dw ? NumberOfSections dw ? TimeDateStamp dd ? PointerToSymbolTable dd ? NumberOfSymbols dd ? SizeOfOptionalHeader dw ? Characteristics dw ? ends ;#define IMAGE_NUMBEROF_DIRECTORY_ENTRIES 16 IMAGE_NUMBEROF_DIRECTORY_ENTRIES = 16 ;typedef struct _IMAGE_DATA_DIRECTORY { ; DWORD VirtualAddress; ; DWORD Size; ;} IMAGE_DATA_DIRECTORY, *PIMAGE_DATA_DIRECTORY; struct IMAGE_DATA_DIRECTORY VirtualAddress dd ? Size dd ? ends ;typedef struct _IMAGE_OPTIONAL_HEADER { ; // ; // Standard fields. ; // ; ; WORD Magic; ; BYTE MajorLinkerVersion; ; BYTE MinorLinkerVersion; ; DWORD SizeOfCode; ; DWORD SizeOfInitializedData; ; DWORD SizeOfUninitializedData; ; DWORD AddressOfEntryPoint; ; DWORD BaseOfCode; ; DWORD BaseOfData; ; ; // ; // NT additional fields. ; // ; ; DWORD ImageBase; ; DWORD SectionAlignment; ; DWORD FileAlignment; ; WORD MajorOperatingSystemVersion; ; WORD MinorOperatingSystemVersion; ; WORD MajorImageVersion; ; WORD MinorImageVersion; ; WORD MajorSubsystemVersion; ; WORD MinorSubsystemVersion; ; DWORD Win32VersionValue; ; DWORD SizeOfImage; ; DWORD SizeOfHeaders; ; DWORD CheckSum; ; WORD Subsystem; ; WORD DllCharacteristics; ; DWORD SizeOfStackReserve; ; DWORD SizeOfStackCommit; ; DWORD SizeOfHeapReserve; ; DWORD SizeOfHeapCommit; ; DWORD LoaderFlags; ; DWORD NumberOfRvaAndSizes; ; IMAGE_DATA_DIRECTORY DataDirectory[IMAGE_NUMBEROF_DIRECTORY_ENTRIES]; ;} IMAGE_OPTIONAL_HEADER32, *PIMAGE_OPTIONAL_HEADER32; struct IMAGE_OPTIONAL_HEADER32 ;Standard fields. Magic dw ? MajorLinkerVersion db ? MinorLinkerVersion db ? SizeOfCode dd ? SizeOfInitializedData dd ? SizeOfUninitializedData dd ? AddressOfEntryPoint dd ? BaseOfCode dd ? BaseOfData dd ? ;NT additional fields. ImageBase dd ? SectionAlignment dd ? FileAlignment dd ? MajorOperatingSystemVersion dw ? MinorOperatingSystemVersion dw ? MajorImageVersion dw ? MinorImageVersion dw ? MajorSubsystemVersion dw ? MinorSubsystemVersion dw ? Win32VersionValue dd ? SizeOfImage dd ? SizeOfHeaders dd ? CheckSum dd ? Subsystem dw ? DllCharacteristics dw ? SizeOfStackReserve dd ? SizeOfStackCommit dd ? SizeOfHeapReserve dd ? SizeOfHeapCommit dd ? LoaderFlags dd ? NumberOfRvaAndSizes dd ? DataDirectory IMAGE_DATA_DIRECTORY; IMAGE_NUMBEROF_DIRECTORY_ENTRIES dup (?) rb sizeof.IMAGE_DATA_DIRECTORY * (IMAGE_NUMBEROF_DIRECTORY_ENTRIES -1) ends ;typedef struct _IMAGE_NT_HEADERS { ; DWORD Signature; ; IMAGE_FILE_HEADER FileHeader; ; IMAGE_OPTIONAL_HEADER32 OptionalHeader; ;} IMAGE_NT_HEADERS32, *PIMAGE_NT_HEADERS32; struct IMAGE_NT_HEADERS32 Signature dd ? FileHeader IMAGE_FILE_HEADER OptionalHeader IMAGE_OPTIONAL_HEADER32 ends ;#define IMAGE_SIZEOF_SHORT_NAME 8 IMAGE_SIZEOF_SHORT_NAME = 8 ;typedef struct _IMAGE_SECTION_HEADER { ; BYTE Name[IMAGE_SIZEOF_SHORT_NAME]; ; union { ; DWORD PhysicalAddress; ; DWORD VirtualSize; ; } Misc; ; DWORD VirtualAddress; ; DWORD SizeOfRawData; ; DWORD PointerToRawData; ; DWORD PointerToRelocations; ; DWORD PointerToLinenumbers; ; WORD NumberOfRelocations; ; WORD NumberOfLinenumbers; ; DWORD Characteristics; ;} IMAGE_SECTION_HEADER, *PIMAGE_SECTION_HEADER; struct IMAGE_SECTION_HEADER Name db IMAGE_SIZEOF_SHORT_NAME dup (?) union PhysicalAddress dd ? VirtualSize dd ? ends VirtualAddress dd ? SizeOfRawData dd ? PointerToRawData dd ? PointerToRelocations dd ? PointerToLinenumbers dd ? NumberOfRelocations dw ? NumberOfLinenumbers dw ? Characteristics dd ? ends ;typedef struct _IMAGE_IMPORT_DESCRIPTOR { ; union { ; DWORD Characteristics; // 0 for terminating null import descriptor ; DWORD OriginalFirstThunk; // RVA to original unbound IAT (PIMAGE_THUNK_DATA) ; }; ; DWORD TimeDateStamp; // 0 if not bound, ; // -1 if bound, and real date\time stamp ; // in IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT (new BIND) ; // O.W. date/time stamp of DLL bound to (Old BIND) ; ; DWORD ForwarderChain; // -1 if no forwarders ; DWORD Name; ; DWORD FirstThunk; // RVA to IAT (if bound this IAT has actual addresses) ;} IMAGE_IMPORT_DESCRIPTOR; ;typedef IMAGE_IMPORT_DESCRIPTOR UNALIGNED *PIMAGE_IMPORT_DESCRIPTOR; struct IMAGE_IMPORT_DESCRIPTOR union Characteristics dd ? OriginalFirstThunk dd ? ends TimeDateStamp dd ? ForwarderChain dd ? Name dd ? FirstThunk dd ? ends ;typedef struct _IMAGE_IMPORT_BY_NAME { ; WORD Hint; ; BYTE Name[1]; ;} IMAGE_IMPORT_BY_NAME, *PIMAGE_IMPORT_BY_NAME; struct IMAGE_IMPORT_BY_NAME Hint dw ? Name db 1 dup (?) ends ;typedef struct _IMAGE_THUNK_DATA32 { ; union { ; DWORD ForwarderString; // PBYTE ; DWORD Function; // PDWORD ; DWORD Ordinal; ; DWORD AddressOfData; // PIMAGE_IMPORT_BY_NAME ; } u1; ;} IMAGE_THUNK_DATA32; struct IMAGE_THUNK_DATA32 union ForwarderString dd ? Function dd ? Ordinal dd ? AddressOfData dd ? ends ends ;#define IMAGE_ORDINAL_FLAG32 0x80000000 IMAGE_ORDINAL_FLAG32 = 0x80000000 IMAGE_SCN_TYPE_REG = 0x00000000 ;Reserved. IMAGE_SCN_TYPE_DSECT = 0x00000001 ;Reserved. IMAGE_SCN_TYPE_NOLOAD = 0x00000002 ;Reserved. IMAGE_SCN_TYPE_GROUP = 0x00000004 ;Reserved. IMAGE_SCN_TYPE_NO_PAD = 0x00000008 ;Reserved. IMAGE_SCN_TYPE_COPY = 0x00000010 ;Reserved. IMAGE_SCN_CNT_CODE = 0x00000020 ;Section contains executable code. IMAGE_SCN_CNT_INITIALIZED_DATA = 0x00000040 ;Section contains initialized data. IMAGE_SCN_CNT_UNINITIALIZED_DATA = 0x00000080 ;Section contains uninitialized data. IMAGE_SCN_LNK_OTHER = 0x00000100 ;Reserved. IMAGE_SCN_LNK_INFO = 0x00000200 ;Reserved. IMAGE_SCN_TYPE_OVER = 0x00000400 ;Reserved. IMAGE_SCN_LNK_COMDAT = 0x00001000 ;Section contains COMDAT data. IMAGE_SCN_MEM_FARDATA = 0x00008000 ;Reserved. IMAGE_SCN_MEM_PURGEABLE = 0x00020000 ;Reserved. IMAGE_SCN_MEM_16BIT = 0x00020000 ;Reserved. IMAGE_SCN_MEM_LOCKED = 0x00040000 ;Reserved. IMAGE_SCN_MEM_PRELOAD = 0x00080000 ;Reserved. IMAGE_SCN_ALIGN_1BYTES = 0x00100000 ;Align data on a 1-byte boundary. IMAGE_SCN_ALIGN_2BYTES = 0x00200000 ;Align data on a 2-byte boundary. IMAGE_SCN_ALIGN_4BYTES = 0x00300000 ;Align data on a 4-byte boundary. IMAGE_SCN_ALIGN_8BYTES = 0x00400000 ;Align data on a 8-byte boundary. IMAGE_SCN_ALIGN_16BYTES = 0x00500000 ;Align data on a 16-byte boundary. IMAGE_SCN_ALIGN_32BYTES = 0x00600000 ;Align data on a 32-byte boundary. IMAGE_SCN_ALIGN_64BYTES = 0x00700000 ;Align data on a 64-byte boundary. IMAGE_SCN_ALIGN_128BYTES = 0x00800000 ;Align data on a 128-byte boundary. IMAGE_SCN_ALIGN_256BYTES = 0x00900000 ;Align data on a 256-byte boundary. IMAGE_SCN_ALIGN_512BYTES = 0x00A00000 ;Align data on a 512-byte boundary. IMAGE_SCN_ALIGN_1024BYTES = 0x00B00000 ;Align data on a 1024-byte boundary. IMAGE_SCN_ALIGN_2048BYTES = 0x00C00000 ;Align data on a 2048-byte boundary. IMAGE_SCN_ALIGN_4096BYTES = 0x00D00000 ;Align data on a 4096-byte boundary. IMAGE_SCN_ALIGN_8192BYTES = 0x00E00000 ;Align data on a 8192-byte boundary. IMAGE_SCN_LNK_NRELOC_OVFL = 0x01000000 ;Section contains extended relocations. IMAGE_SCN_MEM_DISCARDABLE = 0x02000000 ;Section can be discarded as needed. IMAGE_SCN_MEM_NOT_CACHED = 0x04000000 ;Section cannot be cached. IMAGE_SCN_MEM_NOT_PAGED = 0x08000000 ;Section cannot be paged. IMAGE_SCN_MEM_SHARED = 0x10000000 ;Section can be shared in memory. IMAGE_SCN_MEM_EXECUTE = 0x20000000 ;Section can be executed as code. IMAGE_SCN_MEM_READ = 0x40000000 ;Section can be read. IMAGE_SCN_MEM_WRITE = 0x80000000 ;Section can be written to. this is the actual core of the hook it looks up the base address from the modual name, then it used structs defined previously to address the IAT and modify a function based on it's name or ord. sorry i didnt comment much as i didn't think i would be using this source again.) Code: ;#define PAGE_NOACCESS 0x01 PAGE_NOACCESS = 0x01 ;#define PAGE_READONLY 0x02 PAGE_READONLY = 0x02 ;#define PAGE_READWRITE 0x04 PAGE_READWRITE = 0x04 ;#define PAGE_WRITECOPY 0x08 PAGE_WRITECOPY = 0x08 ;#define PAGE_EXECUTE 0x10 PAGE_EXECUTE = 0x10 ;#define PAGE_EXECUTE_READ 0x20 PAGE_EXECUTE_READ = 0x20 ;#define PAGE_EXECUTE_READWRITE 0x40 PAGE_EXECUTE_READWRITE = 0x40 ;#define PAGE_EXECUTE_WRITECOPY 0x80 PAGE_EXECUTE_WRITECOPY = 0x80 ;#define PAGE_GUARD 0x100 PAGE_GUARD = 0x100 ;#define PAGE_NOCACHE 0x200 PAGE_NOCACHE = 0x200 ;#define PAGE_WRITECOMBINE 0x400 PAGE_WRITECOMBINE = 0x400 ;#define TH32CS_SNAPHEAPLIST 0x00000001 ;#define TH32CS_SNAPPROCESS 0x00000002 ;#define TH32CS_SNAPTHREAD 0x00000004 ;#define TH32CS_SNAPMODULE 0x00000008 ;#define TH32CS_SNAPMODULE32 0x00000010 ;#define TH32CS_SNAPALL (TH32CS_SNAPHEAPLIST | TH32CS_SNAPPROCESS | TH32CS_SNAPTHREAD | TH32CS_SNAPMODULE) ;#define TH32CS_INHERIT 0x80000000 TH32CS_SNAPHEAPLIST = 0x00000001 TH32CS_SNAPPROCESS = 0x00000002 TH32CS_SNAPTHREAD = 0x00000004 TH32CS_SNAPMODULE = 0x00000008 TH32CS_SNAPMODULE32 = 0x00000010 TH32CS_SNAPALL = TH32CS_SNAPHEAPLIST or TH32CS_SNAPPROCESS or TH32CS_SNAPTHREAD or TH32CS_SNAPMODULE TH32CS_INHERIT = 0x80000000 INVALID_HANDLE_VALUE = -1 ;#define MAX_MODULE_NAME32 255 ;#define MAX_PATH 260 MAX_MODULE_NAME32 = 255 MAX_PATH = 260 ;typedef struct tagMODULEENTRY32 { ; DWORD dwSize; ; DWORD th32ModuleID; ; DWORD th32ProcessID; ; DWORD GlblcntUsage; ; DWORD ProccntUsage; ; BYTE* modBaseAddr; ; DWORD modBaseSize; ; HMODULE hModule; ; TCHAR szModule[MAX_MODULE_NAME32 + 1]; ; TCHAR szExePath[MAX_PATH]; ;} MODULEENTRY32, ;*PMODULEENTRY32; struct MODULEENTRY32 dwSize dd ? th32ModuleID dd ? th32ProcessID dd ? GlblcntUsage dd ? ProccntUsage dd ? modBaseAddr dd ? modBaseSize dd ? hModule dd ? szModule db (MAX_MODULE_NAME32 + 1) dup (?) szExePath db MAX_PATH dup (?) ends proc HookImport szModule, szImpDll, ImpFunc, ImpFuncIsOrdinal, HookProc local BaseAddr:DWORD push [szModule] call FindModule cmp eax, 0 jz .fail mov [BaseAddr], eax push eax call VerifyPEfromMZ cmp eax, 0 jz .fail2 push [ImpFuncIsOrdinal] push [ImpFunc] push [szImpDll] push [BaseAddr] push eax call FindImports cmp eax, 0 jz .fail3 local HookAddr:DWORD, OldAddr:DWORD, OldProtect:DWORD, JunkProtect:DWORD mov [HookAddr], eax push ebx lea ebx, [OldProtect] push ebx push PAGE_READWRITE push 4 push eax call near [VirtualProtect] cmp eax, 0 jz .fail4 mov eax, [HookAddr] push DWORD [eax] pop DWORD [OldAddr] mov ebx, [HookProc] mov [eax], ebx lea ebx, [JunkProtect] push ebx lea ebx, [OldProtect] push ebx push 4 push eax call [VirtualProtect] mov eax, [OldAddr] pop ebx ret .fail4: pop ebx .fail3: .fail2: .fail: xor eax, eax ret endp proc FindImports PEaddr, BaseAddr, szModual, ImportName, IsOrd push esi push edi push ebx push edx mov esi, [PEaddr] mov esi, [esi + IMAGE_NT_HEADERS32.OptionalHeader\ + IMAGE_OPTIONAL_HEADER32.DataDirectory\ + (sizeof.IMAGE_DATA_DIRECTORY * 1)\ + IMAGE_DATA_DIRECTORY.VirtualAddress] add esi, [BaseAddr] local ImportBaseAddr:DWORD mov [ImportBaseAddr], esi .while0: xor eax, eax or eax, [esi + IMAGE_IMPORT_DESCRIPTOR.OriginalFirstThunk] or eax, [esi + IMAGE_IMPORT_DESCRIPTOR.TimeDateStamp] or eax, [esi + IMAGE_IMPORT_DESCRIPTOR.ForwarderChain] or eax, [esi + IMAGE_IMPORT_DESCRIPTOR.Name] or eax, [esi + IMAGE_IMPORT_DESCRIPTOR.FirstThunk] cmp eax, 0 jz .fail push MAX_MODULE_NAME32 push [szModual] mov eax, [esi + IMAGE_IMPORT_DESCRIPTOR.Name] add eax, [BaseAddr] push eax call stricmp cmp eax, 0 jnz .next0 mov edi, [esi + IMAGE_IMPORT_DESCRIPTOR.OriginalFirstThunk] cmp edi, 0 jz .fail mov ebx, [esi + IMAGE_IMPORT_DESCRIPTOR.FirstThunk] add edi, [BaseAddr] .while1: ;while edi != 0 test dword [edi], IMAGE_ORDINAL_FLAG32 jnz .importByOrdinal cmp [IsOrd], 0 jz .next1 mov eax, [edi] add eax, [BaseAddr] add eax, IMAGE_IMPORT_BY_NAME.Name push MAX_MODULE_NAME32 push [ImportName] push eax call stricmp cmp eax, 0 jz .fin jmp .next1 .importByOrdinal: cmp [IsOrd], 0 jnz .next1 mov edx, [ImportName] mov eax, [edi] and eax, 0xFFFF cmp eax, [edx] jz .fin .next1: add edi, 4 add ebx, 4 cmp dword [edi], 0 jnz .while1 .next0: add esi, sizeof.IMAGE_IMPORT_DESCRIPTOR jmp .while0 ;db 10 dup 0x90 .fin: mov eax, ebx add eax, [BaseAddr] pop edx pop ebx pop edi pop esi ret .fail: xor eax, eax pop edx pop ebx pop edi pop esi ret endp proc VerifyPEfromMZ MZaddr mov eax, [MZaddr] cmp word [eax + IMAGE_DOS_HEADER.e_magic], IMAGE_DOS_SIGNATURE jnz .fail add eax, [eax + IMAGE_DOS_HEADER.e_lfanew] cmp dword [eax + IMAGE_NT_HEADERS32.Signature], IMAGE_NT_SIGNATURE jnz .fail ret .fail: pop ebx xor eax, eax ret endp proc FindModule wszModuleNamePtr push ebx push ecx push edx push 0 push TH32CS_SNAPMODULE call [CreateToolhelp32Snapshot] cmp eax, INVALID_HANDLE_VALUE jz .fail local hSnapshot:DWORD, ModEntry:MODULEENTRY32 mov [hSnapshot], eax mov [ModEntry.dwSize], sizeof.MODULEENTRY32 lea edx, [ModEntry] push edx push eax call near [Module32First] cmp eax, 0 jz .fail cmp [wszModuleNamePtr], 0 jz .exittrue .checkmodname: push MAX_MODULE_NAME32 + 1 push [wszModuleNamePtr] lea eax, [ModEntry.szModule] push eax ;call strcmp call stricmp cmp eax, 0 jz .exittrue lea eax, [ModEntry] push eax push [hSnapshot] call near [Module32Next] cmp eax, 0 jz .fail jmp .checkmodname ;db 'hope your having fun looking at this!',0 .exittrue: push [hSnapshot] call [CloseHandle] mov eax, [ModEntry.modBaseAddr] pop edx pop ecx pop ebx ret .closeandfail: push [hSnapshot] call [CloseHandle] .fail: pop edx pop ecx pop ebx xor eax,eax ret endp proc stricmp dest, src, count push esi push edi push ebx push ecx push edx mov esi, [src] mov edi, [dest] mov ebx, [count] xor eax, eax xor ecx, ecx xor edx, edx .checkloop: cmp ecx, ebx jge .cleanup inc ecx mov al, byte [esi] mov dl, byte [edi] cmp dl, 0 jz .checkagain cmp al, 0 jz .srcisgreater cmp al, 'Z' jg @f cmp al, 'A' jl @f or al, 0x20 @@: cmp dl, 'Z' jg @f cmp dl, 'A' jl @f or dl, 0x20 @@: inc esi inc edi sub al, dl jz .checkloop jmp .cleanup .checkagain: cmp al, 0 jz .same mov eax, 1 jmp .cleanup .srcisgreater: mov eax, -1 jmp .cleanup .same: xor eax, eax .cleanup: pop edx pop ecx pop ebx pop edi pop esi ret endp i almost forgot you will need these funtions for everything to work correctly. Code: ;the follwoing imports are required for proper useage of myHookFinctions section '.itext' import data readable writeable library kernel32, 'KERNEL32.DLL' import kernel32,\ Module32First, 'Module32First',\ ;hook Module32Next, 'Module32Next',\ ; CreateToolhelp32Snapshot, 'CreateToolhelp32Snapshot',\ ;required CloseHandle, 'CloseHandle',\ ; VirtualProtect, 'VirtualProtect'\ ;imports \ ,GetModuleHandle, 'GetModuleHandleA' Admins or mods please delete any material which is against policy's or violation of copyrights. as i am not sure if anything here violates either. Last edited by FrozenKnight on 12 Sep 2007, 08:39; edited 1 time in total |
|||
28 Aug 2007, 17:01 |
|
FrozenKnight 05 Sep 2007, 08:19
i just realized i never gave you an example of how to use the files i provided above.
heres the test file i gave (though they can be used in any pe file i used them in a DLL used to hook a coupple of functions in mIRC. just for test purposes.) Code: format PE GUI 4.0 DLL ;at 7000000h; on 'mirc.exe' entry DllMain include 'win32a.inc' include 'PE.inc' ;include 'HookDllStructs.inc' include 'HookDllData.inc' include 'HookDllImports.inc' include 'hookDllRes.inc' section '.code' code readable executable include 'HookDllFunctions.asm' ;HookImport szModule, szImpDll, ImpFunc, ImpFuncIsOrdinal, HookProc ;retuns old import addr in eax ;dllname db 'HookDll.dll',0 proc DllMain hinstDLL, fdwReason, lpvReserved mov eax, [fdwReason] cmp eax, DLL_PROCESS_ATTACH jz .attach cmp eax, DLL_PROCESS_DETACH jz .detach ret .attach: ;send push fsend push 0 push ordsend push szImpName push 0;szModname call HookImport mov [fOrgsend], eax cmp eax, 0 jz .failattach ;recv push frecv push 0 push ordrecv push szImpName push 0;szModname call HookImport mov [fOrgrecv], eax cmp eax, 0 jz .failattach .failattach: ret .detach: push [fOrgsend] push 0 push ordsend push szImpName push 0;szModname call HookImport ;recv push [fOrgrecv] push 0 push ordrecv push szImpName push 0;szModname call HookImport ret endp ;szModname db 'mirc.exe',0 szImpName db 'WSOCK32.dll',0 ordrecv dd 16;recv ordsend dd 19;send ;int send( ; SOCKET s, ; const char* buf, ; int len, ; int flags ;); proc fsend s, buf, len, flags push [flags] push [len] push [buf] push [s] call [fOrgsend] ret endp ;int recv( ; SOCKET s, ; char* buf, ; int len, ; int flags ;); proc frecv s, buf, len, flags push [flags] push [len] push [buf] push [s] call [fOrgrecv] ret endp section '.reloc' fixups data discardable While i believe with my experience now i could clean these files up quite a bit and even optimize them I haven ever taken the time to do so. Last edited by FrozenKnight on 12 Sep 2007, 08:43; edited 1 time in total |
|||
05 Sep 2007, 08:19 |
|
ManOfSteel 10 Sep 2007, 16:16
Detour example crashes on Win98SE too.
insert_detour call fails since the original MessageBoxA is shown and oMessageBoxA crashes the program. What should be modified to make it work? |
|||
10 Sep 2007, 16:16 |
|
< Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2024, Tomasz Grysztar. Also on GitHub, YouTube.
Website powered by rwasa.