[Question] Thread Injections Confused menu

User Tag List

Results 1 to 11 of 11
  1. #1
    adapa's Avatar Sergeant
    Reputation
    1
    Join Date
    Jul 2011
    Posts
    41
    Thanks G/R
    0/0
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)

    [Question] Thread Injections Confused

    Man, I am so sorry I have been posting a lot recently... but I have some questions.

    I have successfully injected my DLL into a new thread using createremotethread, and have rewritten and have gotten VEH working which does work on some functions for World of Warcraft. The problem is I cant seem to get VEH to work on ws2_32(before it is called)(for testing purposes). I believe that this is because I have to inject my DLL into WOW's main thread?

    My question has two parts.

    1) If I am making a new thread, how can my DLL act on WOW's main thread.

    And

    2) If question 1 is answered, when I do inject my DLL, why doesnt it inject into the main thread anyway? And how do I know which thread ws2_32 is called from? And should createremotethread me used for using VEH?

    -_- Lost and confused... Thanks.

    [Question] Thread Injections Confused
  2. #2
    Cypher's Avatar Kynox's Sister's Pimp
    Reputation
    1358
    Join Date
    Apr 2006
    Posts
    5,368
    Thanks G/R
    0/6
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Wat.

    Post your code and explain more clearly what you're trying to accomplish. I THINK I know what you're trying to do and why it's not working, but more information would be helpful...

  3. #3
    adapa's Avatar Sergeant
    Reputation
    1
    Join Date
    Jul 2011
    Posts
    41
    Thanks G/R
    0/0
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Originally Posted by Cypher View Post
    Wat.

    Post your code and explain more clearly what you're trying to accomplish. I THINK I know what you're trying to do and why it's not working, but more information would be helpful...
    Alright, you asked for it!

    0x6DB370 + start address will give you the address I am trying to break at, for me its: 0x00FFC370.
    (00FFC370 |> 8B45 08 MOV EAX,DWORD PTR SS:[EBP+8])

    I am trying to VEH this location because I believe it holds the location of the K value for when the game starts the scramble. Regardless, I want to VEH this location and spit out the registers, so I know where I have to read memory to gather the K value. When this is working, I can use it to BP at other location so I know what the registers hold, which will be really amazing. Anyway, I hope that is clear enough, here is my injector, and dll.

    INJECTOR
    Code:
    #include "stdafx.h"
    #include <windows.h> 
    #include <tlhelp32.h> 
    #include <shlwapi.h> 
    #include <conio.h> 
    #include <stdio.h> 
    
    #define WIN32_LEAN_AND_MEAN 
    #define CREATE_THREAD_ACCESS (PROCESS_CREATE_THREAD | PROCESS_QUERY_INFORMATION | PROCESS_VM_OPERATION | PROCESS_VM_WRITE | PROCESS_VM_READ
    
    BOOL CreateRemoteThreadInject(DWORD ID, const char * dll);
    
    DWORD GetProcessId(IN PCHAR szExeName);
    
    int main()
    
    {
        char dll[MAX_PATH];
    
       GetFullPathName("VEHBP.dll",MAX_PATH,dll,NULL); 
    
        DWORD ID = GetProcessId("Wow.exe");
        if (!CreateRemoteThreadInject(ID,dll))
        {
            printf("Injection failed!");
            Sleep(3000);
            exit(1);
            
    
        }
        else
        {
    
            Sleep(3000);
            exit(1);
        }
         return 0;
    }
    
    DWORD GetProcessId(IN PCHAR szExeName)
    
    {
        DWORD dwRet = 0;
        DWORD dwCount = 0;
    
        HANDLE hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
    
        if (hSnapshot != INVALID_HANDLE_VALUE)
        {
            PROCESSENTRY32 pe = {0};
            pe.dwSize = sizeof(PROCESSENTRY32);
    
            BOOL bRet = Process32First(hSnapshot, &pe);
            while (bRet)
            {
                if (!_stricmp(pe.szExeFile, szExeName))
                {
                    dwCount++;
                    dwRet = pe.th32ProcessID;
                }
                bRet = Process32Next(hSnapshot, &pe);
            }
    
            if (dwCount > 1)
                dwRet = 0xFFFFFFFF;
    
            CloseHandle(hSnapshot);
        }
    
        return dwRet;
    }
    
    BOOL CreateRemoteThreadInject(DWORD ID, const char * dll) 
    
    { 
       HANDLE Process;
    
       LPVOID Memory;
    
       LPVOID LoadLibrary; 
    
       if(!ID)
     {
           return false;
      }
     
       Process = OpenProcess(PROCESS_CREATE_THREAD|PROCESS_QUERY_INFORMATION|PROCESS_VM_READ|PROCESS_VM_WRITE|PROCESS_VM_OPERATION, FALSE, ID); 
     
       LoadLibrary = (LPVOID)GetProcAddress(GetModuleHandle("kernel32.dll"), "LoadLibraryA"); 
     
       Memory = (LPVOID)VirtualAllocEx(Process, NULL, strlen(dll)+1, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE); 
     
       WriteProcessMemory(Process, (LPVOID)Memory, dll, strlen(dll)+1, NULL); 
    
       CreateRemoteThread(Process, NULL, NULL, (LPTHREAD_START_ROUTINE)LoadLibrary, (LPVOID)Memory, NULL, NULL); 
     
       CloseHandle(Process);
    
       VirtualFreeEx(Process , (LPVOID)Memory , 0, MEM_RELEASE);
    
       return true;
    }
    DLL
    Code:
    #include <Windows.h>
    #include <TlHelp32.h>
    #include <stdio.h>
    
    const DWORD func_addr = 0x00FFC370;				//The address to breakpoint at
    const DWORD func_addr_offset = func_addr + 0x1;
    
    void print_parameters(PCONTEXT debug_context) {
        printf("EAX: %X EBX: %X ECX: %X EDX: %X\n",
            debug_context->Eax, debug_context->Ebx, debug_context->Ecx, debug_context->Edx);
        printf("ESP: %X EBP: %X\n",
            debug_context->Esp, debug_context->Ebp);
        printf("ESI: %X EDI: %X\n",
            debug_context->Esi, debug_context->Edi);
    }
    
    void __declspec(naked) change_text_stub(void) {
        __asm {
            MOV EAX,DWORD PTR SS:[EBP+8]					//this is what 0x00FFC370 holds
            jmp [func_addr_offset]			//this is +1 of 0x00FFC370
        }
    }
    
    LONG WINAPI ExceptionFilter(PEXCEPTION_POINTERS ExceptionInfo) {
        if(ExceptionInfo->ExceptionRecord->ExceptionCode == EXCEPTION_SINGLE_STEP) {
            if((DWORD)ExceptionInfo->ExceptionRecord->ExceptionAddress == func_addr) {
                PCONTEXT debug_context = ExceptionInfo->ContextRecord;
                printf("Breakpoint hit!\n");
                print_parameters(debug_context);
                debug_context->Eip = (DWORD)&change_text_stub;
                return EXCEPTION_CONTINUE_EXECUTION;
            }
        }
        return EXCEPTION_CONTINUE_SEARCH;
    }
    
    void set_breakpoints(void) {
        HANDLE hTool32 = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
        if(hTool32 != INVALID_HANDLE_VALUE) {
            THREADENTRY32 thread_entry32;
            thread_entry32.dwSize = sizeof(THREADENTRY32);
            FILETIME exit_time, kernel_time, user_time;
            FILETIME creation_time;
            FILETIME prev_creation_time;
            prev_creation_time.dwLowDateTime = 0xFFFFFFFF;
            prev_creation_time.dwHighDateTime = INT_MAX;
            HANDLE hMainThread = NULL;
            if(Thread32First(hTool32, &thread_entry32)) {
                do {
                    if(thread_entry32.dwSize >= FIELD_OFFSET(THREADENTRY32, th32OwnerProcessID) + sizeof(thread_entry32.th32OwnerProcessID)
                        && thread_entry32.th32OwnerProcessID == GetCurrentProcessId()
                        && thread_entry32.th32ThreadID != GetCurrentThreadId()) {
                            HANDLE hThread = OpenThread(THREAD_SET_CONTEXT | THREAD_GET_CONTEXT | THREAD_QUERY_INFORMATION,
                                FALSE, thread_entry32.th32ThreadID);
                            GetThreadTimes(hThread, &creation_time, &exit_time, &kernel_time, &user_time);
                            if(CompareFileTime(&creation_time, &prev_creation_time) == -1) {
                                memcpy(&prev_creation_time, &creation_time, sizeof(FILETIME));
                                if(hMainThread != NULL)
                                    CloseHandle(hMainThread);
                                hMainThread = hThread;
                            }
                            else
                                CloseHandle(hThread);
                    }
                    thread_entry32.dwSize = sizeof(THREADENTRY32);
                } while(Thread32Next(hTool32, &thread_entry32));
                AddVectoredExceptionHandler(1, ExceptionFilter);
                CONTEXT thread_context = {CONTEXT_DEBUG_REGISTERS};
                thread_context.Dr0 = func_addr;
                thread_context.Dr7 = (1 << 0);
                SetThreadContext(hMainThread, &thread_context);
                CloseHandle(hMainThread);
            }
            CloseHandle(hTool32);
        }
    }
    
    int APIENTRY DllMain(HMODULE hModule, DWORD reason, LPVOID reserved) {
        if(reason == DLL_PROCESS_ATTACH) {
            DisableThreadLibraryCalls(hModule);
            if(AllocConsole()) {
                freopen("CONOUT$", "w", stdout);
                SetConsoleTitle(L"Console");
                SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE);
                printf("DLL loaded.\n");
            }
            set_breakpoints();
        }
        return TRUE;
    }

  4. #4
    TOM_RUS's Avatar Legendary
    Reputation
    914
    Join Date
    May 2008
    Posts
    699
    Thanks G/R
    0/52
    Trade Feedback
    0 (0%)
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)
    You can just read the key from an address without any breakpoints.
    Code:
    ClientConnection * __cdecl ClientServices::Connection()
    {
        return dword_D7DA5C;
    }
    
    BYTE *__thiscall ClientServices::GetSessionKey(ClientConnection *this)
    {
        return this->SessionKey;
    }
    Last edited by TOM_RUS; 08-18-2011 at 02:37 AM.

  5. #5
    adapa's Avatar Sergeant
    Reputation
    1
    Join Date
    Jul 2011
    Posts
    41
    Thanks G/R
    0/0
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Originally Posted by TOM_RUS View Post
    You can just read the key from an address without any breakpoints.
    Code:
    ClientConnection * __cdecl ClientServices::Connection()
    {
        return dword_D7DA5C;
    }
    
    BYTE *__thiscall ClientServices::GetSessionKey(ClientConnection *this)
    {
        return this->SessionKey;
    }
    I see but since we can't breakpoint WOW(without assertion and crash) and whereas future games will have tight anti-debugging... when you have assembly like this:

    Code:
    .text:00ADC350 Make_RC4_Chart:                         ; CODE XREF: SARC4PrepareKey+29j
    .text:00ADC350                 mov     [eax+esi], al
    .text:00ADC353                 inc     eax
    .text:00ADC354                 cmp     eax, 100h
    .text:00ADC359                 jb      short Make_RC4_Chart
    .text:00ADC35B                 xor     dl, dl
    .text:00ADC35D                 mov     [esi+100h], cl
    .text:00ADC363                 mov     [esi+101h], cl
    .text:00ADC369                 xor     bl, bl
    .text:00ADC36B                 jmp     short loc_ADC370
    .text:00ADC36B ; ---------------------------------------------------------------------------
    .text:00ADC36D                 align 10h
    .text:00ADC370
    .text:00ADC370 loc_ADC370:                             ; CODE XREF: SARC4PrepareKey+3Bj
    .text:00ADC370                                         ; SARC4PrepareKey+78j
    .text:00ADC370                 mov     eax, [ebp+arg_0]
    .text:00ADC373                 movzx   edi, dl
    .text:00ADC376                 movzx   edx, byte ptr [edi+eax]
    .text:00ADC37A                 add     dl, [ecx+esi]
    .text:00ADC37D                 inc     ecx
    .text:00ADC37E                 add     bl, dl
    .text:00ADC380                 movzx   edx, byte ptr [ecx+esi-1]
    .text:00ADC385                 movzx   eax, bl
    .text:00ADC388                 add     eax, esi
    .text:00ADC38A                 mov     byte ptr [ebp+arg_8+3], dl
    .text:00ADC38D                 movzx   edx, byte ptr [eax]
    .text:00ADC390                 mov     [ecx+esi-1], dl
    .text:00ADC394                 movzx   edx, byte ptr [ebp+arg_8+3]
    .text:00ADC398                 mov     [eax], dl
    .text:00ADC39A                 xor     edx, edx
    .text:00ADC39C                 lea     eax, [edi+1]
    .text:00ADC39F                 div     [ebp+arg_4]
    .text:00ADC3A2                 cmp     ecx, 100h
    .text:00ADC3A8                 jb      short loc_ADC370
    .text:00ADC3AA                 pop     edi
    .text:00ADC3AB                 pop     esi
    .text:00ADC3AC                 pop     ebx
    .text:00ADC3AD                 pop     ebp
    .text:00ADC3AE                 retn    0Ch
    .text:00ADC3AE SARC4PrepareKey endp
    You don't know what registers hold what because you cant breakpoint the application(because of anti-debugging), so using VEH solves this because AFAIK, it bypasses any ANTI-Debugging methods and spits out the registers... making it so you know where to locate certain values...

    Right, or am I wrong in how I am going about this?

  6. #6
    Cypher's Avatar Kynox's Sister's Pimp
    Reputation
    1358
    Join Date
    Apr 2006
    Posts
    5,368
    Thanks G/R
    0/6
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    You're complaining it's not working but you're not checking the return values of the APIs you use. Maybe some error handling is in order? Come on man, debugging basics 101...

  7. #7
    adapa's Avatar Sergeant
    Reputation
    1
    Join Date
    Jul 2011
    Posts
    41
    Thanks G/R
    0/0
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Originally Posted by Cypher View Post
    You're complaining it's not working but you're not checking the return values of the APIs you use. Maybe some error handling is in order? Come on man, debugging basics 101...
    AHHHHH, I figured out why its not working, its because WOW's Battle.net.dll is removing my breakpoints on login. Is there anyway to apply my breakpoints after Battle.net.dll does its thing?

    The question is now... I thought VEH was suppose to bypass Battle.Net.Dll... So what gives?

    edit:

    I guess I just have to hook memory locations to get what I want. :-(

    edit 2:

    alright, well it seems like I could prob just do this:
    Code:
    .text:004D5E5C                 call    ClientServices__Connection
    Code:
    .text:004CC780 ClientServices__Connection proc near    ; CODE XREF: start+69Dp
    .text:004CC780                                         ; start+6A6p ...
    .text:004CC780                 mov     eax, dword_D7DA5C
    .text:004CC785                 retn
    .text:004CC785 ClientServices__Connection endp
    Code:
    .text:004D5E61                 mov     ecx, eax
    Code:
    .text:004D5E63                 call    ClientServices__GetSessionKey
    Code:
    .text:00485A90 ClientServices__GetSessionKey proc near ; CODE XREF: sub_4D5E20+43p
    .text:00485A90                                         ; sub_9CF7C0+5Fp ...
    .text:00485A90                 lea     eax, [ecx+508h]
    .text:00485A96                 retn
    .text:00485A96 ClientServices__GetSessionKey endp
    D7DA5C + 508h. Right?
    Last edited by adapa; 08-18-2011 at 03:44 PM.

  8. #8
    JuJuBoSc's Avatar Banned for scamming CoreCoins Purchaser
    Reputation
    1019
    Join Date
    May 2007
    Posts
    922
    Thanks G/R
    1/3
    Trade Feedback
    1 (100%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Yeah that's how I always get that session key since many month

  9. #9
    sitnspinlock's Avatar Elite User CoreCoins Purchaser
    Reputation
    398
    Join Date
    Sep 2010
    Posts
    439
    Thanks G/R
    0/1
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    The battle.net dll does not remove your breakpoints I am not sure where you gather that information from. It just throws rogue exceptions which is part of the anti-debug schematic. I can't really follow any of what you are saying cause it really makes no sense.. =/

    From what I gather you are trying to get a thread context dump with a Vectored Exception Handler because you cannot with a traditional user-mode debugger cause you have not made any bypass, correct?

    Lets say that is the case, and for examples sake lets take the route of a software break. Write 0xCC to the first byte of the instruction, know the original byte, and save it in a buffer of course. When the EXCEPTION_BREAKPOINT is reached (check the instruction pointer), there is no need to retrieve the thread context as its already given to you through a pointer in the VEH model.

    Dump the context, restore the original byte, and return with the EXCEPTION_CONTINUE_EXECUTION constant.

  10. #10
    Cypher's Avatar Kynox's Sister's Pimp
    Reputation
    1358
    Join Date
    Apr 2006
    Posts
    5,368
    Thanks G/R
    0/6
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Originally Posted by everdox View Post
    The battle.net dll does not remove your breakpoints I am not sure where you gather that information from. It just throws rogue exceptions which is part of the anti-debug schematic. I can't really follow any of what you are saying cause it really makes no sense.. =/

    From what I gather you are trying to get a thread context dump with a Vectored Exception Handler because you cannot with a traditional user-mode debugger cause you have not made any bypass, correct?

    Lets say that is the case, and for examples sake lets take the route of a software break. Write 0xCC to the first byte of the instruction, know the original byte, and save it in a buffer of course. When the EXCEPTION_BREAKPOINT is reached (check the instruction pointer), there is no need to retrieve the thread context as its already given to you through a pointer in the VEH model.

    Dump the context, restore the original byte, and return with the EXCEPTION_CONTINUE_EXECUTION constant.
    I haven't looked at it since it was first implemented a long time ago, but doesn't Battle.net use HWBPs that are necessary in order for control flow to be correct (to stop you from just overwriting them with your own hooks)?

  11. #11
    adapa's Avatar Sergeant
    Reputation
    1
    Join Date
    Jul 2011
    Posts
    41
    Thanks G/R
    0/0
    Trade Feedback
    0 (0%)
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    everdox and Cypher... I really appreciate the help! You guys have been more than helpful!
    Last edited by adapa; 08-20-2011 at 09:27 PM.

Similar Threads

  1. [Question]DLL Injection
    By hestas in forum WoW Memory Editing
    Replies: 12
    Last Post: 11-18-2009, 02:26 PM
  2. Warcraft III questions thread
    By ChildeRoland in forum Gaming Chat
    Replies: 4
    Last Post: 06-18-2009, 05:32 PM
  3. [Question] Tauren - NE.. Confused
    By bearny in forum WoW ME Questions and Requests
    Replies: 0
    Last Post: 07-03-2008, 01:35 PM
  4. My Question Thread
    By L'Lawliet in forum World of Warcraft Emulator Servers
    Replies: 17
    Last Post: 12-17-2007, 09:44 AM
  5. Cheezeit's Help/Questions thread
    By Cheezeit117 in forum World of Warcraft General
    Replies: 37
    Last Post: 08-14-2007, 10:04 PM
All times are GMT -5. The time now is 04:09 AM. Powered by vBulletin® Version 4.2.3
Copyright © 2025 vBulletin Solutions, Inc. All rights reserved. User Alert System provided by Advanced User Tagging (Pro) - vBulletin Mods & Addons Copyright © 2025 DragonByte Technologies Ltd.
Google Authenticator verification provided by Two-Factor Authentication (Free) - vBulletin Mods & Addons Copyright © 2025 DragonByte Technologies Ltd.
Digital Point modules: Sphinx-based search