2016-02-13 43 views
0

注入DLL調用過程已翻了出來,但仍需要調用函數在此DLL中,如何實現呢? 但更特別的,在這個過程中注入後,我要打電話去送價值setHWND功能,從我的應用程序注入的工藝......進樣DLL,並從另一個進程這個dll

片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

+1

不要在DllMain中顯示UI。調用CreateThread並在那裏完成工作。 –

+0

我,米需要從主應用程序呼叫setHWND – SEModer

+0

那麼,那樣做。但不是來自DllMain。正如文檔所涵蓋。在DllMain中調用CreateThread來完成這項工作。 –

回答

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加載和死鎖的風險分離,但是您仍然無法打電話給你的線程內同步。
如果你想同步,你將不得不創建另一個線程並在那裏同步。

0

如果您需要導出setHWND(),請確保您使用STDCALL指令

procedure setHWND(hwnd: Cardinal); stdcall; 
begin 
hwnd_param:=hwnd; 
end; 

利用的Windows調用約定。