代码不多,但是我先运行记事本,然后运行我的代码,提示错误说 “XXXX地址不能为Written”,我的代码哪里错了?我是参考了 “” 这个文章啊//记事本为目标进程。
static DWORD WINAPI MyFunc (LPVOID pData)
{
//do something
//...
//pData输入项可以是任何类型值
//这里我们会传入一个DWORD的值做示例,并且简单返回
printf("hello\n");
return *(DWORD*)pData;
}
static void AfterMyFunc (void) {
printf("after test\n");
}int main(){/** declare var **/
HWND hStart;
DWORD PID, TID;
char szBuffer[10];
void *pDataRemote;
HANDLE hProcess;
DWORD cbCodeSize;
PDWORD pCodeRemote;
HANDLE hThread;
DWORD h;
/** end declare **/
printf("Enter main..\n");hStart = FindWindow (TEXT("NotePad"),NULL); TID = GetWindowThreadProcessId (hStart, &PID);hProcess = OpenProcess(PROCESS_ALL_ACCESS,FALSE,PID); *(DWORD*)szBuffer=1000;//for test
pDataRemote =(char*) VirtualAllocEx( hProcess, 0, sizeof(szBuffer),
  MEM_COMMIT,PAGE_READWRITE );//步骤5:写内容到目标进程中分配的变量空间
WriteProcessMemory( hProcess, pDataRemote, szBuffer,(sizeof(szBuffer)),NULL);//步骤6:在目标进程中分配代码地址空间
//计算代码大小
cbCodeSize=((LPBYTE) AfterMyFunc - (LPBYTE) MyFunc);
//分配代码地址空间
pCodeRemote = (PDWORD) VirtualAllocEx( hProcess, 0, cbCodeSize, MEM_COMMIT,PAGE_EXECUTE_READWRITE );//步骤7:写内容到目标进程中分配的代码地址空间
WriteProcessMemory( hProcess, pCodeRemote, &MyFunc, cbCodeSize, NULL);//步骤8:在目标进程中执行代码hThread = CreateRemoteThread(hProcess, NULL, 0,
(LPTHREAD_START_ROUTINE) pCodeRemote,
pDataRemote, 0 , NULL);if (hThread)
{
WaitForSingleObject( hThread, INFINITE );
GetExitCodeThread( hThread, &h );
//TRACE("run and return %d\n",h);
CloseHandle( hThread );
}
//释放空间
VirtualFreeEx( hProcess, pCodeRemote,
               cbCodeSize,MEM_RELEASE );//VirtualFreeEx( hProcess, pDataRemote,
  //             szBuffer,MEM_RELEASE );//关闭进程句柄
CloseHandle( hProcess );
return 0;
}
网上有文章说是VirtualAllocEx 这里分配内存的时候出错了,地址不能这样申请,但不知道为什么,应该怎样修改?? 多谢!

解决方案 »

  1.   

    文章网址: http://www.99inf.net/SoftwareDev/VC/27482.htm
      

  2.   

    思路本身就错了,可能写此文章的人对此法也不太清楚。建议你用LoadLibrary的方式来注入。
      

  3.   


    他的 PDWORD pCodeRemote = (PDWORD) VirtualAllocEx( hProcess, 0, cbCodeSize, MEM_COMMIT,PAGE_EXECUTE_READWRITE ); 也没有问题啊
      

  4.   

    release编译就好了
    debug下代码生成有些不同,大小计算有问题
    用loadlibray简单多了,否则你注入的函数里的地址都要重定位,因为是位于别的进程
      

  5.   

    我写了一个dll测试,执行release可以 detach,但是紧跟着出现一个错误 “0x00000000指令引用的是0x00000000内存,该内存不能为read.”(记事本也关闭了),然后才弹出执行的detach对话框。我的代码哪里有问题?BOOL APIENTRY DllMain( HANDLE hModule, DWORD  ul_reason_for_call, LPVOID lpReserved)
    {
    static TCHAR  processName[MAX_PATH]; switch(ul_reason_for_call)
    {
    case DLL_PROCESS_ATTACH:
    GetModuleFileName(0, processName, MAX_PATH);
    processName[MAX_PATH-1] = '\0'; OutputDebugString("#### enter DLL_PROCESS_ATTACH #### ");
    MessageBox(0, processName, "PROCESS_ATTACH",  MB_OK);

    OutputDebugString("before setPriority");
    SetPriorityClass(GetCurrentProcess(), IDLE_PRIORITY_CLASS);
    break;

    case DLL_PROCESS_DETACH:
    OutputDebugString("### Enter DLL_PROCESS_DETACH##");
    MessageBox(0, processName, "PROCESS_DETACH",  MB_OK);
    break;
    }
    return TRUE;
    }我调用的代码:int main(){/** declare var **/
    HWND hStart;
    DWORD PID, TID;
    char szBuffer[10];
    void *pDataRemote;
    HANDLE hProcess;
    DWORD cbCodeSize;
    PDWORD pCodeRemote;
    HANDLE hThread;
    DWORD h;
    HINSTANCE hModule;
    /** end declare **/
    printf("Enter main..\n");hStart = FindWindow (TEXT("NotePad"),NULL); TID = GetWindowThreadProcessId (hStart, &PID);hProcess = OpenProcess(PROCESS_ALL_ACCESS,FALSE,PID); *(DWORD*)szBuffer=1000;//for test
    pDataRemote =(char*) VirtualAllocEx( hProcess, 0, sizeof(szBuffer),
      MEM_COMMIT,PAGE_READWRITE );//步骤5:写内容到目标进程中分配的变量空间
    WriteProcessMemory( hProcess, pDataRemote, szBuffer,(sizeof(szBuffer)),NULL);//步骤6:在目标进程中分配代码地址空间
    //计算代码大小
    cbCodeSize=((LPBYTE) AfterMyFunc - (LPBYTE) MyFunc);
    //分配代码地址空间
    pCodeRemote = (PDWORD) VirtualAllocEx( hProcess, 0, cbCodeSize, MEM_COMMIT,PAGE_EXECUTE_READWRITE );//步骤7:写内容到目标进程中分配的代码地址空间
    WriteProcessMemory( hProcess, pCodeRemote, &MyFunc, cbCodeSize, NULL);//步骤8:在目标进程中执行代码
    hModule=LoadLibrary("f:/testinjectdll.dll");
    hThread = CreateRemoteThread(hProcess, NULL, 0,
    (LPTHREAD_START_ROUTINE )GetProcAddress(
                hModule, "LoadLibraryA"),
    pDataRemote, 0 , NULL);if (hThread)
    {
    WaitForSingleObject( hThread, INFINITE );
    GetExitCodeThread( hThread, &h );
    //TRACE("run and return %d\n",h);
    CloseHandle( hThread );
    }
    //释放空间
    hThread = CreateRemoteThread( hProcess, NULL, 0,
    (LPTHREAD_START_ROUTINE )GetProcAddress(
    hModule, "FreeLibrary"),
    (void*)h, 0, NULL );//关闭进程句柄
    CloseHandle( hProcess );
    return 0;
    }哪里写错了? 还有就是如果用这种dll的方式可以工作,那么我开始直接写函数的方式连Windows函数都不能调用,这种方式相比使用dll的存在有什么意义?
      

  6.   

    int main(){/** declare var **/
    HWND hStart;
    DWORD PID, TID;
    char szBuffer[10];
    char *pDataRemote;
    HANDLE hProcess;char*   pszLibFileName="f:/testinjectdll.dll";   
    HANDLE hThread;
    HANDLE hFreeThread;
    //HINSTANCE hModule;
    DWORD hLibModule;
    char*   pszLibFileRemote;
    int   cb;
    HMODULE hModuler;
     int   iReturnCode;
    /** end declare **/
    printf("Enter main..\n");hStart = FindWindow (TEXT("NotePad"),NULL); TID = GetWindowThreadProcessId (hStart, &PID);hProcess = OpenProcess(PROCESS_ALL_ACCESS,FALSE,PID); 
     cb   =(1+lstrlen(pszLibFileName));   
    pszLibFileRemote=(char*)VirtualAllocEx(hProcess,NULL,cb,MEM_COMMIT,   PAGE_READWRITE);   
    *(DWORD*)szBuffer=1000;//for test
    pDataRemote =(char*) VirtualAllocEx( hProcess, 0, sizeof(szBuffer),
                                              MEM_COMMIT,PAGE_READWRITE );
    iReturnCode=WriteProcessMemory(hProcess,pszLibFileRemote,(PVOID)pszLibFileName,cb,NULL);
    //步骤8:在目标进程中执行代码
    hModuler=LoadLibrary("kernel32.dll");
    //hModule=LoadLibrary("f:/testinjectdll.dll");
    hThread = CreateRemoteThread(hProcess, NULL, 0,
    (LPTHREAD_START_ROUTINE )GetProcAddress(
                hModuler, "LoadLibraryA"),
    pDataRemote, 0 , NULL);if (hThread)
    {
    WaitForSingleObject( hThread, INFINITE );
    GetExitCodeThread( hThread, &hLibModule );
    //TRACE("run and return %d\n",h);
    CloseHandle( hThread );
    }
    //释放空间
    hFreeThread = CreateRemoteThread( hProcess, NULL, 0,
    (LPTHREAD_START_ROUTINE )GetProcAddress(
    hModuler, "FreeLibrary"),
    (void*)hLibModule, 0, NULL );
    //VirtualFreeEx( hProcess, pCodeRemote,
      //             cbCodeSize,MEM_RELEASE );//VirtualFreeEx( hProcess, pDataRemote,
      //             szBuffer,MEM_RELEASE );//关闭进程句柄
    CloseHandle( hProcess );
    return 0;
    }
    执行后没反映了?
      

  7.   

    DLL中在DLL_PROCESS_ATTACH下面执行代码,执行完后return FALSE。
    方法不是因为有意义才存在的,对于没有意义的方法,大家可以不去用它。不过这种注入的方法还是有意义的,与DLL相比,其优势就是不用DLL。
      

  8.   

    static DWORD WINAPI MyFunc (LPVOID pData)
    {
      //do something
      //...
      //pData输入项可以是任何类型值
      //这里我们会传入一个DWORD的值做示例,并且简单返回
      printf("hello\n");
      return *(DWORD*)pData;
    }lz的这个思路是可行的。虽然不如LoadLibrary那么优雅。出错的原因在于"hello\n"这个字符串的地址是在本进程中,不是在notepad进程中。而且printf这个函数是运行库函数,在notepad进程里调用也没有Console,所以不合适。简单的改法是把printf这行代码去掉。测试远程线程是否正确地返回了1000这个整形值。应该是没问题的。这种复制整个函数代码到远程进程的方式,所有的字符串常量都需要主动申请内存copy过去,做好定位。用到的函数也都需要重定位。所以用LoadLibrary的方式要好得多。