在另一个进程中注入dll已经横空出世,但仍然需要在这个dll中调用该函数,如何实现呢? 但更具体地说,在注入过程之后,我需要调用setHWND函数来发送值,从我的应用程序到注入过程...
切片dll
procedure Init(Reason: integer);
begin
Dll_reason := Reason;
HookPoint_Address := 0;
if (Reason = DLL_PROCESS_ATTACH) then
begin
ShowMessage('Прикрепились');
InitHook;
end;
end;
procedure setHWND(hwnd: Cardinal);
begin
hwnd_param:=hwnd;
end;
exports
setHWND;
begin
DLLProc := Init;
Init(DLL_PROCESS_ATTACH);
切片注射器
function InjectDLL(dwPID: DWORD; DLLPath: PWideChar): integer;
var
dwThreadID: Cardinal;
hProc, hThread, hKernel: THandle;
BytesToWrite, BytesWritten: SIZE_T;
pRemoteBuffer, pLoadLibrary: Pointer;
begin
hProc := OpenProcess(PROCESS_CREATE_THREAD or PROCESS_QUERY_INFORMATION or
PROCESS_VM_OPERATION or PROCESS_VM_WRITE or PROCESS_VM_READ, False, dwPID);
if hProc = 0 then
exit(0);
try
BytesToWrite := SizeOf(WideChar) * (Length(DLLPath) + 1);
pRemoteBuffer := VirtualAllocEx(hProc, nil, BytesToWrite, MEM_COMMIT,
PAGE_READWRITE);
if pRemoteBuffer = nil then
exit(0);
try
if not WriteProcessMemory(hProc, pRemoteBuffer, DLLPath, BytesToWrite,
BytesWritten) then
exit(0);
hKernel := GetModuleHandle('kernel32.dll');
pLoadLibrary := GetProcAddress(hKernel, 'LoadLibraryW');
hThread := CreateRemoteThread(hProc, nil, 0, pLoadLibrary, pRemoteBuffer,
0, dwThreadID);
try
WaitForSingleObject(hThread, INFINITE);
finally
CloseHandle(hThread);
end;
finally
VirtualFreeEx(hProc, pRemoteBuffer, 0, MEM_RELEASE);
end;
finally
CloseHandle(hProc);
end;
exit(1);
end;
procedure TForm1.Button1Click(Sender: TObject);
var
PID: DWORD;
dir: string;
begin
SetSeDebugPrivilege;
PID := GetPID('zorron.exe');
if (PID > 0) then
begin
dir := GetCurrentDir;
InjectDLL(PID, PWideChar(dir + '\trans.dll'));
end;
end;
THX
答案 0 :(得分:0)
正如旧/新事物中所解释的那样。你不能在DllMain功能中做真正的工作 如果您执行此操作并且在DllMain忙碌时应用程序停止,应用程序将会死锁 DllMain中的许多其他活动也可能导致死锁,请参阅:https://msdn.microsoft.com/en-us/library/windows/desktop/dn633971%28v=vs.85%29.aspx
这就是为什么你要创建一个新主题使用CreateThread
只记得不同步你的线程,因为这会导致死锁。只要你不同步,你就是金。
注入dll之后,就会启动一个新线程,如下所示:
procedure DoWorkInDLL(data: pointer): bool; stdcall;
begin
...
end;
procedure EntryPoint(Reason: dword);
var
ThreadID: cardinal;
begin
if Reason = DLL_PROCESS_ATTACH then begin
Win32Check(CreateThread(nil,0, @Main, nil, 0, ThreadId));
end;
Assert(ThreadID <> 0);
end;
begin
DLLProc:= @EntryPoint;
EntryPoint(DLL_PROCESS_ATTACH);
end.
我现在的文档所以不要使用CreateThread
,但实际上只是同步问题才是问题。
这里的问题是通常应用程序启动dll,但是当你注入一个dll时,情况绝对不是这样,因此你必须调整你的参考点。
在DoWork
函数内部,您可以调用SetHWnd
,因为您现在已经脱离了dll加载和死锁的风险,但是您仍然无法在线程内调用同步。
如果要进行同步,则必须创建另一个线程并在那里进行同步。
答案 1 :(得分:0)
如果需要导出setHWND(),请确保使用stdcall指令
procedure setHWND(hwnd: Cardinal); stdcall;
begin
hwnd_param:=hwnd;
end;
使用Windows调用约定。