BOOL CConcreteWGProduct::CreateRemoteThread(DWORD dwPID,LPTHREAD_START_ROUTINE pThreadFun,LPVOID pThreadParam,DWORD dwParamSize){HANDLE hPro=NULL;if (NULL==m_hRemoteThread){//開啟目標進程hPro=OpenProcess(PROCESS_ALL_ACCESS,FALSE,dwPID);if (NULL==hPro)return FALSE;//在目標進程內分配存放線程函數起始地址的記憶體#ifdef _DEBUGBYTE* pF=(BYTE*)pThreadFun;//DEBUG模式下編譯器會有一個函數跳轉表if (*pF==0xe9)//jmp的機器碼為0xE9{pF++;int x=*(int*)pF;//計算jmp後面的跳轉地址pF+=x;//當前地址+位移地址pF+=4;//此處內容為CC CC CC CC再加真實函數機器碼,所以要跳過這4個0xCC,}pThreadFun=(LPTHREAD_START_ROUTINE)pF;#endif//寫入函數機器碼DWORD dwFuncSize=GetFuncByteSize(pThreadFun);LPVOID pThreadFunAdd=VirtualAllocEx(hPro,NULL,dwFuncSize,MEM_COMMIT,PAGE_READWRITE);if (NULL!=pThreadFunAdd){if (!WriteProcessMemory(hPro,pThreadFunAdd,(LPCVOID)pThreadFun,dwFuncSize,NULL)){AfxMessageBox(_T("注入線程失敗"));return FALSE;}}//在目標進程內分配線程參數地址LPVOID pThreadParamAdd=VirtualAllocEx(hPro,NULL,dwParamSize,MEM_COMMIT,PAGE_READWRITE);//寫入參數機器碼if (NULL!=pThreadParamAdd){if (!WriteProcessMemory(hPro,pThreadParamAdd,(LPCVOID)pThreadParam,dwParamSize,NULL)){AfxMessageBox(_T("注入線程失敗"));return FALSE;}}m_hRemoteThread=::CreateRemoteThread(hPro,NULL,0,(LPTHREAD_START_ROUTINE)pThreadFunAdd,pThreadParam,CREATE_SUSPENDED,NULL);StartRemoteThread();if (NULL!=pThreadParamAdd)VirtualFreeEx(hPro,pThreadParamAdd,sizeof(DWORD),MEM_RELEASE);if (NULL!=pThreadFunAdd)VirtualFreeEx(hPro,pThreadFunAdd,sizeof(DWORD),MEM_RELEASE);if (NULL!=hPro)CloseHandle(hPro);return TRUE;}elsereturn FALSE;}