注入DLL并使用CreateRemoteThread调用函数导致"已停止工作",会发生什么?

时间:2014-07-14 16:40:38

标签: c++ dll-injection createremotethread

我正在尝试在进程中注入DLL并在我的DLL中调用导出的函数。

使用该代码注入DLL:

HANDLE Proc;
char buf[50] = { 0 };
LPVOID RemoteString, LoadLibAddy;
if (!pID)
    return false;
Proc = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pID);
if (!Proc)
{
    sprintf_s(buf, "OpenProcess() failed: %d", GetLastError());
    printf(buf);
    return false;
}

LoadLibAddy = (LPVOID)GetProcAddress(GetModuleHandle(L"kernel32.dll"), "LoadLibraryA");
// Allocate space in the process for our DLL 
RemoteString = (LPVOID)VirtualAllocEx(Proc, NULL, strlen(DLL_NAME), MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE);
// Write the string name of our DLL in the memory allocated 
WriteProcessMemory(Proc, (LPVOID)RemoteString, DLL_NAME, strlen(DLL_NAME), NULL);
// Load our DLL 
HANDLE hThread = CreateRemoteThread(Proc, NULL, 0, (LPTHREAD_START_ROUTINE)LoadLibAddy, (LPVOID)RemoteString, NULL, NULL);

我的DLL模块创建正常,就像您在Process Hacker(BootstrapDLL.exe)的图像中看到的那样:

enter image description here

我的导出功能也可以,就像您在Process Hacker(ImplantDotNetAssembly)上导出的功能列表中看到的那样:

enter image description here

我认为,问题发生在偏移计算上,以获取" ImplantDotNetAssembly"的地址,因为上面的所有内容都没问题,当我进行计算时,我得到"的地址。 ImplantDotNetAssembly",但当我再次调用CreateRemoteThread来调用它时,窗口"已停止工作......"显示窗口并停止进程。发生了什么事?

以下是偏移计算的代码:

DWORD_PTR hBootstrap = GetRemoteModuleHandle(ProcId, L"BootstrapDLL.exe");
DWORD_PTR offset = GetFunctionOffset(L"C:\\Users\\Acaz\\Documents\\Visual Studio 2013\\Projects\\Contoso\\Debug\\BootstrapDLL.exe", "ImplantDotNetAssembly");
DWORD_PTR fnImplant = hBootstrap + offset;

HANDLE hThread2 = CreateRemoteThread(Proc, NULL, 0, (LPTHREAD_START_ROUTINE)fnImplant, NULL, 0, NULL);

以下是函数GetRemoteModuleHandle和GetFunctionOffset:

DWORD_PTR GetFunctionOffset(const wstring& library, const char* functionName)
{
    // load library into this process
    HMODULE hLoaded = LoadLibrary(library.c_str());

    // get address of function to invoke
    void* lpInject = GetProcAddress(hLoaded, functionName);

    // compute the distance between the base address and the function to invoke
    DWORD_PTR offset = (DWORD_PTR)lpInject - (DWORD_PTR)hLoaded;

    // unload library from this process
    FreeLibrary(hLoaded);

    // return the offset to the function
    return offset;
}

DWORD_PTR GetRemoteModuleHandle(const int processId, const wchar_t* moduleName)
{
    MODULEENTRY32 me32;
    HANDLE hSnapshot = INVALID_HANDLE_VALUE;

    // get snapshot of all modules in the remote process 
    me32.dwSize = sizeof(MODULEENTRY32);
    hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, processId);

    // can we start looking?
    if (!Module32First(hSnapshot, &me32))
    {
        CloseHandle(hSnapshot);
        return 0;
    }

    // enumerate all modules till we find the one we are looking for or until every one of them is checked
    while (wcscmp(me32.szModule, moduleName) != 0 && Module32Next(hSnapshot, &me32));

    // close the handle
    CloseHandle(hSnapshot);

    // check if module handle was found and return it
    if (wcscmp(me32.szModule, moduleName) == 0)
        return (DWORD_PTR)me32.modBaseAddr;

    return 0;
}

如果有人知道发生了什么,我将非常感激!

我甚至无法调试"已停止工作。"错误。当我按下窗口上的DEBUG按钮时,错误再次抛出,一切都停止。

谢谢。

1 个答案:

答案 0 :(得分:0)

永远不要注入托管程序集。如果由于某种原因必须将代码注入另一个进程,请使用带有NO C库或STATIC C库的本机代码。