2015-01-01 2 views
-1

Так что я вставляю DLL в программу. Я могу проверить, что DLL инъецируется с помощью Process Explorer. После инъекции я перебираю все модули из процесса, сравнивая имена и возвращаю инъецированную dll как HMODULE.Введенные DLL не верны HMODULE

Затем я GetProcAddress() этот HMODULE, чтобы найти внешнюю функцию внутри него, но по какой-то причине это не работает должным образом.

HMODULE dllAddress = getModuleAddressFromProc(pid, "NewDll.dll"); 
externCreateThread createThread = (externCreateThread)GetProcAddress(dllAddress, "createThread"); 

Когда я точка перелома и проверить dllAddress он говорит:

enter image description here

Когда я использую LoadLibrary для загрузки DLL в моей текущей программе и использовать его в качестве HMODULE, он работает.

HMODULE dllAddress = LoadLibrary(L"C:\\NewDll.dll"); 
externCreateThread createThread = (externCreateThread)GetProcAddress(dllAddress, "createThread"); 

Breakpointing проверить dllAddress:

enter image description here

Возвращенный HMODULE из списка HMODULES не то же самое, как HMODULE от LoadLibrary. Хотя адрес указателя тот же.

Список всех модулей процесса выполняется с помощью кода Microsoft. Я немного изменил его для работы со строковым сравнением, но это не влияет на тип HMODULE.

HMODULE getModuleAddressFromProc(DWORD pid, string moduleName) { 
    HMODULE hMods[1024]; 
    DWORD cbNeeded; 
    HMODULE output; 
    unsigned int i; 
    HANDLE newHandle = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, pid); 
    if (EnumProcessModules(newHandle, hMods, sizeof(hMods), &cbNeeded)) { 
     for (i = 0; i < (cbNeeded/sizeof(HMODULE)); i++) { 
      TCHAR szModName[MAX_PATH]; 
      if (GetModuleFileNameEx(newHandle, hMods[i], szModName, sizeof(szModName)/sizeof(TCHAR))) { 
       string s2 = charToString(szModName); 
       if (s2.find(moduleName) != string::npos) { 
        output = hMods[i]; 
        break; 
       } 
      } 
     } 
    } 
    return output; 
} 

ответ

0

Вы можете получить HMODULE из DLL в загруженном в другом процессе, но вы не можете использовать его из процесса, чтобы получить адрес процедуры этого HMODULE.

Это связано с тем, что каждый процесс в Windows имеет собственное пространство памяти. Поэтому значение HMODULE одной и той же DLL, загружаемой в разные процессы, почти всегда различается каждый раз. Поэтому, как только вы получили HMODULE своей DLL в рамках другого процесса и позвоните по телефону GetProcAddress(..), Windows будет выглядеть в памяти вашего приложения, а не внутри другого процесса. Поскольку HMODULE недействителен в вашей заявке, GetProcAddress(..) завершится с ошибкой.

Если вы хотите вызвать функции в контексте другого процесса, вы должны использовать какой-то interprocess communication. Для этого вам нужно иметь поток, выполняющийся в рамках другого процесса, для обработки этих IPC (что, как мне кажется, должно выполняться createThread).

Для достижения этой цели вы можете использовать функцию DllMain(..) вашего нагнетаемой DLL выполнить некоторый код (например, вызов функции createThread(..)):

BOOL WINAPI DllMain(HINSTANCE hinstDLL, // handle to DLL module 
        DWORD fdwReason,  // reason for calling function 
        LPVOID lpReserved) // reserved 
{ 

    switch(fdwReason) 
    { 
     case DLL_PROCESS_ATTACH: 
     createThread(..); 
     break; 

     case DLL_THREAD_ATTACH: 
     // Do thread-specific initialization. 
     break; 

     case DLL_THREAD_DETACH: 
     // Do thread-specific cleanup. 
     break; 

     case DLL_PROCESS_DETACH: 
     // Perform any necessary cleanup. 
     break; 
    } 

    return (TRUE); 
} 
+0

Да, я попробовал это изначально, но, похоже, вы не можете создать поток из DllMain, поскольку он разбивает программу. Поэтому я пошел искать метод вокруг него. – user616396

+0

Вы можете создавать потоки из 'DllMain', как указано MSDN (и сделано мной несколько раз). Единственное различие заключается в том, что поток начинается не сразу, а после загрузки DLL. Вы пробовали очень простой поток для тестирования (например, некоторое время (1) с MessageBox/MessageBeep каждую секунду)? –

+0

Я пробовал бесконечный цикл while из DllMain, программа, которая запустила DLL, зависает до тех пор, пока цикл while не будет экранирован. Я попробовал CreatThread() и убил программу. Редактировать: DllMain запускается во время блокировки загрузчика. – user616396

Смежные вопросы