I'm Korean student.
Now this is my first question after signing up.
DWORD getProcessId() {
PROCESSENTRY32 process_infor;
process_infor.dwSize = sizeof(PROCESSENTRY32);
HANDLE snap_handle = CreateToolhelp32Snapshot(
TH32CS_SNAPALL, //스냅 단계
NULL //스냅할 pid
);
if (snap_handle != INVALID_HANDLE_VALUE) {
Process32First(snap_handle, &process_infor);
do {
wchar_t* temp = process_infor.szExeFile;
wstring ws(temp);
string name(ws.begin(), ws.end());
if (name == "notepad.exe") {
cout << name << " : " << process_infor.th32ProcessID << endl;
return process_infor.th32ProcessID;
}
} while (Process32Next(snap_handle, &process_infor));
}
CloseHandle(snap_handle);
return FALSE;
}
BOOL inject() {
HMODULE dll_handle;
HOOKPROC func;
HHOOK process_hook;
dll_handle = LoadLibrary(L"hello.dll");
func = (HOOKPROC) GetProcAddress(dll_handle, "injectSuccess");
cout << "handle : " << dll_handle << endl;
cout << "pid : " << getProcessId() << endl;
process_hook = SetWindowsHookEx(
WH_KEYBOARD,
func,
dll_handle,
getProcessId()
);
cout << "pook : " << process_hook << endl;
cout << "err : " << GetLastError() << endl;
FreeLibrary(dll_handle);
return FALSE;
}
There seems to be a problem with SetWindowsHookEx of the inject function in this case. The dll file loads well, and the injectSuccess function inside is well fetched. (I tried running it, but it worked)
And I wondered if the argument values of SetWindowsHookEx were entered incorrectly, so I compared them and checked them continuously, but I couldn't find any difference. So, I tried GetLastError() with the return value of SetWindowsHookEx below, but the return value is 0 and the error code is 87 ("the parameter is incorrect").
So I searched, but I can't speak English well and I'm a beginner, so I'm not sure.
According to the SetWindowsHookExW:
dwThreadId
A handle to the DLL containing the hook procedure pointed to by the lpfn parameter. The hMod parameter must be set to NULL if the dwThreadId parameter specifies a thread created by the current process and if the hook procedure is within the code associated with the current process.
So what SetWindowsHookExW needs is the thread ID, and you pass in the process ID of notepad.exe, so the parameter is wrong.
I creat a sample and test the following code:
BOOL inject() {
HMODULE dll_handle;
HOOKPROC func;
HHOOK process_hook;
dll_handle = LoadLibrary(L"hello.dll");
if (dll_handle) func = (HOOKPROC)GetProcAddress(dll_handle, "injectSuccess");
else return FALSE;
cout << "handle : " << dll_handle << endl;
cout << "pid : " << getProcessId() << endl;
HWND h = FindWindow(L"notepad", NULL);
DWORD pid;
threadID = GetWindowThreadProcessId(h, NULL);
cout << "threadID = " << threadID << endl;
process_hook = SetWindowsHookEx(
WH_KEYBOARD,
func,
dll_handle,
threadID
);
cout << "pook : " << process_hook << endl;
cout << "err : " << GetLastError() << endl;
if(dll_handle) FreeLibrary(dll_handle);
return FALSE;
}
This example worked for me, and you can see the difference between pid and threadID:
Edit
According to the document:
An application installs the hook procedure by specifying the
WH_KEYBOARD hook type and a pointer to the hook procedure in a call to
the SetWindowsHookEx function. This hook may be called in the context
of the thread that installed it. The call is made by sending a message
to the thread that installed the hook. Therefore, the thread that
installed the hook must have a message loop. So if you want to run
this func, you need to add a message loop.
You can refer to the following code:
int main()
{
inject();
MSG msg;
while (GetMessageW(&msg, NULL, 0, 0))
{
TranslateMessage(&msg);
DispatchMessageW(&msg);
}
}
When you press the button, the message box will pop up:
Because there are two messages for each key press and release, func is triggered twice each time.If you only want to trigger every time a button is pressed, you can modify the following code:
if ((0x80000000 & lParam) == 0)//This means that when the key is pressed
{
MessageBox(NULL, L"Success (dll injection)", L"Window", MB_OK);
}
You can refer to KeyboardProc to view the messages for each value in lParam.
Related
My problem is that I can't get output from the command line using pipes.
My task: "Redirect the command input stream to cmd.exe | output the result of the cmd.exe command to the main process."
#include <iostream>
#include <windows.h>
using namespace std;
#define deffBuffSize 1024
int funSC() {
HANDLE writeToCL, readFromCL, writeToProcess, readFromProcess;
char lpCmdLine[] = "cmd.exe /k ipconfig";
STARTUPINFOA siA;
PROCESS_INFORMATION piApp;
SECURITY_ATTRIBUTES secAttr;
ZeroMemory(&secAttr, sizeof(SECURITY_ATTRIBUTES));
ZeroMemory(&siA, sizeof(STARTUPINFOA));
secAttr.nLength = sizeof(SECURITY_ATTRIBUTES);
secAttr.lpSecurityDescriptor = NULL;
secAttr.bInheritHandle = TRUE;
if (CreatePipe(&readFromCL, &writeToProcess, &secAttr, 0) == 0) {
cout << "Create pipe error :: " << GetLastError() << endl;
return 1;
}
if (!SetHandleInformation(writeToProcess, HANDLE_FLAG_INHERIT, 0)) {
cout << "SetHandleInformation error :: " << GetLastError() << endl;
}
if (CreatePipe(&readFromProcess, &writeToCL, &secAttr, 0) == 0) {
cout << "Create pipe error :: " << GetLastError() << endl;
return 1;
}
if (!SetHandleInformation(readFromProcess, HANDLE_FLAG_INHERIT, 0)) {
cout << "SetHandleInformation error :: " << GetLastError() << endl;
}
siA.cb = sizeof(STARTUPINFOA);
siA.hStdInput = readFromProcess;
siA.hStdOutput = writeToProcess;
siA.hStdError = writeToProcess;
siA.dwFlags = STARTF_USESTDHANDLES;
if (CreateProcessA(NULL, lpCmdLine, NULL, NULL, TRUE, CREATE_NEW_CONSOLE, NULL, NULL, &siA, &piApp) == 0) {
cout << "CreateProcessA error :: " << GetLastError() << endl;
return 1;
}
else {
CloseHandle(readFromProcess);
CloseHandle(writeToProcess);
}
DWORD dRead = 0;
char chBuff[deffBuffSize];
bool bSuccess = FALSE;
memset(chBuff, '\0', deffBuffSize);
string outStd;
bSuccess = ReadFile(readFromCL, chBuff, deffBuffSize, &dRead, NULL);
cout << "bSuccess: " << bSuccess << endl;
cout << "GetLastError: " << GetLastError() << endl;
cout << "Message: " << chBuff;
//CloseHandle(writeToCL);
//CloseHandle(readFromCL);
CloseHandle(piApp.hProcess);
CloseHandle(piApp.hThread);
return 0;
}
int main() {
int result = 0;
result = funSC();
system("pause");
return result;
}
When I execute ReadFile (), I get the result.
ERROR_BROKEN_PIPE (109) - The pipe has been ended.
As I understand it, the pipe is closed at the end of the recording => Question: "Why should CreateProcess() execute "ipconfig" and not output it to an overridden output stream."
I read MSDN, tried to use the ready-made code (for understanding), but this did not lead to a positive result.
Help me please, I will be very happy if I understand how to solve this problem =)
PS: I cannot "close" the console window, because I must have a valid directory (For example: cd anyFolder) If I close the process, I will lose the directory to which the user passed.
This is how I tried to read from the pipe
for (;;) {
bSuccess = ReadFile(readFromCL, chBuff, deffBuffSize, &dRead, NULL);
if (!bSuccess || dRead == 0) {
break;
}
else {
cout << "Message: " << chBuff;
}
}
This endless loop didn't read anything.
P.S : This is the output of a running program, but it only outputs one line of the "ipconfig" command
First, the error of ERROR_BROKEN_PIPE(109) caused by the cmd.exe exit unexpectedly. According to the sample Creating a Child Process with Redirected Input and Output:
The parent process uses the opposite ends of these two pipes to write
to the child process's input and read from the child process's output.
As specified in the STARTUPINFO structure, these handles are also
inheritable. However, these handles must not be inherited. Therefore,
before creating the child process, the parent process uses the
SetHandleInformation function to ensure that the write handle for
the child process's standard input and the read handle for the child
process's standard output cannot be inherited.
You have set the other two handles to be un-inherited, so that cmd.exe exits without an available standard handle.
Set the pipe side of child process instead:
if (!SetHandleInformation(readFromCL, HANDLE_FLAG_INHERIT, 0)) {
cout << "SetHandleInformation error :: " << GetLastError() << endl;
}
if (!SetHandleInformation(writeToCL, HANDLE_FLAG_INHERIT, 0)) {
cout << "SetHandleInformation error :: " << GetLastError() << endl;
}
The issue of content size may because you need to wait for the output from cmd.exe. Add function like: Sleep(1000) before ReadFile Simply could solve it. Then, you could choose the most suitable method to synchronize the input and output of the two processes. Such as read in a for loop:
for (;;) {
memset(chBuff, '\0', deffBuffSize);
bSuccess = ReadFile(readFromCL, chBuff, deffBuffSize, &dRead, NULL);
if (!bSuccess || dRead == 0) {
break;
}
else {
cout << chBuff;
}
}
When I try to check if some process is using data execution protection (DEP) I get error 87 (INVALID_PARAMETER). I checked my code and it seems to be okay but unfortunately I still have the same error.
Code:
BOOL var = true;
DWORD dwPolicy;
HANDLE hProc = OpenProcess(PROCESS_QUERY_INFORMATION, false, 3624);
if (hProc == NULL) {
cout << "Can't open Process because of the error " << GetLastError() << endl;
}
if (GetProcessDEPPolicy(hProc, &dwPolicy, 0) != FALSE) {
if (dwPolicy == PROCESS_DEP_ENABLE) {
cout << "For try.exe process data execution prevention is enabled" << endl;
}
else if (dwPolicy == NULL) {
cout << "For try.exe process data execution prevention is disabled" << endl;
}
else {
cout << "Data is thrunked and we can't change DEP value in future" << endl;
}
}
else {
cout << "There was an error with discovering DEP in try.exe process because of "<<GetLastError() << endl;
}
After compiling and execution I get:
There was an error with discovering DEP in try.exe process because of 87
Looking at the documentation, the function GetProcessDEPPolicy is defined:
BOOL WINAPI GetProcessDEPPolicy(
_In_ HANDLE hProcess,
_Out_ LPDWORD lpFlags,
_Out_ PBOOL lpPermanent
);
Notice that the last argument is an out parameter and it's not optional, but you're passing 0 aka NULL. The call should be:
BOOL permanent = FALSE;
if (GetProcessDEPPolicy(hProc, &dwPolicy, &permanent) != FALSE) {
I have written DLL injector. I used CreateRemoteThread to inject my DLL to process and all was good.
Now i am trying inject DLL to process by undocumented function - NtCreateThreadEx. I have written injector but he is not working.
When i use 32 bit injector to inject 32 bit DLL to 32 bit process
all working good.
Problem is when i use 64 bit injector to inject 64 bit DLL to 64 bit process.
My DLL code:
#include <windows.h>
///Compilation with option -m64
extern "C" BOOL __stdcall DllMain(HMODULE hDLL, DWORD Reason, LPVOID Reserved)
{
MessageBox( NULL, "MESSAGE FROM 64 BIT DLL", "Lorem ipsum", MB_ICONINFORMATION | MB_OKCANCEL );
return 0;
}
My TestApp code
#include <iostream>
#include <windows.h>
int main()
{
std::cout << " Lorem IPSUM" << std::endl;
//HMODULE HDLL = LoadLibraryA("dll64.dll");
//std::cout << "Error: " << GetLastError() << std::endl;
while(1)
{
std::cout << "petla" << std::endl;
Sleep(5000);
}
return 0;
}
My injector code:
#include <iostream>
#include <string>
#include <windows.h>
/// 64 bit OS - Windows 7
///=====================
///* In this same user context ("User")
///TYPE OF(32/64 bits)
///INJECTOR===DLL===PROCESS===RESULT
/// 32 32 32 -SUCESS
/// 64 64 64 -FALIED (error: 1300)
//Handle to process,Address of'LoadLibraryA',see DllAdr
///TO DO
///* Inject DLL to process from normal user context ("User") to higher user context (Zarzadca)
///* Inject DLL to process from normal user context ("User") to other normal user context (User1)
HANDLE NtCreateThreadEx(HANDLE hProcess,LPVOID lpBaseAddress, LPVOID lpSpace);
int privileges();
int main()
{
int PIDOfProcess = 0;
std::string pathToDLL = "dll64.dll\0"; ///find DLL in local directory
DWORD PID = (DWORD)PIDOfProcess; ///PID
HANDLE HProcess = NULL; ///Handle to process
LPVOID LibAddr = NULL; ///Address of procedure 'LoadLibraryA'
LPVOID DllAdr = NULL; ///Address of memory in other process
HANDLE hThread = NULL; ///Handle to remote thread
int WirteStatus = 0; ///Status of writing to memory of other process
std::cout << "ptr size = " << sizeof(void *) << std::endl;
std::cout << "Get PID of process" << std::endl;
std::cin >> PIDOfProcess;
PID = (DWORD)PIDOfProcess;
///std::cout << "Get path to DLL" << std::endl;
///std::cin >> pathToDLL;
if( privileges() != 0 )
{
std::cout << "Cannot get the right privileges" << std::endl;
}
HProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, PID);
if(HProcess == NULL)
{
std::cout << "Could not find process" << std::endl;
std::cout << GetLastError() << std::endl;
system("pause");
return GetLastError();
}
DllAdr = (LPVOID)VirtualAllocEx(HProcess, NULL, pathToDLL.size() +1, MEM_RESERVE|MEM_COMMIT, PAGE_EXECUTE_READWRITE);
if(DllAdr == NULL)
{
std::cout <<"Can not allocate memory." << std::endl;
std::cout << GetLastError() << std::endl;
system("pause");
return GetLastError();
}
WirteStatus = WriteProcessMemory(HProcess, (LPVOID)DllAdr, pathToDLL.c_str() ,pathToDLL.size()+1, NULL);
if(WirteStatus == 0)
{
std::cout << "Could not write to process's address space" << std::endl;
std::cout << GetLastError() << std::endl;
system("pause");
return GetLastError();
}
LibAddr = (LPVOID)GetProcAddress(GetModuleHandle("kernel32.dll"), "LoadLibraryA");
if(LibAddr == NULL)
{
std::cout << "Unable to locate LoadLibraryA" << std::endl;
std::cout << GetLastError() << std::endl;
system("pause");
return GetLastError();
}
hThread = NtCreateThreadEx(HProcess,LibAddr,DllAdr);
///DWORD threadId = 0;
///hThread = CreateRemoteThread(HProcess, NULL, 0, (LPTHREAD_START_ROUTINE)LibAddr, DllAdr, 0, &threadId);
if(hThread == NULL)
{
std::cout << "Error: ";
std::cout << GetLastError() << std::endl;
system("pause");
return GetLastError();
}
system("pause");
}
HANDLE NtCreateThreadEx(HANDLE hProcess,LPVOID lpBaseAddress,LPVOID lpSpace)
{
///The prototype of NtCreateThreadEx from undocumented.ntinternals.com
typedef DWORD (WINAPI * functypeNtCreateThreadEx)(
PHANDLE ThreadHandle,
ACCESS_MASK DesiredAccess,
LPVOID ObjectAttributes,
HANDLE ProcessHandle,
LPTHREAD_START_ROUTINE lpStartAddress,
LPVOID lpParameter,
BOOL CreateSuspended,
DWORD dwStackSize,
DWORD Unknown1,
DWORD Unknown2,
LPVOID Unknown3
);
HANDLE hRemoteThread = NULL;
HMODULE hNtDllModule = NULL;
functypeNtCreateThreadEx funcNtCreateThreadEx = NULL;
//Get handle for ntdll which contains NtCreateThreadEx
hNtDllModule = GetModuleHandle( "ntdll.dll" );
if ( hNtDllModule == NULL )
{
std::cout << "Cannot get module ntdll.dll error: " << GetLastError() << std::endl;
return NULL;
}
funcNtCreateThreadEx = (functypeNtCreateThreadEx)GetProcAddress( hNtDllModule, "NtCreateThreadEx" );
if ( !funcNtCreateThreadEx )
{
std::cout << "Cannot get procedure address error: " << GetLastError() << std::endl;
return NULL;
}
funcNtCreateThreadEx( &hRemoteThread, /*GENERIC_ALL*/0x1FFFFF, NULL, hProcess, (LPTHREAD_START_ROUTINE)lpBaseAddress, lpSpace, FALSE, NULL, NULL, NULL, NULL );
std::cout << "Status NtCreateThreadEx " << GetLastError() << std::endl;
std::cout << "hRemoteThread: " << hRemoteThread << std::endl;
std::cout << "hNtDllModule: " << hNtDllModule << std::endl;
std::cout << "funcNtCreateThreadEx: " << funcNtCreateThreadEx << std::endl;
return hRemoteThread;
}
int privileges()
{
HANDLE Token;
TOKEN_PRIVILEGES tp;
if(OpenProcessToken( GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY,&Token)) ///It opens the access token associated with a process.
{
LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &tp.Privileges[0].Luid);///Function retrieves the locally unique identifier (LUID)
tp.PrivilegeCount = 1;
tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
if (AdjustTokenPrivileges(Token, false, &tp, sizeof(tp), NULL, NULL) != 0)///Function enables or disables privileges in the specified access token.
{
return 0; //OK
}
}
return 1;
}
When i use 64 bit injector to inject 64 bit DLL to 64 bit process, function NtCreateThreadEx return code of error 1300 and my DLL doesn't execute.
I use to compile on 64 bit architecture: g++ (tdm64-1) 5.1.0
I am working on Virus Windows 7 64 bit as normal user. Run as administrator doesn't help.
I dont know why it doesn't work, what i doing wrong.
PS: When i use 32 bit injector to inject 32 bit DLL to 32 bit process, function NtCreateThreadEx return code of error 1300 but my DLL execute.
In 32 bit version TestApp GetLastError return code 1114.
I use to compile on 32 bit architecture: g++ (tdm-2) 4.8.1
I include image
I based on:
http://www.p-programowanie.pl/cpp/dll-injection/ - Dll Injection (polish)
====
http://www.codeproject.com/Questions/369890/Ask-about-NtCreateThreadEx-in-Window-x
- Ask about NtCreateThreadEx in Window 7 x64!
=====
http://www.rohitab.com/discuss/topic/39535-code-injections-beginner-and-advanced/ Code Injections [beginner and advanced]
=====
http://securityxploded.com/ntcreatethreadex.php Remote Thread Execution in System Process using NtCreateThreadEx for Vista & Windows7
=====
http://cpp0x.pl/dokumentacja/WinAPI/Systemowe-kody-bledow-1300-1699/1470 Systemowe kody błędów (1300-1699) (polish)
Link to my topic on other forum (polish): http://forum.4programmers.net/C_i_C++/267735-dll_injection_w_windows_za_pomoca_nieudokumentowanej_funkcji_w_winapi?p=1234215#id1234215
My injector is working when i use him to inject DLL to other process in my user space (i am working as normal user)
but it is not working when
i am injecting to csrss.exe (or other system's process).
I get code of error 5 - Access Denied, when i run injector as Administrator i get code of error 0 (SUCCESS?) but my DLL not aborting process
( abort() - i try do BSoD).
I read about Session Separation and i think it is reason of my problem so i have one question: How i can hacking Windows :)
If it is imposibble can i inject DLL as normal user to proces in Administrator context (or other normal user's process) ?
I'm learning StackWalk API provided by "DbgHelp" in Windows 7. I wrote an exception filter that uses StackWalk64. The intention is to back trace at most 50 lines with function name and line number. "StackWalk64" iterates through each stack frame. The address(AddrPC) retrieved from Stack Frame is used in "SymGetSymFromAddr64" and "SymGetLineFromAddr64" to retrieve Symbol name and Line number respectively. But, though "SymGetSymFromAddr64" works successfully, "SymGetLineFromAddr64" fails. The Last Error returned is 487. How can the address work successfully for the former but not for the latter?
Am I missing something? Any Help?
LONG WINAPI TestStackWalker (EXCEPTION_POINTERS* lpFilter)
{
STACKFRAME64 st;
CONTEXT cc;
HANDLE hProcess = ::GetCurrentProcess();
HANDLE hThread = ::GetCurrentThread();
vector<IMAGEHLP_SYMBOL64> vectSymbs(50);
vector<IMAGEHLP_LINE64> vectLines(50);
if (!SymInitialize(hProcess, NULL, TRUE))
{
cout << "Issue with SymInitialize ! " << ::GetLastError() << endl;
return 1;
}
cc = *(lpFilter->ContextRecord);
printContext(cc);
::ZeroMemory(&st, sizeof(st));
st.AddrStack.Mode = AddrModeFlat;
st.AddrStack.Offset = cc.Esp;
st.AddrFrame.Mode = AddrModeFlat;
st.AddrFrame.Offset = cc.Ebp;
st.AddrPC.Mode = AddrModeFlat;
st.AddrPC.Offset = cc.Eip;
for (int i = 0; i < 50; i++)
{
if (!::StackWalk64(IMAGE_FILE_MACHINE_I386,
hProcess,
hThread,
&st,
&cc,
NULL,
SymFunctionTableAccess64,
SymGetModuleBase64,
NULL))
{
cout << "Issue with StackWalkFailed: " << ::GetLastError () <<endl;
return 1;
}
if (st.AddrReturn.Offset == st.AddrPC.Offset)
{
cout << "i think it's done!" << endl;
break;
}
if (st.AddrPC.Offset != 0)
{
vectSymbs[i].SizeOfStruct = sizeof(IMAGEHLP_SYMBOL64);
vectSymbs[i].MaxNameLength = 1024;
if (!SymGetSymFromAddr64 (hProcess, st.AddrPC.Offset, 0, &vectSymbs[i]))
{
cout << "Issue with Getting Symbol From Address " << ::GetLastError() << endl;
break;
}
SymSetOptions(SYMOPT_LOAD_LINES);
vectLines[i].SizeOfStruct = sizeof(IMAGEHLP_LINE64);
if (!SymGetLineFromAddr64 (hProcess, st.AddrPC.Offset, 0, &vectLines[i]))
{
cout << "Issue with Getting Line from Address " << ::GetLastError() << endl;
break;
}
cout << vectSymbs[i].Name << " at " << vectLines[i].LineNumber <<endl;
}
if (st.AddrReturn.Offset == 0)
{
cout << "seems finished " << endl;
break;
}
}
return 1;
}
The pdwDisplacement parameter is not optional:
DWORD dis;
if (!SymGetLineFromAddr64 (hProcess, st.AddrPC.Offset, &dis, &vectLines[i]))
{
cout << "Issue with Getting Line from Address " << ::GetLastError() << endl;
break;
}
I had the same problem. My symbols were on a symbol server. The solution was to put symsrv.dll (from the Windows SDK) next to dbghelp.dll, so it can be loaded. Everything worked after that. In practice, the solution was to distribute both dbghelp.dll and symsrv.dll with my application (together with dbgcore.dll and srcsrv.dll). See the Modules list in Visual Studio, to verify that both symsrv.dll and dbghelp.dll are being loaded from where you expect.
More info here:
https://learn.microsoft.com/en-us/windows/desktop/Debug/using-symsrv
(See "Installation" section)
https://learn.microsoft.com/en-us/windows/desktop/Debug/dbghelp-versions (regarding obtaining and distributing those dlls)
I am trying to do some dll injection. I think I tried everything I could but cound not solve the problem unfortunately. I always get ERROR CODE 127 which means ERROR_PROC_NOT_FOUND. I am using Windows 7 64 bit.
#include <iostream>
#include <Windows.h>
#include <TlHelp32.h>
using namespace std;
char FileToInject[] = "theDll.dll";
char ProcessName[] = "calc.exe";
typedef HINSTANCE (*fpLoadLibrary)(char*);
bool InjectDLL(DWORD processId);
int main() {
DWORD processId = NULL;
PROCESSENTRY32 pre32 = {sizeof(PROCESSENTRY32)};
HANDLE hProcSnap;
cout << "BEFORECreateToolhelo32Snapshot:" << GetLastError() <<endl;
while(!processId) {
system("CLS");
cout << "Searching..." << endl;
hProcSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
cout << "CreateToolhelo32Snapshot:" << GetLastError() <<endl;
if(Process32First(hProcSnap, &pre32)) {
do {
if(!(strcmp(pre32.szExeFile, ProcessName))) {
processId = pre32.th32ProcessID;
break;
}
}
while(Process32Next(hProcSnap, &pre32));
}
Sleep(1000);
}
cout << GetLastError() <<endl;
while(!InjectDLL(processId)) {
cout << "DLL Injection failed" << endl;
Sleep(1000);
}
cout << "DLL Injected successfully" << endl;
getchar();
CloseHandle(hProcSnap);
return 0;
}
bool InjectDLL(DWORD processId) {
HANDLE hProc;
LPVOID paramAddr;
cout << "START:" << GetLastError() <<endl;
HINSTANCE hDll = LoadLibrary("KERNEL32");
cout << "LoadLibrary:" << GetLastError() <<endl;
fpLoadLibrary LoadLibraryAddr = (fpLoadLibrary)GetProcAddress(hDll, "LibraryLoadA");
cout << "LoadLibraryArr:" << GetLastError() <<endl;
hProc = OpenProcess(PROCESS_ALL_ACCESS, false, processId);
cout << "OpenProcess:" << GetLastError() <<endl;
char DllPath[250] = "C:\\Hacks\test.dll";
paramAddr = VirtualAllocEx(hProc, 0, strlen(DllPath) + 1, MEM_COMMIT, PAGE_READWRITE);
cout << "VirtualAlloxEx:" <<GetLastError() <<endl;
bool MemoryWritten = WriteProcessMemory(hProc, paramAddr, DllPath, strlen(DllPath) + 1, NULL);
cout << "WriteProcessMemory:" << GetLastError() <<endl;
CreateRemoteThread(hProc, 0, 0, (LPTHREAD_START_ROUTINE)LoadLibraryAddr, paramAddr, 0, 0);
cout << "CreateRemoteThread:" <<GetLastError() <<endl;
CloseHandle(hProc);
return MemoryWritten;
}
The output is the following:
Searching...
CreateToolhelp32Snapshot: 18 ERROR_NO_MORE_FILES
LoadLibrary:18 ERROR_NO_MORE_FILES
LoadLibraryArr:127 ERROR_PROC_NOT_FOUND
OpenProcess:127 ERROR_PROC_NOT_FOUND
VirtualAlloxEx:127 ERROR_PROC_NOT_FOUND
WriteProcessMemory:127 ERROR_PROC_NOT_FOUND
CreateRemoteThread:5 ACCESS DENIED
DLL Injected successfully
The program finds the calc.exe as a process with no problem, but after that something goes wrong. Could someone please help me with this?
Thank you,
Tamas
This is one problem:
char DllPath[250] = "C:\\Hacks\test.dll";
The last backslash is not escaped. Change to:
char DllPath[250] = "C:\\Hacks\\test.dll";
The function is called LoadLibraryA(), not LibraryLoadA():
fpLoadLibrary LoadLibraryAddr =
(fpLoadLibrary)GetProcAddress(hDll, "LibraryLoadA");
A few other suggestions:
Only check GetLastError() if the previous WINAPI function failed.
Only continue processing if the previous WINAPI code (or other code) succeeded.
In
fpLoadLibrary LoadLibraryAddr = (fpLoadLibrary)GetProcAddress(hDll, "LibraryLoadA");
you should rather resolve the string LoadLibraryA. The
OpenProcess:127 ERROR_PROC_NOT_FOUND
VirtualAlloxEx:127 ERROR_PROC_NOT_FOUND (<-- sic)
WriteProcessMemory:127 ERROR_PROC_NOT_FOUND
errors are caused because you're using GetLastError even though these functions maybe didn't even fail. So before calling GetLastError, make sure that these functions yield an error return value (NULL or the like).